Separated compiler into its own package
This commit is contained in:
@ -3,9 +3,7 @@ package core
|
||||
import (
|
||||
"git.akyoto.dev/cli/q/src/build/arch/x64"
|
||||
"git.akyoto.dev/cli/q/src/build/asm"
|
||||
"git.akyoto.dev/cli/q/src/build/ast"
|
||||
"git.akyoto.dev/cli/q/src/build/cpu"
|
||||
"git.akyoto.dev/cli/q/src/build/errors"
|
||||
"git.akyoto.dev/cli/q/src/build/fs"
|
||||
"git.akyoto.dev/cli/q/src/build/token"
|
||||
)
|
||||
@ -15,7 +13,7 @@ type Function struct {
|
||||
Name string
|
||||
File *fs.File
|
||||
Body token.List
|
||||
state
|
||||
State
|
||||
}
|
||||
|
||||
// NewFunction creates a new function.
|
||||
@ -24,8 +22,8 @@ func NewFunction(name string, file *fs.File, body token.List) *Function {
|
||||
Name: name,
|
||||
File: file,
|
||||
Body: body,
|
||||
state: state{
|
||||
assembler: asm.Assembler{
|
||||
State: State{
|
||||
Assembler: asm.Assembler{
|
||||
Instructions: make([]asm.Instruction, 0, 32),
|
||||
},
|
||||
cpu: cpu.CPU{
|
||||
@ -43,65 +41,6 @@ func NewFunction(name string, file *fs.File, body token.List) *Function {
|
||||
}
|
||||
}
|
||||
|
||||
// Compile turns a function into machine code.
|
||||
func (f *Function) Compile() {
|
||||
defer close(f.finished)
|
||||
f.AddLabel(f.Name)
|
||||
f.err = f.CompileTokens(f.Body)
|
||||
f.Return()
|
||||
}
|
||||
|
||||
// CompileTokens compiles a token list.
|
||||
func (f *Function) CompileTokens(tokens token.List) error {
|
||||
body, err := ast.Parse(tokens)
|
||||
|
||||
if err != nil {
|
||||
err.(*errors.Error).File = f.File
|
||||
return err
|
||||
}
|
||||
|
||||
return f.CompileAST(body)
|
||||
}
|
||||
|
||||
// CompileAST compiles an abstract syntax tree.
|
||||
func (f *Function) CompileAST(tree ast.AST) error {
|
||||
for _, node := range tree {
|
||||
err := f.CompileASTNode(node)
|
||||
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
// CompileASTNode compiles a node in the AST.
|
||||
func (f *Function) CompileASTNode(node ast.Node) error {
|
||||
switch node := node.(type) {
|
||||
case *ast.Assign:
|
||||
return f.CompileAssign(node)
|
||||
|
||||
case *ast.Call:
|
||||
return f.CompileCall(node.Expression)
|
||||
|
||||
case *ast.Define:
|
||||
return f.CompileDefinition(node)
|
||||
|
||||
case *ast.Return:
|
||||
return f.CompileReturn(node)
|
||||
|
||||
case *ast.If:
|
||||
return f.CompileIf(node)
|
||||
|
||||
case *ast.Loop:
|
||||
return f.CompileLoop(node)
|
||||
|
||||
default:
|
||||
panic("unknown AST type")
|
||||
}
|
||||
}
|
||||
|
||||
// String returns the function name.
|
||||
func (f *Function) String() string {
|
||||
return f.Name
|
||||
|
Reference in New Issue
Block a user