False positive on LocationParser.attribute_has_location() (#501)
[pyelftools.git] / test / test_dwarf_locationattr.py
1 #-------------------------------------------------------------------------------
2 # elftools tests
3 #
4 # Eli Bendersky (eliben@gmail.com)
5 # This code is in the public domain
6 #-------------------------------------------------------------------------------
7 import unittest
8
9 from elftools.dwarf.locationlists import LocationParser
10 from elftools.dwarf.die import AttributeValue
11
12 class TestLocationAttrubute(unittest.TestCase):
13 def test_has_location(self):
14 # This attribute comes from a DWARFv3 binary that doesn't have a location lists
15 # section. Before the patch, pyelftools would interpret it as an attribute with a
16 # location, more specifically with a location list offset (as opposed to an expression).
17 # Meanwhile, by the spec, DW_AT_data_member_location is not even capable
18 # of storing a location list offset (since structure layout
19 # can't vary by code location). DWARFv3 spec also provides that DW_AT_data_member_location
20 # may be a small integer with an offset from the structure's base address, and that
21 # seems to be the case here. Ergo, pyelftools should not claim this attribute a location.
22 # Since the location/loclist parse function uses the same check, ths fix will
23 # prevent such attribute values from being misparsed, also.
24 #
25 # The notion that member location in a structure had to be a DWARF expression
26 # was a misnomer all along - how often does one see a compound datatype
27 # with a static member set but a dynamic layout?
28 attr = AttributeValue(name='DW_AT_data_member_location', form='DW_FORM_data1', value=0, raw_value=0, offset=402, indirection_length=0)
29 self.assertFalse(LocationParser.attribute_has_location(attr, 3))
30
31 # This attribute comes from a DWARFv5 binary. Its form unambiguously tells us it's a
32 # location expression. Before the patch, pyelftools would not recognize it as one,
33 # because it has a hard-coded list of attributes that may contain a location, and
34 # DW_AT_call_target was not in that list.
35 attr = AttributeValue(name='DW_AT_call_target', form='DW_FORM_exprloc', value=[80], raw_value=[80], offset=8509, indirection_length=0)
36 self.assertTrue(LocationParser.attribute_has_location(attr, 5))
37
38
39 if __name__ == '__main__':
40 unittest.main()