;Hexadecimal adder and subtractor for two-digit unsigned values ;Print a prompt start: load r0, prompt store ffff, r0 load r0, space store ffff, r0 ;Read and convert the first argument and store it to arg1 cleq r0, r0, rarg store arg1, r0 ;Print a newline cleq r0, r0, newln ;Read the operation sign load r0, ffff load r1, plus breq r0, r1, storsg load r1, minus breq r0, r1, storsg ;Error and halt if the character is not a sign breq r0, r0, error storsg: store sign, r0 ;Print a space load r0, space store ffff, r0 ;Read and convert the second argument and load it to r2 cleq r0, r0, rarg xor r2, r2 xor r2, r0 ;Reload the first argument to r0 load r0, arg1 ;Print a newline cleq r0, r0, newln ;Print an equals sign load r3, equals store ffff, r3 ;Check the operation load r3, sign load r1, minus breq r1, r3, brsub ;Add and load the result to r3 ;Addition cleq r0, r0, adder ;Load the result to r3 xor r3, r3 xor r3, r0 ;Skip the subtraction code breq r0, r0, nosign ;Subtract and load the result to r3 ;Subtraction brsub: cleq r0, r0, sub ;Load the result to r3 xor r3, r3 xor r3, r0 ;Print a minus sign and unnegate the result if negative ;Check the sign xor r0, r0 breq r0, r1, nosign ;Print a minus sign load r0, minus store ffff, r0 ;Un-negate the result store arg1, r3 load r2, one cleq r0, r0, sub nand r0, r0 ;Reload the result to r3 xor r3, r3 xor r3, r0 ;Skip printing the first digit breq r0, r0, skip ;Print the overflow for addition or zero for positive results of ;subtraction nosign: xor r0, r0 xor r0, r1 cleq r0, r0, n2hex store ffff, r0 ;Convert and print the result ;Restore the result back to r0 skip: xor r0, r0 xor r0, r3 ;High nibble shr r0 shr r0 shr r0 shr r0 cleq r0, r0, n2hex store ffff, r0 ;Restore the result to r0 xor r0, r0 xor r0, r3 ;Low nibble cleq r0, r0, n2hex store ffff, r0 ;Print a newline cleq r0, r0, newln ;Loop breq r0, r0, start ;Error error: cleq r0, r0, newln load r0, qmark store ffff, r0 cleq r0, r0, newln halt ;Read and convert an argument and load it to r0 ;First digit rarg: load r0, ffff cleq r0, r0, hex2n xor r2, r2 xor r2, r0 shl r2 shl r2 shl r2 shl r2 ;Second digit rarg2: load r0, ffff load r1, backsp breq r0, r1, rarg cleq r0, r0, hex2n ;Confirm load r3, ffff load r1, backsp breq r3, r1, rarg2 load r1, cr breq r3, r1, rarg3 breq r0, r0, error ;Combine the digits rarg3: or r0, r2 ;Return ret ;Print a newline newln: load r3, cr store ffff, r3 load r3, lf store ffff, r3 ret ;Get the value of a hexadecimal digit ;Locate the hexadecimal digit in the table hex2n: load r1, tbl01 breq r0, r1, val0 load r1, tbl03 breq r0, r1, val1 load r1, tbl05 breq r0, r1, val2 load r1, tbl07 breq r0, r1, val3 load r1, tbl09 breq r0, r1, val4 load r1, tbl0b breq r0, r1, val5 load r1, tbl0d breq r0, r1, val6 load r1, tbl0f breq r0, r1, val7 load r1, tbl11 breq r0, r1, val8 load r1, tbl13 breq r0, r1, val9 load r1, tbl15 breq r0, r1, vala load r1, tbl17 breq r0, r1, valb load r1, tbl19 breq r0, r1, valc load r1, tbl1b breq r0, r1, vald load r1, tbl1d breq r0, r1, vale load r1, tbl1f breq r0, r1, valf load r1, tbl21 breq r0, r1, vala load r1, tbl23 breq r0, r1, valb load r1, tbl25 breq r0, r1, valc load r1, tbl27 breq r0, r1, vald load r1, tbl29 breq r0, r1, vale load r1, tbl2b breq r0, r1, valf ;Error and halt if the character is not a digit breq r0, r0, error ;Load the value of the hexadecimal digit val0: load r0, tbl00 breq r0, r0, h2nend val1: load r0, tbl02 breq r0, r0, h2nend val2: load r0, tbl04 breq r0, r0, h2nend val3: load r0, tbl06 breq r0, r0, h2nend val4: load r0, tbl08 breq r0, r0, h2nend val5: load r0, tbl0a breq r0, r0, h2nend val6: load r0, tbl0c breq r0, r0, h2nend val7: load r0, tbl0e breq r0, r0, h2nend val8: load r0, tbl10 breq r0, r0, h2nend val9: load r0, tbl12 breq r0, r0, h2nend vala: load r0, tbl14 breq r0, r0, h2nend valb: load r0, tbl16 breq r0, r0, h2nend valc: load r0, tbl18 breq r0, r0, h2nend vald: load r0, tbl1a breq r0, r0, h2nend vale: load r0, tbl1c breq r0, r0, h2nend valf: load r0, tbl1e breq r0, r0, h2nend ;Return h2nend: ret ;Add r2 to r0 with the overflow stored in r1 ;Reset overflow adder: xor r3, r3 store ovrflw, r3 ;Copy the first argument to r1 addlop: xor r1, r1 xor r1, r0 ;Calculate the sum and carry and copy the pre-shift carry to r1 xor r0, r2 and r2, r1 xor r1, r1 xor r1, r2 shl r2 ;Check for overflow rol r1 breq r1, r2, nvrflw ;Store overflow load r1, one store ovrflw, r1 ;Check for no carry nvrflw: breq r2, r3, addend ;Loop breq r0, r0, addlop ;Load overflow and return addend: load r1, ovrflw ret ;Subtract r2 from arg1 and store the result in r0 with the sign ;bit stored in r1 ;Negate the second argument sub: load r0, one nand r2, r2 cleq r0, r0, adder ;Load the first argument to r2 load r2, arg1 ;Subtract cleq r0, r0, adder ;Invert the sign bit xor r3, r3 breq r3, r1, submin xor r1, r1 breq r0, r0, subend submin: load r1, one ;Return subend: ret ;Get the hexadecimal digit of a nibble ;Extract the low nibble n2hex: load r1, mask and r0, r1 ;Locate the nibble in the table load r1, tbl00 breq r0, r1, dgt0 load r1, tbl02 breq r0, r1, dgt1 load r1, tbl04 breq r0, r1, dgt2 load r1, tbl06 breq r0, r1, dgt3 load r1, tbl08 breq r0, r1, dgt4 load r1, tbl0a breq r0, r1, dgt5 load r1, tbl0c breq r0, r1, dgt6 load r1, tbl0e breq r0, r1, dgt7 load r1, tbl10 breq r0, r1, dgt8 load r1, tbl12 breq r0, r1, dgt9 load r1, tbl14 breq r0, r1, dgta load r1, tbl16 breq r0, r1, dgtb load r1, tbl18 breq r0, r1, dgtc load r1, tbl1a breq r0, r1, dgtd load r1, tbl1c breq r0, r1, dgte load r1, tbl1e breq r0, r1, dgtf ;Load the hexadecimal digit of the nibble dgt0: load r0, tbl01 breq r0, r0, n2hend dgt1: load r0, tbl03 breq r0, r0, n2hend dgt2: load r0, tbl05 breq r0, r0, n2hend dgt3: load r0, tbl07 breq r0, r0, n2hend dgt4: load r0, tbl09 breq r0, r0, n2hend dgt5: load r0, tbl0b breq r0, r0, n2hend dgt6: load r0, tbl0d breq r0, r0, n2hend dgt7: load r0, tbl0f breq r0, r0, n2hend dgt8: load r0, tbl11 breq r0, r0, n2hend dgt9: load r0, tbl13 breq r0, r0, n2hend dgta: load r0, tbl15 breq r0, r0, n2hend dgtb: load r0, tbl17 breq r0, r0, n2hend dgtc: load r0, tbl19 breq r0, r0, n2hend dgtd: load r0, tbl1b breq r0, r0, n2hend dgte: load r0, tbl1d breq r0, r0, n2hend dgtf: load r0, tbl1f breq r0, r0, n2hend ;Return n2hend: ret ;Characters space: data 20 prompt: data 3e plus: data 2b minus: data 2d equals: data 3d qmark: data 3f backsp: data 8 cr: data d lf: data a ;Mask mask: data f ;One one: data 1 ;Hexadecimal table ;Numeric digits tbl00: data 0 tbl01: data 30 tbl02: data 1 tbl03: data 31 tbl04: data 2 tbl05: data 32 tbl06: data 3 tbl07: data 33 tbl08: data 4 tbl09: data 34 tbl0a: data 5 tbl0b: data 35 tbl0c: data 6 tbl0d: data 36 tbl0e: data 7 tbl0f: data 37 tbl10: data 8 tbl11: data 38 tbl12: data 9 tbl13: data 39 ;Upper case letter digits tbl14: data a tbl15: data 41 tbl16: data b tbl17: data 42 tbl18: data c tbl19: data 43 tbl1a: data d tbl1b: data 44 tbl1c: data e tbl1d: data 45 tbl1e: data f tbl1f: data 46 ;Lower case letter digits tbl20: data a tbl21: data 61 tbl22: data b tbl23: data 62 tbl24: data c tbl25: data 63 tbl26: data d tbl27: data 64 tbl28: data e tbl29: data 65 tbl2a: data f tbl2b: data 66 ;Variables ovrflw: data 0 arg1: data 0 sign: data 0