diff --git a/lang/compile.py b/lang/compile.py index b155475..e4eaa84 100755 --- a/lang/compile.py +++ b/lang/compile.py @@ -934,12 +934,12 @@ '', ] for i in includes: - header += "#include %s\n" % i - header += "\nstatic struct object_class module_class;\n" + header += "\n#include %s" % i return header def generate_module_args(module_args): - return """ + return """static struct object_class module_class; + static struct object_list *create_args(VmState state, struct object_list *use_modules) { (void)state; (void)use_modules; int args_count = %i; @@ -954,12 +954,10 @@ for(int i = 0; i < (*args)->length; ++i) object_drop(state, &(*args)->elems[i]); object_list_free(args); -} -""" % (len(module_args)) +}""" % (len(module_args)) def generate_callbacks(): - return """ -static Object module_create(VmState state, struct object_list *use_modules) { + return """static Object module_create(VmState state, struct object_list *use_modules) { Object obj = object_create(state, &module_class, sizeof(struct object_list *)); struct object_list **args = (struct object_list **)object_priv(state, obj, &module_class); *args = create_args(state, use_modules); @@ -974,19 +972,19 @@ static void module_call(VmState state, Object obj, void *priv) { struct object_list **args = (struct object_list **)object_priv(state, obj, &module_class); bytecode_run(state, obj, (const unsigned char *)priv, *args); -}\n\n""" +}""" -def generate_footer(functions): - footer = """static struct object_call calls[] = {\n""" +def generate_structures(functions): + structures = """static struct object_call module_calls[] = {\n""" for function in functions: - footer += "\t" + function + "\n" - footer += "\t{.name = NULL, /* end */}\n};" - footer += """\n + structures += "\t" + function + "\n" + structures += "\t{.name = NULL, /* end */}\n};" + structures += """\n static struct object_class module_class = { .cleanup = module_cleanup, - .calls = &calls[0], + .calls = &module_calls[0], };""" - return footer + return structures def generate_bytecode(node): bytecode = generate_bytecode_function(node) @@ -1014,32 +1012,39 @@ output += "\t.name = \"%s\",\n" % (node.name) output += "\t.uses = module_uses,\n" output += "\t.create = module_create,\n" - output += "};\n\n" + output += "};" return output def generate_c_file(module_args, ir, source): - output = generate_header(ir, source) - output += generate_module_args(module_args) - output += generate_callbacks() + metadata = "" + bytecodes = "" functions = [] for node in ir: - next = None + success = False if isinstance(node, IRMetadata): - next = generate_metadata(node) + metadata = generate_metadata(node) + success = metadata is not None elif isinstance(node, IRFunction): - next = generate_bytecode(node) + bytecode = generate_bytecode(node) + bytecodes += bytecode functions.append(generate_call(node)) + success = bytecode is not None elif isinstance(node, IRClass): - next = "" # Nothing for now - if next is None: + success = True + if not success: print("Can't generate node: %s" % (node)) return None - output += next - footer = generate_footer(functions) - if footer is None: - print("Can't generate footer") - return None - output += footer + output = generate_header(ir, source) + output += "\n\n/* BYTECODES */\n\n" + output += bytecodes + output += "/* MODULE ARGS */\n\n" + output += generate_module_args(module_args) + output += "\n\n/* CALLBACKS */\n\n" + output += generate_callbacks() + output += "\n\n/* STRUCTURES */\n\n" + output += generate_structures(functions) + output += "\n\n/* METADATA */\n\n" + output += metadata return output ## Main wrapper