added: parameter to backend
This commit is contained in:
parent
6afa552347
commit
f243bb6bfe
|
@ -27,7 +27,7 @@ Target create_native_target() {
|
|||
target.features.allocation = LLVM;
|
||||
assert(target.features.str != NULL);
|
||||
|
||||
target.opt = LLVMCodeGenLevelDefault;
|
||||
target.opt = LLVMCodeGenLevelNone;
|
||||
target.reloc = LLVMRelocDefault;
|
||||
target.model = LLVMCodeModelDefault;
|
||||
|
||||
|
|
|
@ -186,6 +186,8 @@ BackendError impl_relational_operation(LLVMBackendCompileUnit *unit,
|
|||
PANIC("invalid type for relational operator");
|
||||
}
|
||||
|
||||
// *llvm_result = convert_integral_to_boolean(builder, *llvm_result);
|
||||
|
||||
return SUCCESS;
|
||||
}
|
||||
|
||||
|
@ -337,7 +339,7 @@ BackendError impl_typecast(LLVMBackendCompileUnit *unit, LLVMLocalScope *scope,
|
|||
const LLVMOpcode opcode =
|
||||
LLVMGetCastOpcode(operand, src_signed, target_type, dst_signed);
|
||||
*llvm_result =
|
||||
LLVMBuildCast(builder, opcode, operand, target_type, "transmute");
|
||||
LLVMBuildCast(builder, opcode, operand, target_type, "typecast");
|
||||
|
||||
return err;
|
||||
}
|
||||
|
@ -357,6 +359,23 @@ BackendError impl_variable_load(LLVMBackendCompileUnit *unit, LLVMLocalScope *sc
|
|||
return SUCCESS;
|
||||
}
|
||||
|
||||
BackendError impl_address_of(LLVMBackendCompileUnit *unit, LLVMLocalScope *scope,
|
||||
LLVMBuilderRef builder, AddressOf* addressOf,
|
||||
LLVMValueRef *llvm_result) {
|
||||
|
||||
LLVMValueRef llvm_variable = NULL;
|
||||
BackendError err = impl_expr(unit, scope, builder, addressOf->variable, &llvm_variable);
|
||||
|
||||
if (err.kind != Success) {
|
||||
return err;
|
||||
}
|
||||
|
||||
LLVMValueRef zero = LLVMConstInt(LLVMInt32Type(), 0, 0);
|
||||
*llvm_result = LLVMBuildGEP2(builder, LLVMTypeOf(llvm_variable), llvm_variable, &zero, 1, "address of");
|
||||
|
||||
return SUCCESS;
|
||||
}
|
||||
|
||||
BackendError impl_expr(LLVMBackendCompileUnit *unit, LLVMLocalScope *scope,
|
||||
LLVMBuilderRef builder, Expression *expr,
|
||||
LLVMValueRef *llvm_result) {
|
||||
|
@ -384,6 +403,10 @@ BackendError impl_expr(LLVMBackendCompileUnit *unit, LLVMLocalScope *scope,
|
|||
err = impl_variable_load(unit, scope, builder, expr->impl.variable,
|
||||
llvm_result);
|
||||
break;
|
||||
case ExpressionKindAddressOf:
|
||||
err = impl_address_of(unit, scope, builder, &expr->impl.addressOf,
|
||||
llvm_result);
|
||||
break;
|
||||
default:
|
||||
err = new_backend_impl_error(Implementation, NULL, "unknown expression");
|
||||
break;
|
||||
|
|
|
@ -10,6 +10,7 @@
|
|||
#include <llvm/llvm-ir/variables.h>
|
||||
#include <set/types.h>
|
||||
#include <sys/log.h>
|
||||
#include <mem/cache.h>
|
||||
|
||||
LLVMLocalScope* new_local_scope(LLVMLocalScope* parent) {
|
||||
LLVMLocalScope* scope = malloc(sizeof(LLVMLocalScope));
|
||||
|
@ -90,18 +91,19 @@ BackendError impl_func_decl(LLVMBackendCompileUnit* unit,
|
|||
DEBUG("implementing function declaration: %s()", name);
|
||||
BackendError err = SUCCESS;
|
||||
|
||||
Parameter* params = (Parameter*)fundef->parameter;
|
||||
GArray* llvm_params = g_array_new(FALSE, FALSE, sizeof(LLVMTypeRef));
|
||||
|
||||
for (size_t i = 0; i < fundef->parameter->len; i++) {
|
||||
Parameter* param = ¶ms[i];
|
||||
Parameter* param = &g_array_index(fundef->parameter, Parameter, i);
|
||||
|
||||
LLVMTypeRef llvm_type = NULL;
|
||||
err = impl_param_type(unit, scope, param, &llvm_type);
|
||||
|
||||
if (err.kind != Success) {
|
||||
break;
|
||||
return err;
|
||||
}
|
||||
|
||||
g_array_append_val(llvm_params, llvm_type);
|
||||
}
|
||||
|
||||
DEBUG("implemented %ld parameter", llvm_params->len);
|
||||
|
@ -144,11 +146,15 @@ BackendError impl_func_def(LLVMBackendCompileUnit* unit,
|
|||
LLVMPositionBuilderAtEnd(builder, entry);
|
||||
|
||||
// create value references for parameter
|
||||
const size_t params = fundef->parameter->len;
|
||||
for (size_t i = 0; i < params; i++) {
|
||||
const Parameter* param = ((Parameter*)fundef->parameter) + i;
|
||||
g_hash_table_insert(func_scope->params, (gpointer)param->name,
|
||||
LLVMGetParam(llvm_func, i));
|
||||
for (guint i = 0; i < fundef->parameter->len; i++) {
|
||||
Parameter* param = &g_array_index(fundef->parameter, Parameter, i);
|
||||
LLVMValueRef llvm_param = LLVMGetParam(llvm_func, i);
|
||||
|
||||
if (llvm_param == NULL) {
|
||||
return new_backend_impl_error(Implementation, NULL, "invalid parameter");
|
||||
}
|
||||
|
||||
g_hash_table_insert(func_scope->params, (gpointer)param->name, llvm_param);
|
||||
}
|
||||
|
||||
LLVMBasicBlockRef llvm_start_body_block = NULL;
|
||||
|
|
|
@ -219,7 +219,7 @@ BackendError impl_branch(LLVMBackendCompileUnit *unit,
|
|||
LLVMBasicBlockRef end_body_block = NULL;
|
||||
LLVMValueRef cond_value = NULL;
|
||||
|
||||
err = impl_cond_block(unit, builder, scope, (Expression *) &branch->ifBranch.conditon, &branch->ifBranch.block,
|
||||
err = impl_cond_block(unit, builder, scope, branch->ifBranch.conditon, &branch->ifBranch.block,
|
||||
&cond_block,
|
||||
&start_body_block, &end_body_block, &cond_value);
|
||||
|
||||
|
@ -230,6 +230,7 @@ BackendError impl_branch(LLVMBackendCompileUnit *unit,
|
|||
}
|
||||
|
||||
// generate else if(s)
|
||||
if (branch->elseIfBranches != NULL) {
|
||||
for (size_t i = 0; i < branch->elseIfBranches->len; i++) {
|
||||
LLVMBasicBlockRef cond_block = NULL;
|
||||
LLVMBasicBlockRef start_body_block = NULL;
|
||||
|
@ -246,30 +247,35 @@ BackendError impl_branch(LLVMBackendCompileUnit *unit,
|
|||
g_array_append_val(end_body_blocks, end_body_block);
|
||||
g_array_append_val(cond_values, cond_value);
|
||||
}
|
||||
}
|
||||
|
||||
LLVMBasicBlockRef after_block = NULL;
|
||||
|
||||
// else block
|
||||
if (branch->elseBranch.nodePtr != NULL) {
|
||||
if (branch->elseBranch.block.statemnts != NULL) {
|
||||
LLVMBasicBlockRef start_else_block = NULL;
|
||||
LLVMBasicBlockRef end_else_block = NULL;
|
||||
err = impl_basic_block(unit, builder, scope, &branch->elseBranch.block, &start_else_block, &end_else_block);
|
||||
err = impl_basic_block(unit, builder, scope, &branch->elseBranch.block, &start_else_block, &after_block);
|
||||
g_array_append_val(cond_blocks, start_else_block);
|
||||
}
|
||||
|
||||
LLVMBasicBlockRef after_block = LLVMAppendBasicBlockInContext(unit->context, scope->func_scope->llvm_func,
|
||||
if (after_block == NULL) {
|
||||
after_block = LLVMAppendBasicBlockInContext(unit->context, scope->func_scope->llvm_func,
|
||||
"stmt.branch.after");
|
||||
}
|
||||
|
||||
LLVMPositionBuilderAtEnd(builder, after_block);
|
||||
// in case no else block is present
|
||||
// make the after block the else
|
||||
if (branch->elseBranch.nodePtr == NULL) {
|
||||
if (branch->elseBranch.block.statemnts == NULL) {
|
||||
g_array_append_val(cond_blocks, after_block);
|
||||
}
|
||||
|
||||
for (size_t i = 0; i < cond_blocks->len - 1; i++) {
|
||||
LLVMBasicBlockRef next_block = ((LLVMBasicBlockRef *) cond_blocks->data)[i + 1];
|
||||
LLVMBasicBlockRef cond_block = ((LLVMBasicBlockRef *) cond_blocks->data)[i];
|
||||
LLVMBasicBlockRef start_body_block = ((LLVMBasicBlockRef *) start_body_blocks->data)[i];
|
||||
LLVMBasicBlockRef end_body_block = ((LLVMBasicBlockRef *) end_body_blocks->data)[i];
|
||||
LLVMValueRef cond_value = ((LLVMValueRef *) cond_values->data)[i];
|
||||
LLVMBasicBlockRef next_block = g_array_index(cond_blocks, LLVMBasicBlockRef, i + 1);
|
||||
LLVMBasicBlockRef cond_block = g_array_index(cond_blocks, LLVMBasicBlockRef, i);
|
||||
LLVMBasicBlockRef start_body_block = g_array_index(start_body_blocks, LLVMBasicBlockRef, i);
|
||||
LLVMBasicBlockRef end_body_block = g_array_index(end_body_blocks, LLVMBasicBlockRef, i);
|
||||
LLVMValueRef cond_value = g_array_index(cond_values, LLVMValueRef, i);
|
||||
|
||||
LLVMPositionBuilderAtEnd(builder, cond_block);
|
||||
LLVMBuildCondBr(builder, cond_value, start_body_block, next_block);
|
||||
|
@ -279,7 +285,7 @@ BackendError impl_branch(LLVMBackendCompileUnit *unit,
|
|||
}
|
||||
|
||||
*branch_start_block = g_array_index(cond_blocks, LLVMBasicBlockRef, 0);
|
||||
*branch_end_block = g_array_index(cond_blocks, LLVMBasicBlockRef, cond_blocks->len - 1);
|
||||
*branch_end_block = after_block;
|
||||
|
||||
g_array_free(cond_blocks, TRUE);
|
||||
g_array_free(start_body_blocks, TRUE);
|
||||
|
|
|
@ -179,9 +179,7 @@ BackendError impl_box_type(LLVMBackendCompileUnit* unit, LLVMGlobalScope* scope,
|
|||
BackendError get_type_impl(LLVMBackendCompileUnit* unit, LLVMGlobalScope* scope,
|
||||
Type* gemstone_type, LLVMTypeRef* llvm_type) {
|
||||
DEBUG("retrieving type implementation...");
|
||||
BackendError err =
|
||||
new_backend_impl_error(Implementation, gemstone_type->nodePtr,
|
||||
"No type implementation covers type");
|
||||
BackendError err;
|
||||
|
||||
switch (gemstone_type->kind) {
|
||||
case TypeKindPrimitive:
|
||||
|
|
|
@ -231,6 +231,21 @@ int set_impl_composite_type(AST_NODE_PTR ast_type, CompositeType *composite) {
|
|||
return check_scale_factor(ast_type, composite->scale);
|
||||
}
|
||||
|
||||
int set_get_type_impl(AST_NODE_PTR currentNode, Type **type);
|
||||
|
||||
int set_impl_reference_type(AST_NODE_PTR currentNode, Type **type) {
|
||||
DEBUG("implementing reference type");
|
||||
ReferenceType reference;
|
||||
|
||||
int status = set_get_type_impl(AST_get_node(currentNode, 0), &reference);
|
||||
|
||||
*type = mem_alloc(MemoryNamespaceSet, sizeof(Type));
|
||||
(*type)->kind = TypeKindReference;
|
||||
(*type)->impl.reference = reference;
|
||||
|
||||
return status;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Converts the given AST node to a gemstone type implementation.
|
||||
* @param currentNode AST node of type kind type
|
||||
|
@ -239,21 +254,22 @@ int set_impl_composite_type(AST_NODE_PTR ast_type, CompositeType *composite) {
|
|||
*/
|
||||
int set_get_type_impl(AST_NODE_PTR currentNode, Type **type) {
|
||||
assert(currentNode != NULL);
|
||||
assert(currentNode->kind == AST_Type);
|
||||
assert(currentNode->kind == AST_Type || currentNode->kind == AST_Reference);
|
||||
assert(currentNode->child_count > 0);
|
||||
DEBUG("start Type");
|
||||
|
||||
int status;
|
||||
|
||||
if (currentNode->kind == AST_Reference) {
|
||||
return set_impl_reference_type(currentNode, type);
|
||||
}
|
||||
|
||||
const char *typekind = currentNode->children[currentNode->child_count - 1]->value;
|
||||
|
||||
//find type in composites
|
||||
if (g_hash_table_contains(declaredComposites, typekind) == TRUE) {
|
||||
*type = g_hash_table_lookup(declaredComposites, typekind);
|
||||
return SEMANTIC_OK;
|
||||
|
||||
|
||||
|
||||
}
|
||||
|
||||
if (g_hash_table_contains(declaredBoxes, typekind) == TRUE) {
|
||||
|
@ -416,6 +432,7 @@ int createDef(AST_NODE_PTR currentNode, GArray **variables) {
|
|||
DEBUG("fill Qualifier");
|
||||
decl.qualifier = Qualifier_from_string(declaration->children[i]->value);
|
||||
break;
|
||||
case AST_Reference:
|
||||
case AST_Type:
|
||||
DEBUG("fill Type");
|
||||
status = set_get_type_impl(declaration->children[i], &decl.type);
|
||||
|
@ -469,7 +486,6 @@ int getVariableFromScope(const char *name, Variable **variable) {
|
|||
}
|
||||
for(size_t i = 0; i < Scope->len; i++) {
|
||||
|
||||
|
||||
GHashTable* variable_table = g_array_index(Scope,GHashTable* ,i );
|
||||
|
||||
if(g_hash_table_contains(variable_table, name)) {
|
||||
|
@ -632,7 +648,7 @@ int createTypeCastFromExpression(Expression * expression, Type * resultType, Exp
|
|||
return SEMANTIC_OK;
|
||||
}
|
||||
|
||||
int createArithOperation(Expression* ParentExpression, AST_NODE_PTR currentNode, [[maybe_unused]] size_t expectedChildCount) {
|
||||
int createArithOperation(Expression* ParentExpression, AST_NODE_PTR currentNode, size_t expectedChildCount) {
|
||||
DEBUG("create arithmetic operation");
|
||||
ParentExpression->impl.operation.kind = Arithmetic;
|
||||
ParentExpression->impl.operation.nodePtr = currentNode;
|
||||
|
@ -769,6 +785,7 @@ int createBoolOperation(Expression *ParentExpression, AST_NODE_PTR currentNode)
|
|||
// fill kind and Nodeptr
|
||||
ParentExpression->impl.operation.kind = Boolean;
|
||||
ParentExpression->impl.operation.nodePtr = currentNode;
|
||||
ParentExpression->impl.operation.operands = g_array_new(FALSE,FALSE,sizeof(Expression*));
|
||||
|
||||
// fill Operands
|
||||
for (size_t i = 0; i < currentNode->child_count; i++){
|
||||
|
@ -794,8 +811,8 @@ int createBoolOperation(Expression *ParentExpression, AST_NODE_PTR currentNode)
|
|||
break;
|
||||
}
|
||||
|
||||
Expression* lhs = ((Expression**) ParentExpression->impl.operation.operands->data)[0];
|
||||
Expression* rhs = ((Expression**) ParentExpression->impl.operation.operands->data)[1];
|
||||
Expression* lhs = g_array_index(ParentExpression->impl.operation.operands, Expression*, 0);
|
||||
Expression* rhs = g_array_index(ParentExpression->impl.operation.operands, Expression*, 1);
|
||||
|
||||
Type* LeftOperandType = lhs->result;
|
||||
Type* RightOperandType = rhs->result;
|
||||
|
@ -852,6 +869,7 @@ int createBoolNotOperation(Expression *ParentExpression, AST_NODE_PTR currentNod
|
|||
//fill kind and Nodeptr
|
||||
ParentExpression->impl.operation.kind = Boolean;
|
||||
ParentExpression->impl.operation.nodePtr = currentNode;
|
||||
ParentExpression->impl.operation.operands = g_array_new(FALSE,FALSE,sizeof(Expression*));
|
||||
|
||||
//fill Operand
|
||||
Expression* expression = createExpression(currentNode->children[0]);
|
||||
|
@ -862,7 +880,7 @@ int createBoolNotOperation(Expression *ParentExpression, AST_NODE_PTR currentNod
|
|||
|
||||
ParentExpression->impl.operation.impl.boolean = BooleanNot;
|
||||
|
||||
Type* Operand = ((Expression**)ParentExpression->impl.operation.operands)[0]->result;
|
||||
Type* Operand = g_array_index(ParentExpression->impl.operation.operands, Expression*, 0)->result;
|
||||
|
||||
Type* result = mem_alloc(MemoryNamespaceSet,sizeof(Type));
|
||||
result->nodePtr = currentNode;
|
||||
|
@ -916,6 +934,7 @@ int createBitOperation(Expression* ParentExpression, AST_NODE_PTR currentNode) {
|
|||
// fill kind and Nodeptr
|
||||
ParentExpression->impl.operation.kind = Boolean;
|
||||
ParentExpression->impl.operation.nodePtr = currentNode;
|
||||
ParentExpression->impl.operation.operands = g_array_new(FALSE,FALSE,sizeof(Expression*));
|
||||
|
||||
// fill Operands
|
||||
for (size_t i = 0; i < currentNode->child_count; i++) {
|
||||
|
@ -946,8 +965,8 @@ int createBitOperation(Expression* ParentExpression, AST_NODE_PTR currentNode) {
|
|||
Type *result = mem_alloc(MemoryNamespaceSet,sizeof(Type));
|
||||
result->nodePtr = currentNode;
|
||||
|
||||
Expression* lhs = ((Expression**) ParentExpression->impl.operation.operands->data)[0];
|
||||
Expression* rhs = ((Expression**) ParentExpression->impl.operation.operands->data)[1];
|
||||
Expression* lhs = g_array_index(ParentExpression->impl.operation.operands, Expression*, 0);
|
||||
Expression* rhs = g_array_index(ParentExpression->impl.operation.operands, Expression*, 1);
|
||||
|
||||
Type* LeftOperandType = lhs->result;
|
||||
Type* RightOperandType = rhs->result;
|
||||
|
@ -1052,6 +1071,7 @@ int createBitNotOperation(Expression* ParentExpression, AST_NODE_PTR currentNode
|
|||
//fill kind and Nodeptr
|
||||
ParentExpression->impl.operation.kind = Bitwise;
|
||||
ParentExpression->impl.operation.nodePtr = currentNode;
|
||||
ParentExpression->impl.operation.operands = g_array_new(FALSE, FALSE,sizeof(Expression*));
|
||||
|
||||
//fill Operand
|
||||
Expression* expression = createExpression(currentNode->children[0]);
|
||||
|
@ -1062,7 +1082,7 @@ int createBitNotOperation(Expression* ParentExpression, AST_NODE_PTR currentNode
|
|||
|
||||
ParentExpression->impl.operation.impl.bitwise = BitwiseNot;
|
||||
|
||||
Type* Operand = ((Expression**) ParentExpression->impl.operation.operands)[0]->result;
|
||||
Type* Operand = g_array_index(ParentExpression->impl.operation.operands, Expression*, 0)->result;
|
||||
|
||||
Type* result = mem_alloc(MemoryNamespaceSet,sizeof(Type));
|
||||
result->nodePtr = currentNode;
|
||||
|
@ -1617,6 +1637,10 @@ int createElseIf(Branch* Parentbranch, AST_NODE_PTR currentNode){
|
|||
ElseIf elseIfBranch;
|
||||
elseIfBranch.nodePtr = currentNode;
|
||||
|
||||
if (Parentbranch->elseIfBranches == NULL) {
|
||||
Parentbranch->elseIfBranches = mem_new_g_array(MemoryNamespaceSet, sizeof(ElseIf));
|
||||
}
|
||||
|
||||
Expression* expression = createExpression(currentNode->children[0]);
|
||||
if (NULL == expression) {
|
||||
return SEMANTIC_ERROR;
|
||||
|
@ -1631,27 +1655,28 @@ int createElseIf(Branch* Parentbranch, AST_NODE_PTR currentNode){
|
|||
return SEMANTIC_OK;
|
||||
}
|
||||
|
||||
|
||||
|
||||
int createBranch(Statement* ParentStatement,AST_NODE_PTR currentNode){
|
||||
Branch Branch;
|
||||
Branch.nodePtr = currentNode;
|
||||
Branch branch;
|
||||
branch.nodePtr = currentNode;
|
||||
branch.elseBranch.block.statemnts = NULL;
|
||||
branch.elseIfBranches = NULL;
|
||||
|
||||
for (size_t i = 0; i < currentNode->child_count; i++ ){
|
||||
switch (currentNode->children[i]->kind){
|
||||
case AST_If:
|
||||
if(createIf(&Branch, currentNode->children[i])){
|
||||
if(createIf(&branch, currentNode->children[i])){
|
||||
return SEMANTIC_ERROR;
|
||||
}
|
||||
break;
|
||||
|
||||
case AST_IfElse:
|
||||
if(createElseIf(&Branch, currentNode)){
|
||||
if(createElseIf(&branch, currentNode->children[i])){
|
||||
return SEMANTIC_ERROR;
|
||||
}
|
||||
break;
|
||||
|
||||
case AST_Else:
|
||||
if(createElse(&Branch, currentNode->children[i])){
|
||||
if(createElse(&branch, currentNode->children[i])){
|
||||
return SEMANTIC_ERROR;
|
||||
}
|
||||
break;
|
||||
|
@ -1661,7 +1686,7 @@ int createBranch(Statement* ParentStatement,AST_NODE_PTR currentNode){
|
|||
break;
|
||||
}
|
||||
}
|
||||
ParentStatement->impl.branch = Branch;
|
||||
ParentStatement->impl.branch = branch;
|
||||
return SEMANTIC_OK;
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in New Issue