Subversion Repositories Kolibri OS

Compare Revisions

Regard whitespace Rev 3538 → Rev 3539

/kernel/trunk/blkdev/cd_drv.inc
9,21 → 9,21
 
 
;**********************************************************
; Íåïîñðåäñòâåííàÿ ðàáîòà ñ óñòðîéñòâîì ÑD (ATAPI)
; Непосредственная работа с устройством СD (ATAPI)
;**********************************************************
; Àâòîð ÷àñòè èñõîäíîãî òåêñòà Êóëàêîâ Âëàäèìèð Ãåííàäüåâè÷
; Àäàïòàöèÿ, äîðàáîòêà è ðàçðàáîòêà Mario79,<Lrz>
; Автор части исходного текста Кулаков Владимир Геннадьевич
; Адаптация, доработка и разработка Mario79,<Lrz>
 
; Ìàêñèìàëüíîå êîëè÷åñòâî ïîâòîðåíèé îïåðàöèè ÷òåíèÿ
; Максимальное количество повторений операции чтения
MaxRetr equ 10
; Ïðåäåëüíîå âðåìÿ îæèäàíèÿ ãîòîâíîñòè ê ïðèåìó êîìàíäû
; (â òèêàõ)
; Предельное время ожидания готовности к приему команды
; (в тиках)
BSYWaitTime equ 1000 ;2
NoTickWaitTime equ 0xfffff
CDBlockSize equ 2048
;********************************************
;* ×ÒÅÍÈÅ ÑÅÊÒÎÐÀ Ñ ÏÎÂÒÎÐÀÌÈ *
;* Ìíîãîêðàòíîå ïîâòîðåíèå ÷òåíèÿ ïðè ñáîÿõ *
;* ЧТЕНИЕ СЕКТОРА С ПОВТОРАМИ *
;* Многократное повторение чтения при сбоях *
;********************************************
ReadCDWRetr:
;-----------------------------------------------------------
85,34 → 85,34
ReadCDWRetr_1:
pushad
 
; Öèêë, ïîêà êîìàíäà íå âûïîëíåíà óñïåøíî èëè íå
; èñ÷åðïàíî êîëè÷åñòâî ïîïûòîê
; Цикл, пока команда не выполнена успешно или не
; исчерпано количество попыток
mov ECX, MaxRetr
@@NextRetr:
; Ïîäàòü êîìàíäó
; Подать команду
;*************************************************
;* ÏÎËÍÎÅ ×ÒÅÍÈÅ ÑÅÊÒÎÐÀ ÊÎÌÏÀÊÒ-ÄÈÑÊÀ *
;* Ñ÷èòûâàþòñÿ äàííûå ïîëüçîâàòåëÿ, èíôîðìàöèÿ *
;* ñóáêàíàëà è êîíòðîëüíàÿ èíôîðìàöèÿ *
;* Âõîäíûå ïàðàìåòðû ïåðåäàþòñÿ ÷åðåç ãëîáàëüíûå *
;* ïåðìåííûå: *
;* ChannelNumber - íîìåð êàíàëà; *
;* DiskNumber - íîìåð äèñêà íà êàíàëå; *
;* CDSectorAddress - àäðåñ ñ÷èòûâàåìîãî ñåêòîðà. *
;* Äàííûå ñ÷èòûâàåòñÿ â ìàññèâ CDDataBuf. *
;* ПОЛНОЕ ЧТЕНИЕ СЕКТОРА КОМПАКТ-ДИСКА *
;* Считываются данные пользователя, информация *
;* субканала и контрольная информация *
;* Входные параметры передаются через глобальные *
;* перменные: *
;* ChannelNumber - номер канала; *
;* DiskNumber - номер диска на канале; *
;* CDSectorAddress - адрес считываемого сектора. *
;* Данные считывается в массив CDDataBuf. *
;*************************************************
;ReadCD:
push ecx
; pusha
; Çàäàòü ðàçìåð ñåêòîðà
; Задать размер сектора
; mov [CDBlockSize],2048 ;2352
; Î÷èñòèòü áóôåð ïàêåòíîé êîìàíäû
; Очистить буфер пакетной команды
call clear_packet_buffer
; Ñôîðìèðîâàòü ïàêåòíóþ êîìàíäó äëÿ ñ÷èòûâàíèÿ
; ñåêòîðà äàííûõ
; Çàäàòü êîä êîìàíäû Read CD
; Сформировать пакетную команду для считывания
; сектора данных
; Задать код команды Read CD
mov [PacketCommand], byte 0x28;0xBE
; Çàäàòü àäðåñ ñåêòîðà
; Задать адрес сектора
mov AX, word [CDSectorAddress+2]
xchg AL, AH
mov word [PacketCommand+2], AX
121,11 → 121,11
mov word [PacketCommand+4], AX
; mov eax,[CDSectorAddress]
; mov [PacketCommand+2],eax
; Çàäàòü êîëè÷åñòâî ñ÷èòûâàåìûõ ñåêòîðîâ
; Задать количество считываемых секторов
mov [PacketCommand+8], byte 1
; Çàäàòü ñ÷èòûâàíèå äàííûõ â ïîëíîì îáúåìå
; Задать считывание данных в полном объеме
; mov [PacketCommand+9],byte 0xF8
; Ïîäàòü êîìàíäó
; Подать команду
call SendPacketDatCommand
pop ecx
; ret
147,7 → 147,7
jz @@NextRetr
jmp .wait
@@:
; Çàäåðæêà íà 2,5 ñåêóíäû
; Задержка на 2,5 секунды
; mov EAX,[timer_ticks]
; add EAX,50 ;250
;@@Wait:
161,53 → 161,53
ret
 
 
; Óíèâåðñàëüíûå ïðîöåäóðû, îáåñïå÷èâàþùèå âûïîëíåíèå
; ïàêåòíûõ êîìàíä â ðåæèìå PIO
; Универсальные процедуры, обеспечивающие выполнение
; пакетных команд в режиме PIO
 
; Ìàêñèìàëüíî äîïóñòèìîå âðåìÿ îæèäàíèÿ ðåàêöèè
; óñòðîéñòâà íà ïàêåòíóþ êîìàíäó (â òèêàõ)
; Максимально допустимое время ожидания реакции
; устройства на пакетную команду (в тиках)
 
MaxCDWaitTime equ 1000 ;200 ;10 ñåêóíä
MaxCDWaitTime equ 1000 ;200 ;10 секунд
uglobal
; Îáëàñòü ïàìÿòè äëÿ ôîðìèðîâàíèÿ ïàêåòíîé êîìàíäû
; Область памяти для формирования пакетной команды
PacketCommand:
rb 12 ;DB 12 DUP (?)
; Îáëàñòü ïàìÿòè äëÿ ïðèåìà äàííûõ îò äèñêîâîäà
; Область памяти для приема данных от дисковода
;CDDataBuf DB 4096 DUP (0)
; Ðàçìåð ïðèíèìàåìîãî áëîêà äàííûõ â áàéòàõ
; Размер принимаемого блока данных в байтах
;CDBlockSize DW ?
; Àäðåñ ñ÷èòûâàåìîãî ñåêòîðà äàííûõ
; Адрес считываемого сектора данных
CDSectorAddress:
DD ?
; Âðåìÿ íà÷àëà î÷åðåäíîé îïåðàöèè ñ äèñêîì
; Время начала очередной операции с диском
TickCounter_1 DD 0
; Âðåìÿ íà÷àëà îæèäàíèÿ ãîòîâíîñòè óñòðîéñòâà
; Время начала ожидания готовности устройства
WURStartTime DD 0
; óêàçàòåëü áóôåðà äëÿ ñ÷èòûâàíèÿ
; указатель буфера для считывания
CDDataBuf_pointer dd 0
endg
;****************************************************
;* ÏÎÑËÀÒÜ ÓÑÒÐÎÉÑÒÂÓ ATAPI ÏÀÊÅÒÍÓÞ ÊÎÌÀÍÄÓ, *
;* ÏÐÅÄÓÑÌÀÒÐÈÂÀÞÙÓÞ ÏÅÐÅÄÀ×Ó ÎÄÍÎÃÎ ÑÅÊÒÎÐÀ ÄÀÍÍÛÕ *
;* ÐÀÇÌÅÐÎÌ 2048 ÁÀÉÒ ÎÒ ÓÑÒÐÎÉÑÒÂÀ Ê ÕÎÑÒÓ *
;* Âõîäíûå ïàðàìåòðû ïåðåäàþòñÿ ÷åðåç ãëîáàëüíûå *
;* ïåðìåííûå: *
;* ChannelNumber - íîìåð êàíàëà; *
;* DiskNumber - íîìåð äèñêà íà êàíàëå; *
;* PacketCommand - 12-áàéòíûé êîìàíäíûé ïàêåò; *
;* CDBlockSize - ðàçìåð ïðèíèìàåìîãî áëîêà äàííûõ. *
;* ПОСЛАТЬ УСТРОЙСТВУ ATAPI ПАКЕТНУЮ КОМАНДУ, *
;* ПРЕДУСМАТРИВАЮЩУЮ ПЕРЕДАЧУ ОДНОГО СЕКТОРА ДАННЫХ *
;* РАЗМЕРОМ 2048 БАЙТ ОТ УСТРОЙСТВА К ХОСТУ *
;* Входные параметры передаются через глобальные *
;* перменные: *
;* ChannelNumber - номер канала; *
;* DiskNumber - номер диска на канале; *
;* PacketCommand - 12-байтный командный пакет; *
;* CDBlockSize - размер принимаемого блока данных. *
; return eax DevErrorCode
;****************************************************
SendPacketDatCommand:
xor eax, eax
; mov byte [DevErrorCode],al
; Çàäàòü ðåæèì CHS
; Задать режим CHS
mov byte [ATAAddressMode], al
; Ïîñëàòü ATA-êîìàíäó ïåðåäà÷è ïàêåòíîé êîìàíäû
; Послать ATA-команду передачи пакетной команды
mov byte [ATAFeatures], al
mov byte [ATASectorCount], al
mov byte [ATASectorNumber], al
; Çàãðóçèòü ðàçìåð ïåðåäàâàåìîãî áëîêà
; Загрузить размер передаваемого блока
mov [ATAHead], al
; mov AX,[CDBlockSize]
mov [ATACylinder], CDBlockSize
214,13 → 214,13
mov [ATACommand], 0A0h
call SendCommandToHDD_1
test eax, eax
; cmp [DevErrorCode],0 ;ïðîâåðèòü êîä îøèáêè
jnz @@End_8 ;çàêîí÷èòü, ñîõðàíèâ êîä îøèáêè
; cmp [DevErrorCode],0 ;проверить код ошибки
jnz @@End_8 ;закончить, сохранив код ошибки
 
