python-exe-unpacker icon indicating copy to clipboard operation
python-exe-unpacker copied to clipboard

Unpacked .pyc files are invalid (with dirty solution)

Open Gowee opened this issue 5 years ago • 10 comments

When I try to decompile .pyc files generated by python-exe-unpacker, I got the following error:

Traceback (most recent call last):
  File "/usr/local/lib/python3.7/site-packages/xdis/load.py", line 209, in load_module_from_file_object
    co = marshal.loads(bytecode)
ValueError: bad marshal data (unknown type code)

And those .pyc are also treated invalid by Python interpreter:

RuntimeError: Bad code object in .pyc file

After spending two hours figuring out what's wrong, I think it is valuable to note them down here even if this project seemingly has ended:

I suppose the problem resides around https://github.com/countercept/python-exe-unpacker/blob/6c88e9b28cb40615b680cefdb5f47ce4cab17833/pyinstxtractor.py#L322 where the appended header (incl. magic number, timestamp, size, etc) seems to mismatch with the .pyc format used by some newer Python versions (in my case 3.7).

To make uncompyle6 work well with malformed .pyc, dirty patch /usr/local/lib/python3.7/site-packages/xdis/load.py to make sure marshal.loads data starting from exactly 12th byte of original .pyc (e.g. utilizing BytesIO so that the fp can be read twice) helps.

Gowee avatar Jan 17 '20 15:01 Gowee

I'm currently experiencing the same issue, and even though you gave the solution, I cannot figure out how to implement it myself. What do I need to change exactly in the load.py for it to work?

EDIT: Some information, I'm using Python 3.8 and also trying to decompile a .pyc file made with Python 3.8 I've been trying to make your solution work, but so far no luck.

appieGIT avatar Jan 21 '20 19:01 appieGIT

@appieGIT The dirty way aforementioned is a little tricky. Here is another way I did not try but expected to work:

Adding a new line pycFile.write(b'\0' * 4) just after the line https://github.com/countercept/python-exe-unpacker/blob/6c88e9b28cb40615b680cefdb5f47ce4cab17833/pyinstxtractor.py#L323

Gowee avatar Jan 31 '20 06:01 Gowee

@Gowee I have tried this solution just now. It does start right now, which is something, but it keeps returning a parse error when decompyling the .pyc files with uncompyle6 or decompyle3. I'm pretty sure this is still due to invalid .pyc files from the unpacker.

Is there any other solution you can think of?

AlbertJanSch avatar Jan 31 '20 10:01 AlbertJanSch

@AlbertJanSch Would you mind sharing a sample .pyc?

Gowee avatar Jan 31 '20 11:01 Gowee

@Gowee Of course. I uploaded a sample called calendar.pyc here: https://www.sendspace.com/file/id2d1f

AlbertJanSch avatar Jan 31 '20 11:01 AlbertJanSch

@AlbertJanSch I see Parse error at or near 'POP_BLOCK' instruction at offset 36. But I do not think it owes to python-exe-unpacker. And I have no idea how to fix it. Open a issue in the uncompyle6 project instead?

Gowee avatar Jan 31 '20 12:01 Gowee

Gonna rephrase the solution in https://github.com/countercept/python-exe-unpacker/issues/14#issue-551482167 for us, newbies. If you use rocky/python-decompile3 after extracting .pyc files and get "bad marshal data", do the following:

  1. Open the file /usr/local/lib/python3.7/site-packages/xdis/load.py
  2. Find lines:
if my_magic_int == magic_int:
    bytecode = fp.read()
    co = marshal.loads(bytecode)
  1. Replace with:
if my_magic_int == magic_int:
    fp.seek(12)
    bytecode = fp.read()
    co = marshal.loads(bytecode)

fp.seek(12) skips reading of the first 12 bytes and makes the decompiler work again.

Don't forget to revert the changes after you're done with decompilation. Thanks to the original solution provider!

CopyMist avatar Mar 24 '20 11:03 CopyMist

It still doesn't works for me.. :( I tried all you have said until this message.

venaxyt avatar Nov 02 '21 17:11 venaxyt

@CopyMist solution worked great for me. Tyty

ecoop3r avatar Mar 07 '22 20:03 ecoop3r

I know this is a fairly old issue, but also try skipping 16 and 8 as well. 16 worked for me in python 3.10, I've heard 8 also works potentially.

rkbennett avatar Oct 18 '23 12:10 rkbennett