Subversion Repositories Kolibri OS

Rev

Rev 593 | Rev 2288 | Go to most recent revision | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
431 serge 1
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2
;;                                                              ;;
3
;; Copyright (C) KolibriOS team 2004-2007. All rights reserved. ;;
4
;; Distributed under terms of the GNU General Public License    ;;
5
;;                                                              ;;
6
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
7
 
593 mikedld 8
$Revision: 1276 $
9
 
10
 
1 ha 11
;******************************************************
12
; поиск приводов HDD и CD
13
; автор исходного текста Кулаков Владимир Геннадьевич.
14
; адаптация и доработка Mario79
15
;******************************************************
16
 
17
;****************************************************
18
;*                 ПОИСК HDD и CD                   *
19
;****************************************************
20
FindHDD:
21
        mov     [ChannelNumber],1
22
        mov     [DiskNumber],0
23
        call    FindHDD_3
346 diamond 24
;        mov     ax,[Sector512+176]
389 serge 25
;        mov     [DRIVE_DATA+6],ax
346 diamond 26
;        mov     ax,[Sector512+126]
389 serge 27
;        mov     [DRIVE_DATA+8],ax
346 diamond 28
;        mov     ax,[Sector512+128]
389 serge 29
;        mov     [DRIVE_DATA+8],ax
1 ha 30
        mov     [DiskNumber],1
31
        call    FindHDD_3
346 diamond 32
;        mov     al,[Sector512+176]
389 serge 33
;        mov     [DRIVE_DATA+7],al
1 ha 34
        inc     [ChannelNumber]
35
        mov     [DiskNumber],0
36
        call    FindHDD_3
346 diamond 37
;        mov     al,[Sector512+176]
389 serge 38
;        mov     [DRIVE_DATA+8],al
1 ha 39
        mov     [DiskNumber],1
40
        call    FindHDD_1
346 diamond 41
;        mov     al,[Sector512+176]
389 serge 42
;        mov     [DRIVE_DATA+9],al
43
 
1 ha 44
        jmp     EndFindHDD
45
 
46
FindHDD_1:
47
        call    ReadHDD_ID
48
        cmp     [DevErrorCode],0
49
        jne     FindHDD_2
346 diamond 50
        cmp     [Sector512+6],word 16
51
        ja      FindHDD_2
52
        cmp     [Sector512+12],word 255
53
        ja      FindHDD_2
389 serge 54
        inc     byte [DRIVE_DATA+1]
346 diamond 55
        jmp     FindHDD_2_2
1 ha 56
   FindHDD_2:
346 diamond 57
        call    DeviceReset
58
        cmp     [DevErrorCode],0
59
        jne     FindHDD_2_2
1 ha 60
        call    ReadCD_ID
61
        cmp     [DevErrorCode],0
62
        jne      FindHDD_2_2
389 serge 63
        inc     byte [DRIVE_DATA+1]
64
        inc     byte [DRIVE_DATA+1]
1 ha 65
   FindHDD_2_2:
66
        ret
67
 
68
FindHDD_3:
69
        call    FindHDD_1
389 serge 70
        shl     byte [DRIVE_DATA+1],2
1 ha 71
        ret
72
 
73
 
74
; Адрес считываемого сектора в режиме LBA
1276 Lrz 75
uglobal
1 ha 76
SectorAddress   DD ?
1276 Lrz 77
endg
1 ha 78
;*************************************************
79
;*     ЧТЕНИЕ ИДЕНТИФИКАТОРА ЖЕСТКОГО ДИСКА      *
80
;* Входные параметры передаются через глобальные *
81
;* переменные:                                   *
82
;* ChannelNumber - номер канала (1 или 2);       *
83
;* DiskNumber - номер диска на канале (0 или 1). *
84
;* Идентификационный блок данных считывается     *
85
;* в массив Sector512.                           *
86
;*************************************************
87
ReadHDD_ID:
88
; Задать режим CHS
89
        mov     [ATAAddressMode],0
90
; Послать команду идентификации устройства
91
        mov     [ATAFeatures],0
92
        mov     [ATAHead],0
93
        mov     [ATACommand],0ECh
94
        call    SendCommandToHDD
95
        cmp     [DevErrorCode],0 ;проверить код ошибки
96
        jne     @@End  ;закончить, сохранив код ошибки
97
        mov     DX,[ATABasePortAddr]
389 serge 98
        add     DX,7     ;адрес регистра состояни
1 ha 99
        mov  ecx,0xffff
100
@@WaitCompleet:
101
        ; Проверить время выполнения команды
102
        dec  ecx
1276 Lrz 103
;        cmp  ecx,0
104
        jz     @@Error1   ;ошибка тайм-аута
1 ha 105
        ; Проверить готовность
106
        in      AL,DX
107
        test    AL,80h   ;состояние сигнала BSY
108
        jnz     @@WaitCompleet
109
        test    AL,1     ;состояние сигнала ERR
110
        jnz     @@Error6
111
        test    AL,08h   ;состояние сигнала DRQ
112
        jz      @@WaitCompleet
113
; Принять блок данных от контроллера
114
;        mov     AX,DS
115
;        mov     ES,AX
116
        mov     EDI,Sector512  ;offset Sector512
117
        mov     DX,[ATABasePortAddr] ;регистр данных
118
        mov     CX,256   ;число считываемых слов
119
        rep     insw     ;принять блок данных
1276 Lrz 120
	ret
1 ha 121
; Записать код ошибки
122
@@Error1:
123
        mov     [DevErrorCode],1
1276 Lrz 124
	ret
1 ha 125
@@Error6:
126
        mov     [DevErrorCode],6
127
@@End:  ret
128
 
129
 
1276 Lrz 130
iglobal
1 ha 131
; Стандартные базовые адреса каналов 1 и 2
132
StandardATABases DW 1F0h, 170h
1276 Lrz 133
endg
134
uglobal
1 ha 135
; Номер канала
136
ChannelNumber   DW ?
137
; Номер диска
138
DiskNumber      DB ?
139
; Базовый адрес группы портов контроллера ATA
140
ATABasePortAddr DW ?
141
; Параметры ATA-команды
142
ATAFeatures     DB ? ;особенности
143
ATASectorCount  DB ? ;количество обрабатываемых секторов
144
ATASectorNumber DB ? ;номер начального сектора
145
ATACylinder     DW ? ;номер начального цилиндра
146
ATAHead         DB ? ;номер начальной головки
147
ATAAddressMode  DB ? ;режим адресации (0 - CHS, 1 - LBA)
148
ATACommand      DB ? ;код команды, подлежащей выполнению
149
; Код ошибки (0 - нет ошибок, 1 - превышен допустимый
150
; интервал ожидания, 2 - неверный код режима адресации,
151
; 3 - неверный номер канала, 4 - неверный номер диска,
152
; 5 - неверный номер головки, 6 - ошибка при выполнении
153
; команды)
1276 Lrz 154
DevErrorCode dd ?
155
endg
1 ha 156
;****************************************************
157
;*          ПОСЛАТЬ КОМАНДУ ЗАДАННОМУ ДИСКУ         *
158
;* Входные параметры передаются через глобальные    *
159
;* переменные:                                      *
160
;* ChannelNumber - номер канала (1 или 2);          *
161
;* DiskNumber - номер диска (0 или 1);              *
162
;* ATAFeatures - "особенности";                     *
163
;* ATASectorCount - количество секторов;            *
164
;* ATASectorNumber - номер начального сектора;      *
165
;* ATACylinder - номер начального цилиндра;         *
166
;* ATAHead - номер начальной головки;               *
167
;* ATAAddressMode - режим адресации (0-CHS, 1-LBA); *
168
;* ATACommand - код команды.                        *
169
;* После успешного выполнения функции:              *
170
;* в ATABasePortAddr - базовый адрес HDD;           *
171
;* в DevErrorCode - ноль.                           *
172
;* При возникновении ошибки в DevErrorCode будет    *
173
;* возвращен код ошибки.                            *
174
;****************************************************
175
SendCommandToHDD:
176
; Проверить значение кода режима
177
        cmp     [ATAAddressMode],1
178
        ja      @@Err2
179
; Проверить корректность номера канала
180
        mov     BX,[ChannelNumber]
181
        cmp     BX,1
182
        jb      @@Err3
183
        cmp     BX,2
184
        ja      @@Err3
185
; Установить базовый адрес
186
        dec     BX
187
        shl     BX,1
188
        movzx   ebx,bx
189
        mov     AX,[ebx+StandardATABases]
190
        mov     [ATABasePortAddr],AX
191
; Ожидание готовности HDD к приему команды
192
        ; Выбрать нужный диск
193
        mov     DX,[ATABasePortAddr]
194
        add     DX,6    ;адрес регистра головок
195
        mov     AL,[DiskNumber]
196
        cmp     AL,1    ;проверить номера диска
197
        ja      @@Err4
198
        shl     AL,4
199
        or      AL,10100000b
200
        out     DX,AL
201
        ; Ожидать, пока диск не будет готов
202
        inc     DX
203
        mov  ecx,0xfff
204
;        mov     eax,[timer_ticks]
205
;        mov     [TickCounter_1],eax
206
@@WaitHDReady:
389 serge 207
        ; Проверить время ожидани
1 ha 208
        dec  ecx
1276 Lrz 209
;        cmp  ecx,0
210
        jz     @@Err1
1 ha 211
;        mov     eax,[timer_ticks]
212
;        sub     eax,[TickCounter_1]
389 serge 213
;        cmp     eax,300    ;ожидать 300 тиков
1 ha 214
;        ja      @@Err1   ;ошибка тайм-аута
389 serge 215
        ; Прочитать регистр состояни
1 ha 216
        in      AL,DX
217
        ; Проверить состояние сигнала BSY
218
        test    AL,80h
219
        jnz     @@WaitHDReady
220
        ; Проверить состояние сигнала DRQ
221
        test    AL,08h
222
        jnz     @@WaitHDReady
223
; Загрузить команду в регистры контроллера
224
        cli
225
        mov     DX,[ATABasePortAddr]
226
        inc     DX      ;регистр "особенностей"
227
        mov     AL,[ATAFeatures]
228
        out     DX,AL
229
        inc     DX      ;счетчик секторов
230
        mov     AL,[ATASectorCount]
231
        out     DX,AL
232
        inc     DX      ;регистр номера сектора
233
        mov     AL,[ATASectorNumber]
234
        out     DX,AL
235
        inc     DX      ;номер цилиндра (младший байт)
236
        mov     AX,[ATACylinder]
237
        out     DX,AL
238
        inc     DX      ;номер цилиндра (старший байт)
239
        mov     AL,AH
240
        out     DX,AL
241
        inc     DX      ;номер головки/номер диска
242
        mov     AL,[DiskNumber]
243
        shl     AL,4
244
        cmp     [ATAHead],0Fh ;проверить номер головки
245
        ja      @@Err5
246
        or      AL,[ATAHead]
247
        or      AL,10100000b
248
        mov     AH,[ATAAddressMode]
249
        shl     AH,6
250
        or      AL,AH
251
        out     DX,AL
252
; Послать команду
253
        mov     AL,[ATACommand]
254
        inc     DX      ;регистр команд
255
        out     DX,AL
256
        sti
257
; Сбросить признак ошибки
258
        mov     [DevErrorCode],0
1276 Lrz 259
        ret
1 ha 260
; Записать код ошибки
261
@@Err1: mov     [DevErrorCode],1
1276 Lrz 262
        ret
1 ha 263
@@Err2: mov     [DevErrorCode],2
1276 Lrz 264
        ret
1 ha 265
@@Err3: mov     [DevErrorCode],3
1276 Lrz 266
        ret
1 ha 267
@@Err4: mov     [DevErrorCode],4
1276 Lrz 268
        ret
1 ha 269
@@Err5: mov     [DevErrorCode],5
270
; Завершение работы программы
271
        ret
272
 
273
;*************************************************
274
;*     ЧТЕНИЕ ИДЕНТИФИКАТОРА УСТРОЙСТВА ATAPI    *
275
;* Входные параметры передаются через глобальные *
276
;* перменные:                                    *
277
;* ChannelNumber - номер канала;                 *
278
;* DiskNumber - номер диска на канале.           *
279
;* Идентификационный блок данных считывается     *
280
;* в массив Sector512.                           *
281
;*************************************************
282
ReadCD_ID:
283
; Задать режим CHS
284
        mov     [ATAAddressMode],0
