Added license snippet to all files in the code. Whitespace cleanup.
[pyelftools.git] / test / test_dwarf_lineprogram.py
1 #-------------------------------------------------------------------------------
2 # elftools tests
3 #
4 # Eli Bendersky (eliben@gmail.com)
5 # This code is in the public domain
6 #-------------------------------------------------------------------------------
7 try:
8 import unittest2 as unittest
9 except ImportError:
10 import unittest
11 import sys
12
13 sys.path.extend(['.', '..'])
14 from elftools.common.py3compat import BytesIO, iteritems
15 from elftools.dwarf.lineprogram import LineProgram, LineState, LineProgramEntry
16 from elftools.dwarf.structs import DWARFStructs
17 from elftools.dwarf.constants import *
18
19
20 class TestLineProgram(unittest.TestCase):
21 def _make_program_in_stream(self, stream):
22 """ Create a LineProgram from the given program encoded in a stream
23 """
24 ds = DWARFStructs(little_endian=True, dwarf_format=32, address_size=4)
25 header = ds.Dwarf_lineprog_header.parse(
26 b'\x04\x10\x00\x00' + # initial lenght
27 b'\x03\x00' + # version
28 b'\x20\x00\x00\x00' + # header length
29 b'\x01\x01\x01\x0F' + # flags
30 b'\x0A' + # opcode_base
31 b'\x00\x01\x04\x08\x0C\x01\x01\x01\x00' + # standard_opcode_lengths
32 # 2 dir names followed by a NULL
33 b'\x61\x62\x00\x70\x00\x00' +
34 # a file entry
35 b'\x61\x72\x00\x0C\x0D\x0F' +
36 # and another entry
37 b'\x45\x50\x51\x00\x86\x12\x07\x08' +
38 # followed by NULL
39 b'\x00')
40
41 lp = LineProgram(header, stream, ds, 0, len(stream.getvalue()))
42 return lp
43
44 def assertLineState(self, state, **kwargs):
45 """ Assert that the state attributes specified in kwargs have the given
46 values (the rest are default).
47 """
48 for k, v in iteritems(kwargs):
49 self.assertEqual(getattr(state, k), v)
50
51 def test_spec_sample_59(self):
52 # Sample in figure 59 of DWARFv3
53 s = BytesIO()
54 s.write(
55 b'\x02\xb9\x04' +
56 b'\x0b' +
57 b'\x38' +
58 b'\x82' +
59 b'\x73' +
60 b'\x02\x02' +
61 b'\x00\x01\x01')
62
63 lp = self._make_program_in_stream(s)
64 linetable = lp.get_entries()
65
66 self.assertEqual(len(linetable), 7)
67 self.assertIs(linetable[0].state, None) # doesn't modify state
68 self.assertEqual(linetable[0].command, DW_LNS_advance_pc)
69 self.assertEqual(linetable[0].args, [0x239])
70 self.assertLineState(linetable[1].state, address=0x239, line=3)
71 self.assertEqual(linetable[1].command, 0xb)
72 self.assertEqual(linetable[1].args, [2, 0])
73 self.assertLineState(linetable[2].state, address=0x23c, line=5)
74 self.assertLineState(linetable[3].state, address=0x244, line=6)
75 self.assertLineState(linetable[4].state, address=0x24b, line=7, end_sequence=False)
76 self.assertEqual(linetable[5].command, DW_LNS_advance_pc)
77 self.assertEqual(linetable[5].args, [2])
78 self.assertLineState(linetable[6].state, address=0x24d, line=7, end_sequence=True)
79
80 def test_spec_sample_60(self):
81 # Sample in figure 60 of DWARFv3
82 s = BytesIO()
83 s.write(
84 b'\x09\x39\x02' +
85 b'\x0b' +
86 b'\x09\x03\x00' +
87 b'\x0b' +
88 b'\x09\x08\x00' +
89 b'\x0a' +
90 b'\x09\x07\x00' +
91 b'\x0a' +
92 b'\x09\x02\x00' +
93 b'\x00\x01\x01')
94
95 lp = self._make_program_in_stream(s)
96 linetable = lp.get_entries()
97
98 self.assertEqual(len(linetable), 10)
99 self.assertIs(linetable[0].state, None) # doesn't modify state
100 self.assertEqual(linetable[0].command, DW_LNS_fixed_advance_pc)
101 self.assertEqual(linetable[0].args, [0x239])
102 self.assertLineState(linetable[1].state, address=0x239, line=3)
103 self.assertLineState(linetable[3].state, address=0x23c, line=5)
104 self.assertLineState(linetable[5].state, address=0x244, line=6)
105 self.assertLineState(linetable[7].state, address=0x24b, line=7, end_sequence=False)
106 self.assertLineState(linetable[9].state, address=0x24d, line=7, end_sequence=True)
107
108
109 if __name__ == '__main__':
110 unittest.main()
111