forked from ish-app/ish
-
Notifications
You must be signed in to change notification settings - Fork 0
/
gadgets.h
208 lines (194 loc) · 4.14 KB
/
gadgets.h
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
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
#include "../gadgets-generic.h"
# register assignments
#define _esp r8d
#define _sp r8w
#define _ip r9
#define _eip r9d
#define _tmp r10d
#define tmp r10
#define tmpd r10d
#define tmpw r10w
#define tmpb r10b
#define _cpu r11
#define _tlb r12
#define _addr r13d
#define _addrq r13
.extern jit_exit
.macro .gadget name
.global.name gadget_\()\name
.endm
.macro gret pop=0
addq $((\pop+1)*8), %_ip
jmp *-8(%_ip)
.endm
# memory reading and writing
.irp type, read,write
.macro \type\()_prep size, id
movl %_addr, %r14d
shrl $12, %r14d
andl $0x3ff, %r14d
movl %_addr, %r15d
shrl $22, %r15d
xor %r15d, %r14d
shll $4, %r14d
movl %_addr, %r15d
andl $0xfff, %r15d
cmpl $(0x1000-(\size/8)), %r15d
ja crosspage_load_\id
movl %_addr, %r15d
andl $0xfffff000, %r15d
.ifc \type,read
cmpl TLB_ENTRY_page(%_tlb,%r14), %r15d
.else
cmpl TLB_ENTRY_page_if_writable(%_tlb,%r14), %r15d
.endif
movl %r15d, -TLB_entries+TLB_dirty_page(%_tlb)
jne handle_miss_\id
addq TLB_ENTRY_data_minus_addr(%_tlb,%r14), %_addrq
back_\id :
.pushsection_bullshit
handle_miss_\id :
call handle_\type\()_miss
jmp back_\id
crosspage_load_\id :
movq $(\size/8), %r14
call crosspage_load
jmp back_\id
.popsection
.endm
.endr
.macro write_done size, id
leaq LOCAL_value(%_cpu), %r14
cmpq %_addrq, %r14
je crosspage_store_\id
back_write_done_\id :
.pushsection_bullshit
crosspage_store_\id :
movq $(\size/8), %r14
call crosspage_store
jmp back_write_done_\id
.popsection
.endm
.macro _invoke size, reg, post, macro:vararg
.if \size == 32
\macro reg_\reg, e\reg\post
.else
\macro reg_\reg, \reg\post
.endif
.endm
.macro .each_reg_size size, macro:vararg
.irp reg, a,b,c,d
_invoke \size, \reg, x, \macro
.endr
.irp reg, si,di,bp
_invoke \size, \reg, , \macro
.endr
.if \size == 32
\macro reg_sp, _esp
.else
\macro reg_sp, _sp
.endif
.endm
.macro .each_reg macro:vararg
.each_reg_size 32, \macro
.endm
.macro ss size, macro, args:vararg
.ifnb \args
.if \size == 8
\macro \args, \size, b, b
.elseif \size == 16
\macro \args, \size, w, w
.elseif \size == 32
\macro \args, \size, d, l
.else
.error "bad size"
.endif
.else
.if \size == 8
\macro \size, b, b
.elseif \size == 16
\macro \size, w, w
.elseif \size == 32
\macro \size, d, l
.else
.error "bad size"
.endif
.endif
.endm
.macro setf_c
setc CPU_cf(%_cpu)
.endm
.macro setf_oc
seto CPU_of(%_cpu)
setf_c
.endm
.macro setf_a src, dst, ss
mov\ss \src, CPU_op1(%_cpu)
mov\ss \dst, CPU_op2(%_cpu)
orl $AF_OPS, CPU_flags_res(%_cpu)
.endm
.macro clearf_a
andl $~AF_FLAG, CPU_eflags(%_cpu)
andl $~AF_OPS, CPU_flags_res(%_cpu)
.endm
#if __APPLE__
#define DOLLAR(x) $$x
#else
#define DOLLAR(x) $x
#endif
.macro clearf_oc
movl DOLLAR(0), CPU_of(%_cpu)
movl DOLLAR(0), CPU_cf(%_cpu)
.endm
.macro setf_zsp res, ss
.ifnc \ss,l
movs\ss\()l \res, %_tmp
.endif
movl %_tmp, CPU_res(%_cpu)
orl $(ZF_RES|SF_RES|PF_RES), CPU_flags_res(%_cpu)
.endm
.macro save_c
push %rax
push %rcx
push %rdx
push %rsi
push %rdi
push %r8
push %r9
push %r10
push %r11
sub DOLLAR(8), %rsp # 16 byte alignment is so annoying
.endm
.macro restore_c
add DOLLAR(8), %rsp
pop %r11
pop %r10
pop %r9
pop %r8
pop %rdi
pop %rsi
pop %rdx
pop %rcx
pop %rax
.endm
.macro load_regs
movl CPU_eax(%_cpu), %eax
movl CPU_ebx(%_cpu), %ebx
movl CPU_ecx(%_cpu), %ecx
movl CPU_edx(%_cpu), %edx
movl CPU_esi(%_cpu), %esi
movl CPU_edi(%_cpu), %edi
movl CPU_ebp(%_cpu), %ebp
movl CPU_esp(%_cpu), %_esp
.endm
.macro save_regs
movl %eax, CPU_eax(%_cpu)
movl %ebx, CPU_ebx(%_cpu)
movl %ecx, CPU_ecx(%_cpu)
movl %edx, CPU_edx(%_cpu)
movl %esi, CPU_esi(%_cpu)
movl %edi, CPU_edi(%_cpu)
movl %ebp, CPU_ebp(%_cpu)
movl %_esp, CPU_esp(%_cpu)
.endm
# vim: ft=gas