Finish creating structure from recipe. TODO: Storing to GCD file.

This commit is contained in:
Markus Birth 2018-10-22 23:50:24 +02:00
parent becb94eb88
commit 70c0734d34
Signed by: mbirth
GPG Key ID: A9928D7A098C3A9A
2 changed files with 82 additions and 14 deletions

View File

@ -2,7 +2,7 @@
# Thanks to TurboCCC and kunix for all your work! # Thanks to TurboCCC and kunix for all your work!
from .chksum import ChkSum from .chksum import ChkSum
from .tlv import TLV, TLV6, TLV7 from .tlv import TLV, TLV6, TLV7, TLVbinary
from struct import unpack from struct import unpack
import configparser import configparser
@ -166,13 +166,39 @@ class Gcd:
if s == "GCD_DUMP": if s == "GCD_DUMP":
continue continue
print("Parsing {}".format(s)) print("Parsing {}".format(s))
params = []
for k in rcp[s]:
params.append((k, rcp[s][k]))
if "from_file" in rcp[s]: if "from_file" in rcp[s]:
# BINARY! Must create type 0006, 0007 and actual binary blocks # BINARY! Must create type 0006, 0007 and actual binary block(s)
tlv6 = TLV6(0x0006, None)
tlv6.load_dump(params)
gcd.struct.append(tlv6)
tlv7 = TLV7(0x0007, None)
tlv7.set_tlv6(tlv6)
tlv7.load_dump(params)
gcd.struct.append(tlv7)
tlv7.parse()
filename = rcp[s]["from_file"]
file_type_id = tlv7.binary_type_id
with open(filename, "rb") as bf:
while True:
read_bytes = bf.read(0xff00)
btlv = TLVbinary(file_type_id, len(read_bytes))
btlv.value = read_bytes
gcd.struct.append(btlv)
if len(read_bytes) < 0xff00:
break
bf.close()
print("Binary block") print("Binary block")
else: else:
params = []
for k in rcp[s]:
params.append((k, rcp[s][k]))
tlv = TLV.create_from_dump(params) tlv = TLV.create_from_dump(params)
gcd.struct.append(tlv) gcd.struct.append(tlv)
return gcd return gcd
def save(self, filename):
self.filename = filename

View File

@ -180,20 +180,28 @@ class TLV6(TLV):
0x5003: ["", "End of definition marker"], 0x5003: ["", "End of definition marker"],
} }
def parse(self): def __init__(self, type_id: int, expected_length: int, value=None, offset: int=None):
if len(self.value) % 2 != 0: super().__init__(type_id, expected_length, value, offset)
raise Exception("Invalid TLV6 payload length!")
self.fids = [] self.fids = []
self.format = "" self.format = ""
self.fields = [] self.fields = []
def add_fid(self, fid: int):
fdef = self.FIELD_TYPES[fid]
self.fids.append(fid)
self.format += fdef[0]
self.fields.append(fdef[1])
def parse(self):
if self.is_parsed:
# already parsed
return
if len(self.value) % 2 != 0:
raise Exception("Invalid TLV6 payload length!")
for i in range(0, len(self.value), 2): for i in range(0, len(self.value), 2):
fid = unpack("H", self.value[i:i+2])[0] fid = unpack("<H", self.value[i:i+2])[0]
fdef = self.FIELD_TYPES[fid] self.add_fid(fid)
self.fids.append(fid)
self.format += fdef[0]
self.fields.append(fdef[1])
self.is_parsed = True self.is_parsed = True
@ -209,16 +217,32 @@ class TLV6(TLV):
# Dump nothing as important info will be chained in binary dump # Dump nothing as important info will be chained in binary dump
return [] return []
def load_dump(self, values):
self.value = b""
for (k, v) in values:
if k == "from_file":
continue
elif k[0:2] != "0x":
continue
fid = int(k, 0)
self.value += pack("<H", fid)
self.value += pack("<H", 0x5003)
self.length = len(self.value)
class TLV7(TLV): class TLV7(TLV):
def __init__(self, type_id: int, expected_length: int, value=None, offset: int=None): def __init__(self, type_id: int, expected_length: int, value=None, offset: int=None):
super().__init__(type_id, expected_length, value, offset) super().__init__(type_id, expected_length, value, offset)
self.tlv6 = None self.tlv6 = None
self.binary_type_id = None
self.attr = [] self.attr = []
def set_tlv6(self, tlv6: TLV6): def set_tlv6(self, tlv6: TLV6):
self.tlv6 = tlv6 self.tlv6 = tlv6
def parse(self): def parse(self):
if self.is_parsed:
# already parsed
return
if not self.tlv6.is_parsed: if not self.tlv6.is_parsed:
# Make sure we have the structure analysed # Make sure we have the structure analysed
self.tlv6.parse() self.tlv6.parse()
@ -226,6 +250,8 @@ class TLV7(TLV):
for i, v in enumerate(values): for i, v in enumerate(values):
fid = self.tlv6.fids[i] fid = self.tlv6.fids[i]
self.attr.append((fid, v)) self.attr.append((fid, v))
if fid == 0x100a:
self.binary_type_id = v
self.is_parsed = True self.is_parsed = True
def __str__(self): def __str__(self):
@ -247,6 +273,22 @@ class TLV7(TLV):
# Dump nothing as important info will be chained in binary dump # Dump nothing as important info will be chained in binary dump
return [] return []
def load_dump(self, values):
self.value = b""
new_values = []
for (k, v) in values:
if k == "from_file":
continue
elif k[0:2] != "0x":
continue
numval = int(v, 0)
new_values.append(numval)
if not self.tlv6.is_parsed:
# Make sure we have the structure analysed (need format attr)
self.tlv6.parse()
self.value = pack("<" + self.tlv6.format, *new_values)
self.length = len(self.value)
class TLVbinary(TLV): class TLVbinary(TLV):
def __init__(self, type_id: int, expected_length: int, value=None, offset: int=None): def __init__(self, type_id: int, expected_length: int, value=None, offset: int=None):
super().__init__(type_id, expected_length, value, offset) super().__init__(type_id, expected_length, value, offset)