195 lines
6.6 KiB
C++
195 lines
6.6 KiB
C++
/*
|
|
* Mr. 4th Dimention - Allen Webster
|
|
*
|
|
* 19.05.2017
|
|
*
|
|
* Parse contexts allocation and locking.
|
|
*
|
|
*/
|
|
|
|
// TOP
|
|
|
|
struct Stored_Parse_Context{
|
|
umem memsize;
|
|
u64 *kw_keywords;
|
|
u64 *pp_keywords;
|
|
u32 kw_max;
|
|
u32 pp_max;
|
|
};
|
|
|
|
struct Stored_Parse_Context_Slot{
|
|
union{
|
|
Stored_Parse_Context_Slot *next;
|
|
Stored_Parse_Context *context;
|
|
};
|
|
b32 freed;
|
|
};
|
|
|
|
struct Parse_Context_Memory{
|
|
Stored_Parse_Context_Slot *parse_context_array;
|
|
u32 parse_context_counter;
|
|
u32 parse_context_max;
|
|
|
|
Stored_Parse_Context_Slot free_sentinel;
|
|
};
|
|
|
|
internal void
|
|
parse_context_init_memory(Parse_Context_Memory *parse_mem, void *mem, umem memsize){
|
|
sll_init_sentinel(&parse_mem->free_sentinel);
|
|
|
|
parse_mem->parse_context_array = (Stored_Parse_Context_Slot*)mem;
|
|
parse_mem->parse_context_counter = 0;
|
|
parse_mem->parse_context_max = (u32)(memsize / sizeof(*parse_mem->parse_context_array));
|
|
}
|
|
|
|
internal Parse_Context_ID
|
|
parse_context_valid_id(Parse_Context_Memory *parse_mem, Parse_Context_ID id){
|
|
Parse_Context_ID valid_id = 0;
|
|
if (id > parse_mem->parse_context_max && id < parse_mem->parse_context_max*2){
|
|
valid_id = id;
|
|
}
|
|
return(valid_id);
|
|
}
|
|
|
|
internal Parse_Context_ID
|
|
parse_context_add(Parse_Context_Memory *parse_mem, General_Memory *general, Parser_String_And_Type *kw_sats, u32 kw_count, Parser_String_And_Type *pp_sats, u32 pp_count){
|
|
Stored_Parse_Context_Slot *slot = 0;
|
|
if (parse_mem->free_sentinel.next != &parse_mem->free_sentinel){
|
|
slot = parse_mem->free_sentinel.next;
|
|
sll_remove(&parse_mem->free_sentinel, slot);
|
|
}
|
|
else if (parse_mem->parse_context_counter < parse_mem->parse_context_max){
|
|
slot = &parse_mem->parse_context_array[parse_mem->parse_context_counter++];
|
|
}
|
|
|
|
u32 result = 0;
|
|
if (slot != 0){
|
|
u32 stride = sizeof(*kw_sats);
|
|
umem kw_memsize = cpp_get_table_memory_size_string_lengths(&kw_sats->length, stride, kw_count);
|
|
umem pp_memsize = cpp_get_table_memory_size_string_lengths(&pp_sats->length, stride, pp_count);
|
|
|
|
umem memsize = kw_memsize + pp_memsize + sizeof(Stored_Parse_Context);
|
|
void *mem = general_memory_allocate(general, (i32)memsize);
|
|
|
|
Stored_Parse_Context *parse_context = (Stored_Parse_Context*)mem;
|
|
u8 *kw_mem = (u8*)(parse_context+1);
|
|
u8 *pp_mem = kw_mem + kw_memsize;
|
|
|
|
Cpp_Keyword_Table kw_table = cpp_make_table(&kw_sats->str, stride, &kw_sats->length, stride, &kw_sats->type, stride, kw_count, kw_mem, kw_memsize);
|
|
|
|
Cpp_Keyword_Table pp_table = cpp_make_table(&pp_sats->str, stride, &pp_sats->length, stride, &pp_sats->type, stride, pp_count, pp_mem, pp_memsize);
|
|
|
|
parse_context->memsize = memsize;
|
|
parse_context->kw_keywords = kw_table.keywords;
|
|
parse_context->pp_keywords = pp_table.keywords;
|
|
parse_context->kw_max = kw_table.max;
|
|
parse_context->pp_max = pp_table.max;
|
|
slot->context = parse_context;
|
|
slot->freed = false;
|
|
|
|
result = (u32)(slot - parse_mem->parse_context_array) + parse_mem->parse_context_max;
|
|
}
|
|
|
|
return(result);
|
|
}
|
|
|
|
internal u32
|
|
parse_context_add_default(Parse_Context_Memory *parse_mem, General_Memory *general){
|
|
Stored_Parse_Context_Slot *slot = 0;
|
|
if (parse_mem->free_sentinel.next != &parse_mem->free_sentinel){
|
|
slot = parse_mem->free_sentinel.next;
|
|
sll_remove(&parse_mem->free_sentinel, slot);
|
|
}
|
|
else if (parse_mem->parse_context_counter < parse_mem->parse_context_max){
|
|
slot = &parse_mem->parse_context_array[parse_mem->parse_context_counter++];
|
|
}
|
|
|
|
u32 result = 0;
|
|
if (slot != 0){
|
|
umem kw_memsize = cpp_get_table_memory_size_default(CPP_TABLE_KEYWORDS);
|
|
umem pp_memsize = cpp_get_table_memory_size_default(CPP_TABLE_PREPROCESSOR_DIRECTIVES);
|
|
|
|
umem memsize = kw_memsize + pp_memsize + sizeof(Stored_Parse_Context);
|
|
void *mem = general_memory_allocate(general, (i32)(memsize));
|
|
|
|
Stored_Parse_Context *parse_context = (Stored_Parse_Context*)mem;
|
|
u8 *kw_mem = (u8*)(parse_context+1);
|
|
u8 *pp_mem = kw_mem + kw_memsize;
|
|
|
|
Cpp_Keyword_Table kw_table = cpp_make_table_default(CPP_TABLE_KEYWORDS, kw_mem, kw_memsize);
|
|
Cpp_Keyword_Table pp_table = cpp_make_table_default(CPP_TABLE_PREPROCESSOR_DIRECTIVES, pp_mem, pp_memsize);
|
|
|
|
parse_context->memsize = memsize;
|
|
parse_context->kw_keywords = kw_table.keywords;
|
|
parse_context->pp_keywords = pp_table.keywords;
|
|
parse_context->kw_max = kw_table.max;
|
|
parse_context->pp_max = pp_table.max;
|
|
slot->context = parse_context;
|
|
slot->freed = false;
|
|
|
|
result = (u32)(slot - parse_mem->parse_context_array) + parse_mem->parse_context_max;
|
|
}
|
|
|
|
return(result);
|
|
}
|
|
|
|
struct Parse_Context{
|
|
b32 valid;
|
|
Cpp_Keyword_Table kw_table;
|
|
Cpp_Keyword_Table pp_table;
|
|
umem memory_size;
|
|
};
|
|
|
|
internal Parse_Context
|
|
parse_context_get(Parse_Context_Memory *parse_mem, Parse_Context_ID id, void *mem, umem memsize){
|
|
Parse_Context result = {0};
|
|
|
|
Stored_Parse_Context_Slot *slot = 0;
|
|
if (id == 0){
|
|
// do nothing
|
|
}
|
|
else{
|
|
id -= parse_mem->parse_context_max;
|
|
}
|
|
|
|
if (id < parse_mem->parse_context_counter){
|
|
slot = &parse_mem->parse_context_array[id];
|
|
if (slot->freed){
|
|
slot = 0;
|
|
}
|
|
}
|
|
|
|
if (slot != 0){
|
|
Stored_Parse_Context *context = slot->context;
|
|
if (context->memsize < memsize){
|
|
u8 *base_ptr = (u8*)context;
|
|
u8 *kw_keywords = (u8*)mem + (((u8*)context->kw_keywords) - base_ptr);
|
|
u8 *pp_keywords = (u8*)mem + (((u8*)context->pp_keywords) - base_ptr);
|
|
result.valid = true;
|
|
result.kw_table.keywords = (u64*)kw_keywords;
|
|
result.pp_table.keywords = (u64*)pp_keywords;
|
|
result.kw_table.max = context->kw_max;
|
|
result.pp_table.max = context->pp_max;
|
|
result.memory_size = context->memsize;
|
|
memcpy(mem, context, context->memsize);
|
|
}
|
|
}
|
|
|
|
return(result);
|
|
}
|
|
|
|
internal void
|
|
parse_context_rebase(Parse_Context *parse_mem, void *old_base, void *new_base){
|
|
u8 *old_base_ptr = (u8*)old_base;
|
|
u8 *new_base_ptr = (u8*)new_base;
|
|
|
|
u8 *ptr = (u8*)parse_mem->kw_table.keywords;
|
|
parse_mem->kw_table.keywords = (u64*)(ptr + (new_base_ptr - old_base_ptr));
|
|
|
|
ptr = (u8*)parse_mem->pp_table.keywords;
|
|
parse_mem->pp_table.keywords = (u64*)(ptr + (new_base_ptr - old_base_ptr));
|
|
}
|
|
|
|
// BOTTOM
|
|
|