Files
symphony_stdlib/src/hashset.asm
T

102 lines
2.5 KiB
NASM

;struct Allocator {
; alloc: (U32) -> ptr
; realloc: (ptr, U32) -> ptr
; free: (ptr) -> ()
;}
;struct HashSet {
; count: U32
; capacity: U32
; alloc_ptr: U32
; hash_ptr: U32
; hash_context: U32
; eq_ptr: U32
; eq_context: U32
; data_ptr: U32
;} - 28 bytes
;struct HashItem {
; hash: U32
; value: U32
;}
; Creates a hashset for the specified allocator, hash function and equality function
; Arguments:
; r1 - The pointer to the allocator
; r2 - The hash function
; r3 - The hash function context
; r4 - The equality function
; r5 - The equality function context
; Result:
; r1 - The pointer to the hashset structure
; Info:
; The hash function should follow the stdlib calling convention
; The hash function receives one argument (the value of the item) and should return an integer which remains the same for the lifetime of the value.
; The equality function should follow the stdlib calling convention
; The equality function receives two arguments (the value of the two items) and should return either a zero (when the items are not equal) or any other value (if they are equal).
pub new_hashset:
; First let's free up all the registers
push r8
push r9
push r10
push r11
push r12
push r13 ; We will be calling alloc
mov r8, r1
mov r9, r2
mov r10, r3
mov r11, r4
mov r12, r5
load_32 r5, [r8] ; Loading the alloc function address
mov r1, 28
counter r13
add r13, r13, 12
jmp r5 ; allocating the space for the hashset struct itself
; Now r1 has the pointer to memory, r2-r7 are clobbered
store_32 [r1], rz ; count is 0 at the start
add r1, r1, 4
mov r2, 8
store_32 [r1], r2 ; initial capacity at 8 item slots
add r1, r1, 4
store_32 [r1], r8 ; allocator pointer is in r8
add r1, r1, 4
store_32 [r1], r9 ; hash pointer is in r9
add r1, r1, 4
store_32 [r1], r10 ; hash context is in r10
add r1, r1, 4
store_32 [r1], r11 ; eq pointer is in r11
add r1, r1, 4
store_32 [r1], r12 ; eq context is in r12
push r1
load_32 r5, [r8] ; Loading the alloc function address
mov r1, 64
counter r13
add r13, r13, 12
jmp r5 ; allocating the space for the data
load r2, [sp] ; Now r1 is data pointer, r2 is hashset pointer at eq context
add r2, r2, 4
store_32 [r2], r1 ; data pointer saved
pop r1 ; Popping the pointer to start of the hashset
pop r13 ; Everything's set up, return
pop r12
pop r11
pop r10
pop r9
pop r8
jmp r13