; Îæèäàíèå ãîòîâíîñòè äèñêîâîäà ê ïðèåìó
; ïàêåòíîé êîìàíäû
; Ожидание готовности дисковода к приему
; пакетной команды
mov DX, [ATABasePortAddr]
add DX, 7 ;ïîðò 1õ7h
add DX, 7 ;порт 1х7h
mov ecx, NoTickWaitTime
@@WaitDevice0:
cmp [timer_ticks_enable], 0
231,21 → 231,21
jmp .test
@@:
call change_task
; Ïðîâåðèòü âðåìÿ âûïîëíåíèÿ êîìàíäû
; Проверить время выполнения команды
mov EAX, [timer_ticks]
sub EAX, [TickCounter_1]
cmp EAX, BSYWaitTime
ja @@Err1_1 ;îøèáêà òàéì-àóòà
; Ïðîâåðèòü ãîòîâíîñòü
ja @@Err1_1 ;ошибка тайм-аута
; Проверить готовность
.test:
in AL, DX
test AL, 80h ;ñîñòîÿíèå ñèãíàëà BSY
test AL, 80h ;состояние сигнала BSY
jnz @@WaitDevice0
test AL, 1 ;ñîñòîÿíèå ñèãíàëà ERR
test AL, 1 ;состояние сигнала ERR
jnz @@Err6
test AL, 08h ;ñîñòîÿíèå ñèãíàëà DRQ
test AL, 08h ;состояние сигнала DRQ
jz @@WaitDevice0
; Ïîñëàòü ïàêåòíóþ êîìàíäó
; Послать пакетную команду
cli
mov DX, [ATABasePortAddr]
mov AX, [PacketCommand]
261,9 → 261,9
mov AX, [PacketCommand+10]
out DX, AX
sti
; Îæèäàíèå ãîòîâíîñòè äàííûõ
; Ожидание готовности данных
mov DX, [ATABasePortAddr]
add DX, 7 ;ïîðò 1õ7h
add DX, 7 ;порт 1х7h
mov ecx, NoTickWaitTime
@@WaitDevice1:
cmp [timer_ticks_enable], 0
274,40 → 274,40
jmp .test_1
@@:
call change_task
; Ïðîâåðèòü âðåìÿ âûïîëíåíèÿ êîìàíäû
; Проверить время выполнения команды
mov EAX, [timer_ticks]
sub EAX, [TickCounter_1]
cmp EAX, MaxCDWaitTime
ja @@Err1_1 ;îøèáêà òàéì-àóòà
; Ïðîâåðèòü ãîòîâíîñòü
ja @@Err1_1 ;ошибка тайм-аута
; Проверить готовность
.test_1:
in AL, DX
test AL, 80h ;ñîñòîÿíèå ñèãíàëà BSY
test AL, 80h ;состояние сигнала BSY
jnz @@WaitDevice1
test AL, 1 ;ñîñòîÿíèå ñèãíàëà ERR
test AL, 1 ;состояние сигнала ERR
jnz @@Err6_temp
test AL, 08h ;ñîñòîÿíèå ñèãíàëà DRQ
test AL, 08h ;состояние сигнала DRQ
jz @@WaitDevice1
; Ïðèíÿòü áëîê äàííûõ îò êîíòðîëëåðà
; Принять блок данных от контроллера
mov EDI, [CDDataBuf_pointer];0x7000 ;CDDataBuf
; Çàãðóçèòü àäðåñ ðåãèñòðà äàííûõ êîíòðîëëåðà
mov DX, [ATABasePortAddr];ïîðò 1x0h
; Çàãðóçèòü â ñ÷åò÷èê ðàçìåð áëîêà â áàéòàõ
; Загрузить адрес регистра данных контроллера
mov DX, [ATABasePortAddr];порт 1x0h
; Загрузить в счетчик размер блока в байтах
xor ecx, ecx
mov CX, CDBlockSize
; Âû÷èñëèòü ðàçìåð áëîêà â 16-ðàçðÿäíûõ ñëîâàõ
shr CX, 1;ðàçäåëèòü ðàçìåð áëîêà íà 2
; Ïðèíÿòü áëîê äàííûõ
; Вычислить размер блока в 16-разрядных словах
shr CX, 1;разделить размер блока на 2
; Принять блок данных
cli
cld
rep insw
sti
; Óñïåøíîå çàâåðøåíèå ïðèåìà äàííûõ
; Успешное завершение приема данных
@@End_8:
xor eax, eax
ret
 
; Çàïèñàòü êîä îøèáêè
; Записать код ошибки
@@Err1_1:
xor eax, eax
inc eax
329,21 → 329,21
 
 
;***********************************************
;* ÏÎÑËÀÒÜ ÓÑÒÐÎÉÑÒÂÓ ATAPI ÏÀÊÅÒÍÓÞ ÊÎÌÀÍÄÓ, *
;* ÍÅ ÏÐÅÄÓÑÌÀÒÐÈÂÀÞÙÓÞ ÏÅÐÅÄÀ×È ÄÀÍÍÛÕ *
;* Âõîäíûå ïàðàìåòðû ïåðåäàþòñÿ ÷åðåç *
;* ãëîáàëüíûå ïåðìåííûå: *
;* ChannelNumber - íîìåð êàíàëà; *
;* DiskNumber - íîìåð äèñêà íà êàíàëå; *
;* PacketCommand - 12-áàéòíûé êîìàíäíûé ïàêåò. *
;* ПОСЛАТЬ УСТРОЙСТВУ ATAPI ПАКЕТНУЮ КОМАНДУ, *
;* НЕ ПРЕДУСМАТРИВАЮЩУЮ ПЕРЕДАЧИ ДАННЫХ *
;* Входные параметры передаются через *
;* глобальные перменные: *
;* ChannelNumber - номер канала; *
;* DiskNumber - номер диска на канале; *
;* PacketCommand - 12-байтный командный пакет. *
;***********************************************
SendPacketNoDatCommand:
pushad
xor eax, eax
; mov byte [DevErrorCode],al
; Çàäàòü ðåæèì CHS
; Задать режим CHS
mov byte [ATAAddressMode], al
; Ïîñëàòü ATA-êîìàíäó ïåðåäà÷è ïàêåòíîé êîìàíäû
; Послать ATA-команду передачи пакетной команды
mov byte [ATAFeatures], al
mov byte [ATASectorCount], al
mov byte [ATASectorNumber], al
351,29 → 351,29
mov byte [ATAHead], al
mov [ATACommand], 0A0h
call SendCommandToHDD_1
; cmp [DevErrorCode],0 ;ïðîâåðèòü êîä îøèáêè
; cmp [DevErrorCode],0 ;проверить код ошибки
test eax, eax
jnz @@End_9 ;çàêîí÷èòü, ñîõðàíèâ êîä îøèáêè
; Îæèäàíèå ãîòîâíîñòè äèñêîâîäà ê ïðèåìó
; ïàêåòíîé êîìàíäû
jnz @@End_9 ;закончить, сохранив код ошибки
; Ожидание готовности дисковода к приему
; пакетной команды
mov DX, [ATABasePortAddr]
add DX, 7 ;ïîðò 1õ7h
add DX, 7 ;порт 1х7h
@@WaitDevice0_1:
call change_task
; Ïðîâåðèòü âðåìÿ îæèäàíèÿ
; Проверить время ожидания
mov EAX, [timer_ticks]
sub EAX, [TickCounter_1]
cmp EAX, BSYWaitTime
ja @@Err1_3 ;îøèáêà òàéì-àóòà
; Ïðîâåðèòü ãîòîâíîñòü
ja @@Err1_3 ;ошибка тайм-аута
; Проверить готовность
in AL, DX
test AL, 80h ;ñîñòîÿíèå ñèãíàëà BSY
test AL, 80h ;состояние сигнала BSY
jnz @@WaitDevice0_1
test AL, 1 ;ñîñòîÿíèå ñèãíàëà ERR
test AL, 1 ;состояние сигнала ERR
jnz @@Err6_1
test AL, 08h ;ñîñòîÿíèå ñèãíàëà DRQ
test AL, 08h ;состояние сигнала DRQ
jz @@WaitDevice0_1
; Ïîñëàòü ïàêåòíóþ êîìàíäó
; Послать пакетную команду
; cli
mov DX, [ATABasePortAddr]
mov AX, word [PacketCommand]
391,29 → 391,29
; sti
cmp [ignore_CD_eject_wait], 1
je @@clear_DEC
; Îæèäàíèå ïîäòâåðæäåíèÿ ïðèåìà êîìàíäû
; Ожидание подтверждения приема команды
mov DX, [ATABasePortAddr]
add DX, 7 ;ïîðò 1õ7h
add DX, 7 ;порт 1х7h
@@WaitDevice1_1:
call change_task
; Ïðîâåðèòü âðåìÿ âûïîëíåíèÿ êîìàíäû
; Проверить время выполнения команды
mov EAX, [timer_ticks]
sub EAX, [TickCounter_1]
cmp EAX, MaxCDWaitTime
ja @@Err1_3 ;îøèáêà òàéì-àóòà
; Îæèäàòü îñâîáîæäåíèÿ óñòðîéñòâà
ja @@Err1_3 ;ошибка тайм-аута
; Ожидать освобождения устройства
in AL, DX
test AL, 80h ;ñîñòîÿíèå ñèãíàëà BSY
test AL, 80h ;состояние сигнала BSY
jnz @@WaitDevice1_1
test AL, 1 ;ñîñòîÿíèå ñèãíàëà ERR
test AL, 1 ;состояние сигнала ERR
jnz @@Err6_1
test AL, 40h ;ñîñòîÿíèå ñèãíàëà DRDY
test AL, 40h ;состояние сигнала DRDY
jz @@WaitDevice1_1
@@clear_DEC:
and [DevErrorCode], 0
popad
ret
; Çàïèñàòü êîä îøèáêè
; Записать код ошибки
@@Err1_3:
xor eax, eax
inc eax
426,53 → 426,53
ret
 
