summaryrefslogtreecommitdiff
path: root/twasm/asm/main.asm
diff options
context:
space:
mode:
Diffstat (limited to 'twasm/asm/main.asm')
-rw-r--r--twasm/asm/main.asm76
1 files changed, 76 insertions, 0 deletions
diff --git a/twasm/asm/main.asm b/twasm/asm/main.asm
index 8fc7b5b..5c41239 100644
--- a/twasm/asm/main.asm
+++ b/twasm/asm/main.asm
@@ -721,6 +721,82 @@ tokenise:
.pending_operator dd 0 ; the operator token that is pending processing
; ------------------------------------------------------------------------------
+; evaluate_constant
+;
+; description:
+; takes a constant and returns its hexidecimal representation. Currently the
+; following constants are supported:
+;
+; | type | p. | description |
+; |------|----|--------------|
+; | 0x00 | 0x | hexidecimal |
+; | 0xFF | | unrecognised |
+;
+; where `p.` is the prefix
+;
+; parameters:
+; rdi -> first byte of constant
+; rsi = size of constant in bytes
+;
+; returned:
+; rax = value of the constant in hexidecimal
+; dl = type of constant; the rest of rdx is zeroed
+; ------------------------------------------------------------------------------
+
+evaluate_constant:
+ ; TODO fix this cheap trick xD
+ mov dl, [rdi]
+ cmp dl, '0'
+ jne .unrecognised
+ dec rsi ; one fewer byte left
+ inc rdi ; point to next byte
+
+ mov dl, [rdi]
+ cmp dl, 'x'
+ jne .unrecognised
+ dec rsi ; one fewer byte left
+ inc rdi ; point to next byte
+
+ ; rsi = number of bytes left
+ ; rdi -> current byte of constant
+ xor eax, eax ; rax = value in hex of constant
+
+ .loop:
+ cmp rsi, 0 ; make sure we're in range
+ je .break ; if not, break
+
+ shl rax, 4 ; make room for next hex digit
+
+ mov dl, [rdi] ; dl = next byte of constant
+
+ sub dl, '0' ; dl = if digit: digit; else :shrug:
+
+ cmp dl, 9 ; if !digit:
+ jg .alpha ; letter
+ jmp .continue ; else loop
+
+ .alpha
+ sub dl, 7 ; map [('A'-'0')..('F'-'0')] to [0xA..0xF]
+ cmp dl, 0xF ; if not in the range [0xA..0xF]
+ jg .unrecognised ; then unrecognised
+
+ .continue
+ and dl, 0x0F ; mask
+ or al, dl ; and add newest nibble
+
+ dec rsi ; one fewer byte left
+ inc rdi ; point to next byte
+ jmp .loop ; and loop
+
+ .break:
+ mov rdx, 0x00 ; hex type
+ ret
+
+ .unrecognised:
+ mov rdx, 0xFF ; unrecognised type
+ ret
+
+; ------------------------------------------------------------------------------
; utilities
; ------------------------------------------------------------------------------