diff options
-rwxr-xr-x | main.py | 59 | ||||
-rwxr-xr-x | run.sh | 4 | ||||
-rw-r--r-- | text.py | 16 |
3 files changed, 53 insertions, 26 deletions
@@ -178,14 +178,15 @@ class Argparser(object): parser.add_argument("--inline", action="store_true", help="inlines reader funcs", default=False) parser.add_argument("--static", action="store_true", help="statics reader funcs", default=False) parser.add_argument("--verbose", action="store_true", help="verbose", default=False) - # TODO parser.add_argument("--forcenullterm", action="store_true", help="terminate all strings with null even if they are not originally null-terminated", default=False) parser.add_argument("--voidtraininitsize", type=int, help="the size of the void train, an integer", default=100) parser.add_argument("--voidtrainfactor", type=float, help="the factor by which the voidtrain will grow, a float", default=2.0) parser.add_argument("--singlefile", action="store_true", help="the generated code will be put in a single file", default=False) parser.add_argument("--calloc", action="store_true", help="use calloc instead of malloc, defaults to false", default=False) + parser.add_argument("--luaalloc", action="store_true", help="use calloc instead of malloc, defaults to false", default=False) parser.add_argument("--singlefilename", type=str, help="name of the single file") self.args = parser.parse_args() + if self.args.calloc and self.args.luaalloc: print("you have selected both calloc and lua_newuserdata. that can't possibly work.\n") class C_Obj(): def __init__(self, str, ancestry): @@ -275,6 +276,7 @@ class CodeGen(object): def gen_reader_funcs(self, alloc): temp_dec_list = [] + lua_udata_set = self.argparser.args.luaalloc read_source = open(self.read_source, "w") read_source.write("\n// automatically generated by faultrieber\n") @@ -283,6 +285,10 @@ class CodeGen(object): read_source.write('#include "./read.h"\n') read_source.write('#include "./structs.h"\n\n') if self.argparser.args.calloc: read_source.write(text.ft_calloc_def) + if self.argparser.args.luaalloc: read_source.write(text.ft_luanewuserdata_def) + read_sig_zzz = str() + if self.argparser.args.luaalloc: read_sig_zzz = ", lua_State* __ls" + else: read_sig_zzz = "" inline = "inline " if self.argparser.args.inline else "" static = "static " if self.argparser.args.static else "" for elem in self.def_elems + self.read_elems: @@ -303,19 +309,27 @@ class CodeGen(object): if "countversion" in elem.attrib: count_version = True else: count_version = False dummy_string += ", " + elem.attrib["name"] + "*" + " dummy_" + elem.attrib["name"] - read_source.write(static + inline + text.c_read_elem_sig.replace("YYY", elem.attrib["name"]).replace("XXX", elem.attrib["name"]+pointer)) + read_source.write(static + inline + text.c_read_elem_sig.replace("YYY", elem.attrib["name"]).replace("XXX", elem.attrib["name"]+pointer).replace("ZZZ", read_sig_zzz)) read_source.write("*dummy = "+alloc+"(sizeof(" + elem.attrib["name"] + "));\n") read_source.write("uint64_t b_count = 0;\n") if count_version: - count_version_buffer = static + inline + text.c_read_elem_sig_c.replace("YYY", elem.attrib["name"]).replace("XXX", elem.attrib["name"]+pointer) + count_version_buffer = static + inline + text.c_read_elem_sig_c.replace("YYY", elem.attrib["name"]).replace("XXX", elem.attrib["name"]+pointer).replace("ZZZ", read_sig_zzz) count_version_buffer += "*dummy = "+alloc+"(sizeof(" + elem.attrib["name"] + "));\n" count_version_buffer += "uint64_t b_count = 0;\n" for sub in elem: if "sizeconst" in sub.attrib: read_source.write("uint64_t agg_b_count = 0;\n") break - read_source.write(text.c_void_manager_proto.replace("XXX", "(*dummy)")); - if count_version: count_version_buffer += text.c_void_manager_proto.replace("XXX", "(*dummy)") + if not lua_udata_set: + read_source.write(text.c_void_manager_proto.replace("XXX", "(*dummy)")); + else: + read_source.write(text.lua_udata_regindex.replace("XXX", elem.attrib["name"]).replace("YYY","(*dummy)")) + if not lua_udata_set: + if count_version: + count_version_buffer += text.c_void_manager_proto.replace("XXX", "(*dummy)") + else: + if count_version: + count_version_buffer += text.lua_udata_regindex.replace("XXX", elem.attrib["name"]).replace("YYY", "(*dummy)") self.malloc_list.append(C_Obj(elem.attrib["name"], [elem.tag])) count = get_elem_count(elem) if count == 1 or count != 1: @@ -341,7 +355,8 @@ class CodeGen(object): if ref_node: read_source.write("if ((*dummy)->" + cond_name + "==" + str(cond.text) + "){\n") read_source.write("(*dummy)->" + cond.attrib["name"] + "="+alloc+"(sizeof(" + ref_node.attrib["name"] + "));") - read_source.write(text.c_void_manager_proto.replace("XXX", "(*dummy)->" + cond.attrib["name"])); + if not lua_udata_set: read_source.write(text.c_void_manager_proto.replace("XXX", "(*dummy)->" + cond.attrib["name"])); + else: read_source.write(text.lua_udata_regindex.replace("XXX", elem.attrib["name"]).replace("YYY", "(*dummy)")) self.malloc_list.append(C_Obj(ref_node.attrib["name"], [elem.tag, child.tag])) if child_count == 1: for_read = text.c_read_elem_sig_2.replace("XXX", ref_node_name).replace("YYY", "&(*dummy)->" + cond.attrib["name"]).replace("ZZZ", "void_train") + ";\n" @@ -357,7 +372,7 @@ class CodeGen(object): count_name_str = cond.attrib["count"][6:] read_source.write("if (" + "(*dummy)->" + get_node_name(count_name_str, elem) + ")\n") read_source.write("(*dummy)->" + cond.attrib["name"] + " = " + alloc+"(sizeof(void*)*" + "(*dummy)->" + get_node_name(count_name_str, child) + ");\n") - read_source.write(text.c_void_manager_proto.replace("XXX", "(*dummy)->" + cond.attri["name"])); + if not lua_udata_set: read_source.write(text.c_void_manager_proto.replace("XXX", "(*dummy)->" + cond.attri["name"])); self.malloc_list.append(C_Obj("sizeof(void*)*(*dummy)->"+get_node_name(count_name_str, child), [elem.attrib["name"], child.attrib["name"], cond.arrtib["name"]])) for_read = text.c_read_elem_sig_2.replace("XXX", ref_node_name).replace("YYY", "&(*dummy)->" + cond.attrib["name"] + "[i]").replace("ZZZ", "void_train") + ";\n" read_source.write(text.simple_loop.replace("YYY", for_read).replace("XXX", "(*dummy)->" + get_node_name(count_name_str, child))) @@ -367,7 +382,7 @@ class CodeGen(object): else: read_source.write("if ((*dummy)->" + cond_name + "==" + str(cond.text) + "){\n") read_source.write("(*dummy)->" + cond.attrib["name"] + "="+alloc+"(sizeof(" + ref_node_name + "));") - read_source.write(text.c_void_manager_proto.replace("XXX", "(*dummy)->" + cond.attrib["name"])); + if not lua_udata_set: read_source.write(text.c_void_manager_proto.replace("XXX", "(*dummy)->" + cond.attrib["name"])); for_read = str() if child_count == 1: array_subscript = "" elif child_count > 1: array_subscript = "[i]" @@ -378,7 +393,7 @@ class CodeGen(object): else: if cond.attrib["name"] == "string": for_read = "(*dummy)->" + cond.attrib["name"] + " = " + alloc+"(" + ref_size + "+1);\n" - read_source.write(text.c_void_manager_proto.replace("XXX", "(*dummy)->" + cond.attrib["name"])); + if not lua_udata_set: read_source.write(text.c_void_manager_proto.replace("XXX", "(*dummy)->" + cond.attrib["name"])); for_read += "(*dummy)->" + cond.attrib["name"] + "["+ref_size+"]=" + "0;\n" for_read = text.c_read_gen_2_no.replace("XXX", "(*dummy)" + "->"+ cond.attrib["name"] + array_subscript).replace("YYY", ref_size) else: @@ -398,7 +413,7 @@ class CodeGen(object): else: # child_count = -1 count_name_str = cond.attrib["count"][6:] read_source.write("(*dummy)->" + cond.attrib["name"] + " = " + alloc+"(sizeof(" + type_resolver(cond, self.def_elems + self.read_elems) + ")*" + "(*dummy)->" + get_node_name(count_name_str, elem) + ");\n") - read_source.write(text.c_void_manager_proto.replace("XXX", "(*dummy)->" + cond.attrib["name"])); + if not lua_udata_set: read_source.write(text.c_void_manager_proto.replace("XXX", "(*dummy)->" + cond.attrib["name"])); read_source.write("if (" + "(*dummy)->" + get_node_name(count_name_str, child) + ")\n") read_source.write(text.simple_loop.replace("YYY", for_read).replace("XXX", "(*dummy)->" + get_node_name(count_name_str, elem))) read_source.write("}\n") @@ -427,7 +442,7 @@ class CodeGen(object): count_name_str = child.attrib["count"][6:] read_source.write("if (" + "(*dummy)->" + get_node_name(count_name_str, elem) + ")\n") read_source.write("(*dummy)->" + child.attrib["name"] + " = " +alloc+"(sizeof(void*)*" + "(*dummy)->" + get_node_name(count_name_str, elem) + ");\n") - read_source.write(text.c_void_manager_proto.replace("XXX", "(*dummy)->" + child.attrib["name"])); + if not lua_udata_set: read_source.write(text.c_void_manager_proto.replace("XXX", "(*dummy)->" + child.attrib["name"])); if "sizeconst" in child.attrib: if "sizeconst" != "end": for_read = text.c_read_elem_sig_2_c.replace("XXX", ref_node_name).replace("YYY", "&(*dummy)->" + child.attrib["name"] + "[i]").replace("ZZZ", "void_train") + ";\n" @@ -456,12 +471,12 @@ class CodeGen(object): delimiter = child.attrib["delimiter"] for_read = "int32_t " + child.attrib["name"] + "_del_pos =" + text.c_read_until_delimiter_proto.replace("XXX", delimiter) + ";\n" for_read += "(*dummy)->" + child.attrib["name"] + "=" +alloc+"(" + child.attrib["name"] + "_del_pos + 1);\n" - for_read +=text.c_void_manager_proto.replace("XXX", "(*dummy)->" + child.attrib["name"]); + if not lua_udata_set: for_read +=text.c_void_manager_proto.replace("XXX", "(*dummy)->" + child.attrib["name"]); for_read += text.c_read_gen_2_no.replace("XXX", "(*dummy)" + "->"+ child.attrib["name"] + array_subscript).replace("YYY", child.attrib["name"]+"_del_pos") for_read += "(*dummy)->" + child.attrib["name"] + "[" + child.attrib["name"] + "_del_pos] = 0;\n" else: for_read = "(*dummy)->" + child.attrib["name"] + " = " + alloc+"(" + ref_size + "+1);\n" - for_read += text.c_void_manager_proto.replace("XXX", "(*dummy)->" + child.attrib["name"]); + if not lua_udata_set: for_read += text.c_void_manager_proto.replace("XXX", "(*dummy)->" + child.attrib["name"]); for_read += "(*dummy)->" + child.attrib["name"] + "["+ref_size+"]=" + "0;\n" for_read += text.c_read_gen_2_no.replace("XXX", "(*dummy)" + "->"+ child.attrib["name"] + array_subscript).replace("YYY", ref_size) else: @@ -490,11 +505,11 @@ class CodeGen(object): else: # child_count = -1 count_name_str = child.attrib["count"][6:] read_source.write("(*dummy)->" + child.attrib["name"] + " = " +alloc+"(sizeof(" + type_resolver(child, self.def_elems + self.read_elems) + ")*" + "(*dummy)->" + get_node_name(count_name_str, elem) + ");\n") - read_source.write(text.c_void_manager_proto.replace("XXX", "(*dummy)->" + child.attrib["name"])); + if not lua_udata_set: read_source.write(text.c_void_manager_proto.replace("XXX", "(*dummy)->" + child.attrib["name"])); read_source.write("if (" + "(*dummy)->" + get_node_name(count_name_str, elem) + ")\n") if count_version: count_version_buffer += "(*dummy)->" + child.attrib["name"] + " = " +alloc+"(sizeof(" + type_resolver(child, self.def_elems + self.read_elems) + ")*" + "(*dummy)->" + get_node_name(count_name_str, elem) + ");\n" - count_version_buffer += text.c_void_manager_proto.replace("XXX", "(*dummy)->" + child.attrib["name"]) + if not lua_udata_set: count_version_buffer += text.c_void_manager_proto.replace("XXX", "(*dummy)->" + child.attrib["name"]) count_version_buffer += "if (" + "(*dummy)->" + get_node_name(count_name_str, elem) + ")\n" count_version_buffer += "(*agg_b_count) += b_count;" if "sizeconst" in child.attrib: @@ -510,9 +525,9 @@ class CodeGen(object): # read funtion so we dont really need to worry about multiple # instances with the same name else: - read_source.write(static + inline + text.c_read_elem_sig.replace("YYY", elem.attrib["name"]).replace("XXX", elem.attrib["name"]+pointer)) + read_source.write(static + inline + text.c_read_elem_sig.replace("YYY", elem.attrib["name"]).replace("XXX", elem.attrib["name"]+pointer).replace("ZZZ", read_sig_zzz)) read_source.write("*dummy = "+alloc+"(sizeof(" + elem.attrib["name"] + "));\n") - read_source.write(text.c_void_manager_proto.replace("XXX", "*dummy")); + if not lua_udata_set: read_source.write(text.c_void_manager_proto.replace("XXX", "*dummy")); read_source.write(text.c_read_gen.replace("XXX", "(*dummy)->" + elem.attrib["name"]).replace("YYY", type_resolver(elem, self.def_elems))) if "sizeconst" in child.attrib: read_source.write("agg_b_count=0;\n") @@ -528,9 +543,9 @@ class CodeGen(object): read_source_header.write('#ifdef __cplusplus\nextern "C" {\n#endif\n') read_source_header.write('#include "./structs.h"\n') for elem in self.def_elems + self.read_elems: - read_source_header.write(static + inline + text.c_read_elem_sig_h.replace("YYY", elem.attrib["name"]).replace("XXX", elem.attrib["name"])) + read_source_header.write(static + inline + text.c_read_elem_sig_h.replace("YYY", elem.attrib["name"]).replace("XXX", elem.attrib["name"]).replace("ZZZ", read_sig_zzz)) if "countversion" in elem.attrib: - read_source_header.write(static + inline + text.c_read_elem_sig_h_c.replace("YYY", elem.attrib["name"]).replace("XXX", elem.attrib["name"])) + read_source_header.write(static + inline + text.c_read_elem_sig_h_c.replace("YYY", elem.attrib["name"]).replace("XXX", elem.attrib["name"]).replace("ZZZ", read_sig_zzz)) read_source_header.write('#ifdef __cplusplus\n}\n#endif\n') read_source_header.write("#endif //end of header guard\n\n") @@ -799,6 +814,7 @@ class CodeGen(object): def run(self): alloc = str() if self.argparser.args.calloc: alloc = "ft_calloc" + if self.argparser.args.luaalloc: alloc = "ft_lua_newuserdata" else: alloc = "malloc" self.init() self.init_hook() @@ -806,7 +822,10 @@ class CodeGen(object): self.read_xml() self.gen_reader_funcs(alloc) self.gen_struct_header_xml() - self.gen_void_train(alloc) + if self.argparser.args.luaalloc: + pass + else: + self.gen_void_train(alloc) self.gen_aggregate_read() self.gen_release() #self.gen_return() @@ -1,5 +1,5 @@ #!/bin/sh cd $(dirname $0) -#"./faultreiber.py" --targetname autowasm --outdir ./test/ --structs ./test/struct.json --xml ./resources/wasm.xml --name wasm --calloc -"./faultreiber.py" --targetname autowasm --outdir ./test/ --structs ./test/struct.json --xml ./resources/wasm2.xml --name wasm --calloc +"./faultreiber.py" --targetname autowasm --outdir ./test/ --structs ./test/struct.json --xml ./resources/wasm2.xml --name wasm --luaalloc +#"./faultreiber.py" --targetname autowasm --outdir ./test/ --structs ./test/struct.json --xml ./resources/wasm2.xml --name wasm --calloc "clang-format" -i ./test/read.c ./test/structs.c ./test/structs.h ./test/aggregate.c ./test/aggregate.h ./test/read.h @@ -11,10 +11,10 @@ class text(): autogen_warning = "// automatically generated by faultreiber\n" last_comment = "// last line intentionally left blank\n\n" read_func_sig = "int read_structured_file(char* path)" - c_read_elem_sig = "void* ft_read_YYY(int _fd, XXX** dummy, void*** void_train, uint64_t* current_void_size, uint64_t* current_void_count) {\n" - c_read_elem_sig_h = "void* ft_read_YYY(int _fd, XXX** dummy, void*** void_train, uint64_t* current_void_size, uint64_t* current_void_count);\n" - c_read_elem_sig_c = "void* ft_read_YYY_c(int _fd, XXX** dummy, void*** void_train, uint64_t* current_void_size, uint64_t* current_void_count, uint64_t* agg_b_count) {\n" - c_read_elem_sig_h_c = "void* ft_read_YYY_c(int _fd, XXX** dummy, void*** void_train, uint64_t* current_void_size, uint64_t* current_void_count, uint64_t* agg_b_count);\n" + c_read_elem_sig = "void* ft_read_YYY(int _fd, XXX** dummy, void*** void_train, uint64_t* current_void_size, uint64_t* current_void_count ZZZ) {\n" + c_read_elem_sig_h = "void* ft_read_YYY(int _fd, XXX** dummy, void*** void_train, uint64_t* current_void_size, uint64_t* current_void_count ZZZ);\n" + c_read_elem_sig_c = "void* ft_read_YYY_c(int _fd, XXX** dummy, void*** void_train, uint64_t* current_void_size, uint64_t* current_void_count, uint64_t* agg_b_count ZZZ) {\n" + c_read_elem_sig_h_c = "void* ft_read_YYY_c(int _fd, XXX** dummy, void*** void_train, uint64_t* current_void_size, uint64_t* current_void_count, uint64_t* agg_b_count ZZZ);\n" #c_read_elem_sig_1 = "ft_read_XXX(_fd)" c_read_elem_sig_2 = "ft_read_XXX(_fd, YYY, ZZZ, current_void_size, current_void_count)" c_read_elem_sig_2_c = "ft_read_XXX_c(_fd, YYY, ZZZ, current_void_size, current_void_count, &agg_b_count)" @@ -131,3 +131,11 @@ void void_manager(void* ptr, void*** void_train, uint64_t* current_void_size, ui c_reserve_void_ptr = "malloc(XXX)" ft_calloc_def="#define ft_calloc(X1) calloc(X1, 1)\n" + ft_luanewuserdata_def="#define ft_luanewuserdata(X1) lua_newuserdata(__ls, X1)\n" + lua_udata_regindex = ''' + luaL_getmetatable(__ls, "XXX"); + lua_setmetatable(__ls, -2); + lua_pushlightuserdata(__ls, YYY); + lua_pushvalue(__ls, -2); + lua_settable(__ls, LUA_REGISTRYINDEX); + ''' |