Листинг 6-6. Исходный текст программы SHOWDRIV.ASM
---------------------------------------------------------------------
PAGE 60,132
; ************ SHOWDRIV *********************************************
;
; SHOWDRIV - Отображение списка загруженных драйверов MS-DOS
;
; ************ INCLUDES *********************************************
;
INCLUDE stdmac.inc
INCLUDE driver.inc
;
; ************ DGROUP (DATA) COMPONENT SEGMENTS *********************
;
_DATA SEGMENT BYTE PUBLIC 'DATA'
_DATA ENDS
;
STACK SEGMENT PARA STACK
dw 1024 dup (?)
STACK ENDS
;
DGROUP GROUP _DATA, STACK
;
; ************ DATA STORAGE & TEMPLATES *****************************
;
_DATA SEGMENT
;
; параметры для поиска
;
nuldev db 'NUL ' ; Имя NUL драйвера
nulattr dw AT_CHR OR AT_NUL ; Слово атрибутов
;
; Текстовые сообщения для вывода на дисплей. Формат :
;
; "Device Type Units Attrib Address STRAT INTRP"
; "-----------------------------------------------------------------"
; "xxxxxxxx xxxx xx xxxx xxxx:xxxx xxxx xxxx"
; "<<< ------------------ End Of Driver List ------------------- >>>"
;
$title db CR,LF
db 'SD-ShowDriv, Version 1.00, Copyright 1988'
db CR,LF,CR,LF
db 'Device Type Units Attrib Address'
db ' STRAT INTRP'
db CR,LF
db '-----------------------------------------------'
db '--------------------'
db CR,LF,'$'
$space db ' $'
$block db '-------- Block $'
$char db 'Char$'
$colon db ':'
$end db CR,LF
db '<<< ------------------ End Of Driver List -----'
db '---------------- >>>'
$crlf db CR,LF,'$'
;
; Шаблон структуры
;
devhead STRUC ; Структура заголовка драйвера
next dd ? ; Указатель на следующего...
attrib dw ? ; Слово атрибутов
strat dw ? ; Смещение программы СТРАТЕГИЙ
intrp dw ? ; Смещение программы ПРЕРЫВАНИЙ
dname db 8 dup (?) ; Имя/количество устройств
term db ? ; Конец заголовка драйвера
devhead ENDS
;
_DATA ENDS
;
; ************ ПРОГРАММА НАЧИНАЕТСЯ ЗДЕСЬ ***************************
;
_TEXT SEGMENT BYTE PUBLIC 'CODE'
ASSUME cs:_TEXT, ds:DGROUP, es:DGROUP, ss:DGROUP
;
EXTRN bin2hex:near ; Шестнадцатиричный вывод
main PROC FAR
mov ax,DGROUP ; Установка сегмента данных
mov ds,ax
;
; Найдем NUL-драйвер с помощью поиска имени "NUL"
;
cld
mov cx,0FFFEh ; Счетчик для поиска
xor ax,ax ;
mov es,ax ; Начало поиска после таблицы
mov di,0400Hh ; прерываний
mov al,nuldev ; Начинаем с поиска этой буквы
search:
repne scasb ; Ищем пока не найдем
jne exit ; Не нашли...
;
push cx ; Возможно нашли...
push di ; Сохраним текущую позицию
mov si,offset nuldev+1 ; Остаток строки "NUL "
mov cx,7 ; Длина остатка
repe cmpsb ; Сравним остаток строки
jne not_it ; Не совпадают...
;
sub di,(offset term - offset attrib) ; Выровняем указатель
cmpsw ; Это атрибут NUL-драйвера ?
jne not_it ; Нет...
add sp,4 ; Удаляем сохраненные DI и CX
sub di,(offset strat - offset next) ; Выравниваем указатель
jmp found_nul ; Нашли заголовок NUL-драйвера!
;
not_it: ; Восстанавливаем позицию
pop di ; и счетчик
pop cx
jmp short search
;
; Нашли заголовок NUL-драйвера. Теперь выводим всю цепочку
;
found_nul:
@DisStr $title ; Выводим название (титул)
show_driver:
call ShowDeviceInfo ; Отобразим заголовок драйвера
cmp word ptr es:[di],-1 ; Проверим на конец цепочки
jne done ; Если (-1) то на выход
les di,es:[di].next ; Если не (-1) то на следующий
jmp short show_driver ; заголовок
done:
@DisStr $end ; Завершающее сообщение
@DisStr $crlf
;
exit: mov al,0 ; Нормальное завершение
@ExitToDOS ; Завершение программы
main ENDP
;
; ************ ShowDeviceInfo ****************************************
; Подпрограмма ShowDeviceInfo отображает блок, адресуемый по ES:DI,
; предполагая что это заголовок драйвера. Формат выводимой информации
; показан выше.
;
ShowDeviceInfo PROC NEAR
test es,[di].attrib,AT_CHR ; Драйвер символьный или
jnz is_char ; блоковый ?
@DisStr $block ; Блоковый (без имени)
xor ah,ah
mov al,es:[di].dname ; Количество устройств
jmp short dis_units
is_char:
push ds ; Сохраним DS
push es ; Выровняем сегменты
pop ds
lea si,es:[di].dname ; SI = смещение имени
mov cx,8 ; Длина имени
show_name:
lodsb ; Выводим по одному символу
@DisChr al ; за раз
loop show_name
pop ds ; Восстанавливаем DS
@DisStr @space
@DisStr @char ; Выводим тип драйвера
@DisStr @space
mov ax,1 ; Только одно устройство
;
dis_units:
mov ch,02 ; Выводим количество устройств
call bin2hex
@DisStr @space
mov ch,04 ; Вывод числовых данных
mov ax,es:[di].attrib
call bin2hex ; Выводим слово атрибутов
@DisStr @space
;
mov ax,es
call bin2hex ; Выводим сегментный адрес
@DisChr $colon
mov ax,di
call bin2hex ; Выводим смещение
@DisStr @space
;
mov ax,es:[di].strat
call bin2hex ; Выводим адрес СТРАТЕГИЙ
@DisStr @space
;
mov ax,es:[di].intrp
call bin2hex ; Выводим адрес ПРЕРЫВАНИЙ
@DisStr @crlf
;
ret
ShowDeviceInfo ENDP
;
; ************ КОНЕЦ ПРОГРАММЫ, КОНЕЦ ФАЙЛА ************************
;
_TEXT ENDS
END main
---------------------------------------------------------------------
|