Документация по формату MSF (черновик).
Формат файла .MSF версии 2.3 (Memory state file) для эмулятора БК 0010(01) и БК 0011(М)
Файлы данного формата обычно хранят в себе полный слепок всей памяти БК на момент сохранения, состояние регистров, уменьшенную копию экрана, фрагмент файла конфигурации с текущими настройками и опциями, а также любую другую информацию, необходимую для последующего восстановления работы. Формат является бинарным, и представляет собой теговую структуру. Каждый тег представляет собой заголовок, и данные некоторого типа. Теги могут располагаться в любом порядке (кроме первого заголовочного тега MSF_FILE_HEADER), а также быть вложенными один в другой (но на практике оказалось, что в этом нет необходимости, незачем переусложнять). Теоретически любой из тегов, являющийся не критически важным, может быть пропущен, а также могут присутствовать теги, которые незнакомы эмулятору данной версии, и будут без проблем пропущены. Таким образом, теоретически осуществляется совместимость форматов разных версий в обе стороны.
Но практически - нет. MSF младших версий не поддерживается из-за того, что там нет критически важных блоков, без которых невозможно восстановить состояние эмулятора. И соответственно, невозможна дальнейшая эмуляция.
Формат 2.x принципиально не совместим с форматом 1.9 из-за полной переделки принципа эмуляции и внутреннего устройства данных эмулируемых устройств. Без проблем понимаются только tap файлы, которые к тому же умышленно сохраняются в старом формате, чтобы было можно использовать их и в старых версиях эмулятора.
Описание структуры
Файл – это последовательность тегов, с выравниванием по байту.
|
Тег заголовка |
Тег 1 |
Тег 2 |
… |
Тег N |
Формат тега заголовка
|
Тип |
Имя |
Размер в байтах |
Описание |
|---|---|---|---|
|
uint32_t |
type |
4 |
Тип MSF файла. Идентификатор (сигнатура), всегда 65536 |
|
uint32_t |
version |
4 |
Версия MSF файла. В настоящее время 21 |
|
uint32_t |
reserved |
4 |
Зарезервировано для обратной совместимости с файлами версии 1.9, всегда 0 |
Формат тегов данных
Заголовок тега бывает обычный, и расширенный. Определяется по типу тега.
Обычный заголовок.
|
Тип |
Имя |
Размер в байтах |
Описание |
|---|---|---|---|
|
uint32_t |
type |
4 |
Тип блока (тега) |
|
uint32_t |
length |
4 |
размер блока = размер этого заголовка + размер данных |
|
uint8_t |
|
N |
Массив данных. |
Расширенный заголовок.
|
Тип |
Имя |
Размер в байтах |
Описание |
|---|---|---|---|
|
uint32_t |
type |
4 |
Тип блока (тега) |
|
uint32_t |
length |
4 |
размер блока = размер этого заголовка + размер данных |
|
uint32_t |
id |
4 |
идентификатор устройства, которому принадлежит блок данных |
|
uint32_t |
flags |
4 |
Флаги, обозначающие разные режимы обработки. На данный момент существует всего один флаг. MSF_EX_FLAG_COMPRESSED = 1 Обозначает, что данные в блоке сжаты алгоритмом LZW. Тем же, что используется в tap файлах. |
|
uint32_t |
unpSize |
4 |
Размер не сжатых данных, чтобы можно было без проблем расжимать архив. |
|
uint8_t |
|
N |
Массив данных. |
Типы тегов
|
Имя |
Значение |
Описание |
|---|---|---|
|
MSF_BLOCKTYPE::UNKNOWN |
-1 |
Не используется, предназначен для обработки ошибочных ситуаций |
|
MSF_BLOCKTYPE::BASEMEMORY |
0 |
Содержит полный слепок памяти устройства, включая загруженные дампы ПЗУ. Устарел, не используется, оставлен для совместимости |
|
MSF_BLOCKTYPE::CPU_REGISTERS |
1 |
Содержит значения регистров процессора |
|
MSF_BLOCKTYPE::PREVIEW |
2 |
Содержит малую копию экрана. |
|
MSF_BLOCKTYPE::B10EXT16 |
3 |
Устарел, не используется, оставлен для совместимости |
|
MSF_BLOCKTYPE::B10EXT32 |
4 |
Устарел, не используется, оставлен для совместимости |
|
MSF_BLOCKTYPE::PLATFORM |
5 |
Содержит параметры платформы и описание устройств, из которых состоит конфигурация |
|
MSF_BLOCKTYPE::PORT_REGS |
6 |
Содержит значения регистров и портов устройства. Устарел, не используется, оставлен для совместимости |
|
MSF_BLOCKTYPE::MEMMAP |
7 |
Содержит копию карты памяти. Устарел, не используется, оставлен для совместимости |
|
MSF_BLOCKTYPE::BASEMEMORY11M |
8 |
Устарел, не используется, оставлен для совместимости |
|
MSF_BLOCKTYPE::MEMORY_SMK512 |
9 |
Устарел, не используется, оставлен для совместимости |
|
MSF_BLOCKTYPE::CONFIG |
10 |
Содержит фрагмент ini файла конфигурации с настройками данной платформы. |
|
MSF_BLOCKTYPE::FRAMEDATA |
11 |
Содержит текущие параметры фрейма и внутренние счётчики. |
|
MSF_BLOCKTYPE::WAVE |
200 |
Используется в tap файлах для хранения контента. |
|
Расширенные блоки |
|
|
|
MSF_BLOCKTYPE::BASEMEMORYEX |
0x10000 |
Содержит полный слепок памяти устройства, включая загруженные дампы ПЗУ |
|
MSF_BLOCKTYPE::CPU_REGISTERSEX |
0x10001 |
Содержит значения регистров процессора |
|
MSF_BLOCKTYPE::PREVIEWEX |
0x10002 |
Содержит малую копию экрана. |
|
MSF_BLOCKTYPE::PLACEHOLDER1 |
0x10003 |
Заглушка |
|
MSF_BLOCKTYPE::PLACEHOLDER2 |
0x10004 |
Заглушка |
|
MSF_BLOCKTYPE::PLATFORMEX |
0x10005 |
Содержит параметры платформы и описание устройств, из которых состоит конфигурация |
|
MSF_BLOCKTYPE::PORT_REGSEX |
0x10006 |
Содержит значения регистров и портов устройства |
|
MSF_BLOCKTYPE::MEMMAPEX |
0x10007 |
Содержит копию карты памяти |
|
MSF_BLOCKTYPE::PLACEHOLDER3 |
0x10008 |
Заглушка |
|
MSF_BLOCKTYPE::PLACEHOLDER4 |
0x10009 |
Заглушка |
|
MSF_BLOCKTYPE::CONFIGEX |
0x1000a |
Содержит фрагмент ini файла конфигурации с настройками данной платформы. |
|
MSF_BLOCKTYPE::FRAMEDATAEX |
0x1000b |
Содержит текущие параметры фрейма и внутренние счётчики. |
|
MSF_BLOCKTYPE::CUSTOMEX |
0x1000c |
Содержит различные данные, специфичные для конкретного устройства. |
Несмотря на то, что значения тегов по возможности такие же, как и в старой версии, их содержимое может быть не совместимо с содержимым старой версии.
Теги делятся на две категории: общего назначения и специального назначения. За исключением тега MSF_BLOCKTYPE::WAVE, он используется только для tap файлов и к файлам сохранения отношения не имеет.
Теги общего назначения – это MSF_BLOCKTYPE::PLATFORM[EX], MSF_BLOCKTYPE::PREVIEW[EX], MSF_BLOCKTYPE::CONFIG[EX], MSF_BLOCKTYPE::FRAMEDATA[EX] и MSF_BLOCKTYPE::CPU_REGISTERS[EX]. Эти теги в файле сохранения находятся в одном экземпляре. У всех расширенных тегов этой группы поле id содержит число -1.
Теги специального назначения - MSF_BLOCKTYPE::BASEMEMORYEX, MSF_BLOCKTYPE::PORT_REGSEX, MSF_BLOCKTYPE::MEMMAPEX, MSF_BLOCKTYPE::CUSTOMEX. Эти теги в файле сохранения содержатся для каждого устройства. У всех этих тегов поле id содержит идентификатор устройства, и все теги с одинаковым идентификатором относятся к одному устройству.
Тег MSF_BLOCKTYPE::CUSTOM опциональный, его может и не быть для заданного устройства.
Тег MSF_BLOCKTYPE::PLATFORM[EX]
Самым главным тегом является MSF_BLOCKTYPE::PLATFORM, он содержит информацию о конфигурации устройства и количестве устройств в конфигурации. От этого зависит интерпретация тегов специального назначения. Тег MSF_BLOCKTYPE::PLATFORMEX не используется из-за своей избыточности.
Формат.
|
Тип |
Имя |
Размер в байтах |
Значение / Описание |
|---|---|---|---|
|
uint32_t |
type |
4 |
MSF_BLOCKTYPE::PLATFORM // Тип блока (тега) |
|
uint32_t |
length |
4 |
Размер блока = размер этого заголовка + размер данных |
|
Данные тега, размер 8 + 8 * nDevNum |
|||
|
uint32_t |
nPlatformConfig |
4 |
Номер конфигурации (см enum CONF_BKMODEL в файле Config.h) |
|
uint32_t |
nDevNum |
4 |
Количество устройств в конфигурации |
|
{ |
|
|
|
|
uint32_t |
nBKBoardModel |
4 |
модель устройства (см. enum BK_DEV_MPI BKMODEL в файле Config.h) |
|
uint32_t |
nUniqueID |
4 |
уникальный идентификатор на случай, если будет в списке несколько одинаковых BK_DEV_MPI. Именно этот идентификатор содержится в поле id тегов специального назначения. |
|
} По количеству nDevNum |
|||
Значение уникального идентификатора начинается с числа 256. Для первого устройства – 256, для второго 257 и т.д.
Тег MSF_BLOCKTYPE::PREVIEW[EX]
Этот тег содержит малую копию экрана. Она используется при загрузке файлов сохранения в диалоге их выбора при предпросмотре. Не является обязательным.
Формат.
|
Тип |
Имя |
Размер в байтах |
Значение / Описание |
|---|---|---|---|
|
uint32_t |
type |
4 |
MSF_BLOCKTYPE::PREVIEW // Тип блока (тега) |
|
uint32_t |
length |
4 |
Размер блока = размер этого заголовка + размер данных |
|
Данные тега, размер переменный |
|||
|
структура |
BITMAPINFOHEADER |
40 |
Стандартная структура BITMAPINFOHEADER |
|
массив |
|
Заранее не известно |
Бинарные данные стандартного объекта HBITMAP |
Расширенный формат.
|
Тип |
Имя |
Размер в байтах |
Значение / Описание |
|---|---|---|---|
|
uint32_t |
type |
4 |
MSF_BLOCKTYPE::PREVIEWEX // Тип блока (тега) |
|
uint32_t |
length |
4 |
Размер блока = размер этого заголовка + размер данных |
|
uint32_t |
id |
4 |
-1 // идентификатор устройства, которому принадлежит блок данных |
|
uint32_t |
flags |
4 |
1 // Флаги |
|
uint32_t |
unpSize |
4 |
Размер распакованных данных |
|
Данные тега, размер переменный |
|||
|
структура |
BITMAPINFOHEADER |
40 |
Стандартная структура BITMAPINFOHEADER |
|
массив |
|
Заранее не известно |
Бинарные данные стандартного объекта HBITMAP, сжатые алгоритмом LZW. |
Тег MSF_BLOCKTYPE::CONFIG[EX]
|
Тип |
Имя |
Размер в байтах |
Значение / Описание |
|---|---|---|---|
|
uint32_t |
type |
4 |
MSF_BLOCKTYPE::CONFIG // Тип блока (тега) |
|
uint32_t |
length |
4 |
Размер блока = размер этого заголовка + размер данных |
|
Данные тега, размер переменный |
|||
|
массив |
|
Заранее не известно |
Текст в формате UTF16-LE, содержащий основную часть настроек заданной конфигурации. |
Расширенный формат:
|
Тип |
Имя |
Размер в байтах |
Значение / Описание |
|---|---|---|---|
|
uint32_t |
type |
4 |
MSF_BLOCKTYPE::CONFIGEX // Тип блока (тега) |
|
uint32_t |
length |
4 |
Размер блока = размер этого заголовка + размер данных |
|
uint32_t |
id |
4 |
-1 // идентификатор устройства, которому принадлежит блок данных |
|
uint32_t |
flags |
4 |
1 // Флаги |
|
uint32_t |
unpSize |
4 |
Размер распакованных данных |
|
Данные тега, размер переменный |
|||
|
массив |
|
Заранее не известно |
Текст в формате UTF16-LE, содержащий основную часть настроек заданной конфигурации, сжатый алгоритмом LZW. |
Тег MSF_BLOCKTYPE::FRAMEDATA[EX]
Этот тег содержит текущие параметры фрейма и внутренние счётчики эмуляции экрана и ВЕ-таймера. Тег MSF_BLOCKTYPE::FRAMEDATAEX не используется из-за своей избыточности.
Формат.
|
Тип |
Имя |
Размер в байтах |
Значение / Описание |
|---|---|---|---|
|
uint32_t |
type |
4 |
MSF_BLOCKTYPE::FRAMEDATA // Тип блока (тега) |
|
uint32_t |
length |
4 |
Размер блока = размер этого заголовка + размер данных |
|
Данные тега, размер 8 * 4 + 3 * 8 |
|||
|
|
// состояние ВЕ таймера |
|
|
|
int |
nTimerSpeed |
4 |
текущее значение счётчика ВЕ таймера |
|
int |
nTimerDiv |
4 |
текущий делитель ВЕ таймера |
|
|
// состояние экрана |
|
|
|
int |
nVideoAddress |
4 |
видео адрес, младшие 6 бит - счётчик строк внутри строки |
|
int |
bHgate |
4 |
флаг отсчёта служебных видеоциклов в строке |
|
int |
bVgate |
4 |
флаг отсчёта служебных строк |
|
int |
nVGateCounter |
4 |
дополнительный счётчик служебных строк |
|
int |
nLineCounter |
4 |
счётчик видео строк |
|
|
// состояние фрейма (значения внутренних счётчиков фрейма) |
||
|
int |
nCPUTicks |
4 |
|
|
double |
fMediaTicks |
8 |
|
|
double |
fMemoryTicks |
8 |
|
|
double |
fFDDTicks |
8 |
|
|
double |
fAZVideoTicks |
8 |
|
Тег MSF_BLOCKTYPE::CPU_REGISTERS[EX]
Тег содержит значения регистров общего назначения процессора 1801ВМ1. Тег MSF_BLOCKTYPE::REGISTERSEX не используется из-за своей избыточности.
Формат.
|
Тип |
Имя |
Размер в байтах |
Значение / Описание |
|---|---|---|---|
|
uint32_t |
type |
4 |
MSF_BLOCKTYPE::CPU_REGISTERS // Тип блока (тега) |
|
uint32_t |
length |
4 |
Размер блока = размер этого заголовка + размер данных |
|
Данные тега, размер 2 * 9 |
|||
|
uint16_t |
r0 |
2 |
|
|
uint16_t |
r1 |
2 |
|
|
uint16_t |
r2 |
2 |
|
|
uint16_t |
r3 |
2 |
|
|
uint16_t |
r4 |
2 |
|
|
uint16_t |
r5 |
2 |
|
|
uint16_t |
sp |
2 |
|
|
uint16_t |
pc |
2 |
|
|
uint16_t |
psw |
2 |
|
Тег MSF_BLOCKTYPE::MEMMAPEX
Это очень важный тег специального назначения, для разных устройств содержимое имеет разный размер.
|
Тип |
Имя |
Размер в байтах |
Значение / Описание |
|---|---|---|---|
|
uint32_t |
type |
4 |
MSF_BLOCKTYPE::MEMMAPEX // Тип блока (тега) |
|
uint32_t |
length |
4 |
Размер блока = размер этого заголовка + размер данных |
|
uint32_t |
id |
4 |
идентификатор устройства, которому принадлежит блок данных |
|
uint32_t |
flags |
4 |
0 // Флаги |
|
uint32_t |
unpSize |
4 |
0 // Размер распакованных данных |
|
Данные тега, размер 5*4 * n + 4 |
|||
|
{ |
|
|
|
|
BOOL |
bReadable |
4 |
флаг, что память доступна для чтения |
|
BOOL |
bWritable |
4 |
флаг, что память доступна для записи |
|
uint32_t |
nBank |
4 |
номер банка памяти, размер зависит от конкретного устройства |
|
uint32_t |
nOffset |
4 |
смещение в массиве памяти |
|
int32_t |
nTimingCorrection |
4 |
значение корректировки тайминга при обращении к памяти, которая не управляется ВП1-037 (ПЗУ или ОЗУ СМК) |
|
} по количеству банков памяти у устройства. |
|||
|
uint32_t |
nROMPresent |
4 |
Маска наличия заявленных ПЗУ для устройства. |
По счастливому стечению обстоятельств, количество банков памяти для всех типов устройств одинаковое и равно 8, кроме AZBK, для него – 16.
Маска наличия ПЗУ служит для эмуляции отсутствия заявленного ПЗУ в системе. Например, можно сэмулировать отсутствие ПЗУ Бейсика в БК11(М), или отсутствие ПЗУ Фокала в БК0010 и т.п.
Тег MSF_BLOCKTYPE::BASEMEMORYEX
|
Тип |
Имя |
Размер в байтах |
Значение / Описание |
|---|---|---|---|
|
uint32_t |
type |
4 |
MSF_BLOCKTYPE::BASEMEMORYEX // Тип блока (тега) |
|
uint32_t |
length |
4 |
Размер блока = размер этого заголовка + размер данных |
|
uint32_t |
id |
4 |
идентификатор устройства, которому принадлежит блок данных |
|
uint32_t |
flags |
4 |
1 // Флаги |
|
uint32_t |
unpSize |
4 |
Размер распакованных данных |
|
Данные тега, размер определяется устройством |
|||
|
массив |
|
… |
Полный массив памяти ОЗУ+ПЗУ для заданного устройства. Сжатый алгоритмом LZW |
Для устройства без памяти, тегов MSF_BLOCKTYPE::MEMMAP и MSF_BLOCKTYPE::BASEMEMORY может и не быть.
Тег MSF_BLOCKTYPE::PORT_REGSEX
Содержит значения портов и регистров заданного устройства. Формат зависит от заданного устройства.
Формат для устройств типа BK_BOARD_TYPE_MDL (материнские платы)
|
Тип |
Имя |
Размер в байтах |
Значение / Описание |
|---|---|---|---|
|
uint32_t |
type |
4 |
MSF_BLOCKTYPE::PORT_REGSEX // Тип блока (тега) |
|
uint32_t |
length |
4 |
Размер блока = размер этого заголовка + размер данных |
|
uint32_t |
id |
4 |
идентификатор устройства, которому принадлежит блок данных |
|
uint32_t |
flags |
4 |
0 // Флаги |
|
uint32_t |
unpSize |
4 |
0 // Размер распакованных данных |
|
Данные тега, размер 2 * 15 |
|||
|
uint16_t |
p0177660 |
2 |
Содержимое регистра 177660 |
|
uint16_t |
p0177662_in |
2 |
Содержимое регистра 177662 по чтению |
|
uint16_t |
p0177662_out |
2 |
Содержимое регистра 177662 по записи |
|
uint16_t |
p0177664 |
2 |
Содержимое регистра 177664 |
|
uint16_t |
p0177700 |
2 |
Содержимое регистра 177700 |
|
uint16_t |
p0177702 |
2 |
Содержимое регистра 177702 |
|
uint16_t |
p0177704 |
2 |
Содержимое регистра 177704 |
|
uint16_t |
p0177706 |
2 |
Содержимое регистра 177706 |
|
uint16_t |
p0177710 |
2 |
Содержимое регистра 177710 |
|
uint16_t |
p0177712 |
2 |
Содержимое регистра 177712 |
|
uint16_t |
p0177714_in |
2 |
Содержимое регистра 177714 по чтению |
|
uint16_t |
p0177714_out |
2 |
Содержимое регистра 177714 по записи |
|
uint16_t |
p0177716_in |
2 |
Содержимое регистра 177716 по чтению |
|
uint16_t |
p0177716_out_tap |
2 |
Содержимое регистра 177716 по записи |
|
uint16_t |
p0177716_out_mem |
2 |
Содержимое регистра 177716 управления памятью по записи |
Некоторые регистры излишни, например 177700..177704 не используются и не изменяются, их сохранение сделано на перспективу.
p0177662_out и p0177716_out_mem в конфигурациях БК-0010 не используются, но сохраняются по причине общей процедуры для всех конфигураций материнских плат БК.
Формат для устройства типа AZBK
В качестве данных сохраняются все регистры AZBK, их много, структура большая, поэтому см. описание структуры sAZRegisters_t в файле AZBK.h
Данные тут не приводятся, потому что сам AZBK ещё не имеет окончательного варианта.
Тег MSF_BLOCKTYPE::CUSTOMEX
Этот тег имеет самый многовариантный формат.
|
Тип |
Имя |
Размер в байтах |
Значение / Описание |
|---|---|---|---|
|
uint32_t |
type |
4 |
MSF_BLOCKTYPE::CUSTOMEX // Тип блока (тега) |
|
uint32_t |
length |
4 |
Размер блока = размер этого заголовка + размер данных |
|
uint32_t |
id |
4 |
идентификатор устройства, которому принадлежит блок данных |
|
uint32_t |
flags |
4 |
0 // Флаги |
|
uint32_t |
unpSize |
4 |
0 // Размер распакованных данных |
|
Данные тега, размер переменный |
|||
|
|
|
|
|
Кастомные структуры, которые сохраняются в разных конфигурациях:
BK_DEV_MPI::BK0011, BK_DEV_MPI::BK0011M – структура CustomData_t в файле BK0011M.h
|
bool |
bWnd1Off |
1 |
флаг выключения окна 1 контроллером АльтПро |
BK_DEV_MPI::MSTD10_EXT32 – структура CustomData_t в файле BKMSTD10_EXT32.h
|
int |
nPage |
4 |
номер подключенной страницы в окно |
BK_DEV_MPI::A16M, BK_DEV_MPI::SMK512– структура AltProCtrlData_t в файле Config.h
|
DWORD |
nAltProMemBank |
4 |
код подключения страницы памяти контроллера |
|
DWORD |
nExtCodes |
4 |
доп коды контроллера, типа 10 - подкл. бейсика и 4 - блокировка регистров 177130 и 177132 по чтению |
|
DWORD |
nAltProMode |
4 |
код режима контроллера |
BK_DEV_MPI::SAMARA – структура CustomData_t в файле FDD_Samara.h
|
bool |
b10 |
1 |
флаг, что подключено к БК10 |
BK_DEV_MPI::AZBK – структура sAZCustom_t в файле AZBK.h
Данные тут не приводятся, потому что сам AZBK ещё не имеет окончательного варианта.