;****************************************************
;* ÏÎÑËÀÒÜ ÊÎÌÀÍÄÓ ÇÀÄÀÍÍÎÌÓ ÄÈÑÊÓ *
;* Âõîäíûå ïàðàìåòðû ïåðåäàþòñÿ ÷åðåç ãëîáàëüíûå *
;* ïåðåìåííûå: *
;* ChannelNumber - íîìåð êàíàëà (1 èëè 2); *
;* DiskNumber - íîìåð äèñêà (0 èëè 1); *
;* ATAFeatures - "îñîáåííîñòè"; *
;* ATASectorCount - êîëè÷åñòâî ñåêòîðîâ; *
;* ATASectorNumber - íîìåð íà÷àëüíîãî ñåêòîðà; *
;* ATACylinder - íîìåð íà÷àëüíîãî öèëèíäðà; *
;* ATAHead - íîìåð íà÷àëüíîé ãîëîâêè; *
;* ATAAddressMode - ðåæèì àäðåñàöèè (0-CHS, 1-LBA); *
;* ATACommand - êîä êîìàíäû. *
;* Ïîñëå óñïåøíîãî âûïîëíåíèÿ ôóíêöèè: *
;* â ATABasePortAddr - áàçîâûé àäðåñ HDD; *
;* â DevErrorCode - íîëü. *
;* Ïðè âîçíèêíîâåíèè îøèáêè â DevErrorCode áóäåò *
;* âîçâðàùåí êîä îøèáêè â eax *
;* ПОСЛАТЬ КОМАНДУ ЗАДАННОМУ ДИСКУ *
;* Входные параметры передаются через глобальные *
;* переменные: *
;* ChannelNumber - номер канала (1 или 2); *
;* DiskNumber - номер диска (0 или 1); *
;* ATAFeatures - "особенности"; *
;* ATASectorCount - количество секторов; *
;* ATASectorNumber - номер начального сектора; *
;* ATACylinder - номер начального цилиндра; *
;* ATAHead - номер начальной головки; *
;* ATAAddressMode - режим адресации (0-CHS, 1-LBA); *
;* ATACommand - код команды. *
;* После успешного выполнения функции: *
;* в ATABasePortAddr - базовый адрес HDD; *
;* в DevErrorCode - ноль. *
;* При возникновении ошибки в DevErrorCode будет *
;* возвращен код ошибки в eax *
;****************************************************
SendCommandToHDD_1:
; pushad
; mov [DevErrorCode],0 not need
; Ïðîâåðèòü çíà÷åíèå êîäà ðåæèìà
; Проверить значение кода режима
cmp [ATAAddressMode], 1
ja @@Err2_4
; Ïðîâåðèòü êîððåêòíîñòü íîìåðà êàíàëà
; Проверить корректность номера канала
mov BX, [ChannelNumber]
cmp BX, 1
jb @@Err3_4
cmp BX, 2
ja @@Err3_4
; Óñòàíîâèòü áàçîâûé àäðåñ
; Установить базовый адрес
dec BX
shl BX, 1
movzx ebx, bx
mov AX, [ebx+StandardATABases]
mov [ATABasePortAddr], AX
; Îæèäàíèå ãîòîâíîñòè HDD ê ïðèåìó êîìàíäû
; Âûáðàòü íóæíûé äèñê
; Ожидание готовности HDD к приему команды
; Выбрать нужный диск
mov DX, [ATABasePortAddr]
add DX, 6 ;àäðåñ ðåãèñòðà ãîëîâîê
add DX, 6 ;адрес регистра головок
mov AL, [DiskNumber]
cmp AL, 1 ;ïðîâåðèòü íîìåðà äèñêà
cmp AL, 1 ;проверить номера диска
ja @@Err4_4
shl AL, 4
or AL, 10100000b
out DX, AL
; Îæèäàòü, ïîêà äèñê íå áóäåò ãîòîâ
; Ожидать, пока диск не будет готов
inc DX
mov eax, [timer_ticks]
mov [TickCounter_1], eax
486,43 → 486,43
jmp .test
@@:
call change_task
; Ïðîâåðèòü âðåìÿ îæèäàíèÿ
; Проверить время ожидания
mov eax, [timer_ticks]
sub eax, [TickCounter_1]
cmp eax, BSYWaitTime;300 ;îæèäàòü 3 ñåê.
ja @@Err1_4 ;îøèáêà òàéì-àóòà
; Ïðî÷èòàòü ðåãèñòð ñîñòîÿíèÿ
cmp eax, BSYWaitTime;300 ;ожидать 3 сек.
ja @@Err1_4 ;ошибка тайм-аута
; Прочитать регистр состояния
.test:
in AL, DX
; Ïðîâåðèòü ñîñòîÿíèå ñèãíàëà BSY
; Проверить состояние сигнала BSY
test AL, 80h
jnz @@WaitHDReady_2
; Ïðîâåðèòü ñîñòîÿíèå ñèãíàëà DRQ
; Проверить состояние сигнала DRQ
test AL, 08h
jnz @@WaitHDReady_2
 
; Çàãðóçèòü êîìàíäó â ðåãèñòðû êîíòðîëëåðà
; Загрузить команду в регистры контроллера
cli
mov DX, [ATABasePortAddr]
inc DX ;ðåãèñòð "îñîáåííîñòåé"
inc DX ;регистр "особенностей"
mov AL, [ATAFeatures]
out DX, AL
inc DX ;ñ÷åò÷èê ñåêòîðîâ
inc DX ;счетчик секторов
mov AL, [ATASectorCount]
out DX, AL
inc DX ;ðåãèñòð íîìåðà ñåêòîðà
inc DX ;регистр номера сектора
mov AL, [ATASectorNumber]
out DX, AL
inc DX ;íîìåð öèëèíäðà (ìëàäøèé áàéò)
inc DX ;номер цилиндра (младший байт)
mov AX, [ATACylinder]
out DX, AL
inc DX ;íîìåð öèëèíäðà (ñòàðøèé áàéò)
inc DX ;номер цилиндра (старший байт)
mov AL, AH
out DX, AL
inc DX ;íîìåð ãîëîâêè/íîìåð äèñêà
inc DX ;номер головки/номер диска
mov AL, [DiskNumber]
shl AL, 4
cmp [ATAHead], 0Fh;ïðîâåðèòü íîìåð ãîëîâêè
cmp [ATAHead], 0Fh;проверить номер головки
ja @@Err5_4
or AL, [ATAHead]
or AL, 10100000b
530,17 → 530,17
shl AH, 6
or AL, AH
out DX, AL
; Ïîñëàòü êîìàíäó
; Послать команду
mov AL, [ATACommand]
inc DX ;ðåãèñòð êîìàíä
inc DX ;регистр команд
out DX, AL
sti
; Ñáðîñèòü ïðèçíàê îøèáêè
; Сбросить признак ошибки
; mov [DevErrorCode],0
@@End_10:
xor eax, eax
ret
; Çàïèñàòü êîä îøèáêè
; Записать код ошибки
@@Err1_4:
xor eax, eax
inc eax
561,31 → 561,31
@@Err5_4:
mov eax, 5
; mov [DevErrorCode],5
; Çàâåðøåíèå ðàáîòû ïðîãðàììû
; Завершение работы программы
ret
; sti
; popad
 
;*************************************************
;* ÎÆÈÄÀÍÈÅ ÃÎÒÎÂÍÎÑÒÈ ÓÑÒÐÎÉÑÒÂÀ Ê ÐÀÁÎÒÅ *
;* Âõîäíûå ïàðàìåòðû ïåðåäàþòñÿ ÷åðåç ãëîáàëüíûå *
;* ïåðìåííûå: *
;* ChannelNumber - íîìåð êàíàëà; *
;* DiskNumber - íîìåð äèñêà íà êàíàëå. *
;* ОЖИДАНИЕ ГОТОВНОСТИ УСТРОЙСТВА К РАБОТЕ *
;* Входные параметры передаются через глобальные *
;* перменные: *
;* ChannelNumber - номер канала; *
;* DiskNumber - номер диска на канале. *
;*************************************************
WaitUnitReady:
pusha
; Çàïîìíèòü âðåìÿ íà÷àëà îïåðàöèè
; Запомнить время начала операции
mov EAX, [timer_ticks]
mov [WURStartTime], EAX
; Î÷èñòèòü áóôåð ïàêåòíîé êîìàíäû
; Очистить буфер пакетной команды
call clear_packet_buffer
; Ñôîðìèðîâàòü êîìàíäó TEST UNIT READY
; Сформировать команду TEST UNIT READY
mov [PacketCommand], word 00h
; ÖÈÊË ÎÆÈÄÀÍÈß ÃÎÒÎÂÍÎÑÒÈ ÓÑÒÐÎÉÑÒÂÀ
; ЦИКЛ ОЖИДАНИЯ ГОТОВНОСТИ УСТРОЙСТВА
mov ecx, NoTickWaitTime
@@SendCommand:
; Ïîäàòü êîìàíäó ïðîâåðêè ãîòîâíîñòè
; Подать команду проверки готовности
call SendPacketNoDatCommand
cmp [timer_ticks_enable], 0
jne @f
597,16 → 597,16
jmp @@SendCommand
@@:
call change_task
; Ïðîâåðèòü êîä îøèáêè
; Проверить код ошибки
cmp [DevErrorCode], 0
je @@End_11
; Ïðîâåðèòü âðåìÿ îæèäàíèÿ ãîòîâíîñòè
; Проверить время ожидания готовности
mov EAX, [timer_ticks]
sub EAX, [WURStartTime]
cmp EAX, MaxCDWaitTime
jb @@SendCommand
.Error:
; Îøèáêà òàéì-àóòà
; Ошибка тайм-аута
mov [DevErrorCode], 1
@@End_11:
popa
613,21 → 613,21
ret
 
