Skip to content

Commit 812e654

Browse files
authored
Update BPF arch (capstone-engine#2568)
1 parent 2c4b05f commit 812e654

23 files changed

+1471
-753
lines changed

Diff for: Mapping.c

+1
Original file line numberDiff line numberDiff line change
@@ -353,6 +353,7 @@ DEFINE_get_detail_op(mips, Mips);
353353
DEFINE_get_detail_op(riscv, RISCV);
354354
DEFINE_get_detail_op(systemz, SystemZ);
355355
DEFINE_get_detail_op(xtensa, Xtensa);
356+
DEFINE_get_detail_op(bpf, BPF);
356357

357358
/// Returns true if for this architecture the
358359
/// alias operands should be filled.

Diff for: Mapping.h

+5
Original file line numberDiff line numberDiff line change
@@ -145,6 +145,7 @@ DECL_get_detail_op(mips, Mips);
145145
DECL_get_detail_op(riscv, RISCV);
146146
DECL_get_detail_op(systemz, SystemZ);
147147
DECL_get_detail_op(xtensa, Xtensa);
148+
DECL_get_detail_op(bpf, BPF);
148149

149150
/// Increments the detail->arch.op_count by one.
150151
#define DEFINE_inc_detail_op_count(arch, ARCH) \
@@ -182,6 +183,8 @@ DEFINE_inc_detail_op_count(systemz, SystemZ);
182183
DEFINE_dec_detail_op_count(systemz, SystemZ);
183184
DEFINE_inc_detail_op_count(xtensa, Xtensa);
184185
DEFINE_dec_detail_op_count(xtensa, Xtensa);
186+
DEFINE_inc_detail_op_count(bpf, BPF);
187+
DEFINE_dec_detail_op_count(bpf, BPF);
185188

186189
/// Returns true if a memory operand is currently edited.
187190
static inline bool doing_mem(const MCInst *MI)
@@ -214,6 +217,7 @@ DEFINE_get_arch_detail(mips, Mips);
214217
DEFINE_get_arch_detail(riscv, RISCV);
215218
DEFINE_get_arch_detail(systemz, SystemZ);
216219
DEFINE_get_arch_detail(xtensa, Xtensa);
220+
DEFINE_get_arch_detail(bpf, BPF);
217221

218222
#define DEFINE_check_safe_inc(Arch, ARCH) \
219223
static inline void Arch##_check_safe_inc(const MCInst *MI) { \
@@ -230,6 +234,7 @@ DEFINE_check_safe_inc(LoongArch, LOONGARCH);
230234
DEFINE_check_safe_inc(RISCV, RISCV);
231235
DEFINE_check_safe_inc(SystemZ, SYSTEMZ);
232236
DEFINE_check_safe_inc(Mips, MIPS);
237+
DEFINE_check_safe_inc(BPF, BPF);
233238

234239
static inline bool detail_is_set(const MCInst *MI)
235240
{

Diff for: SStream.c

+46
Original file line numberDiff line numberDiff line change
@@ -331,6 +331,22 @@ void printInt16(SStream *ss, int16_t val)
331331
}
332332
}
333333

334+
void printInt16HexOffset(SStream *ss, int16_t val)
335+
{
336+
assert(ss);
337+
SSTREAM_RETURN_IF_CLOSED(ss);
338+
if (val >= 0) {
339+
SStream_concat(ss, "+0x%" PRIx16, val);
340+
} else {
341+
if (val == INT16_MIN)
342+
SStream_concat(ss, "-0x%" PRIx16,
343+
(uint16_t)INT16_MAX + 1);
344+
else
345+
SStream_concat(ss, "-0x%" PRIx16, (int16_t)-val);
346+
}
347+
}
348+
349+
334350
void printInt32(SStream *ss, int32_t val)
335351
{
336352
assert(ss);
@@ -352,6 +368,36 @@ void printInt32(SStream *ss, int32_t val)
352368
}
353369
}
354370

