📄 rxdosdev.asm
字号:
cmp al, -1 ; character device ?
jz initReqBlock_08 ; yes, skip address -->
call getAddrDPB ; get address of Drive Paramater Block
mov al, es:[ _dpbUnit ][ bx ] ; get unit
initReqBlock_08:
push ax ; save unit
push di
setES ss
xor al, al
mov cx, sizeMaxReqHeader
rep stosb ; init request block
pop di
mov al, sizeMaxReqHeader
cmp ah, sizeDevDefaultLength
jnc initReqBlock_12
mov bl, ah
xor bh, bh
mov al, byte ptr ss:[ devDefaultLength ][ bx ]
initReqBlock_12:
mov byte ptr es:[ rwrLength ][ di ], al
setES ss
pop ax ; unit
cmp al, -1 ; character device ?
jnz initReqBlock_16 ; no -->
xor al, al ; set unit to 00
initReqBlock_16:
mov byte ptr es:[ rwrUnit ][ di ], al ; set unit
mov byte ptr es:[ rwrFunction ][ di ], ah ; set function
mov bx, di
pop ax ; restore drive
ret
;- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
; default length table
;- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
devDefaultLength:
db sizeMaxReqHeader ; device init
db sizeMEDIAReqHeader ; media request
db sizeBUILDBPBReqHeader ; build dpb
db sizeMaxReqHeader ; ioctl read
db sizeREADReqHeader ; device read
db sizeREADReqHeader ; non destr read
db sizeMaxReqHeader ; input status
db sizeMaxReqHeader ; input flush
db sizeMaxReqHeader ; device write
db sizeMaxReqHeader ; device write verify
db sizeMaxReqHeader ; output status
db sizeMaxReqHeader ; output flush
db sizeMaxReqHeader ; ioctl write
db sizeMaxReqHeader ; open device
db sizeMaxReqHeader ; close device
db sizeMaxReqHeader ; removable media
db sizeMaxReqHeader ; output till busy
db sizeMaxReqHeader ; generic ioctl
db sizeMaxReqHeader ; get logical device
db sizeMaxReqHeader ; set logical device
db sizeMaxReqHeader ; ioctl query
sizeDevDefaultLength equ ($ - devDefaultLength)
;''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''';
; Get Address of Device Parameter Block ;
;- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -;
; ;
; Input: ;
; ax drive ;
; ;
; Output: ;
; ax drive ;
; es:bx address of device parameter block for drive ;
;...............................................................;
getAddrDPB:
push ax
push cx
les bx, dword ptr ss:[ _RxDOS_pCDS ] ; point to CDS
and ax, 7fh ; optimize for drive A:
jz getAddrDPB_08 ; if true -->
mov cl, sizeCDS
mul cl ; create CDS offset
add bx, ax
getAddrDPB_08:
mov ax, word ptr es:[ _cdsPtrToDPB. _segment ][ bx ]
or ax, word ptr es:[ _cdsPtrToDPB. _pointer ][ bx ]
stc ; set error if not intialized
jz getAddrDPB_12 ; not initialized -->
clc
les bx, dword ptr es:[ _cdsPtrToDPB ][ bx ] ; else, pointer is valid.
getAddrDPB_12:
pop cx
pop ax
ret
;''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''';
; Get Device Parameter Block ;
;- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -;
; ;
; Input: ;
; ax drive ;
; ;
; Output: ;
; ax drive ;
; es:bx address of device parameter block for drive ;
;...............................................................;
getDPB:
Entry
def _drive, ax
ddef _dpbAddress
defbytes _devVolumeId, sizeVolumeID
;- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
; see if valid and initialized
;- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
saveAllRegisters
call getAddrDPB
jc getDPB_36 ; if device does not exist -->
stordarg _dpbAddress, es, bx ; save valid address
;- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
; see if removable media and disk changed
;- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
getDPB_08:
getarg ax, _drive ; restore drive
getdarg es, bx, _dpbAddress ; get address of dpb
mov ah, byte ptr es:[ _dpbMediaDescriptor ][ bx ]
lea bx, _devVolumeId [ bp ] ; location to store new label id
call DevMediaRequest ; rebuild Media ID if removable
jc getDPB_24 ; if error, attempt initialize -->
getdarg es, bx, _dpbAddress ; get address of dpb
cmp byte ptr es:[ _dpbAccessFlag ][ bx ], -1 ; this block used before ?
jz getDPB_24 ; no, so just initialize now -->
cmp cl, MEDIA_HASCHANGED ; has media changed ?
jnz getDPB_30 ; no, it has not changed -->
getDPB_10:
cmp ch, byte ptr es:[ _dpbMediaDescriptor ][ bx ]
jnz getDPB_24 ; if different media type -->
mov ax, word ptr [ _devVolumeId. _Low ][ bp ]
cmp ax, word ptr es:[ _dpbVolumeId. _Low ][ bx ]
jnz getDPB_24 ; if different volume -->
mov ax, word ptr [ _devVolumeId. _High ][ bp ]
cmp ax, word ptr es:[ _dpbVolumeId. _High ][ bx ]
jz getDPB_30 ; if same volume, then ok -->
;- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
; init drive parameters
;- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
getDPB_24:
getarg ax, _drive
call invalidateBuffers ; invalidate buffers
call initDriveParameters ; rebuild drive parameters
getdarg es, bx, _dpbAddress ; get address of dpb
mov word ptr es:[ _dpbFreeCount ][ bx ], -1 ; invalidate disk free space
mov ax, word ptr [ _devVolumeId. _Low ][ bp ]
mov dx, word ptr [ _devVolumeId. _High ][ bp ]
mov word ptr es:[ _dpbVolumeId. _Low ][ bx ], ax
mov word ptr es:[ _dpbVolumeId. _High ][ bx ], dx
;- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
; return
;- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
getDPB_30:
clc
getDPB_36:
restoreAllRegisters
getdarg es, bx, _dpbAddress ; get address of dpb
Return
;''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''';
; Translate BIOS Parameter Block to DPB ;
;- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -;
; ;
; Input: ;
; arg pointer to bios parameter block ;
; arg pointer to drive parameter block ;
; ;
;...............................................................;
DefineDPB: ; aka BuildDPB:
Entry 4
darg _biosParamBlock
darg _dosDiskParamBlock
SaveSegments
getdarg ds, di, _biosParamBlock
getdarg es, bx, _dosDiskParamBlock
mov ax, word ptr [ _bpbBytesPerSector ][ di ]
mov word ptr es:[ _dpbBytesPerSector ][ bx ], ax
mov ax, word ptr [ _bpbResSectors ][ di ]
mov word ptr es:[ _dpbFirstFAT ][ bx ], ax
mov al, byte ptr [ _bpbNumCopiesFAT ][ di ]
mov byte ptr es:[ _dpbNumCopiesFAT ][ bx ], al
mov al, byte ptr [ _bpbMediaDescriptor ][ di ]
mov byte ptr es:[ _dpbMediaDescriptor ][ bx ], al
mov ax, word ptr [ _bpbSectorsPerFat ][ di ]
mov word ptr es:[ _dpbSectorsPerFat ][ bx ], ax
; compute shift and mask factors for sectors/cluster
mov al, byte ptr [ _bpbSectorsPerCluster ][ di ]
push di
push es
currSegment es
mov di, offset _bitShiftTable
mov cx, sizeShiftTable
repnz scasb
sub cx, sizeShiftTable - 1
neg cx ; proper sense
pop es
mov byte ptr es:[ _dpbClusterSizeShift ][ bx ], cl
dec al
mov byte ptr es:[ _dpbClusterSizeMask ][ bx ], al
pop di
push cx ; save shift
; compute reserved/ max sectors
xor ax, ax
mov al, byte ptr [ _bpbNumCopiesFAT ][ di ]
mul word ptr [ _bpbSectorsPerFat ][ di ] ; ignore dx
add ax, word ptr [ _bpbResSectors ][ di ]
mov word ptr es:[ _dpbFirstDirSector ][ bx ], ax
xor dx, dx
mov ax, word ptr [ _bpbMaxAllocRootDir ][ di ]
mov word ptr es:[ _dpbMaxAllocRootDir ][ bx ], ax
mov cx, sizeDIRENTRY
mul cx
add ax, word ptr [ _bpbBytesPerSector ][ di ]
dec ax
div word ptr [ _bpbBytesPerSector ][ di ] ;** convert to div 32
add ax, word ptr es:[ _dpbFirstDirSector ][ bx ]
mov word ptr es:[ _dpbFirstDataSector ][ bx ], ax
xor dx, dx
mov ax, word ptr [ _bpbMaxSectors ][ di ]
or ax, ax
jnz DefineDPB_08 ; value is legitimate
mov dx, word ptr [ _bpbHugeSectors. _high ][ di ]
mov ax, word ptr [ _bpbHugeSectors. _low ][ di ]
DefineDPB_08:
sub ax, word ptr es:[ _dpbFirstDataSector ][ bx ]
sbb dx, 0000
pop cx ; restore shift value
DefineDPB_12:
or cx, cx
jz DefineDPB_14
shr dx, 1
rcr ax, 1
loop DefineDPB_12
DefineDPB_14:
; inc ax
mov word ptr es:[ _dpbMaxClusterNumber ][ bx ], ax
or ax, ax
mov byte ptr es:[ _dpbAccessFlag ][ bx ], 00
RestoreSegments
Return
;''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''';
; Init Drive Parameters ;
;- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -;
;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -