Skip to content

Commit 751ec49

Browse files
UtumnoInfernio
authored andcommitted
Optimize Structure wrappers
Note the optimization is twofold - bringing unpacker to local scope and using compiled Struct. Timings pending
1 parent 78f8ba9 commit 751ec49

2 files changed

Lines changed: 44 additions & 31 deletions

File tree

Mopy/bash/bolt.py

Lines changed: 29 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -1498,23 +1498,36 @@ def pop(self,key,default=None):
14981498
return self.data.pop(key,default)
14991499

15001500
# Structure wrappers ----------------------------------------------------------
1501-
def unpack_str8(ins): return ins.read(struct_unpack(u'B', ins.read(1))[0])
1502-
def unpack_str16(ins): return ins.read(struct_unpack(u'H', ins.read(2))[0])
1503-
def unpack_str32(ins): return ins.read(struct_unpack(u'I', ins.read(4))[0])
1504-
def unpack_int(ins): return struct_unpack(u'I', ins.read(4))[0]
1505-
def unpack_short(ins): return struct_unpack(u'H', ins.read(2))[0]
1506-
def unpack_float(ins): return struct_unpack(u'f', ins.read(4))[0]
1507-
def unpack_double(ins): return struct_unpack(u'd', ins.read(8))[0]
1508-
def unpack_byte(ins): return struct_unpack(u'B', ins.read(1))[0]
1509-
def unpack_int_signed(ins): return struct_unpack(u'i', ins.read(4))[0]
1510-
def unpack_int64_signed(ins): return struct_unpack(u'q', ins.read(8))[0]
1511-
def unpack_4s(ins): return struct_unpack(u'4s', ins.read(4))[0]
1512-
def unpack_str16_delim(ins):
1513-
str_value = ins.read(struct_unpack(u'Hc', ins.read(3))[0])
1514-
ins.read(1) # discard delimiter
1501+
def unpack_str8(ins, __unpack=struct.Struct(u'B').unpack):
1502+
return ins.read(__unpack(ins.read(1))[0])
1503+
def unpack_str16(ins, __unpack=struct.Struct(u'H').unpack):
1504+
return ins.read(__unpack(ins.read(2))[0])
1505+
def unpack_str32(ins, __unpack=struct.Struct(u'I').unpack):
1506+
return ins.read(__unpack(ins.read(4))[0])
1507+
def unpack_int(ins, __unpack=struct.Struct(u'I').unpack):
1508+
return __unpack(ins.read(4))[0]
1509+
def unpack_short(ins, __unpack=struct.Struct(u'H').unpack):
1510+
return __unpack(ins.read(2))[0]
1511+
def unpack_float(ins, __unpack=struct.Struct(u'f').unpack):
1512+
return __unpack(ins.read(4))[0]
1513+
def unpack_double(ins, __unpack=struct.Struct(u'd').unpack):
1514+
return __unpack(ins.read(8))[0]
1515+
def unpack_byte(ins, __unpack=struct.Struct(u'B').unpack):
1516+
return __unpack(ins.read(1))[0]
1517+
def unpack_int_signed(ins, __unpack=struct.Struct(u'i').unpack):
1518+
return __unpack(ins.read(4))[0]
1519+
def unpack_int64_signed(ins, __unpack=struct.Struct(u'q').unpack):
1520+
return __unpack(ins.read(8))[0]
1521+
def unpack_4s(ins, __unpack=struct.Struct(u'4s').unpack):
1522+
return __unpack(ins.read(4))[0]
1523+
def unpack_str16_delim_null(ins, __unpack=struct.Struct(u'Hc').unpack):
1524+
str_value = ins.read(__unpack(ins.read(3))[0])
1525+
ins.seek(1, 1) # discard null string terminator
15151526
return str_value
1516-
def unpack_int_delim(ins): return struct_unpack(u'Ic', ins.read(5))[0]
1517-
def unpack_byte_delim(ins): return struct_unpack(u'Bc', ins.read(2))[0]
1527+
def unpack_str_int_delim(ins, __unpack=struct.Struct(u'Ic').unpack):
1528+
return __unpack(ins.read(5))[0]
1529+
def unpack_str_byte_delim(ins, __unpack=struct.Struct(u'Bc').unpack):
1530+
return __unpack(ins.read(2))[0]
15181531

