1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
use std::mem::{size_of, MaybeUninit, transmute};
use crate::{target_ulong, target_ptr_t, panda_physical_memory_read_external, panda_virtual_memory_read_external, panda_virtual_memory_write_external, CPUState};
const READ_CHUNK_SIZE: target_ptr_t = 0x10;
impl CPUState {
pub fn mem_read(&mut self, addr: target_ulong, len: usize) -> Vec<u8> {
let mut temp = vec![0; len];
unsafe {
if panda_virtual_memory_read_external(self, addr, temp.as_mut_ptr() as *mut i8, len as _) != 0 {
panic!("Virtual memory read failed");
}
}
temp
}
pub fn mem_write(&mut self, addr: target_ulong, data: &[u8]) {
unsafe {
if panda_virtual_memory_write_external(self, addr, transmute(data.as_ptr()), data.len() as _) != 0 {
panic!("Virtual memory write failed");
}
}
}
pub fn try_mem_read(&mut self, addr: target_ulong, len: usize) -> Option<Vec<u8>> {
let mut temp = vec![0; len];
let ret = unsafe {
panda_virtual_memory_read_external(self, addr, temp.as_mut_ptr() as *mut i8, len as _)
};
if ret == 0 {
Some(temp)
} else {
None
}
}
pub fn try_mem_read_phys(&mut self, addr: target_ptr_t, len: usize) -> Option<Vec<u8>> {
let mut temp = vec![0; len];
unsafe {
if panda_physical_memory_read_external(addr as _, temp.as_mut_ptr(), len as _) == 0 {
Some(temp)
} else {
None
}
}
}
pub fn mem_read_val<T: Sized>(&mut self, addr: target_ulong) -> T {
let mut temp = MaybeUninit::uninit();
unsafe {
if panda_virtual_memory_read_external(self, addr, temp.as_mut_ptr() as *mut i8, size_of::<T>() as _) != 0 {
panic!("Virtual memory read failed");
}
temp.assume_init()
}
}
pub fn mem_read_string(&mut self, mut addr: target_ptr_t) -> String {
let mut buf = vec![];
let mut temp = [0; READ_CHUNK_SIZE as usize];
loop {
unsafe {
panda_virtual_memory_read_external(self, addr, temp.as_mut_ptr() as *mut i8, READ_CHUNK_SIZE as _);
}
let null_index = temp.iter().position(|x| x == &0);
match null_index {
Some(index) => {
buf.extend_from_slice(&temp[0..index]);
break
}
None => {
buf.extend_from_slice(&temp);
addr += READ_CHUNK_SIZE;
}
}
}
String::from_utf8_lossy(&buf).into_owned()
}
}