mirror of
				https://github.com/janet-lang/janet
				synced 2025-10-31 07:33:01 +00:00 
			
		
		
		
	Rename DstValue to Dst for easier access. Move vector.c into
util.c and make public API smaller. Pad strings and symbols with extra 0 byte for better interop with C.
This commit is contained in:
		
							
								
								
									
										4
									
								
								Makefile
									
									
									
									
									
								
							
							
						
						
									
										4
									
								
								Makefile
									
									
									
									
									
								
							| @@ -31,7 +31,7 @@ PREFIX=/usr/local | |||||||
| DST_TARGET=dst | DST_TARGET=dst | ||||||
| DST_XXD=xxd | DST_XXD=xxd | ||||||
| DEBUGGER=lldb | DEBUGGER=lldb | ||||||
| DST_INTERNAL_HEADERS=$(addprefix core/,symcache.h opcodes.h strtod.h compile.h gc.h sourcemap.h vector.h) | DST_INTERNAL_HEADERS=$(addprefix core/,symcache.h opcodes.h strtod.h compile.h gc.h sourcemap.h util.h) | ||||||
| DST_HEADERS=$(addprefix include/dst/,dst.h dstconfig.h dsttypes.h dststate.h dststl.h) | DST_HEADERS=$(addprefix include/dst/,dst.h dstconfig.h dsttypes.h dststate.h dststl.h) | ||||||
|  |  | ||||||
| ############################# | ############################# | ||||||
| @@ -50,7 +50,7 @@ DST_CORE_SOURCES=$(addprefix core/,\ | |||||||
| 				 abstract.c array.c asm.c buffer.c compile.c\ | 				 abstract.c array.c asm.c buffer.c compile.c\ | ||||||
| 				 fiber.c gc.c math.c parse.c sourcemap.c string.c\ | 				 fiber.c gc.c math.c parse.c sourcemap.c string.c\ | ||||||
| 				 stl.c strtod.c struct.c symcache.c table.c tuple.c util.c\ | 				 stl.c strtod.c struct.c symcache.c table.c tuple.c util.c\ | ||||||
| 				 value.c vector.c vm.c wrap.c) | 				 value.c vm.c wrap.c) | ||||||
|  |  | ||||||
| DST_CLIENT_SOURCES=$(addprefix client/,\ | DST_CLIENT_SOURCES=$(addprefix client/,\ | ||||||
| 				   main.c) | 				   main.c) | ||||||
|   | |||||||
| @@ -30,7 +30,7 @@ | |||||||
| #define DST_CLIENT_REPL 8 | #define DST_CLIENT_REPL 8 | ||||||
| #define DST_CLIENT_UNKNOWN 16 | #define DST_CLIENT_UNKNOWN 16 | ||||||
|  |  | ||||||
| static DstValue env; | static Dst env; | ||||||
|  |  | ||||||
| static int client_strequal(const char *a, const char *b) { | static int client_strequal(const char *a, const char *b) { | ||||||
|     while (*a) if (*a++ != *b++) return 0; |     while (*a) if (*a++ != *b++) return 0; | ||||||
| @@ -115,7 +115,7 @@ static int repl() { | |||||||
|                     if (cres.status == DST_COMPILE_OK) { |                     if (cres.status == DST_COMPILE_OK) { | ||||||
|                         /*dst_puts(dst_formatc("asm: %v\n", dst_disasm(cres.funcdef)));*/ |                         /*dst_puts(dst_formatc("asm: %v\n", dst_disasm(cres.funcdef)));*/ | ||||||
|                         DstFunction *f = dst_compile_func(cres); |                         DstFunction *f = dst_compile_func(cres); | ||||||
|                         DstValue ret; |                         Dst ret; | ||||||
|                         if (dst_run(dst_wrap_function(f), &ret)) { |                         if (dst_run(dst_wrap_function(f), &ret)) { | ||||||
|                             dst_puts(dst_formatc("runtime error: %S\n", dst_to_string(ret)));  |                             dst_puts(dst_formatc("runtime error: %S\n", dst_to_string(ret)));  | ||||||
|                         } else { |                         } else { | ||||||
| @@ -159,7 +159,7 @@ static void runfile(const uint8_t *src, int32_t len) { | |||||||
|                     opts.env = env; |                     opts.env = env; | ||||||
|                     cres = dst_compile(opts); |                     cres = dst_compile(opts); | ||||||
|                     if (cres.status == DST_COMPILE_OK) { |                     if (cres.status == DST_COMPILE_OK) { | ||||||
|                         DstValue ret = dst_wrap_nil(); |                         Dst ret = dst_wrap_nil(); | ||||||
|                         DstFunction *f = dst_compile_func(cres); |                         DstFunction *f = dst_compile_func(cres); | ||||||
|                         if (dst_run(dst_wrap_function(f), &ret)) { |                         if (dst_run(dst_wrap_function(f), &ret)) { | ||||||
|                             dst_puts(dst_formatc("runtime error: %v\n", ret));  |                             dst_puts(dst_formatc("runtime error: %v\n", ret));  | ||||||
|   | |||||||
							
								
								
									
										16
									
								
								core/array.c
									
									
									
									
									
								
							
							
						
						
									
										16
									
								
								core/array.c
									
									
									
									
									
								
							| @@ -25,9 +25,9 @@ | |||||||
|  |  | ||||||
| /* Iniializes an array */ | /* Iniializes an array */ | ||||||
| DstArray *dst_array_init(DstArray *array, int32_t capacity) { | DstArray *dst_array_init(DstArray *array, int32_t capacity) { | ||||||
|     DstValue *data = NULL; |     Dst *data = NULL; | ||||||
|     if (capacity > 0) { |     if (capacity > 0) { | ||||||
|         data = (DstValue *) malloc(sizeof(DstValue) * capacity); |         data = (Dst *) malloc(sizeof(Dst) * capacity); | ||||||
|         if (NULL == data) { |         if (NULL == data) { | ||||||
|             DST_OUT_OF_MEMORY; |             DST_OUT_OF_MEMORY; | ||||||
|         } |         } | ||||||
| @@ -50,10 +50,10 @@ DstArray *dst_array(int32_t capacity) { | |||||||
|  |  | ||||||
| /* Ensure the array has enough capacity for elements */ | /* Ensure the array has enough capacity for elements */ | ||||||
| void dst_array_ensure(DstArray *array, int32_t capacity) { | void dst_array_ensure(DstArray *array, int32_t capacity) { | ||||||
|     DstValue *newData; |     Dst *newData; | ||||||
|     DstValue *old = array->data; |     Dst *old = array->data; | ||||||
|     if (capacity <= array->capacity) return; |     if (capacity <= array->capacity) return; | ||||||
|     newData = realloc(old, capacity * sizeof(DstValue)); |     newData = realloc(old, capacity * sizeof(Dst)); | ||||||
|     if (NULL == newData) { |     if (NULL == newData) { | ||||||
|         DST_OUT_OF_MEMORY; |         DST_OUT_OF_MEMORY; | ||||||
|     } |     } | ||||||
| @@ -76,7 +76,7 @@ void dst_array_setcount(DstArray *array, int32_t count) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Push a value to the top of the array */ | /* Push a value to the top of the array */ | ||||||
| void dst_array_push(DstArray *array, DstValue x) { | void dst_array_push(DstArray *array, Dst x) { | ||||||
|     int32_t newcount = array->count + 1; |     int32_t newcount = array->count + 1; | ||||||
|     if (newcount >= array->capacity) { |     if (newcount >= array->capacity) { | ||||||
|         dst_array_ensure(array, newcount * 2); |         dst_array_ensure(array, newcount * 2); | ||||||
| @@ -86,7 +86,7 @@ void dst_array_push(DstArray *array, DstValue x) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Pop a value from the top of the array */ | /* Pop a value from the top of the array */ | ||||||
| DstValue dst_array_pop(DstArray *array) { | Dst dst_array_pop(DstArray *array) { | ||||||
|     if (array->count) { |     if (array->count) { | ||||||
|         return array->data[--array->count]; |         return array->data[--array->count]; | ||||||
|     } else { |     } else { | ||||||
| @@ -95,7 +95,7 @@ DstValue dst_array_pop(DstArray *array) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Look at the last value in the array */ | /* Look at the last value in the array */ | ||||||
| DstValue dst_array_peek(DstArray *array) { | Dst dst_array_peek(DstArray *array) { | ||||||
|     if (array->count) { |     if (array->count) { | ||||||
|         return array->data[array->count - 1]; |         return array->data[array->count - 1]; | ||||||
|     } else { |     } else { | ||||||
|   | |||||||
							
								
								
									
										71
									
								
								core/asm.c
									
									
									
									
									
								
							
							
						
						
									
										71
									
								
								core/asm.c
									
									
									
									
									
								
							| @@ -26,6 +26,7 @@ | |||||||
| #include "opcodes.h" | #include "opcodes.h" | ||||||
| #include "gc.h" | #include "gc.h" | ||||||
| #include "sourcemap.h" | #include "sourcemap.h" | ||||||
|  | #include "util.h" | ||||||
|  |  | ||||||
| /* Bytecode op argument types */ | /* Bytecode op argument types */ | ||||||
|  |  | ||||||
| @@ -95,7 +96,7 @@ struct DstAssembler { | |||||||
|     int32_t defs_capacity; |     int32_t defs_capacity; | ||||||
|     int32_t bytecode_count; /* Used for calculating labels */ |     int32_t bytecode_count; /* Used for calculating labels */ | ||||||
|  |  | ||||||
|     DstValue name; |     Dst name; | ||||||
|     DstTable labels; /* symbol -> bytecode index */ |     DstTable labels; /* symbol -> bytecode index */ | ||||||
|     DstTable constants; /* symbol -> constant index */ |     DstTable constants; /* symbol -> constant index */ | ||||||
|     DstTable slots; /* symbol -> slot index */ |     DstTable slots; /* symbol -> slot index */ | ||||||
| @@ -214,8 +215,8 @@ static void dst_asm_errorv(DstAssembler *a, const uint8_t *m) { | |||||||
|  * to reference outer function environments, and may change the outer environment.  |  * to reference outer function environments, and may change the outer environment.  | ||||||
|  * Returns the index of the environment in the assembler's environments, or -1 |  * Returns the index of the environment in the assembler's environments, or -1 | ||||||
|  * if not found.  */ |  * if not found.  */ | ||||||
| static int32_t dst_asm_addenv(DstAssembler *a, DstValue envname) { | static int32_t dst_asm_addenv(DstAssembler *a, Dst envname) { | ||||||
|     DstValue check; |     Dst check; | ||||||
|     DstFuncDef *def = a->def; |     DstFuncDef *def = a->def; | ||||||
|     int32_t envindex; |     int32_t envindex; | ||||||
|     int32_t res; |     int32_t res; | ||||||
| @@ -250,7 +251,7 @@ static int32_t dst_asm_addenv(DstAssembler *a, DstValue envname) { | |||||||
| static int32_t doarg_1( | static int32_t doarg_1( | ||||||
|         DstAssembler *a, |         DstAssembler *a, | ||||||
|         DstOpArgType argtype, |         DstOpArgType argtype, | ||||||
|         DstValue x) { |         Dst x) { | ||||||
|     int32_t ret = -1; |     int32_t ret = -1; | ||||||
|     DstTable *c; |     DstTable *c; | ||||||
|     switch (argtype) { |     switch (argtype) { | ||||||
| @@ -286,7 +287,7 @@ static int32_t doarg_1( | |||||||
|             break; |             break; | ||||||
|         case DST_TUPLE: |         case DST_TUPLE: | ||||||
|         { |         { | ||||||
|             const DstValue *t = dst_unwrap_tuple(x); |             const Dst *t = dst_unwrap_tuple(x); | ||||||
|             if (argtype == DST_OAT_TYPE) { |             if (argtype == DST_OAT_TYPE) { | ||||||
|                 int32_t i = 0; |                 int32_t i = 0; | ||||||
|                 ret = 0; |                 ret = 0; | ||||||
| @@ -301,7 +302,7 @@ static int32_t doarg_1( | |||||||
|         case DST_SYMBOL: |         case DST_SYMBOL: | ||||||
|         { |         { | ||||||
|             if (NULL != c) { |             if (NULL != c) { | ||||||
|                 DstValue result = dst_table_get(c, x); |                 Dst result = dst_table_get(c, x); | ||||||
|                 if (dst_checktype(result, DST_INTEGER)) { |                 if (dst_checktype(result, DST_INTEGER)) { | ||||||
|                     if (argtype == DST_OAT_LABEL) { |                     if (argtype == DST_OAT_LABEL) { | ||||||
|                         ret = dst_unwrap_integer(result) - a->bytecode_count; |                         ret = dst_unwrap_integer(result) - a->bytecode_count; | ||||||
| @@ -348,7 +349,7 @@ static uint32_t doarg( | |||||||
|         int nth, |         int nth, | ||||||
|         int nbytes, |         int nbytes, | ||||||
|         int hassign, |         int hassign, | ||||||
|         DstValue x) { |         Dst x) { | ||||||
|     int32_t arg = doarg_1(a, argtype, x); |     int32_t arg = doarg_1(a, argtype, x); | ||||||
|     /* Calculate the min and max values that can be stored given |     /* Calculate the min and max values that can be stored given | ||||||
|      * nbytes, and whether or not the storage is signed */ |      * nbytes, and whether or not the storage is signed */ | ||||||
| @@ -367,7 +368,7 @@ static uint32_t doarg( | |||||||
| static uint32_t read_instruction( | static uint32_t read_instruction( | ||||||
|         DstAssembler *a,  |         DstAssembler *a,  | ||||||
|         const DstInstructionDef *idef, |         const DstInstructionDef *idef, | ||||||
|         const DstValue *argt) { |         const Dst *argt) { | ||||||
|     uint32_t instr = idef->opcode; |     uint32_t instr = idef->opcode; | ||||||
|     switch (idef->type) { |     switch (idef->type) { | ||||||
|         case DIT_0: |         case DIT_0: | ||||||
| @@ -483,11 +484,11 @@ static uint32_t read_instruction( | |||||||
| static DstAssembleResult dst_asm1(DstAssembler *parent, DstAssembleOptions opts) { | static DstAssembleResult dst_asm1(DstAssembler *parent, DstAssembleOptions opts) { | ||||||
|     DstAssembleResult result; |     DstAssembleResult result; | ||||||
|     DstAssembler a; |     DstAssembler a; | ||||||
|     DstValue s = opts.source; |     Dst s = opts.source; | ||||||
|     DstFuncDef *def; |     DstFuncDef *def; | ||||||
|     int32_t count, i; |     int32_t count, i; | ||||||
|     const DstValue *arr; |     const Dst *arr; | ||||||
|     DstValue x; |     Dst x; | ||||||
|  |  | ||||||
|     /* Initialize funcdef */ |     /* Initialize funcdef */ | ||||||
|     def = dst_gcalloc(DST_MEMORY_FUNCDEF, sizeof(DstFuncDef)); |     def = dst_gcalloc(DST_MEMORY_FUNCDEF, sizeof(DstFuncDef)); | ||||||
| @@ -560,9 +561,9 @@ static DstAssembleResult dst_asm1(DstAssembler *parent, DstAssembleOptions opts) | |||||||
|     x = dst_get(s, dst_csymbolv("slots")); |     x = dst_get(s, dst_csymbolv("slots")); | ||||||
|     if (dst_seq_view(x, &arr, &count)) { |     if (dst_seq_view(x, &arr, &count)) { | ||||||
|         for (i = 0; i < count; i++) { |         for (i = 0; i < count; i++) { | ||||||
|             DstValue v = arr[i]; |             Dst v = arr[i]; | ||||||
|             if (dst_checktype(v, DST_TUPLE)) { |             if (dst_checktype(v, DST_TUPLE)) { | ||||||
|                 const DstValue *t = dst_unwrap_tuple(v); |                 const Dst *t = dst_unwrap_tuple(v); | ||||||
|                 int32_t j;  |                 int32_t j;  | ||||||
|                 for (j = 0; j < dst_tuple_length(t); j++) { |                 for (j = 0; j < dst_tuple_length(t); j++) { | ||||||
|                     if (!dst_checktype(t[j], DST_SYMBOL)) |                     if (!dst_checktype(t[j], DST_SYMBOL)) | ||||||
| @@ -581,16 +582,16 @@ static DstAssembleResult dst_asm1(DstAssembler *parent, DstAssembleOptions opts) | |||||||
|     x = dst_get(s, dst_csymbolv("constants")); |     x = dst_get(s, dst_csymbolv("constants")); | ||||||
|     if (dst_seq_view(x, &arr, &count)) { |     if (dst_seq_view(x, &arr, &count)) { | ||||||
|         def->constants_length = count; |         def->constants_length = count; | ||||||
|         def->constants = malloc(sizeof(DstValue) * count); |         def->constants = malloc(sizeof(Dst) * count); | ||||||
|         if (NULL == def->constants) { |         if (NULL == def->constants) { | ||||||
|             DST_OUT_OF_MEMORY; |             DST_OUT_OF_MEMORY; | ||||||
|         } |         } | ||||||
|         for (i = 0; i < count; i++) { |         for (i = 0; i < count; i++) { | ||||||
|             DstValue ct = arr[i]; |             Dst ct = arr[i]; | ||||||
|             if (dst_checktype(ct, DST_TUPLE) && |             if (dst_checktype(ct, DST_TUPLE) && | ||||||
|                 dst_tuple_length(dst_unwrap_tuple(ct)) > 1 && |                 dst_tuple_length(dst_unwrap_tuple(ct)) > 1 && | ||||||
|                 dst_checktype(dst_unwrap_tuple(ct)[0], DST_SYMBOL)) { |                 dst_checktype(dst_unwrap_tuple(ct)[0], DST_SYMBOL)) { | ||||||
|                 const DstValue *t = dst_unwrap_tuple(ct); |                 const Dst *t = dst_unwrap_tuple(ct); | ||||||
|                 int32_t tcount = dst_tuple_length(t); |                 int32_t tcount = dst_tuple_length(t); | ||||||
|                 const uint8_t *macro = dst_unwrap_symbol(t[0]); |                 const uint8_t *macro = dst_unwrap_symbol(t[0]); | ||||||
|                 if (0 == dst_cstrcmp(macro, "quote")) { |                 if (0 == dst_cstrcmp(macro, "quote")) { | ||||||
| @@ -619,7 +620,7 @@ static DstAssembleResult dst_asm1(DstAssembler *parent, DstAssembleOptions opts) | |||||||
|         for (i = 0; i < count; i++) { |         for (i = 0; i < count; i++) { | ||||||
|             DstAssembleResult subres; |             DstAssembleResult subres; | ||||||
|             DstAssembleOptions subopts; |             DstAssembleOptions subopts; | ||||||
|             DstValue subname; |             Dst subname; | ||||||
|             int32_t newlen; |             int32_t newlen; | ||||||
|             subopts.source = arr[i]; |             subopts.source = arr[i]; | ||||||
|             subopts.flags = opts.flags; |             subopts.flags = opts.flags; | ||||||
| @@ -651,7 +652,7 @@ static DstAssembleResult dst_asm1(DstAssembler *parent, DstAssembleOptions opts) | |||||||
|         /* Do labels and find length */ |         /* Do labels and find length */ | ||||||
|         int32_t blength = 0; |         int32_t blength = 0; | ||||||
|         for (i = 0; i < count; ++i) { |         for (i = 0; i < count; ++i) { | ||||||
|             DstValue instr = arr[i]; |             Dst instr = arr[i]; | ||||||
|             if (dst_checktype(instr, DST_SYMBOL)) { |             if (dst_checktype(instr, DST_SYMBOL)) { | ||||||
|                 dst_table_put(&a.labels, instr, dst_wrap_integer(blength)); |                 dst_table_put(&a.labels, instr, dst_wrap_integer(blength)); | ||||||
|             } else if (dst_checktype(instr, DST_TUPLE)) { |             } else if (dst_checktype(instr, DST_TUPLE)) { | ||||||
| @@ -668,13 +669,13 @@ static DstAssembleResult dst_asm1(DstAssembler *parent, DstAssembleOptions opts) | |||||||
|         } |         } | ||||||
|         /* Do bytecode */ |         /* Do bytecode */ | ||||||
|         for (i = 0; i < count; ++i) { |         for (i = 0; i < count; ++i) { | ||||||
|             DstValue instr = arr[i]; |             Dst instr = arr[i]; | ||||||
|             if (dst_checktype(instr, DST_SYMBOL)) { |             if (dst_checktype(instr, DST_SYMBOL)) { | ||||||
|                 continue; |                 continue; | ||||||
|             } else { |             } else { | ||||||
|                 uint32_t op; |                 uint32_t op; | ||||||
|                 const DstInstructionDef *idef; |                 const DstInstructionDef *idef; | ||||||
|                 const DstValue *t; |                 const Dst *t; | ||||||
|                 dst_asm_assert(&a, dst_checktype(instr, DST_TUPLE), "expected tuple"); |                 dst_asm_assert(&a, dst_checktype(instr, DST_TUPLE), "expected tuple"); | ||||||
|                 t = dst_unwrap_tuple(instr); |                 t = dst_unwrap_tuple(instr); | ||||||
|                 if (dst_tuple_length(t) == 0) { |                 if (dst_tuple_length(t) == 0) { | ||||||
| @@ -704,8 +705,8 @@ static DstAssembleResult dst_asm1(DstAssembler *parent, DstAssembleOptions opts) | |||||||
|         dst_asm_assert(&a, count != 2 * def->bytecode_length, "sourcemap must have twice the length of the bytecode"); |         dst_asm_assert(&a, count != 2 * def->bytecode_length, "sourcemap must have twice the length of the bytecode"); | ||||||
|         def->sourcemap = malloc(sizeof(int32_t) * 2 * count); |         def->sourcemap = malloc(sizeof(int32_t) * 2 * count); | ||||||
|         for (i = 0; i < count; i += 2) { |         for (i = 0; i < count; i += 2) { | ||||||
|             DstValue start = arr[i]; |             Dst start = arr[i]; | ||||||
|             DstValue end = arr[i + 1]; |             Dst end = arr[i + 1]; | ||||||
|             if (!(dst_checktype(start, DST_INTEGER) || |             if (!(dst_checktype(start, DST_INTEGER) || | ||||||
|                 dst_unwrap_integer(start) < 0)) { |                 dst_unwrap_integer(start) < 0)) { | ||||||
|                 dst_asm_error(&a, "expected positive integer"); |                 dst_asm_error(&a, "expected positive integer"); | ||||||
| @@ -760,26 +761,26 @@ static const DstInstructionDef *dst_asm_reverse_lookup(uint32_t instr) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Create some constant sized tuples */ | /* Create some constant sized tuples */ | ||||||
| static DstValue tup1(DstValue x) { | static Dst tup1(Dst x) { | ||||||
|     DstValue *tup = dst_tuple_begin(1); |     Dst *tup = dst_tuple_begin(1); | ||||||
|     tup[0] = x; |     tup[0] = x; | ||||||
|     return dst_wrap_tuple(dst_tuple_end(tup)); |     return dst_wrap_tuple(dst_tuple_end(tup)); | ||||||
| } | } | ||||||
| static DstValue tup2(DstValue x, DstValue y) { | static Dst tup2(Dst x, Dst y) { | ||||||
|     DstValue *tup = dst_tuple_begin(2); |     Dst *tup = dst_tuple_begin(2); | ||||||
|     tup[0] = x; |     tup[0] = x; | ||||||
|     tup[1] = y; |     tup[1] = y; | ||||||
|     return dst_wrap_tuple(dst_tuple_end(tup)); |     return dst_wrap_tuple(dst_tuple_end(tup)); | ||||||
| } | } | ||||||
| static DstValue tup3(DstValue x, DstValue y, DstValue z) { | static Dst tup3(Dst x, Dst y, Dst z) { | ||||||
|     DstValue *tup = dst_tuple_begin(3); |     Dst *tup = dst_tuple_begin(3); | ||||||
|     tup[0] = x; |     tup[0] = x; | ||||||
|     tup[1] = y; |     tup[1] = y; | ||||||
|     tup[2] = z; |     tup[2] = z; | ||||||
|     return dst_wrap_tuple(dst_tuple_end(tup)); |     return dst_wrap_tuple(dst_tuple_end(tup)); | ||||||
| } | } | ||||||
| static DstValue tup4(DstValue w, DstValue x, DstValue y, DstValue z) { | static Dst tup4(Dst w, Dst x, Dst y, Dst z) { | ||||||
|     DstValue *tup = dst_tuple_begin(4); |     Dst *tup = dst_tuple_begin(4); | ||||||
|     tup[0] = w; |     tup[0] = w; | ||||||
|     tup[1] = x; |     tup[1] = x; | ||||||
|     tup[2] = y; |     tup[2] = y; | ||||||
| @@ -788,9 +789,9 @@ static DstValue tup4(DstValue w, DstValue x, DstValue y, DstValue z) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Given an argument, convert it to the appriate integer or symbol */ | /* Given an argument, convert it to the appriate integer or symbol */ | ||||||
| DstValue dst_asm_decode_instruction(uint32_t instr) { | Dst dst_asm_decode_instruction(uint32_t instr) { | ||||||
|     const DstInstructionDef *def = dst_asm_reverse_lookup(instr); |     const DstInstructionDef *def = dst_asm_reverse_lookup(instr); | ||||||
|     DstValue name; |     Dst name; | ||||||
|     if (NULL == def) { |     if (NULL == def) { | ||||||
|         return dst_wrap_integer((int32_t)instr); |         return dst_wrap_integer((int32_t)instr); | ||||||
|     } |     } | ||||||
| @@ -832,7 +833,7 @@ DstValue dst_asm_decode_instruction(uint32_t instr) { | |||||||
| #undef oparg | #undef oparg | ||||||
| } | } | ||||||
|  |  | ||||||
| DstValue dst_disasm(DstFuncDef *def) { | Dst dst_disasm(DstFuncDef *def) { | ||||||
|     int32_t i; |     int32_t i; | ||||||
|     DstArray *bcode = dst_array(def->bytecode_length); |     DstArray *bcode = dst_array(def->bytecode_length); | ||||||
|     DstArray *constants; |     DstArray *constants; | ||||||
| @@ -856,8 +857,8 @@ DstValue dst_disasm(DstFuncDef *def) { | |||||||
|         constants = dst_array(def->constants_length); |         constants = dst_array(def->constants_length); | ||||||
|         dst_table_put(ret, dst_csymbolv("constants"), dst_wrap_array(constants)); |         dst_table_put(ret, dst_csymbolv("constants"), dst_wrap_array(constants)); | ||||||
|         for (i = 0; i < def->constants_length; i++) { |         for (i = 0; i < def->constants_length; i++) { | ||||||
|             DstValue src = def->constants[i]; |             Dst src = def->constants[i]; | ||||||
|             DstValue dest; |             Dst dest; | ||||||
|             if (dst_checktype(src, DST_TUPLE)) { |             if (dst_checktype(src, DST_TUPLE)) { | ||||||
|                 dest = tup2(dst_csymbolv("quote"), src); |                 dest = tup2(dst_csymbolv("quote"), src); | ||||||
|             } else { |             } else { | ||||||
|   | |||||||
							
								
								
									
										150
									
								
								core/compile.c
									
									
									
									
									
								
							
							
						
						
									
										150
									
								
								core/compile.c
									
									
									
									
									
								
							| @@ -25,10 +25,10 @@ | |||||||
| #include "compile.h" | #include "compile.h" | ||||||
| #include "gc.h" | #include "gc.h" | ||||||
| #include "sourcemap.h" | #include "sourcemap.h" | ||||||
| #include "vector.h" | #include "util.h" | ||||||
|  |  | ||||||
| /* Throw an error with a dst string. */ | /* Throw an error with a dst string. */ | ||||||
| void dstc_error(DstCompiler *c, const DstValue *sourcemap, const uint8_t *m) { | void dstc_error(DstCompiler *c, const Dst *sourcemap, const uint8_t *m) { | ||||||
|     /* Don't override first error */ |     /* Don't override first error */ | ||||||
|     if (c->result.status == DST_COMPILE_ERROR) { |     if (c->result.status == DST_COMPILE_ERROR) { | ||||||
|         return; |         return; | ||||||
| @@ -45,15 +45,15 @@ void dstc_error(DstCompiler *c, const DstValue *sourcemap, const uint8_t *m) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Throw an error with a message in a cstring */ | /* Throw an error with a message in a cstring */ | ||||||
| void dstc_cerror(DstCompiler *c, const DstValue *sourcemap, const char *m) { | void dstc_cerror(DstCompiler *c, const Dst *sourcemap, const char *m) { | ||||||
|     dstc_error(c, sourcemap, dst_cstring(m)); |     dstc_error(c, sourcemap, dst_cstring(m)); | ||||||
| } | } | ||||||
|  |  | ||||||
| /* Use these to get sub options. They will traverse the source map so | /* Use these to get sub options. They will traverse the source map so | ||||||
|  * compiler errors make sense. Then modify the returned options. */ |  * compiler errors make sense. Then modify the returned options. */ | ||||||
| DstFormOptions dstc_getindex(DstFormOptions opts, int32_t index) { | DstFopts dstc_getindex(DstFopts opts, int32_t index) { | ||||||
|     const DstValue *sourcemap = dst_sourcemap_index(opts.sourcemap, index); |     const Dst *sourcemap = dst_sourcemap_index(opts.sourcemap, index); | ||||||
|     DstValue nextval = dst_getindex(opts.x, index); |     Dst nextval = dst_getindex(opts.x, index); | ||||||
|     opts.x = nextval; |     opts.x = nextval; | ||||||
|     opts.flags = 0; |     opts.flags = 0; | ||||||
|     opts.sourcemap = sourcemap; |     opts.sourcemap = sourcemap; | ||||||
| @@ -61,8 +61,8 @@ DstFormOptions dstc_getindex(DstFormOptions opts, int32_t index) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Index into the key of a table or struct */ | /* Index into the key of a table or struct */ | ||||||
| DstFormOptions dstc_getkey(DstFormOptions opts, DstValue key) { | DstFopts dstc_getkey(DstFopts opts, Dst key) { | ||||||
|     const DstValue *sourcemap = dst_sourcemap_key(opts.sourcemap, key); |     const Dst *sourcemap = dst_sourcemap_key(opts.sourcemap, key); | ||||||
|     opts.x = key; |     opts.x = key; | ||||||
|     opts.sourcemap = sourcemap; |     opts.sourcemap = sourcemap; | ||||||
|     opts.flags = 0; |     opts.flags = 0; | ||||||
| @@ -70,9 +70,9 @@ DstFormOptions dstc_getkey(DstFormOptions opts, DstValue key) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Index into the value of a table or struct */ | /* Index into the value of a table or struct */ | ||||||
| DstFormOptions dstc_getvalue(DstFormOptions opts, DstValue key) { | DstFopts dstc_getvalue(DstFopts opts, Dst key) { | ||||||
|     const DstValue *sourcemap = dst_sourcemap_value(opts.sourcemap, key); |     const Dst *sourcemap = dst_sourcemap_value(opts.sourcemap, key); | ||||||
|     DstValue nextval = dst_get(opts.x, key); |     Dst nextval = dst_get(opts.x, key); | ||||||
|     opts.x = nextval; |     opts.x = nextval; | ||||||
|     opts.sourcemap = sourcemap; |     opts.sourcemap = sourcemap; | ||||||
|     opts.flags = 0; |     opts.flags = 0; | ||||||
| @@ -80,7 +80,7 @@ DstFormOptions dstc_getvalue(DstFormOptions opts, DstValue key) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Check error */ | /* Check error */ | ||||||
| static int dstc_iserr(DstFormOptions *opts) { | static int dstc_iserr(DstFopts *opts) { | ||||||
|     return (opts->compiler->result.status == DST_COMPILE_ERROR); |     return (opts->compiler->result.status == DST_COMPILE_ERROR); | ||||||
| } | } | ||||||
|  |  | ||||||
| @@ -151,7 +151,7 @@ static void dstc_nameslot(DstCompiler *c, const uint8_t *sym, DstSlot s) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Add a constant to the current scope. Return the index of the constant. */ | /* Add a constant to the current scope. Return the index of the constant. */ | ||||||
| static int32_t dstc_const(DstCompiler *c, const DstValue *sourcemap, DstValue x) { | static int32_t dstc_const(DstCompiler *c, const Dst *sourcemap, Dst x) { | ||||||
|     DstScope *scope = &dst_v_last(c->scopes); |     DstScope *scope = &dst_v_last(c->scopes); | ||||||
|     int32_t i, len; |     int32_t i, len; | ||||||
|     /* Get the topmost function scope */ |     /* Get the topmost function scope */ | ||||||
| @@ -203,13 +203,6 @@ void dstc_popscope(DstCompiler *c) { | |||||||
|     int32_t oldcount = dst_v_count(c->scopes); |     int32_t oldcount = dst_v_count(c->scopes); | ||||||
|     dst_assert(oldcount, "could not pop scope"); |     dst_assert(oldcount, "could not pop scope"); | ||||||
|     scope = dst_v_last(c->scopes); |     scope = dst_v_last(c->scopes); | ||||||
|     /* Move free slots to parent scope if not a new function. |  | ||||||
|      * We need to know the total number of slots used when compiling the function. */ |  | ||||||
|     if (!(scope.flags & (DST_SCOPE_FUNCTION | DST_SCOPE_UNUSED)) && oldcount > 1) { |  | ||||||
|         DstScope *newscope = &dst_v_last(c->scopes); |  | ||||||
|         if (newscope->smax < scope.smax)  |  | ||||||
|             newscope->smax = scope.smax; |  | ||||||
|     } |  | ||||||
|     /* Free the scope */ |     /* Free the scope */ | ||||||
|     dst_v_free(scope.consts); |     dst_v_free(scope.consts); | ||||||
|     dst_v_free(scope.syms); |     dst_v_free(scope.syms); | ||||||
| @@ -217,10 +210,17 @@ void dstc_popscope(DstCompiler *c) { | |||||||
|     dst_v_free(scope.defs); |     dst_v_free(scope.defs); | ||||||
|     dst_v_free(scope.slots); |     dst_v_free(scope.slots); | ||||||
|     dst_v_pop(c->scopes); |     dst_v_pop(c->scopes); | ||||||
|  |     /* Move free slots to parent scope if not a new function. | ||||||
|  |      * We need to know the total number of slots used when compiling the function. */ | ||||||
|  |     if (!(scope.flags & (DST_SCOPE_FUNCTION | DST_SCOPE_UNUSED)) && oldcount > 1) { | ||||||
|  |         DstScope *newscope = &dst_v_last(c->scopes); | ||||||
|  |         if (newscope->smax < scope.smax)  | ||||||
|  |             newscope->smax = scope.smax; | ||||||
|  |     } | ||||||
| } | } | ||||||
|  |  | ||||||
| /* Create a slot with a constant */ | /* Create a slot with a constant */ | ||||||
| DstSlot dstc_cslot(DstValue x) { | DstSlot dstc_cslot(Dst x) { | ||||||
|     DstSlot ret; |     DstSlot ret; | ||||||
|     ret.flags = (1 << dst_type(x)) | DST_SLOT_CONSTANT; |     ret.flags = (1 << dst_type(x)) | DST_SLOT_CONSTANT; | ||||||
|     ret.index = -1; |     ret.index = -1; | ||||||
| @@ -232,7 +232,7 @@ DstSlot dstc_cslot(DstValue x) { | |||||||
| /* Allow searching for symbols. Return information about the symbol */ | /* Allow searching for symbols. Return information about the symbol */ | ||||||
| DstSlot dstc_resolve( | DstSlot dstc_resolve( | ||||||
|         DstCompiler *c, |         DstCompiler *c, | ||||||
|         const DstValue *sourcemap, |         const Dst *sourcemap, | ||||||
|         const uint8_t *sym) { |         const uint8_t *sym) { | ||||||
|  |  | ||||||
|     DstSlot ret = dstc_cslot(dst_wrap_nil()); |     DstSlot ret = dstc_cslot(dst_wrap_nil()); | ||||||
| @@ -261,8 +261,8 @@ DstSlot dstc_resolve( | |||||||
|  |  | ||||||
|     /* Symbol not found - check for global */ |     /* Symbol not found - check for global */ | ||||||
|     { |     { | ||||||
|         DstValue check = dst_get(c->env, dst_wrap_symbol(sym)); |         Dst check = dst_get(c->env, dst_wrap_symbol(sym)); | ||||||
|         DstValue ref; |         Dst ref; | ||||||
|         if (!(dst_checktype(check, DST_STRUCT) || dst_checktype(check, DST_TABLE))) { |         if (!(dst_checktype(check, DST_STRUCT) || dst_checktype(check, DST_TABLE))) { | ||||||
|             dstc_error(c, sourcemap, dst_formatc("unknown symbol %q", sym)); |             dstc_error(c, sourcemap, dst_formatc("unknown symbol %q", sym)); | ||||||
|             return dstc_cslot(dst_wrap_nil()); |             return dstc_cslot(dst_wrap_nil()); | ||||||
| @@ -275,7 +275,7 @@ DstSlot dstc_resolve( | |||||||
|             ret.flags &= ~DST_SLOT_CONSTANT; |             ret.flags &= ~DST_SLOT_CONSTANT; | ||||||
|             return ret; |             return ret; | ||||||
|         } else { |         } else { | ||||||
|             DstValue value = dst_get(check, dst_csymbolv("value")); |             Dst value = dst_get(check, dst_csymbolv("value")); | ||||||
|             return dstc_cslot(value); |             return dstc_cslot(value); | ||||||
|         } |         } | ||||||
|     } |     } | ||||||
| @@ -333,7 +333,7 @@ DstSlot dstc_resolve( | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Emit a raw instruction with source mapping. */ | /* Emit a raw instruction with source mapping. */ | ||||||
| void dstc_emit(DstCompiler *c, const DstValue *sourcemap, uint32_t instr) { | void dstc_emit(DstCompiler *c, const Dst *sourcemap, uint32_t instr) { | ||||||
|     dst_v_push(c->buffer, instr); |     dst_v_push(c->buffer, instr); | ||||||
|     if (NULL != sourcemap) { |     if (NULL != sourcemap) { | ||||||
|         dst_v_push(c->mapbuffer, dst_unwrap_integer(sourcemap[0])); |         dst_v_push(c->mapbuffer, dst_unwrap_integer(sourcemap[0])); | ||||||
| @@ -345,7 +345,7 @@ void dstc_emit(DstCompiler *c, const DstValue *sourcemap, uint32_t instr) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Load a constant into a local slot */ | /* Load a constant into a local slot */ | ||||||
| static void dstc_loadconst(DstCompiler *c, const DstValue *sourcemap, DstValue k, int32_t dest) { | static void dstc_loadconst(DstCompiler *c, const Dst *sourcemap, Dst k, int32_t dest) { | ||||||
|     switch (dst_type(k)) { |     switch (dst_type(k)) { | ||||||
|         case DST_NIL: |         case DST_NIL: | ||||||
|             dstc_emit(c, sourcemap, (dest << 8) | DOP_LOAD_NIL); |             dstc_emit(c, sourcemap, (dest << 8) | DOP_LOAD_NIL); | ||||||
| @@ -384,7 +384,7 @@ static void dstc_loadconst(DstCompiler *c, const DstValue *sourcemap, DstValue k | |||||||
|  * that can be used in an instruction. */ |  * that can be used in an instruction. */ | ||||||
| static int32_t dstc_preread( | static int32_t dstc_preread( | ||||||
|         DstCompiler *c, |         DstCompiler *c, | ||||||
|         const DstValue *sourcemap, |         const Dst *sourcemap, | ||||||
|         int32_t max, |         int32_t max, | ||||||
|         int nth, |         int nth, | ||||||
|         DstSlot s) { |         DstSlot s) { | ||||||
| @@ -436,7 +436,7 @@ static void dstc_postread(DstCompiler *c, DstSlot s, int32_t index) { | |||||||
|  * be writeable (not a literal). */ |  * be writeable (not a literal). */ | ||||||
| static void dstc_copy( | static void dstc_copy( | ||||||
|         DstCompiler *c, |         DstCompiler *c, | ||||||
|         const DstValue *sourcemap, |         const Dst *sourcemap, | ||||||
|         DstSlot dest, |         DstSlot dest, | ||||||
|         DstSlot src) { |         DstSlot src) { | ||||||
|     int writeback = 0; |     int writeback = 0; | ||||||
| @@ -559,7 +559,7 @@ static void dstc_copy( | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Generate the return instruction for a slot. */ | /* Generate the return instruction for a slot. */ | ||||||
| static DstSlot dstc_return(DstCompiler *c, const DstValue *sourcemap, DstSlot s) { | static DstSlot dstc_return(DstCompiler *c, const Dst *sourcemap, DstSlot s) { | ||||||
|     if (!(s.flags & DST_SLOT_RETURNED)) { |     if (!(s.flags & DST_SLOT_RETURNED)) { | ||||||
|         if (s.flags & DST_SLOT_CONSTANT && dst_checktype(s.constant, DST_NIL)) { |         if (s.flags & DST_SLOT_CONSTANT && dst_checktype(s.constant, DST_NIL)) { | ||||||
|             dstc_emit(c, sourcemap, DOP_RETURN_NIL); |             dstc_emit(c, sourcemap, DOP_RETURN_NIL); | ||||||
| @@ -575,7 +575,7 @@ static DstSlot dstc_return(DstCompiler *c, const DstValue *sourcemap, DstSlot s) | |||||||
|  |  | ||||||
| /* Get a target slot for emitting an instruction. Will always return | /* Get a target slot for emitting an instruction. Will always return | ||||||
|  * a local slot. */ |  * a local slot. */ | ||||||
| static DstSlot dstc_gettarget(DstFormOptions opts) { | static DstSlot dstc_gettarget(DstFopts opts) { | ||||||
|     DstSlot slot; |     DstSlot slot; | ||||||
|     if ((opts.flags & DST_FOPTS_HINT) && |     if ((opts.flags & DST_FOPTS_HINT) && | ||||||
|         (opts.hint.envindex == 0) && |         (opts.hint.envindex == 0) && | ||||||
| @@ -593,17 +593,17 @@ static DstSlot dstc_gettarget(DstFormOptions opts) { | |||||||
| /* Slot and map pairing */ | /* Slot and map pairing */ | ||||||
| typedef struct SlotMap { | typedef struct SlotMap { | ||||||
|     DstSlot slot; |     DstSlot slot; | ||||||
|     const DstValue *map; |     const Dst *map; | ||||||
| } SlotMap; | } SlotMap; | ||||||
|  |  | ||||||
| /* Get a bunch of slots for function arguments */ | /* Get a bunch of slots for function arguments */ | ||||||
| SlotMap *toslots(DstFormOptions opts, int32_t start) { | SlotMap *toslots(DstFopts opts, int32_t start) { | ||||||
|     int32_t i, len; |     int32_t i, len; | ||||||
|     SlotMap *ret = NULL; |     SlotMap *ret = NULL; | ||||||
|     len = dst_length(opts.x); |     len = dst_length(opts.x); | ||||||
|     for (i = start; i < len; i++) { |     for (i = start; i < len; i++) { | ||||||
|         SlotMap sm; |         SlotMap sm; | ||||||
|         DstFormOptions subopts = dstc_getindex(opts, i); |         DstFopts subopts = dstc_getindex(opts, i); | ||||||
|         sm.slot = dstc_value(subopts); |         sm.slot = dstc_value(subopts); | ||||||
|         sm.map = subopts.sourcemap; |         sm.map = subopts.sourcemap; | ||||||
|         dst_v_push(ret, sm); |         dst_v_push(ret, sm); | ||||||
| @@ -612,13 +612,13 @@ SlotMap *toslots(DstFormOptions opts, int32_t start) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Get a bunch of slots for function arguments */ | /* Get a bunch of slots for function arguments */ | ||||||
| static SlotMap *toslotskv(DstFormOptions opts) { | static SlotMap *toslotskv(DstFopts opts) { | ||||||
|     SlotMap *ret = NULL; |     SlotMap *ret = NULL; | ||||||
|     const DstKV *kv = NULL; |     const DstKV *kv = NULL; | ||||||
|     while (NULL != (kv = dst_next(opts.x, kv))) { |     while (NULL != (kv = dst_next(opts.x, kv))) { | ||||||
|         SlotMap km, vm; |         SlotMap km, vm; | ||||||
|         DstFormOptions kopts = dstc_getkey(opts, kv->key); |         DstFopts kopts = dstc_getkey(opts, kv->key); | ||||||
|         DstFormOptions vopts = dstc_getvalue(opts, kv->key); |         DstFopts vopts = dstc_getvalue(opts, kv->key); | ||||||
|         km.slot = dstc_value(kopts); |         km.slot = dstc_value(kopts); | ||||||
|         km.map = kopts.sourcemap; |         km.map = kopts.sourcemap; | ||||||
|         vm.slot = dstc_value(vopts); |         vm.slot = dstc_value(vopts); | ||||||
| @@ -630,9 +630,9 @@ static SlotMap *toslotskv(DstFormOptions opts) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Push slots load via toslots. */ | /* Push slots load via toslots. */ | ||||||
| static void pushslots(DstFormOptions opts, SlotMap *sms) { | static void pushslots(DstFopts opts, SlotMap *sms) { | ||||||
|     DstCompiler *c = opts.compiler; |     DstCompiler *c = opts.compiler; | ||||||
|     const DstValue *sm = opts.sourcemap; |     const Dst *sm = opts.sourcemap; | ||||||
|     int32_t i; |     int32_t i; | ||||||
|     for (i = 0; i < dst_v_count(sms) - 2; i += 3) { |     for (i = 0; i < dst_v_count(sms) - 2; i += 3) { | ||||||
|         int32_t ls1 = dstc_preread(c, sms[i].map, 0xFF, 1, sms[i].slot); |         int32_t ls1 = dstc_preread(c, sms[i].map, 0xFF, 1, sms[i].slot); | ||||||
| @@ -666,7 +666,7 @@ static void pushslots(DstFormOptions opts, SlotMap *sms) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Free slots loaded via toslots */ | /* Free slots loaded via toslots */ | ||||||
| static void freeslots(DstFormOptions opts, SlotMap *sms) { | static void freeslots(DstFopts opts, SlotMap *sms) { | ||||||
|     int32_t i; |     int32_t i; | ||||||
|     for (i = 0; i < dst_v_count(sms); i++) { |     for (i = 0; i < dst_v_count(sms); i++) { | ||||||
|         dstc_freeslot(opts.compiler, sms[i].slot); |         dstc_freeslot(opts.compiler, sms[i].slot); | ||||||
| @@ -674,7 +674,7 @@ static void freeslots(DstFormOptions opts, SlotMap *sms) { | |||||||
|     dst_v_free(sms); |     dst_v_free(sms); | ||||||
| } | } | ||||||
|  |  | ||||||
| DstSlot dstc_quote(DstFormOptions opts, int32_t argn, const DstValue *argv) { | DstSlot dstc_quote(DstFopts opts, int32_t argn, const Dst *argv) { | ||||||
|     if (argn != 1) { |     if (argn != 1) { | ||||||
|         dstc_cerror(opts.compiler, opts.sourcemap, "expected 1 argument"); |         dstc_cerror(opts.compiler, opts.sourcemap, "expected 1 argument"); | ||||||
|         return dstc_cslot(dst_wrap_nil()); |         return dstc_cslot(dst_wrap_nil()); | ||||||
| @@ -682,9 +682,9 @@ DstSlot dstc_quote(DstFormOptions opts, int32_t argn, const DstValue *argv) { | |||||||
|     return dstc_cslot(argv[0]); |     return dstc_cslot(argv[0]); | ||||||
| } | } | ||||||
|  |  | ||||||
| DstSlot dstc_var(DstFormOptions opts, int32_t argn, const DstValue *argv) { | DstSlot dstc_var(DstFopts opts, int32_t argn, const Dst *argv) { | ||||||
|     DstCompiler *c = opts.compiler; |     DstCompiler *c = opts.compiler; | ||||||
|     DstFormOptions subopts; |     DstFopts subopts; | ||||||
|     DstSlot ret; |     DstSlot ret; | ||||||
|     if (argn != 2) { |     if (argn != 2) { | ||||||
|         dstc_cerror(opts.compiler, opts.sourcemap, "expected 2 arguments"); |         dstc_cerror(opts.compiler, opts.sourcemap, "expected 2 arguments"); | ||||||
| @@ -699,7 +699,7 @@ DstSlot dstc_var(DstFormOptions opts, int32_t argn, const DstValue *argv) { | |||||||
|     ret = dstc_value(subopts); |     ret = dstc_value(subopts); | ||||||
|     if (dst_v_last(c->scopes).flags & DST_SCOPE_TOP) { |     if (dst_v_last(c->scopes).flags & DST_SCOPE_TOP) { | ||||||
|         DstCompiler *c = opts.compiler; |         DstCompiler *c = opts.compiler; | ||||||
|         const DstValue *sm = opts.sourcemap; |         const Dst *sm = opts.sourcemap; | ||||||
|         DstSlot refslot, refarrayslot; |         DstSlot refslot, refarrayslot; | ||||||
|         /* Global var, generate var */ |         /* Global var, generate var */ | ||||||
|         DstTable *reftab = dst_table(1); |         DstTable *reftab = dst_table(1); | ||||||
| @@ -742,8 +742,8 @@ DstSlot dstc_var(DstFormOptions opts, int32_t argn, const DstValue *argv) { | |||||||
|     return ret; |     return ret; | ||||||
| } | } | ||||||
|  |  | ||||||
| DstSlot dstc_varset(DstFormOptions opts, int32_t argn, const DstValue *argv) { | DstSlot dstc_varset(DstFopts opts, int32_t argn, const Dst *argv) { | ||||||
|     DstFormOptions subopts; |     DstFopts subopts; | ||||||
|     DstSlot ret, dest; |     DstSlot ret, dest; | ||||||
|     if (argn != 2) { |     if (argn != 2) { | ||||||
|         dstc_cerror(opts.compiler, opts.sourcemap, "expected 2 arguments"); |         dstc_cerror(opts.compiler, opts.sourcemap, "expected 2 arguments"); | ||||||
| @@ -766,9 +766,9 @@ DstSlot dstc_varset(DstFormOptions opts, int32_t argn, const DstValue *argv) { | |||||||
|     return ret; |     return ret; | ||||||
| } | } | ||||||
|  |  | ||||||
| DstSlot dstc_def(DstFormOptions opts, int32_t argn, const DstValue *argv) { | DstSlot dstc_def(DstFopts opts, int32_t argn, const Dst *argv) { | ||||||
|     DstCompiler *c = opts.compiler; |     DstCompiler *c = opts.compiler; | ||||||
|     DstFormOptions subopts; |     DstFopts subopts; | ||||||
|     DstSlot ret; |     DstSlot ret; | ||||||
|     if (argn != 2) { |     if (argn != 2) { | ||||||
|         dstc_cerror(opts.compiler, opts.sourcemap, "expected 2 arguments"); |         dstc_cerror(opts.compiler, opts.sourcemap, "expected 2 arguments"); | ||||||
| @@ -785,7 +785,7 @@ DstSlot dstc_def(DstFormOptions opts, int32_t argn, const DstValue *argv) { | |||||||
|     if (dst_v_last(c->scopes).flags & DST_SCOPE_TOP) { |     if (dst_v_last(c->scopes).flags & DST_SCOPE_TOP) { | ||||||
|         /* Global def, generate code to store in env when executed */ |         /* Global def, generate code to store in env when executed */ | ||||||
|         DstCompiler *c = opts.compiler; |         DstCompiler *c = opts.compiler; | ||||||
|         const DstValue *sm = opts.sourcemap; |         const Dst *sm = opts.sourcemap; | ||||||
|         /* Root scope, add to def table */ |         /* Root scope, add to def table */ | ||||||
|         DstSlot envslot = dstc_cslot(c->env); |         DstSlot envslot = dstc_cslot(c->env); | ||||||
|         DstSlot nameslot = dstc_cslot(argv[0]); |         DstSlot nameslot = dstc_cslot(argv[0]); | ||||||
| @@ -830,7 +830,7 @@ DstSlot dstc_def(DstFormOptions opts, int32_t argn, const DstValue *argv) { | |||||||
| /* Compile some code that will be thrown away. Used to ensure | /* Compile some code that will be thrown away. Used to ensure | ||||||
|  * that dead code is well formed without including it in the final |  * that dead code is well formed without including it in the final | ||||||
|  * bytecode. */ |  * bytecode. */ | ||||||
| static void dstc_throwaway(DstFormOptions opts) { | static void dstc_throwaway(DstFopts opts) { | ||||||
|     DstCompiler *c = opts.compiler; |     DstCompiler *c = opts.compiler; | ||||||
|     int32_t bufstart = dst_v_count(c->buffer); |     int32_t bufstart = dst_v_count(c->buffer); | ||||||
|     dstc_scope(c, DST_SCOPE_UNUSED); |     dstc_scope(c, DST_SCOPE_UNUSED); | ||||||
| @@ -854,11 +854,11 @@ static void dstc_throwaway(DstFormOptions opts) { | |||||||
|  * ... |  * ... | ||||||
|  * :done |  * :done | ||||||
|  */ |  */ | ||||||
| DstSlot dstc_if(DstFormOptions opts, int32_t argn, const DstValue *argv) { | DstSlot dstc_if(DstFopts opts, int32_t argn, const Dst *argv) { | ||||||
|     DstCompiler *c = opts.compiler; |     DstCompiler *c = opts.compiler; | ||||||
|     const DstValue *sm = opts.sourcemap; |     const Dst *sm = opts.sourcemap; | ||||||
|     int32_t labelr, labeljr, labeld, labeljd, condlocal; |     int32_t labelr, labeljr, labeld, labeljd, condlocal; | ||||||
|     DstFormOptions leftopts, rightopts, condopts; |     DstFopts leftopts, rightopts, condopts; | ||||||
|     DstSlot cond, left, right, target; |     DstSlot cond, left, right, target; | ||||||
|     const int tail = opts.flags & DST_FOPTS_TAIL; |     const int tail = opts.flags & DST_FOPTS_TAIL; | ||||||
|     const int drop = opts.flags & DST_FOPTS_DROP; |     const int drop = opts.flags & DST_FOPTS_DROP; | ||||||
| @@ -893,7 +893,7 @@ DstSlot dstc_if(DstFormOptions opts, int32_t argn, const DstValue *argv) { | |||||||
|     /* Check constant condition. */ |     /* Check constant condition. */ | ||||||
|     /* TODO: Use type info for more short circuits */ |     /* TODO: Use type info for more short circuits */ | ||||||
|     if ((cond.flags & DST_SLOT_CONSTANT) && !(cond.flags & DST_SLOT_REF)) { |     if ((cond.flags & DST_SLOT_CONSTANT) && !(cond.flags & DST_SLOT_REF)) { | ||||||
|         DstFormOptions goodopts, badopts; |         DstFopts goodopts, badopts; | ||||||
|         if (dst_truthy(cond.constant)) { |         if (dst_truthy(cond.constant)) { | ||||||
|             goodopts = leftopts; |             goodopts = leftopts; | ||||||
|             badopts = rightopts; |             badopts = rightopts; | ||||||
| @@ -946,13 +946,13 @@ DstSlot dstc_if(DstFormOptions opts, int32_t argn, const DstValue *argv) { | |||||||
|     return target; |     return target; | ||||||
| } | } | ||||||
|  |  | ||||||
| DstSlot dstc_do(DstFormOptions opts, int32_t argn, const DstValue *argv) { | DstSlot dstc_do(DstFopts opts, int32_t argn, const Dst *argv) { | ||||||
|     int32_t i; |     int32_t i; | ||||||
|     DstSlot ret; |     DstSlot ret; | ||||||
|     dstc_scope(opts.compiler, 0); |     dstc_scope(opts.compiler, 0); | ||||||
|     (void) argv; |     (void) argv; | ||||||
|     for (i = 0; i < argn; i++) { |     for (i = 0; i < argn; i++) { | ||||||
|         DstFormOptions subopts = dstc_getindex(opts, i + 1); |         DstFopts subopts = dstc_getindex(opts, i + 1); | ||||||
|         if (i != argn - 1) { |         if (i != argn - 1) { | ||||||
|             subopts.flags = DST_FOPTS_DROP; |             subopts.flags = DST_FOPTS_DROP; | ||||||
|         } else if (opts.flags & DST_FOPTS_TAIL) { |         } else if (opts.flags & DST_FOPTS_TAIL) { | ||||||
| @@ -976,9 +976,9 @@ DstSlot dstc_do(DstFormOptions opts, int32_t argn, const DstValue *argv) { | |||||||
|  * jump :whiletop |  * jump :whiletop | ||||||
|  * :done |  * :done | ||||||
|  */ |  */ | ||||||
| DstSlot dstc_while(DstFormOptions opts, int32_t argn, const DstValue *argv) { | DstSlot dstc_while(DstFopts opts, int32_t argn, const Dst *argv) { | ||||||
|     DstCompiler *c = opts.compiler; |     DstCompiler *c = opts.compiler; | ||||||
|     const DstValue *sm = opts.sourcemap; |     const Dst *sm = opts.sourcemap; | ||||||
|     DstSlot cond; |     DstSlot cond; | ||||||
|     int32_t condlocal, labelwt, labeld, labeljt, labelc, i; |     int32_t condlocal, labelwt, labeld, labeljt, labelc, i; | ||||||
|     int infinite = 0; |     int infinite = 0; | ||||||
| @@ -1016,7 +1016,7 @@ DstSlot dstc_while(DstFormOptions opts, int32_t argn, const DstValue *argv) { | |||||||
|  |  | ||||||
|     /* Compile body */ |     /* Compile body */ | ||||||
|     for (i = 1; i < argn; i++) { |     for (i = 1; i < argn; i++) { | ||||||
|         DstFormOptions subopts = dstc_getindex(opts, i + 1); |         DstFopts subopts = dstc_getindex(opts, i + 1); | ||||||
|         subopts.flags = DST_FOPTS_DROP; |         subopts.flags = DST_FOPTS_DROP; | ||||||
|         dstc_freeslot(c, dstc_value(subopts)); |         dstc_freeslot(c, dstc_value(subopts)); | ||||||
|     } |     } | ||||||
| @@ -1101,14 +1101,14 @@ static int32_t dstc_addfuncdef(DstCompiler *c, DstFuncDef *def) { | |||||||
|     return dst_v_count(scope->defs) - 1; |     return dst_v_count(scope->defs) - 1; | ||||||
| } | } | ||||||
|  |  | ||||||
| DstSlot dstc_fn(DstFormOptions opts, int32_t argn, const DstValue *argv) { | DstSlot dstc_fn(DstFopts opts, int32_t argn, const Dst *argv) { | ||||||
|     DstCompiler *c = opts.compiler; |     DstCompiler *c = opts.compiler; | ||||||
|     const DstValue *sm = opts.sourcemap; |     const Dst *sm = opts.sourcemap; | ||||||
|     DstFuncDef *def; |     DstFuncDef *def; | ||||||
|     DstSlot ret; |     DstSlot ret; | ||||||
|     int32_t paramcount, argi, parami, arity, localslot, defindex; |     int32_t paramcount, argi, parami, arity, localslot, defindex; | ||||||
|     const DstValue *params; |     const Dst *params; | ||||||
|     const DstValue *psm; |     const Dst *psm; | ||||||
|     int varargs = 0; |     int varargs = 0; | ||||||
|  |  | ||||||
|     if (argn < 2) { |     if (argn < 2) { | ||||||
| @@ -1131,7 +1131,7 @@ DstSlot dstc_fn(DstFormOptions opts, int32_t argn, const DstValue *argv) { | |||||||
|         psm = dst_sourcemap_index(sm, parami + 1); |         psm = dst_sourcemap_index(sm, parami + 1); | ||||||
|         int32_t i; |         int32_t i; | ||||||
|         for (i = 0; i < paramcount; i++) { |         for (i = 0; i < paramcount; i++) { | ||||||
|             const DstValue *psmi = dst_sourcemap_index(psm, i); |             const Dst *psmi = dst_sourcemap_index(psm, i); | ||||||
|             if (dst_checktype(params[i], DST_SYMBOL)) { |             if (dst_checktype(params[i], DST_SYMBOL)) { | ||||||
|                 DstSlot slot; |                 DstSlot slot; | ||||||
|                 /* Check for varargs */ |                 /* Check for varargs */ | ||||||
| @@ -1163,7 +1163,7 @@ DstSlot dstc_fn(DstFormOptions opts, int32_t argn, const DstValue *argv) { | |||||||
|     /* Compile function body */ |     /* Compile function body */ | ||||||
|     for (argi = parami + 1; argi < argn; argi++) { |     for (argi = parami + 1; argi < argn; argi++) { | ||||||
|         DstSlot s; |         DstSlot s; | ||||||
|         DstFormOptions subopts = dstc_getindex(opts, argi + 1); |         DstFopts subopts = dstc_getindex(opts, argi + 1); | ||||||
|         subopts.flags = argi == (argn - 1) ? DST_FOPTS_TAIL : DST_FOPTS_DROP; |         subopts.flags = argi == (argn - 1) ? DST_FOPTS_TAIL : DST_FOPTS_DROP; | ||||||
|         s = dstc_value(subopts); |         s = dstc_value(subopts); | ||||||
|         dstc_freeslot(c, s); |         dstc_freeslot(c, s); | ||||||
| @@ -1210,11 +1210,11 @@ static const DstSpecial dstc_specials[] = { | |||||||
| }; | }; | ||||||
|  |  | ||||||
| /* Compile a tuple */ | /* Compile a tuple */ | ||||||
| DstSlot dstc_tuple(DstFormOptions opts) { | DstSlot dstc_tuple(DstFopts opts) { | ||||||
|     DstSlot head; |     DstSlot head; | ||||||
|     DstFormOptions subopts; |     DstFopts subopts; | ||||||
|     DstCompiler *c = opts.compiler; |     DstCompiler *c = opts.compiler; | ||||||
|     const DstValue *tup = dst_unwrap_tuple(opts.x); |     const Dst *tup = dst_unwrap_tuple(opts.x); | ||||||
|     int headcompiled = 0; |     int headcompiled = 0; | ||||||
|     subopts = dstc_getindex(opts, 0); |     subopts = dstc_getindex(opts, 0); | ||||||
|     subopts.flags = DST_FUNCTION | DST_CFUNCTION; |     subopts.flags = DST_FUNCTION | DST_CFUNCTION; | ||||||
| @@ -1268,9 +1268,9 @@ DstSlot dstc_tuple(DstFormOptions opts) { | |||||||
|     } |     } | ||||||
| } | } | ||||||
|  |  | ||||||
| static DstSlot dstc_array(DstFormOptions opts) { | static DstSlot dstc_array(DstFopts opts) { | ||||||
|     DstCompiler *c = opts.compiler; |     DstCompiler *c = opts.compiler; | ||||||
|     const DstValue *sm = opts.sourcemap; |     const Dst *sm = opts.sourcemap; | ||||||
|     DstSlot ctor, retslot; |     DstSlot ctor, retslot; | ||||||
|     SlotMap *sms; |     SlotMap *sms; | ||||||
|     int32_t localindex; |     int32_t localindex; | ||||||
| @@ -1291,9 +1291,9 @@ static DstSlot dstc_array(DstFormOptions opts) { | |||||||
|     return retslot; |     return retslot; | ||||||
| } | } | ||||||
|  |  | ||||||
| static DstSlot dstc_tablector(DstFormOptions opts, DstCFunction cfun) { | static DstSlot dstc_tablector(DstFopts opts, DstCFunction cfun) { | ||||||
|     DstCompiler *c = opts.compiler; |     DstCompiler *c = opts.compiler; | ||||||
|     const DstValue *sm = opts.sourcemap; |     const Dst *sm = opts.sourcemap; | ||||||
|     DstSlot ctor, retslot; |     DstSlot ctor, retslot; | ||||||
|     SlotMap *sms; |     SlotMap *sms; | ||||||
|     int32_t localindex; |     int32_t localindex; | ||||||
| @@ -1315,7 +1315,7 @@ static DstSlot dstc_tablector(DstFormOptions opts, DstCFunction cfun) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Compile a single value */ | /* Compile a single value */ | ||||||
| DstSlot dstc_value(DstFormOptions opts) { | DstSlot dstc_value(DstFopts opts) { | ||||||
|     DstSlot ret; |     DstSlot ret; | ||||||
|     if (dstc_iserr(&opts)) { |     if (dstc_iserr(&opts)) { | ||||||
|         return dstc_cslot(dst_wrap_nil()); |         return dstc_cslot(dst_wrap_nil()); | ||||||
| @@ -1356,7 +1356,7 @@ DstSlot dstc_value(DstFormOptions opts) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Initialize a compiler */ | /* Initialize a compiler */ | ||||||
| static void dstc_init(DstCompiler *c, DstValue env) { | static void dstc_init(DstCompiler *c, Dst env) { | ||||||
|     c->scopes = NULL; |     c->scopes = NULL; | ||||||
|     c->buffer = NULL; |     c->buffer = NULL; | ||||||
|     c->mapbuffer = NULL; |     c->mapbuffer = NULL; | ||||||
| @@ -1382,7 +1382,7 @@ static void dstc_deinit(DstCompiler *c) { | |||||||
| /* Compile a form. */ | /* Compile a form. */ | ||||||
| DstCompileResult dst_compile(DstCompileOptions opts) { | DstCompileResult dst_compile(DstCompileOptions opts) { | ||||||
|     DstCompiler c; |     DstCompiler c; | ||||||
|     DstFormOptions fopts; |     DstFopts fopts; | ||||||
|     DstSlot s; |     DstSlot s; | ||||||
|  |  | ||||||
|     dstc_init(&c, opts.env); |     dstc_init(&c, opts.env); | ||||||
|   | |||||||
| @@ -33,7 +33,7 @@ typedef struct FormOptions FormOptions; | |||||||
| typedef struct SlotTracker SlotTracker; | typedef struct SlotTracker SlotTracker; | ||||||
| typedef struct DstScope DstScope; | typedef struct DstScope DstScope; | ||||||
| typedef struct DstSlot DstSlot; | typedef struct DstSlot DstSlot; | ||||||
| typedef struct DstFormOptions DstFormOptions; | typedef struct DstFopts DstFopts; | ||||||
| typedef struct DstCFunctionOptimizer DstCFunctionOptimizer; | typedef struct DstCFunctionOptimizer DstCFunctionOptimizer; | ||||||
|  |  | ||||||
| #define DST_SLOT_CONSTANT 0x10000 | #define DST_SLOT_CONSTANT 0x10000 | ||||||
| @@ -50,7 +50,7 @@ struct DstSlot { | |||||||
|     int32_t index; |     int32_t index; | ||||||
|     int32_t envindex; /* 0 is local, positive number is an upvalue */ |     int32_t envindex; /* 0 is local, positive number is an upvalue */ | ||||||
|     uint32_t flags; |     uint32_t flags; | ||||||
|     DstValue constant; /* If the slot has a constant value */ |     Dst constant; /* If the slot has a constant value */ | ||||||
| }; | }; | ||||||
|  |  | ||||||
| /* Special forms that need support */ | /* Special forms that need support */ | ||||||
| @@ -80,7 +80,7 @@ typedef struct SymPair { | |||||||
| struct DstScope { | struct DstScope { | ||||||
|  |  | ||||||
|     /* Constants for this funcdef */ |     /* Constants for this funcdef */ | ||||||
|     DstValue *consts; |     Dst *consts; | ||||||
|  |  | ||||||
|     /* Map of symbols to slots. Use a simple linear scan for symbols. */ |     /* Map of symbols to slots. Use a simple linear scan for symbols. */ | ||||||
|     SymPair *syms; |     SymPair *syms; | ||||||
| @@ -110,7 +110,7 @@ struct DstCompiler { | |||||||
|     int32_t *mapbuffer; |     int32_t *mapbuffer; | ||||||
|  |  | ||||||
|     /* Hold the environment */ |     /* Hold the environment */ | ||||||
|     DstValue env; |     Dst env; | ||||||
|  |  | ||||||
|     DstCompileResult result; |     DstCompileResult result; | ||||||
| }; | }; | ||||||
| @@ -120,10 +120,10 @@ struct DstCompiler { | |||||||
| #define DST_FOPTS_DROP 0x40000 | #define DST_FOPTS_DROP 0x40000 | ||||||
|  |  | ||||||
| /* Options for compiling a single form */ | /* Options for compiling a single form */ | ||||||
| struct DstFormOptions { | struct DstFopts { | ||||||
|     DstCompiler *compiler; |     DstCompiler *compiler; | ||||||
|     DstValue x; |     Dst x; | ||||||
|     const DstValue *sourcemap; |     const Dst *sourcemap; | ||||||
|     uint32_t flags; /* bit set of accepted primitive types */ |     uint32_t flags; /* bit set of accepted primitive types */ | ||||||
|     DstSlot hint; |     DstSlot hint; | ||||||
| }; | }; | ||||||
| @@ -133,40 +133,40 @@ struct DstFormOptions { | |||||||
|  * optimizations should be tried before compiling a normal function call. */ |  * optimizations should be tried before compiling a normal function call. */ | ||||||
| struct DstCFunctionOptimizer { | struct DstCFunctionOptimizer { | ||||||
|     DstCFunction cfun; |     DstCFunction cfun; | ||||||
|     DstSlot (*optimize)(DstFormOptions opts, int32_t argn, const DstValue *argv); |     DstSlot (*optimize)(DstFopts opts, int32_t argn, const Dst *argv); | ||||||
| }; | }; | ||||||
| typedef struct DstSpecial { | typedef struct DstSpecial { | ||||||
|     const char *name; |     const char *name; | ||||||
|     DstSlot (*compile)(DstFormOptions opts, int32_t argn, const DstValue *argv); |     DstSlot (*compile)(DstFopts opts, int32_t argn, const Dst *argv); | ||||||
| } DstSpecial; | } DstSpecial; | ||||||
|  |  | ||||||
| /* An array of optimizers sorted by key */ | /* An array of optimizers sorted by key */ | ||||||
| extern DstCFunctionOptimizer dstcr_optimizers[255]; | extern DstCFunctionOptimizer dstcr_optimizers[255]; | ||||||
|  |  | ||||||
| /* Dispatch to correct form compiler */ | /* Dispatch to correct form compiler */ | ||||||
| DstSlot dstc_value(DstFormOptions opts); | DstSlot dstc_value(DstFopts opts); | ||||||
|  |  | ||||||
| /****************************************************/ | /****************************************************/ | ||||||
|  |  | ||||||
| void dstc_error(DstCompiler *c, const DstValue *sourcemap, const uint8_t *m); | void dstc_error(DstCompiler *c, const Dst *sourcemap, const uint8_t *m); | ||||||
| void dstc_cerror(DstCompiler *c, const DstValue *sourcemap, const char *m); | void dstc_cerror(DstCompiler *c, const Dst *sourcemap, const char *m); | ||||||
|  |  | ||||||
| /* Use these to get sub options. They will traverse the source map so | /* Use these to get sub options. They will traverse the source map so | ||||||
|  * compiler errors make sense. Then modify the returned options. */ |  * compiler errors make sense. Then modify the returned options. */ | ||||||
| DstFormOptions dstc_getindex(DstFormOptions opts, int32_t index); | DstFopts dstc_getindex(DstFopts opts, int32_t index); | ||||||
| DstFormOptions dstc_getkey(DstFormOptions opts, DstValue key); | DstFopts dstc_getkey(DstFopts opts, Dst key); | ||||||
| DstFormOptions dstc_getvalue(DstFormOptions opts, DstValue key); | DstFopts dstc_getvalue(DstFopts opts, Dst key); | ||||||
|  |  | ||||||
| void dstc_scope(DstCompiler *c, int newfn); | void dstc_scope(DstCompiler *c, int newfn); | ||||||
| void dstc_popscope(DstCompiler *c); | void dstc_popscope(DstCompiler *c); | ||||||
|  |  | ||||||
| DstSlot dstc_cslot(DstValue x); | DstSlot dstc_cslot(Dst x); | ||||||
| void dstc_freeslot(DstCompiler *c, DstSlot slot); | void dstc_freeslot(DstCompiler *c, DstSlot slot); | ||||||
|  |  | ||||||
| /* Search for a symbol */ | /* Search for a symbol */ | ||||||
| DstSlot dstc_resolve(DstCompiler *c, const DstValue *sourcemap, const uint8_t *sym); | DstSlot dstc_resolve(DstCompiler *c, const Dst *sourcemap, const uint8_t *sym); | ||||||
|  |  | ||||||
| /* Emit instructions. */ | /* Emit instructions. */ | ||||||
| void dstc_emit(DstCompiler *c, const DstValue *sourcemap, uint32_t instr); | void dstc_emit(DstCompiler *c, const Dst *sourcemap, uint32_t instr); | ||||||
|  |  | ||||||
| #endif | #endif | ||||||
|   | |||||||
							
								
								
									
										24
									
								
								core/fiber.c
									
									
									
									
									
								
							
							
						
						
									
										24
									
								
								core/fiber.c
									
									
									
									
									
								
							| @@ -28,7 +28,7 @@ DstFiber *dst_fiber(int32_t capacity) { | |||||||
|     DstFiber *fiber = dst_gcalloc(DST_MEMORY_FIBER, sizeof(DstFiber)); |     DstFiber *fiber = dst_gcalloc(DST_MEMORY_FIBER, sizeof(DstFiber)); | ||||||
|     fiber->capacity = capacity; |     fiber->capacity = capacity; | ||||||
|     if (capacity) { |     if (capacity) { | ||||||
|         DstValue *data = malloc(sizeof(DstValue) * capacity); |         Dst *data = malloc(sizeof(Dst) * capacity); | ||||||
|         if (NULL == data) { |         if (NULL == data) { | ||||||
|             DST_OUT_OF_MEMORY; |             DST_OUT_OF_MEMORY; | ||||||
|         } |         } | ||||||
| @@ -52,7 +52,7 @@ DstFiber *dst_fiber_reset(DstFiber *fiber) { | |||||||
|  |  | ||||||
| /* Ensure that the fiber has enough extra capacity */ | /* Ensure that the fiber has enough extra capacity */ | ||||||
| void dst_fiber_setcapacity(DstFiber *fiber, int32_t n) { | void dst_fiber_setcapacity(DstFiber *fiber, int32_t n) { | ||||||
|     DstValue *newData = realloc(fiber->data, sizeof(DstValue) * n); |     Dst *newData = realloc(fiber->data, sizeof(Dst) * n); | ||||||
|     if (NULL == newData) { |     if (NULL == newData) { | ||||||
|         DST_OUT_OF_MEMORY; |         DST_OUT_OF_MEMORY; | ||||||
|     } |     } | ||||||
| @@ -61,7 +61,7 @@ void dst_fiber_setcapacity(DstFiber *fiber, int32_t n) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Push a value on the next stack frame */ | /* Push a value on the next stack frame */ | ||||||
| void dst_fiber_push(DstFiber *fiber, DstValue x) { | void dst_fiber_push(DstFiber *fiber, Dst x) { | ||||||
|     if (fiber->stacktop >= fiber->capacity) { |     if (fiber->stacktop >= fiber->capacity) { | ||||||
|         dst_fiber_setcapacity(fiber, 2 * fiber->stacktop); |         dst_fiber_setcapacity(fiber, 2 * fiber->stacktop); | ||||||
|     } |     } | ||||||
| @@ -69,7 +69,7 @@ void dst_fiber_push(DstFiber *fiber, DstValue x) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Push 2 values on the next stack frame */ | /* Push 2 values on the next stack frame */ | ||||||
| void dst_fiber_push2(DstFiber *fiber, DstValue x, DstValue y) { | void dst_fiber_push2(DstFiber *fiber, Dst x, Dst y) { | ||||||
|     int32_t newtop = fiber->stacktop + 2; |     int32_t newtop = fiber->stacktop + 2; | ||||||
|     if (newtop > fiber->capacity) { |     if (newtop > fiber->capacity) { | ||||||
|         dst_fiber_setcapacity(fiber, 2 * newtop); |         dst_fiber_setcapacity(fiber, 2 * newtop); | ||||||
| @@ -80,7 +80,7 @@ void dst_fiber_push2(DstFiber *fiber, DstValue x, DstValue y) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Push 3 values on the next stack frame */ | /* Push 3 values on the next stack frame */ | ||||||
| void dst_fiber_push3(DstFiber *fiber, DstValue x, DstValue y, DstValue z) { | void dst_fiber_push3(DstFiber *fiber, Dst x, Dst y, Dst z) { | ||||||
|     int32_t newtop = fiber->stacktop + 3; |     int32_t newtop = fiber->stacktop + 3; | ||||||
|     if (newtop > fiber->capacity) { |     if (newtop > fiber->capacity) { | ||||||
|         dst_fiber_setcapacity(fiber, 2 * newtop); |         dst_fiber_setcapacity(fiber, 2 * newtop); | ||||||
| @@ -92,12 +92,12 @@ void dst_fiber_push3(DstFiber *fiber, DstValue x, DstValue y, DstValue z) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Push an array on the next stack frame */ | /* Push an array on the next stack frame */ | ||||||
| void dst_fiber_pushn(DstFiber *fiber, const DstValue *arr, int32_t n) { | void dst_fiber_pushn(DstFiber *fiber, const Dst *arr, int32_t n) { | ||||||
|     int32_t newtop = fiber->stacktop + n; |     int32_t newtop = fiber->stacktop + n; | ||||||
|     if (newtop > fiber->capacity) { |     if (newtop > fiber->capacity) { | ||||||
|         dst_fiber_setcapacity(fiber, 2 * newtop); |         dst_fiber_setcapacity(fiber, 2 * newtop); | ||||||
|     } |     } | ||||||
|     memcpy(fiber->data + fiber->stacktop, arr, n * sizeof(DstValue)); |     memcpy(fiber->data + fiber->stacktop, arr, n * sizeof(Dst)); | ||||||
|     fiber->stacktop = newtop; |     fiber->stacktop = newtop; | ||||||
| } | } | ||||||
|  |  | ||||||
| @@ -163,8 +163,8 @@ static void dst_function_detach(DstFunction *func) { | |||||||
|     /* Check for closure environment */ |     /* Check for closure environment */ | ||||||
|     if (NULL != func->envs && NULL != func->envs[0]) { |     if (NULL != func->envs && NULL != func->envs[0]) { | ||||||
|         DstFuncEnv *env = func->envs[0]; |         DstFuncEnv *env = func->envs[0]; | ||||||
|         size_t s = sizeof(DstValue) * env->length; |         size_t s = sizeof(Dst) * env->length; | ||||||
|         DstValue *vmem = malloc(s); |         Dst *vmem = malloc(s); | ||||||
|         if (NULL == vmem) { |         if (NULL == vmem) { | ||||||
|             DST_OUT_OF_MEMORY; |             DST_OUT_OF_MEMORY; | ||||||
|         } |         } | ||||||
| @@ -185,14 +185,14 @@ void dst_fiber_funcframe_tail(DstFiber *fiber, DstFunction *func) { | |||||||
|         dst_fiber_setcapacity(fiber, 2 * nextstacktop); |         dst_fiber_setcapacity(fiber, 2 * nextstacktop); | ||||||
|     } |     } | ||||||
|  |  | ||||||
|     DstValue *stack = fiber->data + fiber->frame; |     Dst *stack = fiber->data + fiber->frame; | ||||||
|     DstValue *args = fiber->data + fiber->stackstart; |     Dst *args = fiber->data + fiber->stackstart; | ||||||
|  |  | ||||||
|     /* Detatch old function */ |     /* Detatch old function */ | ||||||
|     if (NULL != dst_fiber_frame(fiber)->func) |     if (NULL != dst_fiber_frame(fiber)->func) | ||||||
|         dst_function_detach(dst_fiber_frame(fiber)->func); |         dst_function_detach(dst_fiber_frame(fiber)->func); | ||||||
|  |  | ||||||
|     memmove(stack, args, stacksize * sizeof(DstValue)); |     memmove(stack, args, stacksize * sizeof(Dst)); | ||||||
|  |  | ||||||
|     /* Set stack stuff */ |     /* Set stack stuff */ | ||||||
|     fiber->stacktop = fiber->stackstart = nextstacktop; |     fiber->stacktop = fiber->stackstart = nextstacktop; | ||||||
|   | |||||||
							
								
								
									
										28
									
								
								core/gc.c
									
									
									
									
									
								
							
							
						
						
									
										28
									
								
								core/gc.c
									
									
									
									
									
								
							| @@ -30,7 +30,7 @@ uint32_t dst_vm_gc_interval; | |||||||
| uint32_t dst_vm_next_collection; | uint32_t dst_vm_next_collection; | ||||||
|  |  | ||||||
| /* Roots */ | /* Roots */ | ||||||
| DstValue *dst_vm_roots; | Dst *dst_vm_roots; | ||||||
| uint32_t dst_vm_root_count; | uint32_t dst_vm_root_count; | ||||||
| uint32_t dst_vm_root_capacity; | uint32_t dst_vm_root_capacity; | ||||||
|  |  | ||||||
| @@ -41,14 +41,14 @@ static void dst_mark_function(DstFunction *func); | |||||||
| static void dst_mark_array(DstArray *array); | static void dst_mark_array(DstArray *array); | ||||||
| static void dst_mark_table(DstTable *table); | static void dst_mark_table(DstTable *table); | ||||||
| static void dst_mark_struct(const DstKV *st); | static void dst_mark_struct(const DstKV *st); | ||||||
| static void dst_mark_tuple(const DstValue *tuple); | static void dst_mark_tuple(const Dst *tuple); | ||||||
| static void dst_mark_buffer(DstBuffer *buffer); | static void dst_mark_buffer(DstBuffer *buffer); | ||||||
| static void dst_mark_string(const uint8_t *str); | static void dst_mark_string(const uint8_t *str); | ||||||
| static void dst_mark_fiber(DstFiber *fiber); | static void dst_mark_fiber(DstFiber *fiber); | ||||||
| static void dst_mark_abstract(void *adata); | static void dst_mark_abstract(void *adata); | ||||||
|  |  | ||||||
| /* Mark a value */ | /* Mark a value */ | ||||||
| void dst_mark(DstValue x) { | void dst_mark(Dst x) { | ||||||
|     switch (dst_type(x)) { |     switch (dst_type(x)) { | ||||||
|         default: break; |         default: break; | ||||||
|         case DST_STRING: |         case DST_STRING: | ||||||
| @@ -77,8 +77,8 @@ static void dst_mark_abstract(void *adata) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Mark a bunch of items in memory */ | /* Mark a bunch of items in memory */ | ||||||
| static void dst_mark_many(const DstValue *values, int32_t n) { | static void dst_mark_many(const Dst *values, int32_t n) { | ||||||
|     const DstValue *end = values + n; |     const Dst *end = values + n; | ||||||
|     while (values < end) { |     while (values < end) { | ||||||
|         dst_mark(*values); |         dst_mark(*values); | ||||||
|         values += 1; |         values += 1; | ||||||
| @@ -116,7 +116,7 @@ static void dst_mark_struct(const DstKV *st) { | |||||||
|     dst_mark_kvs(st, dst_struct_capacity(st)); |     dst_mark_kvs(st, dst_struct_capacity(st)); | ||||||
| } | } | ||||||
|  |  | ||||||
| static void dst_mark_tuple(const DstValue *tuple) { | static void dst_mark_tuple(const Dst *tuple) { | ||||||
|     if (dst_gc_reachable(dst_tuple_raw(tuple))) |     if (dst_gc_reachable(dst_tuple_raw(tuple))) | ||||||
|         return; |         return; | ||||||
|     dst_gc_mark(dst_tuple_raw(tuple)); |     dst_gc_mark(dst_tuple_raw(tuple)); | ||||||
| @@ -305,11 +305,11 @@ void dst_collect() { | |||||||
| /* Add a root value to the GC. This prevents the GC from removing a value | /* Add a root value to the GC. This prevents the GC from removing a value | ||||||
|  * and all of its children. If gcroot is called on a value n times, unroot |  * and all of its children. If gcroot is called on a value n times, unroot | ||||||
|  * must also be called n times to remove it as a gc root. */ |  * must also be called n times to remove it as a gc root. */ | ||||||
| void dst_gcroot(DstValue root) { | void dst_gcroot(Dst root) { | ||||||
|     uint32_t newcount = dst_vm_root_count + 1; |     uint32_t newcount = dst_vm_root_count + 1; | ||||||
|     if (newcount > dst_vm_root_capacity) { |     if (newcount > dst_vm_root_capacity) { | ||||||
|         uint32_t newcap = 2 * newcount; |         uint32_t newcap = 2 * newcount; | ||||||
|         dst_vm_roots = realloc(dst_vm_roots, sizeof(DstValue) * newcap); |         dst_vm_roots = realloc(dst_vm_roots, sizeof(Dst) * newcap); | ||||||
|         if (NULL == dst_vm_roots) { |         if (NULL == dst_vm_roots) { | ||||||
|             DST_OUT_OF_MEMORY; |             DST_OUT_OF_MEMORY; | ||||||
|         } |         } | ||||||
| @@ -321,9 +321,9 @@ void dst_gcroot(DstValue root) { | |||||||
|  |  | ||||||
| /* Remove a root value from the GC. This allows the gc to potentially reclaim | /* Remove a root value from the GC. This allows the gc to potentially reclaim | ||||||
|  * a value and all its children. */ |  * a value and all its children. */ | ||||||
| int dst_gcunroot(DstValue root) { | int dst_gcunroot(Dst root) { | ||||||
|     DstValue *vtop = dst_vm_roots + dst_vm_root_count; |     Dst *vtop = dst_vm_roots + dst_vm_root_count; | ||||||
|     DstValue *v = dst_vm_roots; |     Dst *v = dst_vm_roots; | ||||||
|     /* Search from top to bottom as access is most likely LIFO */ |     /* Search from top to bottom as access is most likely LIFO */ | ||||||
|     for (v = dst_vm_roots; v < vtop; v++) { |     for (v = dst_vm_roots; v < vtop; v++) { | ||||||
|         if (dst_equals(root, *v)) { |         if (dst_equals(root, *v)) { | ||||||
| @@ -335,9 +335,9 @@ int dst_gcunroot(DstValue root) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Remove a root value from the GC. This sets the effective reference count to 0. */ | /* Remove a root value from the GC. This sets the effective reference count to 0. */ | ||||||
| int dst_gcunrootall(DstValue root) { | int dst_gcunrootall(Dst root) { | ||||||
|     DstValue *vtop = dst_vm_roots + dst_vm_root_count; |     Dst *vtop = dst_vm_roots + dst_vm_root_count; | ||||||
|     DstValue *v = dst_vm_roots; |     Dst *v = dst_vm_roots; | ||||||
|     int ret = 0; |     int ret = 0; | ||||||
|     /* Search from top to bottom as access is most likely LIFO */ |     /* Search from top to bottom as access is most likely LIFO */ | ||||||
|     for (v = dst_vm_roots; v < vtop; v++) { |     for (v = dst_vm_roots; v < vtop; v++) { | ||||||
|   | |||||||
							
								
								
									
										82
									
								
								core/io.c
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										82
									
								
								core/io.c
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,82 @@ | |||||||
|  |  | ||||||
|  | DstAbstractType dst_stl_filetype = { | ||||||
|  |     "stl.file", | ||||||
|  |     NULL, | ||||||
|  |     NULL, | ||||||
|  |     NULL | ||||||
|  | }; | ||||||
|  |  | ||||||
|  | /* Open a a file and return a userdata wrapper arounf the C file API. */ | ||||||
|  | int dst_stl_open(int32_t argn, Dst *argv, Dst *ret) { | ||||||
|  |     if (argn < 2) { | ||||||
|  |         *ret = dst_cstringv("expected at least 2 arguments"); | ||||||
|  |         return 1; | ||||||
|  |     } | ||||||
|  |     const uint8_t *fname = dst_to_string(argv[0]); | ||||||
|  |     const uint8_t *fmode = dst_to_string(argv[1]); | ||||||
|  |     FILE *f; | ||||||
|  |     FILE **fp; | ||||||
|  |     f = fopen((const char *)fname, (const char *)fmode); | ||||||
|  |     if (!f) | ||||||
|  |         dst_c_throwc(vm, "could not open file"); | ||||||
|  |     fp = dst_userdata(vm, sizeof(FILE *), &dst_stl_filetype); | ||||||
|  |     *fp = f; | ||||||
|  |     dst_c_return(vm, dst_wrap_userdata(fp)); | ||||||
|  | } | ||||||
|  |  | ||||||
|  | /* Read an entire file into memory */ | ||||||
|  | int dst_stl_slurp(Dst *vm) { | ||||||
|  |     DstBuffer *b; | ||||||
|  |     long fsize; | ||||||
|  |     FILE *f; | ||||||
|  |     FILE **fp = dst_check_userdata(vm, 0, &dst_stl_filetype); | ||||||
|  |     if (fp == NULL) dst_c_throwc(vm, "expected file"); | ||||||
|  |     if (!dst_check_buffer(vm, 1, &b)) b = dst_buffer(vm, 10); | ||||||
|  |     f = *fp; | ||||||
|  |     /* Read whole file */ | ||||||
|  |     fseek(f, 0, SEEK_END); | ||||||
|  |     fsize = ftell(f); | ||||||
|  |     fseek(f, 0, SEEK_SET); | ||||||
|  |     /* Ensure buffer size */ | ||||||
|  |     dst_buffer_ensure(vm, b, b->count + fsize); | ||||||
|  |     fread((char *)(b->data + b->count), fsize, 1, f); | ||||||
|  |     b->count += fsize; | ||||||
|  |     dst_c_return(vm, dst_wrap_buffer(b)); | ||||||
|  | } | ||||||
|  |  | ||||||
|  | /* Read a certain number of bytes into memory */ | ||||||
|  | int dst_stl_read(Dst *vm) { | ||||||
|  |     DstBuffer *b; | ||||||
|  |     FILE *f; | ||||||
|  |     int64_t len; | ||||||
|  |     FILE **fp = dst_check_userdata(vm, 0, &dst_stl_filetype); | ||||||
|  |     if (fp == NULL) dst_c_throwc(vm, "expected file"); | ||||||
|  |     if (!(dst_check_integer(vm, 1, &len))) dst_c_throwc(vm, "expected integer"); | ||||||
|  |     if (!dst_check_buffer(vm, 2, &b)) b = dst_buffer(vm, 10); | ||||||
|  |     f = *fp; | ||||||
|  |     /* Ensure buffer size */ | ||||||
|  |     dst_buffer_ensure(vm, b, b->count + len); | ||||||
|  |     b->count += fread((char *)(b->data + b->count), len, 1, f) * len; | ||||||
|  |     dst_c_return(vm, dst_wrap_buffer(b)); | ||||||
|  | } | ||||||
|  |  | ||||||
|  | /* Write bytes to a file */ | ||||||
|  | int dst_stl_write(Dst *vm) { | ||||||
|  |     FILE *f; | ||||||
|  |     const uint8_t *data; | ||||||
|  |     uint32_t len; | ||||||
|  |     FILE **fp = dst_check_userdata(vm, 0, &dst_stl_filetype); | ||||||
|  |     if (fp == NULL) dst_c_throwc(vm, "expected file"); | ||||||
|  |     if (!dst_chararray_view(dst_arg(vm, 1), &data, &len)) dst_c_throwc(vm, "expected string|buffer"); | ||||||
|  |     f = *fp; | ||||||
|  |     fwrite(data, len, 1, f); | ||||||
|  |     return DST_RETURN_OK; | ||||||
|  | } | ||||||
|  |  | ||||||
|  | /* Close a file */ | ||||||
|  | int dst_stl_close(Dst *vm) { | ||||||
|  |     FILE **fp = dst_check_userdata(vm, 0, &dst_stl_filetype); | ||||||
|  |     if (fp == NULL) dst_c_throwc(vm, "expected file"); | ||||||
|  |     fclose(*fp); | ||||||
|  |     dst_c_return(vm, dst_wrap_nil()); | ||||||
|  | } | ||||||
							
								
								
									
										36
									
								
								core/math.c
									
									
									
									
									
								
							
							
						
						
									
										36
									
								
								core/math.c
									
									
									
									
									
								
							| @@ -24,7 +24,7 @@ | |||||||
| #include <math.h> | #include <math.h> | ||||||
|  |  | ||||||
| /* Convert a number to an integer */ | /* Convert a number to an integer */ | ||||||
| int dst_int(int32_t argn, DstValue *argv, DstValue *ret) { | int dst_int(int32_t argn, Dst *argv, Dst *ret) { | ||||||
|     if (argn != 1) { |     if (argn != 1) { | ||||||
|         *ret = dst_cstringv("expected 1 argument"); |         *ret = dst_cstringv("expected 1 argument"); | ||||||
|         return 1; |         return 1; | ||||||
| @@ -44,7 +44,7 @@ int dst_int(int32_t argn, DstValue *argv, DstValue *ret) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Convert a number to a real number */ | /* Convert a number to a real number */ | ||||||
| int dst_real(int32_t argn, DstValue *argv, DstValue *ret) { | int dst_real(int32_t argn, Dst *argv, Dst *ret) { | ||||||
|     if (argn != 1) { |     if (argn != 1) { | ||||||
|         *ret = dst_cstringv("expected 1 argument"); |         *ret = dst_cstringv("expected 1 argument"); | ||||||
|         return 1; |         return 1; | ||||||
| @@ -70,7 +70,7 @@ int dst_real(int32_t argn, DstValue *argv, DstValue *ret) { | |||||||
| #define DIV(x, y) ((x) / (y)) | #define DIV(x, y) ((x) / (y)) | ||||||
|  |  | ||||||
| #define DST_DEFINE_BINOP(name, op, rop, onerr)\ | #define DST_DEFINE_BINOP(name, op, rop, onerr)\ | ||||||
| DstValue dst_op_##name(DstValue lhs, DstValue rhs) {\ | Dst dst_op_##name(Dst lhs, Dst rhs) {\ | ||||||
|     if (!(dst_checktype(lhs, DST_INTEGER) || dst_checktype(lhs, DST_REAL))) onerr;\ |     if (!(dst_checktype(lhs, DST_INTEGER) || dst_checktype(lhs, DST_REAL))) onerr;\ | ||||||
|     if (!(dst_checktype(rhs, DST_INTEGER) || dst_checktype(rhs, DST_REAL))) onerr;\ |     if (!(dst_checktype(rhs, DST_INTEGER) || dst_checktype(rhs, DST_REAL))) onerr;\ | ||||||
|     return dst_checktype(lhs, DST_INTEGER)\ |     return dst_checktype(lhs, DST_INTEGER)\ | ||||||
| @@ -87,7 +87,7 @@ DST_DEFINE_BINOP(subtract, SUB, SUB, return dst_wrap_nil()) | |||||||
| DST_DEFINE_BINOP(multiply, MUL, MUL, return dst_wrap_nil()) | DST_DEFINE_BINOP(multiply, MUL, MUL, return dst_wrap_nil()) | ||||||
|  |  | ||||||
| #define DST_DEFINE_DIVIDER_OP(name, op, rop)\ | #define DST_DEFINE_DIVIDER_OP(name, op, rop)\ | ||||||
| DstValue dst_op_##name(DstValue lhs, DstValue rhs) {\ | Dst dst_op_##name(Dst lhs, Dst rhs) {\ | ||||||
|     if (!(dst_checktype(lhs, DST_INTEGER) || dst_checktype(lhs, DST_REAL))) return dst_wrap_nil();\ |     if (!(dst_checktype(lhs, DST_INTEGER) || dst_checktype(lhs, DST_REAL))) return dst_wrap_nil();\ | ||||||
|     if (!(dst_checktype(rhs, DST_INTEGER) || dst_checktype(rhs, DST_REAL))) return dst_wrap_nil();\ |     if (!(dst_checktype(rhs, DST_INTEGER) || dst_checktype(rhs, DST_REAL))) return dst_wrap_nil();\ | ||||||
|     return dst_checktype(lhs, DST_INTEGER)\ |     return dst_checktype(lhs, DST_INTEGER)\ | ||||||
| @@ -105,9 +105,9 @@ DST_DEFINE_DIVIDER_OP(divide, DIV, DIV) | |||||||
| DST_DEFINE_DIVIDER_OP(modulo, MOD, fmod) | DST_DEFINE_DIVIDER_OP(modulo, MOD, fmod) | ||||||
|  |  | ||||||
| #define DST_DEFINE_REDUCER(name, fop, start)\ | #define DST_DEFINE_REDUCER(name, fop, start)\ | ||||||
| int dst_##name(int32_t argn, DstValue *argv, DstValue *ret) {\ | int dst_##name(int32_t argn, Dst *argv, Dst *ret) {\ | ||||||
|     int32_t i;\ |     int32_t i;\ | ||||||
|     DstValue accum = dst_wrap_integer(start);\ |     Dst accum = dst_wrap_integer(start);\ | ||||||
|     for (i = 0; i < argn; i++) {\ |     for (i = 0; i < argn; i++) {\ | ||||||
|         accum = fop(accum, argv[i]);\ |         accum = fop(accum, argv[i]);\ | ||||||
|     }\ |     }\ | ||||||
| @@ -123,9 +123,9 @@ DST_DEFINE_REDUCER(add, dst_op_add, 0) | |||||||
| DST_DEFINE_REDUCER(multiply, dst_op_multiply, 1) | DST_DEFINE_REDUCER(multiply, dst_op_multiply, 1) | ||||||
|  |  | ||||||
| #define DST_DEFINE_DIVIDER(name, unarystart)\ | #define DST_DEFINE_DIVIDER(name, unarystart)\ | ||||||
| int dst_##name(int32_t argn, DstValue *argv, DstValue *ret) {\ | int dst_##name(int32_t argn, Dst *argv, Dst *ret) {\ | ||||||
|     int32_t i;\ |     int32_t i;\ | ||||||
|     DstValue accum;\ |     Dst accum;\ | ||||||
|     if (argn < 1) {\ |     if (argn < 1) {\ | ||||||
|         *ret = dst_cstringv("expected at least one argument");\ |         *ret = dst_cstringv("expected at least one argument");\ | ||||||
|         return 1;\ |         return 1;\ | ||||||
| @@ -157,7 +157,7 @@ DST_DEFINE_DIVIDER(subtract, 0) | |||||||
| #undef MOD | #undef MOD | ||||||
| #undef DST_DEFINE_BINOP | #undef DST_DEFINE_BINOP | ||||||
|  |  | ||||||
| int dst_bnot(int32_t argn, DstValue *argv, DstValue *ret) { | int dst_bnot(int32_t argn, Dst *argv, Dst *ret) { | ||||||
|     if (argn != 1) { |     if (argn != 1) { | ||||||
|         *ret = dst_cstringv("expected 1 argument"); |         *ret = dst_cstringv("expected 1 argument"); | ||||||
|         return 1; |         return 1; | ||||||
| @@ -171,11 +171,11 @@ int dst_bnot(int32_t argn, DstValue *argv, DstValue *ret) { | |||||||
| } | } | ||||||
|  |  | ||||||
| #define DST_DEFINE_BITOP(name, op, start)\ | #define DST_DEFINE_BITOP(name, op, start)\ | ||||||
| int dst_##name(int32_t argn, DstValue *argv, DstValue *ret) {\ | int dst_##name(int32_t argn, Dst *argv, Dst *ret) {\ | ||||||
|     int32_t i;\ |     int32_t i;\ | ||||||
|     int32_t accum = start;\ |     int32_t accum = start;\ | ||||||
|     for (i = 0; i < argn; i++) {\ |     for (i = 0; i < argn; i++) {\ | ||||||
|         DstValue arg = argv[i];\ |         Dst arg = argv[i];\ | ||||||
|         if (!dst_checktype(arg, DST_INTEGER)) {\ |         if (!dst_checktype(arg, DST_INTEGER)) {\ | ||||||
|             *ret = dst_cstringv("expected integer");\ |             *ret = dst_cstringv("expected integer");\ | ||||||
|             return -1;\ |             return -1;\ | ||||||
| @@ -190,7 +190,7 @@ DST_DEFINE_BITOP(band, &=, -1) | |||||||
| DST_DEFINE_BITOP(bor, |=, 0) | DST_DEFINE_BITOP(bor, |=, 0) | ||||||
| DST_DEFINE_BITOP(bxor, ^=, 0) | DST_DEFINE_BITOP(bxor, ^=, 0) | ||||||
|  |  | ||||||
| int dst_lshift(int argn, DstValue *argv, DstValue *ret) { | int dst_lshift(int argn, Dst *argv, Dst *ret) { | ||||||
|     if (argn != 2 || !dst_checktype(argv[0], DST_INTEGER) || !dst_checktype(argv[1], DST_INTEGER)) { |     if (argn != 2 || !dst_checktype(argv[0], DST_INTEGER) || !dst_checktype(argv[1], DST_INTEGER)) { | ||||||
|         *ret = dst_cstringv("expected 2 integers");  |         *ret = dst_cstringv("expected 2 integers");  | ||||||
|         return 1; |         return 1; | ||||||
| @@ -199,7 +199,7 @@ int dst_lshift(int argn, DstValue *argv, DstValue *ret) { | |||||||
|     return 0; |     return 0; | ||||||
| } | } | ||||||
|  |  | ||||||
| int dst_rshift(int argn, DstValue *argv, DstValue *ret) { | int dst_rshift(int argn, Dst *argv, Dst *ret) { | ||||||
|     if (argn != 2 || !dst_checktype(argv[0], DST_INTEGER) || !dst_checktype(argv[1], DST_INTEGER)) { |     if (argn != 2 || !dst_checktype(argv[0], DST_INTEGER) || !dst_checktype(argv[1], DST_INTEGER)) { | ||||||
|         *ret = dst_cstringv("expected 2 integers");  |         *ret = dst_cstringv("expected 2 integers");  | ||||||
|         return 1; |         return 1; | ||||||
| @@ -208,7 +208,7 @@ int dst_rshift(int argn, DstValue *argv, DstValue *ret) { | |||||||
|     return 0; |     return 0; | ||||||
| } | } | ||||||
|  |  | ||||||
| int dst_lshiftu(int argn, DstValue *argv, DstValue *ret) { | int dst_lshiftu(int argn, Dst *argv, Dst *ret) { | ||||||
|     if (argn != 2 || !dst_checktype(argv[0], DST_INTEGER) || !dst_checktype(argv[1], DST_INTEGER)) { |     if (argn != 2 || !dst_checktype(argv[0], DST_INTEGER) || !dst_checktype(argv[1], DST_INTEGER)) { | ||||||
|         *ret = dst_cstringv("expected 2 integers");  |         *ret = dst_cstringv("expected 2 integers");  | ||||||
|         return 1; |         return 1; | ||||||
| @@ -218,7 +218,7 @@ int dst_lshiftu(int argn, DstValue *argv, DstValue *ret) { | |||||||
| } | } | ||||||
|  |  | ||||||
| #define DST_DEFINE_MATHOP(name, fop)\ | #define DST_DEFINE_MATHOP(name, fop)\ | ||||||
| int dst_##name(int32_t argn, DstValue *argv, DstValue *ret) {\ | int dst_##name(int32_t argn, Dst *argv, Dst *ret) {\ | ||||||
|     if (argn != 1) {\ |     if (argn != 1) {\ | ||||||
|         *ret = dst_cstringv("expected 1 argument");\ |         *ret = dst_cstringv("expected 1 argument");\ | ||||||
|         return 1;\ |         return 1;\ | ||||||
| @@ -252,7 +252,7 @@ DST_DEFINE_MATHOP(fabs, fabs) | |||||||
| DST_DEFINE_MATHOP(floor, floor) | DST_DEFINE_MATHOP(floor, floor) | ||||||
|  |  | ||||||
| #define DST_DEFINE_MATH2OP(name, fop)\ | #define DST_DEFINE_MATH2OP(name, fop)\ | ||||||
| int dst_##name(int32_t argn, DstValue *argv, DstValue *ret) {\ | int dst_##name(int32_t argn, Dst *argv, Dst *ret) {\ | ||||||
|     if (argn != 2) {\ |     if (argn != 2) {\ | ||||||
|         *ret = dst_cstringv("expected 2 arguments");\ |         *ret = dst_cstringv("expected 2 arguments");\ | ||||||
|         return 1;\ |         return 1;\ | ||||||
| @@ -274,9 +274,9 @@ DST_DEFINE_MATH2OP(atan2, atan2) | |||||||
| DST_DEFINE_MATH2OP(pow, pow) | DST_DEFINE_MATH2OP(pow, pow) | ||||||
| DST_DEFINE_MATH2OP(fmod, fmod) | DST_DEFINE_MATH2OP(fmod, fmod) | ||||||
|  |  | ||||||
| int dst_modf(int32_t argn, DstValue *argv, DstValue *ret) { | int dst_modf(int32_t argn, Dst *argv, Dst *ret) { | ||||||
|     double intpart; |     double intpart; | ||||||
|     DstValue *tup; |     Dst *tup; | ||||||
|     if (argn != 1) { |     if (argn != 1) { | ||||||
|         *ret = dst_cstringv("expected 1 argument"); |         *ret = dst_cstringv("expected 1 argument"); | ||||||
|         return 1; |         return 1; | ||||||
|   | |||||||
							
								
								
									
										50
									
								
								core/parse.c
									
									
									
									
									
								
							
							
						
						
									
										50
									
								
								core/parse.c
									
									
									
									
									
								
							| @@ -34,8 +34,8 @@ static int check_str_const(const char *ref, const uint8_t *start, const uint8_t | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Quote a value */ | /* Quote a value */ | ||||||
| static DstValue quote(DstValue x) { | static Dst quote(Dst x) { | ||||||
|     DstValue *t = dst_tuple_begin(2); |     Dst *t = dst_tuple_begin(2); | ||||||
|     t[0] = dst_csymbolv("quote"); |     t[0] = dst_csymbolv("quote"); | ||||||
|     t[1] = x; |     t[1] = x; | ||||||
|     return dst_wrap_tuple(dst_tuple_end(t)); |     return dst_wrap_tuple(dst_tuple_end(t)); | ||||||
| @@ -98,9 +98,7 @@ static uint32_t symchars[256] = { | |||||||
| 	0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff | 	0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff | ||||||
| }; | }; | ||||||
|  |  | ||||||
| /* Check if a character is a valid symbol character */ | /* Check if a character is a valid symbol character | ||||||
| /* TODO - allow utf8 - shouldn't be difficult, err on side |  | ||||||
|  * of inclusivity |  | ||||||
|  * symbol chars are A-Z, a-z, 0-9, or one of !$&*+-./:<=>@\^_~| */ |  * symbol chars are A-Z, a-z, 0-9, or one of !$&*+-./:<=>@\^_~| */ | ||||||
| static int is_symbol_char(uint8_t c) { | static int is_symbol_char(uint8_t c) { | ||||||
|     return symchars[c >> 5] & (1 << (c & 0x1F)); |     return symchars[c >> 5] & (1 << (c & 0x1F)); | ||||||
| @@ -158,16 +156,16 @@ static int to_hex(uint8_t c) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Make source mapping for atom (non recursive structure) */ | /* Make source mapping for atom (non recursive structure) */ | ||||||
| static DstValue atom_map(int32_t start, int32_t end) { | static Dst atom_map(int32_t start, int32_t end) { | ||||||
|     DstValue *t = dst_tuple_begin(2); |     Dst *t = dst_tuple_begin(2); | ||||||
|     t[0] = dst_wrap_integer(start); |     t[0] = dst_wrap_integer(start); | ||||||
|     t[1] = dst_wrap_integer(end); |     t[1] = dst_wrap_integer(end); | ||||||
|     return dst_wrap_tuple(dst_tuple_end(t)); |     return dst_wrap_tuple(dst_tuple_end(t)); | ||||||
| } | } | ||||||
|  |  | ||||||
| /* Create mappingd for recursive data structure */ | /* Create mappingd for recursive data structure */ | ||||||
| static DstValue ds_map(int32_t start, int32_t end, DstValue submap) { | static Dst ds_map(int32_t start, int32_t end, Dst submap) { | ||||||
|     DstValue *t = dst_tuple_begin(3); |     Dst *t = dst_tuple_begin(3); | ||||||
|     t[0] = dst_wrap_integer(start); |     t[0] = dst_wrap_integer(start); | ||||||
|     t[1] = dst_wrap_integer(end); |     t[1] = dst_wrap_integer(end); | ||||||
|     t[2] = submap; |     t[2] = submap; | ||||||
| @@ -175,8 +173,8 @@ static DstValue ds_map(int32_t start, int32_t end, DstValue submap) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Create a sourcemapping for a key value pair */ | /* Create a sourcemapping for a key value pair */ | ||||||
| static DstValue kv_map(DstValue k, DstValue v) { | static Dst kv_map(Dst k, Dst v) { | ||||||
|     DstValue *t = dst_tuple_begin(2); |     Dst *t = dst_tuple_begin(2); | ||||||
|     t[0] = k; |     t[0] = k; | ||||||
|     t[1] = v; |     t[1] = v; | ||||||
|     return dst_wrap_tuple(dst_tuple_end(t)); |     return dst_wrap_tuple(dst_tuple_end(t)); | ||||||
| @@ -200,8 +198,8 @@ static const uint8_t *parse_recur( | |||||||
|     const uint8_t *end = args->end; |     const uint8_t *end = args->end; | ||||||
|     const uint8_t *mapstart; |     const uint8_t *mapstart; | ||||||
|     int32_t qcount = 0; |     int32_t qcount = 0; | ||||||
|     DstValue ret; |     Dst ret; | ||||||
|     DstValue submapping; |     Dst submapping; | ||||||
|  |  | ||||||
|     /* Prevent stack overflow */ |     /* Prevent stack overflow */ | ||||||
|     if (recur == 0) goto too_much_recur; |     if (recur == 0) goto too_much_recur; | ||||||
| @@ -238,7 +236,7 @@ static const uint8_t *parse_recur( | |||||||
|         atom: |         atom: | ||||||
|         { |         { | ||||||
|             int ascii = 1; |             int ascii = 1; | ||||||
|             DstValue numcheck; |             Dst numcheck; | ||||||
|             const uint8_t *tokenend = src; |             const uint8_t *tokenend = src; | ||||||
|             if (!is_symbol_char(*src)) goto unexpected_character; |             if (!is_symbol_char(*src)) goto unexpected_character; | ||||||
|             while (tokenend < end && is_symbol_char(*tokenend)) { |             while (tokenend < end && is_symbol_char(*tokenend)) { | ||||||
| @@ -373,8 +371,8 @@ static const uint8_t *parse_recur( | |||||||
|             switch (close) { |             switch (close) { | ||||||
|                 case ')': |                 case ')': | ||||||
|                 { |                 { | ||||||
|                     DstValue *tup = dst_tuple_begin(n); |                     Dst *tup = dst_tuple_begin(n); | ||||||
|                     DstValue *subtup = dst_tuple_begin(n); |                     Dst *subtup = dst_tuple_begin(n); | ||||||
|                     for (i = n; i > 0; i--) { |                     for (i = n; i > 0; i--) { | ||||||
|                         tup[i - 1] = dst_array_pop(&args->stack); |                         tup[i - 1] = dst_array_pop(&args->stack); | ||||||
|                         subtup[i - 1] = dst_array_pop(&args->mapstack); |                         subtup[i - 1] = dst_array_pop(&args->mapstack); | ||||||
| @@ -408,10 +406,10 @@ static const uint8_t *parse_recur( | |||||||
|                         DstTable *t = dst_table(n); |                         DstTable *t = dst_table(n); | ||||||
|                         DstTable *subt = dst_table(n); |                         DstTable *subt = dst_table(n); | ||||||
|                         for (i = n; i > 0; i -= 2) { |                         for (i = n; i > 0; i -= 2) { | ||||||
|                             DstValue val = dst_array_pop(&args->stack); |                             Dst val = dst_array_pop(&args->stack); | ||||||
|                             DstValue key = dst_array_pop(&args->stack); |                             Dst key = dst_array_pop(&args->stack); | ||||||
|                             DstValue subval = dst_array_pop(&args->mapstack); |                             Dst subval = dst_array_pop(&args->mapstack); | ||||||
|                             DstValue subkey = dst_array_pop(&args->mapstack); |                             Dst subkey = dst_array_pop(&args->mapstack); | ||||||
|  |  | ||||||
|                             dst_table_put(t, key, val); |                             dst_table_put(t, key, val); | ||||||
|                             dst_table_put(subt, key, kv_map(subkey, subval)); |                             dst_table_put(subt, key, kv_map(subkey, subval)); | ||||||
| @@ -422,10 +420,10 @@ static const uint8_t *parse_recur( | |||||||
|                         DstKV *st = dst_struct_begin(n >> 1); |                         DstKV *st = dst_struct_begin(n >> 1); | ||||||
|                         DstKV *subst = dst_struct_begin(n >> 1); |                         DstKV *subst = dst_struct_begin(n >> 1); | ||||||
|                         for (i = n; i > 0; i -= 2) { |                         for (i = n; i > 0; i -= 2) { | ||||||
|                             DstValue val = dst_array_pop(&args->stack); |                             Dst val = dst_array_pop(&args->stack); | ||||||
|                             DstValue key = dst_array_pop(&args->stack); |                             Dst key = dst_array_pop(&args->stack); | ||||||
|                             DstValue subval = dst_array_pop(&args->mapstack); |                             Dst subval = dst_array_pop(&args->mapstack); | ||||||
|                             DstValue subkey = dst_array_pop(&args->mapstack); |                             Dst subkey = dst_array_pop(&args->mapstack); | ||||||
|  |  | ||||||
|                             dst_struct_put(st, key, val); |                             dst_struct_put(st, key, val); | ||||||
|                             dst_struct_put(subst, key, kv_map(subkey, subval)); |                             dst_struct_put(subst, key, kv_map(subkey, subval)); | ||||||
| @@ -458,8 +456,8 @@ static const uint8_t *parse_recur( | |||||||
|     while (qcount--) { |     while (qcount--) { | ||||||
|         int32_t start = mapstart - args->srcstart; |         int32_t start = mapstart - args->srcstart; | ||||||
|         int32_t end = src - args->srcstart; |         int32_t end = src - args->srcstart; | ||||||
|         DstValue sourcemap = dst_array_pop(&args->mapstack); |         Dst sourcemap = dst_array_pop(&args->mapstack); | ||||||
|         DstValue* tup = dst_tuple_begin(2); |         Dst* tup = dst_tuple_begin(2); | ||||||
|         tup[0] = atom_map(start, end); |         tup[0] = atom_map(start, end); | ||||||
|         tup[1] = sourcemap; |         tup[1] = sourcemap; | ||||||
|         ret = quote(ret); |         ret = quote(ret); | ||||||
|   | |||||||
| @@ -25,14 +25,14 @@ | |||||||
|  |  | ||||||
| /* Get the sub source map by indexing a value. Used to traverse | /* Get the sub source map by indexing a value. Used to traverse | ||||||
|  * into arrays and tuples */ |  * into arrays and tuples */ | ||||||
| const DstValue *dst_sourcemap_index(const DstValue *map, int32_t index) { | const Dst *dst_sourcemap_index(const Dst *map, int32_t index) { | ||||||
|     if (NULL != map && dst_tuple_length(map) >= 3) { |     if (NULL != map && dst_tuple_length(map) >= 3) { | ||||||
|         const DstValue *seq; |         const Dst *seq; | ||||||
|         int32_t len; |         int32_t len; | ||||||
|         if (dst_seq_view(map[2], &seq, &len)) { |         if (dst_seq_view(map[2], &seq, &len)) { | ||||||
|             if (index >= 0 && index < len) { |             if (index >= 0 && index < len) { | ||||||
|                 if (dst_checktype(seq[index], DST_TUPLE)) { |                 if (dst_checktype(seq[index], DST_TUPLE)) { | ||||||
|                     const DstValue *ret = dst_unwrap_tuple(seq[index]); |                     const Dst *ret = dst_unwrap_tuple(seq[index]); | ||||||
|                     if (dst_tuple_length(ret) >= 2 && |                     if (dst_tuple_length(ret) >= 2 && | ||||||
|                         dst_checktype(ret[0], DST_INTEGER) && |                         dst_checktype(ret[0], DST_INTEGER) && | ||||||
|                         dst_checktype(ret[1], DST_INTEGER)) { |                         dst_checktype(ret[1], DST_INTEGER)) { | ||||||
| @@ -46,14 +46,14 @@ const DstValue *dst_sourcemap_index(const DstValue *map, int32_t index) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Traverse into tables and structs */ | /* Traverse into tables and structs */ | ||||||
| static const DstValue *dst_sourcemap_kv(const DstValue *map, DstValue key, int kv) { | static const Dst *dst_sourcemap_kv(const Dst *map, Dst key, int kv) { | ||||||
|     if (NULL != map && dst_tuple_length(map) >= 3) { |     if (NULL != map && dst_tuple_length(map) >= 3) { | ||||||
|         DstValue kvpair = dst_get(map[2], key); |         Dst kvpair = dst_get(map[2], key); | ||||||
|         if (dst_checktype(kvpair, DST_TUPLE)) { |         if (dst_checktype(kvpair, DST_TUPLE)) { | ||||||
|             const DstValue *kvtup = dst_unwrap_tuple(kvpair); |             const Dst *kvtup = dst_unwrap_tuple(kvpair); | ||||||
|             if (dst_tuple_length(kvtup) >= 2) { |             if (dst_tuple_length(kvtup) >= 2) { | ||||||
|                 if (dst_checktype(kvtup[kv], DST_TUPLE)) { |                 if (dst_checktype(kvtup[kv], DST_TUPLE)) { | ||||||
|                     const DstValue *ret = dst_unwrap_tuple(kvtup[kv]); |                     const Dst *ret = dst_unwrap_tuple(kvtup[kv]); | ||||||
|                     if (dst_tuple_length(ret) >= 2 && |                     if (dst_tuple_length(ret) >= 2 && | ||||||
|                         dst_checktype(ret[0], DST_INTEGER) && |                         dst_checktype(ret[0], DST_INTEGER) && | ||||||
|                         dst_checktype(ret[1], DST_INTEGER)) { |                         dst_checktype(ret[1], DST_INTEGER)) { | ||||||
| @@ -67,11 +67,11 @@ static const DstValue *dst_sourcemap_kv(const DstValue *map, DstValue key, int k | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Traverse into a key of a table or struct */ | /* Traverse into a key of a table or struct */ | ||||||
| const DstValue *dst_sourcemap_key(const DstValue *map, DstValue key) { | const Dst *dst_sourcemap_key(const Dst *map, Dst key) { | ||||||
|     return dst_sourcemap_kv(map, key, 0); |     return dst_sourcemap_kv(map, key, 0); | ||||||
| } | } | ||||||
|  |  | ||||||
| /* Traverse into a value of a table or struct */ | /* Traverse into a value of a table or struct */ | ||||||
| const DstValue *dst_sourcemap_value(const DstValue *map, DstValue key) { | const Dst *dst_sourcemap_value(const Dst *map, Dst key) { | ||||||
|     return dst_sourcemap_kv(map, key, 1); |     return dst_sourcemap_kv(map, key, 1); | ||||||
| } | } | ||||||
|   | |||||||
| @@ -27,18 +27,18 @@ | |||||||
|  |  | ||||||
| /* Get the sub source map by indexing a value. Used to traverse | /* Get the sub source map by indexing a value. Used to traverse | ||||||
|  * into arrays and tuples */ |  * into arrays and tuples */ | ||||||
| const DstValue *dst_sourcemap_index(const DstValue *map, int32_t index); | const Dst *dst_sourcemap_index(const Dst *map, int32_t index); | ||||||
|  |  | ||||||
| /* Traverse into a key of a table or struct */ | /* Traverse into a key of a table or struct */ | ||||||
| const DstValue *dst_sourcemap_key(const DstValue *map, DstValue key); | const Dst *dst_sourcemap_key(const Dst *map, Dst key); | ||||||
|  |  | ||||||
| /* Traverse into a value of a table or struct */ | /* Traverse into a value of a table or struct */ | ||||||
| const DstValue *dst_sourcemap_value(const DstValue *map, DstValue key); | const Dst *dst_sourcemap_value(const Dst *map, Dst key); | ||||||
|  |  | ||||||
| /* Try to rebuild a source map from given another map */ | /* Try to rebuild a source map from given another map */ | ||||||
| const DstValue *dst_sourcemap_remap( | const Dst *dst_sourcemap_remap( | ||||||
|         const DstValue *oldmap, |         const Dst *oldmap, | ||||||
|         DstValue oldsource, |         Dst oldsource, | ||||||
|         DstValue newsource); |         Dst newsource); | ||||||
|  |  | ||||||
| #endif | #endif | ||||||
|   | |||||||
							
								
								
									
										50
									
								
								core/stl.c
									
									
									
									
									
								
							
							
						
						
									
										50
									
								
								core/stl.c
									
									
									
									
									
								
							| @@ -23,7 +23,7 @@ | |||||||
| #include <dst/dst.h> | #include <dst/dst.h> | ||||||
| #include <dst/dststl.h> | #include <dst/dststl.h> | ||||||
|  |  | ||||||
| int dst_stl_print(int32_t argn, DstValue *argv, DstValue *ret) { | int dst_stl_print(int32_t argn, Dst *argv, Dst *ret) { | ||||||
|     (void)ret; |     (void)ret; | ||||||
|  |  | ||||||
|     int32_t i; |     int32_t i; | ||||||
| @@ -39,7 +39,7 @@ int dst_stl_print(int32_t argn, DstValue *argv, DstValue *ret) { | |||||||
|     return 0; |     return 0; | ||||||
| } | } | ||||||
|  |  | ||||||
| int dst_stl_describe(int32_t argn, DstValue *argv, DstValue *ret) { | int dst_stl_describe(int32_t argn, Dst *argv, Dst *ret) { | ||||||
|     (void)ret; |     (void)ret; | ||||||
|  |  | ||||||
|     int32_t i; |     int32_t i; | ||||||
| @@ -55,7 +55,7 @@ int dst_stl_describe(int32_t argn, DstValue *argv, DstValue *ret) { | |||||||
|     return 0; |     return 0; | ||||||
| } | } | ||||||
|  |  | ||||||
| int dst_stl_asm(int32_t argn, DstValue *argv, DstValue *ret) { | int dst_stl_asm(int32_t argn, Dst *argv, Dst *ret) { | ||||||
|     DstAssembleOptions opts; |     DstAssembleOptions opts; | ||||||
|     DstAssembleResult res; |     DstAssembleResult res; | ||||||
|     if (argn < 1) { |     if (argn < 1) { | ||||||
| @@ -74,7 +74,7 @@ int dst_stl_asm(int32_t argn, DstValue *argv, DstValue *ret) { | |||||||
|     } |     } | ||||||
| } | } | ||||||
|  |  | ||||||
| int dst_stl_disasm(int32_t argn, DstValue *argv, DstValue *ret) { | int dst_stl_disasm(int32_t argn, Dst *argv, Dst *ret) { | ||||||
|     DstFunction *f; |     DstFunction *f; | ||||||
|     if (argn < 1 || !dst_checktype(argv[0], DST_FUNCTION)) { |     if (argn < 1 || !dst_checktype(argv[0], DST_FUNCTION)) { | ||||||
|         *ret = dst_cstringv("expected function"); |         *ret = dst_cstringv("expected function"); | ||||||
| @@ -85,20 +85,20 @@ int dst_stl_disasm(int32_t argn, DstValue *argv, DstValue *ret) { | |||||||
|     return 0; |     return 0; | ||||||
| } | } | ||||||
|  |  | ||||||
| int dst_stl_tuple(int32_t argn, DstValue *argv, DstValue *ret) { | int dst_stl_tuple(int32_t argn, Dst *argv, Dst *ret) { | ||||||
|     *ret = dst_wrap_tuple(dst_tuple_n(argv, argn)); |     *ret = dst_wrap_tuple(dst_tuple_n(argv, argn)); | ||||||
|     return 0; |     return 0; | ||||||
| } | } | ||||||
|  |  | ||||||
| int dst_stl_array(int32_t argn, DstValue *argv, DstValue *ret) { | int dst_stl_array(int32_t argn, Dst *argv, Dst *ret) { | ||||||
|     DstArray *array = dst_array(argn); |     DstArray *array = dst_array(argn); | ||||||
|     array->count = argn; |     array->count = argn; | ||||||
|     memcpy(array->data, argv, argn * sizeof(DstValue)); |     memcpy(array->data, argv, argn * sizeof(Dst)); | ||||||
|     *ret = dst_wrap_array(array); |     *ret = dst_wrap_array(array); | ||||||
|     return 0; |     return 0; | ||||||
| } | } | ||||||
|  |  | ||||||
| int dst_stl_table(int32_t argn, DstValue *argv, DstValue *ret) { | int dst_stl_table(int32_t argn, Dst *argv, Dst *ret) { | ||||||
|     int32_t i; |     int32_t i; | ||||||
|     DstTable *table = dst_table(argn >> 1); |     DstTable *table = dst_table(argn >> 1); | ||||||
|     if (argn & 1) { |     if (argn & 1) { | ||||||
| @@ -112,7 +112,7 @@ int dst_stl_table(int32_t argn, DstValue *argv, DstValue *ret) { | |||||||
|     return 0; |     return 0; | ||||||
| } | } | ||||||
|  |  | ||||||
| int dst_stl_struct(int32_t argn, DstValue *argv, DstValue *ret) { | int dst_stl_struct(int32_t argn, Dst *argv, Dst *ret) { | ||||||
|     int32_t i; |     int32_t i; | ||||||
|     DstKV *st = dst_struct_begin(argn >> 1); |     DstKV *st = dst_struct_begin(argn >> 1); | ||||||
|     if (argn & 1) { |     if (argn & 1) { | ||||||
| @@ -126,7 +126,7 @@ int dst_stl_struct(int32_t argn, DstValue *argv, DstValue *ret) { | |||||||
|     return 0; |     return 0; | ||||||
| } | } | ||||||
|  |  | ||||||
| int dst_stl_fiber(int32_t argn, DstValue *argv, DstValue *ret) { | int dst_stl_fiber(int32_t argn, Dst *argv, Dst *ret) { | ||||||
|     DstFiber *fiber; |     DstFiber *fiber; | ||||||
|     if (argn < 1) { |     if (argn < 1) { | ||||||
|         *ret = dst_cstringv("expected at least one argument"); |         *ret = dst_cstringv("expected at least one argument"); | ||||||
| @@ -143,7 +143,7 @@ int dst_stl_fiber(int32_t argn, DstValue *argv, DstValue *ret) { | |||||||
|     return 0; |     return 0; | ||||||
| } | } | ||||||
|  |  | ||||||
| int dst_stl_buffer(int32_t argn, DstValue *argv, DstValue *ret) { | int dst_stl_buffer(int32_t argn, Dst *argv, Dst *ret) { | ||||||
|     DstBuffer *buffer = dst_buffer(10); |     DstBuffer *buffer = dst_buffer(10); | ||||||
|     int32_t i; |     int32_t i; | ||||||
|     for (i = 0; i < argn; ++i) { |     for (i = 0; i < argn; ++i) { | ||||||
| @@ -155,7 +155,7 @@ int dst_stl_buffer(int32_t argn, DstValue *argv, DstValue *ret) { | |||||||
|     return 0; |     return 0; | ||||||
| } | } | ||||||
|  |  | ||||||
| int dst_stl_gensym(int32_t argn, DstValue *argv, DstValue *ret) { | int dst_stl_gensym(int32_t argn, Dst *argv, Dst *ret) { | ||||||
|     if (argn > 1) { |     if (argn > 1) { | ||||||
|         *ret = dst_cstringv("expected one argument"); |         *ret = dst_cstringv("expected one argument"); | ||||||
|         return 1; |         return 1; | ||||||
| @@ -169,9 +169,9 @@ int dst_stl_gensym(int32_t argn, DstValue *argv, DstValue *ret) { | |||||||
|     return 0; |     return 0; | ||||||
| } | } | ||||||
|  |  | ||||||
| int dst_stl_get(int32_t argn, DstValue *argv, DstValue *ret) { | int dst_stl_get(int32_t argn, Dst *argv, Dst *ret) { | ||||||
|     int32_t i; |     int32_t i; | ||||||
|     DstValue ds; |     Dst ds; | ||||||
|     if (argn < 1) { |     if (argn < 1) { | ||||||
|         *ret = dst_cstringv("expected at least 1 argument"); |         *ret = dst_cstringv("expected at least 1 argument"); | ||||||
|         return 1; |         return 1; | ||||||
| @@ -186,8 +186,8 @@ int dst_stl_get(int32_t argn, DstValue *argv, DstValue *ret) { | |||||||
|     return 0; |     return 0; | ||||||
| } | } | ||||||
|  |  | ||||||
| int dst_stl_put(int32_t argn, DstValue *argv, DstValue *ret) { | int dst_stl_put(int32_t argn, Dst *argv, Dst *ret) { | ||||||
|     DstValue ds, key, value; |     Dst ds, key, value; | ||||||
|     if (argn < 3) { |     if (argn < 3) { | ||||||
|         *ret = dst_cstringv("expected at least 3 arguments"); |         *ret = dst_cstringv("expected at least 3 arguments"); | ||||||
|         return 1; |         return 1; | ||||||
| @@ -202,7 +202,7 @@ int dst_stl_put(int32_t argn, DstValue *argv, DstValue *ret) { | |||||||
|     return 0; |     return 0; | ||||||
| } | } | ||||||
|  |  | ||||||
| static int dst_stl_equal(int32_t argn, DstValue *argv, DstValue *ret) { | static int dst_stl_equal(int32_t argn, Dst *argv, Dst *ret) { | ||||||
|     int32_t i; |     int32_t i; | ||||||
|     for (i = 0; i < argn - 1; i++) { |     for (i = 0; i < argn - 1; i++) { | ||||||
|         if (!dst_equals(argv[i], argv[i+1])) { |         if (!dst_equals(argv[i], argv[i+1])) { | ||||||
| @@ -214,25 +214,25 @@ static int dst_stl_equal(int32_t argn, DstValue *argv, DstValue *ret) { | |||||||
|     return 0; |     return 0; | ||||||
| } | } | ||||||
|  |  | ||||||
| static int dst_stl_notequal(int32_t argn, DstValue *argv, DstValue *ret) { | static int dst_stl_notequal(int32_t argn, Dst *argv, Dst *ret) { | ||||||
|     int32_t i; |     int32_t i; | ||||||
|     for (i = 0; i < argn - 1; i++) { |     for (i = 0; i < argn - 1; i++) { | ||||||
|         if (dst_equals(argv[i], argv[i+1])) { |         if (dst_equals(argv[i], argv[i+1])) { | ||||||
|             *ret = dst_wrap_true(); |             *ret = dst_wrap_false(); | ||||||
|             return 0; |             return 0; | ||||||
|         } |         } | ||||||
|     } |     } | ||||||
|     *ret = dst_wrap_false(); |     *ret = dst_wrap_true(); | ||||||
|     return 0; |     return 0; | ||||||
| } | } | ||||||
|  |  | ||||||
| static int dst_stl_not(int32_t argn, DstValue *argv, DstValue *ret) { | static int dst_stl_not(int32_t argn, Dst *argv, Dst *ret) { | ||||||
|     *ret = dst_wrap_boolean(argn == 0 || !dst_truthy(argv[0])); |     *ret = dst_wrap_boolean(argn == 0 || !dst_truthy(argv[0])); | ||||||
|     return 0; |     return 0; | ||||||
| } | } | ||||||
|  |  | ||||||
| #define DST_DEFINE_COMPARATOR(name, pred)\ | #define DST_DEFINE_COMPARATOR(name, pred)\ | ||||||
| static int dst_stl_##name(int32_t argn, DstValue *argv, DstValue *ret) {\ | static int dst_stl_##name(int32_t argn, Dst *argv, Dst *ret) {\ | ||||||
|     int32_t i;\ |     int32_t i;\ | ||||||
|     for (i = 0; i < argn - 1; i++) {\ |     for (i = 0; i < argn - 1; i++) {\ | ||||||
|         if (dst_compare(argv[i], argv[i+1]) pred) {\ |         if (dst_compare(argv[i], argv[i+1]) pred) {\ | ||||||
| @@ -250,6 +250,8 @@ DST_DEFINE_COMPARATOR(notdescending, > 0) | |||||||
| DST_DEFINE_COMPARATOR(notascending, < 0) | DST_DEFINE_COMPARATOR(notascending, < 0) | ||||||
|  |  | ||||||
| static DstReg stl[] = { | static DstReg stl[] = { | ||||||
|  |     {"int", dst_int}, | ||||||
|  |     {"real", dst_real}, | ||||||
|     {"print", dst_stl_print}, |     {"print", dst_stl_print}, | ||||||
|     {"describe", dst_stl_describe}, |     {"describe", dst_stl_describe}, | ||||||
|     {"table", dst_stl_table}, |     {"table", dst_stl_table}, | ||||||
| @@ -296,8 +298,8 @@ static DstReg stl[] = { | |||||||
|     {"not", dst_stl_not} |     {"not", dst_stl_not} | ||||||
| }; | }; | ||||||
|  |  | ||||||
| DstValue dst_loadstl(int flags) { | Dst dst_loadstl(int flags) { | ||||||
|     DstValue ret = dst_loadreg(stl, sizeof(stl)/sizeof(DstReg)); |     Dst ret = dst_loadreg(stl, sizeof(stl)/sizeof(DstReg)); | ||||||
|     if (flags & DST_LOAD_ROOT) { |     if (flags & DST_LOAD_ROOT) { | ||||||
|         dst_gcroot(ret); |         dst_gcroot(ret); | ||||||
|     } |     } | ||||||
|   | |||||||
| @@ -23,12 +23,14 @@ | |||||||
| #include <dst/dst.h> | #include <dst/dst.h> | ||||||
| #include "strtod.h" | #include "strtod.h" | ||||||
| #include "gc.h" | #include "gc.h" | ||||||
|  | #include "util.h" | ||||||
|  |  | ||||||
| /* Begin building a string */ | /* Begin building a string */ | ||||||
| uint8_t *dst_string_begin(int32_t length) { | uint8_t *dst_string_begin(int32_t length) { | ||||||
|     char *data = dst_gcalloc(DST_MEMORY_STRING, 2 * sizeof(int32_t) + length); |     char *data = dst_gcalloc(DST_MEMORY_STRING, 2 * sizeof(int32_t) + length + 1); | ||||||
|     uint8_t *str = (uint8_t *) (data + 2 * sizeof(int32_t)); |     uint8_t *str = (uint8_t *) (data + 2 * sizeof(int32_t)); | ||||||
|     dst_string_length(str) = length; |     dst_string_length(str) = length; | ||||||
|  |     str[length] = 0; | ||||||
|     return str; |     return str; | ||||||
| } | } | ||||||
|  |  | ||||||
| @@ -41,9 +43,10 @@ const uint8_t *dst_string_end(uint8_t *str) { | |||||||
| /* Load a buffer as a string */ | /* Load a buffer as a string */ | ||||||
| const uint8_t *dst_string(const uint8_t *buf, int32_t len) { | const uint8_t *dst_string(const uint8_t *buf, int32_t len) { | ||||||
|     int32_t hash = dst_string_calchash(buf, len); |     int32_t hash = dst_string_calchash(buf, len); | ||||||
|     char *data = dst_gcalloc(DST_MEMORY_STRING, 2 * sizeof(int32_t) + len); |     char *data = dst_gcalloc(DST_MEMORY_STRING, 2 * sizeof(int32_t) + len + 1); | ||||||
|     uint8_t *str = (uint8_t *) (data + 2 * sizeof(int32_t)); |     uint8_t *str = (uint8_t *) (data + 2 * sizeof(int32_t)); | ||||||
|     memcpy(str, buf, len); |     memcpy(str, buf, len); | ||||||
|  |     str[len] = 0; | ||||||
|     dst_string_length(str) = len; |     dst_string_length(str) = len; | ||||||
|     dst_string_hash(str) = hash; |     dst_string_hash(str) = hash; | ||||||
|     return str; |     return str; | ||||||
| @@ -267,7 +270,7 @@ const uint8_t *dst_escape_string(const uint8_t *str) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Returns a string pointer with the description of the string */ | /* Returns a string pointer with the description of the string */ | ||||||
| const uint8_t *dst_short_description(DstValue x) { | const uint8_t *dst_short_description(Dst x) { | ||||||
|     switch (dst_type(x)) { |     switch (dst_type(x)) { | ||||||
|     case DST_NIL: |     case DST_NIL: | ||||||
|         return dst_cstring("nil"); |         return dst_cstring("nil"); | ||||||
| @@ -292,7 +295,7 @@ const uint8_t *dst_short_description(DstValue x) { | |||||||
|     } |     } | ||||||
| } | } | ||||||
|  |  | ||||||
| void dst_short_description_b(DstBuffer *buffer, DstValue x) { | void dst_short_description_b(DstBuffer *buffer, Dst x) { | ||||||
|     switch (dst_type(x)) { |     switch (dst_type(x)) { | ||||||
|     case DST_NIL: |     case DST_NIL: | ||||||
|         dst_buffer_push_cstring(buffer, "nil"); |         dst_buffer_push_cstring(buffer, "nil"); | ||||||
| @@ -357,7 +360,7 @@ static void dst_print_indent(DstPrinter *p) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Check if a value is a print atom (not a printable data structure) */ | /* Check if a value is a print atom (not a printable data structure) */ | ||||||
| static int is_print_ds(DstValue v) { | static int is_print_ds(Dst v) { | ||||||
|     switch (dst_type(v)) { |     switch (dst_type(v)) { | ||||||
|         default: return 0; |         default: return 0; | ||||||
|         case DST_ARRAY: |         case DST_ARRAY: | ||||||
| @@ -407,7 +410,7 @@ static const char *dst_type_colors[16] = { | |||||||
| }; | }; | ||||||
|  |  | ||||||
| /* Forward declaration */ | /* Forward declaration */ | ||||||
| static void dst_description_helper(DstPrinter *p, DstValue x); | static void dst_description_helper(DstPrinter *p, Dst x); | ||||||
|  |  | ||||||
| /* Print a hastable view inline */ | /* Print a hastable view inline */ | ||||||
| static void dst_print_hashtable_inner(DstPrinter *p, const DstKV *data, int32_t len, int32_t cap) { | static void dst_print_hashtable_inner(DstPrinter *p, const DstKV *data, int32_t len, int32_t cap) { | ||||||
| @@ -460,7 +463,7 @@ static void dst_print_hashtable_inner(DstPrinter *p, const DstKV *data, int32_t | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Help print a sequence */ | /* Help print a sequence */ | ||||||
| static void dst_print_seq_inner(DstPrinter *p, const DstValue *data, int32_t len) { | static void dst_print_seq_inner(DstPrinter *p, const Dst *data, int32_t len) { | ||||||
|     int32_t i; |     int32_t i; | ||||||
|     int doindent = 0; |     int doindent = 0; | ||||||
|     if (p->flags & DST_PRINTFLAG_INDENT) { |     if (p->flags & DST_PRINTFLAG_INDENT) { | ||||||
| @@ -495,13 +498,13 @@ static void dst_print_seq_inner(DstPrinter *p, const DstValue *data, int32_t len | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Static debug print helper */ | /* Static debug print helper */ | ||||||
| static void dst_description_helper(DstPrinter *p, DstValue x) { | static void dst_description_helper(DstPrinter *p, Dst x) { | ||||||
|     const char *open; |     const char *open; | ||||||
|     const char *close; |     const char *close; | ||||||
|     int32_t len, cap; |     int32_t len, cap; | ||||||
|     const DstValue *data; |     const Dst *data; | ||||||
|     const DstKV *kvs; |     const DstKV *kvs; | ||||||
|     DstValue check; |     Dst check; | ||||||
|     p->depth--; |     p->depth--; | ||||||
|     switch (dst_type(x)) { |     switch (dst_type(x)) { | ||||||
|         default: |         default: | ||||||
| @@ -565,7 +568,7 @@ static void dst_printer_defaults(DstPrinter *p) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Debug print. Returns a description of an object as a string. */ | /* Debug print. Returns a description of an object as a string. */ | ||||||
| const uint8_t *dst_description(DstValue x) { | const uint8_t *dst_description(Dst x) { | ||||||
|     DstPrinter printer; |     DstPrinter printer; | ||||||
|     const uint8_t *ret; |     const uint8_t *ret; | ||||||
|  |  | ||||||
| @@ -587,7 +590,7 @@ const uint8_t *dst_description(DstValue x) { | |||||||
|  |  | ||||||
| /* Convert any value to a dst string. Similar to description, but | /* Convert any value to a dst string. Similar to description, but | ||||||
|  * strings, symbols, and buffers will return their content. */ |  * strings, symbols, and buffers will return their content. */ | ||||||
| const uint8_t *dst_to_string(DstValue x) { | const uint8_t *dst_to_string(Dst x) { | ||||||
|     switch (dst_type(x)) { |     switch (dst_type(x)) { | ||||||
|         default: |         default: | ||||||
|             return dst_short_description(x); |             return dst_short_description(x); | ||||||
| @@ -655,14 +658,14 @@ const uint8_t *dst_formatc(const char *format, ...) { | |||||||
|                     case 'v': |                     case 'v': | ||||||
|                     { |                     { | ||||||
|                         dst_printer_defaults(&printer); |                         dst_printer_defaults(&printer); | ||||||
|                         dst_description_helper(&printer, va_arg(args, DstValue)); |                         dst_description_helper(&printer, va_arg(args, Dst)); | ||||||
|                         break; |                         break; | ||||||
|                     } |                     } | ||||||
|                     case 'C': |                     case 'C': | ||||||
|                     { |                     { | ||||||
|                         dst_printer_defaults(&printer); |                         dst_printer_defaults(&printer); | ||||||
|                         printer.flags |= DST_PRINTFLAG_COLORIZE; |                         printer.flags |= DST_PRINTFLAG_COLORIZE; | ||||||
|                         dst_description_helper(&printer, va_arg(args, DstValue)); |                         dst_description_helper(&printer, va_arg(args, Dst)); | ||||||
|                         break; |                         break; | ||||||
|                     } |                     } | ||||||
|                     case 'q': |                     case 'q': | ||||||
| @@ -678,7 +681,7 @@ const uint8_t *dst_formatc(const char *format, ...) { | |||||||
|                     } |                     } | ||||||
|                     case 'V':  |                     case 'V':  | ||||||
|                     { |                     { | ||||||
|                         dst_short_description_b(bufp, va_arg(args, DstValue)); |                         dst_short_description_b(bufp, va_arg(args, Dst)); | ||||||
|                         break; |                         break; | ||||||
|                     } |                     } | ||||||
|                 } |                 } | ||||||
|   | |||||||
| @@ -28,7 +28,7 @@ | |||||||
|  * reasonable). |  * reasonable). | ||||||
|  * |  * | ||||||
|  * This version has been modified for much greater flexibility in parsing, such |  * This version has been modified for much greater flexibility in parsing, such | ||||||
|  * as choosing the radix, supporting integer output, and returning DstValues |  * as choosing the radix, supporting integer output, and returning Dsts | ||||||
|  * directly.  |  * directly.  | ||||||
|  * |  * | ||||||
|  * Numbers are of the form [-+]R[rR]I.F[eE&][-+]X where R is the radix, I is |  * Numbers are of the form [-+]R[rR]I.F[eE&][-+]X where R is the radix, I is | ||||||
| @@ -253,7 +253,6 @@ static struct DstScanRes dst_scan_impl( | |||||||
|         goto error; |         goto error; | ||||||
|      |      | ||||||
|     return res; |     return res; | ||||||
|     /* return dst_wrap_real(dst_convert_mantissa_exp(neg, mant, base, ex)); */ |  | ||||||
|  |  | ||||||
|     error: |     error: | ||||||
|     res.error = 1; |     res.error = 1; | ||||||
| @@ -303,7 +302,7 @@ double dst_scan_real( | |||||||
| /* Scans a number from a string. Can return either an integer or a real if | /* Scans a number from a string. Can return either an integer or a real if | ||||||
|  * the number cannot be represented as an integer. Will return nil in case of |  * the number cannot be represented as an integer. Will return nil in case of | ||||||
|  * an error. */ |  * an error. */ | ||||||
| DstValue dst_scan_number( | Dst dst_scan_number( | ||||||
|         const uint8_t *str, |         const uint8_t *str, | ||||||
|         int32_t len) { |         int32_t len) { | ||||||
|     struct DstScanRes res = dst_scan_impl(str, len); |     struct DstScanRes res = dst_scan_impl(str, len); | ||||||
|   | |||||||
| @@ -23,7 +23,7 @@ | |||||||
| #ifndef DST_STRTOD_H_defined | #ifndef DST_STRTOD_H_defined | ||||||
| #define DST_STRTOD_H_defined | #define DST_STRTOD_H_defined | ||||||
|  |  | ||||||
| DstValue dst_scan_number( | Dst dst_scan_number( | ||||||
|         const uint8_t *str,  |         const uint8_t *str,  | ||||||
|         int32_t len); |         int32_t len); | ||||||
|  |  | ||||||
|   | |||||||
| @@ -22,6 +22,7 @@ | |||||||
|  |  | ||||||
| #include <dst/dst.h> | #include <dst/dst.h> | ||||||
| #include "gc.h" | #include "gc.h" | ||||||
|  | #include "util.h" | ||||||
|  |  | ||||||
| #define dst_struct_maphash(cap, hash) ((uint32_t)(hash & (cap - 1))); | #define dst_struct_maphash(cap, hash) ((uint32_t)(hash & (cap - 1))); | ||||||
|  |  | ||||||
| @@ -43,7 +44,7 @@ DstKV *dst_struct_begin(int32_t count) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Find an item in a struct */ | /* Find an item in a struct */ | ||||||
| static const DstKV *dst_struct_find(const DstKV *st, DstValue key) { | static const DstKV *dst_struct_find(const DstKV *st, Dst key) { | ||||||
|     int32_t cap = dst_struct_capacity(st); |     int32_t cap = dst_struct_capacity(st); | ||||||
|     int32_t index = dst_struct_maphash(cap, dst_hash(key)); |     int32_t index = dst_struct_maphash(cap, dst_hash(key)); | ||||||
|     int32_t i; |     int32_t i; | ||||||
| @@ -59,7 +60,7 @@ static const DstKV *dst_struct_find(const DstKV *st, DstValue key) { | |||||||
| /* Put a kv pair into a struct that has not yet been fully constructed. | /* Put a kv pair into a struct that has not yet been fully constructed. | ||||||
|  * Nil keys and values are ignored, extra keys are ignore, and duplicate keys are |  * Nil keys and values are ignored, extra keys are ignore, and duplicate keys are | ||||||
|  * ignored. */ |  * ignored. */ | ||||||
| void dst_struct_put(DstKV *st, DstValue key, DstValue value) { | void dst_struct_put(DstKV *st, Dst key, Dst value) { | ||||||
|     int32_t cap = dst_struct_capacity(st); |     int32_t cap = dst_struct_capacity(st); | ||||||
|     int32_t hash = dst_hash(key); |     int32_t hash = dst_hash(key); | ||||||
|     int32_t index = dst_struct_maphash(cap, hash); |     int32_t index = dst_struct_maphash(cap, hash); | ||||||
| @@ -147,7 +148,7 @@ const DstKV *dst_struct_end(DstKV *st) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Get an item from a struct */ | /* Get an item from a struct */ | ||||||
| DstValue dst_struct_get(const DstKV *st, DstValue key) { | Dst dst_struct_get(const DstKV *st, Dst key) { | ||||||
|     const DstKV *kv = dst_struct_find(st, key); |     const DstKV *kv = dst_struct_find(st, key); | ||||||
|     if (NULL == kv || dst_checktype(kv->key, DST_NIL)) { |     if (NULL == kv || dst_checktype(kv->key, DST_NIL)) { | ||||||
|         return dst_wrap_nil(); |         return dst_wrap_nil(); | ||||||
|   | |||||||
| @@ -27,6 +27,7 @@ | |||||||
|  |  | ||||||
| #include <dst/dst.h> | #include <dst/dst.h> | ||||||
| #include "gc.h" | #include "gc.h" | ||||||
|  | #include "util.h" | ||||||
|  |  | ||||||
| /* Cache state */ | /* Cache state */ | ||||||
| const uint8_t **dst_vm_cache = NULL; | const uint8_t **dst_vm_cache = NULL; | ||||||
| @@ -71,7 +72,7 @@ static const uint8_t **dst_symcache_findmem( | |||||||
|  |  | ||||||
|     /* We will search two ranges - index to the end, |     /* We will search two ranges - index to the end, | ||||||
|      * and 0 to the index. */ |      * and 0 to the index. */ | ||||||
|     index = (uint32_t)hash % dst_vm_cache_capacity; |     index = (uint32_t)hash & (dst_vm_cache_capacity - 1); | ||||||
|     bounds[0] = index; |     bounds[0] = index; | ||||||
|     bounds[1] = dst_vm_cache_capacity; |     bounds[1] = dst_vm_cache_capacity; | ||||||
|     bounds[2] = 0; |     bounds[2] = 0; | ||||||
| @@ -142,9 +143,9 @@ static void dst_cache_resize(uint32_t newCapacity) { | |||||||
|  |  | ||||||
| /* Add an item to the cache */ | /* Add an item to the cache */ | ||||||
| static void dst_symcache_put(const uint8_t *x, const uint8_t **bucket) { | static void dst_symcache_put(const uint8_t *x, const uint8_t **bucket) { | ||||||
| if ((dst_vm_cache_count + dst_vm_cache_deleted) * 2 > dst_vm_cache_capacity) { |     if ((dst_vm_cache_count + dst_vm_cache_deleted) * 2 > dst_vm_cache_capacity) { | ||||||
|         int status; |         int status; | ||||||
|         dst_cache_resize(dst_vm_cache_count * 4); |         dst_cache_resize(dst_tablen((2 * dst_vm_cache_count + 1))); | ||||||
|         bucket = dst_symcache_find(x, &status); |         bucket = dst_symcache_find(x, &status); | ||||||
|     } |     } | ||||||
|     /* Add x to the cache */ |     /* Add x to the cache */ | ||||||
| @@ -171,11 +172,12 @@ const uint8_t *dst_symbol(const uint8_t *str, int32_t len) { | |||||||
|     const uint8_t **bucket = dst_symcache_findmem(str, len, hash, &success); |     const uint8_t **bucket = dst_symcache_findmem(str, len, hash, &success); | ||||||
|     if (success) |     if (success) | ||||||
|         return *bucket; |         return *bucket; | ||||||
|     newstr = dst_gcalloc(DST_MEMORY_SYMBOL, 2 * sizeof(int32_t) + len) |     newstr = dst_gcalloc(DST_MEMORY_SYMBOL, 2 * sizeof(int32_t) + len + 1) | ||||||
|         + (2 * sizeof(int32_t)); |         + (2 * sizeof(int32_t)); | ||||||
|     dst_string_hash(newstr) = hash; |     dst_string_hash(newstr) = hash; | ||||||
|     dst_string_length(newstr) = len; |     dst_string_length(newstr) = len; | ||||||
|     memcpy(newstr, str, len); |     memcpy(newstr, str, len); | ||||||
|  |     newstr[len] = 0; | ||||||
|     dst_symcache_put((const uint8_t *)newstr, bucket); |     dst_symcache_put((const uint8_t *)newstr, bucket); | ||||||
|     return newstr; |     return newstr; | ||||||
| } | } | ||||||
| @@ -223,12 +225,13 @@ const uint8_t *dst_symbol_gen(const uint8_t *buf, int32_t len) { | |||||||
|     /* Leave spaces for 6 base 64 digits and two dashes. That means 64^6 possible suffixes, which |     /* Leave spaces for 6 base 64 digits and two dashes. That means 64^6 possible suffixes, which | ||||||
|      * is enough for resolving collisions. */ |      * is enough for resolving collisions. */ | ||||||
|     int32_t newlen = len + 8; |     int32_t newlen = len + 8; | ||||||
|     int32_t newbufsize = newlen + 2 * sizeof(int32_t); |     int32_t newbufsize = newlen + 2 * sizeof(int32_t) + 1; | ||||||
|     uint8_t *str = (uint8_t *)(dst_gcalloc(DST_MEMORY_SYMBOL, newbufsize) + 2 * sizeof(int32_t)); |     uint8_t *str = (uint8_t *)(dst_gcalloc(DST_MEMORY_SYMBOL, newbufsize) + 2 * sizeof(int32_t)); | ||||||
|     dst_string_length(str) = newlen; |     dst_string_length(str) = newlen; | ||||||
|     memcpy(str, buf, len); |     memcpy(str, buf, len); | ||||||
|     str[len] = '-'; |     str[len] = '-'; | ||||||
|     str[len + 1] = '-'; |     str[len + 1] = '-'; | ||||||
|  |     str[newlen] = 0; | ||||||
|     uint8_t *saltbuf = str + len + 2; |     uint8_t *saltbuf = str + len + 2; | ||||||
|     int status = 1; |     int status = 1; | ||||||
|     while (status) { |     while (status) { | ||||||
|   | |||||||
							
								
								
									
										11
									
								
								core/table.c
									
									
									
									
									
								
							
							
						
						
									
										11
									
								
								core/table.c
									
									
									
									
									
								
							| @@ -22,6 +22,7 @@ | |||||||
|  |  | ||||||
| #include <dst/dst.h> | #include <dst/dst.h> | ||||||
| #include "gc.h" | #include "gc.h" | ||||||
|  | #include "util.h" | ||||||
|  |  | ||||||
| #define dst_table_maphash(cap, hash) ((uint32_t)(hash) & (cap - 1)) | #define dst_table_maphash(cap, hash) ((uint32_t)(hash) & (cap - 1)) | ||||||
|  |  | ||||||
| @@ -58,7 +59,7 @@ DstTable *dst_table(int32_t capacity) { | |||||||
|  |  | ||||||
| /* Find the bucket that contains the given key. Will also return | /* Find the bucket that contains the given key. Will also return | ||||||
|  * bucket where key should go if not in the table. */ |  * bucket where key should go if not in the table. */ | ||||||
| static DstKV *dst_table_find(DstTable *t, DstValue key) { | static DstKV *dst_table_find(DstTable *t, Dst key) { | ||||||
|     int32_t index = dst_table_maphash(t->capacity, dst_hash(key)); |     int32_t index = dst_table_maphash(t->capacity, dst_hash(key)); | ||||||
|     int32_t i; |     int32_t i; | ||||||
|     DstKV *first_bucket = NULL; |     DstKV *first_bucket = NULL; | ||||||
| @@ -114,7 +115,7 @@ static void dst_table_rehash(DstTable *t, int32_t size) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Get a value out of the object */ | /* Get a value out of the object */ | ||||||
| DstValue dst_table_get(DstTable *t, DstValue key) { | Dst dst_table_get(DstTable *t, Dst key) { | ||||||
|     DstKV *bucket = dst_table_find(t, key); |     DstKV *bucket = dst_table_find(t, key); | ||||||
|     if (NULL != bucket && !dst_checktype(bucket->key, DST_NIL)) |     if (NULL != bucket && !dst_checktype(bucket->key, DST_NIL)) | ||||||
|         return bucket->value; |         return bucket->value; | ||||||
| @@ -124,10 +125,10 @@ DstValue dst_table_get(DstTable *t, DstValue key) { | |||||||
|  |  | ||||||
| /* Remove an entry from the dictionary. Return the value that | /* Remove an entry from the dictionary. Return the value that | ||||||
|  * was removed. */ |  * was removed. */ | ||||||
| DstValue dst_table_remove(DstTable *t, DstValue key) { | Dst dst_table_remove(DstTable *t, Dst key) { | ||||||
|     DstKV *bucket = dst_table_find(t, key); |     DstKV *bucket = dst_table_find(t, key); | ||||||
|     if (NULL != bucket && !dst_checktype(bucket->key, DST_NIL)) { |     if (NULL != bucket && !dst_checktype(bucket->key, DST_NIL)) { | ||||||
|         DstValue ret = bucket->key; |         Dst ret = bucket->key; | ||||||
|         t->count--; |         t->count--; | ||||||
|         t->deleted++; |         t->deleted++; | ||||||
|         bucket->key = dst_wrap_nil(); |         bucket->key = dst_wrap_nil(); | ||||||
| @@ -139,7 +140,7 @@ DstValue dst_table_remove(DstTable *t, DstValue key) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Put a value into the object */ | /* Put a value into the object */ | ||||||
| void dst_table_put(DstTable *t, DstValue key, DstValue value) { | void dst_table_put(DstTable *t, Dst key, Dst value) { | ||||||
|     if (dst_checktype(key, DST_NIL)) return; |     if (dst_checktype(key, DST_NIL)) return; | ||||||
|     if (dst_checktype(value, DST_NIL)) { |     if (dst_checktype(value, DST_NIL)) { | ||||||
|         dst_table_remove(t, key); |         dst_table_remove(t, key); | ||||||
|   | |||||||
							
								
								
									
										23
									
								
								core/tuple.c
									
									
									
									
									
								
							
							
						
						
									
										23
									
								
								core/tuple.c
									
									
									
									
									
								
							| @@ -23,32 +23,33 @@ | |||||||
| #include <dst/dst.h> | #include <dst/dst.h> | ||||||
| #include "symcache.h" | #include "symcache.h" | ||||||
| #include "gc.h" | #include "gc.h" | ||||||
|  | #include "util.h" | ||||||
|  |  | ||||||
| /* Create a new empty tuple of the given size. This will return memory | /* Create a new empty tuple of the given size. This will return memory | ||||||
|  * which should be filled with DstValues. The memory will not be collected until |  * which should be filled with Dsts. The memory will not be collected until | ||||||
|  * dst_tuple_end is called. */ |  * dst_tuple_end is called. */ | ||||||
| DstValue *dst_tuple_begin(int32_t length) { | Dst *dst_tuple_begin(int32_t length) { | ||||||
|     char *data = dst_gcalloc(DST_MEMORY_TUPLE, 2 * sizeof(int32_t) + length * sizeof(DstValue)); |     char *data = dst_gcalloc(DST_MEMORY_TUPLE, 2 * sizeof(int32_t) + length * sizeof(Dst)); | ||||||
|     DstValue *tuple = (DstValue *)(data + (2 * sizeof(int32_t))); |     Dst *tuple = (Dst *)(data + (2 * sizeof(int32_t))); | ||||||
|     dst_tuple_length(tuple) = length; |     dst_tuple_length(tuple) = length; | ||||||
|     return tuple; |     return tuple; | ||||||
| } | } | ||||||
|  |  | ||||||
| /* Finish building a tuple */ | /* Finish building a tuple */ | ||||||
| const DstValue *dst_tuple_end(DstValue *tuple) { | const Dst *dst_tuple_end(Dst *tuple) { | ||||||
|     dst_tuple_hash(tuple) = dst_array_calchash(tuple, dst_tuple_length(tuple)); |     dst_tuple_hash(tuple) = dst_array_calchash(tuple, dst_tuple_length(tuple)); | ||||||
|     return (const DstValue *)tuple; |     return (const Dst *)tuple; | ||||||
| } | } | ||||||
|  |  | ||||||
| /* Build a tuple with n values */ | /* Build a tuple with n values */ | ||||||
| const DstValue *dst_tuple_n(DstValue *values, int32_t n) { | const Dst *dst_tuple_n(Dst *values, int32_t n) { | ||||||
|     DstValue *t = dst_tuple_begin(n); |     Dst *t = dst_tuple_begin(n); | ||||||
|     memcpy(t, values, sizeof(DstValue) * n); |     memcpy(t, values, sizeof(Dst) * n); | ||||||
|     return dst_tuple_end(t); |     return dst_tuple_end(t); | ||||||
| } | } | ||||||
|  |  | ||||||
| /* Check if two tuples are equal */ | /* Check if two tuples are equal */ | ||||||
| int dst_tuple_equal(const DstValue *lhs, const DstValue *rhs) { | int dst_tuple_equal(const Dst *lhs, const Dst *rhs) { | ||||||
|     int32_t index; |     int32_t index; | ||||||
|     int32_t llen = dst_tuple_length(lhs); |     int32_t llen = dst_tuple_length(lhs); | ||||||
|     int32_t rlen = dst_tuple_length(rhs); |     int32_t rlen = dst_tuple_length(rhs); | ||||||
| @@ -70,7 +71,7 @@ int dst_tuple_equal(const DstValue *lhs, const DstValue *rhs) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Compare tuples */ | /* Compare tuples */ | ||||||
| int dst_tuple_compare(const DstValue *lhs, const DstValue *rhs) { | int dst_tuple_compare(const Dst *lhs, const Dst *rhs) { | ||||||
|     int32_t i; |     int32_t i; | ||||||
|     int32_t llen = dst_tuple_length(lhs); |     int32_t llen = dst_tuple_length(lhs); | ||||||
|     int32_t rlen = dst_tuple_length(rhs); |     int32_t rlen = dst_tuple_length(rhs); | ||||||
|   | |||||||
							
								
								
									
										71
									
								
								core/util.c
									
									
									
									
									
								
							
							
						
						
									
										71
									
								
								core/util.c
									
									
									
									
									
								
							| @@ -21,6 +21,7 @@ | |||||||
| */ | */ | ||||||
|  |  | ||||||
| #include <dst/dst.h> | #include <dst/dst.h> | ||||||
|  | #include "util.h" | ||||||
|  |  | ||||||
| /* Base 64 lookup table for digits */ | /* Base 64 lookup table for digits */ | ||||||
| const char dst_base64[65] = | const char dst_base64[65] = | ||||||
| @@ -51,8 +52,8 @@ const char *dst_type_names[16] = { | |||||||
| }; | }; | ||||||
|  |  | ||||||
| /* Computes hash of an array of values */ | /* Computes hash of an array of values */ | ||||||
| int32_t dst_array_calchash(const DstValue *array, int32_t len) { | int32_t dst_array_calchash(const Dst *array, int32_t len) { | ||||||
|     const DstValue *end = array + len; |     const Dst *end = array + len; | ||||||
|     uint32_t hash = 5381; |     uint32_t hash = 5381; | ||||||
|     while (array < end) |     while (array < end) | ||||||
|         hash = (hash << 5) + hash + dst_hash(*array++); |         hash = (hash << 5) + hash + dst_hash(*array++); | ||||||
| @@ -134,7 +135,7 @@ const void *dst_strbinsearch( | |||||||
|  |  | ||||||
| /* Read both tuples and arrays as c pointers + int32_t length. Return 1 if the | /* Read both tuples and arrays as c pointers + int32_t length. Return 1 if the | ||||||
|  * view can be constructed, 0 if an invalid type. */ |  * view can be constructed, 0 if an invalid type. */ | ||||||
| int dst_seq_view(DstValue seq, const DstValue **data, int32_t *len) { | int dst_seq_view(Dst seq, const Dst **data, int32_t *len) { | ||||||
|     if (dst_checktype(seq, DST_ARRAY)) { |     if (dst_checktype(seq, DST_ARRAY)) { | ||||||
|         *data = dst_unwrap_array(seq)->data; |         *data = dst_unwrap_array(seq)->data; | ||||||
|         *len = dst_unwrap_array(seq)->count; |         *len = dst_unwrap_array(seq)->count; | ||||||
| @@ -149,7 +150,7 @@ int dst_seq_view(DstValue seq, const DstValue **data, int32_t *len) { | |||||||
|  |  | ||||||
| /* Read both strings and buffer as unsigned character array + int32_t len. | /* Read both strings and buffer as unsigned character array + int32_t len. | ||||||
|  * Returns 1 if the view can be constructed and 0 if the type is invalid. */ |  * Returns 1 if the view can be constructed and 0 if the type is invalid. */ | ||||||
| int dst_chararray_view(DstValue str, const uint8_t **data, int32_t *len) { | int dst_chararray_view(Dst str, const uint8_t **data, int32_t *len) { | ||||||
|     if (dst_checktype(str, DST_STRING) || dst_checktype(str, DST_SYMBOL)) { |     if (dst_checktype(str, DST_STRING) || dst_checktype(str, DST_SYMBOL)) { | ||||||
|         *data = dst_unwrap_string(str); |         *data = dst_unwrap_string(str); | ||||||
|         *len = dst_string_length(dst_unwrap_string(str)); |         *len = dst_string_length(dst_unwrap_string(str)); | ||||||
| @@ -165,7 +166,7 @@ int dst_chararray_view(DstValue str, const uint8_t **data, int32_t *len) { | |||||||
| /* Read both structs and tables as the entries of a hashtable with | /* Read both structs and tables as the entries of a hashtable with | ||||||
|  * identical structure. Returns 1 if the view can be constructed and |  * identical structure. Returns 1 if the view can be constructed and | ||||||
|  * 0 if the type is invalid. */ |  * 0 if the type is invalid. */ | ||||||
| int dst_hashtable_view(DstValue tab, const DstKV **data, int32_t *len, int32_t *cap) { | int dst_hashtable_view(Dst tab, const DstKV **data, int32_t *len, int32_t *cap) { | ||||||
|     if (dst_checktype(tab, DST_TABLE)) { |     if (dst_checktype(tab, DST_TABLE)) { | ||||||
|         *data = dst_unwrap_table(tab)->data; |         *data = dst_unwrap_table(tab)->data; | ||||||
|         *cap = dst_unwrap_table(tab)->capacity; |         *cap = dst_unwrap_table(tab)->capacity; | ||||||
| @@ -181,15 +182,69 @@ int dst_hashtable_view(DstValue tab, const DstKV **data, int32_t *len, int32_t * | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Load c functions into an environment */ | /* Load c functions into an environment */ | ||||||
| DstValue dst_loadreg(DstReg *regs, size_t count) { | Dst dst_loadreg(DstReg *regs, size_t count) { | ||||||
|     size_t i; |     size_t i; | ||||||
|     DstTable *t = dst_table(count); |     DstTable *t = dst_table(count); | ||||||
|     for (i = 0; i < count; i++) { |     for (i = 0; i < count; i++) { | ||||||
|         DstValue sym = dst_csymbolv(regs[i].name); |         Dst sym = dst_csymbolv(regs[i].name); | ||||||
|         DstValue func = dst_wrap_cfunction(regs[i].function); |         Dst func = dst_wrap_cfunction(regs[i].function); | ||||||
|         DstTable *subt = dst_table(1); |         DstTable *subt = dst_table(1); | ||||||
|         dst_table_put(subt, dst_csymbolv("value"), func); |         dst_table_put(subt, dst_csymbolv("value"), func); | ||||||
|         dst_table_put(t, sym, dst_wrap_table(subt)); |         dst_table_put(t, sym, dst_wrap_table(subt)); | ||||||
|     } |     } | ||||||
|     return dst_wrap_table(t); |     return dst_wrap_table(t); | ||||||
| } | } | ||||||
|  |  | ||||||
|  | /* Vector code */ | ||||||
|  |  | ||||||
|  | /* Grow the buffer dynamically. Used for push operations. */ | ||||||
|  | void *dst_v_grow(void *v, int32_t increment, int32_t itemsize) { | ||||||
|  |     int32_t dbl_cur = (NULL != v) ? 2 * dst_v__cap(v) : 0; | ||||||
|  |     int32_t min_needed = dst_v_count(v) + increment; | ||||||
|  |     int32_t m = dbl_cur > min_needed ? dbl_cur : min_needed; | ||||||
|  |     int32_t *p = (int32_t *) realloc(v ? dst_v__raw(v) : 0, itemsize * m + sizeof(int32_t)*2); | ||||||
|  |     if (NULL != p) { | ||||||
|  |         if (!v) p[1] = 0; | ||||||
|  |         p[0] = m; | ||||||
|  |         return p + 2; | ||||||
|  |    } else { | ||||||
|  |        { | ||||||
|  |            DST_OUT_OF_MEMORY; | ||||||
|  |        } | ||||||
|  |        return (void *) (2 * sizeof(int32_t)); // try to force a NULL pointer exception later | ||||||
|  |    } | ||||||
|  | } | ||||||
|  |  | ||||||
|  | /* Clone a buffer. */ | ||||||
|  | void *dst_v_copymem(void *v, int32_t itemsize) { | ||||||
|  |     int32_t *p; | ||||||
|  |     if (NULL == v) return NULL; | ||||||
|  |     p = malloc(2 * sizeof(int32_t) + itemsize * dst_v__cap(v)); | ||||||
|  |     if (NULL != p) { | ||||||
|  |         memcpy(p, dst_v__raw(v), 2 * sizeof(int32_t) + itemsize * dst_v__cnt(v)); | ||||||
|  |         return p + 2; | ||||||
|  |     } else { | ||||||
|  |        { | ||||||
|  |            DST_OUT_OF_MEMORY; | ||||||
|  |        } | ||||||
|  |        return (void *) (2 * sizeof(int32_t)); // try to force a NULL pointer exception later | ||||||
|  |     } | ||||||
|  | } | ||||||
|  |  | ||||||
|  | /* Convert a buffer to normal allocated memory (forget capacity) */ | ||||||
|  | void *dst_v_flattenmem(void *v, int32_t itemsize) { | ||||||
|  |     int32_t *p; | ||||||
|  |     int32_t sizen; | ||||||
|  |     if (NULL == v) return NULL; | ||||||
|  |     sizen = itemsize * dst_v__cnt(v); | ||||||
|  |     p = malloc(sizen); | ||||||
|  |     if (NULL != p) { | ||||||
|  |         memcpy(p, v, sizen); | ||||||
|  |         return p; | ||||||
|  |     } else { | ||||||
|  |        { | ||||||
|  |            DST_OUT_OF_MEMORY; | ||||||
|  |        } | ||||||
|  |        return NULL; | ||||||
|  |     } | ||||||
|  | } | ||||||
|   | |||||||
| @@ -20,11 +20,28 @@ | |||||||
| * IN THE SOFTWARE. | * IN THE SOFTWARE. | ||||||
| */ | */ | ||||||
| 
 | 
 | ||||||
| #ifndef DST_VECTOR_H_defined | #ifndef DST_UTIL_H_defined | ||||||
| #define DST_VECTOR_H_defined | #define DST_UTIL_H_defined | ||||||
|  | 
 | ||||||
|  | #include <dst/dst.h> | ||||||
|  | 
 | ||||||
|  | /* Utils internal to dst. */ | ||||||
|  | 
 | ||||||
|  | /* Utils */ | ||||||
|  | extern const char dst_base64[65]; | ||||||
|  | int32_t dst_array_calchash(const Dst *array, int32_t len); | ||||||
|  | int32_t dst_kv_calchash(const DstKV *kvs, int32_t len); | ||||||
|  | int32_t dst_string_calchash(const uint8_t *str, int32_t len); | ||||||
|  | int32_t dst_tablen(int32_t n); | ||||||
|  | int dst_cstrcmp(const uint8_t *str, const char *other); | ||||||
|  | const void *dst_strbinsearch( | ||||||
|  |         const void *tab, | ||||||
|  |         size_t tabcount, | ||||||
|  |         size_t itemsize, | ||||||
|  |         const uint8_t *key); | ||||||
| 
 | 
 | ||||||
| /*
 | /*
 | ||||||
|  * Modified from |  * vector code modified from | ||||||
|  * https://github.com/nothings/stb/blob/master/stretchy_buffer.h
 |  * https://github.com/nothings/stb/blob/master/stretchy_buffer.h
 | ||||||
| */ | */ | ||||||
| 
 | 
 | ||||||
| @@ -32,8 +49,6 @@ | |||||||
|  * need vector like data structures that are not garbage collected |  * need vector like data structures that are not garbage collected | ||||||
|  * and used only from C */ |  * and used only from C */ | ||||||
| 
 | 
 | ||||||
| #include <dst/dst.h> |  | ||||||
| 
 |  | ||||||
| #define dst_v_free(v)         (((v) != NULL) ? (free(dst_v__raw(v)), 0) : 0) | #define dst_v_free(v)         (((v) != NULL) ? (free(dst_v__raw(v)), 0) : 0) | ||||||
| #define dst_v_push(v, x)      (dst_v__maybegrow(v, 1), (v)[dst_v__cnt(v)++] = (x)) | #define dst_v_push(v, x)      (dst_v__maybegrow(v, 1), (v)[dst_v__cnt(v)++] = (x)) | ||||||
| #define dst_v_pop(v)          (dst_v_count(v) ? dst_v__cnt(v)-- : 0) | #define dst_v_pop(v)          (dst_v_count(v) ? dst_v__cnt(v)-- : 0) | ||||||
| @@ -41,7 +56,7 @@ | |||||||
| #define dst_v_add(v, n)       (dst_v__maybegrow(v, n), dst_v_cnt(v) += (n), &(v)[dst_v__cnt(v) - (n)]) | #define dst_v_add(v, n)       (dst_v__maybegrow(v, n), dst_v_cnt(v) += (n), &(v)[dst_v__cnt(v) - (n)]) | ||||||
| #define dst_v_last(v)         ((v)[dst_v__cnt(v) - 1]) | #define dst_v_last(v)         ((v)[dst_v__cnt(v) - 1]) | ||||||
| #define dst_v_copy(v)         (dst_v_copymem((v), sizeof(*(v)))) | #define dst_v_copy(v)         (dst_v_copymem((v), sizeof(*(v)))) | ||||||
| #define dst_v_flatten(v)         (dst_v_flattenmem((v), sizeof(*(v)))) | #define dst_v_flatten(v)      (dst_v_flattenmem((v), sizeof(*(v)))) | ||||||
| 
 | 
 | ||||||
| #define dst_v__raw(v) ((int32_t *)(v) - 2) | #define dst_v__raw(v) ((int32_t *)(v) - 2) | ||||||
| #define dst_v__cap(v) dst_v__raw(v)[0] | #define dst_v__cap(v) dst_v__raw(v)[0] | ||||||
							
								
								
									
										22
									
								
								core/value.c
									
									
									
									
									
								
							
							
						
						
									
										22
									
								
								core/value.c
									
									
									
									
									
								
							| @@ -23,11 +23,11 @@ | |||||||
| #include <dst/dst.h> | #include <dst/dst.h> | ||||||
|  |  | ||||||
| /* | /* | ||||||
|  * Define a number of functions that can be used internally on ANY DstValue. |  * Define a number of functions that can be used internally on ANY Dst. | ||||||
|  */ |  */ | ||||||
|  |  | ||||||
| /* Check if two values are equal. This is strict equality with no conversion. */ | /* Check if two values are equal. This is strict equality with no conversion. */ | ||||||
| int dst_equals(DstValue x, DstValue y) { | int dst_equals(Dst x, Dst y) { | ||||||
|     int result = 0; |     int result = 0; | ||||||
|     if (dst_type(x) != dst_type(y)) { |     if (dst_type(x) != dst_type(y)) { | ||||||
|         result = 0; |         result = 0; | ||||||
| @@ -63,7 +63,7 @@ int dst_equals(DstValue x, DstValue y) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Computes a hash value for a function */ | /* Computes a hash value for a function */ | ||||||
| int32_t dst_hash(DstValue x) { | int32_t dst_hash(Dst x) { | ||||||
|     int32_t hash = 0; |     int32_t hash = 0; | ||||||
|     switch (dst_type(x)) { |     switch (dst_type(x)) { | ||||||
|     case DST_NIL: |     case DST_NIL: | ||||||
| @@ -98,7 +98,7 @@ int32_t dst_hash(DstValue x) { | |||||||
| /* Compares x to y. If they are equal retuns 0. If x is less, returns -1. | /* Compares x to y. If they are equal retuns 0. If x is less, returns -1. | ||||||
|  * If y is less, returns 1. All types are comparable |  * If y is less, returns 1. All types are comparable | ||||||
|  * and should have strict ordering. */ |  * and should have strict ordering. */ | ||||||
| int dst_compare(DstValue x, DstValue y) { | int dst_compare(Dst x, Dst y) { | ||||||
|     if (dst_type(x) == dst_type(y)) { |     if (dst_type(x) == dst_type(y)) { | ||||||
|         switch (dst_type(x)) { |         switch (dst_type(x)) { | ||||||
|             case DST_NIL: |             case DST_NIL: | ||||||
| @@ -147,7 +147,7 @@ int dst_compare(DstValue x, DstValue y) { | |||||||
|  |  | ||||||
| /* Get a value out af an associated data structure. For invalid | /* Get a value out af an associated data structure. For invalid | ||||||
|  * data structure or invalid key, returns nil. */ |  * data structure or invalid key, returns nil. */ | ||||||
| DstValue dst_get(DstValue ds, DstValue key) { | Dst dst_get(Dst ds, Dst key) { | ||||||
|     switch (dst_type(ds)) { |     switch (dst_type(ds)) { | ||||||
|     case DST_ARRAY: |     case DST_ARRAY: | ||||||
|         if (dst_checktype(key, DST_INTEGER) && |         if (dst_checktype(key, DST_INTEGER) && | ||||||
| @@ -186,7 +186,7 @@ DstValue dst_get(DstValue ds, DstValue key) { | |||||||
|  |  | ||||||
| /* Set a value in an associative data structure. Returns possible | /* Set a value in an associative data structure. Returns possible | ||||||
|  * error message, and NULL if no error. */ |  * error message, and NULL if no error. */ | ||||||
| void dst_put(DstValue ds, DstValue key, DstValue value) { | void dst_put(Dst ds, Dst key, Dst value) { | ||||||
|     switch (dst_type(ds)) { |     switch (dst_type(ds)) { | ||||||
|     case DST_ARRAY: |     case DST_ARRAY: | ||||||
|         if (dst_checktype(key, DST_INTEGER) && |         if (dst_checktype(key, DST_INTEGER) && | ||||||
| @@ -211,7 +211,7 @@ void dst_put(DstValue ds, DstValue key, DstValue value) { | |||||||
|  |  | ||||||
| /* Get the next key in an associative data structure. Used for iterating through an | /* Get the next key in an associative data structure. Used for iterating through an | ||||||
|  * associative data structure. */ |  * associative data structure. */ | ||||||
| const DstKV *dst_next(DstValue ds, const DstKV *kv) { | const DstKV *dst_next(Dst ds, const DstKV *kv) { | ||||||
|     switch(dst_type(ds)) { |     switch(dst_type(ds)) { | ||||||
|         default: |         default: | ||||||
|             return NULL; |             return NULL; | ||||||
| @@ -223,7 +223,7 @@ const DstKV *dst_next(DstValue ds, const DstKV *kv) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Get the length of an object. Returns errors for invalid types */ | /* Get the length of an object. Returns errors for invalid types */ | ||||||
| int32_t dst_length(DstValue x) { | int32_t dst_length(Dst x) { | ||||||
|     switch (dst_type(x)) { |     switch (dst_type(x)) { | ||||||
|         default: |         default: | ||||||
|             return 0; |             return 0; | ||||||
| @@ -243,7 +243,7 @@ int32_t dst_length(DstValue x) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Get the capacity of an object. Returns 0 for invalid types */ | /* Get the capacity of an object. Returns 0 for invalid types */ | ||||||
| int32_t dst_capacity(DstValue x) { | int32_t dst_capacity(Dst x) { | ||||||
|     switch (dst_type(x)) { |     switch (dst_type(x)) { | ||||||
|         default: |         default: | ||||||
|             return 0; |             return 0; | ||||||
| @@ -263,7 +263,7 @@ int32_t dst_capacity(DstValue x) { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Index into a data structure. Returns nil for out of bounds or invlalid data structure */ | /* Index into a data structure. Returns nil for out of bounds or invlalid data structure */ | ||||||
| DstValue dst_getindex(DstValue ds, int32_t index) { | Dst dst_getindex(Dst ds, int32_t index) { | ||||||
|     switch (dst_type(ds)) { |     switch (dst_type(ds)) { | ||||||
|         default: |         default: | ||||||
|             return dst_wrap_nil(); |             return dst_wrap_nil(); | ||||||
| @@ -284,7 +284,7 @@ DstValue dst_getindex(DstValue ds, int32_t index) { | |||||||
|  |  | ||||||
| /* Set an index in a linear data structure. Does nothing if data structure | /* Set an index in a linear data structure. Does nothing if data structure | ||||||
|  * is invalid */ |  * is invalid */ | ||||||
| void dst_setindex(DstValue ds, DstValue value, int32_t index) { | void dst_setindex(Dst ds, Dst value, int32_t index) { | ||||||
|     switch (dst_type(ds)) { |     switch (dst_type(ds)) { | ||||||
|         default: |         default: | ||||||
|             return; |             return; | ||||||
|   | |||||||
| @@ -1,73 +0,0 @@ | |||||||
| /* |  | ||||||
| * Copyright (c) 2017 Calvin Rose |  | ||||||
| * |  | ||||||
| * Permission is hereby granted, free of charge, to any person obtaining a copy |  | ||||||
| * of this software and associated documentation files (the "Software"), to |  | ||||||
| * deal in the Software without restriction, including without limitation the |  | ||||||
| * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or |  | ||||||
| * sell copies of the Software, and to permit persons to whom the Software is |  | ||||||
| * furnished to do so, subject to the following conditions: |  | ||||||
| * |  | ||||||
| * The above copyright notice and this permission notice shall be included in |  | ||||||
| * all copies or substantial portions of the Software. |  | ||||||
| * |  | ||||||
| * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR |  | ||||||
| * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, |  | ||||||
| * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE |  | ||||||
| * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER |  | ||||||
| * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING |  | ||||||
| * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS |  | ||||||
| * IN THE SOFTWARE. |  | ||||||
| */ |  | ||||||
|  |  | ||||||
| #include <dst/dst.h> |  | ||||||
| #include "vector.h" |  | ||||||
|  |  | ||||||
| void *dst_v_grow(void *v, int32_t increment, int32_t itemsize) { |  | ||||||
|     int32_t dbl_cur = (NULL != v) ? 2 * dst_v__cap(v) : 0; |  | ||||||
|     int32_t min_needed = dst_v_count(v) + increment; |  | ||||||
|     int32_t m = dbl_cur > min_needed ? dbl_cur : min_needed; |  | ||||||
|     int32_t *p = (int32_t *) realloc(v ? dst_v__raw(v) : 0, itemsize * m + sizeof(int32_t)*2); |  | ||||||
|     if (NULL != p) { |  | ||||||
|         if (!v) p[1] = 0; |  | ||||||
|         p[0] = m; |  | ||||||
|         return p + 2; |  | ||||||
|    } else { |  | ||||||
|        { |  | ||||||
|            DST_OUT_OF_MEMORY; |  | ||||||
|        } |  | ||||||
|        return (void *) (2 * sizeof(int32_t)); // try to force a NULL pointer exception later |  | ||||||
|    } |  | ||||||
| } |  | ||||||
|  |  | ||||||
| void *dst_v_copymem(void *v, int32_t itemsize) { |  | ||||||
|     int32_t *p; |  | ||||||
|     if (NULL == v) return NULL; |  | ||||||
|     p = malloc(2 * sizeof(int32_t) + itemsize * dst_v__cap(v)); |  | ||||||
|     if (NULL != p) { |  | ||||||
|         memcpy(p, dst_v__raw(v), 2 * sizeof(int32_t) + itemsize * dst_v__cnt(v)); |  | ||||||
|         return p + 2; |  | ||||||
|     } else { |  | ||||||
|        { |  | ||||||
|            DST_OUT_OF_MEMORY; |  | ||||||
|        } |  | ||||||
|        return (void *) (2 * sizeof(int32_t)); // try to force a NULL pointer exception later |  | ||||||
|     } |  | ||||||
| } |  | ||||||
|  |  | ||||||
| void *dst_v_flattenmem(void *v, int32_t itemsize) { |  | ||||||
|     int32_t *p; |  | ||||||
|     int32_t sizen; |  | ||||||
|     if (NULL == v) return NULL; |  | ||||||
|     sizen = itemsize * dst_v__cnt(v); |  | ||||||
|     p = malloc(sizen); |  | ||||||
|     if (NULL != p) { |  | ||||||
|         memcpy(p, v, sizen); |  | ||||||
|         return p; |  | ||||||
|     } else { |  | ||||||
|        { |  | ||||||
|            DST_OUT_OF_MEMORY; |  | ||||||
|        } |  | ||||||
|        return NULL; |  | ||||||
|     } |  | ||||||
| } |  | ||||||
							
								
								
									
										22
									
								
								core/vm.c
									
									
									
									
									
								
							
							
						
						
									
										22
									
								
								core/vm.c
									
									
									
									
									
								
							| @@ -52,13 +52,13 @@ static int dst_update_fiber() { | |||||||
| } | } | ||||||
|  |  | ||||||
| /* Start running the VM from where it left off. */ | /* Start running the VM from where it left off. */ | ||||||
| static int dst_continue(DstValue *returnreg) { | static int dst_continue(Dst *returnreg) { | ||||||
|  |  | ||||||
|     /* VM state */ |     /* VM state */ | ||||||
|     DstValue *stack; |     Dst *stack; | ||||||
|     uint32_t *pc; |     uint32_t *pc; | ||||||
|     DstFunction *func; |     DstFunction *func; | ||||||
|     DstValue retreg; |     Dst retreg; | ||||||
|  |  | ||||||
| /* Eventually use computed gotos for more effient vm loop. */ | /* Eventually use computed gotos for more effient vm loop. */ | ||||||
| #define vm_next() continue | #define vm_next() continue | ||||||
| @@ -94,8 +94,8 @@ static int dst_continue(DstValue *returnreg) { | |||||||
|  |  | ||||||
| #define vm_binop(op)\ | #define vm_binop(op)\ | ||||||
|     {\ |     {\ | ||||||
|         DstValue op1 = stack[oparg(2, 0xFF)];\ |         Dst op1 = stack[oparg(2, 0xFF)];\ | ||||||
|         DstValue op2 = stack[oparg(3, 0xFF)];\ |         Dst op2 = stack[oparg(3, 0xFF)];\ | ||||||
|         vm_assert(dst_checktype(op1, DST_INTEGER) || dst_checktype(op1, DST_REAL), "expected number");\ |         vm_assert(dst_checktype(op1, DST_INTEGER) || dst_checktype(op1, DST_REAL), "expected number");\ | ||||||
|         vm_assert(dst_checktype(op2, DST_INTEGER) || dst_checktype(op2, DST_REAL), "expected number");\ |         vm_assert(dst_checktype(op2, DST_INTEGER) || dst_checktype(op2, DST_REAL), "expected number");\ | ||||||
|         stack[oparg(1, 0xFF)] = dst_checktype(op1, DST_INTEGER)\ |         stack[oparg(1, 0xFF)] = dst_checktype(op1, DST_INTEGER)\ | ||||||
| @@ -216,8 +216,8 @@ static int dst_continue(DstValue *returnreg) { | |||||||
|  |  | ||||||
|         case DOP_DIVIDE: |         case DOP_DIVIDE: | ||||||
|         { |         { | ||||||
|             DstValue op1 = stack[oparg(2, 0xFF)]; |             Dst op1 = stack[oparg(2, 0xFF)]; | ||||||
|             DstValue op2 = stack[oparg(3, 0xFF)]; |             Dst op2 = stack[oparg(3, 0xFF)]; | ||||||
|             vm_assert(dst_checktype(op1, DST_INTEGER) || dst_checktype(op1, DST_REAL), "expected number"); |             vm_assert(dst_checktype(op1, DST_INTEGER) || dst_checktype(op1, DST_REAL), "expected number"); | ||||||
|             vm_assert(dst_checktype(op2, DST_INTEGER) || dst_checktype(op2, DST_REAL), "expected number"); |             vm_assert(dst_checktype(op2, DST_INTEGER) || dst_checktype(op2, DST_REAL), "expected number"); | ||||||
|             if (dst_checktype(op2, DST_INTEGER) && dst_unwrap_integer(op2) == 0) |             if (dst_checktype(op2, DST_INTEGER) && dst_unwrap_integer(op2) == 0) | ||||||
| @@ -469,7 +469,7 @@ static int dst_continue(DstValue *returnreg) { | |||||||
|  |  | ||||||
|         case DOP_CALL: |         case DOP_CALL: | ||||||
|         { |         { | ||||||
|             DstValue callee = stack[oparg(2, 0xFFFF)]; |             Dst callee = stack[oparg(2, 0xFFFF)]; | ||||||
|             if (dst_checktype(callee, DST_FUNCTION)) { |             if (dst_checktype(callee, DST_FUNCTION)) { | ||||||
|                 func = dst_unwrap_function(callee); |                 func = dst_unwrap_function(callee); | ||||||
|                 dst_stack_frame(stack)->pc = pc; |                 dst_stack_frame(stack)->pc = pc; | ||||||
| @@ -494,7 +494,7 @@ static int dst_continue(DstValue *returnreg) { | |||||||
|  |  | ||||||
|         case DOP_TAILCALL: |         case DOP_TAILCALL: | ||||||
|         { |         { | ||||||
|             DstValue callee = stack[oparg(1, 0xFFFFFF)]; |             Dst callee = stack[oparg(1, 0xFFFFFF)]; | ||||||
|             if (dst_checktype(callee, DST_FUNCTION)) { |             if (dst_checktype(callee, DST_FUNCTION)) { | ||||||
|                 func = dst_unwrap_function(callee); |                 func = dst_unwrap_function(callee); | ||||||
|                 dst_fiber_funcframe_tail(dst_vm_fiber, func); |                 dst_fiber_funcframe_tail(dst_vm_fiber, func); | ||||||
| @@ -520,7 +520,7 @@ static int dst_continue(DstValue *returnreg) { | |||||||
|         { |         { | ||||||
|             DstFiber *nextfiber; |             DstFiber *nextfiber; | ||||||
|             DstStackFrame *frame = dst_stack_frame(stack); |             DstStackFrame *frame = dst_stack_frame(stack); | ||||||
|             DstValue temp = stack[oparg(2, 0xFF)]; |             Dst temp = stack[oparg(2, 0xFF)]; | ||||||
|             retreg = stack[oparg(3, 0xFF)]; |             retreg = stack[oparg(3, 0xFF)]; | ||||||
|             vm_assert(dst_checktype(temp, DST_FIBER) || |             vm_assert(dst_checktype(temp, DST_FIBER) || | ||||||
|                       dst_checktype(temp, DST_NIL), "expected fiber"); |                       dst_checktype(temp, DST_NIL), "expected fiber"); | ||||||
| @@ -645,7 +645,7 @@ static int dst_continue(DstValue *returnreg) { | |||||||
|  |  | ||||||
| /* Run the vm with a given function. This function is | /* Run the vm with a given function. This function is | ||||||
|  * called to start the vm. */ |  * called to start the vm. */ | ||||||
| int dst_run(DstValue callee, DstValue *returnreg) { | int dst_run(Dst callee, Dst *returnreg) { | ||||||
|     if (NULL == dst_vm_fiber) { |     if (NULL == dst_vm_fiber) { | ||||||
|         dst_vm_fiber = dst_fiber(0); |         dst_vm_fiber = dst_fiber(0); | ||||||
|     } else { |     } else { | ||||||
|   | |||||||
							
								
								
									
										40
									
								
								core/wrap.c
									
									
									
									
									
								
							
							
						
						
									
										40
									
								
								core/wrap.c
									
									
									
									
									
								
							| @@ -24,7 +24,7 @@ | |||||||
|  |  | ||||||
| #ifdef DST_NANBOX | #ifdef DST_NANBOX | ||||||
|  |  | ||||||
| void *dst_nanbox_to_pointer(DstValue x) { | void *dst_nanbox_to_pointer(Dst x) { | ||||||
|     /* We need to do this shift to keep the higher bits of the pointer |     /* We need to do this shift to keep the higher bits of the pointer | ||||||
|      * the same as bit 47 as required by the x86 architecture. We may save |      * the same as bit 47 as required by the x86 architecture. We may save | ||||||
|      * an instruction if we do x.u64 & DST_NANBOX_POINTERBITS, but this 0s |      * an instruction if we do x.u64 & DST_NANBOX_POINTERBITS, but this 0s | ||||||
| @@ -39,8 +39,8 @@ void *dst_nanbox_to_pointer(DstValue x) { | |||||||
|     return x.pointer; |     return x.pointer; | ||||||
| } | } | ||||||
|  |  | ||||||
| DstValue dst_nanbox_from_pointer(void *p, uint64_t tagmask) { | Dst dst_nanbox_from_pointer(void *p, uint64_t tagmask) { | ||||||
|     DstValue ret; |     Dst ret; | ||||||
|     ret.pointer = p; |     ret.pointer = p; | ||||||
| #if defined (DST_NANBOX_47) || defined (DST_32) | #if defined (DST_NANBOX_47) || defined (DST_32) | ||||||
| #else | #else | ||||||
| @@ -50,8 +50,8 @@ DstValue dst_nanbox_from_pointer(void *p, uint64_t tagmask) { | |||||||
|     return ret; |     return ret; | ||||||
| } | } | ||||||
|  |  | ||||||
| DstValue dst_nanbox_from_cpointer(const void *p, uint64_t tagmask) { | Dst dst_nanbox_from_cpointer(const void *p, uint64_t tagmask) { | ||||||
|     DstValue ret; |     Dst ret; | ||||||
|     ret.cpointer = p; |     ret.cpointer = p; | ||||||
| #if defined (DST_NANBOX_47) || defined (DST_32) | #if defined (DST_NANBOX_47) || defined (DST_32) | ||||||
| #else | #else | ||||||
| @@ -61,8 +61,8 @@ DstValue dst_nanbox_from_cpointer(const void *p, uint64_t tagmask) { | |||||||
|     return ret; |     return ret; | ||||||
| } | } | ||||||
|  |  | ||||||
| DstValue dst_nanbox_from_double(double d) { | Dst dst_nanbox_from_double(double d) { | ||||||
|     DstValue ret; |     Dst ret; | ||||||
|     ret.real = d; |     ret.real = d; | ||||||
|     /* Normalize NaNs */ |     /* Normalize NaNs */ | ||||||
|     if (d != d) |     if (d != d) | ||||||
| @@ -70,8 +70,8 @@ DstValue dst_nanbox_from_double(double d) { | |||||||
|     return ret; |     return ret; | ||||||
| } | } | ||||||
|  |  | ||||||
| DstValue dst_nanbox_from_bits(uint64_t bits) { | Dst dst_nanbox_from_bits(uint64_t bits) { | ||||||
|     DstValue ret; |     Dst ret; | ||||||
|     ret.u64 = bits; |     ret.u64 = bits; | ||||||
|     return ret; |     return ret; | ||||||
| } | } | ||||||
| @@ -104,37 +104,37 @@ void dst_nanbox_memempty(DstKV *mem, int32_t count) { | |||||||
|  * leak memory, where as the stack based API ensures that all values can |  * leak memory, where as the stack based API ensures that all values can | ||||||
|  * be collected by the garbage collector. */ |  * be collected by the garbage collector. */ | ||||||
|  |  | ||||||
| DstValue dst_wrap_nil() { | Dst dst_wrap_nil() { | ||||||
|     DstValue y; |     Dst y; | ||||||
|     y.type = DST_NIL; |     y.type = DST_NIL; | ||||||
|     y.as.u64 = 0; |     y.as.u64 = 0; | ||||||
|     return y; |     return y; | ||||||
| } | } | ||||||
|  |  | ||||||
| DstValue dst_wrap_true() { | Dst dst_wrap_true() { | ||||||
|     DstValue y; |     Dst y; | ||||||
|     y.type = DST_TRUE; |     y.type = DST_TRUE; | ||||||
|     y.as.u64 = 0; |     y.as.u64 = 0; | ||||||
|     return y; |     return y; | ||||||
| } | } | ||||||
|  |  | ||||||
| DstValue dst_wrap_false() { | Dst dst_wrap_false() { | ||||||
|     DstValue y; |     Dst y; | ||||||
|     y.type = DST_FALSE; |     y.type = DST_FALSE; | ||||||
|     y.as.u64 = 0; |     y.as.u64 = 0; | ||||||
|     return y; |     return y; | ||||||
| } | } | ||||||
|  |  | ||||||
| DstValue dst_wrap_boolean(int x) { | Dst dst_wrap_boolean(int x) { | ||||||
|     DstValue y; |     Dst y; | ||||||
|     y.type = x ? DST_TRUE : DST_FALSE; |     y.type = x ? DST_TRUE : DST_FALSE; | ||||||
|     y.as.u64 = 0; |     y.as.u64 = 0; | ||||||
|     return y; |     return y; | ||||||
| } | } | ||||||
|  |  | ||||||
| #define DST_WRAP_DEFINE(NAME, TYPE, DTYPE, UM)\ | #define DST_WRAP_DEFINE(NAME, TYPE, DTYPE, UM)\ | ||||||
| DstValue dst_wrap_##NAME(TYPE x) {\ | Dst dst_wrap_##NAME(TYPE x) {\ | ||||||
|     DstValue y;\ |     Dst y;\ | ||||||
|     y.type = DTYPE;\ |     y.type = DTYPE;\ | ||||||
|     y.as.u64 = 0; /* zero other bits in case of 32 bit integer */ \ |     y.as.u64 = 0; /* zero other bits in case of 32 bit integer */ \ | ||||||
|     y.as.UM = x;\ |     y.as.UM = x;\ | ||||||
| @@ -146,7 +146,7 @@ DST_WRAP_DEFINE(integer, int32_t, DST_INTEGER, integer) | |||||||
| DST_WRAP_DEFINE(string, const uint8_t *, DST_STRING, cpointer) | DST_WRAP_DEFINE(string, const uint8_t *, DST_STRING, cpointer) | ||||||
| DST_WRAP_DEFINE(symbol, const uint8_t *, DST_SYMBOL, cpointer) | DST_WRAP_DEFINE(symbol, const uint8_t *, DST_SYMBOL, cpointer) | ||||||
| DST_WRAP_DEFINE(array, DstArray *, DST_ARRAY, pointer) | DST_WRAP_DEFINE(array, DstArray *, DST_ARRAY, pointer) | ||||||
| DST_WRAP_DEFINE(tuple, const DstValue *, DST_TUPLE, cpointer) | DST_WRAP_DEFINE(tuple, const Dst *, DST_TUPLE, cpointer) | ||||||
| DST_WRAP_DEFINE(struct, const DstKV *, DST_STRUCT, cpointer) | DST_WRAP_DEFINE(struct, const DstKV *, DST_STRUCT, cpointer) | ||||||
| DST_WRAP_DEFINE(fiber, DstFiber *, DST_FIBER, pointer) | DST_WRAP_DEFINE(fiber, DstFiber *, DST_FIBER, pointer) | ||||||
| DST_WRAP_DEFINE(buffer, DstBuffer *, DST_BUFFER, pointer) | DST_WRAP_DEFINE(buffer, DstBuffer *, DST_BUFFER, pointer) | ||||||
|   | |||||||
| @@ -38,9 +38,9 @@ DstArray *dst_array_init(DstArray *array, int32_t capacity); | |||||||
| void dst_array_deinit(DstArray *array); | void dst_array_deinit(DstArray *array); | ||||||
| void dst_array_ensure(DstArray *array, int32_t capacity); | void dst_array_ensure(DstArray *array, int32_t capacity); | ||||||
| void dst_array_setcount(DstArray *array, int32_t count); | void dst_array_setcount(DstArray *array, int32_t count); | ||||||
| void dst_array_push(DstArray *array, DstValue x); | void dst_array_push(DstArray *array, Dst x); | ||||||
| DstValue dst_array_pop(DstArray *array); | Dst dst_array_pop(DstArray *array); | ||||||
| DstValue dst_array_peek(DstArray *array); | Dst dst_array_peek(DstArray *array); | ||||||
|  |  | ||||||
| /* Buffer functions */ | /* Buffer functions */ | ||||||
| DstBuffer *dst_buffer(int32_t capacity); | DstBuffer *dst_buffer(int32_t capacity); | ||||||
| @@ -59,11 +59,11 @@ void dst_buffer_push_u64(DstBuffer *buffer, uint64_t x); | |||||||
| #define dst_tuple_raw(t) ((int32_t *)(t) - 2) | #define dst_tuple_raw(t) ((int32_t *)(t) - 2) | ||||||
| #define dst_tuple_length(t) (dst_tuple_raw(t)[0]) | #define dst_tuple_length(t) (dst_tuple_raw(t)[0]) | ||||||
| #define dst_tuple_hash(t) ((dst_tuple_raw(t)[1])) | #define dst_tuple_hash(t) ((dst_tuple_raw(t)[1])) | ||||||
| DstValue *dst_tuple_begin(int32_t length); | Dst *dst_tuple_begin(int32_t length); | ||||||
| const DstValue *dst_tuple_end(DstValue *tuple); | const Dst *dst_tuple_end(Dst *tuple); | ||||||
| const DstValue *dst_tuple_n(DstValue *values, int32_t n); | const Dst *dst_tuple_n(Dst *values, int32_t n); | ||||||
| int dst_tuple_equal(const DstValue *lhs, const DstValue *rhs); | int dst_tuple_equal(const Dst *lhs, const Dst *rhs); | ||||||
| int dst_tuple_compare(const DstValue *lhs, const DstValue *rhs); | int dst_tuple_compare(const Dst *lhs, const Dst *rhs); | ||||||
|  |  | ||||||
| /* String/Symbol functions */ | /* String/Symbol functions */ | ||||||
| #define dst_string_raw(s) ((int32_t *)(s) - 2) | #define dst_string_raw(s) ((int32_t *)(s) - 2) | ||||||
| @@ -78,9 +78,10 @@ int dst_string_equal(const uint8_t *lhs, const uint8_t *rhs); | |||||||
| int dst_string_equalconst(const uint8_t *lhs, const uint8_t *rhs, int32_t rlen, int32_t rhash); | int dst_string_equalconst(const uint8_t *lhs, const uint8_t *rhs, int32_t rlen, int32_t rhash); | ||||||
| const uint8_t *dst_string_unique(const uint8_t *buf, int32_t len); | const uint8_t *dst_string_unique(const uint8_t *buf, int32_t len); | ||||||
| const uint8_t *dst_cstring_unique(const char *s); | const uint8_t *dst_cstring_unique(const char *s); | ||||||
| const uint8_t *dst_description(DstValue x); | const uint8_t *dst_description(Dst x); | ||||||
| const uint8_t *dst_short_description(DstValue x); | const uint8_t *dst_short_description(Dst x); | ||||||
| const uint8_t *dst_to_string(DstValue x); | const uint8_t *dst_to_string(Dst x); | ||||||
|  | const char *dst_to_zerostring(Dst x); | ||||||
| #define dst_cstringv(cstr) dst_wrap_string(dst_cstring(cstr)) | #define dst_cstringv(cstr) dst_wrap_string(dst_cstring(cstr)) | ||||||
| #define dst_stringv(str, len) dst_wrap_string(dst_string((str), (len))) | #define dst_stringv(str, len) dst_wrap_string(dst_string((str), (len))) | ||||||
| const uint8_t *dst_formatc(const char *format, ...); | const uint8_t *dst_formatc(const char *format, ...); | ||||||
| @@ -101,9 +102,9 @@ const uint8_t *dst_symbol_gen(const uint8_t *buf, int32_t len); | |||||||
| #define dst_struct_hash(t) (dst_struct_raw(t)[2]) | #define dst_struct_hash(t) (dst_struct_raw(t)[2]) | ||||||
| /* Do something with the 4th header slot - flags? */ | /* Do something with the 4th header slot - flags? */ | ||||||
| DstKV *dst_struct_begin(int32_t count); | DstKV *dst_struct_begin(int32_t count); | ||||||
| void dst_struct_put(DstKV *st, DstValue key, DstValue value); | void dst_struct_put(DstKV *st, Dst key, Dst value); | ||||||
| const DstKV *dst_struct_end(DstKV *st); | const DstKV *dst_struct_end(DstKV *st); | ||||||
| DstValue dst_struct_get(const DstKV *st, DstValue key); | Dst dst_struct_get(const DstKV *st, Dst key); | ||||||
| const DstKV *dst_struct_next(const DstKV *st, const DstKV *kv); | const DstKV *dst_struct_next(const DstKV *st, const DstKV *kv); | ||||||
| DstTable *dst_struct_to_table(const DstKV *st); | DstTable *dst_struct_to_table(const DstKV *st); | ||||||
| int dst_struct_equal(const DstKV *lhs, const DstKV *rhs); | int dst_struct_equal(const DstKV *lhs, const DstKV *rhs); | ||||||
| @@ -113,12 +114,12 @@ int dst_struct_compare(const DstKV *lhs, const DstKV *rhs); | |||||||
| DstTable *dst_table(int32_t capacity); | DstTable *dst_table(int32_t capacity); | ||||||
| DstTable *dst_table_init(DstTable *table, int32_t capacity); | DstTable *dst_table_init(DstTable *table, int32_t capacity); | ||||||
| void dst_table_deinit(DstTable *table); | void dst_table_deinit(DstTable *table); | ||||||
| DstValue dst_table_get(DstTable *t, DstValue key); | Dst dst_table_get(DstTable *t, Dst key); | ||||||
| DstValue dst_table_remove(DstTable *t, DstValue key); | Dst dst_table_remove(DstTable *t, Dst key); | ||||||
| void dst_table_put(DstTable *t, DstValue key, DstValue value); | void dst_table_put(DstTable *t, Dst key, Dst value); | ||||||
| const DstKV *dst_table_next(DstTable *t, const DstKV *kv); | const DstKV *dst_table_next(DstTable *t, const DstKV *kv); | ||||||
| const DstKV *dst_table_to_struct(DstTable *t); | const DstKV *dst_table_to_struct(DstTable *t); | ||||||
| void dst_table_merge(DstTable *t, DstValue other); | void dst_table_merge(DstTable *t, Dst other); | ||||||
|  |  | ||||||
| /* Fiber */ | /* Fiber */ | ||||||
| DstFiber *dst_fiber(int32_t capacity); | DstFiber *dst_fiber(int32_t capacity); | ||||||
| @@ -126,10 +127,10 @@ DstFiber *dst_fiber(int32_t capacity); | |||||||
| #define dst_fiber_frame(f) dst_stack_frame((f)->data + (f)->frame) | #define dst_fiber_frame(f) dst_stack_frame((f)->data + (f)->frame) | ||||||
| DstFiber *dst_fiber_reset(DstFiber *fiber); | DstFiber *dst_fiber_reset(DstFiber *fiber); | ||||||
| void dst_fiber_setcapacity(DstFiber *fiber, int32_t n); | void dst_fiber_setcapacity(DstFiber *fiber, int32_t n); | ||||||
| void dst_fiber_push(DstFiber *fiber, DstValue x); | void dst_fiber_push(DstFiber *fiber, Dst x); | ||||||
| void dst_fiber_push2(DstFiber *fiber, DstValue x, DstValue y); | void dst_fiber_push2(DstFiber *fiber, Dst x, Dst y); | ||||||
| void dst_fiber_push3(DstFiber *fiber, DstValue x, DstValue y, DstValue z); | void dst_fiber_push3(DstFiber *fiber, Dst x, Dst y, Dst z); | ||||||
| void dst_fiber_pushn(DstFiber *fiber, const DstValue *arr, int32_t n); | void dst_fiber_pushn(DstFiber *fiber, const Dst *arr, int32_t n); | ||||||
| void dst_fiber_funcframe(DstFiber *fiber, DstFunction *func); | void dst_fiber_funcframe(DstFiber *fiber, DstFunction *func); | ||||||
| void dst_fiber_funcframe_tail(DstFiber *fiber, DstFunction *func); | void dst_fiber_funcframe_tail(DstFiber *fiber, DstFunction *func); | ||||||
| void dst_fiber_cframe(DstFiber *fiber); | void dst_fiber_cframe(DstFiber *fiber); | ||||||
| @@ -138,13 +139,13 @@ void dst_fiber_popframe(DstFiber *fiber); | |||||||
| /* Assembly */ | /* Assembly */ | ||||||
| DstAssembleResult dst_asm(DstAssembleOptions opts); | DstAssembleResult dst_asm(DstAssembleOptions opts); | ||||||
| DstFunction *dst_asm_func(DstAssembleResult result); | DstFunction *dst_asm_func(DstAssembleResult result); | ||||||
| DstValue dst_disasm(DstFuncDef *def); | Dst dst_disasm(DstFuncDef *def); | ||||||
| DstValue dst_asm_decode_instruction(uint32_t instr); | Dst dst_asm_decode_instruction(uint32_t instr); | ||||||
|  |  | ||||||
| /* Treat similar types through uniform interfaces for iteration */ | /* Treat similar types through uniform interfaces for iteration */ | ||||||
| int dst_seq_view(DstValue seq, const DstValue **data, int32_t *len); | int dst_seq_view(Dst seq, const Dst **data, int32_t *len); | ||||||
| int dst_chararray_view(DstValue str, const uint8_t **data, int32_t *len); | int dst_chararray_view(Dst str, const uint8_t **data, int32_t *len); | ||||||
| int dst_hashtable_view(DstValue tab, const DstKV **data, int32_t *len, int32_t *cap); | int dst_hashtable_view(Dst tab, const DstKV **data, int32_t *len, int32_t *cap); | ||||||
|  |  | ||||||
| /* Abstract */ | /* Abstract */ | ||||||
| #define dst_abstract_header(u) ((DstAbstractHeader *)(u) - 1) | #define dst_abstract_header(u) ((DstAbstractHeader *)(u) - 1) | ||||||
| @@ -152,33 +153,16 @@ int dst_hashtable_view(DstValue tab, const DstKV **data, int32_t *len, int32_t * | |||||||
| #define dst_abstract_size(u) (dst_abstract_header(u)->size) | #define dst_abstract_size(u) (dst_abstract_header(u)->size) | ||||||
|  |  | ||||||
| /* Value functions */ | /* Value functions */ | ||||||
| int dst_equals(DstValue x, DstValue y); | int dst_equals(Dst x, Dst y); | ||||||
| int32_t dst_hash(DstValue x); | int32_t dst_hash(Dst x); | ||||||
| int dst_compare(DstValue x, DstValue y); | int dst_compare(Dst x, Dst y); | ||||||
| DstValue dst_get(DstValue ds, DstValue key); | Dst dst_get(Dst ds, Dst key); | ||||||
| void dst_put(DstValue ds, DstValue key, DstValue value); | void dst_put(Dst ds, Dst key, Dst value); | ||||||
| const DstKV *dst_next(DstValue ds, const DstKV *kv); | const DstKV *dst_next(Dst ds, const DstKV *kv); | ||||||
| int32_t dst_length(DstValue x); | int32_t dst_length(Dst x); | ||||||
| int32_t dst_capacity(DstValue x); | int32_t dst_capacity(Dst x); | ||||||
| DstValue dst_getindex(DstValue ds, int32_t index); | Dst dst_getindex(Dst ds, int32_t index); | ||||||
| void dst_setindex(DstValue ds, DstValue value, int32_t index); | void dst_setindex(Dst ds, Dst value, int32_t index); | ||||||
|  |  | ||||||
| /* Utils */ |  | ||||||
| extern const char dst_base64[65]; |  | ||||||
| int32_t dst_array_calchash(const DstValue *array, int32_t len); |  | ||||||
| int32_t dst_kv_calchash(const DstKV *kvs, int32_t len); |  | ||||||
| int32_t dst_string_calchash(const uint8_t *str, int32_t len); |  | ||||||
| int32_t dst_tablen(int32_t n); |  | ||||||
| DstValue dst_loadreg(DstReg *regs, size_t count); |  | ||||||
| DstValue dst_scan_number(const uint8_t *src, int32_t len); |  | ||||||
| int32_t dst_scan_integer(const uint8_t *str, int32_t len, int *err); |  | ||||||
| double dst_scan_real(const uint8_t *str, int32_t len, int *err); |  | ||||||
| int dst_cstrcmp(const uint8_t *str, const char *other); |  | ||||||
| const void *dst_strbinsearch( |  | ||||||
|         const void *tab, |  | ||||||
|         size_t tabcount, |  | ||||||
|         size_t itemsize, |  | ||||||
|         const uint8_t *key); |  | ||||||
|  |  | ||||||
| /* Parsing */ | /* Parsing */ | ||||||
| DstParseResult dst_parse(const uint8_t *src, int32_t len); | DstParseResult dst_parse(const uint8_t *src, int32_t len); | ||||||
| @@ -187,7 +171,13 @@ DstParseResult dst_parsec(const char *src); | |||||||
| /* VM functions */ | /* VM functions */ | ||||||
| int dst_init(); | int dst_init(); | ||||||
| void dst_deinit(); | void dst_deinit(); | ||||||
| int dst_run(DstValue callee, DstValue *returnreg); | int dst_run(Dst callee, Dst *returnreg); | ||||||
|  |  | ||||||
|  | /* Misc */ | ||||||
|  | Dst dst_loadreg(DstReg *regs, size_t count); | ||||||
|  | Dst dst_scan_number(const uint8_t *src, int32_t len); | ||||||
|  | int32_t dst_scan_integer(const uint8_t *str, int32_t len, int *err); | ||||||
|  | double dst_scan_real(const uint8_t *str, int32_t len, int *err); | ||||||
|  |  | ||||||
| /* Compile */ | /* Compile */ | ||||||
| DstCompileResult dst_compile(DstCompileOptions opts); | DstCompileResult dst_compile(DstCompileOptions opts); | ||||||
| @@ -195,16 +185,16 @@ DstFunction *dst_compile_func(DstCompileResult result); | |||||||
|  |  | ||||||
| /* STL */ | /* STL */ | ||||||
| #define DST_LOAD_ROOT 1 | #define DST_LOAD_ROOT 1 | ||||||
| DstValue dst_loadstl(int flags); | Dst dst_loadstl(int flags); | ||||||
|  |  | ||||||
| /* GC */ | /* GC */ | ||||||
| void dst_mark(DstValue x); | void dst_mark(Dst x); | ||||||
| void dst_sweep(); | void dst_sweep(); | ||||||
| void dst_collect(); | void dst_collect(); | ||||||
| void dst_clear_memory(); | void dst_clear_memory(); | ||||||
| void dst_gcroot(DstValue root); | void dst_gcroot(Dst root); | ||||||
| int dst_gcunroot(DstValue root); | int dst_gcunroot(Dst root); | ||||||
| int dst_gcunrootall(DstValue root); | int dst_gcunrootall(Dst root); | ||||||
| #define dst_maybe_collect() do {\ | #define dst_maybe_collect() do {\ | ||||||
|     if (dst_vm_next_collection >= dst_vm_gc_interval) dst_collect(); } while (0) |     if (dst_vm_next_collection >= dst_vm_gc_interval) dst_collect(); } while (0) | ||||||
|  |  | ||||||
|   | |||||||
| @@ -45,7 +45,7 @@ extern uint32_t dst_vm_cache_count; | |||||||
| extern uint32_t dst_vm_cache_deleted; | extern uint32_t dst_vm_cache_deleted; | ||||||
|  |  | ||||||
| /* GC roots */ | /* GC roots */ | ||||||
| extern DstValue *dst_vm_roots; | extern Dst *dst_vm_roots; | ||||||
| extern uint32_t dst_vm_root_count; | extern uint32_t dst_vm_root_count; | ||||||
| extern uint32_t dst_vm_root_capacity; | extern uint32_t dst_vm_root_capacity; | ||||||
|  |  | ||||||
|   | |||||||
| @@ -25,41 +25,47 @@ | |||||||
|  |  | ||||||
| #include "dsttypes.h" | #include "dsttypes.h" | ||||||
|  |  | ||||||
| int dst_add(int32_t argn, DstValue *argv, DstValue *ret); | /* File type definition */ | ||||||
| int dst_subtract(int32_t argn, DstValue *argv, DstValue *ret); | extern DstAbstractType dst_stl_filetype; | ||||||
| int dst_multiply(int32_t argn, DstValue *argv, DstValue *ret); |  | ||||||
| int dst_divide(int32_t argn, DstValue *argv, DstValue *ret); |  | ||||||
| int dst_modulo(int32_t argn, DstValue *argv, DstValue *ret); |  | ||||||
|  |  | ||||||
| int dst_acos(int32_t argn, DstValue *argv, DstValue *ret); | int dst_int(int32_t argn, Dst *argv, Dst *ret); | ||||||
| int dst_asin(int32_t argn, DstValue *argv, DstValue *ret); | int dst_real(int32_t argn, Dst *argv, Dst *ret); | ||||||
| int dst_atan(int32_t argn, DstValue *argv, DstValue *ret); |  | ||||||
| int dst_cos(int32_t argn, DstValue *argv, DstValue *ret);  |  | ||||||
| int dst_cosh(int32_t argn, DstValue *argv, DstValue *ret);  |  | ||||||
| int dst_sin(int32_t argn, DstValue *argv, DstValue *ret);  |  | ||||||
| int dst_sinh(int32_t argn, DstValue *argv, DstValue *ret);  |  | ||||||
| int dst_tan(int32_t argn, DstValue *argv, DstValue *ret);  |  | ||||||
| int dst_tanh(int32_t argn, DstValue *argv, DstValue *ret);  |  | ||||||
| int dst_exp(int32_t argn, DstValue *argv, DstValue *ret);  |  | ||||||
| int dst_log(int32_t argn, DstValue *argv, DstValue *ret);  |  | ||||||
| int dst_log10(int32_t argn, DstValue *argv, DstValue *ret);  |  | ||||||
| int dst_sqrt(int32_t argn, DstValue *argv, DstValue *ret);  |  | ||||||
| int dst_ceil(int32_t argn, DstValue *argv, DstValue *ret);  |  | ||||||
| int dst_fabs(int32_t argn, DstValue *argv, DstValue *ret);  |  | ||||||
| int dst_floor(int32_t argn, DstValue *argv, DstValue *ret);  |  | ||||||
| int dst_pow(int32_t argn, DstValue *argv, DstValue *ret);  |  | ||||||
|  |  | ||||||
| int dst_stl_table(int32_t argn, DstValue *argv, DstValue *ret); | int dst_add(int32_t argn, Dst *argv, Dst *ret); | ||||||
| int dst_stl_array(int32_t argn, DstValue *argv, DstValue *ret); | int dst_subtract(int32_t argn, Dst *argv, Dst *ret); | ||||||
| int dst_stl_struct(int32_t argn, DstValue *argv, DstValue *ret); | int dst_multiply(int32_t argn, Dst *argv, Dst *ret); | ||||||
| int dst_stl_tuple(int32_t argn, DstValue *argv, DstValue *ret); | int dst_divide(int32_t argn, Dst *argv, Dst *ret); | ||||||
|  | int dst_modulo(int32_t argn, Dst *argv, Dst *ret); | ||||||
|  |  | ||||||
| int dst_band(int32_t argn, DstValue *argv, DstValue *ret); | int dst_acos(int32_t argn, Dst *argv, Dst *ret); | ||||||
| int dst_bor(int32_t argn, DstValue *argv, DstValue *ret); | int dst_asin(int32_t argn, Dst *argv, Dst *ret); | ||||||
| int dst_bxor(int32_t argn, DstValue *argv, DstValue *ret); | int dst_atan(int32_t argn, Dst *argv, Dst *ret); | ||||||
|  | int dst_cos(int32_t argn, Dst *argv, Dst *ret);  | ||||||
|  | int dst_cosh(int32_t argn, Dst *argv, Dst *ret);  | ||||||
|  | int dst_sin(int32_t argn, Dst *argv, Dst *ret);  | ||||||
|  | int dst_sinh(int32_t argn, Dst *argv, Dst *ret);  | ||||||
|  | int dst_tan(int32_t argn, Dst *argv, Dst *ret);  | ||||||
|  | int dst_tanh(int32_t argn, Dst *argv, Dst *ret);  | ||||||
|  | int dst_exp(int32_t argn, Dst *argv, Dst *ret);  | ||||||
|  | int dst_log(int32_t argn, Dst *argv, Dst *ret);  | ||||||
|  | int dst_log10(int32_t argn, Dst *argv, Dst *ret);  | ||||||
|  | int dst_sqrt(int32_t argn, Dst *argv, Dst *ret);  | ||||||
|  | int dst_ceil(int32_t argn, Dst *argv, Dst *ret);  | ||||||
|  | int dst_fabs(int32_t argn, Dst *argv, Dst *ret);  | ||||||
|  | int dst_floor(int32_t argn, Dst *argv, Dst *ret);  | ||||||
|  | int dst_pow(int32_t argn, Dst *argv, Dst *ret);  | ||||||
|  |  | ||||||
| int dst_lshift(int argn, DstValue *argv, DstValue *ret); | int dst_stl_table(int32_t argn, Dst *argv, Dst *ret); | ||||||
| int dst_rshift(int argn, DstValue *argv, DstValue *ret); | int dst_stl_array(int32_t argn, Dst *argv, Dst *ret); | ||||||
| int dst_lshiftu(int argn, DstValue *argv, DstValue *ret); | int dst_stl_struct(int32_t argn, Dst *argv, Dst *ret); | ||||||
|  | int dst_stl_tuple(int32_t argn, Dst *argv, Dst *ret); | ||||||
|  |  | ||||||
|  | int dst_band(int32_t argn, Dst *argv, Dst *ret); | ||||||
|  | int dst_bor(int32_t argn, Dst *argv, Dst *ret); | ||||||
|  | int dst_bxor(int32_t argn, Dst *argv, Dst *ret); | ||||||
|  |  | ||||||
|  | int dst_lshift(int argn, Dst *argv, Dst *ret); | ||||||
|  | int dst_rshift(int argn, Dst *argv, Dst *ret); | ||||||
|  | int dst_lshiftu(int argn, Dst *argv, Dst *ret); | ||||||
|  |  | ||||||
| #endif /* DST_MATH_H_defined */ | #endif /* DST_MATH_H_defined */ | ||||||
|   | |||||||
| @@ -27,9 +27,9 @@ | |||||||
| #include "dstconfig.h" | #include "dstconfig.h" | ||||||
|  |  | ||||||
| #ifdef DST_NANBOX | #ifdef DST_NANBOX | ||||||
| typedef union DstValue DstValue; | typedef union Dst Dst; | ||||||
| #else | #else | ||||||
| typedef struct DstValue DstValue; | typedef struct Dst Dst; | ||||||
| #endif | #endif | ||||||
|  |  | ||||||
| /* All of the dst types */ | /* All of the dst types */ | ||||||
| @@ -47,7 +47,7 @@ typedef struct DstFuncEnv DstFuncEnv; | |||||||
| typedef struct DstKV DstKV; | typedef struct DstKV DstKV; | ||||||
| typedef struct DstStackFrame DstStackFrame; | typedef struct DstStackFrame DstStackFrame; | ||||||
| typedef struct DstAbstractType DstAbstractType; | typedef struct DstAbstractType DstAbstractType; | ||||||
| typedef int (*DstCFunction)(int32_t argn, DstValue *argv, DstValue *ret); | typedef int (*DstCFunction)(int32_t argn, Dst *argv, Dst *ret); | ||||||
|  |  | ||||||
| typedef enum DstAssembleStatus DstAssembleStatus; | typedef enum DstAssembleStatus DstAssembleStatus; | ||||||
| typedef struct DstAssembleResult DstAssembleResult; | typedef struct DstAssembleResult DstAssembleResult; | ||||||
| @@ -78,11 +78,11 @@ typedef enum DstType { | |||||||
|     DST_ABSTRACT |     DST_ABSTRACT | ||||||
| } DstType; | } DstType; | ||||||
|  |  | ||||||
| /* We provide two possible implemenations of DstValues. The preferred | /* We provide two possible implemenations of Dsts. The preferred | ||||||
|  * nanboxing approach, and the standard C version. Code in the rest of the |  * nanboxing approach, and the standard C version. Code in the rest of the | ||||||
|  * application must interact through exposed interface. */ |  * application must interact through exposed interface. */ | ||||||
|  |  | ||||||
| /* Required interface for DstValue */ | /* Required interface for Dst */ | ||||||
| /* wrap and unwrap for all types */ | /* wrap and unwrap for all types */ | ||||||
| /* Get type quickly */ | /* Get type quickly */ | ||||||
| /* Check against type quickly */ | /* Check against type quickly */ | ||||||
| @@ -102,7 +102,7 @@ typedef enum DstType { | |||||||
|  |  | ||||||
| #include <math.h> | #include <math.h> | ||||||
|  |  | ||||||
| union DstValue { | union Dst { | ||||||
|     uint64_t u64; |     uint64_t u64; | ||||||
|     int64_t i64; |     int64_t i64; | ||||||
|     void *pointer; |     void *pointer; | ||||||
| @@ -177,13 +177,13 @@ union DstValue { | |||||||
|         ? dst_nanbox_isreal(x) \ |         ? dst_nanbox_isreal(x) \ | ||||||
|         : dst_nanbox_checkauxtype((x), (t))) |         : dst_nanbox_checkauxtype((x), (t))) | ||||||
|  |  | ||||||
| void *dst_nanbox_to_pointer(DstValue x); | void *dst_nanbox_to_pointer(Dst x); | ||||||
| void dst_nanbox_memempty(DstKV *mem, int32_t count); | void dst_nanbox_memempty(DstKV *mem, int32_t count); | ||||||
| void *dst_nanbox_memalloc_empty(int32_t count); | void *dst_nanbox_memalloc_empty(int32_t count); | ||||||
| DstValue dst_nanbox_from_pointer(void *p, uint64_t tagmask); | Dst dst_nanbox_from_pointer(void *p, uint64_t tagmask); | ||||||
| DstValue dst_nanbox_from_cpointer(const void *p, uint64_t tagmask); | Dst dst_nanbox_from_cpointer(const void *p, uint64_t tagmask); | ||||||
| DstValue dst_nanbox_from_double(double d); | Dst dst_nanbox_from_double(double d); | ||||||
| DstValue dst_nanbox_from_bits(uint64_t bits); | Dst dst_nanbox_from_bits(uint64_t bits); | ||||||
|  |  | ||||||
| #define dst_memempty(mem, len) dst_nanbox_memempty((mem), (len)) | #define dst_memempty(mem, len) dst_nanbox_memempty((mem), (len)) | ||||||
| #define dst_memalloc_empty(count) dst_nanbox_memalloc_empty(count) | #define dst_memalloc_empty(count) dst_nanbox_memalloc_empty(count) | ||||||
| @@ -231,7 +231,7 @@ DstValue dst_nanbox_from_bits(uint64_t bits); | |||||||
|  |  | ||||||
| /* Unwrap the pointer types */ | /* Unwrap the pointer types */ | ||||||
| #define dst_unwrap_struct(x) ((const DstKV *)dst_nanbox_to_pointer(x)) | #define dst_unwrap_struct(x) ((const DstKV *)dst_nanbox_to_pointer(x)) | ||||||
| #define dst_unwrap_tuple(x) ((const DstValue *)dst_nanbox_to_pointer(x)) | #define dst_unwrap_tuple(x) ((const Dst *)dst_nanbox_to_pointer(x)) | ||||||
| #define dst_unwrap_fiber(x) ((DstFiber *)dst_nanbox_to_pointer(x)) | #define dst_unwrap_fiber(x) ((DstFiber *)dst_nanbox_to_pointer(x)) | ||||||
| #define dst_unwrap_array(x) ((DstArray *)dst_nanbox_to_pointer(x)) | #define dst_unwrap_array(x) ((DstArray *)dst_nanbox_to_pointer(x)) | ||||||
| #define dst_unwrap_table(x) ((DstTable *)dst_nanbox_to_pointer(x)) | #define dst_unwrap_table(x) ((DstTable *)dst_nanbox_to_pointer(x)) | ||||||
| @@ -247,7 +247,7 @@ DstValue dst_nanbox_from_bits(uint64_t bits); | |||||||
| #else | #else | ||||||
|  |  | ||||||
| /* A general dst value type */ | /* A general dst value type */ | ||||||
| struct DstValue { | struct Dst { | ||||||
|     union { |     union { | ||||||
|         uint64_t u64; |         uint64_t u64; | ||||||
|         double real; |         double real; | ||||||
| @@ -267,7 +267,7 @@ struct DstValue { | |||||||
|     ((x).type != DST_NIL && (x).type != DST_FALSE) |     ((x).type != DST_NIL && (x).type != DST_FALSE) | ||||||
|  |  | ||||||
| #define dst_unwrap_struct(x) ((const DstKV *)(x).as.pointer) | #define dst_unwrap_struct(x) ((const DstKV *)(x).as.pointer) | ||||||
| #define dst_unwrap_tuple(x) ((const DstValue *)(x).as.pointer) | #define dst_unwrap_tuple(x) ((const Dst *)(x).as.pointer) | ||||||
| #define dst_unwrap_fiber(x) ((DstFiber *)(x).as.pointer) | #define dst_unwrap_fiber(x) ((DstFiber *)(x).as.pointer) | ||||||
| #define dst_unwrap_array(x) ((DstArray *)(x).as.pointer) | #define dst_unwrap_array(x) ((DstArray *)(x).as.pointer) | ||||||
| #define dst_unwrap_table(x) ((DstTable *)(x).as.pointer) | #define dst_unwrap_table(x) ((DstTable *)(x).as.pointer) | ||||||
| @@ -282,23 +282,23 @@ struct DstValue { | |||||||
| #define dst_unwrap_integer(x) ((x).as.integer) | #define dst_unwrap_integer(x) ((x).as.integer) | ||||||
| #define dst_unwrap_real(x) ((x).as.real) | #define dst_unwrap_real(x) ((x).as.real) | ||||||
|  |  | ||||||
| DstValue dst_wrap_nil(); | Dst dst_wrap_nil(); | ||||||
| DstValue dst_wrap_real(double x); | Dst dst_wrap_real(double x); | ||||||
| DstValue dst_wrap_integer(int32_t x); | Dst dst_wrap_integer(int32_t x); | ||||||
| DstValue dst_wrap_true(); | Dst dst_wrap_true(); | ||||||
| DstValue dst_wrap_false(); | Dst dst_wrap_false(); | ||||||
| DstValue dst_wrap_boolean(int x); | Dst dst_wrap_boolean(int x); | ||||||
| DstValue dst_wrap_string(const uint8_t *x); | Dst dst_wrap_string(const uint8_t *x); | ||||||
| DstValue dst_wrap_symbol(const uint8_t *x); | Dst dst_wrap_symbol(const uint8_t *x); | ||||||
| DstValue dst_wrap_array(DstArray *x); | Dst dst_wrap_array(DstArray *x); | ||||||
| DstValue dst_wrap_tuple(const DstValue *x); | Dst dst_wrap_tuple(const Dst *x); | ||||||
| DstValue dst_wrap_struct(const DstKV *x); | Dst dst_wrap_struct(const DstKV *x); | ||||||
| DstValue dst_wrap_fiber(DstFiber *x); | Dst dst_wrap_fiber(DstFiber *x); | ||||||
| DstValue dst_wrap_buffer(DstBuffer *x); | Dst dst_wrap_buffer(DstBuffer *x); | ||||||
| DstValue dst_wrap_function(DstFunction *x); | Dst dst_wrap_function(DstFunction *x); | ||||||
| DstValue dst_wrap_cfunction(DstCFunction x); | Dst dst_wrap_cfunction(DstCFunction x); | ||||||
| DstValue dst_wrap_table(DstTable *x); | Dst dst_wrap_table(DstTable *x); | ||||||
| DstValue dst_wrap_abstract(void *x); | Dst dst_wrap_abstract(void *x); | ||||||
|  |  | ||||||
| /* End of tagged union implementation */ | /* End of tagged union implementation */ | ||||||
| #endif | #endif | ||||||
| @@ -312,7 +312,7 @@ struct DstReg { | |||||||
| /* A lightweight green thread in dst. Does not correspond to | /* A lightweight green thread in dst. Does not correspond to | ||||||
|  * operating system threads. */ |  * operating system threads. */ | ||||||
| struct DstFiber { | struct DstFiber { | ||||||
|     DstValue *data; |     Dst *data; | ||||||
|     DstFiber *parent; |     DstFiber *parent; | ||||||
|     int32_t frame; /* Index of the stack frame */ |     int32_t frame; /* Index of the stack frame */ | ||||||
|     int32_t stackstart; /* Beginning of next args */ |     int32_t stackstart; /* Beginning of next args */ | ||||||
| @@ -333,12 +333,12 @@ struct DstStackFrame { | |||||||
|     int32_t prevframe; |     int32_t prevframe; | ||||||
| }; | }; | ||||||
|  |  | ||||||
| /* Number of DstValues a frame takes up in the stack */ | /* Number of Dsts a frame takes up in the stack */ | ||||||
| #define DST_FRAME_SIZE ((sizeof(DstStackFrame) + sizeof(DstValue) - 1)/ sizeof(DstValue)) | #define DST_FRAME_SIZE ((sizeof(DstStackFrame) + sizeof(Dst) - 1)/ sizeof(Dst)) | ||||||
|  |  | ||||||
| /* A dynamic array type. */ | /* A dynamic array type. */ | ||||||
| struct DstArray { | struct DstArray { | ||||||
|     DstValue *data; |     Dst *data; | ||||||
|     int32_t count; |     int32_t count; | ||||||
|     int32_t capacity; |     int32_t capacity; | ||||||
| }; | }; | ||||||
| @@ -360,8 +360,8 @@ struct DstTable { | |||||||
|  |  | ||||||
| /* A key value pair in a struct or table */ | /* A key value pair in a struct or table */ | ||||||
| struct DstKV { | struct DstKV { | ||||||
|     DstValue key; |     Dst key; | ||||||
|     DstValue value; |     Dst value; | ||||||
| }; | }; | ||||||
|  |  | ||||||
| /* Some function defintion flags */ | /* Some function defintion flags */ | ||||||
| @@ -371,7 +371,7 @@ struct DstKV { | |||||||
| /* A function definition. Contains information needed to instantiate closures. */ | /* A function definition. Contains information needed to instantiate closures. */ | ||||||
| struct DstFuncDef { | struct DstFuncDef { | ||||||
|     int32_t *environments; /* Which environments to capture from parent. */ |     int32_t *environments; /* Which environments to capture from parent. */ | ||||||
|     DstValue *constants; |     Dst *constants; | ||||||
|     DstFuncDef **defs; |     DstFuncDef **defs; | ||||||
|     uint32_t *bytecode; |     uint32_t *bytecode; | ||||||
|  |  | ||||||
| @@ -393,7 +393,7 @@ struct DstFuncDef { | |||||||
| struct DstFuncEnv { | struct DstFuncEnv { | ||||||
|     union { |     union { | ||||||
|         DstFiber *fiber; |         DstFiber *fiber; | ||||||
|         DstValue *values; |         Dst *values; | ||||||
|     } as; |     } as; | ||||||
|     int32_t length; /* Size of environment */ |     int32_t length; /* Size of environment */ | ||||||
|     int32_t offset; /* Stack offset when values still on stack. If offset is <= 0, then |     int32_t offset; /* Stack offset when values still on stack. If offset is <= 0, then | ||||||
| @@ -428,7 +428,7 @@ enum DstAssembleStatus { | |||||||
| }; | }; | ||||||
|  |  | ||||||
| struct DstAssembleOptions { | struct DstAssembleOptions { | ||||||
|     DstValue source; |     Dst source; | ||||||
|     uint32_t flags; |     uint32_t flags; | ||||||
| }; | }; | ||||||
|  |  | ||||||
| @@ -454,9 +454,9 @@ struct DstCompileResult { | |||||||
|  |  | ||||||
| struct DstCompileOptions { | struct DstCompileOptions { | ||||||
|     uint32_t flags; |     uint32_t flags; | ||||||
|     const DstValue *sourcemap; |     const Dst *sourcemap; | ||||||
|     DstValue source; |     Dst source; | ||||||
|     DstValue env; |     Dst env; | ||||||
| }; | }; | ||||||
|  |  | ||||||
| /* Parse structs */ | /* Parse structs */ | ||||||
| @@ -468,9 +468,9 @@ enum DstParseStatus { | |||||||
| }; | }; | ||||||
|  |  | ||||||
| struct DstParseResult { | struct DstParseResult { | ||||||
|     DstValue value; |     Dst value; | ||||||
|     const uint8_t *error; |     const uint8_t *error; | ||||||
|     const DstValue *map; |     const Dst *map; | ||||||
|     int32_t bytes_read; |     int32_t bytes_read; | ||||||
|     DstParseStatus status; |     DstParseStatus status; | ||||||
| }; | }; | ||||||
|   | |||||||
		Reference in New Issue
	
	Block a user
	 bakpakin
					bakpakin