Сообщение от
AFZ
где взять описание виртуального "железа" HD, чтобы склепать для него дровишки под ДИАМС?
Да собственно описание простое. В примерах:
Код:
;
;РЕГИСТРЫ КОНТРОЛЛЕРА
;
HDCS =: 0 ;РЕГИСТР СОСТОЯНИЯ
HDDA =: 2 ;РЕГИСТР ДАННЫХ
;
;КОМАНДЫ
;
CS.UNI =: 1 ;ВЫБРАТЬ НОМЕР УСТРОЙСТВА
CS.BLK =: 2 ;ВЫБРАТЬ НОМЕР БЛОКА
CS.BUF =: 3 ;УСТАНОВИТЬ АДРЕС БУФЕРА
CS.WCT =: 4 ;УСТАНОВИТЬ КОЛИЧЕСТВО СЛОВ
CS.RLB =: 5 ;ЧТЕНИЕ
CS.WLB =: 6 ;ЗАПИСЬ
CS.SIZ =: 7 ;ПОЛУЧЕНИЕ РАЗМЕРА
MOV #177720,R5 ;РЕГИСТР УСТРОЙСТВА
;
;ПРОВЕРКА ТИПА КОНТРОЛЛЕРА
;
CLR @R5 ;КОМАНДА NOP (ЧИСТКА CSR)
TSTB @R5 ;ПРОВЕРЯЕМ ЧТО В РЕГИСТРЕ
BPL ... ;ЕСЛИ 200 - ЭТО НОВЫЙ КОНТРОЛЛЕР
;ОН СОВМЕСТИМ С 22-BIT
;ИНАЧЕ СТАРЫЙ 16-БИТНЫЙ
;
;РАБОТА С КОНТРОЛЛЕРОМ
;
MOV #unit,HDDA(R5) ;ВЫБОР НОМЕРА УСТРОЙСТВА
MOV #CS.UNI,@R5 ;
;
;ЕСЛИ ПОСЛЕ ЭТОГО СТАРШИЙ БИТ HDCS УСТАНОВЛЕН - УСТРОЙСТВО НЕ ПОДКЛЮЧЕНО.
;В НОВОМ КОНТРОЛЛЕРЕ ТАКЖЕ ПОСЛЕ ВЫПОЛНЕНИЯ КОМАНДЫ МЛАДШИЙ БАЙТ HDDA
;СОДЕРЖИТ КОД ОШИБКИ СОВМЕСТИМЫЙ С RSX-11, ПРИ ОШИБКЕ ОН ОТРИЦАТЕЛЬНЫЙ
;
MOV #blkn,HDDA(R5) ;ВЫБОР НОМЕРА БЛОКА
MOV #CS.BLK,@R5 ;
;
;ВОЗВРАЩАЕТ ОШИБКУ ЕСЛИ БЛОК ВЫХОДИТ ЗА ПРЕДЕЛЫ ДИСКА
;
MOV #buff,HDDA(R5) ;ВЫБОР АДРЕСА БУФЕРА
MOV #CS.BUF,@R5 ;(БИТЫ 0-15)
;
;ДЛЯ СТАРОГО КОНТРОЛЛЕРА ЭТ ВСЕ. ДЛЯ НОВОГО СТАРШИЕ БИТЫ
;АДРЕСА НУЖНО ЗАПИСАТЬ В СТАРШИЙ БАЙТ HDCS (МОЖНО С
;КОМАНДОЙ ЧТЕНИЯ/ЗАПИСИ
;
MOV #wcnt,HDDA(R5) ;КОЛИЧЕСТВО СЛОВ ДЛЯ ПЕРЕДАЧИ
MOV #CS.WCT,@R5 ;
;
;МОЖЕТ ВЕРНУТЬ ОШИБКУ ЕСЛИ В РЕЗУЛЬТАТЕ ОПЕРАЦИИ БУДЕТ ВЫХОД
;ЗА ПРЕДЕЛЫ ДИСКА
;
MOV #CS.RLB,@R5 ;ЗАПУСК I/O
;
;КАК ПИСАЛОСЬ ВЫШЕ, В СТАРШЕМ БАЙТЕ ДОЛЖНЫ БЫТЬ СТАРШИЕ БИТЫ
;АДРЕСА ДЛЯ НОВОГО КОНТРОЛЛЕРА. МОЖНО ВМЕСТЕ С КОМАНДОЙ,
;МОЖНО ЗАРАНЕЕ ЗАПИСАТЬ, А ЗАПУСКАТЬ КОМАНДОЙ MOVB.
;
Ну и остается команда получения размера диска (он ограничен 65535 блоками). Сначала выбрать устройство, потом записать команду CS.SIZ и прочитать размер из регистра данных.
Сейчас занимаюсь RSXными делами и позже предложе третью версию спецификации, совместимую с первыми двумя
- - - Добавлено - - -
Код:
.DRBEG HD
MOV (PC)+,R3 ;GET CSR ADDRESS
HDCSR: .WORD HD$CSR ;
MOV HDCQE,R5 ;GET ADDRESS OF QUEUE ELEMENT
MOV R5,R4 ;
MOV (R5)+,R0 ;GET BLOCK NUMBER
MOVB (R5)+,R1 ;GET FUNCTION CODE
MOVB (R5)+,R2 ;GET UNIT NUMBER
BIC #^C7,R2 ;MASK IRRELEVANT BITS
MOV R2,HDDA(R3) ;SET DEVICE UNIT
MOV #CS.UNI,@R3 ;
TST @R3 ;DEVICE ONLINE?
BMI HDERR ;IF MI NO
TSTB R1 ;SPFUN REQUESTED
BMI HDFUN ;IF MI YES
MOV R0,HDDA(R3) ;SET BLOCK NUMBER
MOV #CS.BLK,@R3 ;
TST @R3 ;BLOCK NUMBER TOO LAGRE?
BMI HDEOF ;IF MI YES
.IF EQ MMG$T
CLR R1 ;ZERO BAE
MOV (R5)+,HDDA(R3) ;SET BUFFER ADDRESS
.IFF
CALL @$MPPTR ;MAP I/O BUFFER
MPPTR =: .-2 ;*** PATCH ***
MOV (SP)+,R0 ;GET BUFFER ADDRESS
MOV (SP)+,R1 ;GET BAE
BEQ 10$ ;IF EQ 16-BIT ADDRESS
TSTB @R3 ;22-BIT CONTROLLER?
BPL HDERR ;IF PL NO
ASH #4,R1 ;SHIFL LEFT (SAFE TO USE ASH)
10$: MOV R0,HDDA(R3) ;SET BUFFER ADDRESS
.ENDC
MOV #CS.BUF,@R3 ;SET BUFFER ADDRESS
MOV #CS.RLB,R0 ;ASSUME READ COMMAND
MOV (R5)+,R2 ;GET WORD COUNT
BPL 20$ ;IF PL READ
MOV #CS.WLB,R0 ;SET WRITE COMMAND
NEG R2 ;
20$: MOV R2,HDDA(R3) ;SET WORD COUNT
MOV #CS.WCT,@R3 ;
TST @R3 ;READ/WRITE PAST END OF DEVICE?
BPL 30$ ;IF PL NO
BIS #EOF$,@-2(R4) ;SET END OF FILE STATUS
30$: BIS R0,R1 ;MEGRE IN BAE
MOV R1,@R3 ;START I/O
TST @R3 ;I/O ERROR?
BPL HDFIN ;IF PL NO
HDERR: BIS #HDERR$,@-(R4) ;SET HARD ERROR STATUS
HDFIN: .DRFIN HD ;FINISH I/O
HDEOF: BIS #EOF$,@-(R4) ;SET END OF FILE STATUS
BR HDFIN ;FINISH I/O
HDFUN: CMPB #SF.SIZ,R1 ;GET DEVICE SIZE FUNCTION?
BNE HDERR ;IF NE NO
MOV #CS.SIZ,@R3 ;GET DEVICE SIZE
.IF EQ MMG$T
MOV HDDA(R3),@(R5)+ ;PUT INTO BUFFER
.IFF
MOV HDDA(R3),-(SP) ;PUT INTO BUFFER
CALL @$PTWRD ;
PTWRD =: .-2 ;*** PATCH ***
.ENDC
BR HDFIN ;FINISH I/O