;*************************************************
;* ÇÀÏÐÅÒÈÒÜ ÑÌÅÍÓ ÄÈÑÊÀ *
;* Âõîäíûå ïàðàìåòðû ïåðåäàþòñÿ ÷åðåç ãëîáàëüíûå *
;* ïåðìåííûå: *
;* ChannelNumber - íîìåð êàíàëà; *
;* DiskNumber - íîìåð äèñêà íà êàíàëå. *
;* ЗАПРЕТИТЬ СМЕНУ ДИСКА *
;* Входные параметры передаются через глобальные *
;* перменные: *
;* ChannelNumber - номер канала; *
;* DiskNumber - номер диска на канале. *
;*************************************************
prevent_medium_removal:
pusha
; Î÷èñòèòü áóôåð ïàêåòíîé êîìàíäû
; Очистить буфер пакетной команды
call clear_packet_buffer
; Çàäàòü êîä êîìàíäû
; Задать код команды
mov [PacketCommand], byte 0x1E
; Çàäàòü êîä çàïðåòà
; Задать код запрета
mov [PacketCommand+4], byte 11b
; Ïîäàòü êîìàíäó
; Подать команду
call SendPacketNoDatCommand
mov eax, ATAPI_IDE0_lock
add eax, [cdpos]
637,21 → 637,21
ret
 
;*************************************************
;* ÐÀÇÐÅØÈÒÜ ÑÌÅÍÓ ÄÈÑÊÀ *
;* Âõîäíûå ïàðàìåòðû ïåðåäàþòñÿ ÷åðåç ãëîáàëüíûå *
;* ïåðìåííûå: *
;* ChannelNumber - íîìåð êàíàëà; *
;* DiskNumber - íîìåð äèñêà íà êàíàëå. *
;* РАЗРЕШИТЬ СМЕНУ ДИСКА *
;* Входные параметры передаются через глобальные *
;* перменные: *
;* ChannelNumber - номер канала; *
;* DiskNumber - номер диска на канале. *
;*************************************************
allow_medium_removal:
pusha
; Î÷èñòèòü áóôåð ïàêåòíîé êîìàíäû
; Очистить буфер пакетной команды
call clear_packet_buffer
; Çàäàòü êîä êîìàíäû
; Задать код команды
mov [PacketCommand], byte 0x1E
; Çàäàòü êîä çàïðåòà
; Задать код запрета
mov [PacketCommand+4], byte 00b
; Ïîäàòü êîìàíäó
; Подать команду
call SendPacketNoDatCommand
mov eax, ATAPI_IDE0_lock
add eax, [cdpos]
661,54 → 661,54
ret
 
;*************************************************
;* ÇÀÃÐÓÇÈÒÜ ÍÎÑÈÒÅËÜ Â ÄÈÑÊÎÂÎÄ *
;* Âõîäíûå ïàðàìåòðû ïåðåäàþòñÿ ÷åðåç ãëîáàëüíûå *
;* ïåðìåííûå: *
;* ChannelNumber - íîìåð êàíàëà; *
;* DiskNumber - íîìåð äèñêà íà êàíàëå. *
;* ЗАГРУЗИТЬ НОСИТЕЛЬ В ДИСКОВОД *
;* Входные параметры передаются через глобальные *
;* перменные: *
;* ChannelNumber - номер канала; *
;* DiskNumber - номер диска на канале. *
;*************************************************
LoadMedium:
pusha
; Î÷èñòèòü áóôåð ïàêåòíîé êîìàíäû
; Очистить буфер пакетной команды
call clear_packet_buffer
; Ñôîðìèðîâàòü êîìàíäó START/STOP UNIT
; Çàäàòü êîä êîìàíäû
; Сформировать команду START/STOP UNIT
; Задать код команды
mov [PacketCommand], word 1Bh
; Çàäàòü îïåðàöèþ çàãðóçêè íîñèòåëÿ
; Задать операцию загрузки носителя
mov [PacketCommand+4], word 00000011b
; Ïîäàòü êîìàíäó
; Подать команду
call SendPacketNoDatCommand
popa
ret
 
;*************************************************
;* ÈÇÂËÅ×Ü ÍÎÑÈÒÅËÜ ÈÇ ÄÈÑÊÎÂÎÄÀ *
;* Âõîäíûå ïàðàìåòðû ïåðåäàþòñÿ ÷åðåç ãëîáàëüíûå *
;* ïåðìåííûå: *
;* ChannelNumber - íîìåð êàíàëà; *
;* DiskNumber - íîìåð äèñêà íà êàíàëå. *
;* ИЗВЛЕЧЬ НОСИТЕЛЬ ИЗ ДИСКОВОДА *
;* Входные параметры передаются через глобальные *
;* перменные: *
;* ChannelNumber - номер канала; *
;* DiskNumber - номер диска на канале. *
;*************************************************
EjectMedium:
pusha
; Î÷èñòèòü áóôåð ïàêåòíîé êîìàíäû
; Очистить буфер пакетной команды
call clear_packet_buffer
; Ñôîðìèðîâàòü êîìàíäó START/STOP UNIT
; Çàäàòü êîä êîìàíäû
; Сформировать команду START/STOP UNIT
; Задать код команды
mov [PacketCommand], word 1Bh
; Çàäàòü îïåðàöèþ èçâëå÷åíèÿ íîñèòåëÿ
; Задать операцию извлечения носителя
mov [PacketCommand+4], word 00000010b
; Ïîäàòü êîìàíäó
; Подать команду
call SendPacketNoDatCommand
popa
ret
 
;*************************************************
;* Ïðîâåðèòü ñîáûòèå íàæàòèÿ êíîïêè èçâëå÷åíèÿ *
;* äèñêà *
;* Âõîäíûå ïàðàìåòðû ïåðåäàþòñÿ ÷åðåç ãëîáàëüíûå *
;* ïåðåìåííûå: *
;* ChannelNumber - íîìåð êàíàëà; *
;* DiskNumber - íîìåð äèñêà íà êàíàëå. *
;* Проверить событие нажатия кнопки извлечения *
;* диска *
;* Входные параметры передаются через глобальные *
;* переменные: *
;* ChannelNumber - номер канала; *
;* DiskNumber - номер диска на канале. *
;*************************************************
proc check_ATAPI_device_event_has_work?
mov eax, [timer_ticks]
867,78 → 867,78
ignore_CD_eject_wait db 0
endg
;*************************************************
;* Ïîëó÷èòü ñîîáùåíèå î ñîáûòèè èëè ñîñòîÿíèè *
;* óñòðîéñòâà *
;* Âõîäíûå ïàðàìåòðû ïåðåäàþòñÿ ÷åðåç ãëîáàëüíûå *
;* ïåðåìåííûå: *
;* ChannelNumber - íîìåð êàíàëà; *
;* DiskNumber - íîìåð äèñêà íà êàíàëå. *
;* Получить сообщение о событии или состоянии *
;* устройства *
;* Входные параметры передаются через глобальные *
;* переменные: *
;* ChannelNumber - номер канала; *
;* DiskNumber - номер диска на канале. *
;*************************************************
GetEvent_StatusNotification:
pusha
mov [CDDataBuf_pointer], CDDataBuf
; Î÷èñòèòü áóôåð ïàêåòíîé êîìàíäû
; Очистить буфер пакетной команды
call clear_packet_buffer
; Çàäàòü êîä êîìàíäû
; Задать код команды
mov [PacketCommand], byte 4Ah
mov [PacketCommand+1], byte 00000001b
; Çàäàòü çàïðîñ êëàññà ñîîáùåíèé
; Задать запрос класса сообщений
mov [PacketCommand+4], byte 00010000b
; Ðàçìåð âûäåëåííîé îáëàñòè
; Размер выделенной области
mov [PacketCommand+7], byte 8h
mov [PacketCommand+8], byte 0h
; Ïîäàòü êîìàíäó
; Подать команду
call SendPacketDatCommand
popa
ret
 
