Skip to content

Commit 7e0dc68

Browse files
authored
Refactor read/write hooks (#99)
* Refactor read/write hooks * add PC to the callbacks * simplify code, merge common code * remove useless tcg frees * use tcg_constant_tl as much as possible, removing most #if in libafl code.
1 parent 30ad91f commit 7e0dc68

File tree

11 files changed

+179
-214
lines changed

11 files changed

+179
-214
lines changed

include/libafl/hook.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -53,7 +53,7 @@
5353
}
5454

5555
// TODO: cleanup this
56-
extern target_ulong libafl_gen_cur_pc;
56+
extern tcg_target_ulong libafl_gen_cur_pc;
5757
extern size_t libafl_qemu_hooks_num;
5858

5959
void libafl_tcg_gen_asan(TCGTemp* addr, size_t size);

include/libafl/hooks/tcg/instruction.h

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,8 @@
1414
#define LIBAFL_TABLES_HASH(p) \
1515
(((13 * ((size_t)(p))) ^ (((size_t)(p)) >> 15)) % LIBAFL_TABLES_SIZE)
1616

17+
typedef void (*libafl_instruction_cb)(uint64_t data, target_ulong pc);
18+
1719
struct libafl_instruction_hook {
1820
// data
1921
uint64_t data;
@@ -28,8 +30,7 @@ struct libafl_instruction_hook {
2830
};
2931

3032
size_t libafl_qemu_add_instruction_hooks(target_ulong pc,
31-
void (*callback)(uint64_t data,
32-
target_ulong pc),
33+
libafl_instruction_cb callback,
3334
uint64_t data, int invalidate);
3435

3536
int libafl_qemu_remove_instruction_hook(size_t num, int invalidate);

include/libafl/hooks/tcg/read_write.h

Lines changed: 20 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -2,11 +2,6 @@
22

33
#include "qemu/osdep.h"
44

5-
#include "qapi/error.h"
6-
7-
#include "exec/exec-all.h"
8-
#include "exec/tb-flush.h"
9-
105
#include "libafl/exit.h"
116
#include "libafl/hook.h"
127

@@ -17,9 +12,16 @@
1712
#define LIBAFL_TABLES_HASH(p) \
1813
(((13 * ((size_t)(p))) ^ (((size_t)(p)) >> 15)) % LIBAFL_TABLES_SIZE)
1914

15+
typedef uint64_t (*libafl_rw_gen_cb)(uint64_t data, target_ulong pc,
16+
TCGTemp* addr, MemOpIdx oi);
17+
typedef void (*libafl_rw_exec_cb)(uint64_t data, uint64_t id, target_ulong pc,
18+
target_ulong addr);
19+
typedef void (*libafl_rw_execN_cb)(uint64_t data, uint64_t id, target_ulong pc,
20+
target_ulong addr, size_t size);
21+
2022
struct libafl_rw_hook {
2123
// functions
22-
uint64_t (*gen)(uint64_t data, target_ulong pc, TCGTemp* addr, MemOpIdx oi);
24+
libafl_rw_gen_cb gen;
2325

2426
// data
2527
uint64_t data;
@@ -36,25 +38,18 @@ struct libafl_rw_hook {
3638
struct libafl_rw_hook* next;
3739
};
3840

39-
void libafl_gen_read(TCGTemp* addr, MemOpIdx oi);
40-
void libafl_gen_write(TCGTemp* addr, MemOpIdx oi);
41-
42-
size_t libafl_add_read_hook(
43-
uint64_t (*gen)(uint64_t data, target_ulong pc, TCGTemp* addr, MemOpIdx oi),
44-
void (*exec1)(uint64_t data, uint64_t id, target_ulong addr),
45-
void (*exec2)(uint64_t data, uint64_t id, target_ulong addr),
46-
void (*exec4)(uint64_t data, uint64_t id, target_ulong addr),
47-
void (*exec8)(uint64_t data, uint64_t id, target_ulong addr),
48-
void (*execN)(uint64_t data, uint64_t id, target_ulong addr, size_t size),
49-
uint64_t data);
50-
size_t libafl_add_write_hook(
51-
uint64_t (*gen)(uint64_t data, target_ulong pc, TCGTemp* addr, MemOpIdx oi),
52-
void (*exec1)(uint64_t data, uint64_t id, target_ulong addr),
53-
void (*exec2)(uint64_t data, uint64_t id, target_ulong addr),
54-
void (*exec4)(uint64_t data, uint64_t id, target_ulong addr),
55-
void (*exec8)(uint64_t data, uint64_t id, target_ulong addr),
56-
void (*execN)(uint64_t data, uint64_t id, target_ulong addr, size_t size),
57-
uint64_t data);
41+
void libafl_gen_read(TCGTemp* pc, TCGTemp* addr, MemOpIdx oi);
42+
void libafl_gen_write(TCGTemp* pc, TCGTemp* addr, MemOpIdx oi);
43+
44+
size_t libafl_add_read_hook(libafl_rw_gen_cb gen, libafl_rw_exec_cb exec1,
45+
libafl_rw_exec_cb exec2, libafl_rw_exec_cb exec4,
46+
libafl_rw_exec_cb exec8, libafl_rw_execN_cb execN,
47+
uint64_t data);
48+
49+
size_t libafl_add_write_hook(libafl_rw_gen_cb gen, libafl_rw_exec_cb exec1,
50+
libafl_rw_exec_cb exec2, libafl_rw_exec_cb exec4,
51+
libafl_rw_exec_cb exec8, libafl_rw_execN_cb execN,
52+
uint64_t data);
5853

5954
int libafl_qemu_remove_read_hook(size_t num, int invalidate);
6055
int libafl_qemu_remove_write_hook(size_t num, int invalidate);

libafl/cpu.c

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -140,7 +140,8 @@ int libafl_qemu_num_regs(CPUState* cpu)
140140
if (cc->gdb_num_core_regs) {
141141
num_regs = cc->gdb_num_core_regs;
142142
} else {
143-
const GDBFeature *feature = gdb_find_static_feature(cc->gdb_core_xml_file);
143+
const GDBFeature* feature =
144+
gdb_find_static_feature(cc->gdb_core_xml_file);
144145

145146
g_assert(feature);
146147
g_assert(feature->num_regs > 0);

libafl/exit.c

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -165,7 +165,6 @@ void libafl_qemu_breakpoint_run(vaddr pc_next)
165165
if (bp->addr == pc_next) {
166166
TCGv_i64 tmp0 = tcg_constant_i64((uint64_t)pc_next);
167167
gen_helper_libafl_qemu_handle_breakpoint(tcg_env, tmp0);
168-
tcg_temp_free_i64(tmp0);
169168
}
170169
bp = bp->next;
171170
}

libafl/hooks/tcg/cmp.c

Lines changed: 1 addition & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -116,14 +116,8 @@ void libafl_gen_cmp(target_ulong pc, TCGv op0, TCGv op1, MemOp ot)
116116
TCGv_i64 tmp0 = tcg_constant_i64(hook->data);
117117
TCGv_i64 tmp1 = tcg_constant_i64(cur_id);
118118
TCGTemp* tmp2[4] = {tcgv_i64_temp(tmp0), tcgv_i64_temp(tmp1),
119-
#if TARGET_LONG_BITS == 32
120-
tcgv_i32_temp(op0), tcgv_i32_temp(op1)};
121-
#else
122-
tcgv_i64_temp(op0), tcgv_i64_temp(op1)};
123-
#endif
119+
tcgv_tl_temp(op0), tcgv_tl_temp(op1)};
124120
tcg_gen_callN(info->func, info, NULL, tmp2);
125-
tcg_temp_free_i64(tmp0);
126-
tcg_temp_free_i64(tmp1);
127121
}
128122
hook = hook->next;
129123
}

libafl/hooks/tcg/instruction.c

Lines changed: 13 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -3,18 +3,21 @@
33

44
#include "libafl/cpu.h"
55

6-
target_ulong libafl_gen_cur_pc;
6+
static TCGHelperInfo libafl_instruction_info = {
7+
.func = NULL,
8+
.name = "libafl_instruction_hook",
9+
.flags = dh_callflag(void),
10+
.typemask = dh_typemask(void, 0) | dh_typemask(i64, 1) | dh_typemask(tl, 2),
11+
};
12+
13+
tcg_target_ulong libafl_gen_cur_pc;
714
struct libafl_instruction_hook*
815
libafl_qemu_instruction_hooks[LIBAFL_TABLES_SIZE];
916
size_t libafl_qemu_hooks_num = 0;
1017

1118
size_t libafl_qemu_add_instruction_hooks(target_ulong pc,
12-
void (*callback)(uint64_t data,
13-
target_ulong pc),
14-
uint64_t
15-
16-
data,
17-
int invalidate)
19+
libafl_instruction_cb callback,
20+
uint64_t data, int invalidate)
1821
{
1922
CPUState* cpu;
2023

@@ -27,13 +30,9 @@ size_t libafl_qemu_add_instruction_hooks(target_ulong pc,
2730
struct libafl_instruction_hook* hk =
2831
calloc(sizeof(struct libafl_instruction_hook), 1);
2932
hk->addr = pc;
30-
// hk->callback = callback;
3133
hk->data = data;
34+
hk->helper_info = libafl_instruction_info;
3235
hk->helper_info.func = callback;
33-
hk->helper_info.name = "libafl_instruction_hook";
34-
hk->helper_info.flags = dh_callflag(void);
35-
hk->helper_info.typemask =
36-
dh_typemask(void, 0) | dh_typemask(i64, 1) | dh_typemask(tl, 2);
3736
// TODO check for overflow
3837
hk->num = libafl_qemu_hooks_num++;
3938
hk->next = libafl_qemu_instruction_hooks[idx];
@@ -117,20 +116,8 @@ void libafl_qemu_hook_instruction_run(vaddr pc_next)
117116
libafl_search_instruction_hook(pc_next);
118117
if (hk) {
119118
TCGv_i64 tmp0 = tcg_constant_i64(hk->data);
120-
#if TARGET_LONG_BITS == 32
121-
TCGv_i32 tmp1 = tcg_constant_i32(pc_next);
122-
TCGTemp* tmp2[2] = {tcgv_i64_temp(tmp0), tcgv_i32_temp(tmp1)};
123-
#else
124-
TCGv_i64 tmp1 = tcg_constant_i64(pc_next);
125-
TCGTemp* tmp2[2] = {tcgv_i64_temp(tmp0), tcgv_i64_temp(tmp1)};
126-
#endif
127-
// tcg_gen_callN(hk->callback, NULL, 2, tmp2);
119+
TCGv tmp1 = tcg_constant_tl(pc_next);
120+
TCGTemp* tmp2[2] = {tcgv_i64_temp(tmp0), tcgv_tl_temp(tmp1)};
128121
tcg_gen_callN(hk->helper_info.func, &hk->helper_info, NULL, tmp2);
129-
#if TARGET_LONG_BITS == 32
130-
tcg_temp_free_i32(tmp1);
131-
#else
132-
tcg_temp_free_i64(tmp1);
133-
#endif
134-
tcg_temp_free_i64(tmp0);
135122
}
136123
}

0 commit comments

Comments
 (0)