Closed ptr-yudai closed 2 years ago
Hey there, thank you for the contribution.
I will have to mull this one over a bit because I'm not totally convinced on its usefulness compared to doing directly what the user wants (eg. avoiding bytes in the address etc). I think that this would be the preferred path but I could probably be convinced otherwise.
Also note that there currently is an address range filtering feature for the low address range thing.
Thanks for the quick response.
Actually I hadn't met any problems for a long time but I got a situation recently where I needed this feature. There is a very rare case that the gadget doesn't work when kASLR is enabled in kernel exploitation. The gadget comes from an instruction like
mov al,BYTE PTR [rdi-0xXXXXXXXX]
where the value 0xXXXXXXXX is recognized as pop rcx; ret;
gadget.
$ ropr vmlinux -R "^pop rcx; ret;"
0xffffffff812ea083: pop rcx; ret;
==> Found 1 gadgets in 1.042 seconds
This works fine when kASLR is disabled:
pwndbg> x/4i 0xffffffff812ea083
0xffffffff812ea083: pop rcx
0xffffffff812ea084: ret
0xffffffff812ea085: add ebx,0x100ff81
0xffffffff812ea08b: add BYTE PTR [rax],al
However, the gadget changes when kASLR is enabled:
pwndbg> x/4i 0xffffffff9e600000 + 0x2ea083
0xffffffff9e8ea083: pop rcx
0xffffffff9e8ea084: and ebx,DWORD PTR [rdi+0xff81c3]
0xffffffff9e8ea08a: add DWORD PTR [rax],eax
0xffffffff9e8ea08c: add BYTE PTR [rcx],bl
I'm still investigation why this happens in a normal Linux kernel but I guess it changes a part of the code dynamically on load. This behavior happened to some other people too. I believe this will be a common problem if FGKASLR gets enabled by default. Address range filtering would also work for this problem but I think just printing all gadgets would be more convenient.
Still, I'm not good at programming Rust so please do not trust my code. It'd be nice if you could implement this feature in a more beautiful way.
Thank you for your consideration.
That's some very strange behaviour. Plz update if you figure out why it happens.
It will probably be a few weeks until I can do anything about this PR anyway.
I like the solution of adding a unique ID to the gadgets. This seems OK to merge. Thanks for the contribution.
There is a chance that this may be removed in the future if I find a solution to this kernel self-patching thing, but for now I think it's ok.
Description
This PR introduces a new option
--nouniq
or-u
, which enables ropr to show non-unique gadgets.Motivation and Context
The current ropr deduplicates gadgets and shows only unique ones. However, sometimes it's desirable to see every gadget available. (i.e. avoid 0x0A in the gadget address / use gadgets with lower address for kernel exploitation)
Changes
I've added a new field
unique_id
toGadget
struct. This field is set to the address of the gadget when --nouniq is enabled, otherwise 0. This change can switch the behavior when it's inserted intoHashMap
.How Has This Been Tested?
I've tested some gadgets such as
pop rax; ret;
on libc binary and checked if it outputs the same gadgets as those by rp-lin-x64.