* fix: make mprotect command truly multi-arch
Added register saving based on reg_sets defined for each processor architecture, additionally shellcraft is used to generate the arch-specific shellcode.
Unfortunately this command is not currently tested on platforms other than x86_64.
* Update pwndbg/commands/mprotect.py
Co-authored-by: Disconnect3d <dominik.b.czarnota@gmail.com>
* mprotect: Add parsing, alignment to the addr argument
This change makes sure that the addr argument is parsed as an gdb expression (so you can use registers for example) and aligns it to the nearest page boundary.
* mprotect: Clean up register saving, print the result
Cleaned up saving of registers and added printing of the results, as per disconnect's sugesstions.
* Simplify the test for mprotect
Simplify the code and remove the useless binary
* Update tests/test_mprotect.py
Co-authored-by: Disconnect3d <dominik.b.czarnota@gmail.com>
The `set history expansion on` setting we set seems to cause troubles if users want to execute a shell command by using the exclamation mark.
I do not like it, especially taking into account the recent shell command deprecation we did.
* Add reset_on_thread decorator
* Apply reset_on_thread to Heap.multithreaded
* Add multithreaded malloc_chunk tests
* Clarify comment in C source
* Clarify expected thread number with assert in test
* Don't catch the error of the heap commands for developers
* Use `pwndbg.config` and re-raise the error
See https://github.com/pwndbg/pwndbg/pull/1270#discussion_r992209956
* Update pwndbg/commands/__init__.py
Co-authored-by: Disconnect3d <dominik.b.czarnota@gmail.com>
Before this commit we passed `pwndbg.gdblib.arch.current` as `arch=...`
keyword argument to pwnlib functions like `asm` and `disasm`.
Since pwnlib has a concept of "context" that holds variables like
currently set architecture or number of bits, this commit starts using
those for the `patch` command implementation as we started to set pwnlib
context recently in 9e84c18c44
* Fix#1256: fixes next cmds hangs on segfaults
Before this commit the next/step commands like `nextret`, `stepret`,
`nextsyscall`, `nextproginstr` etc. would hang if they approach a
segfault. This commit fixes it by checking for ANY signals by executing
the GDB's `info prog` command and parsing its output.
* fix lint
This commit allows for setting the selected thread's registers by using
the pwndbg.gdblib.regs.<register-name> = <new-value> expressions. Before
this commit invoking such Python code would set the internal Pwndbg
register value, but not really the inferior value. This could lead to
weird issues when the displayed context shows the new register value but
e.g. `info reg rax` displays the old value.
* Move symbol.py to gdblib
* Renamed private methods
* Renamed pwndbg.symbol to pwndbg.gdblib.symbol
* Cleanup symbol.py
* Fix lint issues
* Handle tls error on symbol lookup
* Fix merge conflicts
* Remove old way of looking up symbols
* Enhance the error handling of the heap command
* Add a new method: `can_be_resolved()` to heap classes to check whether we can resolve the heap after the heap is initialized.
* Add a new function: `get_got_plt_address()` to `pwndbg.glibc`, by doing this, we can determine the location of the symbols without `_IO_list_all` by parsing the output of `info files`.
* Add a new subclass of Exception: `SymbolUnresolvableError` to handle the error when we can't resolve some symbols.
* If we didn't set the GLIBC version manually, we won't get the unnecessary Python error from this now, instead, we tell the user how to set it.
* If we didn't have enough information to resolve some symbols, we show which symbol we lack and tell the user how to set it manually instead of just executing it and showing a Python error.
* Avoid getting the wrong heap config
* List the symbols manually instead of using `locals()`
* Avoid the extra function call by `can_be_resolved`
* Enhance the error handling when finding TLS (#1237)
* Enhance the error handling for more cases
* Add support to use `gdb.lookup_static_symbol` in `pwndbg.symbol`
* Enhance the strategy when handling the heap-related symbols
* Use `pwndbg.symbol.static_linkage_symbol_address()` to get the address of the symbol first
e.g. Let's say we have a file called `FILENAME.c`:
```
void *main_arena = 0xdeadbeaf;
int main(){
free(malloc(0x20));
return 0;
}
```
If we compiled it with `gcc FILENAME.c -g`, the old heap command will fail because it thinks `main_arena` is this 0xdeadbeaf `main_arena`, not the "real" `main_arena` in GLIBC.
With this commit, it should work without this issue.
* Revert "Enhance the error handling when finding TLS (#1237)"
This reverts commit 7d2d1ae6b6.
* Enhance the error handling when finding TLS (#1237)
* Catch the error when reading the address of the static linkage symbol
* Bug fix for `thread_cache` under heuristic mode
* Bug fix for `static_linkage_symbol_address()`
* If `gdb.lookup_static_symbol(symbol)` is None, it will cause the
error.
* Use new code after refactoring
* Fix#1197: dont display ctx on reg/mem changes
This commit fixes a bug where we displayed context on registers or memory changes made by the user, so e.g. when user executed one of:
```
set *rax=1
set *(int*)0x<some address> = 0x1234
set *(unsigned long long*)$rsp+4=0x44444444
```
It fixes it by just... setting a flag after the context is displayed for
the first time and resetting it on a continue GDB event.
There was a previous attempt to fix this bug in #1226 but it was rather
a hack than a proper fix. This current commit should be a proper fix :P.
Below is some more explanation of this bug.
The fact that we displayed ctx on regs/mem changes was a result us clearing the cache of the `prompt_hook_on_stop` function:
```python
@pwndbg.lib.memoize.reset_on_stop
def prompt_hook_on_stop(*a):
pwndbg.commands.context.context()
```
Where this function is called in `prompt_hook`, on each prompt display:
```python
def prompt_hook(*a):
global cur
new = (gdb.selected_inferior(), gdb.selected_thread())
if cur != new:
pwndbg.gdblib.events.after_reload(start=cur is None)
cur = new
if pwndbg.proc.alive and pwndbg.proc.thread_is_stopped:
prompt_hook_on_stop(*a)
```
So, since we cleared this function cache on each register/memory changes, it resulted in us displaying context on each prompt hook.
So how did we clear this function cache? Through the `memoize_on_stop` function:
```
@pwndbg.gdblib.events.stop
@pwndbg.gdblib.events.mem_changed
@pwndbg.gdblib.events.reg_changed
def memoize_on_stop():
reset_on_stop._reset()
```
But why? We need this to make sure that all of the executed commands, when they read memory or registry, get proper new (not cached) values!
So it makes sense to keep reseting the stop caches on mem/reg changed events. Otherwise, we would use incorrect (old) values if user set a register/memory and then used some commands like `context` or other that depend on register/memory state.
* lint