diff --git a/core/compile.c b/core/compile.c index 2d73af1f..0d8d7340 100644 --- a/core/compile.c +++ b/core/compile.c @@ -1237,5 +1237,5 @@ static const GstModuleItem gst_compile_module[] = { /* Load compiler library */ void gst_compile_load(Gst *vm) { - gst_module_put(vm, "std.compile", gst_cmodule_struct(vm, gst_compile_module)); + gst_module(vm, "std.compile", gst_compile_module); } diff --git a/core/parse.c b/core/parse.c index ef4c5990..dcd80e28 100644 --- a/core/parse.c +++ b/core/parse.c @@ -648,5 +648,5 @@ static const GstModuleItem gst_parser_module[] = { /* Load the module */ void gst_parse_load(Gst *vm) { - gst_module_put(vm, "std.parse", gst_cmodule_struct(vm, gst_parser_module)); + gst_module(vm, "std.parse", gst_parser_module); } diff --git a/core/serialize.c b/core/serialize.c index 8b718f45..f27224e4 100644 --- a/core/serialize.c +++ b/core/serialize.c @@ -411,9 +411,17 @@ static const char *gst_deserialize_impl( break; case 216: /* C function */ - /* TODO - add registry for c functions */ { - ret.type = GST_NIL; + GstValue id; + read_u32(length); + deser_datacheck(length); + id = gst_wrap_string(gst_string_b(vm, data, length)); + data += length; + ret = gst_table_get(vm->registry, id); + if (ret.type != GST_CFUNCTION) { + deser_error("unabled to deserialize c function"); + } + break; } break; @@ -477,7 +485,6 @@ const char *gst_serialize_impl( /* Check non reference types - if successful, return NULL */ switch (x.type) { - case GST_CFUNCTION: case GST_USERDATA: case GST_NIL: write_byte(201); @@ -565,6 +572,18 @@ const char *gst_serialize_impl( } break; + case GST_CFUNCTION: + write_byte(216); + { + GstValue id = gst_table_get(vm->registry, x); + count = gst_string_length(id.data.string); + write_u32(count); + for (i = 0; i < count; ++i) { + write_byte(id.data.string[i]); + } + } + break; + case GST_TABLE: { const GstValue *data; diff --git a/core/stl.c b/core/stl.c index 60b6cd81..f11a962f 100644 --- a/core/stl.c +++ b/core/stl.c @@ -603,13 +603,6 @@ int gst_stl_deserialize(Gst *vm) { /* Registry */ /****/ -/* Export a symbol definition to the current namespace. Used to implement - * def */ -int gst_stl_export(Gst *vm) { - gst_table_put(vm, vm->registry, gst_arg(vm, 0), gst_arg(vm, 1)); - gst_c_return(vm, gst_arg(vm, 1)); -} - /* Get everything in the current namespace */ int gst_stl_namespace(Gst *vm) { gst_c_return(vm, gst_wrap_table(vm->registry)); @@ -774,16 +767,14 @@ static const GstModuleItem const io_dat[] = { /* Load the io module */ void gst_stlio_load(Gst *vm) { /* Load the normal c functions */ - GstValue module = gst_cmodule_table(vm, io_dat); - GstTable *tab = module.data.table; + gst_module_mutable(vm, "std.io", io_dat); /* Wrap stdin and stdout */ FILE **inp = gst_userdata(vm, sizeof(FILE *), &gst_stl_filetype); FILE **outp = gst_userdata(vm, sizeof(FILE *), &gst_stl_filetype); *inp = stdin; *outp = stdout; - gst_table_put(vm, tab, gst_string_cv(vm, "stdin"), gst_wrap_userdata(inp)); - gst_table_put(vm, tab, gst_string_cv(vm, "stdout"), gst_wrap_userdata(outp)); - gst_module_put(vm, "std.io", module); + gst_module_put(vm, "std.io", "stdin", gst_wrap_userdata(inp)); + gst_module_put(vm, "std.io", "stdout", gst_wrap_userdata(outp)); } /****/ @@ -919,7 +910,6 @@ static const GstModuleItem const std_module[] = { {"error", gst_stl_error}, {"serialize", gst_stl_serialize}, {"deserialize", gst_stl_deserialize}, - {"export!", gst_stl_export}, {"namespace", gst_stl_namespace}, {"namespace-set!", gst_stl_namespace_set}, {"namespace-get", gst_stl_namespace_get}, @@ -944,5 +934,5 @@ static const GstModuleItem const std_module[] = { /* Load all libraries */ void gst_stl_load(Gst *vm) { gst_stlio_load(vm); - gst_module_put(vm, "std", gst_cmodule_struct(vm, std_module)); + gst_module(vm, "std", std_module); } diff --git a/core/util.c b/core/util.c index 2f2bf546..2a4b0b0a 100644 --- a/core/util.c +++ b/core/util.c @@ -84,7 +84,24 @@ void *gst_check_userdata(Gst *vm, uint32_t i, const GstUserType *type) { return x.data.pointer; } -GstValue gst_cmodule_table(Gst *vm, const GstModuleItem *mod) { +static void gst_cmodule_register(Gst *vm, const char *name, const GstModuleItem *mod) { + uint32_t startLength; + GstBuffer *buffer = gst_buffer(vm, 10); + gst_buffer_append_cstring(vm, buffer, name); + gst_buffer_push(vm, buffer, '.'); + startLength = buffer->count; + while (mod->name != NULL) { + GstValue key; + buffer->count = startLength; + gst_buffer_append_cstring(vm, buffer, mod->name); + key = gst_wrap_string(gst_buffer_to_string(vm, buffer)); + gst_table_put(vm, vm->registry, key, gst_wrap_cfunction(mod->data)); + gst_table_put(vm, vm->registry, gst_wrap_cfunction(mod->data), key); + mod++; + } +} + +static GstValue gst_cmodule_table(Gst *vm, const GstModuleItem *mod) { GstTable *module = gst_table(vm, 10); while (mod->name != NULL) { GstValue key = gst_string_cv(vm, mod->name); @@ -94,7 +111,7 @@ GstValue gst_cmodule_table(Gst *vm, const GstModuleItem *mod) { return gst_wrap_table(module); } -GstValue gst_cmodule_struct(Gst *vm, const GstModuleItem *mod) { +static GstValue gst_cmodule_struct(Gst *vm, const GstModuleItem *mod) { uint32_t count = 0; const GstModuleItem *m = mod; GstValue *st; @@ -113,22 +130,38 @@ GstValue gst_cmodule_struct(Gst *vm, const GstModuleItem *mod) { return gst_wrap_struct(gst_struct_end(vm, st)); } -void gst_module_put(Gst *vm, const char *packagename, GstValue mod) { - gst_table_put(vm, vm->modules, gst_string_cv(vm, packagename), mod); +void gst_module(Gst *vm, const char *packagename, const GstModuleItem *mod) { + gst_table_put(vm, vm->modules, gst_string_cv(vm, packagename), gst_cmodule_struct(vm, mod)); + gst_cmodule_register(vm, packagename, mod); +} + +void gst_module_mutable(Gst *vm, const char *packagename, const GstModuleItem *mod) { + gst_table_put(vm, vm->modules, gst_string_cv(vm, packagename), gst_cmodule_table(vm, mod)); + gst_cmodule_register(vm, packagename, mod); +} + +void gst_module_put(Gst *vm, const char *packagename, const char *name, GstValue v) { + GstValue modtable = gst_table_get(vm->modules, gst_string_cv(vm, packagename)); + if (modtable.type == GST_TABLE) { + GstTable *table = modtable.data.table; + if (v.type == GST_CFUNCTION) { + GstValue key; + GstBuffer *buffer = gst_buffer(vm, 10); + gst_buffer_append_cstring(vm, buffer, packagename); + gst_buffer_push(vm, buffer, '.'); + gst_buffer_append_cstring(vm, buffer, name); + key = gst_wrap_string(gst_buffer_to_string(vm, buffer)); + gst_table_put(vm, vm->registry, key, v); + gst_table_put(vm, vm->registry, v, key); + } + gst_table_put(vm, table, gst_string_cv(vm, name), v); + } } GstValue gst_module_get(Gst *vm, const char *packagename) { return gst_table_get(vm->modules, gst_string_cv(vm, packagename)); } -void gst_register_put(Gst *vm, const char *name, GstValue c) { - gst_table_put(vm, vm->registry, gst_string_cv(vm, name), c); -} - -GstValue gst_register_get(Gst *vm, const char *name) { - return gst_table_get(vm->registry, gst_string_cv(vm, name)); -} - /****/ /* Misc */ /****/ diff --git a/include/gst/gst.h b/include/gst/gst.h index f51470ca..51fae5e4 100644 --- a/include/gst/gst.h +++ b/include/gst/gst.h @@ -490,12 +490,10 @@ uint32_t gst_count_args(Gst *vm); /* C Api */ /****/ -GstValue gst_cmodule_table(Gst *vm, const GstModuleItem *mod); -GstValue gst_cmodule_struct(Gst *vm, const GstModuleItem *mod); -void gst_module_put(Gst *vm, const char *packagename, GstValue mod); +void gst_module(Gst *vm, const char *packagename, const GstModuleItem *mod); +void gst_module_mutable(Gst *vm, const char *packagename, const GstModuleItem *mod); GstValue gst_module_get(Gst *vm, const char *packagename); -void gst_register_put(Gst *vm, const char *packagename, GstValue mod); -GstValue gst_register_get(Gst *vm, const char *name); +void gst_module_put(Gst *vm, const char *packagename, const char *name, GstValue v); /* Wrap data in GstValue */ GstValue gst_wrap_nil();