mork work on 04b compiler
This commit is contained in:
parent
9760d898b7
commit
dfd0610698
2 changed files with 303 additions and 32 deletions
304
04b/in03
304
04b/in03
|
@ -29,6 +29,12 @@ A=d3
|
||||||
J=A
|
J=A
|
||||||
?J<0:output_file_error
|
?J<0:output_file_error
|
||||||
|
|
||||||
|
; write ELF header
|
||||||
|
J=d4
|
||||||
|
I=:ELF_header
|
||||||
|
D=x78
|
||||||
|
syscall x1
|
||||||
|
|
||||||
:read_line
|
:read_line
|
||||||
; increment line number
|
; increment line number
|
||||||
D=:line_number
|
D=:line_number
|
||||||
|
@ -54,7 +60,7 @@ R=:line
|
||||||
; check if the character was a tab:
|
; check if the character was a tab:
|
||||||
D=x9
|
D=x9
|
||||||
; if so, don't increment rbp
|
; if so, don't increment rbp
|
||||||
?C=D:read_line
|
?C=D:read_line_loop
|
||||||
; check if the character was a semicolon:
|
; check if the character was a semicolon:
|
||||||
D=';
|
D=';
|
||||||
; if so, it's a comment
|
; if so, it's a comment
|
||||||
|
@ -105,6 +111,33 @@ call :string=
|
||||||
D=A
|
D=A
|
||||||
?D!0:handle_global
|
?D!0:handle_global
|
||||||
|
|
||||||
|
I=:line
|
||||||
|
J=:"local"
|
||||||
|
C=x20
|
||||||
|
call :string=
|
||||||
|
D=A
|
||||||
|
?D!0:handle_local
|
||||||
|
I=:line
|
||||||
|
J=:"argument"
|
||||||
|
C=x20
|
||||||
|
call :string=
|
||||||
|
D=A
|
||||||
|
?D!0:handle_local
|
||||||
|
|
||||||
|
I=:line
|
||||||
|
J=:"return"
|
||||||
|
C=x20
|
||||||
|
call :string=
|
||||||
|
D=A
|
||||||
|
?D!0:handle_return
|
||||||
|
|
||||||
|
C=xa
|
||||||
|
I=:line
|
||||||
|
J=:"function"
|
||||||
|
call :string=
|
||||||
|
D=A
|
||||||
|
?D!0:handle_function
|
||||||
|
|
||||||
|
|
||||||
!:read_line
|
!:read_line
|
||||||
|
|
||||||
|
@ -112,10 +145,58 @@ D=A
|
||||||
J=d0
|
J=d0
|
||||||
syscall x3c
|
syscall x3c
|
||||||
|
|
||||||
|
:handle_local
|
||||||
|
R=I
|
||||||
|
|
||||||
|
; emit sub rsp, 8
|
||||||
|
J=d4
|
||||||
|
I=:sub_rsp_8
|
||||||
|
D=d7
|
||||||
|
syscall x1
|
||||||
|
|
||||||
|
I=R
|
||||||
|
; skip ' '
|
||||||
|
I+=d1
|
||||||
|
call :read_type
|
||||||
|
R=A
|
||||||
|
I+=d1
|
||||||
|
J=:local_variables_end
|
||||||
|
J=8J
|
||||||
|
call :ident_copy
|
||||||
|
; store type
|
||||||
|
1J=R
|
||||||
|
J+=d1
|
||||||
|
; store address
|
||||||
|
D=:stack_end
|
||||||
|
D=8D
|
||||||
|
8J=D
|
||||||
|
J+=d8
|
||||||
|
; store null terminator
|
||||||
|
1J=0
|
||||||
|
; update :stack_end
|
||||||
|
D=:stack_end
|
||||||
|
C=8D
|
||||||
|
C+=d8
|
||||||
|
8D=C
|
||||||
|
; update :local_variables_end
|
||||||
|
I=:local_variables_end
|
||||||
|
8I=J
|
||||||
|
; read the next line
|
||||||
|
!:read_line
|
||||||
|
|
||||||
|
:sub_rsp_8
|
||||||
|
x48
|
||||||
|
x81
|
||||||
|
xec
|
||||||
|
x08
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
|
||||||
:handle_global
|
:handle_global
|
||||||
I=:line
|
; @TODO: check if already exists
|
||||||
; skip "global "
|
; skip ' '
|
||||||
I+=d7
|
I+=d1
|
||||||
call :read_type
|
call :read_type
|
||||||
; put type in R
|
; put type in R
|
||||||
R=A
|
R=A
|
||||||
|
@ -131,6 +212,9 @@ D=A
|
||||||
D=:static_memory_end
|
D=:static_memory_end
|
||||||
D=8D
|
D=8D
|
||||||
8J=D
|
8J=D
|
||||||
|
J+=d8
|
||||||
|
; store null terminator
|
||||||
|
1J=0
|
||||||
; update :static_memory_end
|
; update :static_memory_end
|
||||||
D=:static_memory_end
|
D=:static_memory_end
|
||||||
C=8D
|
C=8D
|
||||||
|
@ -142,9 +226,49 @@ D=A
|
||||||
; go read the next line
|
; go read the next line
|
||||||
!:read_line
|
!:read_line
|
||||||
|
|
||||||
:"global"
|
:handle_function
|
||||||
str global
|
; emit "mov rbp, rsp"
|
||||||
x20
|
J=d4
|
||||||
|
I=:mov_rbp_rsp
|
||||||
|
D=d3
|
||||||
|
syscall x1
|
||||||
|
|
||||||
|
; reset local variable table
|
||||||
|
D=:local_variables
|
||||||
|
1D=0
|
||||||
|
C=:local_variables_end
|
||||||
|
8C=D
|
||||||
|
|
||||||
|
; go read the next line
|
||||||
|
!:read_line
|
||||||
|
|
||||||
|
:mov_rbp_rsp
|
||||||
|
R=S
|
||||||
|
|
||||||
|
:handle_return
|
||||||
|
; @TODO: handle argument
|
||||||
|
|
||||||
|
|
||||||
|
; emit "mov rsp, rbp"
|
||||||
|
J=d4
|
||||||
|
I=:mov_rsp_rbp
|
||||||
|
D=d3
|
||||||
|
syscall x1
|
||||||
|
|
||||||
|
; emit "ret"
|
||||||
|
J=d4
|
||||||
|
I=:ret
|
||||||
|
D=d1
|
||||||
|
syscall x1
|
||||||
|
|
||||||
|
; go read the next lines
|
||||||
|
!:read_line
|
||||||
|
|
||||||
|
:mov_rsp_rbp
|
||||||
|
S=R
|
||||||
|
|
||||||
|
:ret
|
||||||
|
return
|
||||||
|
|
||||||
; copy the newline-terminated identifier from rsi to rdi
|
; copy the newline-terminated identifier from rsi to rdi
|
||||||
:ident_copy
|
:ident_copy
|
||||||
|
@ -237,19 +361,6 @@ D=A
|
||||||
?D!0:return_8
|
?D!0:return_8
|
||||||
!:bad_type
|
!:bad_type
|
||||||
|
|
||||||
:"char"
|
|
||||||
str char
|
|
||||||
x20
|
|
||||||
:"short"
|
|
||||||
str short
|
|
||||||
x20
|
|
||||||
:"int"
|
|
||||||
str int
|
|
||||||
x20
|
|
||||||
:"long"
|
|
||||||
str long
|
|
||||||
x20
|
|
||||||
|
|
||||||
|
|
||||||
:usage_error
|
:usage_error
|
||||||
B=:usage_error_message
|
B=:usage_error_message
|
||||||
|
@ -467,6 +578,36 @@ D=A
|
||||||
D-=d1
|
D-=d1
|
||||||
!:memcpy
|
!:memcpy
|
||||||
|
|
||||||
|
|
||||||
|
:"char"
|
||||||
|
str char
|
||||||
|
x20
|
||||||
|
:"short"
|
||||||
|
str short
|
||||||
|
x20
|
||||||
|
:"int"
|
||||||
|
str int
|
||||||
|
x20
|
||||||
|
:"long"
|
||||||
|
str long
|
||||||
|
x20
|
||||||
|
|
||||||
|
:"global"
|
||||||
|
str global
|
||||||
|
x20
|
||||||
|
:"argument"
|
||||||
|
str argument
|
||||||
|
x20
|
||||||
|
:"local"
|
||||||
|
str local
|
||||||
|
x20
|
||||||
|
:"return"
|
||||||
|
str return
|
||||||
|
x20
|
||||||
|
:"function"
|
||||||
|
str function
|
||||||
|
xa
|
||||||
|
|
||||||
; put a 0 byte before the line (this is important for removing whitespace at the end of the line,
|
; put a 0 byte before the line (this is important for removing whitespace at the end of the line,
|
||||||
; specifically, we don't want this to be a space character)
|
; specifically, we don't want this to be a space character)
|
||||||
x0
|
x0
|
||||||
|
@ -478,10 +619,129 @@ align
|
||||||
reserve d8
|
reserve d8
|
||||||
:static_memory_end
|
:static_memory_end
|
||||||
reserve d8
|
reserve d8
|
||||||
|
:local_variables_end
|
||||||
|
reserve d8
|
||||||
|
:stack_end
|
||||||
|
reserve d8
|
||||||
:line_number
|
:line_number
|
||||||
reserve d8
|
reserve d8
|
||||||
:global_variables
|
:global_variables
|
||||||
reserve d50000
|
reserve d50000
|
||||||
|
:local_variables
|
||||||
; we shouldn't end the file with a reserve; we don't handle that properly
|
reserve d20000
|
||||||
|
:label_table
|
||||||
|
reserve d200000
|
||||||
|
|
||||||
|
:ELF_header
|
||||||
|
x7f
|
||||||
|
x45
|
||||||
|
x4c
|
||||||
|
x46
|
||||||
|
x02
|
||||||
|
x01
|
||||||
|
x01
|
||||||
|
|
||||||
|
reserve d9
|
||||||
|
|
||||||
|
x02
|
||||||
x00
|
x00
|
||||||
|
|
||||||
|
x3e
|
||||||
|
x00
|
||||||
|
|
||||||
|
x01
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
|
||||||
|
x78
|
||||||
|
x00
|
||||||
|
x40
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
|
||||||
|
x40
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
|
||||||
|
reserve d12
|
||||||
|
|
||||||
|
x40
|
||||||
|
x00
|
||||||
|
x38
|
||||||
|
x00
|
||||||
|
x01
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
|
||||||
|
x01
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
|
||||||
|
x07
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
|
||||||
|
x78
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
|
||||||
|
x78
|
||||||
|
x00
|
||||||
|
x40
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
|
||||||
|
reserve d8
|
||||||
|
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x20
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x20
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
|
||||||
|
x00
|
||||||
|
x10
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
x00
|
||||||
|
|
||||||
|
; NOTE: we shouldn't end the file with a reserve; we don't handle that properly
|
||||||
|
|
31
04b/in04b
31
04b/in04b
|
@ -52,38 +52,49 @@ global char x
|
||||||
global short y ;123
|
global short y ;123
|
||||||
global long z
|
global long z
|
||||||
|
|
||||||
function strlen(*char s)
|
:strlen
|
||||||
|
function
|
||||||
|
argument *char s
|
||||||
local long len
|
local long len
|
||||||
local char c
|
local char c
|
||||||
len = 0
|
len = 0
|
||||||
:strlen.loop
|
:strlen_loop
|
||||||
c = s[len]
|
c = s[len]
|
||||||
if c == 0 goto strlen.loop_end
|
if c == 0 goto strlen_loop_end
|
||||||
len += 1
|
len += 1
|
||||||
goto strlen.loop
|
goto strlen_loop
|
||||||
:strlen.loop_end
|
:strlen_loop_end
|
||||||
return len
|
return len
|
||||||
|
|
||||||
function putc(char c)
|
:putc
|
||||||
local char *p
|
function
|
||||||
|
argument char c
|
||||||
|
local *char p
|
||||||
p = &c
|
p = &c
|
||||||
syscall(1, 1, p, 1, 0, 0, 0, 0)
|
syscall(1, 1, p, 1, 0, 0, 0, 0)
|
||||||
return
|
return
|
||||||
|
|
||||||
function puts(*char s)
|
:puts
|
||||||
|
function
|
||||||
|
argument *char s
|
||||||
local long len
|
local long len
|
||||||
len = strlen(s)
|
len = strlen(s)
|
||||||
syscall(1, 1, s, len, 0, 0, 0, 0)
|
syscall(1, 1, s, len, 0, 0, 0, 0)
|
||||||
return
|
return
|
||||||
|
|
||||||
function main()
|
:main
|
||||||
|
function
|
||||||
local *char hello
|
local *char hello
|
||||||
hello = `Hello, world!
|
hello = `Hello, world!
|
||||||
`
|
`
|
||||||
puts(hello)
|
puts(hello)
|
||||||
syscall(0x3c, 0, 0, 0, 0, 0, 0, 0)
|
syscall(0x3c, 0, 0, 0, 0, 0, 0, 0)
|
||||||
|
|
||||||
function f(*long x, *long y)
|
|
||||||
|
:f
|
||||||
|
function
|
||||||
|
argument *long x
|
||||||
|
argument *long y
|
||||||
local long v
|
local long v
|
||||||
local *long p
|
local *long p
|
||||||
v = *x
|
v = *x
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue