Estex-DSS/DSS/DOS_FM.ASM
Anatoliy Belyanskiy b6c902f4f7 refactoring
2023-07-19 01:18:08 +10:00

1053 lines
16 KiB
NASM
Raw Blame History

This file contains invisible Unicode characters

This file contains invisible Unicode characters that are indistinguishable to humans but may be processed differently by a computer. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

;[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
*/
; ­  ¢ë室¥ ¡¥§ ®è¨¡®ª IY 㪠§ë¢ ¥â ­  ä ©«®¢ë© ¬ ­¨¯ã«ïâ®à
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 ;!HARDCODE ­®¬¥à ®è¨¡ª¨
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
JP .DO
;from End File
.B_end: LD C,(IY+_sFM.F_SIZE)
LD B,(IY+_sFM.F_SIZE+1)
LD E,(IY+_sFM.F_SIZE+2)
LD D,(IY+_sFM.F_SIZE+3)
JP .DO
;from Current Position
.F_current:
LD C,(IY+_sFM.F_POSITION)
LD B,(IY+_sFM.F_POSITION+1)
LD E,(IY+_sFM.F_POSITION+2)
LD D,(IY+_sFM.F_POSITION+3)
.DO: ADD IX,BC
ADC HL,DE
LD D,XH
LD E,XL
LD (IY+_sFM.F_POSITION),E
LD (IY+_sFM.F_POSITION+1),D
LD (IY+_sFM.F_POSITION+2),L
LD (IY+_sFM.F_POSITION+3),H
XOR A
RET
;FP COMPARE
; CY - FILE POINTER > SIZE
; NC - FILE POINTER < SIZE
MOVE_CP:
LD L,(IY+_sFM.F_SIZE)
LD H,(IY+_sFM.F_SIZE+1)
LD E,(IY+_sFM.F_POSITION)
LD D,(IY+_sFM.F_POSITION+1)
AND A
SBC HL,DE
LD L,(IY+_sFM.F_SIZE+2)
LD H,(IY+_sFM.F_SIZE+3)
LD E,(IY+_sFM.F_POSITION+2)
LD D,(IY+_sFM.F_POSITION+3)
SBC HL,DE
RET
;--------------------
ECL2:
;!TEST SAVE CLUSTER AFTER READ
POP BC
;
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
;HL:DE / BC => DE:IX HL-OSTATOK
CALL DIV32 ;!FIXIT § ¬¥­¨âì ¢ë§®¢ HLDE/BC ­  HLDE/C
;!FIXIT ¤ «¥¥ § â®çª  ­  â®, çâ® ¢ DE ¢á¥£¤  0 - à §¤¥« ­¥ ¡®«ìè¥ 2Gb
LD B,XH
LD C,XL
PUSH HL ;RESIDUE
LD L,(IY+_sFM.ST_CLUSTER) ;START CLUSTER
LD H,(IY+_sFM.ST_CLUSTER+1)
LD A,H
OR L
;!TEST SAVE CLUSTER AFTER READ
;JR NZ,BLOKRD2
PUSH BC
JR NZ,.testFunc
;
JP ECL2 ;R01 JR BLOKRD0
.testFunc:
;!TEST SAVE CLUSTER AFTER READ
LD E,(IY+_sFM.KnownCluster_L)
LD D,(IY+_sFM.KnownCluster_H)
LD A,D
OR E
JR Z,BLOKRD2
PUSH DE
PUSH HL
PUSH BC
LD E,(IY+_sFM.KnownOffset_L)
LD D,(IY+_sFM.KnownOffset_H)
LD A,D
OR E
JR Z,.noOptimization_1
POP HL
AND A
SBC HL,DE
JR C,.noOptimization_2
LD C,L
LD B,H
POP HL
POP DE
EX DE,HL
JP BLOKRD2
;
.noOptimization_1:
POP BC
.noOptimization_2:
POP HL
POP DE
JP BLOKRD2
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
;!TEST SAVE CLUSTER AFTER READ
LD (IY+_sFM.KnownCluster_L),L
LD (IY+_sFM.KnownCluster_H),H
POP BC
LD (IY+_sFM.KnownOffset_L),C
LD (IY+_sFM.KnownOffset_H),B
;
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,Dss.DRV.Read
RST ToDSS.DRV
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,Dss.DRV.Read
RST ToDSS.DRV
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
;!TEST SAVE CLUSTER AFTER WRITE
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
;HL:DE / BC => DE:IX HL-OSTATOK
CALL DIV32
LD B,XH
LD C,XL
PUSH HL ;RESIDUE
LD L,(IY+_sFM.ST_CLUSTER) ;START CLUSTER
LD H,(IY+_sFM.ST_CLUSTER+1)
LD A,H
OR L
;!TEST SAVE CLUSTER AFTER WRITE
;JR NZ,BLOKWR2
PUSH BC
JR NZ,.testFunc
;
PUSH BC
CALL G_CLUST
JR C,BLOKWRC
LD (IY+_sFM.ST_CLUSTER),L
LD (IY+_sFM.ST_CLUSTER+1),H
LD DE,(FatBuffer.ENDCLUS)
CALL W_T_FAT
PUSH HL
CALL WR_FAT
POP HL
POP BC
JP BLOKWR2
.testFunc:
;!TEST SAVE CLUSTER AFTER WRITE
LD E,(IY+_sFM.KnownCluster_L)
LD D,(IY+_sFM.KnownCluster_H)
LD A,D
OR E
JR Z,BLOKWR2
PUSH DE
PUSH HL
PUSH BC
LD E,(IY+_sFM.KnownOffset_L)
LD D,(IY+_sFM.KnownOffset_H)
LD A,D
OR E
JR Z,.noOptimization_1
POP HL
AND A
SBC HL,DE
JR C,.noOptimization_2
LD C,L
LD B,H
POP HL
POP DE
EX DE,HL
JP BLOKWR2
;
.noOptimization_1:
POP BC
.noOptimization_2:
POP HL
POP DE
JP 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
;!TEST SAVE CLUSTER AFTER WRITE
LD (IY+_sFM.KnownCluster_L),L
LD (IY+_sFM.KnownCluster_H),H
POP BC
LD (IY+_sFM.KnownOffset_L),C
LD (IY+_sFM.KnownOffset_H),B
;
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,Dss.DRV.Write
RST ToDSS.DRV
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,Dss.DRV.Write
RST ToDSS.DRV
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 _sFM.F_POSITION
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) ; _sFM.F_SIZE
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 ;!FIXIT ¬®¦­® ¯¥à¥­¥á⨠¢ ­ ç «® ¯à®æ¥¤ãàë
PUSH DE
LD A,(IY+_sFM.DRIVE)
CALL OPENDSK
;
JP C,RPERR1
;<3B> áçñâ ᬥ饭¨ï ¢ ᥪâ®à å
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 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
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+_sFM.F_POSITION)
LD A,(IY+_sFM.F_POSITION+1)
LD E,A
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,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 / C => DE:IX HL-OSTATOK (DE:BC.HL). ‹¥£ª® ¯¥à¥¤¥« âì ¯®¤ HL:DE / A => HL:DE.A
DIV32: LD A,C
DEC A
JR Z,.exit
;
AND E
LD B,A ; ®áâ â®ª
LD A,C
RRCA
;
.loop: SRL H : RR L
RR D : RR E
RRCA
JR NC,.loop
LD A,B
;
.exit: LD XH,D
LD XL,E
EX DE,HL
LD H,0
LD L,A
RET
; DIV32: LD A,#FF
; LD B,E
; .loop: SRL C
; JR C,.exitLoop
; SRL H : RR L : RR D : RR E : SLA A
; JP .loop
; .exitLoop:
; CPL
; AND B
; LD XH,D
; LD XL,E
; EX DE,HL
; LD H,0
; LD L,A
; RET
/*
DEFINE NEW_DIV 1
DIV32: LD XH,D
LD XL,E
IFN NEW_DIV
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
ELSE
div32_16:
;HLIX/BC -> HLIX remainder DE
;174+4*div32_16_sub8
;min: 2186cc
;max: 2794cc
;avg: 2466cc
;61 bytes
ex de,hl ; 4
; Negate BC to allow add instead of sbc
xor a ; 4
; Need to set HL to 0 anyways, so save 2cc and a byte
ld h,a ; 4
ld l,a ; 4
sub c ; 4
ld c,a ; 4
sbc a,a ; 4
sub b ; 4
ld b,a ; 4
ld a,d ; 4
call div32_16_sub8 ; 17
rla ; 4
ld d,a ; 4
ld a,e ; 4
call div32_16_sub8 ; 17
rla ; 4
ld e,a ; 4
ld a,ixh ; 8
call div32_16_sub8 ; 17
rla ; 4
ld ixh,a ; 8
ld a,ixl ; 8
call div32_16_sub8 ; 17
rla ; 4
ld ixl,a ; 8
;ex de,hl ; 4
ret ; 10
div32_16_sub8:
;119+8*div32_16_sub
;min: 503cc
;max: 655cc
;avg: 573cc
call 1F
1:
;17+2(17+2(div32_16_sub)))
call 1F
1:
;17+2(div32_16_sub)
call div32_16_sub
div32_16_sub:
;48+{8,0+{0,19}}
;min: 48cc
;max: 67cc
;avg: 56.75cc
rla ; 4
adc hl,hl ; 15
jr c,1F ;12/7
add hl,bc ; 11
ret c ;11/5
sbc hl,bc ; 15
ret ; 10
1:
add hl,bc ; 11
scf ; 4
ret ; 10
ENDIF
*/
;