Shared_Includes/printf.asm
2025-05-10 02:58:49 +10:00

436 lines
6.4 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.

;universal color print to console procedure like printf()
; in: IY
;
; <20>ਬ¥à ¤ ­­ëå:
; DskInfo_Msg: DB "Formatted disk parameters:",cr,lf
; DB "Total sectors: ",tab,col_cmd,col_magenta, "%lu", col_cmd,col_white,cr,lf
; DB "Total size: ",tab,col_cmd,col_magenta, "%uMb", col_cmd,col_white,cr,lf
; DB "Units: ",tab,tab,col_cmd,col_magenta, "%u", col_cmd,col_white,cr,lf
; DB "Unit size: ",tab,col_cmd,col_magenta, "%u%c", col_cmd,col_white,cr,lf
; .FS: DB "File system: ",tab,col_cmd,col_magenta,"FAT16",col_cmd,col_white,cr,lf
; DB "Serial: ",tab,col_cmd,col_magenta, "%02x-%02x", col_cmd,col_white,cr,lf
; DB "Label: ",tab,tab,col_cmd,col_magenta, "NO LABEL",col_cmd,col_white,cr,lf,cr,lf,0
; .ptr: DW DskInfo_Msg
; .sectors: DS 4
; .mb: DW 0
; .units: DW 0
; .u_size: DW 0
; .u_sym: DB "K",0
; .serial: DS 4
;
; ¢ IY ¯®¬¥é ¥âáï DskInfo_Msg.ptr
;
; x, X hexadecimal
; D signed decimal
; U unsigned decimal
; L long
; C single character
; O octal
; S string
IFUSED printf#.str
MODULE printf#
cmd EQU 16
str: PUSH IY
LD C,Dss.Cursor
RST ToDSS
LD (coords),DE
POP IY
;
LD L,(IY) ; at iy we have pointer to format string
LD H,(IY+1)
loop: LD A,(HL)
INC HL
OR A
RET Z
CP '%'
JR Z,loc3
loc4: CALL outch
JP loop
loc3: LD A,(HL)
INC HL
CP '%'
JR Z,loc4
DEC HL
CALL scan_length ; scan [-][0][0-9*][lL]
loop1: LD A,(HL)
INC HL
CP 'x'
JP Z,prt_x1
CP 'X'
JP Z,prt_x2 ; hexadecimal
;
AND %1101'1111
;
CP 'D'
JP Z,prt_d ; signed decimal
CP 'U'
JP Z,prt_u ; unsigned decimal
CP 'L'
JP Z,prt_l ; long
CP 'C'
JP Z,prt_c ; print single character
CP 'O'
JP Z,prt_o ; octal
CP 'S'
JP Z,prt_s ; string
JP loop
; %l - long
prt_l: LD (flong),A
INC HL
JP loop1
; %c symbol
prt_c: LD A,(iy+2)
CALL outch
; ld de,(nprtd+1)
; inc de
; ld (nprtd+1),de
prt_q: INC IY
INC IY
LD A,(flong)
OR A
JP Z,loop ; false
INC IY
INC IY
JP loop
; %s string
prt_s: LD A,' '
LD (padch),A
PUSH HL
PUSH IY
LD L,(iy+2)
LD H,(iy+3)
fmt0: PUSH HL
CALL _strlen
EX DE,HL
LD HL,(flen)
LD A,H
OR L
JR Z,fmt01
; call _pad
; or a
SBC HL,DE
LD (flen),HL
LD A,(fladj)
OR A
CALL Z,_pad
fmt01:
POP HL
fmt1: LD A,(HL)
INC HL
OR A
JR Z,fmt21
CALL outch
; ld de,(nprtd+1)
; inc de
; ld (nprtd+1),de
JP fmt1
fmt2:
LD HL,(flen)
LD A,(fladj)
OR A
CALL NZ,_pad
fmt21: POP IY
POP HL
JP prt_q
; %u unsigned decimal
prt_u: PUSH HL
PUSH IY
CALL getnum
JR fmt4
; %d signed decimal
prt_d: PUSH HL
PUSH IY
CALL getnum
LD A,(flong)
OR A
JR NZ,fmt3 ; true
BIT 7,H
JR Z,fmt3
LD DE,-1
fmt3: BIT 7,D
JR Z,fmt4
LD A,'-'
LD (sign),A
XOR A
SUB L
LD L,A
LD A,0
SBC A,H
LD H,A
LD A,0
SBC A,E
LD E,A
LD A,0
SBC A,D
LD D,A
fmt4: LD A,10 ; base
LD BC,char1
CALL mk_num
JP fmt0
; %o octal
prt_o: PUSH HL
PUSH IY
CALL getnum
LD A,8 ; base
LD BC,char1
CALL mk_num
JP fmt0
; %X hex
prt_x2: LD BC,char1
prt_x: PUSH HL
PUSH IY
CALL getnum
LD A,16 ; base
CALL mk_num
JP fmt0
; %x hex
prt_x1: LD BC,char2
JR prt_x
;---------------------------------------
getnum: XOR A
LD (sign),A
LD L,(iy+2)
LD H,(iy+3)
LD A,(flong)
OR A
JR Z,gnu1 ; false
LD E,(iy+4)
LD D,(iy+5)
RET
gnu1: LD DE,0
RET
mk_num: LD (mn0+1),A ; base
LD (chars),BC
EXX
LD HL,number
EXX
CALL mn0
EXX
LD (HL),0
EXX
LD HL,number
LD A,(sign)
OR A
RET Z
DEC HL
RET
mn0: LD BC,0x200a
XOR A
mn1: ADD HL,HL
RL E
RL D
RLA
CP C
JR C,mn2
SUB C
INC L
mn2: DJNZ mn1
; DEHL-quot; A-rem
PUSH AF
LD A,D
OR E
OR H
OR L
CALL NZ,mn0
POP AF
PUSH HL
chars+1: LD HL,char1 ; save char1 or char2
LD C,A
LD B,0
ADD HL,BC
LD A,(HL)
POP HL
EXX
LD (HL),A
INC HL
EXX
RET
scan_length:
XOR A
LD (flong),A ; false
LD (fladj),A
LD (flen+0),A ; make length = 0
LD (flen+1),A
LD A,' '
LD (padch),A ; space padding by default
LD A,(HL)
CP '-'
JR NZ,.sl1
LD (fladj),A ; all will be LEFT adjusted, not right
INC HL
.sl1: LD A,(HL)
CP '0'
JR NZ,sl2
LD A,(fladj)
OR A
JR NZ,sl1a
LD A,'0'
LD (padch),A ; pad numbers with '0's, not spaces
sl1a: INC HL
sl2: LD DE,0
sl2a: LD A,(HL)
SUB '0'
JR C,sl3
CP 9+1
JR NC,sl3
EX DE,HL
LD C,L
LD B,H
ADD HL,HL
ADD HL,HL
ADD HL,BC
ADD HL,HL
LD B,0
LD C,A
ADD HL,BC
EX DE,HL
INC HL
JR sl2a
sl3: LD (flen),DE ; set explicit length
LD A,(HL)
CP 'l'
JR Z,sl4
CP 'L'
RET NZ
sl4: LD (flong),A ; true
INC HL
RET
_pad: DEC HL
BIT 7,H
RET NZ
PUSH HL
LD A,(padch)
CALL outch
POP HL
; ld de,(nprtd+1)
; inc de
; ld (nprtd+1),de
JP _pad
_strlen: EX DE,HL
LD HL,0
.loop0: LD A,(DE)
OR A
RET Z
INC HL
INC DE
JR .loop0
;---------------------------------------
outch: PUSH IY
PUSH HL
CP "\r"
JP Z,.new_line
CP "\n"
JP Z,.prtNullX
CP "\t"
JP Z,.tabpr
CP cmd
JP Z,.set_attr
.next0: EX AF,AF
LD DE,(coords)
LD A,(print_attr)
LD B,A
EX AF,AF'
LD C,Dss.WrChar
RST ToDSS
LD A,(coords)
INC A
CP 80 ;ª®®à¤¨­ â  ¯® X 0..79 (¨â®£® 80)
JR NC,.new_line ;­  ­®¢ãî áâபã.
LD (coords),A
.end_pr: POP HL
POP IY
RET
.new_line: LD A,(coords+1) ;Y
CP 31
JR C,.noscroll
CALL .ScrollUP
JR .prtNullX
.noscroll: INC A
LD (coords+1),A ;y
.prtNullX: XOR A
LD (coords),A ;x
JR .end_pr
.ScrollUP: XOR A
LD D,A
LD E,A
LD HL,0x2050
LD BC,Dss.Scroll.Up
XOR A
RST ToDSS
RET
.tabpr: LD C,Dss.Cursor
RST ToDSS
INC E ;x++
LD A,E
ADD A,8
AND 0x78
LD E,A
LD (coords),DE
LD C,Dss.Locate
RST ToDSS
JP .end_pr
;Set attribute
.set_attr: LD A,(HL)
LD (print_attr),A
POP HL
POP IY
INC HL
RET
; jp .end_pr
char1: DB '0123456789ABCDEF'
char2: DB '0123456789abcdef'
flen: DW 0
fladj: DB 0
flong: DB 0 ; false/true
padch: DB ' '
sign: DB 0 ; §­ ª ç¨á« 
number: DS 16 ; ¡ãä¥à ç¨á« 
coords: DW 0000
print_attr: DB 7
ENDMODULE
ENDIF