Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Mnemonic of kernel instructions as NOP DWORD #1

Closed
colbacc8 opened this issue Dec 22, 2020 · 6 comments
Closed

Mnemonic of kernel instructions as NOP DWORD #1

colbacc8 opened this issue Dec 22, 2020 · 6 comments

Comments

@colbacc8
Copy link

Hi! I'm using the distorm3 tool in a simulator named COTSon and I noticed a possible bug of the distorm...or mybe I'm wrong in interpreting the output of the distorm.

In my execution environment, the instructions are executed inside a virtual machine Linux based named SimNow. The executed instructions are, then, passed to the COTSon simulator which disassembles the instructions through the distorm3 tool.

I print out an execution trace with all the information regarding the executed instruction (physical address, virtual address, opcode) adding also the distorm3 output (operands, mnemonic).

During the validation of the trace output, I noticed some kernel instructions with mnemonic name as "NOP DWORD", which seems not a x86_64 instruction.

So, I extracted the kernel image used during the experiment and I compared the objdump output with the output of distorm3 by using the virtual addresses. As result, I noticed that some of the NOP DWORD instructions interpreted by the distorm are actually named "callq" in the output of distorm.

Can be considered a wrong interpretation of the kernel instruction? Or the distorm3 has a "default" case when it cannot disassembles the mnemonic of an instruction?

@gdabah
Copy link
Owner

gdabah commented Dec 24, 2020

Hi @colbacc8
Thanks for the detail submission, however if I don't have the actual disassembled bytes I can't help you.
If you can please share them with me, then I will be able to cross check with the documentation and distorm's results and learn if it's legit result or not.

Thanks

@gdabah
Copy link
Owner

gdabah commented Jan 3, 2021

@colbacc8 bumping. Requiring more info please.

@colbacc8
Copy link
Author

colbacc8 commented Jan 8, 2021

Hi gdabah, sorry for the late reply...
I noticed several NOP DWORD in the execution trace translated by distorm3, sometimes are correct sometimes seem not...

  1. working correctly case:
    Disassebling with objdump the executed binary, this is an instruction correctly translated in NOP DWORD

image

output of trace information + distorm3 (fields are: 1)physical address, 2) virtual address, 3) instruction size, 4) opcode, 5) coreid 6)mnemonics + operand (output of distorm3)

image

  1. The translation seems different in case of a kernel instruction.
    This is the instructions disassembled from the used linux kernel image, which is a callq to the "rcu_irq_enter" syscall
    image

the mnemonic and operand output in the distorm3 is the following:
image

as you can see, the callq is translated with NOP DWORD.
What I noticed is that also the opcode differs...

I followed the trace and the objdump output of the linux kernel instruction by instruction and at the point of the NOP DWORD should be exactly the callq to the syscall...

@gdabah
Copy link
Owner

gdabah commented Jan 8, 2021 via email

@colbacc8
Copy link
Author

colbacc8 commented Jan 8, 2021

sorry, it was a mistake in linking the screenshot...I updated my previous answer...
the virtual addresses are now equal (second field of the output trace)

yes, I'm decoding in 64 bits mode.

I'm controlling also if the problem depends on the relocation...

@gdabah
Copy link
Owner

gdabah commented Jan 9, 2021

It doesn’t matter if the virtual addresses happen to be correct if the actual bytes disassembled are not! Means it’s a different instruction.

make sure you start disassembling from a fixed known address like the start of the function and even then if there’s data in between distorm doesn’t know it - it reads everything linearly nevertheless so you can get different stuff. Comparison must be done correctly using same bytes only. In case of different addresses something is wrong with your file-memory offsets or usage as explained.
Thanks and good luck

@gdabah gdabah closed this as completed Jan 9, 2021
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants