electroscat, похоже я ошибался, отличия в отношении рестарта между некоторыми эмуляторами и реалом есть, хотя пока не ясно, влияет ли это на визуальные эффекты или хотя бы некоторые из них.
Вид для печати
electroscat, похоже я ошибался, отличия в отношении рестарта между некоторыми эмуляторами и реалом есть, хотя пока не ясно, влияет ли это на визуальные эффекты или хотя бы некоторые из них.
Прошу простить мне мою назойливость, но очень хочется понять.... Помогите пожалуйста...
Я сравнил код системы mdos31h.com с базиса и патченной системы mdos31hp2.rom от ivagor, изменения внес в таблицу:
И не могу понять вообще соответствия... Изменены байты которых нету в опубликованном вами коде, количество измененных байт разное... В общем, мне хочется верить что вы не колдуны какие то, но разум такая штука, он все что по полкам не может разложить, считает каким то колдовством :D Помогите разобраться хоть немного....
electroscat, упоминавшийся инициализатор доса распихивает байты в нужные места.
1. Базисная версия записывала F7 по адресу 0000, я заменил записываемый байт на 01 и адрес на 0003, отсюда две первые строки сравнения.
2. Раньше фрагмент кода обработки rst пересылался по адресу 0030, теперь с адреса 0008, отсюда третья строка.
3. После пересылки патча был переход по адресу 0103, теперь нужно еще кое-что сделать, поэтому переход на 02B1, отсюда 4 и 5 строки.
4. Строки 6-8 для записи байта 01 по адресу 0000.
5. Строки 9-12 для перехода по адресу 0103.
6. Последняя строка пропатчена, чтобы байт C3 не переписал 01 по адресу 0000.
Чтобы было понятнее надо трассировать в отладчике.
Спасибо за ответ !!!
То есть есть часть кода, которая формирует из загруженного массива операционную систему, так ?
И это конфигуратор, вы патчите его, чтобы он формировал систему в памяти так как нужно...
Полегчало ))) А конфигуратор, судя по всему находится с адреса 110H по 1B0H (в базисной версии) или по 1B8H в патченой, по крайней мере конфигуратор области с 0000H по 0100H.... ?
В целом, если разобрать его код, наверняка станет понятнее, буду пробовать. Благодарю за пояснение !!!
electroscat, для большего понимания (или запутывания) работы инициализатора могу привести его дизассемблированный код:
Это всё получено из файла с Базиса, большие части файла, состоящие из наборов данных (DB...) из текста я просто вырезал, их я дизассемблирвал только частично, в отличие от Т-34 и Т-72, приведённых тут ранее. При необходимости можете посмотреть и восстановить их из исходного файла mdos31h.com...mdos31h.asm
Код:ORG 00100h
L_0100: JMP L_0210
;---------------------
L_0103: LHLD L_0201 ; загрузить в HL данные с адреса L_0201 (= 2000h)
MOV B, H
MOV C, L ; в BC -- сколько
LDA 00002h ; в А из памяти с адр.00002h
SUB B ; вычесть B из А
MOV D, A
MVI E, 000h ; в DE -- куда
PUSH D
PUSH B
PUSH D
LXI H, L_0300 ; откуда
L_0115: MOV A, B
ORA C
JZ L_0122
DCX B
MOV A, M ; считать по адресу в HL
STAX D ; записать по адресу в DE
INX D
INX H
JMP L_0115
;
L_0122: POP D
POP B
PUSH H
MOV H, D
DCR H
L_0127: MOV A, B
ORA C
JZ L_0145 ; ---------->>>>>>>>
DCX B
MOV A, E
ANI 007h
JNZ L_0138
XTHL
MOV A, M ; ?????? (02300h...026FFh)
INX H
XTHL
MOV L, A
L_0138: MOV A, L
RAL
MOV L, A
JNC L_0141
LDAX D
ADD H
STAX D
L_0141: INX D
JMP L_0127
;
L_0145: POP H
RET ; ==============>>>>>>>>>>>>>>> запуск (0B500h)
; --- вырезано цензурой --------------------------------------------
L_0200: db 000h ; <_> - | | (offset 0100h)
L_0201: db 000h ; <_> - | | (offset 0101h)
db 020h ; < > - | ■ | (offset 0102h)
; --- вырезано цензурой --------------------------------------------
;
L_0210: DI
LXI SP,0100h ; стек == 0100h
LXI H, 0D00h ; сколько
LXI D, L_2700 ; откуда
LXI B, 0F300h ; куда
CALL L_02A6 ; переброска данных
CALL 0F800h ; вызов START BIOS (в т.ч. включение КД)
PUSH H ; ??? -- он и так сохранится...
MVI A, 0C0h
LXI B, 0A020h
MVI B, 0A0h ; почему не LXI B,0A020h ???
MVI C, 020h
;;; LXI B, 0A020h
L_022A: MVI D, 008h ; от HL=0EF00h до HL=0F100h
L_022C: MOV M, A ; заполняем "C0 A0...", "C1 A1...", ...
INX H
MOV M, B
INX H
DCR D
JNZ L_022C
INR A
INR B
DCR C
JNZ L_022A
POP H ; восстанавливаем HL (0EF00h)
LXI B, 00200h
DAD B ; HL = HL+DE = 0F100h
MVI A, 080h
MVI C, 000h
L_0243: MOV M, A ; от HL=0F100h до HL=0F300h
INX H ; заполняем строки "80 80 40 40 ... 01 01"
MOV M, A
INX H
RRC
DCR C
JNZ L_0243
MVI C, 01Bh ; символ очистки экрана
CALL 0F809h ;-BIOS-(вывод символа)----->>>>>>>>>>
MVI C, 045h ; установка латинской клавиатуры
CALL 0F809h ;-BIOS-(вывод символа)----->>>>>>>>>>
LXI H, 128Eh ; сколько
LXI D, L_3400 ; откуда
LXI B, 0D800h ; куда
CALL L_02A6 ; переброска данных (часть 2)
CALL L_468E ; инициализация НЖМД
LXI H, 0D500h ;
SHLD 00001h ; заносим 00 по адресу 0001 и 0D5h по адресу 0002
MVI A, 0F7h
STA 00000h ; заносим RST 6 по адресу 0000
LXI D, L_029E ; откуда
LXI B, 00030h ; куда
LXI H, 00008h ; сколько
CALL L_02A6 ; переброска данных (для RST 6)
IN 001h
ANI 040h ; нажата клавиша УС?
CZ 0D81Bh ; форматнуть КД
MVI A, 081h
OUT 004h
MVI A, 0FFh
OUT 005h
OUT 006h
MVI A, 00Dh
OUT 007h
MVI A, 0EFh
OUT 005h
MVI A, 0FFh
OUT 005h
OUT 007h
JMP L_0103
;
L_029E: db 03Eh ; <>> - | ■■■■■ | (offset 019Eh) (для RST)
db 023h ; <#> - | ■ ■■| (offset 019Fh)
db 0D3h ; <╙> - |■■ ■ ■■| (offset 01A0h)
db 010h ; <_> - | ■ | (offset 01A1h)
db 02Ah ; <*> - | ■ ■ ■ | (offset 01A2h)
db 001h ; <_> - | ■| (offset 01A3h)
db 000h ; <_> - | | (offset 01A4h)
db 0E9h ; <щ> - |■■■ ■ ■| (offset 01A5h)
;
L_02A6: LDAX D ; ПП переброски данных
STAX B
INX D
INX B
DCX H
MOV A, L
ORA H
JNZ L_02A6
RET
;
; --- вырезано цензурой --------------------------------------------
L_0300: db 021h ; <!> - | ■ ■| (offset 0200h)
; --- вырезано цензурой --------------------------------------------
L_0D00: db 00Dh ; <_> - | ■■ ■| (offset 0C00h)
db 03Ah ; <:> - | ■■■ ■ | (offset 0C01h)
; --- вырезано цензурой --------------------------------------------
db 000h ; <_> - | | (offset 21FFh)
;
db 020h ; < > - | ■ | (offset 2200h)
db 002h ; <_> - | ■ | (offset 2201h)
; --- вырезано цензурой --------------------------------------------
db 000h ; <_> - | | (offset 25FEh)
db 000h ; <_> - | | (offset 25FFh)
;
L_2700: db 000h ;(offset 2600h) BIOS >>> F300h
;==== вырезано цензурой =============================================
;
L_3400: db 0C3h ;(offset 3300h) часть 2 >>> D800h
;==== вырезано цензурой =============================================
;
L_468E: XRA A
STA 0E86Fh ; дорожка, =0
MVI A, 0FFh
STA 0E86Dh ; сектор, =-1 (FFh)
CALL 0D82Dh ; ---------->>>>>>>>>>>> грузит сектор в EB00-ED00
JNZ L_468E
LDA 0EB80h ; читает из буфера EB00-ED00 количество секторов
MOV L, A
MVI H, 000h
PUSH H ; (в стек сектора)
SHLD 0D88Dh ; -- сохр. количество секторов НЖМД
CALL L_46CD ; HL = -(HL * 10h) + 1
SHLD 0D887h ; -- патч драйвера НЖМД
POP D ; (сектора из стека)
LXI H, 00000h
LDA 0EB81h ; читает из буфера EB00-ED00 количество головок
L_46B4: DAD D
DCR A
JNZ L_46B4 ; HL = секторов * головок
SHLD 0D8FAh ; -- патч драйвера НЖМД
CALL L_46CD ; HL = -(HL * 10h) + 1
SHLD 0D8F4h ; -- патч драйвера НЖМД
LHLD 0EB84h ; читает из буфера EB00-ED00 количество дискет на НЖМД
CALL L_46D8 ; инверсия HL
DCX H
SHLD 0D920h ; -- патч на максимальное количество дискет НЖМД
RET
;
L_46CD: MVI B, 010h
XCHG
LXI H, 00000h
L_46D3: DAD D
DCR B
JNZ L_46D3
L_46D8: MOV A, H
CMA
MOV H, A
MOV A, L
CMA
MOV L, A
INX H
RET
;
END
[свернуть]
Можно еще добавить, что фрагмент с L_0122 до L_0145 адаптирует дос на рабочие адреса из "перемещаемого" формата.
Решил я поизучать тему "заворота" на жёстких дисках начиная с дискеты №42 (2Bh), на примере MDOS31H. В кратце, никаких новых результатов не было найдено, всё, что обнаружил уже обсуждалось тут в форуме, поэтому прячу под спойлер:
Ничего нового...
1. На количество секторов и количество головок НЖМД отводится по 8 бит, но в расчётах используется формула 1 - (сектора * головки)*10h с сохранением результата в 16 бит, поэтому (сектора * головки) <= 1000h (= 4096), и, соответственно, может быть, например, не больше 16 секторов Х 256 головок, 32х128, 63х65... (По стандарту НЖМД может иметь до 256 головок и до 63 секторов, головки считаются с нулевой, а сектора с первого). По последним данным, есть ограничение (секторов*головок)<256.
2. Количество цилиндров на НЖМД сохраняется в 16 битах (при положенных для стандарта CHS десяти битах), но оно особого значения не имеет и не учитывается, при обращении расчёты ведутся по количеству дискет, секторам и головкам.
3. В БДОС применяется сквозная нумерация секторов (почти как LBA), для этого используется 24 бита, и это даёт максимальный размер диска 8 Гб (при размере сектора 512 байт), после этой границы будет "заворот".
4. Размер дискеты равен 622h (= 1570) секторов, смещение первой на +2 сектора. Первые 8 дорожек дискеты НЖМД системные (8*10 секторов * 512байт = 40960 байт), эта область одна для всех дискет на НЖМД.
5. Максимальное количество целых дискет исходя из п.3 и 4 равно 29BEh = 10686, что укладывается в отведённые 16 бит для хранения их числа, нераспределённый остаток в конце диска до границы в 8 Гб равен 57 секторов или 29184 байта.
6. Обращение к диску в МДОС осуществляется по номеру дорожки и номеру сектора, на оба значения отводится по 8 бит, отсюда ограничение теоретического максимального размера дискеты будет 256*256*128 (размер сектора в МДОС) и равно 8Мб, практически же МДОС видит дискету 164 дорожки * 40 секторов * 128 байт = 839 680 байт.
7. При обращении к НЖМД в БДОС читаются/пишутся по два сектора диска (2*512=1024 байта), что соответствует восьми секторам МДОС (МДОС понимает один размер сектора, 128 байт). БДОС при последовательном чтении копирует данные из буфера в 1кБайт в буфер дисковых операций. При изменении на НЖМД запись данных производится также в размере двух секторов, даже если один из секторов не изменялся.
8. БСВВ (БДОС) выполняется перерасчёт данных полученных от МДОС: лог.номер сектора = 10 * дорожка + 2 * (сектор - 1)/8, что соответствует дискете на 820 кб. Результат сохраняется в 16 бит и потом суммируется с начальным номером сектора дискеты в 24 бит.
9. Максимальное значение дорожки, получаемое БДОС от МикроДОС равно 164 (A4h), при большем значении БДОС возвращает ошибку. Исключение -- можно считать с НЖМД дорожку 0FFh (это нулевой цилиндр с записанной при инициализации конфигурацией).[свернуть]
В общем, могу резюмировать, что никаких особых багов на эту тему в MDOS31H не выявил, диски до 8Гб включительно должны там работать без "заворотов". Есть только предположение, что глюк с "заворотом" может возникать, если прерывание прилетит точно в момент расчёта и передачи на НЖМД номера цилиндра по "OUT 055h" - "OUT 054h", из-за чего там будет большой разрыв по времени и старшие биты обнулятся. Либо, как предполагал ранее, некоторые программы обращаются к функциям БДОС напрямую, при этом сами имеют такой баг.-- Баг найден.
Но есть и положительные моменты, в ходе разборок с НЖМД собрал версию МикроДОС Т-72 с драйвером жёсткого диска, вот архив с новой версией и исходниками, Т-72h: Вложение 72071
Отличия от предыдущей версии:
- Добавлена команда "9" -- выбор дискеты жёсткого диска (работает аналогично mdos31h).
- Из-за нехватки памяти убран драйвер для флоповодов (думаю, его следует вернуть, но для этого понадобится немного подвинуть МДОС, да и сам драйвер надо будет немного переделать). Сейчас при обращении к флопикам просто выдаётся ошибка.
Добавленный драйвер НЖМД, по сравнению с mdos31h, существенно переработан, а именно:
- Добавил запрет прерываний на время записи конфигурации НЖМД, посмотрим, как устранит это глюк с заворотом...
- Размер буфера драйвера уменьшил до одного физического сектора НЖМД, т.е. до 512 Байт.
- Исправил проблему с линией "RESET" на IDE, из-за чего приходилось отключать вывод 1 у жёсткого диска. Теперь тормозов нет, даже если он подключён.
Погонял новую версию МДОСа на эмуляторе и на своём реальном Векторе, работает хорошо и с одним, и с двумя квази-дисками. :-) В новой версии по тестам копирование файлов с одной дискеты НЖМД на другую выполняется раза в полтора быстрее, замерял и по тактам (в эмуляторе), и по времени. Единственный ньюанс: программа FDIR не работает, подвисает до сброса. Надо будет как-нибудь сделать ей замену, уж больно глючна...
Improver, это здорово, но пока проблема с заворотом осталась, по крайней мере у меня. До дискеты 2A включительно все нормально, начиная с 2B - заворот.
Может что-то с параметрами hdd, вот строка из конфига emu
drive[0].geometry=255C16H18S
Или проблема с командой 1 доса, которой я пишу файл