diff options
Diffstat (limited to 'python_modules')
-rw-r--r-- | python_modules/demarshal.py | 16 | ||||
-rw-r--r-- | python_modules/marshal.py | 27 | ||||
-rw-r--r-- | python_modules/spice_parser.py | 2 |
3 files changed, 33 insertions, 12 deletions
diff --git a/python_modules/demarshal.py b/python_modules/demarshal.py index faaf8620..48b4e73e 100644 --- a/python_modules/demarshal.py +++ b/python_modules/demarshal.py @@ -604,7 +604,7 @@ def read_array_len(writer, prefix, array, dest, scope, handles_bytes = False): elif array.is_bytes_length(): if not handles_bytes: raise NotImplementedError("handling of bytes() not supported here yet") - writer.assign(nelements, dest.get_ref(array.size[1])) + writer.assign(nelements, array.size[1]) else: raise NotImplementedError("TODO array size type not handled yet") return nelements @@ -714,10 +714,15 @@ def write_array_parser(writer, nelements, array, dest, scope): writer.increment("end", nelements) else: if is_byte_size: + real_nelements = nelements[:-len("nbytes")] + "nelements" scope.variable_def("uint8_t *", "array_end") + scope.variable_def("uint32_t", real_nelements) writer.assign("array_end", "end + %s" % nelements) + writer.assign(real_nelements, 0) with writer.index(no_block = is_byte_size) as index: with writer.while_loop("end < array_end") if is_byte_size else writer.for_loop(index, nelements) as array_scope: + if is_byte_size: + writer.increment(real_nelements, 1) if element_type.is_primitive(): writer.statement("*(%s *)end = consume_%s(&in)" % (element_type.c_type(), element_type.primitive_type())) writer.increment("end", element_type.sizeof()) @@ -725,6 +730,8 @@ def write_array_parser(writer, nelements, array, dest, scope): dest2 = dest.child_at_end(writer, element_type) dest2.reuse_scope = array_scope write_container_parser(writer, element_type, dest2) + if is_byte_size: + writer.assign(dest.get_ref(array.size[2]), real_nelements) def write_parse_pointer(writer, t, at_end, as_c_ptr, dest, member_name, scope): target_type = t.target_type @@ -766,7 +773,12 @@ def write_member_parser(writer, container, member, dest, scope): writer.statement("*(%s *)end = consume_%s(&in)" % (t.c_type(), t.primitive_type())) writer.increment("end", t.sizeof()) else: - writer.assign(dest.get_ref(member.name), "consume_%s(&in)" % (t.primitive_type())) + if member.has_attr("bytes_count"): + scope.variable_def("uint32_t", member.name); + dest_var = member.name + else: + dest_var = dest.get_ref(member.name) + writer.assign(dest_var, "consume_%s(&in)" % (t.primitive_type())) #TODO validate e.g. flags and enums elif t.is_array(): nelements = read_array_len(writer, member.name, t, dest, scope, handles_bytes = True) diff --git a/python_modules/marshal.py b/python_modules/marshal.py index 1eb36751..250147f4 100644 --- a/python_modules/marshal.py +++ b/python_modules/marshal.py @@ -165,7 +165,7 @@ def get_array_size(array, container_src): else: return "(((%s * %s + 7) / 8 ) * %s)" % (bpp, width_v, rows_v) elif array.is_bytes_length(): - return container_src.get_ref(array.size[1]) + return container_src.get_ref(array.size[2]) else: raise NotImplementedError("TODO array size type not handled yet") @@ -179,20 +179,18 @@ def write_array_marshaller(writer, at_end, member, array, container_src, scope): nelements = get_array_size(array, container_src) is_byte_size = array.is_bytes_length() - if is_byte_size: - element = "%s__bytes" % member.name - else: - element = "%s__element" % member.name + element = "%s__element" % member.name if not at_end: writer.assign(element, container_src.get_ref(member.name)) if is_byte_size: - scope.variable_def("size_t", "array_end") - writer.assign("array_end", "spice_marshaller_get_size(m) + %s" % nelements) + size_start_var = "%s__size_start" % member.name + scope.variable_def("size_t", size_start_var) + writer.assign(size_start_var, "spice_marshaller_get_size(m)") - with writer.index(no_block = is_byte_size) as index: - with writer.while_loop("spice_marshaller_get_size(m) < array_end") if is_byte_size else writer.for_loop(index, nelements) as array_scope: + with writer.index() as index: + with writer.for_loop(index, nelements) as array_scope: array_scope.variable_def(element_type.c_type() + " *", element) if at_end: writer.assign(element, "(%s *)end" % element_type.c_type()) @@ -210,6 +208,12 @@ def write_array_marshaller(writer, at_end, member, array, container_src, scope): if not at_end: writer.statement("%s++" % element) + if is_byte_size: + size_var = member.container.lookup_member(array.size[1]) + size_var_type = size_var.member_type + var = "%s__ref" % array.size[1] + writer.statement("spice_marshaller_set_%s(m, %s, spice_marshaller_get_size(m) - %s)" % (size_var_type.primitive_type(), var, size_start_var)) + def write_switch_marshaller(writer, container, switch, src, scope): var = container.lookup_member(switch.variable) var_type = var.member_type @@ -289,6 +293,11 @@ def write_member_marshaller(writer, container, member, src, scope): elif t.is_primitive(): if member.has_attr("zero"): writer.statement("spice_marshaller_add_%s(m, 0)" % (t.primitive_type())) + if member.has_attr("bytes_count"): + var = "%s__ref" % member.name + scope.variable_def("void *", var) + writer.statement("%s = spice_marshaller_add_%s(m, %s)" % (var, t.primitive_type(), 0)) + elif member.has_end_attr(): writer.statement("spice_marshaller_add_%s(m, *(%s_t *)end)" % (t.primitive_type(), t.primitive_type())) writer.increment("end", t.sizeof()) diff --git a/python_modules/spice_parser.py b/python_modules/spice_parser.py index 65916b35..61ef458b 100644 --- a/python_modules/spice_parser.py +++ b/python_modules/spice_parser.py @@ -87,7 +87,7 @@ def SPICE_BNF(): attribute = Group(Combine ("@" + identifier) + Optional(lparen + delimitedList(attributeValue) + rparen)) attributes = Group(ZeroOrMore(attribute)) arraySizeSpecImage = Group(image_size_ + lparen + integer + comma + identifier + comma + identifier + rparen) - arraySizeSpecBytes = Group(bytes_ + lparen + identifier + rparen) + arraySizeSpecBytes = Group(bytes_ + lparen + identifier + comma + identifier + rparen) arraySizeSpecCString = Group(cstring_ + lparen + rparen) arraySizeSpec = lbrack + Optional(identifier ^ integer ^ arraySizeSpecImage ^ arraySizeSpecBytes ^arraySizeSpecCString, default="") + rbrack variableDef = Group(typeSpec + Optional("*", default=None) + identifier + Optional(arraySizeSpec, default=None) + attributes - semi) \ |