Compare commits
8 commits
56354237c6
...
e79af01925
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
e79af01925 | ||
|
|
935a3e0a53 | ||
|
|
cd04a5a4ca | ||
|
|
cd5b714051 | ||
|
|
a769fece84 | ||
|
|
746f82f732 | ||
|
|
928be75faf | ||
|
|
adb30e983c |
501
lang/src/ast.asm
501
lang/src/ast.asm
|
|
@ -68,6 +68,7 @@ global parse_statement
|
||||||
global parse_block
|
global parse_block
|
||||||
global ast_build_symtable
|
global ast_build_symtable
|
||||||
global ast_walk_for_each
|
global ast_walk_for_each
|
||||||
|
global ast_resolve_var_refs
|
||||||
|
|
||||||
;; start very simple, with only functions and addition
|
;; start very simple, with only functions and addition
|
||||||
;; ```rust
|
;; ```rust
|
||||||
|
|
@ -82,6 +83,7 @@ global ast_walk_for_each
|
||||||
;; kind: u8,
|
;; kind: u8,
|
||||||
;; data: *const (),
|
;; data: *const (),
|
||||||
;; extra: usize,
|
;; extra: usize,
|
||||||
|
;; span: u64,
|
||||||
;; }
|
;; }
|
||||||
;;
|
;;
|
||||||
;; struct AstArgument {
|
;; struct AstArgument {
|
||||||
|
|
@ -101,6 +103,7 @@ global ast_walk_for_each
|
||||||
parse_func:
|
parse_func:
|
||||||
push rbp
|
push rbp
|
||||||
mov rbp, rsp
|
mov rbp, rsp
|
||||||
|
sub rsp, 8 ; span
|
||||||
push rdi
|
push rdi
|
||||||
|
|
||||||
; start-structs
|
; start-structs
|
||||||
|
|
@ -114,17 +117,21 @@ parse_func:
|
||||||
; }
|
; }
|
||||||
; end-structs
|
; end-structs
|
||||||
|
|
||||||
sub rsp, 56
|
; span: u64 [64..72]
|
||||||
; name: *const u8 [0..8]
|
|
||||||
; name_len: usize [8..16]
|
|
||||||
; args_ptr: *const u64 [16..24]
|
|
||||||
; args_len: usize [24..32]
|
|
||||||
; return_type: Type [32..48]
|
|
||||||
; body: u64 [48..56]
|
|
||||||
; ast: *mut Ast [56..64]
|
; ast: *mut Ast [56..64]
|
||||||
|
; body: u64 [48..56]
|
||||||
|
; return_type: Type [32..48]
|
||||||
|
; args_len: usize [24..32]
|
||||||
|
; args_ptr: *const u64 [16..24]
|
||||||
|
; name_len: usize [8..16]
|
||||||
|
; name: *const u8 [0..8]
|
||||||
|
sub rsp, 56
|
||||||
mov qword [rsp + 16], 8 ; <*u64>::dangling()
|
mov qword [rsp + 16], 8 ; <*u64>::dangling()
|
||||||
mov qword [rsp + 24], 0 ; args_len
|
mov qword [rsp + 24], 0 ; args_len
|
||||||
|
|
||||||
|
call tokeniser_get_cursor
|
||||||
|
mov [rsp + 64], rax ; span
|
||||||
|
|
||||||
mov dil, TOKEN_FN
|
mov dil, TOKEN_FN
|
||||||
call unwrap_token
|
call unwrap_token
|
||||||
mov dil, TOKEN_IDENT
|
mov dil, TOKEN_IDENT
|
||||||
|
|
@ -161,9 +168,11 @@ parse_func:
|
||||||
mov rdx, 56 ; size_of::<AstFunction>
|
mov rdx, 56 ; size_of::<AstFunction>
|
||||||
call memcpy
|
call memcpy
|
||||||
|
|
||||||
mov byte [rsp], AST_FUNCTION ; kind
|
mov byte [rsp], AST_FUNCTION ; AstNode.kind
|
||||||
mov [rsp + 8], rdi ; data
|
mov [rsp + 8], rdi ; AstNode.data
|
||||||
mov qword [rsp + 16], 0 ; extra
|
mov qword [rsp + 16], 0 ; AstNode.extra
|
||||||
|
mov rdi, [rsp + 64] ; span
|
||||||
|
mov [rsp + 24], rdi ; AstNode.span
|
||||||
mov rdi, [rsp + 56] ; Ast
|
mov rdi, [rsp + 56] ; Ast
|
||||||
lea rsi, [rsp] ; &AstNode
|
lea rsi, [rsp] ; &AstNode
|
||||||
call vec_push
|
call vec_push
|
||||||
|
|
@ -172,6 +181,7 @@ parse_func:
|
||||||
dec rax
|
dec rax
|
||||||
add rsp, 56
|
add rsp, 56
|
||||||
pop rdi
|
pop rdi
|
||||||
|
add rsp, 8
|
||||||
pop rbp
|
pop rbp
|
||||||
ret
|
ret
|
||||||
|
|
||||||
|
|
@ -189,6 +199,7 @@ parse_func:
|
||||||
parse_args:
|
parse_args:
|
||||||
push rbp
|
push rbp
|
||||||
mov rbp, rsp
|
mov rbp, rsp
|
||||||
|
; span: u64 [80..88]
|
||||||
; vec: [40..80]
|
; vec: [40..80]
|
||||||
; argument: AstArgument { [8..40]
|
; argument: AstArgument { [8..40]
|
||||||
; name: *const u8 [8..16]
|
; name: *const u8 [8..16]
|
||||||
|
|
@ -196,7 +207,7 @@ parse_args:
|
||||||
; arg_type: Type [24..40]
|
; arg_type: Type [24..40]
|
||||||
; }
|
; }
|
||||||
; ast [0..8]
|
; ast [0..8]
|
||||||
sub rsp, 80
|
sub rsp, 88
|
||||||
mov [rsp], rdi ; Ast
|
mov [rsp], rdi ; Ast
|
||||||
|
|
||||||
lea rdi, [rsp + 40] ; vec
|
lea rdi, [rsp + 40] ; vec
|
||||||
|
|
@ -210,6 +221,10 @@ parse_args:
|
||||||
call expect_token
|
call expect_token
|
||||||
test rax, rax
|
test rax, rax
|
||||||
jnz .done_args
|
jnz .done_args
|
||||||
|
|
||||||
|
call tokeniser_get_cursor
|
||||||
|
mov [rsp + 80], rax ; span
|
||||||
|
|
||||||
mov dil, TOKEN_IDENT
|
mov dil, TOKEN_IDENT
|
||||||
call unwrap_token
|
call unwrap_token
|
||||||
mov [rsp + 8], rax ; AstArgument.name
|
mov [rsp + 8], rax ; AstArgument.name
|
||||||
|
|
@ -232,6 +247,8 @@ parse_args:
|
||||||
mov qword [rsp + 8], AST_ARG ; AstNode.kind
|
mov qword [rsp + 8], AST_ARG ; AstNode.kind
|
||||||
mov [rsp + 16], rdi ; AstNode.data
|
mov [rsp + 16], rdi ; AstNode.data
|
||||||
mov qword [rsp + 24], 0 ; AstNode.extra
|
mov qword [rsp + 24], 0 ; AstNode.extra
|
||||||
|
mov rdi, [rsp + 80] ; span
|
||||||
|
mov [rsp + 32], rdi ; AstNode.span
|
||||||
|
|
||||||
mov rdi, [rsp] ; Ast
|
mov rdi, [rsp] ; Ast
|
||||||
lea rsi, [rsp + 8] ; &AstNode
|
lea rsi, [rsp + 8] ; &AstNode
|
||||||
|
|
@ -256,7 +273,7 @@ parse_args:
|
||||||
.done_args:
|
.done_args:
|
||||||
mov rax, [rsp + 40] ; args_ptr
|
mov rax, [rsp + 40] ; args_ptr
|
||||||
mov rdx, [rsp + 48] ; args_len
|
mov rdx, [rsp + 48] ; args_len
|
||||||
add rsp, 80
|
add rsp, 88
|
||||||
pop rbp
|
pop rbp
|
||||||
ret
|
ret
|
||||||
|
|
||||||
|
|
@ -317,7 +334,7 @@ parse_number:
|
||||||
parse_primary_expr:
|
parse_primary_expr:
|
||||||
push rbp
|
push rbp
|
||||||
mov rbp, rsp
|
mov rbp, rsp
|
||||||
sub rsp, 32
|
sub rsp, 40
|
||||||
mov [rsp], rdi ; Ast
|
mov [rsp], rdi ; Ast
|
||||||
|
|
||||||
; start-structs
|
; start-structs
|
||||||
|
|
@ -328,6 +345,9 @@ parse_primary_expr:
|
||||||
; }
|
; }
|
||||||
; end-structs
|
; end-structs
|
||||||
|
|
||||||
|
call tokeniser_get_cursor
|
||||||
|
mov [rsp + 32], rax ; span
|
||||||
|
|
||||||
mov dil, TOKEN_NUMBER
|
mov dil, TOKEN_NUMBER
|
||||||
call expect_token
|
call expect_token
|
||||||
test rax, rax
|
test rax, rax
|
||||||
|
|
@ -342,7 +362,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
|
||||||
|
|
||||||
|
|
@ -357,6 +377,7 @@ parse_primary_expr:
|
||||||
mov qword [rsp + 8], AST_VAR_REF ; AstNode.kind
|
mov qword [rsp + 8], AST_VAR_REF ; AstNode.kind
|
||||||
mov [rsp + 16], rdi ; AstNode.data
|
mov [rsp + 16], rdi ; AstNode.data
|
||||||
mov qword [rsp + 24], 0 ; AstNode.extra
|
mov qword [rsp + 24], 0 ; AstNode.extra
|
||||||
|
; mov [rsp + 32], span ; AstNode.span
|
||||||
mov rdi, [rsp] ; Ast
|
mov rdi, [rsp] ; Ast
|
||||||
lea rsi, [rsp + 8] ; &AstNode
|
lea rsi, [rsp + 8] ; &AstNode
|
||||||
call vec_push
|
call vec_push
|
||||||
|
|
@ -370,9 +391,10 @@ parse_primary_expr:
|
||||||
mov rsi, rdx ; lexeme len
|
mov rsi, rdx ; lexeme len
|
||||||
call parse_number
|
call parse_number
|
||||||
mov rdi, [rsp] ; Ast
|
mov rdi, [rsp] ; Ast
|
||||||
mov byte [rsp + 8], AST_NUMBER ; kind
|
mov byte [rsp + 8], AST_NUMBER ; AstNode.kind
|
||||||
mov [rsp + 16], rax ; data
|
mov [rsp + 16], rax ; AstNode.data
|
||||||
mov qword [rsp + 24], 0 ; extra
|
mov qword [rsp + 24], 0 ; AstNode.extra
|
||||||
|
; mov [rsp + 32], [rsp + 32] ; AstNode.span
|
||||||
lea rsi, [rsp + 8] ; &AstNode
|
lea rsi, [rsp + 8] ; &AstNode
|
||||||
call vec_push
|
call vec_push
|
||||||
mov rdi, [rsp] ; Ast
|
mov rdi, [rsp] ; Ast
|
||||||
|
|
@ -388,7 +410,7 @@ parse_primary_expr:
|
||||||
call unwrap_token
|
call unwrap_token
|
||||||
mov rax, [rsp + 8] ; expr
|
mov rax, [rsp + 8] ; expr
|
||||||
.epilogue:
|
.epilogue:
|
||||||
add rsp, 32
|
add rsp, 40
|
||||||
pop rbp
|
pop rbp
|
||||||
ret
|
ret
|
||||||
.panic:
|
.panic:
|
||||||
|
|
@ -412,6 +434,8 @@ parse_binary_expr:
|
||||||
; end-structs
|
; end-structs
|
||||||
|
|
||||||
sub rsp, 64
|
sub rsp, 64
|
||||||
|
; span: u64 [56..64]
|
||||||
|
; AstNode [32..64]
|
||||||
; lexeme: Lexeme [32..56]
|
; lexeme: Lexeme [32..56]
|
||||||
; right: u64 [24..32]
|
; right: u64 [24..32]
|
||||||
; right_placeness: u8 [20..21]
|
; right_placeness: u8 [20..21]
|
||||||
|
|
@ -426,6 +450,9 @@ parse_binary_expr:
|
||||||
mov byte [rsp + 17], sil ; upper_precedence
|
mov byte [rsp + 17], sil ; upper_precedence
|
||||||
mov byte [rsp + 16], 0
|
mov byte [rsp + 16], 0
|
||||||
|
|
||||||
|
call tokeniser_get_cursor
|
||||||
|
mov [rsp + 56], rax ; span
|
||||||
|
|
||||||
call parse_prefix_expr
|
call parse_prefix_expr
|
||||||
mov [rsp + 8], rax ; left
|
mov [rsp + 8], rax ; left
|
||||||
mov [rsp + 19], dl ; left_placeness
|
mov [rsp + 19], dl ; left_placeness
|
||||||
|
|
@ -510,6 +537,7 @@ parse_binary_expr:
|
||||||
mov byte [rsp + 32], AST_BINARY_OP ; AstNode.kind
|
mov byte [rsp + 32], AST_BINARY_OP ; AstNode.kind
|
||||||
mov [rsp + 40], rax ; AstNode.data
|
mov [rsp + 40], rax ; AstNode.data
|
||||||
mov qword [rsp + 48], 0 ; AstNode.extra
|
mov qword [rsp + 48], 0 ; AstNode.extra
|
||||||
|
; mov [rsp + 56], [rsp + 56] ; AstNode.span
|
||||||
mov rdi, [rsp] ; Ast
|
mov rdi, [rsp] ; Ast
|
||||||
lea rsi, [rsp + 32] ; &AstNode
|
lea rsi, [rsp + 32] ; &AstNode
|
||||||
call vec_push
|
call vec_push
|
||||||
|
|
@ -547,10 +575,13 @@ parse_statement:
|
||||||
push rbp
|
push rbp
|
||||||
mov rbp, rsp
|
mov rbp, rsp
|
||||||
|
|
||||||
; Ast [24..32]
|
; AstNode [8..40]
|
||||||
; AstNode [0..24]
|
; Ast [0..8]
|
||||||
sub rsp, 32
|
sub rsp, 40
|
||||||
mov [rsp + 24], rdi ; Ast
|
mov [rsp], rdi ; Ast
|
||||||
|
|
||||||
|
call tokeniser_get_cursor
|
||||||
|
mov [rsp + 32], rax ; AstNode.span
|
||||||
|
|
||||||
mov dil, TOKEN_RETURN
|
mov dil, TOKEN_RETURN
|
||||||
call expect_token
|
call expect_token
|
||||||
|
|
@ -563,21 +594,21 @@ parse_statement:
|
||||||
jmp .panic
|
jmp .panic
|
||||||
|
|
||||||
.let:
|
.let:
|
||||||
mov rdi, [rsp + 24] ; Ast
|
mov rdi, [rsp] ; Ast
|
||||||
call ast_parse_let
|
call ast_parse_let
|
||||||
mov [rsp], rax ; statement
|
mov [rsp], rax ; statement
|
||||||
jmp .semi
|
jmp .semi
|
||||||
|
|
||||||
.return:
|
.return:
|
||||||
mov rdi, [rsp + 24] ; Ast
|
mov rdi, [rsp] ; Ast
|
||||||
call parse_expr
|
call parse_expr
|
||||||
mov byte [rsp], AST_RETURN_STATEMENT ; kind
|
mov byte [rsp + 8], AST_RETURN_STATEMENT ; AstNode.kind
|
||||||
mov [rsp + 8], rax ; data
|
mov [rsp + 16], rax ; AstNode.data
|
||||||
mov qword [rsp + 16], 0 ; extra
|
mov qword [rsp + 24], 0 ; AstNode.extra
|
||||||
mov rdi, [rsp + 24] ; Ast
|
mov rdi, [rsp] ; Ast
|
||||||
lea rsi, [rsp] ; &AstNode
|
lea rsi, [rsp + 8] ; &AstNode
|
||||||
call vec_push
|
call vec_push
|
||||||
mov rdi, [rsp + 24] ; Ast
|
mov rdi, [rsp] ; Ast
|
||||||
mov rax, [rdi + 8] ; Ast.nodes.len()
|
mov rax, [rdi + 8] ; Ast.nodes.len()
|
||||||
dec rax
|
dec rax
|
||||||
mov [rsp], rax
|
mov [rsp], rax
|
||||||
|
|
@ -586,7 +617,7 @@ parse_statement:
|
||||||
mov dil, TOKEN_SEMI
|
mov dil, TOKEN_SEMI
|
||||||
call unwrap_token
|
call unwrap_token
|
||||||
mov rax, [rsp] ; expression
|
mov rax, [rsp] ; expression
|
||||||
add rsp, 32
|
add rsp, 40
|
||||||
pop rbp
|
pop rbp
|
||||||
ret
|
ret
|
||||||
.panic:
|
.panic:
|
||||||
|
|
@ -598,12 +629,16 @@ parse_block:
|
||||||
push rbp
|
push rbp
|
||||||
mov rbp, rsp
|
mov rbp, rsp
|
||||||
|
|
||||||
|
; span: u64 [64..72]
|
||||||
; Ast: *mut Ast [56..64]
|
; Ast: *mut Ast [56..64]
|
||||||
; statements: Vec<Statement> [8..56]
|
; statements: Vec<Statement> [8..56]
|
||||||
; statement: u64 [0..8]
|
; statement: u64 [0..8]
|
||||||
sub rsp, 64
|
sub rsp, 72
|
||||||
mov [rsp + 56], rdi ; Ast
|
mov [rsp + 56], rdi ; Ast
|
||||||
|
|
||||||
|
call tokeniser_get_cursor
|
||||||
|
mov [rsp + 64], rax ; span
|
||||||
|
|
||||||
mov dil, TOKEN_LBRACE
|
mov dil, TOKEN_LBRACE
|
||||||
call unwrap_token
|
call unwrap_token
|
||||||
|
|
||||||
|
|
@ -632,13 +667,15 @@ parse_block:
|
||||||
jmp .loop
|
jmp .loop
|
||||||
.done:
|
.done:
|
||||||
mov rdi, [rsp + 56] ; Ast
|
mov rdi, [rsp + 56] ; Ast
|
||||||
mov qword [rsp], AST_BLOCK ; kind
|
mov qword [rsp], AST_BLOCK ; AstNode.kind
|
||||||
|
mov rsi, [rsp + 64] ; span
|
||||||
|
mov [rsp + 24], rsi ; AstNode.span
|
||||||
lea rsi, [rsp] ; &AstNode
|
lea rsi, [rsp] ; &AstNode
|
||||||
call vec_push
|
call vec_push
|
||||||
mov rdi, [rsp + 56] ; Ast
|
mov rdi, [rsp + 56] ; Ast
|
||||||
mov rax, [rdi + 8] ; Ast.nodes.len()
|
mov rax, [rdi + 8] ; Ast.nodes.len()
|
||||||
dec rax
|
dec rax
|
||||||
add rsp, 64
|
add rsp, 72
|
||||||
pop rbp
|
pop rbp
|
||||||
ret
|
ret
|
||||||
|
|
||||||
|
|
@ -707,11 +744,14 @@ parse_prefix_expr:
|
||||||
push rbp
|
push rbp
|
||||||
mov rbp, rsp
|
mov rbp, rsp
|
||||||
|
|
||||||
|
; AstNode [8..40]
|
||||||
; ast [0..8]
|
; ast [0..8]
|
||||||
sub rsp, 32
|
sub rsp, 40
|
||||||
|
|
||||||
mov [rsp], rdi ; Ast
|
mov [rsp], rdi ; Ast
|
||||||
|
|
||||||
|
call tokeniser_get_cursor
|
||||||
|
mov [rsp + 32], rax ; AstNode.span
|
||||||
|
|
||||||
mov dil, TOKEN_STAR
|
mov dil, TOKEN_STAR
|
||||||
call expect_token
|
call expect_token
|
||||||
test rax, rax
|
test rax, rax
|
||||||
|
|
@ -763,7 +803,7 @@ parse_prefix_expr:
|
||||||
jmp .done
|
jmp .done
|
||||||
|
|
||||||
.done:
|
.done:
|
||||||
add rsp, 32
|
add rsp, 40
|
||||||
pop rbp
|
pop rbp
|
||||||
ret
|
ret
|
||||||
|
|
||||||
|
|
@ -773,13 +813,17 @@ parse_assignment_expr:
|
||||||
push rbp
|
push rbp
|
||||||
mov rbp, rsp
|
mov rbp, rsp
|
||||||
|
|
||||||
|
; span: u64 [32..40]
|
||||||
; source [24..32]
|
; source [24..32]
|
||||||
; dest [16..24]
|
; dest [16..24]
|
||||||
; dest_placeness [8..9]
|
; dest_placeness [8..9]
|
||||||
; ast [0..8]
|
; ast [0..8]
|
||||||
sub rsp, 32
|
sub rsp, 40
|
||||||
mov [rsp], rdi ; Ast
|
mov [rsp], rdi ; Ast
|
||||||
|
|
||||||
|
call tokeniser_get_cursor
|
||||||
|
mov [rsp + 32], rax ; span
|
||||||
|
|
||||||
mov rdi, [rsp] ; Ast
|
mov rdi, [rsp] ; Ast
|
||||||
call parse_binary_expr
|
call parse_binary_expr
|
||||||
mov [rsp + 16], rax ; dest
|
mov [rsp + 16], rax ; dest
|
||||||
|
|
@ -796,7 +840,7 @@ parse_assignment_expr:
|
||||||
mov rsi, [rsp + 16] ; dest
|
mov rsi, [rsp + 16] ; dest
|
||||||
movzx rdx, byte [rsp + 8] ; placeness
|
movzx rdx, byte [rsp + 8] ; placeness
|
||||||
call ast_value_to_place
|
call ast_value_to_place
|
||||||
mov [rsp + 16], rax ; source
|
mov [rsp + 16], rax ; dest
|
||||||
|
|
||||||
mov rdi, [rsp] ; Ast
|
mov rdi, [rsp] ; Ast
|
||||||
call parse_expr
|
call parse_expr
|
||||||
|
|
@ -820,7 +864,7 @@ parse_assignment_expr:
|
||||||
.done:
|
.done:
|
||||||
mov rax, [rsp + 16] ; dest
|
mov rax, [rsp + 16] ; dest
|
||||||
movzx rdx, byte [rsp + 8] ; placeness
|
movzx rdx, byte [rsp + 8] ; placeness
|
||||||
add rsp, 32
|
add rsp, 40
|
||||||
pop rbp
|
pop rbp
|
||||||
ret
|
ret
|
||||||
|
|
||||||
|
|
@ -843,12 +887,17 @@ ast_parse_let:
|
||||||
; }
|
; }
|
||||||
; end-structs
|
; end-structs
|
||||||
|
|
||||||
; AstNode [8..32]
|
; expr: u64 [48..56]
|
||||||
|
; *AstVarDecl [40..48]
|
||||||
|
; 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
|
||||||
|
mov [rsp + 40], rax ; span
|
||||||
|
|
||||||
; skipped in parse_statement
|
; skipped in parse_statement
|
||||||
; mov dil, TOKEN_LET
|
; mov dil, TOKEN_LET
|
||||||
; call unwrap_token
|
; call unwrap_token
|
||||||
|
|
@ -874,21 +923,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] ; 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
|
||||||
|
|
@ -896,10 +933,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
|
||||||
|
|
@ -907,7 +967,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
|
||||||
|
|
@ -924,17 +984,26 @@ ast_value_to_place:
|
||||||
mov rax, rsi
|
mov rax, rsi
|
||||||
je .done
|
je .done
|
||||||
; create new AST node
|
; create new AST node
|
||||||
sub rsp, 32
|
sub rsp, 40
|
||||||
mov [rsp], rdi
|
mov [rsp], rdi ; Ast
|
||||||
mov byte [rsp + 8], AST_VALUE_TO_PLACE ; kind
|
mov [rsp + 8], rsi ; node_index
|
||||||
mov [rsp + 16], rsi ; data
|
|
||||||
mov qword [rsp + 24], 0 ; extra
|
; load original node's span
|
||||||
|
call vec_get
|
||||||
|
mov rdi, [rax + 24] ; AstNode.span
|
||||||
|
mov [rsp + 32], rdi ; AstNode.span
|
||||||
|
|
||||||
|
mov rsi, [rsp + 8] ; node_index
|
||||||
|
mov byte [rsp + 8], AST_VALUE_TO_PLACE ; AstNode.kind
|
||||||
|
mov [rsp + 16], rsi ; AstNode.data
|
||||||
|
mov qword [rsp + 24], 0 ; AstNode.extra
|
||||||
lea rsi, [rsp + 8] ; &AstNode
|
lea rsi, [rsp + 8] ; &AstNode
|
||||||
|
mov rdi, [rsp] ; Ast
|
||||||
call vec_push
|
call vec_push
|
||||||
mov rdi, [rsp] ; Ast
|
mov rdi, [rsp] ; Ast
|
||||||
mov rax, [rdi + 8] ; Ast.nodes.len()
|
mov rax, [rdi + 8] ; Ast.nodes.len()
|
||||||
dec rax
|
dec rax
|
||||||
add rsp, 32
|
add rsp, 40
|
||||||
.done:
|
.done:
|
||||||
pop rbp
|
pop rbp
|
||||||
ret
|
ret
|
||||||
|
|
@ -951,17 +1020,26 @@ ast_place_to_value:
|
||||||
mov rax, rsi
|
mov rax, rsi
|
||||||
je .done
|
je .done
|
||||||
; create new AST node
|
; create new AST node
|
||||||
sub rsp, 32
|
sub rsp, 40
|
||||||
mov [rsp], rdi
|
mov [rsp], rdi ; Ast
|
||||||
mov byte [rsp + 8], AST_PLACE_TO_VALUE ; kind
|
mov [rsp + 8], rsi ; node_index
|
||||||
mov [rsp + 16], rsi ; data
|
|
||||||
mov qword [rsp + 24], 0 ; extra
|
; load original node's span
|
||||||
|
call vec_get
|
||||||
|
mov rdi, [rax + 24] ; AstNode.span
|
||||||
|
mov [rsp + 32], rdi ; AstNode.span
|
||||||
|
|
||||||
|
mov rsi, [rsp + 8] ; node_index
|
||||||
|
mov byte [rsp + 8], AST_PLACE_TO_VALUE ; AstNode.kind
|
||||||
|
mov [rsp + 16], rsi ; AstNode.data
|
||||||
|
mov qword [rsp + 24], 0 ; AstNode.extra
|
||||||
lea rsi, [rsp + 8] ; &AstNode
|
lea rsi, [rsp + 8] ; &AstNode
|
||||||
|
mov rdi, [rsp] ; Ast
|
||||||
call vec_push
|
call vec_push
|
||||||
mov rdi, [rsp] ; Ast
|
mov rdi, [rsp] ; Ast
|
||||||
mov rax, [rdi + 8] ; Ast.nodes.len()
|
mov rax, [rdi + 8] ; Ast.nodes.len()
|
||||||
dec rax
|
dec rax
|
||||||
add rsp, 32
|
add rsp, 40
|
||||||
.done:
|
.done:
|
||||||
pop rbp
|
pop rbp
|
||||||
ret
|
ret
|
||||||
|
|
@ -976,21 +1054,21 @@ symkey_cmp:
|
||||||
mov rbp, rsp
|
mov rbp, rsp
|
||||||
push rbx
|
push rbx
|
||||||
|
|
||||||
|
sub rsp, 16
|
||||||
|
mov [rsp], rsi
|
||||||
|
mov [rsp + 8], rdx
|
||||||
|
|
||||||
mov al, byte [rsi] ; a.kind
|
mov al, byte [rsi] ; a.kind
|
||||||
mov bl, byte [rdx] ; b.kind
|
mov bl, byte [rdx] ; b.kind
|
||||||
cmp al, bl
|
cmp al, bl
|
||||||
jl .a_less
|
jl .a_less
|
||||||
jg .a_greater
|
jg .a_greater
|
||||||
|
|
||||||
mov rax, [rsi + 8] ; a.scope_index
|
mov rax, [rsi + 8] ; a.scope_index
|
||||||
mov rbx, [rdx + 8] ; b.scope_index
|
mov rbx, [rdx + 8] ; b.scope_index
|
||||||
cmp rax, rbx
|
cmp rax, rbx
|
||||||
jl .a_less
|
jl .a_less
|
||||||
jg .a_greater
|
jg .a_greater
|
||||||
mov rax, [rsi + 16] ; a.span
|
|
||||||
mov rbx, [rdx + 16] ; b.span
|
|
||||||
cmp rax, rbx
|
|
||||||
jl .a_less
|
|
||||||
jg .a_greater
|
|
||||||
|
|
||||||
mov rdi, [rsi + 24] ; a.ident
|
mov rdi, [rsi + 24] ; a.ident
|
||||||
mov rsi, [rsi + 32] ; a.ident_len
|
mov rsi, [rsi + 32] ; a.ident_len
|
||||||
|
|
@ -1000,6 +1078,15 @@ symkey_cmp:
|
||||||
cmp rax, 0
|
cmp rax, 0
|
||||||
jl .a_less
|
jl .a_less
|
||||||
jg .a_greater
|
jg .a_greater
|
||||||
|
|
||||||
|
mov rsi, [rsp]
|
||||||
|
mov rdx, [rsp + 8]
|
||||||
|
mov rax, [rsi + 16] ; a.span
|
||||||
|
mov rbx, [rdx + 16] ; b.span
|
||||||
|
cmp rax, rbx
|
||||||
|
jl .a_less
|
||||||
|
jg .a_greater
|
||||||
|
|
||||||
xor rax, rax
|
xor rax, rax
|
||||||
jmp .epilogue
|
jmp .epilogue
|
||||||
.a_less:
|
.a_less:
|
||||||
|
|
@ -1008,6 +1095,7 @@ symkey_cmp:
|
||||||
.a_greater:
|
.a_greater:
|
||||||
mov rax, 1
|
mov rax, 1
|
||||||
.epilogue:
|
.epilogue:
|
||||||
|
add rsp, 16
|
||||||
pop rbx
|
pop rbx
|
||||||
pop rbp
|
pop rbp
|
||||||
ret
|
ret
|
||||||
|
|
@ -1033,23 +1121,17 @@ ast_build_symtable:
|
||||||
push rbp
|
push rbp
|
||||||
mov rbp, rsp
|
mov rbp, rsp
|
||||||
|
|
||||||
; BuildSymtableCtx [24..104]
|
; BuildSymtableCtx [24..64]
|
||||||
; *SymbolTable [16..24]
|
; *SymbolTable [16..24]
|
||||||
; root_index [8..16]
|
; root_index [8..16]
|
||||||
; Ast [0..8]
|
; Ast [0..8]
|
||||||
sub rsp, 104
|
sub rsp, 64
|
||||||
mov [rsp], rdi ; Ast
|
mov [rsp], rdi ; Ast
|
||||||
mov [rsp + 8], rsi ; root_index
|
mov [rsp + 8], rsi ; root_index
|
||||||
mov [rsp + 16], rdx ; *SymbolTable
|
mov [rsp + 16], rdx ; *SymbolTable
|
||||||
|
|
||||||
; initialise scope_stack and symtable vecs
|
; initialise scope_stack and symtable vecs
|
||||||
lea rdi, [rsp + 24] ; &BuildSymtableCtx.scope_stack
|
lea rdi, [rsp + 24] ; &BuildSymtableCtx.symtable
|
||||||
mov rsi, 8 ; size of u64
|
|
||||||
mov rdx, 0 ; drop = None
|
|
||||||
mov rcx, 128 ; capacity
|
|
||||||
call vec_init_with
|
|
||||||
|
|
||||||
lea rdi, [rsp + 24 + 40] ; &BuildSymtableCtx.symtable
|
|
||||||
mov rsi, 56 ; size_of::<SymEntry>
|
mov rsi, 56 ; size_of::<SymEntry>
|
||||||
mov rdx, 0 ; drop = None
|
mov rdx, 0 ; drop = None
|
||||||
mov rcx, 128 ; capacity
|
mov rcx, 128 ; capacity
|
||||||
|
|
@ -1064,11 +1146,11 @@ ast_build_symtable:
|
||||||
; memcpy symtable out
|
; memcpy symtable out
|
||||||
|
|
||||||
mov rdi, [rsp + 16] ; *SymbolTable
|
mov rdi, [rsp + 16] ; *SymbolTable
|
||||||
lea rsi, [rsp + 24 + 40] ; &BuildSymtableCtx.symtable
|
lea rsi, [rsp + 24] ; &BuildSymtableCtx.symtable
|
||||||
mov rdx, 40 ; size_of::<Vec<SymEntry>>
|
mov rdx, 40 ; size_of::<Vec<SymEntry>>
|
||||||
call memcpy
|
call memcpy
|
||||||
|
|
||||||
add rsp, 104
|
add rsp, 64
|
||||||
pop rbp
|
pop rbp
|
||||||
ret
|
ret
|
||||||
|
|
||||||
|
|
@ -1118,7 +1200,6 @@ ast_build_symtable:
|
||||||
;;
|
;;
|
||||||
;; #start-structs
|
;; #start-structs
|
||||||
;; struct BuildSymtableCtx {
|
;; struct BuildSymtableCtx {
|
||||||
;; scope_stack: Vec<u64>,
|
|
||||||
;; symtable: Vec<SymEntry>,
|
;; symtable: Vec<SymEntry>,
|
||||||
;; }
|
;; }
|
||||||
;; #end-structs
|
;; #end-structs
|
||||||
|
|
@ -1129,21 +1210,24 @@ ast_build_symtable:
|
||||||
;; rdi: Ctx
|
;; rdi: Ctx
|
||||||
;; rsi: Ast
|
;; rsi: Ast
|
||||||
;; rdx: index
|
;; rdx: index
|
||||||
|
;; rcx: scope
|
||||||
ast_build_symtable_for_each:
|
ast_build_symtable_for_each:
|
||||||
push rbp
|
push rbp
|
||||||
mov rbp, rsp
|
mov rbp, rsp
|
||||||
push rbx
|
push rbx
|
||||||
|
|
||||||
|
; scope: u64 [88..96]
|
||||||
; SymEntry [32..88]
|
; SymEntry [32..88]
|
||||||
; SymKey [32..72]
|
; SymKey [32..72]
|
||||||
; *AstNode [24..32]
|
; *AstNode [24..32]
|
||||||
; index [16..24]
|
; index [16..24]
|
||||||
; ctx [8..16]
|
; ctx [8..16]
|
||||||
; ast [0..8]
|
; ast [0..8]
|
||||||
sub rsp, 88
|
sub rsp, 96
|
||||||
mov [rsp], rsi ; Ast
|
mov [rsp], rsi ; Ast
|
||||||
mov [rsp + 8], rdi ; Ctx
|
mov [rsp + 8], rdi ; Ctx
|
||||||
mov [rsp + 16], rdx ; index
|
mov [rsp + 16], rdx ; index
|
||||||
|
mov [rsp + 88], rcx ; scope
|
||||||
|
|
||||||
mov rdi, rsi ; Ast
|
mov rdi, rsi ; Ast
|
||||||
mov rsi, rdx ; index
|
mov rsi, rdx ; index
|
||||||
|
|
@ -1164,40 +1248,49 @@ ast_build_symtable_for_each:
|
||||||
mov byte [rsp + 32], SYM_KEY_SCOPE ; SymKey.kind
|
mov byte [rsp + 32], SYM_KEY_SCOPE ; SymKey.kind
|
||||||
mov rdx, [rsp + 16] ; index
|
mov rdx, [rsp + 16] ; index
|
||||||
mov qword [rsp + 40], rdx ; SymKey.scope_index
|
mov qword [rsp + 40], rdx ; SymKey.scope_index
|
||||||
mov qword [rsp + 48], 0 ; SymKey.span
|
mov rdx, [rax + 24] ; AstNode.span
|
||||||
|
mov qword [rsp + 48], rdx ; SymKey.span
|
||||||
mov qword [rsp + 56], 1 ; SymKey.ident
|
mov qword [rsp + 56], 1 ; SymKey.ident
|
||||||
mov qword [rsp + 64], 0 ; SymKey.ident_len
|
mov qword [rsp + 64], 0 ; SymKey.ident_len
|
||||||
|
|
||||||
; mov rbx, [rax + 16] ; AstNode.data
|
|
||||||
; mov rdx, [rbx + 8] ; Func.name
|
|
||||||
; mov rcx, [rbx + 16] ; Func.name_len
|
|
||||||
mov rbx, [rax + 8] ; AstNode.data
|
mov rbx, [rax + 8] ; AstNode.data
|
||||||
mov rdx, [rbx + 0] ; Func.name
|
mov rdx, [rbx + 0] ; Func.name
|
||||||
mov rcx, [rbx + 8] ; Func.name_len
|
mov rcx, [rbx + 8] ; Func.name_len
|
||||||
|
|
||||||
mov qword [rsp + 72], rdx ; SymEntry.index
|
mov [rsp + 72], rdx ; SymEntry.index
|
||||||
mov qword [rsp + 80], rcx ; SymEntry.extra
|
mov [rsp + 80], rcx ; SymEntry.extra
|
||||||
|
|
||||||
mov rdi, [rsp + 8] ; *Ctx
|
mov rdi, [rsp + 8] ; Ctx.symtable
|
||||||
lea rdi, [rdi + 40] ; Ctx.symtable
|
|
||||||
lea rsi, [rsp + 32] ; &SymEntry
|
lea rsi, [rsp + 32] ; &SymEntry
|
||||||
mov rcx, 0 ; cmp_ctx
|
mov rcx, 0 ; cmp_ctx
|
||||||
mov rdx, symkey_cmp ; cmp
|
mov rdx, symkey_cmp ; cmp
|
||||||
call vec_insert_sorted
|
call vec_insert_sorted
|
||||||
|
|
||||||
; push scope index onto scope_stack
|
; add parent scope
|
||||||
|
mov byte [rsp + 32], SYM_KEY_PARENT_SCOPE ; SymKey.kind
|
||||||
|
mov rdx, [rsp + 16] ; index
|
||||||
|
mov qword [rsp + 40], rdx ; SymKey.scope_index
|
||||||
|
mov qword [rsp + 48], 0 ; SymKey.span
|
||||||
|
mov qword [rsp + 56], 1 ; SymKey.ident
|
||||||
|
mov qword [rsp + 64], 0 ; SymKey.ident_len
|
||||||
|
|
||||||
|
mov rdx, [rsp + 88] ; parent scope
|
||||||
|
mov [rsp + 72], rdx ; SymEntry.index
|
||||||
|
mov qword [rsp + 80], 0 ; SymEntry.extra
|
||||||
|
|
||||||
mov rdi, [rsp + 8] ; *Ctx
|
mov rdi, [rsp + 8] ; *Ctx
|
||||||
lea rdi, [rdi + 0] ; Ctx.scope_stack
|
lea rsi, [rsp + 32] ; &SymEntry
|
||||||
lea rsi, [rsp + 16] ; &index
|
mov rcx, 0 ; cmp_ctx
|
||||||
call vec_push
|
mov rdx, symkey_cmp ; cmp
|
||||||
|
call vec_insert_sorted
|
||||||
|
|
||||||
jmp .done
|
jmp .done
|
||||||
.var_decl:
|
.var_decl:
|
||||||
; insert variable entry
|
; insert variable entry
|
||||||
mov byte [rsp + 32], SYM_KEY_VAR ; SymKey.kind
|
mov byte [rsp + 32], SYM_KEY_VAR ; SymKey.kind
|
||||||
|
|
||||||
; TODO: set span correctly
|
mov rdx, [rax + 24] ; AstNode.span
|
||||||
mov qword [rsp + 48], 0 ; SymKey.span
|
mov qword [rsp + 48], rdx ; SymKey.span
|
||||||
|
|
||||||
mov rbx, [rsp + 24] ; AstNode.data
|
mov rbx, [rsp + 24] ; AstNode.data
|
||||||
mov rbx, [rbx + 8] ; AstNode.data
|
mov rbx, [rbx + 8] ; AstNode.data
|
||||||
|
|
@ -1211,17 +1304,10 @@ ast_build_symtable_for_each:
|
||||||
mov [rsp + 72], rdx ; SymEntry.index
|
mov [rsp + 72], rdx ; SymEntry.index
|
||||||
mov qword [rsp + 80], 0 ; SymEntry.extra
|
mov qword [rsp + 80], 0 ; SymEntry.extra
|
||||||
|
|
||||||
mov qword [rsp + 40], 0 ; SymKey.scope_index = default
|
mov rdx, [rsp + 88] ; current scope
|
||||||
lea rdx, [rsp + 40]
|
mov [rsp + 40], rdx ; SymKey.scope_index = default
|
||||||
mov rdi, [rsp + 8] ; *Ctx
|
|
||||||
mov rsi, [rdi + 8] ; Ctx.scope_stack.len()
|
|
||||||
dec rsi
|
|
||||||
call vec_get_or
|
|
||||||
mov rax, [rax] ; current scope index
|
|
||||||
mov [rsp + 40], rax ; SymKey.scope_index = scope_stack.last_or(0)
|
|
||||||
|
|
||||||
mov rdi, [rsp + 8] ; *Ctx
|
mov rdi, [rsp + 8] ; *Ctx
|
||||||
lea rdi, [rdi + 40] ; Ctx.symtable
|
|
||||||
lea rsi, [rsp + 32] ; &SymEntry
|
lea rsi, [rsp + 32] ; &SymEntry
|
||||||
mov rcx, 0 ; cmp_ctx
|
mov rcx, 0 ; cmp_ctx
|
||||||
mov rdx, symkey_cmp ; cmp
|
mov rdx, symkey_cmp ; cmp
|
||||||
|
|
@ -1232,8 +1318,8 @@ ast_build_symtable_for_each:
|
||||||
; insert variable entry
|
; insert variable entry
|
||||||
mov byte [rsp + 32], SYM_KEY_ARG ; SymKey.kind
|
mov byte [rsp + 32], SYM_KEY_ARG ; SymKey.kind
|
||||||
|
|
||||||
; TODO: set span correctly
|
mov rdx, [rax + 24] ; AstNode.span
|
||||||
mov qword [rsp + 48], 0 ; SymKey.span
|
mov qword [rsp + 48], rdx ; SymKey.span
|
||||||
|
|
||||||
mov rbx, [rsp + 24] ; *AstNode
|
mov rbx, [rsp + 24] ; *AstNode
|
||||||
mov rbx, [rbx + 8] ; AstNode.data
|
mov rbx, [rbx + 8] ; AstNode.data
|
||||||
|
|
@ -1247,24 +1333,18 @@ ast_build_symtable_for_each:
|
||||||
mov [rsp + 72], rdx ; SymEntry.index
|
mov [rsp + 72], rdx ; SymEntry.index
|
||||||
mov qword [rsp + 80], 0 ; SymEntry.extra
|
mov qword [rsp + 80], 0 ; SymEntry.extra
|
||||||
|
|
||||||
mov qword [rsp + 40], 0 ; SymKey.scope_index = default
|
mov rdx, [rsp + 88] ; current scope
|
||||||
lea rdx, [rsp + 40]
|
mov [rsp + 40], rdx ; SymKey.scope_index = default
|
||||||
mov rdi, [rsp + 8] ; *Ctx
|
|
||||||
mov rsi, [rdi + 8] ; Ctx.scope_stack.len()
|
|
||||||
dec rsi
|
|
||||||
call vec_get_or
|
|
||||||
mov rax, [rax] ; current scope index
|
|
||||||
mov [rsp + 40], rax ; SymKey.scope_index = scope_stack.last_or(0)
|
|
||||||
|
|
||||||
mov rdi, [rsp + 8] ; *Ctx
|
mov rdi, [rsp + 8] ; *Ctx
|
||||||
lea rdi, [rdi + 40] ; Ctx.symtable
|
|
||||||
lea rsi, [rsp + 32] ; &SymEntry
|
lea rsi, [rsp + 32] ; &SymEntry
|
||||||
mov rcx, 0 ; cmp_ctx
|
mov rcx, 0 ; cmp_ctx
|
||||||
mov rdx, symkey_cmp ; cmp
|
mov rdx, symkey_cmp ; cmp
|
||||||
call vec_insert_sorted
|
call vec_insert_sorted
|
||||||
|
jmp .done
|
||||||
|
|
||||||
.done:
|
.done:
|
||||||
add rsp, 88
|
add rsp, 96
|
||||||
pop rbx
|
pop rbx
|
||||||
pop rbp
|
pop rbp
|
||||||
ret
|
ret
|
||||||
|
|
@ -1273,26 +1353,39 @@ ast_build_symtable_for_each:
|
||||||
;; rsi: start_index
|
;; rsi: start_index
|
||||||
;; rdx: ctx
|
;; rdx: ctx
|
||||||
;; rcx: for_each
|
;; rcx: for_each
|
||||||
;; define-fn: fn ast_walk_for_each(ast: *mut Ast, start_index: u64, ctx: *mut (), for_each: unsafe extern "C" fn(ctx: *mut (), *mut Ast, node_index: u64))
|
;; define-fn: fn ast_walk_for_each(ast: *mut Ast, start_index: u64, ctx: *mut (), for_each: unsafe extern "C" fn(ctx: *mut (), *mut Ast, node_index: u64, scope: u64))
|
||||||
ast_walk_for_each:
|
ast_walk_for_each:
|
||||||
push rbp
|
push rbp
|
||||||
push r15
|
push r15
|
||||||
push r14
|
push r14
|
||||||
push rbx
|
push rbx
|
||||||
|
|
||||||
; current_index [24..32]
|
; INVALID_SCOPE [48..56]
|
||||||
|
; current_index [40..48]
|
||||||
|
; *current_scope [32..40]
|
||||||
|
; current_node_ptr [24..32]
|
||||||
; for_each [16..24]
|
; for_each [16..24]
|
||||||
; ctx [8..16]
|
; ctx [8..16]
|
||||||
; ast [0..8]
|
; ast [0..8]
|
||||||
sub rsp, 32
|
sub rsp, 56
|
||||||
mov [rsp], rdi ; Ast
|
mov [rsp], rdi ; Ast
|
||||||
mov [rsp + 8], rdx ; ctx
|
mov [rsp + 8], rdx ; ctx
|
||||||
mov [rsp + 16], rcx ; for_each
|
mov [rsp + 16], rcx ; for_each
|
||||||
mov [rsp + 24], rsi ; current_node_ptr
|
mov qword [rsp + 24], 0 ; current_node_ptr
|
||||||
|
lea rdi, [rsp + 48] ; &INVALID_SCOPE
|
||||||
|
mov [rsp + 32], rdi ; current_scope
|
||||||
|
mov [rsp + 40], rsi ; current_index
|
||||||
|
mov qword [rsp + 48], -1 ; INVALID_SCOPE
|
||||||
|
|
||||||
mov rbp, rsp
|
mov rbp, rsp
|
||||||
push rsi
|
push rsi
|
||||||
|
|
||||||
|
; `current_scope` points to the index of the current scope on the stack.
|
||||||
|
; When we enter a new scope, we push `current_scope` onto the stack, then
|
||||||
|
; update it to point to the new scope index.
|
||||||
|
; When `rsp` is equal to `current_scope`, we need to additionally pop into
|
||||||
|
; `current_scope` after popping the current index.
|
||||||
|
|
||||||
.loop:
|
.loop:
|
||||||
cmp rsp, rbp
|
cmp rsp, rbp
|
||||||
jge .done
|
jge .done
|
||||||
|
|
@ -1300,6 +1393,8 @@ ast_walk_for_each:
|
||||||
mov rdi, [rbp + 8] ; ctx
|
mov rdi, [rbp + 8] ; ctx
|
||||||
mov rsi, [rbp] ; Ast
|
mov rsi, [rbp] ; Ast
|
||||||
mov rdx, [rsp] ; current_index
|
mov rdx, [rsp] ; current_index
|
||||||
|
mov rcx, [rbp + 32] ; current_scope
|
||||||
|
mov rcx, [rcx] ; current_scope value
|
||||||
mov rax, [rbp + 16] ; for_each
|
mov rax, [rbp + 16] ; for_each
|
||||||
|
|
||||||
; align stack to 16 bytes before call
|
; align stack to 16 bytes before call
|
||||||
|
|
@ -1313,6 +1408,8 @@ ast_walk_for_each:
|
||||||
; get current_node_ptr
|
; get current_node_ptr
|
||||||
mov rdi, [rbp] ; Ast
|
mov rdi, [rbp] ; Ast
|
||||||
pop rsi ; current_index
|
pop rsi ; current_index
|
||||||
|
mov [rbp + 40], rsi ; update current_index
|
||||||
|
|
||||||
call vec_get
|
call vec_get
|
||||||
mov [rbp + 24], rax ; current_node_ptr
|
mov [rbp + 24], rax ; current_node_ptr
|
||||||
mov bl, byte [rax] ; AstNode.kind
|
mov bl, byte [rax] ; AstNode.kind
|
||||||
|
|
@ -1334,9 +1431,14 @@ ast_walk_for_each:
|
||||||
je .address_of
|
je .address_of
|
||||||
cmp bl, AST_RETURN_STATEMENT
|
cmp bl, AST_RETURN_STATEMENT
|
||||||
je .return_statement
|
je .return_statement
|
||||||
jmp .loop
|
jmp .check_scope
|
||||||
|
|
||||||
.func:
|
.func:
|
||||||
|
; push scope
|
||||||
|
push qword [rbp + 32] ; scope-ptr
|
||||||
|
push qword [rbp + 40] ; current_index
|
||||||
|
mov [rbp + 32], rsp ; update current_scope
|
||||||
|
|
||||||
; push child indices to stack
|
; push child indices to stack
|
||||||
mov rbx, [rax + 8] ; AstNode.data
|
mov rbx, [rax + 8] ; AstNode.data
|
||||||
|
|
||||||
|
|
@ -1354,7 +1456,7 @@ ast_walk_for_each:
|
||||||
inc r14
|
inc r14
|
||||||
jmp .arg_loop
|
jmp .arg_loop
|
||||||
.arg_loop_done:
|
.arg_loop_done:
|
||||||
jmp .loop
|
jmp .check_scope
|
||||||
|
|
||||||
.block:
|
.block:
|
||||||
mov rbx, [rax + 8] ; AstNode.data
|
mov rbx, [rax + 8] ; AstNode.data
|
||||||
|
|
@ -1368,7 +1470,7 @@ ast_walk_for_each:
|
||||||
push rdx ; push statement index
|
push rdx ; push statement index
|
||||||
jmp .stmt_loop
|
jmp .stmt_loop
|
||||||
.stmt_loop_done:
|
.stmt_loop_done:
|
||||||
jmp .loop
|
jmp .check_scope
|
||||||
|
|
||||||
.binary_op:
|
.binary_op:
|
||||||
mov rbx, [rax + 8] ; AstNode.data
|
mov rbx, [rax + 8] ; AstNode.data
|
||||||
|
|
@ -1376,14 +1478,14 @@ ast_walk_for_each:
|
||||||
push rdx ; push right index
|
push rdx ; push right index
|
||||||
mov rdx, [rbx + 0] ; left index
|
mov rdx, [rbx + 0] ; left index
|
||||||
push rdx ; push left index
|
push rdx ; push left index
|
||||||
jmp .loop
|
jmp .check_scope
|
||||||
|
|
||||||
.assignment:
|
.assignment:
|
||||||
mov rbx, [rax + 8] ; AstNode.data = dest
|
mov rbx, [rax + 8] ; AstNode.data = dest
|
||||||
mov rdx, [rax + 16] ; AstNode.extra = source
|
mov rdx, [rax + 16] ; AstNode.extra = source
|
||||||
push rdx ; push source index
|
push rdx ; push source index
|
||||||
push rbx ; push dest index
|
push rbx ; push dest index
|
||||||
jmp .loop
|
jmp .check_scope
|
||||||
|
|
||||||
.value_to_place:
|
.value_to_place:
|
||||||
.place_to_value:
|
.place_to_value:
|
||||||
|
|
@ -1392,30 +1494,145 @@ ast_walk_for_each:
|
||||||
.return_statement:
|
.return_statement:
|
||||||
mov rbx, [rax + 8] ; AstNode.data
|
mov rbx, [rax + 8] ; AstNode.data
|
||||||
push rbx ; push inner expr index
|
push rbx ; push inner expr index
|
||||||
|
jmp .check_scope
|
||||||
|
|
||||||
|
.check_scope:
|
||||||
|
cmp rsp, [rbp + 32] ; current_scope
|
||||||
|
je .pop_scope
|
||||||
jmp .loop
|
jmp .loop
|
||||||
|
|
||||||
; weird alloca thing
|
.pop_scope:
|
||||||
|
; pop current_scope
|
||||||
|
; the stack may look something like this:
|
||||||
|
; current_scope---+
|
||||||
|
; == stack == ^ | points here
|
||||||
|
; scope-ptr[0]-+ |
|
||||||
|
; scope: func0 <-----+
|
||||||
|
; stmt0 | |
|
||||||
|
; stmt1 | |
|
||||||
|
; scope-ptr[1] ------+
|
||||||
|
; scope: block0 <-+
|
||||||
|
; stmt2
|
||||||
|
; stmt3
|
||||||
|
; ...
|
||||||
|
|
||||||
|
pop rax ; scope
|
||||||
|
pop rax ; scope_ptr
|
||||||
|
mov [rbp + 32], rax ; update current_scope pointer
|
||||||
|
jmp .check_scope
|
||||||
|
|
||||||
.done:
|
.done:
|
||||||
add rsp, 32
|
add rsp, 56
|
||||||
pop rbx
|
pop rbx
|
||||||
pop r14
|
pop r14
|
||||||
pop r15
|
pop r15
|
||||||
pop rbp
|
pop rbp
|
||||||
ret
|
ret
|
||||||
|
|
||||||
|
;; rdi: *mut SymbolTable
|
||||||
|
;; rsi: *mut Ast
|
||||||
|
;; rdx: node_index
|
||||||
|
;; rcx: scope
|
||||||
|
ast_resolve_var_refs_for_each:
|
||||||
|
push rbp
|
||||||
|
mov rbp, rsp
|
||||||
|
push rbx
|
||||||
|
|
||||||
|
; lower_bound [88..96]
|
||||||
|
; scope: u64 [80..88]
|
||||||
|
; SymEntry [24..80]
|
||||||
|
; *AstNode [16..24]
|
||||||
|
; *BuildSymtableCtx [8..16]
|
||||||
|
; *Ast [0..8]
|
||||||
|
sub rsp, 96
|
||||||
|
mov [rsp], rsi ; Ast
|
||||||
|
mov [rsp + 8], rdi ; Ctx
|
||||||
|
|
||||||
|
mov [rsp + 80], rcx ; SymKey.scope_index
|
||||||
|
|
||||||
|
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
|
||||||
|
|
||||||
|
; binary search lower bound
|
||||||
|
mov byte [rsp + 24 + 0], SYM_KEY_START_LOCALS ; SymKey.kind
|
||||||
|
mov qword [rsp + 24 + 8], 0 ; SymKey.scope_index
|
||||||
|
mov qword [rsp + 24 + 16], 0 ; SymKey.span
|
||||||
|
mov qword [rsp + 24 + 24], 1 ; SymKey.name
|
||||||
|
mov qword [rsp + 24 + 32], 0 ; SymKey.name_len
|
||||||
|
|
||||||
|
; binary search in symbol table
|
||||||
|
mov rdi, [rsp + 8] ; *Ctx
|
||||||
|
lea rsi, [rsp + 24] ; &SymKey
|
||||||
|
mov rdx, symkey_cmp ; cmp
|
||||||
|
mov rcx, 0 ; cmp_ctx
|
||||||
|
call vec_binary_search_by
|
||||||
|
mov [rsp + 88], rax ; lower_bound
|
||||||
|
|
||||||
|
; construct key
|
||||||
|
mov byte [rsp + 24 + 0], SYM_KEY_VAR ; SymKey.kind
|
||||||
|
mov rax, [rsp + 80] ; scope
|
||||||
|
mov [rsp + 24 + 8], rax ; SymKey.scope_index
|
||||||
|
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 rsi, [rsp + 24] ; &SymKey
|
||||||
|
mov rdx, symkey_cmp ; cmp
|
||||||
|
mov rcx, 0 ; cmp_ctx
|
||||||
|
call vec_binary_search_by
|
||||||
|
test rdx, rdx
|
||||||
|
jz .fixup
|
||||||
|
dec rax
|
||||||
|
|
||||||
|
.fixup:
|
||||||
|
cmp rax, [rsp + 88] ; lower_bound
|
||||||
|
jl .panic
|
||||||
|
|
||||||
|
mov rdi, [rsp + 8] ; *Ctx
|
||||||
|
mov rsi, rax ; index
|
||||||
|
call vec_get
|
||||||
|
mov rax, [rax + 40] ; SymEntry.index
|
||||||
|
|
||||||
|
mov rdx, [rsp + 16] ; *AstNode
|
||||||
|
mov rdx, [rdx + 8] ; AstNode.data
|
||||||
|
mov [rdx + 0], rax ; AstVarRef.resolved_index
|
||||||
|
|
||||||
|
.epilogue:
|
||||||
|
add rsp, 96
|
||||||
|
pop rbx
|
||||||
|
pop rbp
|
||||||
|
ret
|
||||||
|
.panic:
|
||||||
|
call panic
|
||||||
|
|
||||||
;; rdi: Ast
|
;; rdi: Ast
|
||||||
;; define-fn: fn ast_resolve_var_refs(ast: *mut Ast)
|
;; rsi: *mut SymbolTable
|
||||||
|
;; rdx: root_index
|
||||||
|
;; define-fn: fn ast_resolve_var_refs(ast: *mut Ast, ctx: *mut SymbolTable, root_index: u64)
|
||||||
ast_resolve_var_refs:
|
ast_resolve_var_refs:
|
||||||
push rbp
|
push rbp
|
||||||
mov rbp, rsp
|
mov rbp, rsp
|
||||||
push r15
|
|
||||||
push r14
|
xchg rsi, rdx
|
||||||
push rbx
|
mov rcx, ast_resolve_var_refs_for_each
|
||||||
|
call ast_walk_for_each
|
||||||
|
|
||||||
.epilogue:
|
.epilogue:
|
||||||
add rsp, 8
|
|
||||||
pop rbx
|
|
||||||
pop r14
|
|
||||||
pop r15
|
|
||||||
pop rbp
|
pop rbp
|
||||||
ret
|
ret
|
||||||
|
|
|
||||||
|
|
@ -29,22 +29,31 @@ fn main() {
|
||||||
eprintln!("Parsed expression ID: {}", expr_id);
|
eprintln!("Parsed expression ID: {}", expr_id);
|
||||||
println!("{:#}", &ast);
|
println!("{:#}", &ast);
|
||||||
|
|
||||||
// unsafe extern "C" fn visit_node(_this: *mut (), ast: *mut Ast, node_id: u64) {
|
// unsafe extern "C" fn visit_node(
|
||||||
|
// _this: *mut (),
|
||||||
|
// ast: *mut Ast,
|
||||||
|
// node_id: u64,
|
||||||
|
// scope: u64,
|
||||||
|
// ) {
|
||||||
// let ast = unsafe { &*ast };
|
// let ast = unsafe { &*ast };
|
||||||
// let node = ast.nodes.get(node_id as usize).unwrap();
|
// let node = ast.nodes.get(node_id as usize).unwrap();
|
||||||
// eprintln!("Visiting node {node_id}: {node}");
|
// eprintln!("{scope}: Visiting node {node_id}: {node}");
|
||||||
// }
|
// }
|
||||||
|
|
||||||
// util::defs::ast_walk_for_each(&mut ast, expr_id, core::ptr::null_mut(), visit_node);
|
// util::defs::ast_walk_for_each(&mut ast, expr_id, core::ptr::null_mut(), visit_node);
|
||||||
|
|
||||||
let mut symtable = core::mem::MaybeUninit::<util::defs::SymbolTable>::uninit();
|
let mut symtable = core::mem::MaybeUninit::<util::defs::SymbolTable>::uninit();
|
||||||
util::defs::ast_build_symtable(&mut ast, expr_id, &mut symtable);
|
util::defs::ast_build_symtable(&mut ast, expr_id, &mut symtable);
|
||||||
let symtable = symtable.assume_init();
|
let mut symtable = symtable.assume_init();
|
||||||
use util::DisplayedSliceExt;
|
use util::DisplayedSliceExt;
|
||||||
println!(
|
println!(
|
||||||
"Symbol Table: {:#?}",
|
"Symbol Table: {:#?}",
|
||||||
symtable.symtable.as_slice().displayed()
|
symtable.symtable.as_slice().displayed()
|
||||||
);
|
);
|
||||||
|
|
||||||
|
util::defs::ast_resolve_var_refs(&mut ast, &mut symtable, expr_id);
|
||||||
|
|
||||||
|
println!("{:#}", &ast);
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -66,14 +75,14 @@ fn main() {
|
||||||
// print_ast(b"fn main() -> void { let x: u32 = 4; }", |ast| unsafe {
|
// print_ast(b"fn main() -> void { let x: u32 = 4; }", |ast| unsafe {
|
||||||
// parse_func(ast)
|
// parse_func(ast)
|
||||||
// });
|
// });
|
||||||
print_ast(
|
// print_ast(
|
||||||
b"fn main(a: u32) -> void { let x: u32 = a + 4; }",
|
// b"fn main(a: u32) -> void { let x: u32 = a + 4; }",
|
||||||
|ast| unsafe { parse_func(ast) },
|
// |ast| unsafe { parse_func(ast) },
|
||||||
);
|
// );
|
||||||
print_ast(
|
print_ast(
|
||||||
b"fn main(a: u32) -> void {
|
b"fn main(a: u32) -> void {
|
||||||
let x: u32 = a + 4;
|
let y: u32 = a + 4;
|
||||||
let y: *u32 = &x;
|
let y: *u32 = &y;
|
||||||
return *y;
|
return *y;
|
||||||
}",
|
}",
|
||||||
|ast| unsafe { parse_func(ast) },
|
|ast| unsafe { parse_func(ast) },
|
||||||
|
|
@ -110,7 +119,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 {
|
||||||
|
|
@ -184,7 +193,7 @@ impl std::fmt::Display for AstNode {
|
||||||
AST_VALUE_TO_PLACE => {
|
AST_VALUE_TO_PLACE => {
|
||||||
write!(f, "ValueToPlace(value: {})", self.data as usize)
|
write!(f, "ValueToPlace(value: {})", self.data as usize)
|
||||||
}
|
}
|
||||||
_ => write!(f, "UnknownNode"),
|
kind => write!(f, "UnknownNode(kind: {kind})"),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -15,8 +15,8 @@ unsafe extern "C" {
|
||||||
pub unsafe fn ast_parse_let(ast: *mut Ast) -> (u64, bool);
|
pub unsafe fn ast_parse_let(ast: *mut Ast) -> (u64, bool);
|
||||||
pub unsafe fn symkey_cmp(a: *const SymKey, b: *const SymKey) -> i32;
|
pub unsafe fn symkey_cmp(a: *const SymKey, b: *const SymKey) -> i32;
|
||||||
pub unsafe fn ast_build_symtable(ast: *mut Ast, root_index: u64, symtable: *mut core::mem::MaybeUninit<SymbolTable>);
|
pub unsafe fn ast_build_symtable(ast: *mut Ast, root_index: u64, symtable: *mut core::mem::MaybeUninit<SymbolTable>);
|
||||||
pub unsafe fn ast_walk_for_each(ast: *mut Ast, start_index: u64, ctx: *mut (), for_each: unsafe extern "C" fn(ctx: *mut (), *mut Ast, node_index: u64));
|
pub unsafe fn ast_walk_for_each(ast: *mut Ast, start_index: u64, ctx: *mut (), for_each: unsafe extern "C" fn(ctx: *mut (), *mut Ast, node_index: u64, scope: u64));
|
||||||
pub unsafe fn ast_resolve_var_refs(ast: *mut Ast);
|
pub unsafe fn ast_resolve_var_refs(ast: *mut Ast, ctx: *mut SymbolTable, root_index: u64);
|
||||||
}
|
}
|
||||||
|
|
||||||
pub const AST_FUNCTION: u8 = 1;
|
pub const AST_FUNCTION: u8 = 1;
|
||||||
|
|
@ -106,6 +106,7 @@ pub struct AstNode {
|
||||||
pub kind: u8,
|
pub kind: u8,
|
||||||
pub data: *const (),
|
pub data: *const (),
|
||||||
pub extra: usize,
|
pub extra: usize,
|
||||||
|
pub span: u64,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[repr(C)]
|
#[repr(C)]
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue