Pratt parsing, basic ast, decl parse const
This commit is contained in:
169
main.cpp
169
main.cpp
@@ -154,7 +154,7 @@ wrap_around_pow2(U64 x, U64 power_of_2) {
|
||||
//-----------------------------------------------------------------------------
|
||||
// OS Memory
|
||||
//-----------------------------------------------------------------------------
|
||||
constexpr SizeU os_page_size = 4096;
|
||||
const SizeU os_page_size = 4096;
|
||||
struct OS_Memory{
|
||||
SizeU commit, reserve;
|
||||
U8 *data;
|
||||
@@ -395,6 +395,7 @@ struct Thread_Ctx{
|
||||
Arena scratch[2];
|
||||
Allocator *implicit_allocator;
|
||||
void *ctx;
|
||||
U64 ctx_id;
|
||||
Log_Proc *log_proc;
|
||||
};
|
||||
thread_local Thread_Ctx thread_ctx;
|
||||
@@ -433,15 +434,26 @@ struct Scoped_Allocator{
|
||||
}
|
||||
};
|
||||
|
||||
#define Get_Ctx(T) T *ctx = (T *)thread_ctx.ctx
|
||||
#define Set_Ctx(ctx) Scoped_Ctx scoped_ctx_##__LINE__((void *)ctx)
|
||||
function void *
|
||||
thread_ctx_get_user_ctx(U64 id){
|
||||
assert(id == thread_ctx.ctx_id);
|
||||
assert(id != 0);
|
||||
assert(thread_ctx.ctx_id != 0);
|
||||
assert(thread_ctx.ctx != 0);
|
||||
return thread_ctx.ctx;
|
||||
}
|
||||
#define Get_Ctx(T) T *ctx = (T *)thread_ctx_get_user_ctx(T##_ID)
|
||||
#define Set_Ctx(ctx, id) Scoped_Ctx scoped_ctx_##__LINE__((void *)ctx, id)
|
||||
struct Scoped_Ctx{
|
||||
void *prev_ctx;
|
||||
Scoped_Ctx(void *in_ctx){
|
||||
U64 prev_id;
|
||||
Scoped_Ctx(void *in_ctx, U64 id){
|
||||
prev_ctx = thread_ctx.ctx;
|
||||
prev_id = thread_ctx.ctx_id;
|
||||
thread_ctx.ctx = in_ctx;
|
||||
thread_ctx.ctx_id = id;
|
||||
}
|
||||
~Scoped_Ctx(){thread_ctx.ctx = prev_ctx;}
|
||||
~Scoped_Ctx(){thread_ctx.ctx = prev_ctx; thread_ctx.ctx_id = prev_id;}
|
||||
};
|
||||
|
||||
enum Alloc_Flag{AF_None,AF_ZeroMemory};
|
||||
@@ -579,6 +591,7 @@ test_heap_allocator(){
|
||||
assert(thread_ctx.implicit_allocator == &heap);
|
||||
}
|
||||
|
||||
const U64 Test_Context_ID = 14242;
|
||||
struct Test_Context{
|
||||
int value;
|
||||
};
|
||||
@@ -592,7 +605,7 @@ test_custom_context_2(){
|
||||
function void
|
||||
test_custom_context_1(){
|
||||
Test_Context context = {};
|
||||
Set_Ctx(&context);
|
||||
Set_Ctx(&context, Test_Context_ID);
|
||||
Get_Ctx(Test_Context);
|
||||
ctx->value = 10;
|
||||
test_custom_context_2();
|
||||
@@ -640,78 +653,60 @@ struct Array{
|
||||
S64 len;
|
||||
Allocator *allocator;
|
||||
|
||||
void init(S64 size){
|
||||
if(!allocator) allocator = imp_get();
|
||||
data = exp_alloc_array(allocator, T, size);
|
||||
cap = size;
|
||||
}
|
||||
|
||||
void grow(S64 required_size){
|
||||
if(cap == 0){
|
||||
S64 cap = max(required_size*2, (S64)16);
|
||||
init(cap);
|
||||
}
|
||||
else if(len + required_size > cap){
|
||||
S64 cap = (len + required_size)*2;
|
||||
data = exp_resize_array(allocator, data, T, cap);
|
||||
cap = cap;
|
||||
}
|
||||
}
|
||||
|
||||
void add(T item){
|
||||
grow(1);
|
||||
data[len++] = item;
|
||||
}
|
||||
|
||||
void add(T *item){
|
||||
grow(1);
|
||||
data[len++] = *item;
|
||||
}
|
||||
|
||||
void clear(){
|
||||
len = 0;
|
||||
}
|
||||
|
||||
T *begin(){ return data; }
|
||||
T *end (){ return data + len; }
|
||||
T &operator[](S64 i){ return data[i]; }
|
||||
};
|
||||
#define For(array,it,i) for(SizeU i = 0; i < array.len; i++) for(auto *it = &array[i]; it; it = 0)
|
||||
#define IFor(array) for(auto *it = array.begin(); it != array.end(); it++)
|
||||
#define IterList(list,it) for(auto *it = list->first; it; it=it->next)
|
||||
|
||||
template<class T>
|
||||
void array_init(Array<T> *a, S64 size){
|
||||
if(!a->allocator) a->allocator = thread_ctx.implicit_allocator;
|
||||
a->data = exp_alloc_array(a->allocator, T, size);
|
||||
a->cap = size;
|
||||
}
|
||||
|
||||
template<class T>
|
||||
void array_grow(Array<T> *a, S64 required_size){
|
||||
if(a->cap == 0){
|
||||
S64 cap = max(required_size*2, (S64)16);
|
||||
array_init(a, cap);
|
||||
}
|
||||
else if(a->len + required_size > a->cap){
|
||||
S64 cap = (a->len + required_size)*2;
|
||||
a->data = exp_resize_array(a->allocator, a->data, T, cap);
|
||||
a->cap = cap;
|
||||
}
|
||||
}
|
||||
|
||||
template<class T>
|
||||
Array<T> array_make(S64 size){
|
||||
Array<T> result = {};
|
||||
array_init(&result, size);
|
||||
result.init(size);
|
||||
return result;
|
||||
}
|
||||
|
||||
template<class T>
|
||||
T *array_alloc(Array<T> *a, S64 count){
|
||||
array_grow(a, count);
|
||||
T *result = a->data + a->len;
|
||||
a->len += count;
|
||||
return result;
|
||||
}
|
||||
|
||||
template<class T>
|
||||
void array_push(Array<T> *a, T &item){
|
||||
array_grow(a, 1);
|
||||
a->data[a->len++] = item;
|
||||
}
|
||||
|
||||
template<class T>
|
||||
T array_pop_get(Array<T> *a){
|
||||
assert(a->len > 0);
|
||||
return a->data[--a->len];
|
||||
}
|
||||
|
||||
template<class T>
|
||||
void array_pop(Array<T> *a){
|
||||
assert(a->len > 0);
|
||||
--a->len;
|
||||
}
|
||||
|
||||
template<class T>
|
||||
void array_clear(Array<T> *array){
|
||||
array->len = 0;
|
||||
}
|
||||
|
||||
function void
|
||||
test_array(){
|
||||
Set_Scratch();
|
||||
Array<int> array = {};
|
||||
int size = 1000;
|
||||
for(int i = 0; i < size; i++){
|
||||
array_push(&array, i);
|
||||
array.add(i);
|
||||
}
|
||||
For(array, it, i){
|
||||
assert(*it == i);
|
||||
@@ -721,17 +716,11 @@ test_array(){
|
||||
Array<int> array2 = {};
|
||||
array2.allocator = &arena;
|
||||
for(int i = 0; i < size; i++){
|
||||
array_push(&array2, i);
|
||||
array2.add(i);
|
||||
}
|
||||
For(array2, iterator, count){
|
||||
assert(*iterator == count);
|
||||
}
|
||||
for(int i = 999; i > 950; i--){
|
||||
assert(array_pop_get(&array) == i);
|
||||
}
|
||||
for(int i = 0; i < 10; i++){
|
||||
array_pop(&array2);
|
||||
}
|
||||
exp_destroy(&arena);
|
||||
assert(arena.memory.data == 0);
|
||||
assert(thread_ctx.scratch->memory.data != 0);
|
||||
@@ -775,6 +764,13 @@ map_grow(Map *map, S64 new_size){
|
||||
*map = new_map;
|
||||
}
|
||||
|
||||
function Map
|
||||
map_make(S64 size){
|
||||
Map result = {};
|
||||
map_grow(&result, size);
|
||||
return result;
|
||||
}
|
||||
|
||||
function void
|
||||
map_insert_u64(Map *map, U64 key, void *val){
|
||||
assert(val);
|
||||
@@ -849,30 +845,6 @@ map_test(){
|
||||
}
|
||||
}
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
// Bucket Array
|
||||
//-----------------------------------------------------------------------------
|
||||
template<class T>
|
||||
struct Bucket_Array{
|
||||
struct Bucket{
|
||||
Bucket *next;
|
||||
S64 len, cap;
|
||||
T data[0];
|
||||
};
|
||||
|
||||
Allocator *allocator;
|
||||
Bucket *first;
|
||||
Bucket *last;
|
||||
|
||||
Bucket *iter;
|
||||
S64 iter_len;
|
||||
};
|
||||
|
||||
function void
|
||||
test_bucket_array(){
|
||||
Bucket_Array<int> arr = {};
|
||||
}
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
// Linked lists
|
||||
//-----------------------------------------------------------------------------
|
||||
@@ -1027,8 +999,18 @@ test_string_builder(){
|
||||
struct Intern_Table{
|
||||
Allocator *string_allocator;
|
||||
Map map;
|
||||
U8 *first_keyword;
|
||||
U8 *last_keyword;
|
||||
};
|
||||
|
||||
function Intern_Table
|
||||
intern_table_make(S64 initial_size){
|
||||
Intern_Table result = {};
|
||||
result.map = map_make(initial_size);
|
||||
result.string_allocator = imp_get();
|
||||
return result;
|
||||
}
|
||||
|
||||
function Intern_String
|
||||
intern_string(Intern_Table *t, String string){
|
||||
if(!t->string_allocator) t->string_allocator = imp_get();
|
||||
@@ -1063,11 +1045,18 @@ test_intern_table(){ Set_Scratch();
|
||||
}
|
||||
|
||||
#include "new_lex.cpp"
|
||||
#include "new_ast.cpp"
|
||||
#include "new_parse.cpp"
|
||||
int main(){
|
||||
test_custom_context();
|
||||
test_heap_allocator();
|
||||
test_os_memory();
|
||||
|
||||
thread_ctx_init();
|
||||
|
||||
test_parse_decl();
|
||||
test_parse_expr();
|
||||
|
||||
test_array();
|
||||
map_test();
|
||||
test_string_builder();
|
||||
|
||||
Reference in New Issue
Block a user