-
Notifications
You must be signed in to change notification settings - Fork 1.3k
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
Remove UnicornInner in Rust bindings #1632
base: dev
Are you sure you want to change the base?
Conversation
Hey I started using the new binds, and I have problems mapping memory within a hook. Example: use unicorn_engine::unicorn_const::{Arch, HookType, MemType, Mode, Permission};
use unicorn_engine::Unicorn;
pub fn page_fault_hook<D>(
emu: &mut Unicorn<D>,
_mem_type: MemType,
address: u64,
_mem_size: usize,
_value: i64,
) -> bool {
let page_start = address & 0xfffffffffffff000;
emu.mem_map(page_start, 0x1000, Permission::READ | Permission::WRITE)
.unwrap();
true
}
fn main() {
let mut unicorn = Unicorn::new(Arch::X86, Mode::MODE_64).unwrap();
unicorn
.add_mem_hook(HookType::MEM_INVALID, 0, u64::MAX, page_fault_hook)
.expect("Could not add mem hook");
} The compiler will tell me that the pub struct Unicorn<'a, D: 'a> {
handle: uc_handle,
ffi: bool,
arch: Arch,
/// to keep ownership over the hook for this uc instance's lifetime
hooks: Vec<(ffi::uc_hook, Box<dyn ffi::IsUcHook<'a> + 'a>)>,
/// To keep ownership over the mmio callbacks for this uc instance's lifetime
mmio_callbacks: Vec<MmioCallbackScope<'a>>,
data: D,
} Is there a reason why Unicorn's data can't be restricted to |
I think you are right! Fixed. |
Hmm, aliasing, and later accessing, a |
@bet4it Could you check domenukk's comments? |
I'm a newbie in Rust, and I really can't understand what @domenukk said is about. |
Some codes of this PR base on unicorn-rs. macro_rules! destructure_hook {
($hook_type:path, $hook:ident) => {{
let $hook_type { unicorn, callback } = unsafe { &mut *$hook };
(unsafe { &**unicorn }, callback)
}};
} |
I haven't found the code he is referencing, but what he means is following: Somewhere in the code you create a raw pointer from a |
OK, I have understand this now, for the callbacks you create a raw pointer of self and add this to the user data of the callback. later in the callback-wrapper you access the pointer and cast it to a Unicorn object. This is undefined in rust. The old code used |
Thanks for your help @PhilippTakacs ! @bet4it A small tip on ub: https://github.com/rust-lang/miri . Using miri may be super helpful. |
Do you mean that we cast the pointer to an Unicorn object, but if the pointer doesn't point to an Unicorn object, the behavior is undefined? But the callback is only called by the Unicorn object, so we can assure the pointer is an Unicorn object in the callback. That's what we have done in C, right? |
Yes
But C is not Rust. The important difference here is that in C you are responsible to have correct references, in Rust the language is responsible. Problem now is a mutable reference might get moved in memory. For later access rust can ensure a correct reference. But rust can't change a raw pointer. Therefore is aliasing and accessing a raw pointer of a
https://doc.rust-lang.org/stable/std/cell/struct.UnsafeCell.html But exactly this do you do with UcHook. The current code creates a owned [0] probably be the only one |
So you think |
Yes |
Fix #1619