Author: Maciej Fijalkowski <[email protected]>
Branch:
Changeset: r45364:6e65afd1e3a4
Date: 2011-07-06 18:37 +0200
http://bitbucket.org/pypy/pypy/changeset/6e65afd1e3a4/
Log: start implementing slicing assembler into ops
diff --git a/pypy/jit/tool/oparser.py b/pypy/jit/tool/oparser.py
--- a/pypy/jit/tool/oparser.py
+++ b/pypy/jit/tool/oparser.py
@@ -337,6 +337,11 @@
num += 1
return num, ops, last_offset
+ def postprocess(self, loop):
+ """ A hook that can be overloaded to do some postprocessing
+ """
+ return loop
+
def parse_offset(self, line):
if line.startswith('+'):
# it begins with an offset, like: "+10: i1 = int_add(...)"
diff --git a/pypy/tool/jitlogparser/parser.py b/pypy/tool/jitlogparser/parser.py
--- a/pypy/tool/jitlogparser/parser.py
+++ b/pypy/tool/jitlogparser/parser.py
@@ -5,6 +5,8 @@
class Op(object):
bridge = None
+ offset = None
+ asm = None
def __init__(self, name, args, res, descr):
self.name = name
@@ -54,10 +56,53 @@
Op = Op
use_mock_model = True
+ def postprocess(self, loop, backend_dump=None, backend_tp=None,
+ loop_start=0, dump_start=0):
+ if backend_dump is not None:
+ raw_asm = self._asm_disassemble(backend_dump.decode('hex'),
+ backend_tp, dump_start)
+ asm = []
+ start = 0
+ for elem in raw_asm:
+ if len(elem.split("\t")) != 3:
+ continue
+ adr, _, v = elem.split("\t")
+ if not start:
+ start = int(adr.strip(":"), 16)
+ ofs = int(adr.strip(":"), 16) - start
+ if ofs >= 0:
+ asm.append((ofs, v.strip("\n")))
+ asm_index = 0
+ for i, op in enumerate(loop.operations):
+ end = 0
+ j = i + 1
+ while end == 0:
+ if j == len(loop.operations):
+ end = loop.last_offset
+ break
+ if loop.operations[j].offset is None:
+ j += 1
+ else:
+ end = loop.operations[j].offset
+ if op.offset is not None:
+ while asm[asm_index][0] < op.offset:
+ asm_index += 1
+ end_index = asm_index
+ while asm[end_index][0] < end:
+ end_index += 1
+ op.asm = '\n'.join([asm[i][1] for i in range(asm_index,
end_index)])
+ return loop
+
+ def _asm_disassemble(self, d, origin_addr, tp):
+ from pypy.jit.backend.x86.tool.viewcode import machine_code_dump
+ return list(machine_code_dump(d, tp, origin_addr))
+
@classmethod
- def parse_from_input(cls, input):
- return cls(input, None, {}, 'lltype', None,
- nonstrict=True).parse()
+ def parse_from_input(cls, input, **kwds):
+ parser = cls(input, None, {}, 'lltype', None,
+ nonstrict=True)
+ loop = parser.parse()
+ return parser.postprocess(loop, **kwds)
def parse_args(self, opname, argspec):
if not argspec.strip():
diff --git a/pypy/tool/jitlogparser/test/test_parser.py
b/pypy/tool/jitlogparser/test/test_parser.py
--- a/pypy/tool/jitlogparser/test/test_parser.py
+++ b/pypy/tool/jitlogparser/test/test_parser.py
@@ -5,8 +5,8 @@
from pypy.tool.jitlogparser.storage import LoopStorage
import py
-def parse(input):
- return SimpleParser.parse_from_input(input)
+def parse(input, **kwds):
+ return SimpleParser.parse_from_input(input, **kwds)
def test_parse():
@@ -179,3 +179,31 @@
ops = Function.from_operations(loop.operations, LoopStorage())
chunk = ops.chunks[0]
assert chunk.bytecode_name == 'StrLiteralSearch'
+
+def test_parsing_assembler():
+ backend_dump =
"554889E5534154415541564157488DA500000000488B042590C5540148C7042590C554010000000048898570FFFFFF488B042598C5540148C7042598C554010000000048898568FFFFFF488B0425A0C5540148C70425A0C554010000000048898560FFFFFF488B0425A8C5540148C70425A8C554010000000048898558FFFFFF4C8B3C2550525B0149BB30E06C96FC7F00004D8B334983C60149BB30E06C96FC7F00004D89334981FF102700000F8D000000004983C7014C8B342580F76A024983EE014C89342580F76A024983FE000F8C00000000E9AEFFFFFF488B042588F76A024829E0483B042580EC3C01760D49BB05F30894FC7F000041FFD3554889E5534154415541564157488DA550FFFFFF4889BD70FFFFFF4889B568FFFFFF48899560FFFFFF48898D58FFFFFF4D89C7E954FFFFFF49BB00F00894FC7F000041FFD34440484C3D030300000049BB00F00894FC7F000041FFD34440484C3D070304000000"
+ dump_start = 0x7f3b0b2e63d5
+ loop = parse("""
+ # Loop 0 : loop with 19 ops
+ [p0, p1, p2, p3, i4]
+ debug_merge_point(0, '<code object f. file 'x.py'. line 2> #15 COMPARE_OP')
+ +166: i6 = int_lt(i4, 10000)
+ guard_true(i6, descr=<Guard3>) [p1, p0, p2, p3, i4]
+ debug_merge_point(0, '<code object f. file 'x.py'. line 2> #27
INPLACE_ADD')
+ +179: i8 = int_add(i4, 1)
+ debug_merge_point(0, '<code object f. file 'x.py'. line 2> #31
JUMP_ABSOLUTE')
+ +183: i10 = getfield_raw(40564608, descr=<SignedFieldDescr
pypysig_long_struct.c_value 0>)
+ +191: i12 = int_sub(i10, 1)
+ +195: setfield_raw(40564608, i12, descr=<SignedFieldDescr
pypysig_long_struct.c_value 0>)
+ +203: i14 = int_lt(i12, 0)
+ guard_false(i14, descr=<Guard4>) [p1, p0, p2, p3, i8, None]
+ debug_merge_point(0, '<code object f. file 'x.py'. line 2> #9 LOAD_FAST')
+ +213: jump(p0, p1, p2, p3, i8, descr=<Loop0>)
+ +218: --end of the loop--""", backend_dump=backend_dump,
+ dump_start=dump_start,
+ backend_tp='x86_64',
+ loop_start=0x7f3b0b2e645d)
+ cmp = loop.operations[1]
+ assert 'jge' in cmp.asm
+ assert '0x2710' in cmp.asm
+ assert 'jmp' in loop.operations[-1].asm
_______________________________________________
pypy-commit mailing list
[email protected]
http://mail.python.org/mailman/listinfo/pypy-commit