Estex-DSS/DSS/DOS_FM.ASM
Anatoliy Belyanskiy 91774c8b23 Initial commit
Estex DSS
2023-06-14 19:09:19 +10:00

832 lines
12 KiB
NASM

;[BEGIN]
;//MODULE: DOS_FM
;//CREATE: 19-05-1998 AUTHOR: Denis Parinov
;//UPDATE: 24-10-1999 DNS Restore module
;---------------------------------------------------------------
;Rev Date Name Description
;---------------------------------------------------------------
;R01 16-11-1999 DNS ERROR READING FAT CHAIN
;---------------------------------------------------------------
;FMS DB FMCOUNT
;ACCESS MODE:
; 00 - READ/WRITE
; 01 - READ
; 02 - WRITE
;FM_BUF:
;File Manipulator (FM)
; BYTE '. ' ;+00 NAME
; BYTE ' ' ;+08 EXT
; BYTE #10 ;+11 ATTRIBUT
; BYTE 0 ;+12 RESERVED; !TODO á«¥¤ãî騩 ª« áâ¥à ¤«ï ç⥭¨ï
; BYTE 0 ;+13 RESERVED; !TODO á«¥¤ãî騩 ª« áâ¥à ¤«ï § ¯¨á¨
; BLOCK 8,0 ;+14 RESERVED
; WORD #0000 ;+22 TIME
; WORD #0000 ;+24 DATE
; WORD #0000 ;+26 START CLUSTER
; DWORD #0000 ;+28 SIZE FILE
; DWORD #0000 ;+32 FILE POSITION (FP)
; WORD #0000 ;+36 DIRECTORY CLUSTER
; WORD #0000 ;+38 HANDLE NUMBER
; BYTE #00 ;+40 DRIVE OR CURRENT
; BYTE #00 ;+41 ACCESS MODE
; BYTE #00 ;+42 TASK
; BYTE #00 ;+43 EMPTY
/*
;!TEST
FM_BUF: _sFM
.Size EQU _sFM
BLOCK (FMCOUNT-1)*FM_BUF.Size, 0
*/
MACRO _mFM_FIND
CP FMCOUNT+1
JR NC,ABS_FM
PUSH DE
LD IY,FM_BUF
LD DE,FM_BUF.Size
AND A
JR Z,.endLoop
.loop: ADD IY,DE
DEC A
JR NZ,.loop
.endLoop:
POP DE
; A=0
OR (IY) ;+00 NAME
ENDM
SET_FM:
_mFM_FIND
LD A,0 ;!FIXIT ­®¬¥à ®è¨¡ª¨
RET NZ
ABS_FM LD A,DSS_Error.sys.INVALID_HANDLE
SCF
RET
RES_FM:
_mFM_FIND
LD A,5
EXX
SCF
RET Z
XOR A
LD (IY+0),A
RET
GET_FM: LD B,FMCOUNT
LD C,#FF
LD IY,FM_BUF-FM_BUF.Size
LD DE,FM_BUF.Size
.loop: ADD IY,DE
INC C
LD A,(IY+0)
OR A
RET Z
DJNZ .loop
LD A,DSS_Error.sys.NO_HANDLES
SCF
RET
; HL:IX - OFFSET POINTER
; A - FILE MANIPULATOR
MOVE_FP CALL SET_FM
RET C
INC B
DEC B
JR Z,.F_start
DEC B
JR Z,.F_current
DEC B
JR Z,.B_end
LD A,DSS_Error.sys.INVALID_FUNCTION
SCF
RET
;from Start File
.F_start:
; B=0
LD C,B
LD D,B
LD E,B
JR MOVE_F1
;from End File
.B_end: LD C,(IY+28)
LD B,(IY+29)
LD E,(IY+30)
LD D,(IY+31)
JR MOVE_F1
;from Current Position
.F_current:
LD C,(IY+32)
LD B,(IY+33)
LD E,(IY+34)
LD D,(IY+35)
MOVE_F1 ADD IX,BC
ADC HL,DE
LD D,XH
LD E,XL
LD (IY+32),E
LD (IY+33),D
LD (IY+34),L
LD (IY+35),H
XOR A
RET
;FP COMPARE
; CY - FILE POINTER > SIZE
; NC - FILE POINTER < SIZE
MOVE_CP LD L,(IY+28)
LD H,(IY+29)
LD E,(IY+32)
LD D,(IY+33)
AND A
SBC HL,DE
LD L,(IY+30)
LD H,(IY+31)
LD E,(IY+34)
LD D,(IY+35)
SBC HL,DE
RET
;--------------------
ECL2 POP BC
POP DE
AND A
RET
BLOKRD0 POP BC
POP DE
SCF
RET
;READ SECTORS OF FILE
;HL:DE - FP (in sectors)
; B - Amount sectors
BLOK_RD PUSH BC
LD (READMEM),IX
LD A,(BootSector.S_P_C) ;SECTORS PER CLUSTER
LD C,A
LD B,0
CALL DIV32
LD B,XH
LD C,XL
PUSH HL ;RESIDUE
LD L,(IY+26) ;START CLUSTER
LD H,(IY+27)
LD A,H
OR L
JR NZ,BLOKRD2
JR ECL2 ;R01 JR BLOKRD0
BLOKRD1 PUSH BC
CALL R_F_FAT
POP BC
JR C,ECL2 ;R01
EX DE,HL
DEC BC
BLOKRD2 LD A,B
OR C
JR NZ,BLOKRD1
POP DE
POP BC
LD A,(BootSector.S_P_C)
SUB E
LD C,A ;\
CP B ; \
JR C,BLOKRD3 ;SIZE > RESIDUE CLUSTER ; \
LD C,B ;SIZE < CLUSTER ;->-|--> ; !TODO à §®¡à âìáï
BLOKRD3 LD A,B ; /
SUB C ; /
LD B,A ;/
PUSH HL
PUSH BC
PUSH DE
CALL NSECTOR
POP DE
ADD IX,DE
JR NC,BLOKRD4
INC HL
BLOKRD4 LD DE,(READMEM)
LD A,(FatBuffer.DRIVE)
LD B,C
LD C,5
RST #18
JP C,BLOKRD0
POP BC
LD HL,(READMEM)
LD DE,(BootSector.B_P_S)
BLOKRD5 ADD HL,DE
DEC C
JR NZ,BLOKRD5
LD (READMEM),HL
POP DE
LD A,B
OR A
RET Z
BLOKRD6 LD HL,BootSector.S_P_C
LD A,B
SUB (HL)
LD B,A
LD C,(HL)
JR NC,BLOKRD7
LD B,0
ADD A,(HL) ;0 AND CF
LD C,A
OR A ;CLEAR CF
RET Z
BLOKRD7 EX DE,HL
PUSH BC
CALL R_F_FAT
POP BC
JP C,ECL1 ;R01?
EX DE,HL
PUSH HL
PUSH BC
CALL NSECTOR
LD DE,(READMEM)
LD A,(FatBuffer.DRIVE)
LD B,C
LD C,5
RST #18
JP C,BLOKRD0
POP BC
LD HL,(READMEM)
LD DE,(BootSector.B_P_S)
BLOKRD8 ADD HL,DE
DEC C
JR NZ,BLOKRD8
LD (READMEM),HL
POP DE
JR BLOKRD6
ECL1 AND A
RET
;--------------------
BLOKWRC POP BC
BLOKWR0 POP BC
POP DE
SCF
RET
;WRITE SECTORS OF FILE
;HL:DE - FP (in sectors)
; B - Amount sectors
BLOK_WR PUSH BC
LD (READMEM),IX
LD A,(BootSector.S_P_C) ;SECTORS PER CLUSTER
LD C,A
LD B,0
CALL DIV32
LD B,XH
LD C,XL
PUSH HL ;RESIDUE
LD L,(IY+26) ;START CLUSTER
LD H,(IY+27)
LD A,H
OR L
JR NZ,BLOKWR2
PUSH BC
CALL G_CLUST
JR C,BLOKWRC
LD (IY+26),L
LD (IY+27),H
LD DE,(FatBuffer.ENDCLUS)
CALL W_T_FAT
PUSH HL
CALL WR_FAT
POP HL
POP BC
JR BLOKWR2
BLOKWR1 PUSH BC
CALL R_F_FAT
JR NC,BLOKWRB
PUSH HL
CALL INC_FAT
POP HL
JR C,BLOKWRC
CALL R_F_FAT
BLOKWRB POP BC
EX DE,HL
DEC BC
BLOKWR2 LD A,B
OR C
JR NZ,BLOKWR1
POP DE
POP BC
LD A,(BootSector.S_P_C)
SUB E
LD C,A
CP B
JR C,BLOKWR3 ;SIZE > RESIDUE CLUSTER
LD C,B ;SIZE < CLUSTER
BLOKWR3 LD A,B
SUB C
LD B,A
PUSH HL
PUSH BC
PUSH DE
CALL NSECTOR
POP DE
ADD IX,DE
JR NC,BLOKWR4
INC HL
BLOKWR4 LD DE,(READMEM)
LD A,(FatBuffer.DRIVE)
LD B,C
LD C,6
RST #18
JP C,BLOKWR0
POP BC
LD HL,(READMEM)
LD DE,(BootSector.B_P_S)
BLOKWR5 ADD HL,DE
DEC C
JR NZ,BLOKWR5
LD (READMEM),HL
POP DE
LD A,B
OR A
RET Z
BLOKWR6 LD HL,BootSector.S_P_C
LD A,B
SUB (HL)
LD B,A
LD C,(HL)
JR NC,BLOKWR7
LD B,0
ADD A,(HL) ;0 AND CF
LD C,A
OR A ;CLEAR CF
RET Z
BLOKWR7 EX DE,HL
PUSH BC
CALL R_F_FAT
JR NC,BLOKWR9
PUSH HL
CALL INC_FAT
POP HL
JR C,BLOKWRA
CALL R_F_FAT
BLOKWR9 POP BC
EX DE,HL
PUSH HL
PUSH BC
CALL NSECTOR
LD DE,(READMEM)
LD A,(FatBuffer.DRIVE)
LD B,C
LD C,6
RST #18
JP C,BLOKWR0
POP BC
LD HL,(READMEM)
LD DE,(BootSector.B_P_S)
BLOKWR8 ADD HL,DE
DEC C
JR NZ,BLOKWR8
LD (READMEM),HL
POP DE
JR BLOKWR6
BLOKWRA POP BC
LD A,DSS_Error.sys.DISK_FULL
SCF
RET
TSTSIZE XOR A
LD (READCOD),A
LD L,(IY+32) ;FP LOW
LD H,(IY+33)
ADD HL,DE
EXX
LD DE,0
LD L,(IY+34) ;FP HIGH
LD H,(IY+35)
ADC HL,DE
EXX ;HL':HL - NEW FP
LD C,(IY+28)
LD B,(IY+29) ;SIZE LOW
AND A
SBC HL,BC
EXX
LD C,(IY+30) ;SIZE HIGH
LD B,(IY+31)
SBC HL,BC
EXX
RET C ;OK READ ALL
EX DE,HL
SBC HL,DE ;VERY BIG
EX DE,HL
LD A,#FF
LD (READCOD),A
RET
; HL - ADDRESS
; DE - SIZE
; A - FM
READ LD (R_POINT),HL
LD (S_POINT),HL
CALL SET_FM
RET C
CALL TSTSIZE
LD A,D
OR E
JP Z,NOREAD
PUSH DE
LD A,(IY+_sFM.DRIVE)
CALL OPENDSK
JP C,RPERR1
LD C,(IY+_sFM.F_POSITION)
LD E,(IY+_sFM.F_POSITION+1)
LD A,E
AND #01
LD B,A
LD D,(IY+_sFM.F_POSITION+2)
LD L,(IY+_sFM.F_POSITION+3)
LD H,0
OR A
RR L
RR D
RR E ;HL:DE FP (in sectors)
; BC FP residue (in bytes)
LD A,B
OR C
JP NZ,ROV1
ROV4 POP BC
PUSH BC
SRL B
JR Z,ROV2
LD (SECTORH),HL
LD (SECTORL),DE
LD IX,(R_POINT)
CALL BLOK_RD
JP C,RPERR1
LD DE,(R_POINT)
READMEM+1: LD HL,0 // LD HL,(READMEM)
AND A
SBC HL,DE
LD C,H
LD B,0
ADD HL,DE
LD (R_POINT),HL
SRL C
SECTORL+1: LD HL,0 // LD HL,(SECTORL)
ADD HL,BC
EX DE,HL
SECTORH+1: LD HL,0 // LD HL,(SECTORH)
LD C,B
ADC HL,BC
ROV2 POP BC
LD A,B
AND #01
LD B,A
OR C
JP Z,ROV6
PUSH BC
LD IX,BUFFER+#C000
LD B,1
IN A,(SLOT3)
PUSH AF
IN A,(SLOT0)
OUT (SLOT3),A
CALL BLOK_RD
POP BC
LD C,SLOT3
OUT (C),B
JP C,RPERR1
LD HL,BUFFER
LD DE,(R_POINT)
POP BC
LDIR
LD (R_POINT),DE
ROV6:
S_POINT+1: LD HL,0 // LD HL,(S_POINT)
LD DE,(R_POINT)
EX DE,HL
AND A
SBC HL,DE
PUSH HL
EX DE,HL
LD XH,D
LD XL,E
LD HL,0
CALL MOVE_FP.F_current
POP DE
NOREAD:
READCOD+1: LD A,0 // LD A,(READCOD)
OR A
RET
ROV1 PUSH BC
PUSH HL
PUSH DE
LD IX,BUFFER+#C000
LD B,1
IN A,(SLOT3)
PUSH AF
IN A,(SLOT0)
OUT (SLOT3),A
CALL BLOK_RD
POP BC
LD C,SLOT3
OUT (C),B
POP HL
JP C,RPERR3
LD BC,1
ADD HL,BC
EX DE,HL
POP HL
LD C,B
ADC HL,BC
EXX
POP DE
LD HL,512
AND A
SBC HL,DE
LD B,H
LD C,L
POP HL
AND A
SBC HL,BC
JR NC,ROV3
ADD HL,BC
LD B,H
LD C,L
LD HL,0
ROV3 PUSH HL
LD HL,BUFFER
ADD HL,DE
LD DE,(R_POINT)
LDIR
LD (R_POINT),DE
EXX
JP ROV4
RPERR3 POP HL
RPERR2 POP HL
RPERR1 POP BC
SCF
RET
PWERR3 POP HL
PWERR2 POP HL
PWERR1 POP BC
SCF
RET
RD_ONLY POP DE
LD A,DSS_Error.sys.READONLY
SCF
RET
; HL - ADDRESS
; DE - SIZE
; A - FM
WRITE LD (R_POINT),HL
LD (S_POINT),HL
PUSH DE
CALL SET_FM
JP C,PWERR1
LD A,(IY+_sFM.ACCESS_MODE)
AND #01
JR NZ,RD_ONLY
SET 7,(IY+_sFM.ACCESS_MODE)
SET 5,(IY+_sFM.ATTRIBUT)
LD A,(IY+_sFM.DRIVE)
CALL OPENDSK
JP C,PWERR1
LD C,(IY+32)
LD A,(IY+33)
LD E,A
AND #01
LD B,A
LD D,(IY+34)
LD L,(IY+35)
LD H,0
OR A
RR L
RR D
RR E ;HL:DE FP (in sectors)
; BC FP residue (in bytes)
LD A,B
OR C
JP NZ,WOV1
WOV4 POP BC
PUSH BC
SRL B
JR Z,WOV2
PUSH HL
PUSH DE
PUSH BC
R_POINT+2: LD IX,0 // LD IX,(R_POINT)
CALL BLOK_WR
POP BC
JP C,PWERR3
LD C,B
LD HL,(R_POINT)
LD DE,#0200
WOV5 ADD HL,DE
DJNZ WOV5
LD (R_POINT),HL
LD B,0
POP HL
ADD HL,BC
EX DE,HL
POP HL
LD C,B
ADC HL,BC
WOV2 POP BC
LD A,B
AND #01
LD B,A
OR C
JP Z,WOV6
PUSH HL
PUSH DE
PUSH BC
LD IX,BUFFER+#C000
LD B,1
IN A,(SLOT3)
PUSH AF
IN A,(SLOT0)
OUT (SLOT3),A
CALL BLOK_RD
POP BC
LD C,SLOT3
OUT (C),B
LD DE,BUFFER
LD HL,(R_POINT)
POP BC
JP C,PWERR2
LDIR
LD (R_POINT),HL
POP DE
POP HL
LD IX,BUFFER+#C000
LD B,1
IN A,(SLOT3)
PUSH AF
IN A,(SLOT0)
OUT (SLOT3),A
CALL BLOK_WR
POP BC
LD C,SLOT3
OUT (C),B
RET C
WOV6 LD DE,(S_POINT)
LD HL,(R_POINT)
AND A
SBC HL,DE
PUSH HL
EX DE,HL
LD XH,D
LD XL,E
LD HL,0
CALL MOVE_FP.F_current
CALL MOVE_CP
POP DE
RET NC
LD L,(IY+32)
LD H,(IY+33)
LD C,(IY+34)
LD B,(IY+35)
LD (IY+28),L
LD (IY+29),H
LD (IY+30),C
LD (IY+31),B
AND A
RET
WOV1 PUSH BC
PUSH HL
PUSH DE
LD IX,BUFFER+#C000
LD B,1
IN A,(SLOT3)
PUSH AF
IN A,(SLOT0)
OUT (SLOT3),A
CALL BLOK_RD
POP BC
LD C,SLOT3
OUT (C),B
POP DE
POP HL
EXX
POP DE
JP C,PWERR1
LD HL,512
AND A
SBC HL,DE
LD B,H
LD C,L
POP HL
AND A
SBC HL,BC
JR NC,WOV3
ADD HL,BC
LD B,H
LD C,L
LD HL,0
WOV3 PUSH HL
LD HL,BUFFER
ADD HL,DE
LD DE,(R_POINT)
EX DE,HL
LDIR
LD (R_POINT),HL
EXX
PUSH HL
PUSH DE
LD IX,BUFFER+#C000
LD B,1
IN A,(SLOT3)
PUSH AF
IN A,(SLOT0)
OUT (SLOT3),A
CALL BLOK_WR
POP BC
LD C,SLOT3
OUT (C),B
POP HL
JP C,PWERR2
LD BC,1
ADD HL,BC
EX DE,HL
POP HL
LD C,B
ADC HL,BC
JP WOV4
; HL - CLUSTER
; HL:IX - SECTOR
NSECTOR DEC HL
DEC HL
EX DE,HL
LD A,(BootSector.S_P_C)
LD B,A
LD HL,0
LD IX,0
ADD_DE1 ADD IX,DE
JR NC,ADD_DE2
INC HL
ADD_DE2 DJNZ ADD_DE1
LD DE,(FatBuffer.DAT_FRM)
ADD IX,DE
LD DE,#0000
ADC HL,DE
RET
; HL:DE / BC => DE:IX HL-OSTATOK
DIV32 LD XH,D
LD XL,E
EX DE,HL
LD HL,0
LD A,#20
DIV001 ADD IX,IX
EX DE,HL
ADC HL,HL
EX DE,HL
ADC HL,HL
SBC HL,BC
JR NC,DIV002
ADD HL,BC
DEC A
JR NZ,DIV001
RET
DIV002 INC IX
DEC A
JR NZ,DIV001
RET
//READCOD DB #00
//READMEM DW #0000
//SECTORH DW 0
//SECTORL DW 0
//R_POINT DW 0
//S_POINT DW 0
;//MODULE: DOS_FM
;[END]