eliben / pyelftools

Parsing ELF and DWARF in Python
Other
2.04k stars 512 forks source link

pyelftools failed to with an exception #531

Closed Ruturaj4 closed 7 months ago

Ruturaj4 commented 10 months ago

Failed to run pyelftools on:

I have a suspicion that it is possible that the binary is may be corrupted.

I am using following binary:

https://github.com/vusec/typearmor/blob/master/server-bins/sshd

Is there a way to circumvent this error?

Backtrace:

Traceback (most recent call last):
  File "/users/r668v698/.local/lib/python3.10/site-packages/elftools/construct/core.py", line 351, in _parse
    return self.packer.unpack(_read_stream(stream, self.length))[0]
  File "/users/r668v698/.local/lib/python3.10/site-packages/elftools/construct/core.py", line 293, in _read_stream
    raise FieldError("expected %d, found %d" % (length, len(data)))
elftools.construct.core.FieldError: expected 1, found 0

During handling of the above exception, another exception occurred:

Traceback (most recent call last):
  File "/users/r668v698/.local/lib/python3.10/site-packages/elftools/construct/core.py", line 426, in _parse
    obj.append(self.subcon._parse(stream, context))
  File "/users/r668v698/.local/lib/python3.10/site-packages/elftools/construct/core.py", line 353, in _parse
    raise FieldError(ex)
elftools.construct.core.FieldError: expected 1, found 0

During handling of the above exception, another exception occurred:

Traceback (most recent call last):
  File "/users/r668v698/.local/lib/python3.10/site-packages/elftools/common/utils.py", line 41, in struct_parse
    return struct.parse_stream(stream)
  File "/users/r668v698/.local/lib/python3.10/site-packages/elftools/construct/core.py", line 190, in parse_stream
    return self._parse(stream, Container())
  File "/users/r668v698/.local/lib/python3.10/site-packages/elftools/construct/core.py", line 276, in _parse
    return self._decode(self.subcon._parse(stream, context), context)
  File "/users/r668v698/.local/lib/python3.10/site-packages/elftools/construct/core.py", line 707, in _parse
    subobj = sc._parse(stream, context)
  File "/users/r668v698/.local/lib/python3.10/site-packages/elftools/construct/core.py", line 429, in _parse
    raise ArrayError("expected %d, found %d" % (count, c), ex)
elftools.construct.core.ArrayError: ('expected 118, found 80', FieldError(FieldError('expected 1, found 0')))

During handling of the above exception, another exception occurred:

Traceback (most recent call last):
  File "/panfs/panfs.ittc.ku.edu/scratch/r668v698/ghyali/ghidra_10.3.1_PUBLIC/Ghidra/Extensions/Ghidrathon/data/python/jeprunscript.py", line 31, in jep_runscript
    exec(compile(source, path, "exec"), {**globals(), **additional_globals})
  File "/volatile/zephyr/Ruturaj/pcfi/framework/ghrun/yali.py", line 356, in <module>
    main()
  File "/volatile/zephyr/Ruturaj/pcfi/framework/ghrun/yali.py", line 350, in main
    process_dwarf()
  File "/volatile/zephyr/Ruturaj/pcfi/framework/ghrun/yali.py", line 340, in process_dwarf
    fun_params = get_parameters(DIE)
  File "/volatile/zephyr/Ruturaj/pcfi/framework/ghrun/yali.py", line 156, in get_parameters
    typeDIE = child.cu.get_DIE_from_refaddr(child.cu.cu_offset\
  File "/users/r668v698/.local/lib/python3.10/site-packages/elftools/dwarf/compileunit.py", line 130, in get_DIE_from_refaddr
    return self._get_cached_DIE(refaddr)
  File "/users/r668v698/.local/lib/python3.10/site-packages/elftools/dwarf/compileunit.py", line 241, in _get_cached_DIE
    die = DIE(cu=self, stream=top_die_stream, offset=offset)
  File "/users/r668v698/.local/lib/python3.10/site-packages/elftools/dwarf/die.py", line 95, in __init__
    self._parse_DIE()
  File "/users/r668v698/.local/lib/python3.10/site-packages/elftools/dwarf/die.py", line 254, in _parse_DIE
    raw_value = struct_parse(structs.Dwarf_dw_form[form], self.stream)
  File "/users/r668v698/.local/lib/python3.10/site-packages/elftools/common/utils.py", line 43, in struct_parse
    raise ELFParseError(str(e))
elftools.common.exceptions.ELFParseError: ('expected 118, found 80', FieldError(FieldError('expected 1, found 0')))
eliben commented 10 months ago

Handling corrupt binaries is out of scope for pyelftools

Ruturaj4 commented 10 months ago

Handling corrupt binaries is out of scope for pyelftools

I agree as it makes perfect sense (And, it is just my speculation that the binary might be corrupted).

However, objectdump and readelf work just fine:

$readelf -wi sshd.elf | less

Contents of the .debug_info section:

  Compilation Unit @ offset 0x0:
   Length:        0x2694 (32-bit)
   Version:       4
   Abbrev Offset: 0x0
   Pointer Size:  8
 <0><b>: Abbrev Number: 1 (DW_TAG_compile_unit)
    <c>   DW_AT_producer    : (indirect string, offset: 0x0): clang version 3.4 (tags/RELEASE_34/final 249356) (llvm/tags/RELEASE_34/final 249354)
    <10>   DW_AT_language    : 12       (ANSI C99)
    <12>   DW_AT_name        : (indirect string, offset: 0x55): sshd.c
    <16>   DW_AT_low_pc      : 0x0
    <1e>   DW_AT_stmt_list   : 0x0
    <22>   DW_AT_comp_dir    : (indirect string, offset: 0x5c): /home/vvdveen/src/typearmor-runtime/apps/openssh-3.5p1
 <1><26>: Abbrev Number: 2 (DW_TAG_variable)
    <27>   DW_AT_name        : (indirect string, offset: 0x93): config_file_name
sevaa commented 10 months ago

The binary, and the DWARF in it, looks fine to me.

The error happens in the method CU.get_DIE_from_refaddr(), as called from get_parameters() in yali.py:156. The surrounding script is trying to follow a DIE reference. That call might be miswritten - passing a bogus DIE offset, one that causes the library to look in the wrong place. For one thing, I can tell that it treats whatever attribute contents are there as a CU-relative offset, which may not be the case.

It's yali.py that needs debugging, not pyelftools proper.

sevaa commented 7 months ago

@Ruturaj4 : what's the status of this? I won't mind taking a look at yali.py, if you care to share.

Ruturaj4 commented 7 months ago

@Ruturaj4 : what's the status of this? I won't mind taking a look at yali.py, if you care to share.

Yeah, I can't open source yali.py now, but I am working on some other things and don't have time to take a look at that, thanks nonetheless

sevaa commented 7 months ago

If you think the issue may be closed, please do. It does not seem like a problem with pyelftools anyway.