diff --git a/4coder_default_hooks.cpp b/4coder_default_hooks.cpp index 05a57e86..fe42ed58 100644 --- a/4coder_default_hooks.cpp +++ b/4coder_default_hooks.cpp @@ -55,7 +55,10 @@ RENDER_CALLER_SIG(default_render_caller){ View_Summary view = get_view(app, view_id, AccessAll); Buffer_Summary buffer = get_buffer(app, view.buffer_id, AccessAll); - Managed_Scope render_scope = create_user_managed_scope(app); + static Managed_Scope render_scope = 0; + if (render_scope == 0){ + render_scope = create_user_managed_scope(app); + } // NOTE(allen): Line highlight setup if (highlight_line_at_cursor){ @@ -129,8 +132,10 @@ RENDER_CALLER_SIG(default_render_caller){ Temp_Memory marker_temp = begin_temp_memory(scratch); Marker *markers = push_array(scratch, Marker, marker_count); memset(markers, 0, sizeof(*markers)*marker_count); - Range *range_ptr = ranges + i; - for (int32_t j = 0; j < marker_count; j += 2, range_ptr += 4){ + // NOTE(allen): Iterate the ranges in reverse order, + // to ensure top level scopes always get the first color. + Range *range_ptr = ranges + count - 1 - i; + for (int32_t j = 0; j < marker_count; j += 2, range_ptr -= 4){ markers[j + 0].pos = range_ptr->first; markers[j + 1].pos = range_ptr->one_past_last - 1; } @@ -146,7 +151,7 @@ RENDER_CALLER_SIG(default_render_caller){ do_core_render(app); - destroy_user_managed_scope(app, render_scope); + clear_managed_scope_and_all_dependent_scopes(app, render_scope); } HOOK_SIG(default_exit){ diff --git a/4coder_generated/app_functions.h b/4coder_generated/app_functions.h index 857ec49f..eccbd578 100644 --- a/4coder_generated/app_functions.h +++ b/4coder_generated/app_functions.h @@ -53,6 +53,9 @@ struct Application_Links; #define DESTROY_USER_MANAGED_SCOPE_SIG(n) bool32 n(Application_Links *app, Managed_Scope scope) #define GET_GLOBAL_MANAGED_SCOPE_SIG(n) Managed_Scope n(Application_Links *app) #define GET_MANAGED_SCOPE_WITH_MULTIPLE_DEPENDENCIES_SIG(n) Managed_Scope n(Application_Links *app, Managed_Scope *intersected_scopes, int32_t count) +#define MANAGED_SCOPE_CLEAR_CONTENTS_SIG(n) bool32 n(Application_Links *app, Managed_Scope scope) +#define CLEAR_MANAGED_SCOPE_SIG(n) bool32 n(Application_Links *app, Managed_Scope scope) +#define CLEAR_MANAGED_SCOPE_AND_ALL_DEPENDENT_SCOPES_SIG(n) bool32 n(Application_Links *app, Managed_Scope scope) #define MANAGED_VARIABLE_CREATE_SIG(n) Managed_Variable_ID n(Application_Links *app, char *null_terminated_name, uint64_t default_value) #define MANAGED_VARIABLE_GET_ID_SIG(n) Managed_Variable_ID n(Application_Links *app, char *null_terminated_name) #define MANAGED_VARIABLE_CREATE_OR_GET_ID_SIG(n) Managed_Variable_ID n(Application_Links *app, char *null_terminated_name, uint64_t default_value) @@ -161,6 +164,9 @@ typedef CREATE_USER_MANAGED_SCOPE_SIG(Create_User_Managed_Scope_Function); typedef DESTROY_USER_MANAGED_SCOPE_SIG(Destroy_User_Managed_Scope_Function); typedef GET_GLOBAL_MANAGED_SCOPE_SIG(Get_Global_Managed_Scope_Function); typedef GET_MANAGED_SCOPE_WITH_MULTIPLE_DEPENDENCIES_SIG(Get_Managed_Scope_With_Multiple_Dependencies_Function); +typedef MANAGED_SCOPE_CLEAR_CONTENTS_SIG(Managed_Scope_Clear_Contents_Function); +typedef CLEAR_MANAGED_SCOPE_SIG(Clear_Managed_Scope_Function); +typedef CLEAR_MANAGED_SCOPE_AND_ALL_DEPENDENT_SCOPES_SIG(Clear_Managed_Scope_And_All_Dependent_Scopes_Function); typedef MANAGED_VARIABLE_CREATE_SIG(Managed_Variable_Create_Function); typedef MANAGED_VARIABLE_GET_ID_SIG(Managed_Variable_Get_ID_Function); typedef MANAGED_VARIABLE_CREATE_OR_GET_ID_SIG(Managed_Variable_Create_Or_Get_ID_Function); @@ -271,6 +277,9 @@ Create_User_Managed_Scope_Function *create_user_managed_scope; Destroy_User_Managed_Scope_Function *destroy_user_managed_scope; Get_Global_Managed_Scope_Function *get_global_managed_scope; Get_Managed_Scope_With_Multiple_Dependencies_Function *get_managed_scope_with_multiple_dependencies; +Managed_Scope_Clear_Contents_Function *managed_scope_clear_contents; +Clear_Managed_Scope_Function *clear_managed_scope; +Clear_Managed_Scope_And_All_Dependent_Scopes_Function *clear_managed_scope_and_all_dependent_scopes; Managed_Variable_Create_Function *managed_variable_create; Managed_Variable_Get_ID_Function *managed_variable_get_id; Managed_Variable_Create_Or_Get_ID_Function *managed_variable_create_or_get_id; @@ -380,6 +389,9 @@ Create_User_Managed_Scope_Function *create_user_managed_scope_; Destroy_User_Managed_Scope_Function *destroy_user_managed_scope_; Get_Global_Managed_Scope_Function *get_global_managed_scope_; Get_Managed_Scope_With_Multiple_Dependencies_Function *get_managed_scope_with_multiple_dependencies_; +Managed_Scope_Clear_Contents_Function *managed_scope_clear_contents_; +Clear_Managed_Scope_Function *clear_managed_scope_; +Clear_Managed_Scope_And_All_Dependent_Scopes_Function *clear_managed_scope_and_all_dependent_scopes_; Managed_Variable_Create_Function *managed_variable_create_; Managed_Variable_Get_ID_Function *managed_variable_get_id_; Managed_Variable_Create_Or_Get_ID_Function *managed_variable_create_or_get_id_; @@ -497,6 +509,9 @@ app_links->create_user_managed_scope_ = Create_User_Managed_Scope;\ app_links->destroy_user_managed_scope_ = Destroy_User_Managed_Scope;\ app_links->get_global_managed_scope_ = Get_Global_Managed_Scope;\ app_links->get_managed_scope_with_multiple_dependencies_ = Get_Managed_Scope_With_Multiple_Dependencies;\ +app_links->managed_scope_clear_contents_ = Managed_Scope_Clear_Contents;\ +app_links->clear_managed_scope_ = Clear_Managed_Scope;\ +app_links->clear_managed_scope_and_all_dependent_scopes_ = Clear_Managed_Scope_And_All_Dependent_Scopes;\ app_links->managed_variable_create_ = Managed_Variable_Create;\ app_links->managed_variable_get_id_ = Managed_Variable_Get_ID;\ app_links->managed_variable_create_or_get_id_ = Managed_Variable_Create_Or_Get_ID;\ @@ -606,6 +621,9 @@ static inline Managed_Scope create_user_managed_scope(Application_Links *app){re static inline bool32 destroy_user_managed_scope(Application_Links *app, Managed_Scope scope){return(app->destroy_user_managed_scope(app, scope));} static inline Managed_Scope get_global_managed_scope(Application_Links *app){return(app->get_global_managed_scope(app));} static inline Managed_Scope get_managed_scope_with_multiple_dependencies(Application_Links *app, Managed_Scope *intersected_scopes, int32_t count){return(app->get_managed_scope_with_multiple_dependencies(app, intersected_scopes, count));} +static inline bool32 managed_scope_clear_contents(Application_Links *app, Managed_Scope scope){return(app->managed_scope_clear_contents(app, scope));} +static inline bool32 clear_managed_scope(Application_Links *app, Managed_Scope scope){return(app->clear_managed_scope(app, scope));} +static inline bool32 clear_managed_scope_and_all_dependent_scopes(Application_Links *app, Managed_Scope scope){return(app->clear_managed_scope_and_all_dependent_scopes(app, scope));} static inline Managed_Variable_ID managed_variable_create(Application_Links *app, char *null_terminated_name, uint64_t default_value){return(app->managed_variable_create(app, null_terminated_name, default_value));} static inline Managed_Variable_ID managed_variable_get_id(Application_Links *app, char *null_terminated_name){return(app->managed_variable_get_id(app, null_terminated_name));} static inline Managed_Variable_ID managed_variable_create_or_get_id(Application_Links *app, char *null_terminated_name, uint64_t default_value){return(app->managed_variable_create_or_get_id(app, null_terminated_name, default_value));} @@ -715,6 +733,9 @@ static inline Managed_Scope create_user_managed_scope(Application_Links *app){re static inline bool32 destroy_user_managed_scope(Application_Links *app, Managed_Scope scope){return(app->destroy_user_managed_scope_(app, scope));} static inline Managed_Scope get_global_managed_scope(Application_Links *app){return(app->get_global_managed_scope_(app));} static inline Managed_Scope get_managed_scope_with_multiple_dependencies(Application_Links *app, Managed_Scope *intersected_scopes, int32_t count){return(app->get_managed_scope_with_multiple_dependencies_(app, intersected_scopes, count));} +static inline bool32 managed_scope_clear_contents(Application_Links *app, Managed_Scope scope){return(app->managed_scope_clear_contents_(app, scope));} +static inline bool32 clear_managed_scope(Application_Links *app, Managed_Scope scope){return(app->clear_managed_scope_(app, scope));} +static inline bool32 clear_managed_scope_and_all_dependent_scopes(Application_Links *app, Managed_Scope scope){return(app->clear_managed_scope_and_all_dependent_scopes_(app, scope));} static inline Managed_Variable_ID managed_variable_create(Application_Links *app, char *null_terminated_name, uint64_t default_value){return(app->managed_variable_create_(app, null_terminated_name, default_value));} static inline Managed_Variable_ID managed_variable_get_id(Application_Links *app, char *null_terminated_name){return(app->managed_variable_get_id_(app, null_terminated_name));} static inline Managed_Variable_ID managed_variable_create_or_get_id(Application_Links *app, char *null_terminated_name, uint64_t default_value){return(app->managed_variable_create_or_get_id_(app, null_terminated_name, default_value));} diff --git a/4ed_api_implementation.cpp b/4ed_api_implementation.cpp index 9d477d28..36522961 100644 --- a/4ed_api_implementation.cpp +++ b/4ed_api_implementation.cpp @@ -2273,7 +2273,7 @@ Destroy_User_Managed_Scope(Application_Links *app, Managed_Scope scope){ Command_Data *cmd = (Command_Data*)app->cmd_context; Models *models = cmd->models; Dynamic_Workspace *workspace = get_dynamic_workspace(models, scope); - if (workspace != 0){ + if (workspace != 0 && workspace->user_type == DynamicWorkspace_Unassociated){ Lifetime_Object *lifetime_object = (Lifetime_Object*)workspace->user_back_ptr; lifetime_free_object(&models->mem.heap, &models->lifetime_allocator, lifetime_object); return(true); @@ -2289,6 +2289,28 @@ Get_Global_Managed_Scope(Application_Links *app) return((Managed_Scope)models->dynamic_workspace.scope_id); } +internal Lifetime_Object* +get_lifetime_object_from_workspace(Dynamic_Workspace *workspace){ + Lifetime_Object *result = 0; + switch (workspace->user_type){ + case DynamicWorkspace_Unassociated: + { + result = (Lifetime_Object*)workspace->user_back_ptr; + }break; + case DynamicWorkspace_Buffer: + { + Editing_File *file = (Editing_File*)workspace->user_back_ptr; + result = file->lifetime_object; + }break; + case DynamicWorkspace_View: + { + View *vptr = (View*)workspace->user_back_ptr; + result = vptr->transient.lifetime_object; + }break; + } + return(result); +} + API_EXPORT Managed_Scope Get_Managed_Scope_With_Multiple_Dependencies(Application_Links *app, Managed_Scope *intersected_scopes, int32_t count) { @@ -2315,23 +2337,13 @@ Get_Managed_Scope_With_Multiple_Dependencies(Application_Links *app, Managed_Sco }break; case DynamicWorkspace_Unassociated: - { - Lifetime_Object **new_object_ptr = push_array(scratch, Lifetime_Object*, 1); - *new_object_ptr = (Lifetime_Object*)workspace->user_back_ptr; - }break; - case DynamicWorkspace_Buffer: - { - Editing_File *file = (Editing_File*)workspace->user_back_ptr; - Lifetime_Object **new_object_ptr = push_array(scratch, Lifetime_Object*, 1); - *new_object_ptr = file->lifetime_object; - }break; - case DynamicWorkspace_View: { - View *vptr = (View*)workspace->user_back_ptr; + Lifetime_Object *object = get_lifetime_object_from_workspace(workspace); + Assert(object != 0); Lifetime_Object **new_object_ptr = push_array(scratch, Lifetime_Object*, 1); - *new_object_ptr = vptr->transient.lifetime_object; + *new_object_ptr = object; }break; case DynamicWorkspace_Intersected: @@ -2368,6 +2380,44 @@ Get_Managed_Scope_With_Multiple_Dependencies(Application_Links *app, Managed_Sco return(result); } +API_EXPORT bool32 +Managed_Scope_Clear_Contents(Application_Links *app, Managed_Scope scope){ + Command_Data *cmd = (Command_Data*)app->cmd_context; + Models *models = cmd->models; + Dynamic_Workspace *workspace = get_dynamic_workspace(models, scope); + if (workspace != 0){ + dynamic_workspace_clear_contents(&models->mem.heap, workspace); + return(true); + } + return(false); +} + +API_EXPORT bool32 +Clear_Managed_Scope(Application_Links *app, Managed_Scope scope){ + Command_Data *cmd = (Command_Data*)app->cmd_context; + Models *models = cmd->models; + Dynamic_Workspace *workspace = get_dynamic_workspace(models, scope); + if (workspace != 0){ + dynamic_workspace_clear_contents(&models->mem.heap, workspace); + return(true); + } + return(false); +} + +API_EXPORT bool32 +Clear_Managed_Scope_And_All_Dependent_Scopes(Application_Links *app, Managed_Scope scope){ + Command_Data *cmd = (Command_Data*)app->cmd_context; + Models *models = cmd->models; + Dynamic_Workspace *workspace = get_dynamic_workspace(models, scope); + if (workspace != 0 && workspace->user_type != DynamicWorkspace_Global && workspace->user_type != DynamicWorkspace_Intersected){ + Lifetime_Object *object = get_lifetime_object_from_workspace(workspace); + Assert(object != 0); + lifetime_object_reset(&models->mem.heap, &models->lifetime_allocator, object); + return(true); + } + return(false); +} + API_EXPORT Managed_Variable_ID Managed_Variable_Create(Application_Links *app, char *null_terminated_name, uint64_t default_value) { diff --git a/4ed_dynamic_variables.cpp b/4ed_dynamic_variables.cpp index 6f2d22fa..43f1e490 100644 --- a/4ed_dynamic_variables.cpp +++ b/4ed_dynamic_variables.cpp @@ -182,6 +182,14 @@ dynamic_workspace_free(Heap *heap, Lifetime_Allocator *lifetime_allocator, Dynam dynamic_memory_bank_free_all(heap, &workspace->mem_bank); } +internal void +dynamic_workspace_clear_contents(Heap *heap, Dynamic_Workspace *workspace){ + dynamic_variables_block_free(heap, &workspace->var_block); + dynamic_memory_bank_free_all(heap, &workspace->mem_bank); + dynamic_variables_block_init(heap, &workspace->var_block); + dynamic_memory_bank_init(heap, &workspace->mem_bank); +} + internal u32 dynamic_workspace_store_pointer(Heap *heap, Dynamic_Workspace *workspace, void *ptr){ if (workspace->object_id_counter == 0){ @@ -342,8 +350,7 @@ lifetime__key_table_copy(Heap *heap, Lifetime_Key_Table table, u32 new_max){ } internal void -lifetime__free_key(Heap *heap, Lifetime_Allocator *lifetime_allocator, - Lifetime_Key *key, Lifetime_Object *skip_object){ +lifetime__free_key(Heap *heap, Lifetime_Allocator *lifetime_allocator, Lifetime_Key *key, Lifetime_Object *skip_object){ // Deinit dynamic_workspace_free(heap, lifetime_allocator, &key->dynamic_workspace); @@ -464,9 +471,7 @@ lifetime_alloc_object(Heap *heap, Lifetime_Allocator *lifetime_allocator, i32 us } internal void -lifetime_free_object(Heap *heap, Lifetime_Allocator *lifetime_allocator, Lifetime_Object *lifetime_object){ - dynamic_workspace_free(heap, lifetime_allocator, &lifetime_object->workspace); - +lifetime__object_free_all_keys(Heap *heap, Lifetime_Allocator *lifetime_allocator, Lifetime_Object *lifetime_object){ i32 key_i = 0; for (Lifetime_Key_Ref_Node *node = lifetime_object->key_node_first; node != 0; @@ -484,10 +489,24 @@ lifetime_free_object(Heap *heap, Lifetime_Allocator *lifetime_allocator, Lifetim i32 node_count = (lifetime_object->key_count + (lifetime_key_reference_per_node - 1))/lifetime_key_reference_per_node; lifetime_allocator->free_key_references.count += node_count; } - +} + +internal void +lifetime_free_object(Heap *heap, Lifetime_Allocator *lifetime_allocator, Lifetime_Object *lifetime_object){ + lifetime__object_free_all_keys(heap, lifetime_allocator, lifetime_object); + dynamic_workspace_free(heap, lifetime_allocator, &lifetime_object->workspace); zdll_push_back(lifetime_allocator->free_objects.first, lifetime_allocator->free_objects.last, lifetime_object); } +internal void +lifetime_object_reset(Heap *heap, Lifetime_Allocator *lifetime_allocator, Lifetime_Object *lifetime_object){ + lifetime__object_free_all_keys(heap, lifetime_allocator, lifetime_object); + lifetime_object->key_node_first = 0; + lifetime_object->key_node_last = 0; + lifetime_object->key_count = 0; + dynamic_workspace_clear_contents(heap, &lifetime_object->workspace); +} + internal i32 lifetime_sort_object_set__part(Lifetime_Object **ptr_array, i32 first, i32 one_past_last){ i32 pivot_index = one_past_last - 1;