15191532
def unpack_string(ins, string_len):
15201533
return struct_unpack(u'%ds' % string_len, ins.read(string_len))[0]

Mopy/bash/bosh/save_headers.py

Lines changed: 15 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -40,8 +40,8 @@
4040
from .. import bolt
4141
from ..bolt import decode, cstrip, unpack_string, unpack_int, unpack_str8, \
4242
unpack_short, unpack_float, unpack_str16, unpack_byte, struct_pack, \
43-
unpack_int_delim, unpack_str16_delim, unpack_byte_delim, unpack_many, \
44-
encode
43+
unpack_str_int_delim, unpack_str16_delim_null, unpack_str_byte_delim, \
44+
unpack_many, encode
4545
from ..bosh import ModInfo
4646
from ..exception import SaveHeaderError, raise_bolt_error
4747

@@ -427,25 +427,25 @@ class FalloutNVSaveHeader(SaveFileHeader):
427427
_masters_unknown_byte = 0x1B
428428
unpackers = OrderedDict([
429429
('header_size', (00, unpack_int)),
430-
('_unknown', (00, unpack_int_delim)),
430+
('_unknown', (00, unpack_str_int_delim)),
431431
('language', (00, lambda ins: unpack_many(ins, '64sc')[0])),
432-
('ssWidth', (00, unpack_int_delim)),
433-
('ssHeight', (00, unpack_int_delim)),
434-
('ssDepth', (00, unpack_int_delim)),
435-
('pcName', (00, unpack_str16_delim)),
436-
('pcNick', (00, unpack_str16_delim)),
437-
('pcLevel', (00, unpack_int_delim)),
438-
('pcLocation', (00, unpack_str16_delim)),
439-
('gameDate', (00, unpack_str16_delim)),
432+
('ssWidth', (00, unpack_str_int_delim)),
433+
('ssHeight', (00, unpack_str_int_delim)),
434+
('ssDepth', (00, unpack_str_int_delim)),
435+
('pcName', (00, unpack_str16_delim_null)),
436+
('pcNick', (00, unpack_str16_delim_null)),
437+
('pcLevel', (00, unpack_str_int_delim)),
438+
('pcLocation', (00, unpack_str16_delim_null)),
439+
('gameDate', (00, unpack_str16_delim_null)),
440440
])
441441

442442
def load_masters(self, ins):
443443
self._mastersStart = ins.tell()
444444
self._master_list_size(ins)
445445
self.masters = []
446-
numMasters = unpack_byte_delim(ins)
446+
numMasters = unpack_str_byte_delim(ins)
447447
for count in xrange(numMasters):
448-
self.masters.append(unpack_str16_delim(ins))
448+
self.masters.append(unpack_str16_delim_null(ins))
449449

450450
def _master_list_size(self, ins):
451451
formVersion, masterListSize = unpack_many(ins, '=BI')
@@ -459,7 +459,7 @@ def _write_masters(self, ins, out):
459459
_pack(out, '=B', self._masters_unknown_byte)
460460
_pack(out, '=I', self._master_block_size())
461461
#--Skip old masters
462-
numMasters = unpack_byte_delim(ins) # get me the Byte
462+
numMasters = unpack_str_byte_delim(ins) # get me the Byte
463463
oldMasters = self._dump_masters(ins, numMasters, out)
464464
#--Offsets
465465
offset = out.tell() - ins.tell()
@@ -473,7 +473,7 @@ def _write_masters(self, ins, out):
473473
def _dump_masters(self, ins, numMasters, out):
474474
oldMasters = []
475475
for count in xrange(numMasters):
476-
oldMasters.append(unpack_str16_delim(ins))
476+
oldMasters.append(unpack_str16_delim_null(ins))
477477
# Write new masters - note the silly delimiters
478478
_pack(out, '=B', len(self.masters))
479479
_pack(out, '=c', '|')

0 commit comments

Comments
 (0)