From: Brendan Hansen Date: Fri, 5 Feb 2021 22:12:38 +0000 (-0600) Subject: converted symbol introducing to be an entity, instead of in the parser X-Git-Url: https://git.brendanfh.com/?a=commitdiff_plain;h=153f01b945e2a77720081cb3d284f77f928a1aea;p=onyx.git converted symbol introducing to be an entity, instead of in the parser --- diff --git a/bin/onyx b/bin/onyx index a2d9e6ea..b25ec394 100755 Binary files a/bin/onyx and b/bin/onyx differ diff --git a/include/onyxastnodes.h b/include/onyxastnodes.h index e27854ac..bda0f218 100644 --- a/include/onyxastnodes.h +++ b/include/onyxastnodes.h @@ -859,6 +859,7 @@ typedef enum EntityState { Entity_State_Error, Entity_State_Parse_Builtin, + Entity_State_Introduce_Symbols, Entity_State_Parse, Entity_State_Resolve_Symbols, Entity_State_Check_Types, @@ -877,6 +878,7 @@ typedef enum EntityType { Entity_Type_Load_Path, Entity_Type_Load_File, + Entity_Type_Binding, Entity_Type_Use_Package, Entity_Type_String_Literal, Entity_Type_File_Contents, @@ -910,6 +912,7 @@ typedef struct Entity { union { AstInclude *include; AstUsePackage *use_package; + AstBinding *binding; AstFunction *function; AstOverloadedFunction *overloaded_function; AstGlobal *global; diff --git a/src/onyx.c b/src/onyx.c index f796c3ff..f3f4f0e9 100644 --- a/src/onyx.c +++ b/src/onyx.c @@ -271,24 +271,39 @@ static b32 process_entity(Entity* ent) { if (context.options->verbose_output == 3) { if (ent->expr && ent->expr->token) printf("%s | %s | %s:%i:%i\n", - entity_state_strings[ent->state], - entity_type_strings[ent->type], - ent->expr->token->pos.filename, - ent->expr->token->pos.line, - ent->expr->token->pos.column); + entity_state_strings[ent->state], + entity_type_strings[ent->type], + ent->expr->token->pos.filename, + ent->expr->token->pos.line, + ent->expr->token->pos.column); + + else if (ent->expr) + printf("%s | %s\n", + entity_state_strings[ent->state], + entity_type_strings[ent->type]); } + + // CLEANUP: There should be a nicer way to track if the builtins have + // already been initialized. + static b32 builtins_initialized = 0; switch (ent->state) { case Entity_State_Parse_Builtin: process_load_entity(ent); ent->state = Entity_State_Finalized; - if (onyx_has_errors()) return 0; - - initialize_builtins(context.ast_alloc); + case Entity_State_Introduce_Symbols: + // Currently, introducing symbols is handled in the symbol resolution + // function. Maybe there should be a different place where that happens? + symres_entity(ent); break; - + case Entity_State_Parse: + if (!builtins_initialized) { + builtins_initialized = 1; + initialize_builtins(context.ast_alloc); + } + process_load_entity(ent); ent->state = Entity_State_Finalized; break; @@ -308,6 +323,7 @@ static b32 process_entity(Entity* ent) { #if defined(_BH_LINUX) static void output_dummy_progress_bar() { EntityHeap* eh = &context.entities; + if (bh_arr_length(eh->entities) == 0) return; printf("\e[2;1H"); for (i32 i = 0; i < Entity_State_Count - 1; i++) { diff --git a/src/onyxastnodes.c b/src/onyxastnodes.c index 9d39772f..5969e12d 100644 --- a/src/onyxastnodes.c +++ b/src/onyxastnodes.c @@ -105,10 +105,11 @@ const char *binaryop_string[Binary_Op_Count] = { const char* entity_state_strings[Entity_State_Count] = { "Error", "Parse Builtin", + "Introduce Symbols", "Parse", - "Resolve_Symbols", - "Check_Types", - "Code_Gen", + "Resolve Symbols", + "Check Types", + "Code Gen", "Finalized", }; @@ -116,6 +117,7 @@ const char* entity_type_strings[Entity_Type_Count] = { "Unknown", "Add to Load Path", "Load File", + "Binding (Declaration)", "Use Package", "String Literal", "File Contents", diff --git a/src/onyxentities.c b/src/onyxentities.c index 0f90faaa..ceb2b6cf 100644 --- a/src/onyxentities.c +++ b/src/onyxentities.c @@ -105,6 +105,14 @@ void add_entities_for_node(AstNode* node, Scope* scope, Package* package) { break; } + case Ast_Kind_Binding: { + ent.state = Entity_State_Introduce_Symbols; + ent.type = Entity_Type_Binding; + ent.binding = (AstBinding *) node; + entity_heap_insert(entities, ent); + break; + } + case Ast_Kind_Function: { if ((node->flags & Ast_Flag_Foreign) != 0) { ent.type = Entity_Type_Foreign_Function_Header; diff --git a/src/onyxparser.c b/src/onyxparser.c index fe7a86a0..14c2c387 100644 --- a/src/onyxparser.c +++ b/src/onyxparser.c @@ -1,10 +1,7 @@ -// The job of the parser for Onyx is to do two things: -// 1. Submit nodes to the entity heap for further processing. -// Nodes such as procedure defintions, string literals, etc. -// -// 2. Insert static symbols into scopes. -// Things defined at top level or inside of static scopes such -// as bindings in procedures or in struct scopes. +// The sole job of the parser for Onyx is to submit nodes to the +// entity heap for further processing. These nodes include things +// such as procedure definitions, string literals, struct definitions +// and declarations to be introduced into scopes. // Things that need to be cleaned up in the parser: // - control block local variables should be more extensible and reuse more code @@ -17,9 +14,10 @@ #include "onyxutils.h" // NOTE: The one weird define you need to know before read the code below -#define make_node(nclass, kind) onyx_ast_node_new(parser->allocator, sizeof(nclass), kind) -#define peek_token(ahead) (parser->curr + ahead) -#define ENTITY_SUBMIT(node) (add_entities_for_node((AstNode *) (node), bh_arr_last(parser->scope_stack), parser->package)) +#define make_node(nclass, kind) onyx_ast_node_new(parser->allocator, sizeof(nclass), kind) +#define peek_token(ahead) (parser->curr + ahead) +#define ENTITY_SUBMIT(node) (add_entities_for_node((AstNode *) (node), bh_arr_last(parser->scope_stack), parser->package)) +#define ENTITY_SUBMIT_IN_SCOPE(node, scope) (add_entities_for_node((AstNode *) (node), scope, parser->package)) static AstNode error_node = { Ast_Kind_Error, 0, NULL, NULL }; @@ -1077,8 +1075,7 @@ static i32 parse_possible_symbol_declaration(OnyxParser* parser, AstNode** ret) AstBinding* binding = parse_top_level_binding(parser, symbol); if (parser->hit_unexpected_token) return 2; - Scope* insertion_scope = bh_arr_last(parser->scope_stack); - symbol_introduce(insertion_scope, symbol, binding->node); + ENTITY_SUBMIT(binding); return 2; } @@ -1705,7 +1702,7 @@ static AstStructType* parse_struct(OnyxParser* parser) { consume_token(parser); AstBinding* binding = parse_top_level_binding(parser, binding_name); - symbol_introduce(s_node->scope, binding->token, binding->node); + ENTITY_SUBMIT(binding); consume_token_if_next(parser, ';'); @@ -2397,10 +2394,8 @@ void onyx_parse(OnyxParser *parser) { target_scope = parser->package->private_scope; if (((AstBinding *) curr_stmt)->node->flags & Ast_Flag_Private_File) target_scope = parser->file_scope; - - symbol_introduce(target_scope, - ((AstBinding *) curr_stmt)->token, - ((AstBinding *) curr_stmt)->node); + + ENTITY_SUBMIT_IN_SCOPE(curr_stmt, target_scope); break; } diff --git a/src/onyxsymres.c b/src/onyxsymres.c index dd3053ac..4d54afb4 100644 --- a/src/onyxsymres.c +++ b/src/onyxsymres.c @@ -957,6 +957,12 @@ void symres_entity(Entity* ent) { EntityState next_state = Entity_State_Check_Types; switch (ent->type) { + case Entity_Type_Binding: { + symbol_introduce(curr_scope, ent->binding->token, ent->binding->node); + next_state = Entity_State_Finalized; + break; + } + case Entity_Type_Foreign_Function_Header: case Entity_Type_Function_Header: symres_function_header(ent->function); break; case Entity_Type_Function: symres_function(ent->function); break;