try to resolve var refs

This commit is contained in:
janis 2025-10-30 23:28:31 +01:00
parent 928be75faf
commit 746f82f732
Signed by: janis
SSH key fingerprint: SHA256:bB1qbbqmDXZNT0KKD5c2Dfjg53JGhj7B3CFcLIzSqq8
2 changed files with 96 additions and 24 deletions

View file

@ -361,7 +361,7 @@ parse_primary_expr:
jnz .var_ref jnz .var_ref
jmp .panic jmp .panic
.var_ref: .var_ref:
mov qword [rsp + 8], 0 ; AstVarRef.resolved mov qword [rsp + 8], -1 ; AstVarRef.resolved
mov [rsp + 16], rax ; AstVarRef.name mov [rsp + 16], rax ; AstVarRef.name
mov [rsp + 24], rdx ; AstVarRef.name_len mov [rsp + 24], rdx ; AstVarRef.name_len
@ -886,11 +886,12 @@ ast_parse_let:
; } ; }
; end-structs ; end-structs
; span: u64 [40..48] ; expr: u64 [48..56]
; *AstVarDecl [40..48]
; AstNode [8..40] ; AstNode [8..40]
; AstVarDecl [8..40] ; AstVarDecl [8..40]
; Ast [0..8] ; Ast [0..8]
sub rsp, 48 sub rsp, 56
mov [rsp], rdi ; Ast mov [rsp], rdi ; Ast
call tokeniser_get_cursor call tokeniser_get_cursor
@ -921,23 +922,9 @@ ast_parse_let:
mov rdx, 32 ; size_of::<AstVarDecl> mov rdx, 32 ; size_of::<AstVarDecl>
call memcpy call memcpy
mov qword [rsp + 8], AST_VAR_DECL ; AstNode.kind mov [rsp + 40], rdi ; AstVarDecl ptr
mov [rsp + 16], rdi ; AstNode.data
mov qword [rsp + 24], 0 ; AstNode.extra
mov rdi, [rsp + 40] ; span
mov [rsp + 32], rdi ; AstNode.span
mov rdi, [rsp] ; Ast
lea rsi, [rsp + 8] ; &AstNode
call vec_push
; variable is already a place
mov rdi, [rsp] ; Ast
mov rax, [rdi + 8] ; Ast.nodes.len()
dec rax
mov qword [rsp + 8], AST_ASSIGNMENT ; AstNode.kind
mov [rsp + 16], rax ; AstNode.data (variable index)
; parse the expression
mov dil, TOKEN_EQUALS mov dil, TOKEN_EQUALS
call unwrap_token call unwrap_token
mov rdi, [rsp] ; Ast mov rdi, [rsp] ; Ast
@ -945,10 +932,33 @@ ast_parse_let:
mov rdi, [rsp] ; Ast mov rdi, [rsp] ; Ast
mov rsi, rax ; expr mov rsi, rax ; expr
; mov rdx, rdx ; is_placeness ; mov rdx, rdx ; placeness
call ast_place_to_value call ast_place_to_value
mov [rsp + 48], rax ; expr index
; variable is defined at this point so that the expression cannot reference it
call tokeniser_get_cursor
mov rdi, [rsp + 40] ; AstVarDecl ptr
mov qword [rsp + 8], AST_VAR_DECL ; AstNode.kind
mov [rsp + 16], rdi ; AstNode.data
mov qword [rsp + 24], 0 ; AstNode.extra
mov [rsp + 32], rax ; AstNode.span
mov rdi, [rsp] ; Ast
lea rsi, [rsp + 8] ; &AstNode
call vec_push
; variables are places
mov rdi, [rsp] ; Ast
mov rax, [rdi + 8] ; Ast.nodes.len()
dec rax
mov qword [rsp + 8], AST_ASSIGNMENT ; AstNode.kind
mov [rsp + 16], rax ; AstNode.data (variable index)
mov rax, [rsp + 48] ; expr index
mov [rsp + 24], rax ; AstNode.extra (expr index) mov [rsp + 24], rax ; AstNode.extra (expr index)
; reuse span from variable declaration
mov rdi, [rsp] ; Ast mov rdi, [rsp] ; Ast
lea rsi, [rsp + 8] ; &AstNode lea rsi, [rsp + 8] ; &AstNode
call vec_push call vec_push
@ -956,7 +966,7 @@ ast_parse_let:
mov rax, [rdi + 8] ; Ast.nodes.len() mov rax, [rdi + 8] ; Ast.nodes.len()
dec rax dec rax
add rsp, 48 add rsp, 56
xor rdx, rdx ; placeness = false xor rdx, rdx ; placeness = false
pop rbp pop rbp
ret ret
@ -1478,16 +1488,78 @@ ast_walk_for_each:
pop rbp pop rbp
ret ret
;; rdi: Ctx ;; rdi: BuildSymtableCtx
;; rsi: Ast ;; rsi: *mut Ast
;; rdx: node_index ;; rdx: node_index
ast_resolve_var_refs_for_each: ast_resolve_var_refs_for_each:
push rbp push rbp
mov rbp, rsp mov rbp, rsp
push rbx
; SymEntry [24..80]
; *AstNode [16..24]
; *BuildSymtableCtx [8..16]
; *Ast [0..8]
sub rsp, 24
mov [rsp], rsi ; Ast
mov [rsp + 8], rdi ; Ctx
mov rdi, rsi ; Ast
mov rsi, rdx ; node_index
call vec_get
mov [rsp + 16], rax ; *AstNode
mov bl, byte [rax] ; AstNode.kind
cmp bl, AST_VAR_REF
jne .epilogue
; lookup variable in symbol table
; get current scope index
mov qword [rsp + 32], 0 ; SymKey.scope_index = default
mov rdi, [rsp + 8] ; *Ctx
lea rdi, [rdi + 0] ; Ctx.scope_stack
mov rsi, [rdi + 8] ; Ctx.scope_stack.len()
dec rsi
lea rdx, [rsp + 32]
call vec_get_or
mov rax, [rax] ; current scope index
; construct key
mov byte [rsp + 24 + 0], SYM_KEY_VAR ; SymKey.kind
mov [rsp + 24 + 8], rax ; SymKey.scope_index = scope_stack.last_or(0)
mov rax, [rsp + 16] ; *AstNode
mov rbx, [rax + 24] ; AstNode.span
mov [rsp + 24 + 16], rbx ; SymKey.span
mov rbx, [rax + 8] ; AstNode.data
mov rax, [rbx + 8] ; AstVarRef.name
mov rbx, [rbx + 16] ; AstVarRef.name_len
mov [rsp + 24 + 24], rax ; SymKey.ident
mov [rsp + 24 + 32], rbx ; SymKey.ident_len
; binary search in symbol table
mov rdi, [rsp + 8] ; *Ctx
lea rdi, [rdi + 40] ; Ctx.symtable
lea rsi, [rsp + 24] ; &SymKey
mov rdx, 0 ; cmp_ctx
mov rcx, symkey_cmp ; cmp
call vec_binary_search_by
test rdx, rdx
jnz .panic
mov rdx, [rsp + 16] ; *AstNode
mov rdx, [rdx + 8] ; AstNode.data
mov [rdx + 0], rax ; AstVarRef.resolved_index
.epilogue: .epilogue:
add rsp, 24
pop rbx
pop rbp pop rbp
ret ret
.panic:
call panic
;; rdi: Ast ;; rdi: Ast
;; define-fn: fn ast_resolve_var_refs(ast: *mut Ast) ;; define-fn: fn ast_resolve_var_refs(ast: *mut Ast)

View file

@ -110,7 +110,7 @@ impl std::fmt::Display for AstNode {
} }
AST_VAR_REF => { AST_VAR_REF => {
let var_ref = unsafe { self.data.cast::<util::defs::AstVarRef>().read() }; let var_ref = unsafe { self.data.cast::<util::defs::AstVarRef>().read() };
if var_ref.resolved != 0 { if var_ref.resolved != u64::MAX {
write!(f, "VarRef({})", var_ref.resolved) write!(f, "VarRef({})", var_ref.resolved)
} else { } else {
write!(f, "VarRef(name: {:?})", unsafe { write!(f, "VarRef(name: {:?})", unsafe {