view src/print.s @ 80:bb50ac9fdf37

Checkpoint with very basic integer and floating point arithmetic, untested This commit has implementations for floating point add, subtract, multiply, and divide, along with 32 bit signed integer equivalents. These can probably be optimized and they are untested.
author William Astle <lost@l-w.ca>
date Sat, 07 Oct 2023 02:56:59 -0600
parents 5f8f0b0781e8
children 663d8e77b579
line wrap: on
line source

                *pragmapush list
                *pragma list
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
; Print out an unsigned 16 bit value in D to the selected output stream
print_uint16d   pshs d,x,y,u                    ; save number and make some temporaries on the stack
                leay 2,s                        ; point to start of buffer
                ldu #10000                      ; do the 10000s digit
                bsr print_uint16d4
                ldu #1000                       ; do the 1000s digit
                bsr print_uint16d4
                ldu #100                        ; do the 100s digit
                bsr print_uint16d4
                ldu #10                         ; do the 10s digit
                bsr print_uint16d4
                puls d                          ; get back number residue and clean up stack
                addb #0x30                      ; convert 1s digit to number
                stb ,y                          ; stash it
                clr 1,y                         ; NUL terminate it
                leay ,s                         ; point to start of converted number
print_uint16d0  lda ,y                          ; get digit at start
                cmpa #0x30                      ; zero digit?
                bne print_uint16d1              ; brif not - we can just show the number from here
                ldb 1,y                         ; end of number?
                beq print_uint16d1              ; brif so - show the zero anyway
                leay 1,y                        ; move past the zero
                bra print_uint16d0              ; see if we have more zeroes to skip
print_uint16d1  lda ,y+                         ; get number digit
                beq print_uint16d2              ; brif end of number
                jsr writechr                    ; output the digit
                bra print_uint16d1              ; handle next digit
print_uint16d2  leas 6,s                        ; clean up the stack
                rts
print_uint16d4  lda #0x30-1                     ; init digit value
                pshs a,u                        ; save the digit position and digit value
                ldd 5,s                         ; get back residue
print_uint16d5  inc ,s                          ; bump digit
                subd 1,s                        ; subtract out place value
                bcc print_uint16d5              ; brif we haven't got the right digit yet
                addd 1,s                        ; restore residue
                std 5,s                         ; save new residue
                puls a,u                        ; get back digit and place value off stack
                sta ,y+                         ; save digit in buffer
                rts

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
; PRINT command
cmd_print       beq cmd_printeol                ; brif no argument - do a newline
cmd_print0      cmpa #';                        ; semicolon?
                bne cmd_print1                  ; brif not
                jsr nextchar                    ; skip the semicolon
                bne cmd_print0                  ; brif not end of the statement
                rts
cmd_print1      jsr eval_expr                   ; evaluate the expression
                ldb val0+val.type               ; get value type
                cmpb #valtype_int               ; integer?
                beq cmd_printint                ; brif so - print integer
                lda #'!                         ; flag unknown expression type
                jsr console_outchr
                jsr console_outchr
                jsr console_outchr
cmd_printnext   jsr curchar                     ; see what we have here
                bra cmd_print                   ; and go process
cmd_printeol    jmp console_outnl               ; do a newline and return
cmd_printint    leas -12,s                      ; make a buffer
                leay ,s                         ; point to buffer
                lda #0x20                       ; default sign (positive)
                ldb val0+val.int                ; is it negative?
                bpl cmd_printint0               ; brif not
                jsr int32_neg                   ; negate the integer
                lda #'-                         ; negative sign
cmd_printint0   sta ,y+                         ; save sign
                ldu #cmd_printintpc             ; point to positive constant table
                ldx #10                         ; there are 10 constants to process
; subtraction loop - positive residue
cmd_printint1   lda #'0-1                       ; initialize digit
                sta ,y
cmd_printint2   inc ,y                          ; bump digit
                ldd val0+val.int+2              ; subtract constant
                subd 2,u
                std val0+val.int+2
                ldd val0+val.int
                sbcb 1,u
                sbca ,u
                std val0+val.int
                bcc cmd_printint2               ; brif we didn't go negative
                ldd val0+val.int+2              ; undo last subtract
                addd 2,u
                std val0+val.int+2
                ldd val0+val.int
                adcb 1,u
                adca ,u
                std val0+val.int
                leay 1,y                        ; move to next digit in buffer
                leau 4,u                        ; move to next constant
                leax -1,x                       ; done all constants?
                bne cmd_printint1               ; brif not - done all
cmd_printint5   clr ,y                          ; NUL terminate the string
                leax 1,s                        ; point past the sign
cmd_printint6   lda ,x+                         ; get digit
                beq cmd_printint8               ; brif end of number
                cmpa #'0                        ; is it a zero?
                beq cmd_printint6               ; brif so - skip it
cmd_printint7   lda ,s                          ; get the sign
                sta ,--x                        ; put it at the start of the number
                jsr console_outstr              ; display the number
                leas 12,s                       ; clean up stack
                bra cmd_printnext               ; go print the next thing
cmd_printint8   leax -1,x                       ; restore one of the zeros
                bra cmd_printint7               ; go finish up
cmd_printintpc  fqb 1000000000                  ; 10^9
                fqb 100000000                   ; 10^8
                fqb 10000000                    ; 10^7
                fqb 1000000                     ; 10^6
                fqb 100000                      ; 10^5
                fqb 10000                       ; 10^4
                fqb 1000                        ; 10^3
                fqb 100                         ; 10^2
                fqb 10                          ; 10^1
                fqb 1                           ; 10^0
                *pragmapop list