285
; Послать команду идентификации устройства
286
        mov     [ATAFeatures],0
287
        mov     [ATASectorCount],0
288
        mov     [ATASectorNumber],0
289
        mov     [ATACylinder],0
290
        mov     [ATAHead],0
291
        mov     [ATACommand],0A1h
292
        call    SendCommandToHDD
293
        cmp     [DevErrorCode],0 ;проверить код ошибки
294
        jne     @@End_1  ;закончить, сохранив код ошибки
295
; Ожидать готовность данных HDD
296
        mov     DX,[ATABasePortAddr]
297
        add     DX,7   ;порт 1х7h
1276 Lrz 298
        mov  	ecx,0xffff
1 ha 299
@@WaitCompleet_1:
389 serge 300
        ; Проверить врем
1276 Lrz 301
        dec  	ecx
302
;        cmp  	ecx,0
303
        jz     @@Error1_1  ;ошибка тайм-аута
1 ha 304
        ; Проверить готовность
305
        in      AL,DX
306
        test    AL,80h   ;состояние сигнала BSY
307
        jnz     @@WaitCompleet_1
308
        test    AL,1     ;состояние сигнала ERR
309
        jnz     @@Error6_1
310
        test    AL,08h   ;состояние сигнала DRQ
311
        jz      @@WaitCompleet_1
312
; Принять блок данных от контроллера
313
;        mov     AX,DS
314
;        mov     ES,AX
315
        mov     EDI,Sector512  ;offset Sector512
316
        mov     DX,[ATABasePortAddr] ;порт 1x0h
317
        mov     CX,256 ;число считываемых слов
318
        rep     insw
1276 Lrz 319
        ret
1 ha 320
; Записать код ошибки
321
@@Error1_1:
322
        mov     [DevErrorCode],1
1276 Lrz 323
        ret
1 ha 324
@@Error6_1:
325
        mov     [DevErrorCode],6
326
@@End_1:
327
        ret
328
 
329
;*************************************************
330
;*                СБРОС УСТРОЙСТВА               *
331
;* Входные параметры передаются через глобальные *
332
;* переменные:                                   *
333
;* ChannelNumber - номер канала (1 или 2);       *
334
;* DiskNumber - номер диска (0 или 1).           *
335
;*************************************************
336
DeviceReset:
337
; Проверить корректность номера канала
338
        mov     BX,[ChannelNumber]
339
        cmp     BX,1
340
        jb      @@Err3_2
341
        cmp     BX,2
342
        ja      @@Err3_2
343
; Установить базовый адрес
344
        dec     BX
345
        shl     BX,1
346
        movzx   ebx,bx
347
        mov     DX,[ebx+StandardATABases]
348
        mov     [ATABasePortAddr],DX
349
; Выбрать нужный диск
350
        add     DX,6    ;адрес регистра головок
351
        mov     AL,[DiskNumber]
352
        cmp     AL,1    ;проверить номера диска
353
        ja      @@Err4_2
354
        shl     AL,4
355
        or      AL,10100000b
356
        out     DX,AL
357
; Послать команду "Сброс"
358
        mov     AL,08h
359
        inc     DX      ;регистр команд
360
        out     DX,AL
143 diamond 361
        mov     ecx,0x80000
1 ha 362
@@WaitHDReady_1:
389 serge 363
        ; Проверить время ожидани
1 ha 364
        dec     ecx
1276 Lrz 365
;        cmp     ecx,0
1 ha 366
        je      @@Err1_2 ;ошибка тайм-аута
389 serge 367
        ; Прочитать регистр состояни
1 ha 368
        in      AL,DX
369
        ; Проверить состояние сигнала BSY
370
        test    AL,80h
371
        jnz     @@WaitHDReady_1
372
; Сбросить признак ошибки
373
        mov     [DevErrorCode],0
1276 Lrz 374
        ret
1 ha 375
; Обработка ошибок
376
@@Err1_2: mov     [DevErrorCode],1
1276 Lrz 377
        ret
1 ha 378
@@Err3_2: mov     [DevErrorCode],3
1276 Lrz 379
        ret
1 ha 380
@@Err4_2: mov     [DevErrorCode],4
381
; Записать код ошибки
382
        ret
383
 
384
EndFindHDD:
385