371+
void printInt32HexOffset(SStream *ss, int32_t val)
372+
{
373+
assert(ss);
374+
SSTREAM_RETURN_IF_CLOSED(ss);
375+
if (val >= 0) {
376+
SStream_concat(ss, "+0x%" PRIx32, val);
377+
} else {
378+
if (val == INT32_MIN)
379+
SStream_concat(ss, "-0x%" PRIx32,
380+
(uint32_t)INT32_MAX + 1);
381+
else
382+
SStream_concat(ss, "-0x%" PRIx32, (int32_t)-val);
383+
}
384+
}
385+
386+
void printInt32Hex(SStream *ss, int32_t val)
387+
{
388+
assert(ss);
389+
SSTREAM_RETURN_IF_CLOSED(ss);
390+
if (val >= 0) {
391+
SStream_concat(ss, "0x%" PRIx32, val);
392+
} else {
393+
if (val == INT32_MIN)
394+
SStream_concat(ss, "-0x%" PRIx32,
395+
(uint32_t)INT32_MAX + 1);
396+
else
397+
SStream_concat(ss, "-0x%" PRIx32, (int32_t)-val);
398+
}
399+
}
400+
355401
void printUInt32Bang(SStream *ss, uint32_t val)
356402
{
357403
assert(ss);

Diff for: SStream.h

+4
Original file line numberDiff line numberDiff line change
@@ -73,7 +73,11 @@ void printInt32Bang(SStream *O, int32_t val);
7373

7474
void printInt8(SStream *O, int8_t val);
7575
void printInt16(SStream *O, int16_t val);
76+
void printInt16HexOffset(SStream *O, int16_t val);
77+
7678
void printInt32(SStream *O, int32_t val);
79+
void printInt32Hex(SStream *ss, int32_t val);
80+
void printInt32HexOffset(SStream *ss, int32_t val);
7781

7882
void printUInt32Bang(SStream *O, uint32_t val);
7983

Diff for: arch/BPF/BPFConstants.h

+70-55
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,7 @@
11
/* Capstone Disassembly Engine */
22
/* BPF Backend by david942j <[email protected]>, 2019 */
3+
/* SPDX-FileCopyrightText: 2024 Roee Toledano <[email protected]> */
4+
/* SPDX-License-Identifier: BSD-3 */
35

46
/* This file defines constants and macros used for parsing a BPF instruction */
57

@@ -9,80 +11,93 @@
911
#define BPF_CLASS(code) ((code) & 0x7)
1012

1113
///< Instruction classes
12-
#define BPF_CLASS_LD 0x00
13-
#define BPF_CLASS_LDX 0x01
14-
#define BPF_CLASS_ST 0x02
15-
#define BPF_CLASS_STX 0x03
16-
#define BPF_CLASS_ALU 0x04
17-
#define BPF_CLASS_JMP 0x05
18-
#define BPF_CLASS_RET 0x06 ///< cBPF only
19-
#define BPF_CLASS_MISC 0x07 ///< cBPF only
20-
#define BPF_CLASS_ALU64 0x07 ///< eBPF only
14+
#define BPF_CLASS_LD 0x00
15+
#define BPF_CLASS_LDX 0x01
16+
#define BPF_CLASS_ST 0x02
17+
#define BPF_CLASS_STX 0x03
18+
#define BPF_CLASS_ALU 0x04
19+
#define BPF_CLASS_JMP 0x05
20+
#define BPF_CLASS_RET 0x06 ///< cBPF only
21+
#define BPF_CLASS_JMP32 0x06 ///< eBPF only
22+
#define BPF_CLASS_MISC 0x07 ///< cBPF only
23+
#define BPF_CLASS_ALU64 0x07 ///< eBPF only
2124

2225
#define BPF_OP(code) ((code) & 0xf0)
2326

2427
///< Types of ALU instruction
25-
#define BPF_ALU_ADD 0x00
26-
#define BPF_ALU_SUB 0x10
27-
#define BPF_ALU_MUL 0x20
28-
#define BPF_ALU_DIV 0x30
29-
#define BPF_ALU_OR 0x40
30-
#define BPF_ALU_AND 0x50
31-
#define BPF_ALU_LSH 0x60
32-
#define BPF_ALU_RSH 0x70
33-
#define BPF_ALU_NEG 0x80
34-
#define BPF_ALU_MOD 0x90
35-
#define BPF_ALU_XOR 0xa0
36-
#define BPF_ALU_MOV 0xb0 ///< eBPF only: mov reg to reg
37-
#define BPF_ALU_ARSH 0xc0 ///< eBPF only: sign extending shift right
38-
#define BPF_ALU_END 0xd0 ///< eBPF only: endianness conversion
28+
#define BPF_ALU_ADD 0x00
29+
#define BPF_ALU_SUB 0x10
30+
#define BPF_ALU_MUL 0x20
31+
#define BPF_ALU_DIV 0x30
32+
#define BPF_ALU_OR 0x40
33+
#define BPF_ALU_AND 0x50
34+
#define BPF_ALU_LSH 0x60
35+
#define BPF_ALU_RSH 0x70
36+
#define BPF_ALU_NEG 0x80
37+
#define BPF_ALU_MOD 0x90
38+
#define BPF_ALU_XOR 0xa0
39+
#define BPF_ALU_MOV 0xb0 ///< eBPF only: mov reg to reg
40+
#define BPF_ALU_ARSH 0xc0 ///< eBPF only: sign extending shift right
41+
#define BPF_ALU_END 0xd0 ///< eBPF only: endianness conversion
3942

4043
///< Types of jmp instruction
41-
#define BPF_JUMP_JA 0x00 ///< goto
42-
#define BPF_JUMP_JEQ 0x10 ///< '=='
43-
#define BPF_JUMP_JGT 0x20 ///< unsigned '>'
44-
#define BPF_JUMP_JGE 0x30 ///< unsigned '>='
45-
#define BPF_JUMP_JSET 0x40 ///< '&'
46-
#define BPF_JUMP_JNE 0x50 ///< eBPF only: '!=' */
47-
#define BPF_JUMP_JSGT 0x60 ///< eBPF only: signed '>'
48-
#define BPF_JUMP_JSGE 0x70 ///< eBPF only: signed '>='
49-
#define BPF_JUMP_CALL 0x80 ///< eBPF only: function call
50-
#define BPF_JUMP_EXIT 0x90 ///< eBPF only: exit
51-
#define BPF_JUMP_JLT 0xa0 ///< eBPF only: unsigned '<'
52-
#define BPF_JUMP_JLE 0xb0 ///< eBPF only: unsigned '<='
53-
#define BPF_JUMP_JSLT 0xc0 ///< eBPF only: signed '<'
54-
#define BPF_JUMP_JSLE 0xd0 ///< eBPF only: signed '<='
44+
#define BPF_JUMP_JA 0x00 ///< goto
45+
#define BPF_JUMP_JEQ 0x10 ///< '=='
46+
#define BPF_JUMP_JGT 0x20 ///< unsigned '>'
47+
#define BPF_JUMP_JGE 0x30 ///< unsigned '>='
48+
#define BPF_JUMP_JSET 0x40 ///< '&'
49+
#define BPF_JUMP_JNE 0x50 ///< eBPF only: '!=' */
50+
#define BPF_JUMP_JSGT 0x60 ///< eBPF only: signed '>'
51+
#define BPF_JUMP_JSGE 0x70 ///< eBPF only: signed '>='
52+
#define BPF_JUMP_CALL 0x80 ///< eBPF only: function call
53+
#define BPF_JUMP_EXIT 0x90 ///< eBPF only: exit
54+
#define BPF_JUMP_JLT 0xa0 ///< eBPF only: unsigned '<'
55+
#define BPF_JUMP_JLE 0xb0 ///< eBPF only: unsigned '<='
56+
#define BPF_JUMP_JSLT 0xc0 ///< eBPF only: signed '<'
57+
#define BPF_JUMP_JSLE 0xd0 ///< eBPF only: signed '<='
58+
59+
///< Types of complex atomic instructions
60+
#define BPF_ATOMIC_XCHG 0xe0 ///< eBPF only: atomic exchange
61+
#define BPF_ATOMIC_CMPXCHG 0xf0 ///< eBPF only: atomic compare and exchange
5562

5663
#define BPF_SRC(code) ((code) & 0x08)
5764
#define BPF_RVAL(code) ((code) & 0x18) /* cBPF only: for return types */
5865
///< Source operand
59-
#define BPF_SRC_K 0x00
60-
#define BPF_SRC_X 0x08
61-
#define BPF_SRC_A 0x10 /* cBPF only */
66+
#define BPF_SRC_K 0x00
67+
#define BPF_SRC_X 0x08
68+
#define BPF_SRC_A 0x10 /* cBPF only */
6269

63-
#define BPF_SRC_LITTLE BPF_SRC_K
64-
#define BPF_SRC_BIG BPF_SRC_X
70+
#define BPF_SRC_LITTLE BPF_SRC_K
71+
#define BPF_SRC_BIG BPF_SRC_X
6572

6673
#define BPF_SIZE(code) ((code) & 0x18)
6774
///< Size modifier
68-
#define BPF_SIZE_W 0x00 ///< word
69-
#define BPF_SIZE_H 0x08 ///< half word
70-
#define BPF_SIZE_B 0x10 ///< byte
71-
#define BPF_SIZE_DW 0x18 ///< eBPF only: double word
75+
#define BPF_SIZE_W 0x00 ///< word
76+
#define BPF_SIZE_H 0x08 ///< half word
77+
#define BPF_SIZE_B 0x10 ///< byte
78+
#define BPF_SIZE_DW 0x18 ///< eBPF only: double word
7279

7380
#define BPF_MODE(code) ((code) & 0xe0)
7481
///< Mode modifier
75-
#define BPF_MODE_IMM 0x00 ///< used for 32-bit mov in cBPF and 64-bit in eBPF
76-
#define BPF_MODE_ABS 0x20
77-
#define BPF_MODE_IND 0x40
78-
#define BPF_MODE_MEM 0x60
79-
#define BPF_MODE_LEN 0x80 ///< cBPF only, reserved in eBPF
80-
#define BPF_MODE_MSH 0xa0 ///< cBPF only, reserved in eBPF
81-
#define BPF_MODE_XADD 0xc0 ///< eBPF only: exclusive add
82+
#define BPF_MODE_IMM 0x00 ///< used for 32-bit mov in cBPF and 64-bit in eBPF
83+
#define BPF_MODE_ABS \
84+
0x20 ///< absolute indexing of socket buffer. eBPF only, but deprecated in new versions
85+
#define BPF_MODE_IND \
86+
0x40 ///< indirect indexing of socket buffer. eBPF only, but deprecated in new versions
87+
#define BPF_MODE_MEM 0x60
88+
#define BPF_MODE_LEN 0x80 ///< cBPF only, reserved in eBPF
89+
#define BPF_MODE_MSH 0xa0 ///< cBPF only, reserved in eBPF
90+
#define BPF_MODE_ATOMIC \
91+
0xc0 ///< eBPF only: atomic operations. Originally BPF_MODE_XADD
92+
93+
#define BPF_MODE_FETCH \
94+
0x01 /* eBPF only: overwrite 'src' with what was in the modified mem address before it was modified.
95+
NOTE: in contrast to regular modifiers, this one is encoded in the 'imm' field, not opcode!
96+
Must be used for BPF_XCHG and BPF_CMPXCHG. Optional for the other atomic operations. */
8297

8398
#define BPF_MISCOP(code) ((code) & 0x80)
8499
///< Operation of misc
85-
#define BPF_MISCOP_TAX 0x00
86-
#define BPF_MISCOP_TXA 0x80
100+
#define BPF_MISCOP_TAX 0x00
101+
#define BPF_MISCOP_TXA 0x80
87102

88103
#endif

0 commit comments

Comments
 (0)