History

Fixed LDT generation, adding a trailing zero after an empty section and ensuring that items are padded to word boundaries. Added types, data and other information to the output of the list method. Started working on reading exceptions.

David Boddie committed 9 years ago

Commit f918dba1 parent 3740cbe1 file · +140 −2Browse files

Unified · Split

dis.py+140−2
@@ -21,7 +21,7 @@ import opcodes · 20 unmodified lines
21from utils import _read, read_B, read_C, read_OP, read_F, read_L, read_P, \21from utils import _read, read_B, read_C, read_OP, read_F, read_L, read_P, \
22 read_W, \22 read_W, \
23 _write, write_B, write_C, write_OP, write_F, write_L, \23 _write, write_B, write_C, write_OP, write_F, write_L, \
24 write_P, write_W24 write_P, write_W, dbl_repr
25 25
26XMAGIC = 0x0c803026XMAGIC = 0x0c8030
27SMAGIC = 0x0e172227SMAGIC = 0x0e1722
@@ -86,6 +86,9 @@ class Dis: · 58 unmodified lines
86 if self.runtime_flag.contains(RuntimeFlag.HASLDT):86 if self.runtime_flag.contains(RuntimeFlag.HASLDT):
87 self.read_ldt(f)87 self.read_ldt(f)
88 88
89 if self.runtime_flag.contains(RuntimeFlag.HASEXCEPT):
90 self.read_exceptions(f)
91
89 self.path = read_C(f)92 self.path = read_C(f)
90 93
91 def read_code(self, f):94 def read_code(self, f):
@@ -180,6 +183,8 @@ class Dis: · 88 unmodified lines
180 183
181 def read_ldt(self, f):184 def read_ldt(self, f):
182 185
186 # Described in the section about the load operand in the Dis Virtual
187 # Machine Specification.
183 self.ldt = []188 self.ldt = []
184 189
185 # The Limbo compiler seems to include the number of initialised globals.190 # The Limbo compiler seems to include the number of initialised globals.
@@ -203,6 +208,24 @@ class Dis: · 17 unmodified lines
203 i += 1208 i += 1
204 209
205 self.ldt.append(sequence)210 self.ldt.append(sequence)
211
212 # Discard the dummy value that occurs after an empty set of LDTs.
213 if not self.ldt:
214 read_OP(f)
215
216 def read_exceptions(self, f):
217
218 self.exceptions = []
219 number = read_OP(f)
220 i = 0
221
222 while i < number:
223
224 self.exceptions.append(ExceptionInfo().read(f))
225 i += 1
226
227 # Discard the dummy value that occurs after a set of exceptions.
228 read_OP(f)
206 229
207 def write(self, f):230 def write(self, f):
208 231
@@ -303,7 +326,60 @@ class Dis: · 94 unmodified lines
303 def list(self):326 def list(self):
304 327
305 for i, ins in enumerate(self.code):328 for i, ins in enumerate(self.code):
306 print hex(i), str(ins)329 print hex(i) + ":", str(ins)
330
331 print
332 print "entry %s, %i" % (hex(self.entry_pc), self.entry_type)
333
334 for type_ in self.types:
335 print 'desc $0x%x, %i, "%s"' % (type_.desc_number, type_.size,
336 "".join(map(lambda x: "%02x" % ord(x), type_.array)))
337
338 print
339 print "var @mp, %i" % self.data_size
340
341 items = self.data.items()
342 items.sort()
343
344 for address, item in items:
345 if item.array_type == 3:
346 print 'string @mp+%i, %s' % (address, dbl_repr(item.data()))
347 else:
348 print "?",
349
350 print
351 print "module", self.module_name
352
353 for link in self.link:
354 print
355 print "link %s, %i, %s, %s" % (hex(link.pc), link.desc_number,
356 hex(link.sig), dbl_repr(link.name))
357
358 if self.runtime_flag.contains(RuntimeFlag.HASLDT):
359 print
360 print "ldts @ldt, %i" % len(self.ldt)
361 i = 0
362 start = 4
363
364 for sequence in self.ldt:
365 print "word @ldt+%i,%i" % (i, len(sequence))
366 i += 1
367
368 j = start
369
370 for ldt in sequence:
371 print "ext @ldt+%i, %s, %s" % (j, hex(ldt.sig),
372 dbl_repr(ldt.name))
373 size = 4 + len(ldt.name) + 1
374 if size % 4 != 0:
375 size += 4 - (size % 4)
376 j += size
377
378 if i % 4 == 1:
379 start += 4
380
381 print
382 print "source %s" % dbl_repr(self.path)
307 383
308 384
309class RuntimeFlag:385class RuntimeFlag:
@@ -498,6 +574,8 @@ class Link: · 188 unmodified lines
498 self.desc_number = read_OP(f)574 self.desc_number = read_OP(f)
499 self.sig = read_W(f) # unsigned for hashes575 self.sig = read_W(f) # unsigned for hashes
500 self.name = read_C(f)576 self.name = read_C(f)
577
578 return self
501 579
502 def __repr__(self):580 def __repr__(self):
503 581
@@ -523,6 +601,8 @@ class LDT: · 19 unmodified lines
523 601
524 self.sig = _read(f, ">I") # unsigned for hashes602 self.sig = _read(f, ">I") # unsigned for hashes
525 self.name = read_C(f)603 self.name = read_C(f)
604
605 return self
526 606
527 def __repr__(self):607 def __repr__(self):
528 608
@@ -532,3 +612,61 @@ class LDT: · 3 unmodified lines
532 612
533 _write(f, ">I", self.sig)613 _write(f, ">I", self.sig)
534 write_C(f, self.name)614 write_C(f, self.name)
615
616 # Pad to a word boundary if necessary.
617 remainder = len(self.name) % 4
618 if remainder != 0:
619 f.write("\x00" * (4 - remainder))
620
621
622class ExceptionInfo:
623
624 def __init__(self, offset = 0, p1 = 0, p2 = 0, id = -1, nlab_ne = 0,
625 pcs = None, iwild = -1):
626
627 self.offset = offset
628 self.p1 = p1
629 self.p2 = p2
630
631 if id != -1:
632 self.desc = id
633 else:
634 self.desc = -1
635
636 if pcs:
637 self.pcs = pcs
638 else:
639 self.pcs = []
640
641 if iwild != -1:
642 self.pc = iwild
643 else:
644 self.pc = -1
645
646 def read(self, f):
647
648 self.offset = read_OP(f)
649 self.p1 = read_OP(f)
650 self.p2 = read_OP(f)
651
652 id = read_OP(f)
653 if id != -1:
654 self.desc = id
655 else:
656 self.desc = -1
657
658 nlab_ne = read_OP(f)
659 self.nlab = nlab_ne & 0xffff
660 self.ne = nlab_ne >> 16
661
662 self.pcs = []
663 i = 0
664 while i < self.nlab:
665 name = read_C(f)
666 pc = read_OP(f)
667 self.pcs.append((name, pc))
668 i += 1
669
670 self.pc = read_OP(f)
671
672 return self