Add operation works!
This commit is contained in:
@@ -1,47 +1,54 @@
|
||||
|
||||
function Register_Index
|
||||
bc_emit_expr(Bc *b, Ast *ast){
|
||||
if(!ast) return -1;
|
||||
if(!is_flag_set(ast->flags, AST_EXPR))
|
||||
compiler_error(ast->pos, "Internal compiler error: Trying to emit expression but it doesn't have appropriate flag");
|
||||
switch(ast->kind){
|
||||
|
||||
// @todo pass type and figure out what to do with untyped ??
|
||||
CASE(VALUE, Atom){
|
||||
Register_Index dst = allocate_register(b);
|
||||
emit_load_constant(b, node->pos, dst, node->value);
|
||||
|
||||
return dst;
|
||||
BREAK();
|
||||
}
|
||||
|
||||
CASE(BINARY, Binary){
|
||||
Register_Index left = bc_emit_expr(b, node->left);
|
||||
Register_Index right = bc_emit_expr(b, node->right);
|
||||
emit_arithmetic(b, node->pos, BC_ADD_S64, left, right, left);
|
||||
release_register(b, right);
|
||||
return left;
|
||||
BREAK();
|
||||
}
|
||||
|
||||
default:{}
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
||||
struct Incomplete_Instruction{
|
||||
Instruction *instruction;
|
||||
Ast_Decl *decl;
|
||||
};
|
||||
|
||||
function void
|
||||
bc_emit_expr(Bc *b, Ast *ast, Register_Index result_index){
|
||||
if(!ast) return;
|
||||
if(!is_flag_set(ast->flags, AST_EXPR))
|
||||
compiler_error(ast->pos, "Internal compiler error: Trying to emit expression but it doesn't have appropriate flag");
|
||||
|
||||
switch(ast->kind){
|
||||
CASE(VALUE, Atom){
|
||||
emit_load_constant(b, node->pos, result_index, node->value);
|
||||
BREAK();
|
||||
}
|
||||
|
||||
CASE(IDENT, Atom){
|
||||
emit_load_constant(b, node->pos, result_index, node->resolved_decl->value);
|
||||
BREAK();
|
||||
}
|
||||
|
||||
CASE(BINARY, Binary){
|
||||
Register_Index left_index = allocate_register(b);
|
||||
Register_Index right_index = allocate_register(b);
|
||||
bc_emit_expr(b, node->left, left_index);
|
||||
bc_emit_expr(b, node->right, right_index);
|
||||
|
||||
emit_arithmetic(b, node->pos, BC_ADD_S64, left_index, right_index, result_index);
|
||||
release_register(b, left_index);
|
||||
release_register(b, right_index);
|
||||
BREAK();
|
||||
}
|
||||
|
||||
invalid_default_case;
|
||||
}
|
||||
}
|
||||
|
||||
function void
|
||||
emit_stmt(Bc *b, Ast *ast){
|
||||
switch(ast->kind){
|
||||
CASE(VAR, Decl){
|
||||
node->register_index = allocate_register(b);
|
||||
if(is_flag_set(node->flags, AST_VAR_IS_CONST)){
|
||||
// emit_load_
|
||||
}
|
||||
bc_emit_expr(b, node->expr, node->register_index);
|
||||
BREAK();
|
||||
}
|
||||
|
||||
CASE(RETURN, Return){
|
||||
|
||||
emit_return(b, node->pos);
|
||||
BREAK();
|
||||
}
|
||||
default:{}
|
||||
@@ -60,7 +67,7 @@ compile_to_bc(){
|
||||
// auto incomplete = array_make<Incomplete_Instruction>(scratch, 512);
|
||||
|
||||
Register_Index main_call_register = allocate_register(b);
|
||||
Instruction *load_main_address = emit_load_constant(b, 0, main_call_register, {});
|
||||
Instruction *load_main_address = emit_load_constant(b, 0, 0, {});
|
||||
emit_call(b, 0, 0);
|
||||
|
||||
For_Named(pctx->ordered_decls, ast){
|
||||
@@ -69,6 +76,7 @@ compile_to_bc(){
|
||||
CASE(LAMBDA, Decl){
|
||||
Ast_Lambda *lambda = node->lambda;
|
||||
if(!lambda->scope) break;
|
||||
if(node->pos->file.s == "language.kl"_s) break;
|
||||
node->bytecode_data_position = b->instruction_pointer;
|
||||
|
||||
For(node->lambda->args){
|
||||
@@ -79,6 +87,10 @@ compile_to_bc(){
|
||||
emit_stmt(b, it);
|
||||
}
|
||||
|
||||
For(node->lambda->args){
|
||||
release_register(b, it->register_index);
|
||||
}
|
||||
|
||||
|
||||
if(node->name == intern_main){
|
||||
found_main = true;
|
||||
@@ -90,6 +102,7 @@ compile_to_bc(){
|
||||
}
|
||||
|
||||
CASE(VAR, Decl){
|
||||
if(node->pos->file.s == "language.kl"_s) break;
|
||||
node->bytecode_data_position = exp_alloc(&b->memory, node->type->size, AF_ZeroMemory);
|
||||
if(is_flag_set(node->flags, AST_VAR_IS_CONST)){
|
||||
switch(node->type->kind){
|
||||
@@ -100,15 +113,6 @@ compile_to_bc(){
|
||||
}
|
||||
}
|
||||
else if(node->expr) compiler_error(node->pos, "Todo: Global variable with non constant expression");
|
||||
|
||||
// if(node->expr){
|
||||
// Register_Index expression_index = bc_emit_expr(b, node->expr);
|
||||
// Register_Index address_index = allocate_register(b);
|
||||
// emit_load_constant_address(b, node->pos, address_index, node->bytecode_data_position);
|
||||
// emit_memory(b, node->pos, BC_STORE_TO_MEMORY64, address_index, expression_index);
|
||||
// release_register(b, expression_index);
|
||||
// release_register(b, address_index);
|
||||
// }
|
||||
BREAK();
|
||||
}
|
||||
default: {}
|
||||
@@ -119,6 +123,7 @@ compile_to_bc(){
|
||||
compiler_error(0, "Having a [main] function is required, it's an entry point of the application");
|
||||
}
|
||||
|
||||
release_register(b, main_call_register);
|
||||
emit_end(b);
|
||||
run_bytecode_interp(b);
|
||||
destroy_bytecode_interp(b);
|
||||
|
||||
Reference in New Issue
Block a user