diff options
Diffstat (limited to 'include/data.s')
| -rw-r--r-- | include/data.s | 272 |
1 files changed, 217 insertions, 55 deletions
diff --git a/include/data.s b/include/data.s index 2c512d4..35c4c8d 100644 --- a/include/data.s +++ b/include/data.s @@ -1,14 +1,7 @@ .ifndef _data_s_file _data_s_file: - -# Simple values and boxed machine integers -# | ptr | value | -CON_evacuate1: - retq # TODO -CON_scavenge1: - add $020, %rsi - retq + nop # avoid confusing gdb # Format of the info tables: # - code @@ -16,27 +9,160 @@ CON_scavenge1: # - 8B helper information for eval/apply (generally this is 0, and only gets used for FUN/PAP) # - 8B pointer to scavenge # - 8B pointer to evacuate +# +# Evacuate interface: +# in: %rbp what to evacuate +# out: %rbp where the thing is now +# ret: jump to _gc_evacuate_ret +# Notes: +# - IND thunks skip themselves on evacuate +# - checking if whether stuff is already in write region are managed by +# _gc_evacuate prelude +# +# Scavenge interface: +# in: %rbp what to scavenge +# out: %rbp next thing to scavenge in memory +# ret: jump to _gc_scavenge_ret +# +# Saved registers during the GC process: +# - _uskel_gc uses %r8-%r11 +# - scavenges use %r12-%r15 +# - %rax-%rdx is scratch and evacuate use + +# Simple values and boxed machine integers +# | ptr | value | +INT_evacuate: + pushq 010(%rbp) + pushq $INT_code + mov %rsp,%rbp + jmp _gc_evacuate_ret +INT_scavenge: + add $020, %rbp + jmp _gc_scavenge_ret INT_info_table: - cell CON_evacuate1 - cell CON_scavenge1 + cell INT_evacuate + cell INT_scavenge cell 0 INT_code: continue +# Indirection +# | ptr | indptr | +IND_evacuate: + mov 010(%rbp), %rbp + jmp _gc_evacuate +IND_scavenge: + # this should never be triggered but let's play it safe + add $020, %rbp + jmp _gc_scavenge_ret + +IND_info: + cell IND_evacuate + cell IND_scavenge + cell 0 +IND_code: + enter 010(%rbp) + +# Blackhole (contains the original thunkptr for debugging purposes) +# | ptr | orig_thunkptr | +BLE_evacuate: + jmp _gc_evacuate_ret +BLE_scavenge: + jmp _gc_scavenge_ret + +BLE_info_table: + cell BLE_evacuate + cell BLE_scavenge + cell 0 +BLE_code: + # if we hit this, we've got a pure loop in a program, and it is never + # going to actually progress. So let's just shoot it down with a + # helpful message or so. + mov 010(%rbp), %r15 + + mov $1, %rdi #stdout + + mov $14, %rdx + mov $BLE_msg, %rsi + mov $1, %rax #write + syscall + + mov $1, %rdx + BLE_loop: + mov %r15, %rcx + and $0xf, %rcx + mov $BLE_hex, %rsi + add %rcx, %rsi + mov $1, %rax + syscall + shr $4, %r15 + jnz BLE_loop + + mov $BLE_nl, %rsi + mov $1, %rax + syscall + + # shot self down (and retry if it doesn't succeed) + BLE_retry_sigkill: + mov $39, %rax + syscall # getpid + mov %rax, %rdi + mov $6, %rsi # SIGABRT + mov $62, %rax # kill + syscall + jmp BLE_retry_sigkill + +BLE_msg: + .ascii "diverged at 0x" +BLE_hex: + .ascii "0123456789abcdef" +BLE_nl: + .ascii "\n" + # List -# | ptr | 0 | -# | ptr | 1 | a | b | +# | ptr | 0 | # [] case +# | ptr | 1 | a | b | # (a:b) case LIST_evacuate: - # [] | a : b - retq #TODO + cmpq $0, 010(%rbp) + je LIST_evacuate_nil + pushq 030(%rbp) + pushq 020(%rbp) + pushq $1 + pushq $LIST_code + mov %rsp, %rbp + jmp _gc_evacuate_ret + + LIST_evacuate_nil: + pushq $0 + pushq $LIST_code + mov %rsp, %rbp + jmp _gc_evacuate_ret LIST_scavenge: - mov 010(%rbp), %rax - shl $1, %rax - add $2, %rax - shl $3, %rax - add %rax, %rsi - retq + cmpq $0, 010(%rbp) + je LIST_scavenge_nil + mov %rbp, %r15 + + mov $LIST_scavenge1, %rsi + mov 020(%r15), %rbp + jmp _gc_evacuate + LIST_scavenge1: + mov %rbp, 020(%r15) + + mov $LIST_scavenge2, %rsi + mov 030(%r15), %rbp + jmp _gc_evacuate + LIST_scavenge2: + mov %rbp, 030(%r15) + + mov %r15, %rbp + add $040, %rbp + jmp _gc_scavenge_ret + + LIST_scavenge_nil: + add $020, %rbp + jmp _gc_scavenge_ret + LIST_info_table: cell LIST_evacuate cell LIST_scavenge @@ -47,13 +173,42 @@ LIST_code: # FUN objects # | ptr | thunkptr | args | arg[0] | arg[1] | ... | arg[args] | FUN_evacuate: - retq #TODO + mov 020(%rbp), %rbx # rbx = count of arguments + mov %rbx, %rcx # rcx = count of arguments for later looping + lea 030(%rbp, %rbx, 010), %rdx # rdx = address of the arguments + FUN_evacuate_one: + sub $1, %rcx + jl FUN_evacuate_fini + sub $010, %rdx + pushq (%rdx) + jmp FUN_evacuate_one + FUN_evacuate_fini: + pushq %rbx + pushq 010(%rbp) + pushq 000(%rbp) + mov %rsp, %rbp + jmp _gc_evacuate_ret FUN_scavenge: - mov 020(%rbp), %rax - add $3, %rax - shl $3, %rax - add %rax, %rsi - retq + mov 020(%rbp), %r13 # r13 = count of arguments (for looping) + mov %rbp, %r15 # r15 = scavengee ptr + lea 030(%rbp, %r13, 010), %r14 # r14 = address of argument + + FUN_scavenge_one: + sub $1, %r13 + jl FUN_scavenge_fini + sub $010, %r14 + mov (%r14), %rbp + mov $FUN_scavenge_one_cont, %rsi + jmp _gc_evacuate + FUN_scavenge_one_cont: + mov %rbp, (%r14) + jmp FUN_scavenge_one + + FUN_scavenge_fini: + mov %r15, %rbp # restore rbp + mov 020(%rbp), %r14 + lea 030(%rbp, %r14, 010), %rbp + jmp _gc_scavenge_ret # Info tables for FUN objects. FUN0_info_table: @@ -90,39 +245,46 @@ FUN4_info_table: cell 4 FUN4_code: continue +# add more funN here as needed -# TODO: add more funN here as needed - -# indirection (Q: how to recognize IND and THUNK on return?) -# | ptr | indptr | -IND_evacuate: - retq #TODO -IND_scavenge: - add $020,%rsi - retq -IND_info: - cell IND_evacuate - cell IND_scavenge - cell 0 -IND_code: - enter 010(%rbp) - -# THU objects (gc implementation only, actual THUs are defined by functions) +# THU objects (gc implementation only, actual THU data are created by functions) # | ptr | args | arg[0] | arg[1] | ... | arg[args] | # args wouldn't need to be here but let's keep them for gc simplicity THU_evacuate: - retq #TODO + mov 010(%rbp), %rbx # rbx = count of arguments + mov %rbx, %rcx # rcx = count of arguments for later looping + lea 020(%rbp, %rbx, 010), %rdx # rdx = address of the argument + THU_evacuate_one: + sub $1, %rcx + jl THU_evacuate_fini + sub $010, %rdx + pushq (%rdx) + jmp THU_evacuate_one + THU_evacuate_fini: + pushq %rbx + pushq 000(%rbp) + mov %rsp, %rbp + jmp _gc_evacuate_ret THU_scavenge: - mov 010(%rbp), %rax - add $2,%rax - shl $3,%rax - add %rax,%rsi - retq + mov 010(%rbp), %r13 # r13 = count of arguments (for looping) + mov %rbp, %r15 # r15 = scavengee ptr + lea 020(%rbp, %r13, 010), %r14 # r14 = address of argument -.endif # _data_s_file + THU_scavenge_one: + sub $1, %r13 + jl THU_scavenge_fini + sub $010, %r14 + mov (%r14), %rbp + mov $THU_scavenge_one_cont, %rsi + jmp _gc_evacuate + THU_scavenge_one_cont: + mov %rbp, (%r14) + jmp THU_scavenge_one + + THU_scavenge_fini: + mov %r15, %rbp # restore rbp + mov 010(%rbp), %r14 + lea 020(%rbp, %r14, 010), %rbp + jmp _gc_scavenge_ret -# evacuate and scavenge: -# - evacuate just copies the object -# - scavenge evacuates all children (to the new location IF they are in the old -# location), changes the pointer, and moves the scavenge pointer to the next -# object (because everything needs to be scavenged) +.endif # _data_s_file |
