.define printf .sect .text .sect .rom .sect .data .sect .bss .sect .text printf: popl saveret, *RR14 ldm savereg, R4, $10 ld R3, $buff !R3 is pointer to a buffer, in which !we built the string to be printed. pop R2, *RR14 !R2 is pointer to format-string prloop: ldb RL0, 0(R2) testb RL0 jr EQ, ready inc R2 cpb RL0, $045 ! '%'? jr NE, 1f ldb RL0, 0(R2) inc R2 cpb RL0, $0163 ! 's'? jr EQ, 3f cpb RL0, $0170 ! 'x'? ld R4, $16 ! print number hexadecimal jr EQ, 2f cpb RL0, $0144 ! 'd'? ld R4, $10 ! print number decimal jr EQ, 2f cpb RL0, $0157 ! 'o'? ld R4, $8 ! print number octal jr EQ, 2f 1: ldb 0(R3), RL0 inc R3 jr prloop 2: !in case of %x, %d or %o pop R1, *RR14 test R1 jr PL, 4f cp R4, $10 jr NE, 4f ! print only '-' in case of %d ldb 0(R3), $055 ! '-' inc R3 neg R1 4: calr printn jr prloop 3: !in case of %s pop R1, *RR14 6: ldb RL0, 0(R1) testb RL0 jr EQ, prloop inc R1 ldb 0(R3), RL0 inc R3 jr 6b ready: !now really print the string we built in the buffer ldb 0(R3), RL0 !end string with '\0' sub R3, $buff-1 !R3 contains the number of characters ld R1, $buff push *RR14, R3 !count push *RR14, R1 !buffer push *RR14, $2 !file descriptor calr WRITE inc R15, $6 ldm R4, savereg, $10 pushl *RR14, saveret ret printn: ldk R0, $0 div RR0, R4 !%x, %d or %o determined by R4 test R1 jr EQ, 5f !if quotient is '0' printn is ready push *RR14, R0 !push remainder onto the stack calr printn pop R0, *RR14 5: add R0, $060 cp R0, $071 !'9' jr LE, 8f add R0, $7 8: ldb 0(R3), RL0 inc R3 ret .sect .data buff: .space 256