From: Brendan Hansen Date: Sat, 28 Aug 2021 20:10:18 +0000 (-0500) Subject: added macros at the expression level X-Git-Url: https://git.brendanfh.com/?a=commitdiff_plain;h=9330bfa08958d2fe78f4e517602ecf2cbea20506;p=onyx.git added macros at the expression level --- diff --git a/bin/onyx b/bin/onyx index 7758c4dc..a124e137 100755 Binary files a/bin/onyx and b/bin/onyx differ diff --git a/docs/bugs b/docs/bugs index 55a74452..c7739086 100644 --- a/docs/bugs +++ b/docs/bugs @@ -1,6 +1,6 @@ List of known bugs: -[ ] macros are not allowed at the expression level. This is not necessarily a bug, but does +[X] macros are not allowed at the expression level. This is not necessarily a bug, but does bring many complications to the table about how resolve this. Current solution is to turn expression macros (macros that specify a return value) into a `do` expression. diff --git a/src/onyxchecker.c b/src/onyxchecker.c index 9a7b4f8d..a2ff9458 100644 --- a/src/onyxchecker.c +++ b/src/onyxchecker.c @@ -462,10 +462,6 @@ static CheckStatus check_resolve_callee(AstCall* call, AstTyped** effective_call } if (callee->kind == Ast_Kind_Macro) { - if (current_checking_level == EXPRESSION_LEVEL) { - ERROR(call->token->pos, "Macros calls are not allowed at the expression level yet."); - } - calling_a_macro = 1; call->callee = callee; diff --git a/src/onyxsymres.c b/src/onyxsymres.c index 475e3f95..0bc9b32a 100644 --- a/src/onyxsymres.c +++ b/src/onyxsymres.c @@ -359,10 +359,14 @@ static SymresStatus symres_method_call(AstBinaryOp** mcall) { SYMRES(expression, &(*mcall)->left); if ((*mcall)->left == NULL) return Symres_Error; - AstFieldAccess* implicit_field_access = make_field_access(context.ast_alloc, (*mcall)->left, NULL); - implicit_field_access->token = call_node->callee->token; - call_node->callee = (AstTyped *) implicit_field_access; + if (((*mcall)->flags & Ast_Flag_Has_Been_Symres) == 0) { + AstFieldAccess* implicit_field_access = make_field_access(context.ast_alloc, (*mcall)->left, NULL); + implicit_field_access->token = call_node->callee->token; + call_node->callee = (AstTyped *) implicit_field_access; + } + SYMRES(expression, (AstTyped **) &call_node); + (*mcall)->flags |= Ast_Flag_Has_Been_Symres; return Symres_Success; } diff --git a/src/onyxutils.c b/src/onyxutils.c index 6e64c768..3e44f60c 100644 --- a/src/onyxutils.c +++ b/src/onyxutils.c @@ -1212,12 +1212,26 @@ void expand_macro(AstCall** pcall, AstFunction* template) { assert(template->kind == Ast_Kind_Function); assert(template->type != NULL); + assert(template->type->kind == Type_Kind_Function); AstBlock* expansion = (AstBlock *) ast_clone(context.ast_alloc, template->body); expansion->rules = Block_Rule_Macro; expansion->scope = NULL; expansion->next = call->next; + AstNode* subst = (AstNode *) expansion; + + if (template->type->Function.return_type != &basic_types[Basic_Kind_Void]) { + AstDoBlock* doblock = (AstDoBlock *) onyx_ast_node_new(context.ast_alloc, sizeof(AstDoBlock), Ast_Kind_Do_Block); + doblock->token = expansion->token; + doblock->block = expansion; + doblock->type = template->type->Function.return_type; + doblock->next = expansion->next; + expansion->next = NULL; + + subst = (AstNode *) doblock; + } + Scope* argument_scope = scope_create(context.ast_alloc, NULL, call->token->pos); if (expansion->binding_scope != NULL) scope_include(argument_scope, expansion->binding_scope, call->token->pos); @@ -1245,7 +1259,7 @@ void expand_macro(AstCall** pcall, AstFunction* template) { bh_table_each_end; } - *(AstBlock **) pcall = expansion; + *(AstNode **) pcall = subst; return; } diff --git a/src/onyxwasm.c b/src/onyxwasm.c index c15a66d0..ff62a185 100644 --- a/src/onyxwasm.c +++ b/src/onyxwasm.c @@ -2296,6 +2296,8 @@ EMIT_FUNC(if_expression, AstIfExpression* if_expr) { WIL(WI_LOCAL_GET, result_local); } + local_free(mod->local_alloc, (AstTyped *) if_expr); + *pcode = code; } @@ -2320,6 +2322,7 @@ EMIT_FUNC(do_block, AstDoBlock* doblock) { } bh_arr_pop(mod->return_location_stack); + local_free(mod->local_alloc, (AstTyped *) doblock); *pcode = code; }