;*************************************************
; ïðî÷èòàòü èíôîðìàöèþ èç TOC
;* Âõîäíûå ïàðàìåòðû ïåðåäàþòñÿ ÷åðåç ãëîáàëüíûå *
;* ïåðåìåííûå: *
;* ChannelNumber - íîìåð êàíàëà; *
;* DiskNumber - íîìåð äèñêà íà êàíàëå. *
; прочитать информацию из TOC
;* Входные параметры передаются через глобальные *
;* переменные: *
;* ChannelNumber - номер канала; *
;* DiskNumber - номер диска на канале. *
;*************************************************
Read_TOC:
pusha
mov [CDDataBuf_pointer], CDDataBuf
; Î÷èñòèòü áóôåð ïàêåòíîé êîìàíäû
; Очистить буфер пакетной команды
call clear_packet_buffer
; Ñôîðìèðîâàòü ïàêåòíóþ êîìàíäó äëÿ ñ÷èòûâàíèÿ
; ñåêòîðà äàííûõ
; Сформировать пакетную команду для считывания
; сектора данных
mov [PacketCommand], byte 0x43
; Çàäàòü ôîðìàò
; Задать формат
mov [PacketCommand+2], byte 1
; Ðàçìåð âûäåëåííîé îáëàñòè
; Размер выделенной области
mov [PacketCommand+7], byte 0xFF
mov [PacketCommand+8], byte 0h
; Ïîäàòü êîìàíäó
; Подать команду
call SendPacketDatCommand
popa
ret
 
;*************************************************
;* ÎÏÐÅÄÅËÈÒÜ ÎÁÙÅÅ ÊÎËÈ×ÅÑÒÂÎ ÑÅÊÒÎÐΠÍÀ ÄÈÑÊÅ *
;* Âõîäíûå ïàðàìåòðû ïåðåäàþòñÿ ÷åðåç ãëîáàëüíûå *
;* ïåðåìåííûå: *
;* ChannelNumber - íîìåð êàíàëà; *
;* DiskNumber - íîìåð äèñêà íà êàíàëå. *
;* ОПРЕДЕЛИТЬ ОБЩЕЕ КОЛИЧЕСТВО СЕКТОРОВ НА ДИСКЕ *
;* Входные параметры передаются через глобальные *
;* переменные: *
;* ChannelNumber - номер канала; *
;* DiskNumber - номер диска на канале. *
;*************************************************
;ReadCapacity:
; pusha
;; Î÷èñòèòü áóôåð ïàêåòíîé êîìàíäû
;; Очистить буфер пакетной команды
; call clear_packet_buffer
;; Çàäàòü ðàçìåð áóôåðà â áàéòàõ
;; Задать размер буфера в байтах
; mov [CDBlockSize],8
;; Ñôîðìèðîâàòü êîìàíäó READ CAPACITY
;; Сформировать команду READ CAPACITY
; mov [PacketCommand],word 25h
;; Ïîäàòü êîìàíäó
;; Подать команду
; call SendPacketDatCommand
; popa
; ret
 
clear_packet_buffer:
; Î÷èñòèòü áóôåð ïàêåòíîé êîìàíäû
; Очистить буфер пакетной команды
and [PacketCommand], dword 0
and [PacketCommand+4], dword 0
and [PacketCommand+8], dword 0
/kernel/trunk/blkdev/disk_cache.inc
397,7 → 397,7
mov dword [esi+8], 1 ; same as in hd
mov eax, [esi]
mov edx, [esi+4] ; edx:eax = sector to write
; Îáúåäèíÿåì çàïèñü öåïî÷êè ïîñëåäîâàòåëüíûõ ñåêòîðîâ â îäíî îáðàùåíèå ê äèñêó
; Объединяем запись цепочки последовательных секторов в одно обращение к диску
cmp ecx, 1
jz .nonext
cmp dword [esi+12+8], 2
/kernel/trunk/blkdev/fdc.inc
37,9 → 37,9
call check_label
cmp [FDC_Status], 0
jne unnecessary_save_image
mov [FDD_Track], 0; Öèëèíäð
mov [FDD_Head], 0; Ñòîðîíà
mov [FDD_Sector], 1; Ñåêòîð
mov [FDD_Track], 0; Цилиндр
mov [FDD_Head], 0; Сторона
mov [FDD_Sector], 1; Сектор
mov esi, RAMDISK
call SeekTrack
save_image_1:
/kernel/trunk/blkdev/flp_drv.inc
9,12 → 9,12
 
 
;**********************************************************
; Íåïîñðåäñòâåííàÿ ðàáîòà ñ êîíòðîëëåðîì ãèáêîãî äèñêà
; Непосредственная работа с контроллером гибкого диска
;**********************************************************
; Àâòîð èñõîäíîãî òåêñòà Êóëàêîâ Âëàäèìèð Ãåííàäüåâè÷.
; Àäàïòàöèÿ è äîðàáîòêà Mario79
; Автор исходного текста Кулаков Владимир Геннадьевич.
; Адаптация и доработка Mario79
 
;give_back_application_data: ; ïåðåñëàòü ïðèëîæåíèþ
;give_back_application_data: ; переслать приложению
; mov edi,[TASK_BASE]
; mov edi,[edi+TASKDATA.mem_start]
; add edi,ecx
26,7 → 26,7
rep movsd
ret
 
;take_data_from_application: ; âçÿòü èç ïðèëîæåíè
;take_data_from_application: ; взять из приложени
; mov esi,[TASK_BASE]
; mov esi,[esi+TASKDATA.mem_start]
; add esi,ecx
38,37 → 38,37
rep movsd
ret
 
; Êîäû çàâåðøåíèÿ îïåðàöèè ñ êîíòðîëëåðîì (FDC_Status)
FDC_Normal equ 0 ;íîðìàëüíîå çàâåðøåíèå
FDC_TimeOut equ 1 ;îøèáêà òàéì-àóòà
FDC_DiskNotFound equ 2 ;â äèñêîâîäå íåò äèñêà
FDC_TrackNotFound equ 3 ;äîðîæêà íå íàéäåíà
FDC_SectorNotFound equ 4 ;ñåêòîð íå íàéäåí
; Коды завершения операции с контроллером (FDC_Status)
FDC_Normal equ 0 ;нормальное завершение
FDC_TimeOut equ 1 ;ошибка тайм-аута
FDC_DiskNotFound equ 2 ;в дисководе нет диска
FDC_TrackNotFound equ 3 ;дорожка не найдена
FDC_SectorNotFound equ 4 ;сектор не найден
 
; Ìàêñèìàëüíûå çíà÷åíèÿ êîîðäèíàò ñåêòîðà (çàäàííûå
; çíà÷åíèÿ ñîîòâåòñòâóþò ïàðàìåòðàì ñòàíäàðòíîãî
; òðåõäþéìîâîãî ãèáêîãî äèñêà îáúåìîì 1,44 Ìá)
; Максимальные значения координат сектора (заданные
; значения соответствуют параметрам стандартного
; трехдюймового гибкого диска объемом 1,44 Мб)
MAX_Track equ 79
MAX_Head equ 1
MAX_Sector equ 18
 
uglobal
; Ñ÷åò÷èê òèêîâ òàéìåðà
; Счетчик тиков таймера
TickCounter dd ?
; Êîä çàâåðøåíèÿ îïåðàöèè ñ êîíòðîëëåðîì ÍÃÌÄ
; Код завершения операции с контроллером НГМД
FDC_Status DB ?
; Ôëàã ïðåðûâàíèÿ îò ÍÃÌÄ
; Флаг прерывания от НГМД
FDD_IntFlag DB ?
; Ìîìåíò íà÷àëà ïîñëåäíåé îïåðàöèè ñ ÍÃÌÄ
; Момент начала последней операции с НГМД
FDD_Time DD ?
; Íîìåð äèñêîâîäà
; Номер дисковода
FDD_Type db 0
; Êîîðäèíàòû ñåêòîðà
; Координаты сектора
FDD_Track DB ?
FDD_Head DB ?
FDD_Sector DB ?
 
; Áëîê ðåçóëüòàòà îïåðàöèè
; Блок результата операции
FDC_ST0 DB ?
FDC_ST1 DB ?
FDC_ST2 DB ?
76,18 → 76,18
FDC_H DB ?
FDC_R DB ?
FDC_N DB ?
; Ñ÷åò÷èê ïîâòîðåíèÿ îïåðàöèè ÷òåíè
; Счетчик повторения операции чтени
ReadRepCounter DB ?
; Ñ÷åò÷èê ïîâòîðåíèÿ îïåðàöèè ðåêàëèáðîâêè
; Счетчик повторения операции рекалибровки
RecalRepCounter DB ?
endg
; Îáëàñòü ïàìÿòè äëÿ õðàíåíèÿ ïðî÷èòàííîãî ñåêòîðà
; Область памяти для хранения прочитанного сектора
;FDD_DataBuffer: times 512 db 0 ;DB 512 DUP (?)
fdd_motor_status db 0
timer_fdd_motor dd 0
 
;*************************************
;* ÈÍÈÖÈÀËÈÇÀÖÈß ÐÅÆÈÌÀ ÏÄÏ ÄËß ÍÃÌÄ *
;* ИНИЦИАЛИЗАЦИЯ РЕЖИМА ПДП ДЛЯ НГМД *
;*************************************
Init_FDC_DMA:
pushad
117,29 → 117,29
ret
 
;***********************************
;* ÇÀÏÈÑÀÒÜ ÁÀÉÒ Â ÏÎÐÒ ÄÀÍÍÛÕ FDC *
;* Ïàðàìåòðû: *
;* AL - âûâîäèìûé áàéò. *
;* ЗАПИСАТЬ БАЙТ В ПОРТ ДАННЫХ FDC *
;* Параметры: *
;* AL - выводимый байт. *
;***********************************
FDCDataOutput:
; pusha
push eax ecx edx
mov AH, AL ;çàïîìíèòü áàéò â AH
; Ñáðîñèòü ïåðåìåííóþ ñîñòîÿíèÿ êîíòðîëëåðà
mov AH, AL ;запомнить байт в AH
; Сбросить переменную состояния контроллера
mov [FDC_Status], FDC_Normal
; Ïðîâåðèòü ãîòîâíîñòü êîíòðîëëåðà ê ïðèåìó äàííûõ
mov DX, 3F4h ;(ïîðò ñîñòîÿíèÿ FDC)
mov ecx, 0x10000 ;óñòàíîâèòü ñ÷åò÷èê òàéì-àóòà
; Проверить готовность контроллера к приему данных
mov DX, 3F4h ;(порт состояния FDC)
mov ecx, 0x10000 ;установить счетчик тайм-аута
@@TestRS:
in AL, DX ;ïðî÷èòàòü ðåãèñòð RS
and AL, 0C0h ;âûäåëèòü ðàçðÿäû 6 è 7
cmp AL, 80h ;ïðîâåðèòü ðàçðÿäû 6 è 7
in AL, DX ;прочитать регистр RS
and AL, 0C0h ;выделить разряды 6 и 7
cmp AL, 80h ;проверить разряды 6 и 7
je @@OutByteToFDC
loop @@TestRS
; Îøèáêà òàéì-àóòà
; Ошибка тайм-аута
mov [FDC_Status], FDC_TimeOut
jmp @@End_5
; Âûâåñòè áàéò â ïîðò äàííûõ
; Вывести байт в порт данных
@@OutByteToFDC:
inc DX
mov AL, AH
150,29 → 150,29
ret
 
;******************************************
;* ÏÐÎ×ÈÒÀÒÜ ÁÀÉÒ ÈÇ ÏÎÐÒÀ ÄÀÍÍÛÕ FDC *
;* Ïðîöåäóðà íå èìååò âõîäíûõ ïàðàìåòðîâ. *
;* Âûõîäíûå äàííûå: *
;* AL - ñ÷èòàííûé áàéò. *
;* ПРОЧИТАТЬ БАЙТ ИЗ ПОРТА ДАННЫХ FDC *
;* Процедура не имеет входных параметров. *
;* Выходные данные: *
;* AL - считанный байт. *
;******************************************
FDCDataInput:
push ECX
push DX
; Ñáðîñèòü ïåðåìåííóþ ñîñòîÿíèÿ êîíòðîëëåðà
; Сбросить переменную состояния контроллера
mov [FDC_Status], FDC_Normal
; Ïðîâåðèòü ãîòîâíîñòü êîíòðîëëåðà ê ïåðåäà÷å äàííûõ
mov DX, 3F4h ;(ïîðò ñîñòîÿíèÿ FDC)
xor CX, CX ;óñòàíîâèòü ñ÷åò÷èê òàéì-àóòà
; Проверить готовность контроллера к передаче данных
mov DX, 3F4h ;(порт состояния FDC)
xor CX, CX ;установить счетчик тайм-аута
@@TestRS_1:
in AL, DX ;ïðî÷èòàòü ðåãèñòð RS
and AL, 0C0h ;âûäëèòü ðàçðÿäû 6 è 7
cmp AL, 0C0h ;ïðîâåðèòü ðàçðÿäû 6 è 7
in AL, DX ;прочитать регистр RS
and AL, 0C0h ;выдлить разряды 6 и 7
cmp AL, 0C0h ;проверить разряды 6 и 7
je @@GetByteFromFDC
loop @@TestRS_1
; Îøèáêà òàéì-àóòà
; Ошибка тайм-аута
mov [FDC_Status], FDC_TimeOut
jmp @@End_6
; Ââåñòè áàéò èç ïîðòà äàííûõ
; Ввести байт из порта данных
@@GetByteFromFDC:
inc DX
in AL, DX
182,17 → 182,17
ret
 
;*********************************************
;* ÎÁÐÀÁÎÒ×ÈÊ ÏÐÅÐÛÂÀÍÈß ÎÒ ÊÎÍÒÐÎËËÅÐÀ ÍÃÌÄ *
;* ОБРАБОТЧИК ПРЕРЫВАНИЯ ОТ КОНТРОЛЛЕРА НГМД *
;*********************************************
FDCInterrupt:
; Óñòàíîâèòü ôëàã ïðåðûâàíè
; Установить флаг прерывани
mov [FDD_IntFlag], 1
ret
 
 
;******************************************
;* ÓÑÒÀÍÎÂÈÒÜ ÍÎÂÛÉ ÎÁÐÀÁÎÒ×ÈÊ ÏÐÅÐÛÂÀÍÈÉ *
;* ÍÃÌÄ *
;* УСТАНОВИТЬ НОВЫЙ ОБРАБОТЧИК ПРЕРЫВАНИЙ *
;* НГМД *
;******************************************
SetUserInterrupts:
mov [fdc_irq_func], FDCInterrupt
199,28 → 199,28
ret
 
;*******************************************
;* ÎÆÈÄÀÍÈÅ ÏÐÅÐÛÂÀÍÈß ÎÒ ÊÎÍÒÐÎËËÅÐÀ ÍÃÌÄ *
;* ОЖИДАНИЕ ПРЕРЫВАНИЯ ОТ КОНТРОЛЛЕРА НГМД *
;*******************************************
WaitFDCInterrupt:
pusha
; Ñáðîñèòü áàéò ñîñòîÿíèÿ îïåðàöèè
; Сбросить байт состояния операции
mov [FDC_Status], FDC_Normal
; Ñáðîñèòü ôëàã ïðåðûâàíè
; Сбросить флаг прерывани
mov [FDD_IntFlag], 0
; Îáíóëèòü ñ÷åò÷èê òèêîâ
; Обнулить счетчик тиков
mov eax, [timer_ticks]
mov [TickCounter], eax
; Îæèäàòü óñòàíîâêè ôëàãà ïðåðûâàíèÿ ÍÃÌÄ
; Ожидать установки флага прерывания НГМД
@@TestRS_2:
cmp [FDD_IntFlag], 0
jnz @@End_7 ;ïðåðûâàíèå ïðîèçîøëî
jnz @@End_7 ;прерывание произошло
call change_task
mov eax, [timer_ticks]
sub eax, [TickCounter]
cmp eax, 50 ;25 ;5 ;îæèäàòü 5 òèêîâ
cmp eax, 50 ;25 ;5 ;ожидать 5 тиков
jb @@TestRS_2
; jl @@TestRS_2
; Îøèáêà òàéì-àóòà
; Ошибка тайм-аута
mov [FDC_Status], FDC_TimeOut
; mov [flp_status],0
@@End_7:
228,7 → 228,7
ret
 
;*********************************
;* ÂÊËÞ×ÈÒÜ ÌÎÒÎÐ ÄÈÑÊÎÂÎÄÀ "A:" *
;* ВКЛЮЧИТЬ МОТОР ДИСКОВОДА "A:" *
;*********************************
FDDMotorON:
pusha
237,11 → 237,11
mov al, [flp_number]
cmp [fdd_motor_status], al
je fdd_motor_on
; Ïðîèçâåñòè ñáðîñ êîíòðîëëåðà ÍÃÌÄ
mov DX, 3F2h;ïîðò óïðàâëåíèÿ äâèãàòåëÿìè
; Произвести сброс контроллера НГМД
mov DX, 3F2h;порт управления двигателями
mov AL, 0
out DX, AL
; Âûáðàòü è âêëþ÷èòü ìîòîð äèñêîâîäà
; Выбрать и включить мотор дисковода
cmp [flp_number], 1
jne FDDMotorON_B
; call FDDMotorOFF_B
252,10 → 252,10
mov AL, 2Dh ; Floppy B
FDDMotorON_1:
out DX, AL
; Îáíóëèòü ñ÷åò÷èê òèêîâ
; Обнулить счетчик тиков
mov eax, [timer_ticks]
mov [TickCounter], eax
; Îæèäàòü 0,5 ñ
; Ожидать 0,5 с
@@dT:
call change_task
mov eax, [timer_ticks]
274,7 → 274,7
ret
 
;*****************************************
;* ÑÎÕÐÀÍÅÍÈÅ ÓÊÀÇÀÒÅËß ÂÐÅÌÅÍÈ *
;* СОХРАНЕНИЕ УКАЗАТЕЛЯ ВРЕМЕНИ *
;*****************************************
save_timer_fdd_motor:
mov eax, [timer_ticks]
282,7 → 282,7
ret
 
;*****************************************
;* ÏÐÎÂÅÐÊÀ ÇÀÄÅÐÆÊÈ ÂÛÊËÞ×ÅÍÈß ÌÎÒÎÐÀ *
;* ПРОВЕРКА ЗАДЕРЖКИ ВЫКЛЮЧЕНИЯ МОТОРА *
;*****************************************
proc check_fdd_motor_status_has_work?
cmp [flp_status], 0
318,7 → 318,7
ret
 
;**********************************
;* ÂÛÊËÞ×ÈÒÜ ÌÎÒÎÐ ÄÈÑÊÎÂÎÄÀ *
;* ВЫКЛЮЧИТЬ МОТОР ДИСКОВОДА *
;**********************************
FDDMotorOFF:
push AX
332,35 → 332,35
FDDMotorOFF_2:
pop DX
pop AX
; ñáðîñ ôëàãîâ êåøèðîâàíèÿ â ñâÿçè ñ óñòàðåâàíèåì èíôîðìàöèè
; сброс флагов кеширования в связи с устареванием информации
mov [root_read], 0
mov [flp_fat], 0
ret
 
FDDMotorOFF_A:
mov DX, 3F2h;ïîðò óïðàâëåíèÿ äâèãàòåëÿìè
mov DX, 3F2h;порт управления двигателями
mov AL, 0Ch ; Floppy A
out DX, AL
ret
 
FDDMotorOFF_B:
mov DX, 3F2h;ïîðò óïðàâëåíèÿ äâèãàòåëÿìè
mov DX, 3F2h;порт управления двигателями
mov AL, 5h ; Floppy B
out DX, AL
ret
 
;*******************************
;* ÐÅÊÀËÈÁÐÎÂÊÀ ÄÈÑÊÎÂÎÄÀ "A:" *
;* РЕКАЛИБРОВКА ДИСКОВОДА "A:" *
;*******************************
RecalibrateFDD:
pusha
call save_timer_fdd_motor
; Ïîäàòü êîìàíäó "Ðåêàëèáðîâêà"
; Подать команду "Рекалибровка"
mov AL, 07h
call FDCDataOutput
mov AL, 00h
call FDCDataOutput
; Îæèäàòü çàâåðøåíèÿ îïåðàöèè
; Ожидать завершения операции
call WaitFDCInterrupt
; cmp [FDC_Status],0
; je no_fdc_status_error
371,30 → 371,30
ret
 
;*****************************************************
;* ÏÎÈÑÊ ÄÎÐÎÆÊÈ *
;* Ïàðàìåòðû ïåðåäàþòñÿ ÷åðåç ãëîáàëüíûå ïåðåìåííûå: *
;* FDD_Track - íîìåð äîðîæêè (0-79); *
;* FDD_Head - íîìåð ãîëîâêè (0-1). *
;* Ðåçóëüòàò îïåðàöèè çàíîñèòñÿ â FDC_Status. *
;* ПОИСК ДОРОЖКИ *
;* Параметры передаются через глобальные переменные: *
;* FDD_Track - номер дорожки (0-79); *
;* FDD_Head - номер головки (0-1). *
;* Результат операции заносится в FDC_Status. *
;*****************************************************
SeekTrack:
pusha
call save_timer_fdd_motor
; Ïîäàòü êîìàíäó "Ïîèñê"
; Подать команду "Поиск"
mov AL, 0Fh
call FDCDataOutput
; Ïåðåäàòü áàéò íîìåðà ãîëîâêè/íàêîïèòåë
; Передать байт номера головки/накопител
mov AL, [FDD_Head]
shl AL, 2
call FDCDataOutput
; Ïåðåäàòü áàéò íîìåðà äîðîæêè
; Передать байт номера дорожки
mov AL, [FDD_Track]
call FDCDataOutput
; Îæèäàòü çàâåðøåíèÿ îïåðàöèè
; Ожидать завершения операции
call WaitFDCInterrupt
cmp [FDC_Status], FDC_Normal
jne @@Exit
; Ñîõðàíèòü ðåçóëüòàò ïîèñêà
; Сохранить результат поиска
mov AL, 08h
call FDCDataOutput
call FDCDataInput
401,24 → 401,24
mov [FDC_ST0], AL
call FDCDataInput
mov [FDC_C], AL
; Ïðîâåðèòü ðåçóëüòàò ïîèñêà
; Ïîèñê çàâåðøåí?
; Проверить результат поиска
; Поиск завершен?
test [FDC_ST0], 100000b
je @@Err
; Çàäàííûé òðåê íàéäåí?
; Заданный трек найден?
mov AL, [FDC_C]
cmp AL, [FDD_Track]
jne @@Err
; Íîìåð ãîëîâêè ñîâïàäàåò ñ çàäàííûì?
; Номер головки совпадает с заданным?
mov AL, [FDC_ST0]
and AL, 100b
shr AL, 2
cmp AL, [FDD_Head]
jne @@Err
; Îïåðàöèÿ çàâåðøåíà óñïåøíî
; Операция завершена успешно
mov [FDC_Status], FDC_Normal
jmp @@Exit
@@Err: ; Òðåê íå íàéäåí
@@Err: ; Трек не найден
mov [FDC_Status], FDC_TrackNotFound
; mov [flp_status],0
@@Exit:
427,27 → 427,27
ret
 
;*******************************************************
;* ×ÒÅÍÈÅ ÑÅÊÒÎÐÀ ÄÀÍÍÛÕ *
;* Ïàðàìåòðû ïåðåäàþòñÿ ÷åðåç ãëîáàëüíûå ïåðåìåííûå: *
;* FDD_Track - íîìåð äîðîæêè (0-79); *
;* FDD_Head - íîìåð ãîëîâêè (0-1); *
;* FDD_Sector - íîìåð ñåêòîðà (1-18). *
;* Ðåçóëüòàò îïåðàöèè çàíîñèòñÿ â FDC_Status. *
;*  ñëó÷àå óñïåøíîãî âûïîëíåíèÿ îïåðàöèè ÷òåíèÿ *
;* ñîäåðæèìîå ñåêòîðà áóäåò çàíåñåíî â FDD_DataBuffer. *
;* ЧТЕНИЕ СЕКТОРА ДАННЫХ *
;* Параметры передаются через глобальные переменные: *
;* FDD_Track - номер дорожки (0-79); *
;* FDD_Head - номер головки (0-1); *
;* FDD_Sector - номер сектора (1-18). *
;* Результат операции заносится в FDC_Status. *
;* В случае успешного выполнения операции чтения *
;* содержимое сектора будет занесено в FDD_DataBuffer. *
;*******************************************************
ReadSector:
pushad
call save_timer_fdd_motor
; Óñòàíîâèòü ñêîðîñòü ïåðåäà÷è 500 Êáàéò/ñ
; Установить скорость передачи 500 Кбайт/с
mov AX, 0
mov DX, 03F7h
out DX, AL
; Èíèöèàëèçèðîâàòü êàíàë ïðÿìîãî äîñòóïà ê ïàìÿòè
; Инициализировать канал прямого доступа к памяти
mov [dmamode], 0x46
call Init_FDC_DMA
; Ïîäàòü êîìàíäó "×òåíèå äàííûõ"
mov AL, 0E6h ;÷òåíèå â ìóëüòèòðåêîâîì ðåæèìå
; Подать команду "Чтение данных"
mov AL, 0E6h ;чтение в мультитрековом режиме
call FDCDataOutput
mov AL, [FDD_Head]
shl AL, 2
458,19 → 458,19
call FDCDataOutput
mov AL, [FDD_Sector]
call FDCDataOutput
mov AL, 2 ;êîä ðàçìåðà ñåêòîðà (512 áàéò)
mov AL, 2 ;код размера сектора (512 байт)
call FDCDataOutput
mov AL, 18 ;+1; 3Fh ;÷èñëî ñåêòîðîâ íà äîðîæêå
mov AL, 18 ;+1; 3Fh ;число секторов на дорожке
call FDCDataOutput
mov AL, 1Bh ;çíà÷åíèå GPL
mov AL, 1Bh ;значение GPL
call FDCDataOutput
mov AL, 0FFh;çíà÷åíèå DTL
mov AL, 0FFh;значение DTL
call FDCDataOutput
; Îæèäàåì ïðåðûâàíèå ïî çàâåðøåíèè îïåðàöèè
; Ожидаем прерывание по завершении операции
call WaitFDCInterrupt
cmp [FDC_Status], FDC_Normal
jne @@Exit_1
; Ñ÷èòûâàåì ñòàòóñ çàâåðøåíèÿ îïåðàöèè
; Считываем статус завершения операции
call GetStatusInfo
test [FDC_ST0], 11011000b
jnz @@Err_1
485,21 → 485,21
ret
 
;*******************************************************
;* ×ÒÅÍÈÅ ÑÅÊÒÎÐÀ (Ñ ÏÎÂÒÎÐÅÍÈÅÌ ÎÏÅÐÀÖÈÈ ÏÐÈ ÑÁÎÅ) *
;* Ïàðàìåòðû ïåðåäàþòñÿ ÷åðåç ãëîáàëüíûå ïåðåìåííûå: *
;* FDD_Track - íîìåð äîðîæêè (0-79); *
;* FDD_Head - íîìåð ãîëîâêè (0-1); *
;* FDD_Sector - íîìåð ñåêòîðà (1-18). *
;* Ðåçóëüòàò îïåðàöèè çàíîñèòñÿ â FDC_Status. *
;*  ñëó÷àå óñïåøíîãî âûïîëíåíèÿ îïåðàöèè ÷òåíèÿ *
;* ñîäåðæèìîå ñåêòîðà áóäåò çàíåñåíî â FDD_DataBuffer. *
;* ЧТЕНИЕ СЕКТОРА (С ПОВТОРЕНИЕМ ОПЕРАЦИИ ПРИ СБОЕ) *
;* Параметры передаются через глобальные переменные: *
;* FDD_Track - номер дорожки (0-79); *
;* FDD_Head - номер головки (0-1); *
;* FDD_Sector - номер сектора (1-18). *
;* Результат операции заносится в FDC_Status. *
;* В случае успешного выполнения операции чтения *
;* содержимое сектора будет занесено в FDD_DataBuffer. *
;*******************************************************
ReadSectWithRetr:
pusha
; Îáíóëèòü ñ÷åò÷èê ïîâòîðåíèÿ îïåðàöèè ðåêàëèáðîâêè
; Обнулить счетчик повторения операции рекалибровки
mov [RecalRepCounter], 0
@@TryAgain:
; Îáíóëèòü ñ÷åò÷èê ïîâòîðåíèÿ îïåðàöèè ÷òåíè
; Обнулить счетчик повторения операции чтени
mov [ReadRepCounter], 0
@@ReadSector_1:
call ReadSector
507,11 → 507,11
je @@Exit_2
cmp [FDC_Status], 1
je @@Err_3
; Òðîåêðàòíîå ïîâòîðåíèå ÷òåíè
; Троекратное повторение чтени
inc [ReadRepCounter]
cmp [ReadRepCounter], 3
jb @@ReadSector_1
; Òðîåêðàòíîå ïîâòîðåíèå ðåêàëèáðîâêè
; Троекратное повторение рекалибровки
call RecalibrateFDD
call SeekTrack
inc [RecalRepCounter]
527,27 → 527,27
ret
 
;*******************************************************
;* ÇÀÏÈÑÜ ÑÅÊÒÎÐÀ ÄÀÍÍÛÕ *
;* Ïàðàìåòðû ïåðåäàþòñÿ ÷åðåç ãëîáàëüíûå ïåðåìåííûå: *
;* FDD_Track - íîìåð äîðîæêè (0-79); *
;* FDD_Head - íîìåð ãîëîâêè (0-1); *
;* FDD_Sector - íîìåð ñåêòîðà (1-18). *
;* Ðåçóëüòàò îïåðàöèè çàíîñèòñÿ â FDC_Status. *
;*  ñëó÷àå óñïåøíîãî âûïîëíåíèÿ îïåðàöèè çàïèñè *
;* ñîäåðæèìîå FDD_DataBuffer áóäåò çàíåñåíî â ñåêòîð. *
;* ЗАПИСЬ СЕКТОРА ДАННЫХ *
;* Параметры передаются через глобальные переменные: *
;* FDD_Track - номер дорожки (0-79); *
;* FDD_Head - номер головки (0-1); *
;* FDD_Sector - номер сектора (1-18). *
;* Результат операции заносится в FDC_Status. *
;* В случае успешного выполнения операции записи *
;* содержимое FDD_DataBuffer будет занесено в сектор. *
;*******************************************************
WriteSector:
pushad
call save_timer_fdd_motor
; Óñòàíîâèòü ñêîðîñòü ïåðåäà÷è 500 Êáàéò/ñ
; Установить скорость передачи 500 Кбайт/с
mov AX, 0
mov DX, 03F7h
out DX, AL
; Èíèöèàëèçèðîâàòü êàíàë ïðÿìîãî äîñòóïà ê ïàìÿòè
; Инициализировать канал прямого доступа к памяти
mov [dmamode], 0x4A
call Init_FDC_DMA
; Ïîäàòü êîìàíäó "Çàïèñü äàííûõ"
mov AL, 0xC5 ;0x45 ;çàïèñü â ìóëüòèòðåêîâîì ðåæèìå
; Подать команду "Запись данных"
mov AL, 0xC5 ;0x45 ;запись в мультитрековом режиме
call FDCDataOutput
mov AL, [FDD_Head]
shl AL, 2
558,19 → 558,19
call FDCDataOutput
mov AL, [FDD_Sector]
call FDCDataOutput
mov AL, 2 ;êîä ðàçìåðà ñåêòîðà (512 áàéò)
mov AL, 2 ;код размера сектора (512 байт)
call FDCDataOutput
mov AL, 18; 3Fh ;÷èñëî ñåêòîðîâ íà äîðîæêå
mov AL, 18; 3Fh ;число секторов на дорожке
call FDCDataOutput
mov AL, 1Bh ;çíà÷åíèå GPL
mov AL, 1Bh ;значение GPL
call FDCDataOutput
mov AL, 0FFh;çíà÷åíèå DTL
mov AL, 0FFh;значение DTL
call FDCDataOutput
; Îæèäàåì ïðåðûâàíèå ïî çàâåðøåíèè îïåðàöèè
; Ожидаем прерывание по завершении операции
call WaitFDCInterrupt
cmp [FDC_Status], FDC_Normal
jne @@Exit_3
; Ñ÷èòûâàåì ñòàòóñ çàâåðøåíèÿ îïåðàöèè
; Считываем статус завершения операции
call GetStatusInfo
test [FDC_ST0], 11000000b ;11011000b
jnz @@Err_2
584,21 → 584,21
ret
 
;*******************************************************
;* ÇÀÏÈÑÜ ÑÅÊÒÎÐÀ (Ñ ÏÎÂÒÎÐÅÍÈÅÌ ÎÏÅÐÀÖÈÈ ÏÐÈ ÑÁÎÅ) *
;* Ïàðàìåòðû ïåðåäàþòñÿ ÷åðåç ãëîáàëüíûå ïåðåìåííûå: *
;* FDD_Track - íîìåð äîðîæêè (0-79); *
;* FDD_Head - íîìåð ãîëîâêè (0-1); *
;* FDD_Sector - íîìåð ñåêòîðà (1-18). *
;* Ðåçóëüòàò îïåðàöèè çàíîñèòñÿ â FDC_Status. *
;*  ñëó÷àå óñïåøíîãî âûïîëíåíèÿ îïåðàöèè çàïèñè *
;* ñîäåðæèìîå FDD_DataBuffer áóäåò çàíåñåíî â ñåêòîð. *
;* ЗАПИСЬ СЕКТОРА (С ПОВТОРЕНИЕМ ОПЕРАЦИИ ПРИ СБОЕ) *
;* Параметры передаются через глобальные переменные: *
;* FDD_Track - номер дорожки (0-79); *
;* FDD_Head - номер головки (0-1); *
;* FDD_Sector - номер сектора (1-18). *
;* Результат операции заносится в FDC_Status. *
;* В случае успешного выполнения операции записи *
;* содержимое FDD_DataBuffer будет занесено в сектор. *
;*******************************************************
WriteSectWithRetr:
pusha
; Îáíóëèòü ñ÷åò÷èê ïîâòîðåíèÿ îïåðàöèè ðåêàëèáðîâêè
; Обнулить счетчик повторения операции рекалибровки
mov [RecalRepCounter], 0
@@TryAgain_1:
; Îáíóëèòü ñ÷åò÷èê ïîâòîðåíèÿ îïåðàöèè ÷òåíè
; Обнулить счетчик повторения операции чтени
mov [ReadRepCounter], 0
@@WriteSector_1:
call WriteSector
606,11 → 606,11
je @@Exit_4
cmp [FDC_Status], 1
je @@Err_4
; Òðîåêðàòíîå ïîâòîðåíèå ÷òåíè
; Троекратное повторение чтени
inc [ReadRepCounter]
cmp [ReadRepCounter], 3
jb @@WriteSector_1
; Òðîåêðàòíîå ïîâòîðåíèå ðåêàëèáðîâêè
; Троекратное повторение рекалибровки
call RecalibrateFDD
call SeekTrack
inc [RecalRepCounter]
625,7 → 625,7
ret
 
;*********************************************
;* ÏÎËÓ×ÈÒÜ ÈÍÔÎÐÌÀÖÈÞ Î ÐÅÇÓËÜÒÀÒÅ ÎÏÅÐÀÖÈÈ *
;* ПОЛУЧИТЬ ИНФОРМАЦИЮ О РЕЗУЛЬТАТЕ ОПЕРАЦИИ *
;*********************************************
GetStatusInfo:
push AX
/kernel/trunk/blkdev/hd_drv.inc
109,28 → 109,28
xor eax, eax
mov edx, [hdbase]
inc edx
out dx, al; ATAFeatures ॣ¨áâà "®á®¡¥­­®á⥩"
out dx, al; ATAFeatures регистр "особенностей"
inc edx
inc eax
out dx, al; ATASectorCount áçñâ稪 ᥪâ®à®¢
out dx, al; ATASectorCount счётчик секторов
inc edx
mov eax, [esp+4]
out dx, al; ATASectorNumber ॣ¨áâà ­®¬¥à  ᥪâ®à 
out dx, al; ATASectorNumber регистр номера сектора
shr eax, 8
inc edx
out dx, al; ATACylinder ­®¬¥à 樫¨­¤à  (¬« ¤è¨© ¡ ©â)
out dx, al; ATACylinder номер цилиндра (младший байт)
shr eax, 8
inc edx
out dx, al; ­®¬¥à 樫¨­¤à  (áâ à訩 ¡ ©â)
out dx, al; номер цилиндра (старший байт)
shr eax, 8
inc edx
and al, 1+2+4+8
add al, byte [hdid]
add al, 128+64+32
out dx, al; ­®¬¥à £®«®¢ª¨/­®¬¥à ¤¨áª 
out dx, al; номер головки/номер диска
inc edx
mov al, 20h
out dx, al; ATACommand ॣ¨áâà ª®¬ ­¤
out dx, al; ATACommand регистр команд
sti
 
call wait_for_sector_buffer
/kernel/trunk/blkdev/ide_cache.inc
52,7 → 52,7
cmp [dma_hdd], 1
jnz .nodma
@@:
; Ž¡ê¥¤¨­ï¥¬ § ¯¨áì 楯®çª¨ ¯®á«¥¤®¢ â¥«ì­ëå ᥪâ®à®¢ ¢ ®¤­® ®¡à é¥­¨¥ ª ¤¨áªã
; Объединяем запись цепочки последовательных секторов в одно обращение к диску
cmp ecx, 1
jz .nonext
cmp dword [esi+8+4], 2
/kernel/trunk/blkdev/rd.inc
346,10 → 346,10
mov al, '_'
jmp .doit
.yo1:
mov al, 'ð'
mov al, 0xF0 ; 'Ё'
jmp .doit
.yo2:
mov al, 'ñ'
mov al, 0xF1 ; 'ё'
jmp .doit
.rus1:
; 0x410-0x43F -> 0x80-0xAF
389,9 → 389,9
; 0xF0 -> 0x401
; 0xF1 -> 0x451
@@:
cmp al, 'ð'
cmp al, 0xF0 ; 'Ё'
jz .yo1
cmp al, 'ñ'
cmp al, 0xF1 ; 'ё'
jz .yo2
.unk:
mov al, '_' ; ah=0
411,16 → 411,16
jb .ret
cmp al, 'z'
jbe .az
cmp al, 'ñ'
cmp al, 0xF1 ; 'ё'
jz .yo1
cmp al, ' '
cmp al, 0xA0 ; 'а'
jb .ret
cmp al, 'à'
cmp al, 0xE0 ; 'р'
jb .rus1
cmp al, 'ï'
cmp al, 0xEF ; 'я'
ja .ret
; 0xE0-0xEF -> 0x90-0x9F
sub al, 'à'-''
sub al, 0xE0-0x90
.ret:
ret
.rus1: