0001
0002
0003
0004
0005
0006
0007
0008 #define pr_fmt(fmt) "bpf_jit: " fmt
0009
0010 #include <linux/bitfield.h>
0011 #include <linux/bpf.h>
0012 #include <linux/filter.h>
0013 #include <linux/memory.h>
0014 #include <linux/printk.h>
0015 #include <linux/slab.h>
0016
0017 #include <asm/asm-extable.h>
0018 #include <asm/byteorder.h>
0019 #include <asm/cacheflush.h>
0020 #include <asm/debug-monitors.h>
0021 #include <asm/insn.h>
0022 #include <asm/patching.h>
0023 #include <asm/set_memory.h>
0024
0025 #include "bpf_jit.h"
0026
0027 #define TMP_REG_1 (MAX_BPF_JIT_REG + 0)
0028 #define TMP_REG_2 (MAX_BPF_JIT_REG + 1)
0029 #define TCALL_CNT (MAX_BPF_JIT_REG + 2)
0030 #define TMP_REG_3 (MAX_BPF_JIT_REG + 3)
0031 #define FP_BOTTOM (MAX_BPF_JIT_REG + 4)
0032
0033 #define check_imm(bits, imm) do { \
0034 if ((((imm) > 0) && ((imm) >> (bits))) || \
0035 (((imm) < 0) && (~(imm) >> (bits)))) { \
0036 pr_info("[%2d] imm=%d(0x%x) out of range\n", \
0037 i, imm, imm); \
0038 return -EINVAL; \
0039 } \
0040 } while (0)
0041 #define check_imm19(imm) check_imm(19, imm)
0042 #define check_imm26(imm) check_imm(26, imm)
0043
0044
0045 static const int bpf2a64[] = {
0046
0047 [BPF_REG_0] = A64_R(7),
0048
0049 [BPF_REG_1] = A64_R(0),
0050 [BPF_REG_2] = A64_R(1),
0051 [BPF_REG_3] = A64_R(2),
0052 [BPF_REG_4] = A64_R(3),
0053 [BPF_REG_5] = A64_R(4),
0054
0055 [BPF_REG_6] = A64_R(19),
0056 [BPF_REG_7] = A64_R(20),
0057 [BPF_REG_8] = A64_R(21),
0058 [BPF_REG_9] = A64_R(22),
0059
0060 [BPF_REG_FP] = A64_R(25),
0061
0062 [TMP_REG_1] = A64_R(10),
0063 [TMP_REG_2] = A64_R(11),
0064 [TMP_REG_3] = A64_R(12),
0065
0066 [TCALL_CNT] = A64_R(26),
0067
0068 [BPF_REG_AX] = A64_R(9),
0069 [FP_BOTTOM] = A64_R(27),
0070 };
0071
0072 struct jit_ctx {
0073 const struct bpf_prog *prog;
0074 int idx;
0075 int epilogue_offset;
0076 int *offset;
0077 int exentry_idx;
0078 __le32 *image;
0079 u32 stack_size;
0080 int fpb_offset;
0081 };
0082
0083 struct bpf_plt {
0084 u32 insn_ldr;
0085 u32 insn_br;
0086 u64 target;
0087 };
0088
0089 #define PLT_TARGET_SIZE sizeof_field(struct bpf_plt, target)
0090 #define PLT_TARGET_OFFSET offsetof(struct bpf_plt, target)
0091
0092 static inline void emit(const u32 insn, struct jit_ctx *ctx)
0093 {
0094 if (ctx->image != NULL)
0095 ctx->image[ctx->idx] = cpu_to_le32(insn);
0096
0097 ctx->idx++;
0098 }
0099
0100 static inline void emit_a64_mov_i(const int is64, const int reg,
0101 const s32 val, struct jit_ctx *ctx)
0102 {
0103 u16 hi = val >> 16;
0104 u16 lo = val & 0xffff;
0105
0106 if (hi & 0x8000) {
0107 if (hi == 0xffff) {
0108 emit(A64_MOVN(is64, reg, (u16)~lo, 0), ctx);
0109 } else {
0110 emit(A64_MOVN(is64, reg, (u16)~hi, 16), ctx);
0111 if (lo != 0xffff)
0112 emit(A64_MOVK(is64, reg, lo, 0), ctx);
0113 }
0114 } else {
0115 emit(A64_MOVZ(is64, reg, lo, 0), ctx);
0116 if (hi)
0117 emit(A64_MOVK(is64, reg, hi, 16), ctx);
0118 }
0119 }
0120
0121 static int i64_i16_blocks(const u64 val, bool inverse)
0122 {
0123 return (((val >> 0) & 0xffff) != (inverse ? 0xffff : 0x0000)) +
0124 (((val >> 16) & 0xffff) != (inverse ? 0xffff : 0x0000)) +
0125 (((val >> 32) & 0xffff) != (inverse ? 0xffff : 0x0000)) +
0126 (((val >> 48) & 0xffff) != (inverse ? 0xffff : 0x0000));
0127 }
0128
0129 static inline void emit_a64_mov_i64(const int reg, const u64 val,
0130 struct jit_ctx *ctx)
0131 {
0132 u64 nrm_tmp = val, rev_tmp = ~val;
0133 bool inverse;
0134 int shift;
0135
0136 if (!(nrm_tmp >> 32))
0137 return emit_a64_mov_i(0, reg, (u32)val, ctx);
0138
0139 inverse = i64_i16_blocks(nrm_tmp, true) < i64_i16_blocks(nrm_tmp, false);
0140 shift = max(round_down((inverse ? (fls64(rev_tmp) - 1) :
0141 (fls64(nrm_tmp) - 1)), 16), 0);
0142 if (inverse)
0143 emit(A64_MOVN(1, reg, (rev_tmp >> shift) & 0xffff, shift), ctx);
0144 else
0145 emit(A64_MOVZ(1, reg, (nrm_tmp >> shift) & 0xffff, shift), ctx);
0146 shift -= 16;
0147 while (shift >= 0) {
0148 if (((nrm_tmp >> shift) & 0xffff) != (inverse ? 0xffff : 0x0000))
0149 emit(A64_MOVK(1, reg, (nrm_tmp >> shift) & 0xffff, shift), ctx);
0150 shift -= 16;
0151 }
0152 }
0153
0154 static inline void emit_bti(u32 insn, struct jit_ctx *ctx)
0155 {
0156 if (IS_ENABLED(CONFIG_ARM64_BTI_KERNEL))
0157 emit(insn, ctx);
0158 }
0159
0160
0161
0162
0163
0164
0165 static inline void emit_addr_mov_i64(const int reg, const u64 val,
0166 struct jit_ctx *ctx)
0167 {
0168 u64 tmp = val;
0169 int shift = 0;
0170
0171 emit(A64_MOVN(1, reg, ~tmp & 0xffff, shift), ctx);
0172 while (shift < 32) {
0173 tmp >>= 16;
0174 shift += 16;
0175 emit(A64_MOVK(1, reg, tmp & 0xffff, shift), ctx);
0176 }
0177 }
0178
0179 static inline void emit_call(u64 target, struct jit_ctx *ctx)
0180 {
0181 u8 tmp = bpf2a64[TMP_REG_1];
0182
0183 emit_addr_mov_i64(tmp, target, ctx);
0184 emit(A64_BLR(tmp), ctx);
0185 }
0186
0187 static inline int bpf2a64_offset(int bpf_insn, int off,
0188 const struct jit_ctx *ctx)
0189 {
0190
0191 bpf_insn++;
0192
0193
0194
0195
0196
0197 return ctx->offset[bpf_insn + off] - (ctx->offset[bpf_insn] - 1);
0198 }
0199
0200 static void jit_fill_hole(void *area, unsigned int size)
0201 {
0202 __le32 *ptr;
0203
0204 for (ptr = area; size >= sizeof(u32); size -= sizeof(u32))
0205 *ptr++ = cpu_to_le32(AARCH64_BREAK_FAULT);
0206 }
0207
0208 static inline int epilogue_offset(const struct jit_ctx *ctx)
0209 {
0210 int to = ctx->epilogue_offset;
0211 int from = ctx->idx;
0212
0213 return to - from;
0214 }
0215
0216 static bool is_addsub_imm(u32 imm)
0217 {
0218
0219 return !(imm & ~0xfff) || !(imm & ~0xfff000);
0220 }
0221
0222
0223
0224
0225
0226
0227
0228
0229
0230
0231
0232
0233
0234
0235
0236
0237
0238
0239
0240
0241
0242
0243
0244
0245
0246
0247
0248
0249 static bool is_lsi_offset(int offset, int scale)
0250 {
0251 if (offset < 0)
0252 return false;
0253
0254 if (offset > (0xFFF << scale))
0255 return false;
0256
0257 if (offset & ((1 << scale) - 1))
0258 return false;
0259
0260 return true;
0261 }
0262
0263
0264
0265
0266
0267
0268
0269
0270
0271
0272
0273
0274
0275
0276
0277
0278
0279 #define BTI_INSNS (IS_ENABLED(CONFIG_ARM64_BTI_KERNEL) ? 1 : 0)
0280 #define PAC_INSNS (IS_ENABLED(CONFIG_ARM64_PTR_AUTH_KERNEL) ? 1 : 0)
0281
0282
0283 #define POKE_OFFSET (BTI_INSNS + 1)
0284
0285
0286 #define PROLOGUE_OFFSET (BTI_INSNS + 2 + PAC_INSNS + 8)
0287
0288 static int build_prologue(struct jit_ctx *ctx, bool ebpf_from_cbpf)
0289 {
0290 const struct bpf_prog *prog = ctx->prog;
0291 const bool is_main_prog = prog->aux->func_idx == 0;
0292 const u8 r6 = bpf2a64[BPF_REG_6];
0293 const u8 r7 = bpf2a64[BPF_REG_7];
0294 const u8 r8 = bpf2a64[BPF_REG_8];
0295 const u8 r9 = bpf2a64[BPF_REG_9];
0296 const u8 fp = bpf2a64[BPF_REG_FP];
0297 const u8 tcc = bpf2a64[TCALL_CNT];
0298 const u8 fpb = bpf2a64[FP_BOTTOM];
0299 const int idx0 = ctx->idx;
0300 int cur_offset;
0301
0302
0303
0304
0305
0306
0307
0308
0309
0310
0311
0312
0313
0314
0315
0316
0317
0318
0319
0320
0321
0322
0323
0324
0325 emit_bti(A64_BTI_C, ctx);
0326
0327 emit(A64_MOV(1, A64_R(9), A64_LR), ctx);
0328 emit(A64_NOP, ctx);
0329
0330
0331 if (IS_ENABLED(CONFIG_ARM64_PTR_AUTH_KERNEL))
0332 emit(A64_PACIASP, ctx);
0333
0334
0335 emit(A64_PUSH(A64_FP, A64_LR, A64_SP), ctx);
0336 emit(A64_MOV(1, A64_FP, A64_SP), ctx);
0337
0338
0339 emit(A64_PUSH(r6, r7, A64_SP), ctx);
0340 emit(A64_PUSH(r8, r9, A64_SP), ctx);
0341 emit(A64_PUSH(fp, tcc, A64_SP), ctx);
0342 emit(A64_PUSH(fpb, A64_R(28), A64_SP), ctx);
0343
0344
0345 emit(A64_MOV(1, fp, A64_SP), ctx);
0346
0347 if (!ebpf_from_cbpf && is_main_prog) {
0348
0349 emit(A64_MOVZ(1, tcc, 0, 0), ctx);
0350
0351 cur_offset = ctx->idx - idx0;
0352 if (cur_offset != PROLOGUE_OFFSET) {
0353 pr_err_once("PROLOGUE_OFFSET = %d, expected %d!\n",
0354 cur_offset, PROLOGUE_OFFSET);
0355 return -1;
0356 }
0357
0358
0359 emit_bti(A64_BTI_J, ctx);
0360 }
0361
0362 emit(A64_SUB_I(1, fpb, fp, ctx->fpb_offset), ctx);
0363
0364
0365 ctx->stack_size = round_up(prog->aux->stack_depth, 16);
0366
0367
0368 emit(A64_SUB_I(1, A64_SP, A64_SP, ctx->stack_size), ctx);
0369 return 0;
0370 }
0371
0372 static int out_offset = -1;
0373 static int emit_bpf_tail_call(struct jit_ctx *ctx)
0374 {
0375
0376 const u8 r2 = bpf2a64[BPF_REG_2];
0377 const u8 r3 = bpf2a64[BPF_REG_3];
0378
0379 const u8 tmp = bpf2a64[TMP_REG_1];
0380 const u8 prg = bpf2a64[TMP_REG_2];
0381 const u8 tcc = bpf2a64[TCALL_CNT];
0382 const int idx0 = ctx->idx;
0383 #define cur_offset (ctx->idx - idx0)
0384 #define jmp_offset (out_offset - (cur_offset))
0385 size_t off;
0386
0387
0388
0389
0390 off = offsetof(struct bpf_array, map.max_entries);
0391 emit_a64_mov_i64(tmp, off, ctx);
0392 emit(A64_LDR32(tmp, r2, tmp), ctx);
0393 emit(A64_MOV(0, r3, r3), ctx);
0394 emit(A64_CMP(0, r3, tmp), ctx);
0395 emit(A64_B_(A64_COND_CS, jmp_offset), ctx);
0396
0397
0398
0399
0400
0401
0402 emit_a64_mov_i64(tmp, MAX_TAIL_CALL_CNT, ctx);
0403 emit(A64_CMP(1, tcc, tmp), ctx);
0404 emit(A64_B_(A64_COND_CS, jmp_offset), ctx);
0405 emit(A64_ADD_I(1, tcc, tcc, 1), ctx);
0406
0407
0408
0409
0410
0411 off = offsetof(struct bpf_array, ptrs);
0412 emit_a64_mov_i64(tmp, off, ctx);
0413 emit(A64_ADD(1, tmp, r2, tmp), ctx);
0414 emit(A64_LSL(1, prg, r3, 3), ctx);
0415 emit(A64_LDR64(prg, tmp, prg), ctx);
0416 emit(A64_CBZ(1, prg, jmp_offset), ctx);
0417
0418
0419 off = offsetof(struct bpf_prog, bpf_func);
0420 emit_a64_mov_i64(tmp, off, ctx);
0421 emit(A64_LDR64(tmp, prg, tmp), ctx);
0422 emit(A64_ADD_I(1, tmp, tmp, sizeof(u32) * PROLOGUE_OFFSET), ctx);
0423 emit(A64_ADD_I(1, A64_SP, A64_SP, ctx->stack_size), ctx);
0424 emit(A64_BR(tmp), ctx);
0425
0426
0427 if (out_offset == -1)
0428 out_offset = cur_offset;
0429 if (cur_offset != out_offset) {
0430 pr_err_once("tail_call out_offset = %d, expected %d!\n",
0431 cur_offset, out_offset);
0432 return -1;
0433 }
0434 return 0;
0435 #undef cur_offset
0436 #undef jmp_offset
0437 }
0438
0439 #ifdef CONFIG_ARM64_LSE_ATOMICS
0440 static int emit_lse_atomic(const struct bpf_insn *insn, struct jit_ctx *ctx)
0441 {
0442 const u8 code = insn->code;
0443 const u8 dst = bpf2a64[insn->dst_reg];
0444 const u8 src = bpf2a64[insn->src_reg];
0445 const u8 tmp = bpf2a64[TMP_REG_1];
0446 const u8 tmp2 = bpf2a64[TMP_REG_2];
0447 const bool isdw = BPF_SIZE(code) == BPF_DW;
0448 const s16 off = insn->off;
0449 u8 reg;
0450
0451 if (!off) {
0452 reg = dst;
0453 } else {
0454 emit_a64_mov_i(1, tmp, off, ctx);
0455 emit(A64_ADD(1, tmp, tmp, dst), ctx);
0456 reg = tmp;
0457 }
0458
0459 switch (insn->imm) {
0460
0461 case BPF_ADD:
0462 emit(A64_STADD(isdw, reg, src), ctx);
0463 break;
0464 case BPF_AND:
0465 emit(A64_MVN(isdw, tmp2, src), ctx);
0466 emit(A64_STCLR(isdw, reg, tmp2), ctx);
0467 break;
0468 case BPF_OR:
0469 emit(A64_STSET(isdw, reg, src), ctx);
0470 break;
0471 case BPF_XOR:
0472 emit(A64_STEOR(isdw, reg, src), ctx);
0473 break;
0474
0475 case BPF_ADD | BPF_FETCH:
0476 emit(A64_LDADDAL(isdw, src, reg, src), ctx);
0477 break;
0478 case BPF_AND | BPF_FETCH:
0479 emit(A64_MVN(isdw, tmp2, src), ctx);
0480 emit(A64_LDCLRAL(isdw, src, reg, tmp2), ctx);
0481 break;
0482 case BPF_OR | BPF_FETCH:
0483 emit(A64_LDSETAL(isdw, src, reg, src), ctx);
0484 break;
0485 case BPF_XOR | BPF_FETCH:
0486 emit(A64_LDEORAL(isdw, src, reg, src), ctx);
0487 break;
0488
0489 case BPF_XCHG:
0490 emit(A64_SWPAL(isdw, src, reg, src), ctx);
0491 break;
0492
0493 case BPF_CMPXCHG:
0494 emit(A64_CASAL(isdw, src, reg, bpf2a64[BPF_REG_0]), ctx);
0495 break;
0496 default:
0497 pr_err_once("unknown atomic op code %02x\n", insn->imm);
0498 return -EINVAL;
0499 }
0500
0501 return 0;
0502 }
0503 #else
0504 static inline int emit_lse_atomic(const struct bpf_insn *insn, struct jit_ctx *ctx)
0505 {
0506 return -EINVAL;
0507 }
0508 #endif
0509
0510 static int emit_ll_sc_atomic(const struct bpf_insn *insn, struct jit_ctx *ctx)
0511 {
0512 const u8 code = insn->code;
0513 const u8 dst = bpf2a64[insn->dst_reg];
0514 const u8 src = bpf2a64[insn->src_reg];
0515 const u8 tmp = bpf2a64[TMP_REG_1];
0516 const u8 tmp2 = bpf2a64[TMP_REG_2];
0517 const u8 tmp3 = bpf2a64[TMP_REG_3];
0518 const int i = insn - ctx->prog->insnsi;
0519 const s32 imm = insn->imm;
0520 const s16 off = insn->off;
0521 const bool isdw = BPF_SIZE(code) == BPF_DW;
0522 u8 reg;
0523 s32 jmp_offset;
0524
0525 if (!off) {
0526 reg = dst;
0527 } else {
0528 emit_a64_mov_i(1, tmp, off, ctx);
0529 emit(A64_ADD(1, tmp, tmp, dst), ctx);
0530 reg = tmp;
0531 }
0532
0533 if (imm == BPF_ADD || imm == BPF_AND ||
0534 imm == BPF_OR || imm == BPF_XOR) {
0535
0536 emit(A64_LDXR(isdw, tmp2, reg), ctx);
0537 if (imm == BPF_ADD)
0538 emit(A64_ADD(isdw, tmp2, tmp2, src), ctx);
0539 else if (imm == BPF_AND)
0540 emit(A64_AND(isdw, tmp2, tmp2, src), ctx);
0541 else if (imm == BPF_OR)
0542 emit(A64_ORR(isdw, tmp2, tmp2, src), ctx);
0543 else
0544 emit(A64_EOR(isdw, tmp2, tmp2, src), ctx);
0545 emit(A64_STXR(isdw, tmp2, reg, tmp3), ctx);
0546 jmp_offset = -3;
0547 check_imm19(jmp_offset);
0548 emit(A64_CBNZ(0, tmp3, jmp_offset), ctx);
0549 } else if (imm == (BPF_ADD | BPF_FETCH) ||
0550 imm == (BPF_AND | BPF_FETCH) ||
0551 imm == (BPF_OR | BPF_FETCH) ||
0552 imm == (BPF_XOR | BPF_FETCH)) {
0553
0554 const u8 ax = bpf2a64[BPF_REG_AX];
0555
0556 emit(A64_MOV(isdw, ax, src), ctx);
0557 emit(A64_LDXR(isdw, src, reg), ctx);
0558 if (imm == (BPF_ADD | BPF_FETCH))
0559 emit(A64_ADD(isdw, tmp2, src, ax), ctx);
0560 else if (imm == (BPF_AND | BPF_FETCH))
0561 emit(A64_AND(isdw, tmp2, src, ax), ctx);
0562 else if (imm == (BPF_OR | BPF_FETCH))
0563 emit(A64_ORR(isdw, tmp2, src, ax), ctx);
0564 else
0565 emit(A64_EOR(isdw, tmp2, src, ax), ctx);
0566 emit(A64_STLXR(isdw, tmp2, reg, tmp3), ctx);
0567 jmp_offset = -3;
0568 check_imm19(jmp_offset);
0569 emit(A64_CBNZ(0, tmp3, jmp_offset), ctx);
0570 emit(A64_DMB_ISH, ctx);
0571 } else if (imm == BPF_XCHG) {
0572
0573 emit(A64_MOV(isdw, tmp2, src), ctx);
0574 emit(A64_LDXR(isdw, src, reg), ctx);
0575 emit(A64_STLXR(isdw, tmp2, reg, tmp3), ctx);
0576 jmp_offset = -2;
0577 check_imm19(jmp_offset);
0578 emit(A64_CBNZ(0, tmp3, jmp_offset), ctx);
0579 emit(A64_DMB_ISH, ctx);
0580 } else if (imm == BPF_CMPXCHG) {
0581
0582 const u8 r0 = bpf2a64[BPF_REG_0];
0583
0584 emit(A64_MOV(isdw, tmp2, r0), ctx);
0585 emit(A64_LDXR(isdw, r0, reg), ctx);
0586 emit(A64_EOR(isdw, tmp3, r0, tmp2), ctx);
0587 jmp_offset = 4;
0588 check_imm19(jmp_offset);
0589 emit(A64_CBNZ(isdw, tmp3, jmp_offset), ctx);
0590 emit(A64_STLXR(isdw, src, reg, tmp3), ctx);
0591 jmp_offset = -4;
0592 check_imm19(jmp_offset);
0593 emit(A64_CBNZ(0, tmp3, jmp_offset), ctx);
0594 emit(A64_DMB_ISH, ctx);
0595 } else {
0596 pr_err_once("unknown atomic op code %02x\n", imm);
0597 return -EINVAL;
0598 }
0599
0600 return 0;
0601 }
0602
0603 void dummy_tramp(void);
0604
0605 asm (
0606 " .pushsection .text, \"ax\", @progbits\n"
0607 " .global dummy_tramp\n"
0608 " .type dummy_tramp, %function\n"
0609 "dummy_tramp:"
0610 #if IS_ENABLED(CONFIG_ARM64_BTI_KERNEL)
0611 " bti j\n"
0612 #endif
0613 " mov x10, x30\n"
0614 " mov x30, x9\n"
0615 " ret x10\n"
0616 " .size dummy_tramp, .-dummy_tramp\n"
0617 " .popsection\n"
0618 );
0619
0620
0621
0622
0623
0624
0625
0626
0627
0628
0629
0630
0631
0632 static void build_plt(struct jit_ctx *ctx)
0633 {
0634 const u8 tmp = bpf2a64[TMP_REG_1];
0635 struct bpf_plt *plt = NULL;
0636
0637
0638 if ((ctx->idx + PLT_TARGET_OFFSET / AARCH64_INSN_SIZE) % 2)
0639 emit(A64_NOP, ctx);
0640
0641 plt = (struct bpf_plt *)(ctx->image + ctx->idx);
0642
0643 emit(A64_LDR64LIT(tmp, 2 * AARCH64_INSN_SIZE), ctx);
0644 emit(A64_BR(tmp), ctx);
0645
0646 if (ctx->image)
0647 plt->target = (u64)&dummy_tramp;
0648 }
0649
0650 static void build_epilogue(struct jit_ctx *ctx)
0651 {
0652 const u8 r0 = bpf2a64[BPF_REG_0];
0653 const u8 r6 = bpf2a64[BPF_REG_6];
0654 const u8 r7 = bpf2a64[BPF_REG_7];
0655 const u8 r8 = bpf2a64[BPF_REG_8];
0656 const u8 r9 = bpf2a64[BPF_REG_9];
0657 const u8 fp = bpf2a64[BPF_REG_FP];
0658 const u8 fpb = bpf2a64[FP_BOTTOM];
0659
0660
0661 emit(A64_ADD_I(1, A64_SP, A64_SP, ctx->stack_size), ctx);
0662
0663
0664 emit(A64_POP(fpb, A64_R(28), A64_SP), ctx);
0665
0666 emit(A64_POP(fp, A64_R(26), A64_SP), ctx);
0667
0668
0669 emit(A64_POP(r8, r9, A64_SP), ctx);
0670 emit(A64_POP(r6, r7, A64_SP), ctx);
0671
0672
0673 emit(A64_POP(A64_FP, A64_LR, A64_SP), ctx);
0674
0675
0676 emit(A64_MOV(1, A64_R(0), r0), ctx);
0677
0678
0679 if (IS_ENABLED(CONFIG_ARM64_PTR_AUTH_KERNEL))
0680 emit(A64_AUTIASP, ctx);
0681
0682 emit(A64_RET(A64_LR), ctx);
0683 }
0684
0685 #define BPF_FIXUP_OFFSET_MASK GENMASK(26, 0)
0686 #define BPF_FIXUP_REG_MASK GENMASK(31, 27)
0687
0688 bool ex_handler_bpf(const struct exception_table_entry *ex,
0689 struct pt_regs *regs)
0690 {
0691 off_t offset = FIELD_GET(BPF_FIXUP_OFFSET_MASK, ex->fixup);
0692 int dst_reg = FIELD_GET(BPF_FIXUP_REG_MASK, ex->fixup);
0693
0694 regs->regs[dst_reg] = 0;
0695 regs->pc = (unsigned long)&ex->fixup - offset;
0696 return true;
0697 }
0698
0699
0700 static int add_exception_handler(const struct bpf_insn *insn,
0701 struct jit_ctx *ctx,
0702 int dst_reg)
0703 {
0704 off_t offset;
0705 unsigned long pc;
0706 struct exception_table_entry *ex;
0707
0708 if (!ctx->image)
0709
0710 return 0;
0711
0712 if (BPF_MODE(insn->code) != BPF_PROBE_MEM)
0713 return 0;
0714
0715 if (!ctx->prog->aux->extable ||
0716 WARN_ON_ONCE(ctx->exentry_idx >= ctx->prog->aux->num_exentries))
0717 return -EINVAL;
0718
0719 ex = &ctx->prog->aux->extable[ctx->exentry_idx];
0720 pc = (unsigned long)&ctx->image[ctx->idx - 1];
0721
0722 offset = pc - (long)&ex->insn;
0723 if (WARN_ON_ONCE(offset >= 0 || offset < INT_MIN))
0724 return -ERANGE;
0725 ex->insn = offset;
0726
0727
0728
0729
0730
0731
0732
0733
0734
0735 offset = (long)&ex->fixup - (pc + AARCH64_INSN_SIZE);
0736 if (!FIELD_FIT(BPF_FIXUP_OFFSET_MASK, offset))
0737 return -ERANGE;
0738
0739 ex->fixup = FIELD_PREP(BPF_FIXUP_OFFSET_MASK, offset) |
0740 FIELD_PREP(BPF_FIXUP_REG_MASK, dst_reg);
0741
0742 ex->type = EX_TYPE_BPF;
0743
0744 ctx->exentry_idx++;
0745 return 0;
0746 }
0747
0748
0749
0750
0751
0752
0753
0754 static int build_insn(const struct bpf_insn *insn, struct jit_ctx *ctx,
0755 bool extra_pass)
0756 {
0757 const u8 code = insn->code;
0758 const u8 dst = bpf2a64[insn->dst_reg];
0759 const u8 src = bpf2a64[insn->src_reg];
0760 const u8 tmp = bpf2a64[TMP_REG_1];
0761 const u8 tmp2 = bpf2a64[TMP_REG_2];
0762 const u8 fp = bpf2a64[BPF_REG_FP];
0763 const u8 fpb = bpf2a64[FP_BOTTOM];
0764 const s16 off = insn->off;
0765 const s32 imm = insn->imm;
0766 const int i = insn - ctx->prog->insnsi;
0767 const bool is64 = BPF_CLASS(code) == BPF_ALU64 ||
0768 BPF_CLASS(code) == BPF_JMP;
0769 u8 jmp_cond;
0770 s32 jmp_offset;
0771 u32 a64_insn;
0772 u8 src_adj;
0773 u8 dst_adj;
0774 int off_adj;
0775 int ret;
0776
0777 switch (code) {
0778
0779 case BPF_ALU | BPF_MOV | BPF_X:
0780 case BPF_ALU64 | BPF_MOV | BPF_X:
0781 emit(A64_MOV(is64, dst, src), ctx);
0782 break;
0783
0784 case BPF_ALU | BPF_ADD | BPF_X:
0785 case BPF_ALU64 | BPF_ADD | BPF_X:
0786 emit(A64_ADD(is64, dst, dst, src), ctx);
0787 break;
0788 case BPF_ALU | BPF_SUB | BPF_X:
0789 case BPF_ALU64 | BPF_SUB | BPF_X:
0790 emit(A64_SUB(is64, dst, dst, src), ctx);
0791 break;
0792 case BPF_ALU | BPF_AND | BPF_X:
0793 case BPF_ALU64 | BPF_AND | BPF_X:
0794 emit(A64_AND(is64, dst, dst, src), ctx);
0795 break;
0796 case BPF_ALU | BPF_OR | BPF_X:
0797 case BPF_ALU64 | BPF_OR | BPF_X:
0798 emit(A64_ORR(is64, dst, dst, src), ctx);
0799 break;
0800 case BPF_ALU | BPF_XOR | BPF_X:
0801 case BPF_ALU64 | BPF_XOR | BPF_X:
0802 emit(A64_EOR(is64, dst, dst, src), ctx);
0803 break;
0804 case BPF_ALU | BPF_MUL | BPF_X:
0805 case BPF_ALU64 | BPF_MUL | BPF_X:
0806 emit(A64_MUL(is64, dst, dst, src), ctx);
0807 break;
0808 case BPF_ALU | BPF_DIV | BPF_X:
0809 case BPF_ALU64 | BPF_DIV | BPF_X:
0810 emit(A64_UDIV(is64, dst, dst, src), ctx);
0811 break;
0812 case BPF_ALU | BPF_MOD | BPF_X:
0813 case BPF_ALU64 | BPF_MOD | BPF_X:
0814 emit(A64_UDIV(is64, tmp, dst, src), ctx);
0815 emit(A64_MSUB(is64, dst, dst, tmp, src), ctx);
0816 break;
0817 case BPF_ALU | BPF_LSH | BPF_X:
0818 case BPF_ALU64 | BPF_LSH | BPF_X:
0819 emit(A64_LSLV(is64, dst, dst, src), ctx);
0820 break;
0821 case BPF_ALU | BPF_RSH | BPF_X:
0822 case BPF_ALU64 | BPF_RSH | BPF_X:
0823 emit(A64_LSRV(is64, dst, dst, src), ctx);
0824 break;
0825 case BPF_ALU | BPF_ARSH | BPF_X:
0826 case BPF_ALU64 | BPF_ARSH | BPF_X:
0827 emit(A64_ASRV(is64, dst, dst, src), ctx);
0828 break;
0829
0830 case BPF_ALU | BPF_NEG:
0831 case BPF_ALU64 | BPF_NEG:
0832 emit(A64_NEG(is64, dst, dst), ctx);
0833 break;
0834
0835 case BPF_ALU | BPF_END | BPF_FROM_LE:
0836 case BPF_ALU | BPF_END | BPF_FROM_BE:
0837 #ifdef CONFIG_CPU_BIG_ENDIAN
0838 if (BPF_SRC(code) == BPF_FROM_BE)
0839 goto emit_bswap_uxt;
0840 #else
0841 if (BPF_SRC(code) == BPF_FROM_LE)
0842 goto emit_bswap_uxt;
0843 #endif
0844 switch (imm) {
0845 case 16:
0846 emit(A64_REV16(is64, dst, dst), ctx);
0847
0848 emit(A64_UXTH(is64, dst, dst), ctx);
0849 break;
0850 case 32:
0851 emit(A64_REV32(is64, dst, dst), ctx);
0852
0853 break;
0854 case 64:
0855 emit(A64_REV64(dst, dst), ctx);
0856 break;
0857 }
0858 break;
0859 emit_bswap_uxt:
0860 switch (imm) {
0861 case 16:
0862
0863 emit(A64_UXTH(is64, dst, dst), ctx);
0864 break;
0865 case 32:
0866
0867 emit(A64_UXTW(is64, dst, dst), ctx);
0868 break;
0869 case 64:
0870
0871 break;
0872 }
0873 break;
0874
0875 case BPF_ALU | BPF_MOV | BPF_K:
0876 case BPF_ALU64 | BPF_MOV | BPF_K:
0877 emit_a64_mov_i(is64, dst, imm, ctx);
0878 break;
0879
0880 case BPF_ALU | BPF_ADD | BPF_K:
0881 case BPF_ALU64 | BPF_ADD | BPF_K:
0882 if (is_addsub_imm(imm)) {
0883 emit(A64_ADD_I(is64, dst, dst, imm), ctx);
0884 } else if (is_addsub_imm(-imm)) {
0885 emit(A64_SUB_I(is64, dst, dst, -imm), ctx);
0886 } else {
0887 emit_a64_mov_i(is64, tmp, imm, ctx);
0888 emit(A64_ADD(is64, dst, dst, tmp), ctx);
0889 }
0890 break;
0891 case BPF_ALU | BPF_SUB | BPF_K:
0892 case BPF_ALU64 | BPF_SUB | BPF_K:
0893 if (is_addsub_imm(imm)) {
0894 emit(A64_SUB_I(is64, dst, dst, imm), ctx);
0895 } else if (is_addsub_imm(-imm)) {
0896 emit(A64_ADD_I(is64, dst, dst, -imm), ctx);
0897 } else {
0898 emit_a64_mov_i(is64, tmp, imm, ctx);
0899 emit(A64_SUB(is64, dst, dst, tmp), ctx);
0900 }
0901 break;
0902 case BPF_ALU | BPF_AND | BPF_K:
0903 case BPF_ALU64 | BPF_AND | BPF_K:
0904 a64_insn = A64_AND_I(is64, dst, dst, imm);
0905 if (a64_insn != AARCH64_BREAK_FAULT) {
0906 emit(a64_insn, ctx);
0907 } else {
0908 emit_a64_mov_i(is64, tmp, imm, ctx);
0909 emit(A64_AND(is64, dst, dst, tmp), ctx);
0910 }
0911 break;
0912 case BPF_ALU | BPF_OR | BPF_K:
0913 case BPF_ALU64 | BPF_OR | BPF_K:
0914 a64_insn = A64_ORR_I(is64, dst, dst, imm);
0915 if (a64_insn != AARCH64_BREAK_FAULT) {
0916 emit(a64_insn, ctx);
0917 } else {
0918 emit_a64_mov_i(is64, tmp, imm, ctx);
0919 emit(A64_ORR(is64, dst, dst, tmp), ctx);
0920 }
0921 break;
0922 case BPF_ALU | BPF_XOR | BPF_K:
0923 case BPF_ALU64 | BPF_XOR | BPF_K:
0924 a64_insn = A64_EOR_I(is64, dst, dst, imm);
0925 if (a64_insn != AARCH64_BREAK_FAULT) {
0926 emit(a64_insn, ctx);
0927 } else {
0928 emit_a64_mov_i(is64, tmp, imm, ctx);
0929 emit(A64_EOR(is64, dst, dst, tmp), ctx);
0930 }
0931 break;
0932 case BPF_ALU | BPF_MUL | BPF_K:
0933 case BPF_ALU64 | BPF_MUL | BPF_K:
0934 emit_a64_mov_i(is64, tmp, imm, ctx);
0935 emit(A64_MUL(is64, dst, dst, tmp), ctx);
0936 break;
0937 case BPF_ALU | BPF_DIV | BPF_K:
0938 case BPF_ALU64 | BPF_DIV | BPF_K:
0939 emit_a64_mov_i(is64, tmp, imm, ctx);
0940 emit(A64_UDIV(is64, dst, dst, tmp), ctx);
0941 break;
0942 case BPF_ALU | BPF_MOD | BPF_K:
0943 case BPF_ALU64 | BPF_MOD | BPF_K:
0944 emit_a64_mov_i(is64, tmp2, imm, ctx);
0945 emit(A64_UDIV(is64, tmp, dst, tmp2), ctx);
0946 emit(A64_MSUB(is64, dst, dst, tmp, tmp2), ctx);
0947 break;
0948 case BPF_ALU | BPF_LSH | BPF_K:
0949 case BPF_ALU64 | BPF_LSH | BPF_K:
0950 emit(A64_LSL(is64, dst, dst, imm), ctx);
0951 break;
0952 case BPF_ALU | BPF_RSH | BPF_K:
0953 case BPF_ALU64 | BPF_RSH | BPF_K:
0954 emit(A64_LSR(is64, dst, dst, imm), ctx);
0955 break;
0956 case BPF_ALU | BPF_ARSH | BPF_K:
0957 case BPF_ALU64 | BPF_ARSH | BPF_K:
0958 emit(A64_ASR(is64, dst, dst, imm), ctx);
0959 break;
0960
0961
0962 case BPF_JMP | BPF_JA:
0963 jmp_offset = bpf2a64_offset(i, off, ctx);
0964 check_imm26(jmp_offset);
0965 emit(A64_B(jmp_offset), ctx);
0966 break;
0967
0968 case BPF_JMP | BPF_JEQ | BPF_X:
0969 case BPF_JMP | BPF_JGT | BPF_X:
0970 case BPF_JMP | BPF_JLT | BPF_X:
0971 case BPF_JMP | BPF_JGE | BPF_X:
0972 case BPF_JMP | BPF_JLE | BPF_X:
0973 case BPF_JMP | BPF_JNE | BPF_X:
0974 case BPF_JMP | BPF_JSGT | BPF_X:
0975 case BPF_JMP | BPF_JSLT | BPF_X:
0976 case BPF_JMP | BPF_JSGE | BPF_X:
0977 case BPF_JMP | BPF_JSLE | BPF_X:
0978 case BPF_JMP32 | BPF_JEQ | BPF_X:
0979 case BPF_JMP32 | BPF_JGT | BPF_X:
0980 case BPF_JMP32 | BPF_JLT | BPF_X:
0981 case BPF_JMP32 | BPF_JGE | BPF_X:
0982 case BPF_JMP32 | BPF_JLE | BPF_X:
0983 case BPF_JMP32 | BPF_JNE | BPF_X:
0984 case BPF_JMP32 | BPF_JSGT | BPF_X:
0985 case BPF_JMP32 | BPF_JSLT | BPF_X:
0986 case BPF_JMP32 | BPF_JSGE | BPF_X:
0987 case BPF_JMP32 | BPF_JSLE | BPF_X:
0988 emit(A64_CMP(is64, dst, src), ctx);
0989 emit_cond_jmp:
0990 jmp_offset = bpf2a64_offset(i, off, ctx);
0991 check_imm19(jmp_offset);
0992 switch (BPF_OP(code)) {
0993 case BPF_JEQ:
0994 jmp_cond = A64_COND_EQ;
0995 break;
0996 case BPF_JGT:
0997 jmp_cond = A64_COND_HI;
0998 break;
0999 case BPF_JLT:
1000 jmp_cond = A64_COND_CC;
1001 break;
1002 case BPF_JGE:
1003 jmp_cond = A64_COND_CS;
1004 break;
1005 case BPF_JLE:
1006 jmp_cond = A64_COND_LS;
1007 break;
1008 case BPF_JSET:
1009 case BPF_JNE:
1010 jmp_cond = A64_COND_NE;
1011 break;
1012 case BPF_JSGT:
1013 jmp_cond = A64_COND_GT;
1014 break;
1015 case BPF_JSLT:
1016 jmp_cond = A64_COND_LT;
1017 break;
1018 case BPF_JSGE:
1019 jmp_cond = A64_COND_GE;
1020 break;
1021 case BPF_JSLE:
1022 jmp_cond = A64_COND_LE;
1023 break;
1024 default:
1025 return -EFAULT;
1026 }
1027 emit(A64_B_(jmp_cond, jmp_offset), ctx);
1028 break;
1029 case BPF_JMP | BPF_JSET | BPF_X:
1030 case BPF_JMP32 | BPF_JSET | BPF_X:
1031 emit(A64_TST(is64, dst, src), ctx);
1032 goto emit_cond_jmp;
1033
1034 case BPF_JMP | BPF_JEQ | BPF_K:
1035 case BPF_JMP | BPF_JGT | BPF_K:
1036 case BPF_JMP | BPF_JLT | BPF_K:
1037 case BPF_JMP | BPF_JGE | BPF_K:
1038 case BPF_JMP | BPF_JLE | BPF_K:
1039 case BPF_JMP | BPF_JNE | BPF_K:
1040 case BPF_JMP | BPF_JSGT | BPF_K:
1041 case BPF_JMP | BPF_JSLT | BPF_K:
1042 case BPF_JMP | BPF_JSGE | BPF_K:
1043 case BPF_JMP | BPF_JSLE | BPF_K:
1044 case BPF_JMP32 | BPF_JEQ | BPF_K:
1045 case BPF_JMP32 | BPF_JGT | BPF_K:
1046 case BPF_JMP32 | BPF_JLT | BPF_K:
1047 case BPF_JMP32 | BPF_JGE | BPF_K:
1048 case BPF_JMP32 | BPF_JLE | BPF_K:
1049 case BPF_JMP32 | BPF_JNE | BPF_K:
1050 case BPF_JMP32 | BPF_JSGT | BPF_K:
1051 case BPF_JMP32 | BPF_JSLT | BPF_K:
1052 case BPF_JMP32 | BPF_JSGE | BPF_K:
1053 case BPF_JMP32 | BPF_JSLE | BPF_K:
1054 if (is_addsub_imm(imm)) {
1055 emit(A64_CMP_I(is64, dst, imm), ctx);
1056 } else if (is_addsub_imm(-imm)) {
1057 emit(A64_CMN_I(is64, dst, -imm), ctx);
1058 } else {
1059 emit_a64_mov_i(is64, tmp, imm, ctx);
1060 emit(A64_CMP(is64, dst, tmp), ctx);
1061 }
1062 goto emit_cond_jmp;
1063 case BPF_JMP | BPF_JSET | BPF_K:
1064 case BPF_JMP32 | BPF_JSET | BPF_K:
1065 a64_insn = A64_TST_I(is64, dst, imm);
1066 if (a64_insn != AARCH64_BREAK_FAULT) {
1067 emit(a64_insn, ctx);
1068 } else {
1069 emit_a64_mov_i(is64, tmp, imm, ctx);
1070 emit(A64_TST(is64, dst, tmp), ctx);
1071 }
1072 goto emit_cond_jmp;
1073
1074 case BPF_JMP | BPF_CALL:
1075 {
1076 const u8 r0 = bpf2a64[BPF_REG_0];
1077 bool func_addr_fixed;
1078 u64 func_addr;
1079
1080 ret = bpf_jit_get_func_addr(ctx->prog, insn, extra_pass,
1081 &func_addr, &func_addr_fixed);
1082 if (ret < 0)
1083 return ret;
1084 emit_call(func_addr, ctx);
1085 emit(A64_MOV(1, r0, A64_R(0)), ctx);
1086 break;
1087 }
1088
1089 case BPF_JMP | BPF_TAIL_CALL:
1090 if (emit_bpf_tail_call(ctx))
1091 return -EFAULT;
1092 break;
1093
1094 case BPF_JMP | BPF_EXIT:
1095
1096
1097 if (i == ctx->prog->len - 1)
1098 break;
1099 jmp_offset = epilogue_offset(ctx);
1100 check_imm26(jmp_offset);
1101 emit(A64_B(jmp_offset), ctx);
1102 break;
1103
1104
1105 case BPF_LD | BPF_IMM | BPF_DW:
1106 {
1107 const struct bpf_insn insn1 = insn[1];
1108 u64 imm64;
1109
1110 imm64 = (u64)insn1.imm << 32 | (u32)imm;
1111 if (bpf_pseudo_func(insn))
1112 emit_addr_mov_i64(dst, imm64, ctx);
1113 else
1114 emit_a64_mov_i64(dst, imm64, ctx);
1115
1116 return 1;
1117 }
1118
1119
1120 case BPF_LDX | BPF_MEM | BPF_W:
1121 case BPF_LDX | BPF_MEM | BPF_H:
1122 case BPF_LDX | BPF_MEM | BPF_B:
1123 case BPF_LDX | BPF_MEM | BPF_DW:
1124 case BPF_LDX | BPF_PROBE_MEM | BPF_DW:
1125 case BPF_LDX | BPF_PROBE_MEM | BPF_W:
1126 case BPF_LDX | BPF_PROBE_MEM | BPF_H:
1127 case BPF_LDX | BPF_PROBE_MEM | BPF_B:
1128 if (ctx->fpb_offset > 0 && src == fp) {
1129 src_adj = fpb;
1130 off_adj = off + ctx->fpb_offset;
1131 } else {
1132 src_adj = src;
1133 off_adj = off;
1134 }
1135 switch (BPF_SIZE(code)) {
1136 case BPF_W:
1137 if (is_lsi_offset(off_adj, 2)) {
1138 emit(A64_LDR32I(dst, src_adj, off_adj), ctx);
1139 } else {
1140 emit_a64_mov_i(1, tmp, off, ctx);
1141 emit(A64_LDR32(dst, src, tmp), ctx);
1142 }
1143 break;
1144 case BPF_H:
1145 if (is_lsi_offset(off_adj, 1)) {
1146 emit(A64_LDRHI(dst, src_adj, off_adj), ctx);
1147 } else {
1148 emit_a64_mov_i(1, tmp, off, ctx);
1149 emit(A64_LDRH(dst, src, tmp), ctx);
1150 }
1151 break;
1152 case BPF_B:
1153 if (is_lsi_offset(off_adj, 0)) {
1154 emit(A64_LDRBI(dst, src_adj, off_adj), ctx);
1155 } else {
1156 emit_a64_mov_i(1, tmp, off, ctx);
1157 emit(A64_LDRB(dst, src, tmp), ctx);
1158 }
1159 break;
1160 case BPF_DW:
1161 if (is_lsi_offset(off_adj, 3)) {
1162 emit(A64_LDR64I(dst, src_adj, off_adj), ctx);
1163 } else {
1164 emit_a64_mov_i(1, tmp, off, ctx);
1165 emit(A64_LDR64(dst, src, tmp), ctx);
1166 }
1167 break;
1168 }
1169
1170 ret = add_exception_handler(insn, ctx, dst);
1171 if (ret)
1172 return ret;
1173 break;
1174
1175
1176 case BPF_ST | BPF_NOSPEC:
1177
1178
1179
1180
1181
1182
1183
1184
1185
1186 break;
1187
1188
1189 case BPF_ST | BPF_MEM | BPF_W:
1190 case BPF_ST | BPF_MEM | BPF_H:
1191 case BPF_ST | BPF_MEM | BPF_B:
1192 case BPF_ST | BPF_MEM | BPF_DW:
1193 if (ctx->fpb_offset > 0 && dst == fp) {
1194 dst_adj = fpb;
1195 off_adj = off + ctx->fpb_offset;
1196 } else {
1197 dst_adj = dst;
1198 off_adj = off;
1199 }
1200
1201 emit_a64_mov_i(1, tmp, imm, ctx);
1202 switch (BPF_SIZE(code)) {
1203 case BPF_W:
1204 if (is_lsi_offset(off_adj, 2)) {
1205 emit(A64_STR32I(tmp, dst_adj, off_adj), ctx);
1206 } else {
1207 emit_a64_mov_i(1, tmp2, off, ctx);
1208 emit(A64_STR32(tmp, dst, tmp2), ctx);
1209 }
1210 break;
1211 case BPF_H:
1212 if (is_lsi_offset(off_adj, 1)) {
1213 emit(A64_STRHI(tmp, dst_adj, off_adj), ctx);
1214 } else {
1215 emit_a64_mov_i(1, tmp2, off, ctx);
1216 emit(A64_STRH(tmp, dst, tmp2), ctx);
1217 }
1218 break;
1219 case BPF_B:
1220 if (is_lsi_offset(off_adj, 0)) {
1221 emit(A64_STRBI(tmp, dst_adj, off_adj), ctx);
1222 } else {
1223 emit_a64_mov_i(1, tmp2, off, ctx);
1224 emit(A64_STRB(tmp, dst, tmp2), ctx);
1225 }
1226 break;
1227 case BPF_DW:
1228 if (is_lsi_offset(off_adj, 3)) {
1229 emit(A64_STR64I(tmp, dst_adj, off_adj), ctx);
1230 } else {
1231 emit_a64_mov_i(1, tmp2, off, ctx);
1232 emit(A64_STR64(tmp, dst, tmp2), ctx);
1233 }
1234 break;
1235 }
1236 break;
1237
1238
1239 case BPF_STX | BPF_MEM | BPF_W:
1240 case BPF_STX | BPF_MEM | BPF_H:
1241 case BPF_STX | BPF_MEM | BPF_B:
1242 case BPF_STX | BPF_MEM | BPF_DW:
1243 if (ctx->fpb_offset > 0 && dst == fp) {
1244 dst_adj = fpb;
1245 off_adj = off + ctx->fpb_offset;
1246 } else {
1247 dst_adj = dst;
1248 off_adj = off;
1249 }
1250 switch (BPF_SIZE(code)) {
1251 case BPF_W:
1252 if (is_lsi_offset(off_adj, 2)) {
1253 emit(A64_STR32I(src, dst_adj, off_adj), ctx);
1254 } else {
1255 emit_a64_mov_i(1, tmp, off, ctx);
1256 emit(A64_STR32(src, dst, tmp), ctx);
1257 }
1258 break;
1259 case BPF_H:
1260 if (is_lsi_offset(off_adj, 1)) {
1261 emit(A64_STRHI(src, dst_adj, off_adj), ctx);
1262 } else {
1263 emit_a64_mov_i(1, tmp, off, ctx);
1264 emit(A64_STRH(src, dst, tmp), ctx);
1265 }
1266 break;
1267 case BPF_B:
1268 if (is_lsi_offset(off_adj, 0)) {
1269 emit(A64_STRBI(src, dst_adj, off_adj), ctx);
1270 } else {
1271 emit_a64_mov_i(1, tmp, off, ctx);
1272 emit(A64_STRB(src, dst, tmp), ctx);
1273 }
1274 break;
1275 case BPF_DW:
1276 if (is_lsi_offset(off_adj, 3)) {
1277 emit(A64_STR64I(src, dst_adj, off_adj), ctx);
1278 } else {
1279 emit_a64_mov_i(1, tmp, off, ctx);
1280 emit(A64_STR64(src, dst, tmp), ctx);
1281 }
1282 break;
1283 }
1284 break;
1285
1286 case BPF_STX | BPF_ATOMIC | BPF_W:
1287 case BPF_STX | BPF_ATOMIC | BPF_DW:
1288 if (cpus_have_cap(ARM64_HAS_LSE_ATOMICS))
1289 ret = emit_lse_atomic(insn, ctx);
1290 else
1291 ret = emit_ll_sc_atomic(insn, ctx);
1292 if (ret)
1293 return ret;
1294 break;
1295
1296 default:
1297 pr_err_once("unknown opcode %02x\n", code);
1298 return -EINVAL;
1299 }
1300
1301 return 0;
1302 }
1303
1304
1305
1306
1307
1308 static int find_fpb_offset(struct bpf_prog *prog)
1309 {
1310 int i;
1311 int offset = 0;
1312
1313 for (i = 0; i < prog->len; i++) {
1314 const struct bpf_insn *insn = &prog->insnsi[i];
1315 const u8 class = BPF_CLASS(insn->code);
1316 const u8 mode = BPF_MODE(insn->code);
1317 const u8 src = insn->src_reg;
1318 const u8 dst = insn->dst_reg;
1319 const s32 imm = insn->imm;
1320 const s16 off = insn->off;
1321
1322 switch (class) {
1323 case BPF_STX:
1324 case BPF_ST:
1325
1326 if (class == BPF_STX && mode == BPF_ATOMIC &&
1327 ((imm == BPF_XCHG ||
1328 imm == (BPF_FETCH | BPF_ADD) ||
1329 imm == (BPF_FETCH | BPF_AND) ||
1330 imm == (BPF_FETCH | BPF_XOR) ||
1331 imm == (BPF_FETCH | BPF_OR)) &&
1332 src == BPF_REG_FP))
1333 return 0;
1334
1335 if (mode == BPF_MEM && dst == BPF_REG_FP &&
1336 off < offset)
1337 offset = insn->off;
1338 break;
1339
1340 case BPF_JMP32:
1341 case BPF_JMP:
1342 break;
1343
1344 case BPF_LDX:
1345 case BPF_LD:
1346
1347 if (dst == BPF_REG_FP)
1348 return 0;
1349
1350 if (class == BPF_LDX && mode == BPF_MEM &&
1351 src == BPF_REG_FP && off < offset)
1352 offset = off;
1353 break;
1354
1355 case BPF_ALU:
1356 case BPF_ALU64:
1357 default:
1358
1359 if (dst == BPF_REG_FP)
1360 return 0;
1361 }
1362 }
1363
1364 if (offset < 0) {
1365
1366
1367
1368
1369 offset = -offset;
1370
1371 offset = ALIGN_DOWN(offset, 8);
1372 }
1373
1374 return offset;
1375 }
1376
1377 static int build_body(struct jit_ctx *ctx, bool extra_pass)
1378 {
1379 const struct bpf_prog *prog = ctx->prog;
1380 int i;
1381
1382
1383
1384
1385
1386
1387
1388
1389
1390
1391 for (i = 0; i < prog->len; i++) {
1392 const struct bpf_insn *insn = &prog->insnsi[i];
1393 int ret;
1394
1395 if (ctx->image == NULL)
1396 ctx->offset[i] = ctx->idx;
1397 ret = build_insn(insn, ctx, extra_pass);
1398 if (ret > 0) {
1399 i++;
1400 if (ctx->image == NULL)
1401 ctx->offset[i] = ctx->idx;
1402 continue;
1403 }
1404 if (ret)
1405 return ret;
1406 }
1407
1408
1409
1410
1411
1412 if (ctx->image == NULL)
1413 ctx->offset[i] = ctx->idx;
1414
1415 return 0;
1416 }
1417
1418 static int validate_code(struct jit_ctx *ctx)
1419 {
1420 int i;
1421
1422 for (i = 0; i < ctx->idx; i++) {
1423 u32 a64_insn = le32_to_cpu(ctx->image[i]);
1424
1425 if (a64_insn == AARCH64_BREAK_FAULT)
1426 return -1;
1427 }
1428 return 0;
1429 }
1430
1431 static int validate_ctx(struct jit_ctx *ctx)
1432 {
1433 if (validate_code(ctx))
1434 return -1;
1435
1436 if (WARN_ON_ONCE(ctx->exentry_idx != ctx->prog->aux->num_exentries))
1437 return -1;
1438
1439 return 0;
1440 }
1441
1442 static inline void bpf_flush_icache(void *start, void *end)
1443 {
1444 flush_icache_range((unsigned long)start, (unsigned long)end);
1445 }
1446
1447 struct arm64_jit_data {
1448 struct bpf_binary_header *header;
1449 u8 *image;
1450 struct jit_ctx ctx;
1451 };
1452
1453 struct bpf_prog *bpf_int_jit_compile(struct bpf_prog *prog)
1454 {
1455 int image_size, prog_size, extable_size, extable_align, extable_offset;
1456 struct bpf_prog *tmp, *orig_prog = prog;
1457 struct bpf_binary_header *header;
1458 struct arm64_jit_data *jit_data;
1459 bool was_classic = bpf_prog_was_classic(prog);
1460 bool tmp_blinded = false;
1461 bool extra_pass = false;
1462 struct jit_ctx ctx;
1463 u8 *image_ptr;
1464
1465 if (!prog->jit_requested)
1466 return orig_prog;
1467
1468 tmp = bpf_jit_blind_constants(prog);
1469
1470
1471
1472 if (IS_ERR(tmp))
1473 return orig_prog;
1474 if (tmp != prog) {
1475 tmp_blinded = true;
1476 prog = tmp;
1477 }
1478
1479 jit_data = prog->aux->jit_data;
1480 if (!jit_data) {
1481 jit_data = kzalloc(sizeof(*jit_data), GFP_KERNEL);
1482 if (!jit_data) {
1483 prog = orig_prog;
1484 goto out;
1485 }
1486 prog->aux->jit_data = jit_data;
1487 }
1488 if (jit_data->ctx.offset) {
1489 ctx = jit_data->ctx;
1490 image_ptr = jit_data->image;
1491 header = jit_data->header;
1492 extra_pass = true;
1493 prog_size = sizeof(u32) * ctx.idx;
1494 goto skip_init_ctx;
1495 }
1496 memset(&ctx, 0, sizeof(ctx));
1497 ctx.prog = prog;
1498
1499 ctx.offset = kvcalloc(prog->len + 1, sizeof(int), GFP_KERNEL);
1500 if (ctx.offset == NULL) {
1501 prog = orig_prog;
1502 goto out_off;
1503 }
1504
1505 ctx.fpb_offset = find_fpb_offset(prog);
1506
1507
1508
1509
1510
1511
1512
1513 if (build_prologue(&ctx, was_classic)) {
1514 prog = orig_prog;
1515 goto out_off;
1516 }
1517
1518 if (build_body(&ctx, extra_pass)) {
1519 prog = orig_prog;
1520 goto out_off;
1521 }
1522
1523 ctx.epilogue_offset = ctx.idx;
1524 build_epilogue(&ctx);
1525 build_plt(&ctx);
1526
1527 extable_align = __alignof__(struct exception_table_entry);
1528 extable_size = prog->aux->num_exentries *
1529 sizeof(struct exception_table_entry);
1530
1531
1532 prog_size = sizeof(u32) * ctx.idx;
1533
1534 extable_offset = round_up(prog_size + PLT_TARGET_SIZE, extable_align);
1535 image_size = extable_offset + extable_size;
1536 header = bpf_jit_binary_alloc(image_size, &image_ptr,
1537 sizeof(u32), jit_fill_hole);
1538 if (header == NULL) {
1539 prog = orig_prog;
1540 goto out_off;
1541 }
1542
1543
1544
1545 ctx.image = (__le32 *)image_ptr;
1546 if (extable_size)
1547 prog->aux->extable = (void *)image_ptr + extable_offset;
1548 skip_init_ctx:
1549 ctx.idx = 0;
1550 ctx.exentry_idx = 0;
1551
1552 build_prologue(&ctx, was_classic);
1553
1554 if (build_body(&ctx, extra_pass)) {
1555 bpf_jit_binary_free(header);
1556 prog = orig_prog;
1557 goto out_off;
1558 }
1559
1560 build_epilogue(&ctx);
1561 build_plt(&ctx);
1562
1563
1564 if (validate_ctx(&ctx)) {
1565 bpf_jit_binary_free(header);
1566 prog = orig_prog;
1567 goto out_off;
1568 }
1569
1570
1571 if (bpf_jit_enable > 1)
1572 bpf_jit_dump(prog->len, prog_size, 2, ctx.image);
1573
1574 bpf_flush_icache(header, ctx.image + ctx.idx);
1575
1576 if (!prog->is_func || extra_pass) {
1577 if (extra_pass && ctx.idx != jit_data->ctx.idx) {
1578 pr_err_once("multi-func JIT bug %d != %d\n",
1579 ctx.idx, jit_data->ctx.idx);
1580 bpf_jit_binary_free(header);
1581 prog->bpf_func = NULL;
1582 prog->jited = 0;
1583 prog->jited_len = 0;
1584 goto out_off;
1585 }
1586 bpf_jit_binary_lock_ro(header);
1587 } else {
1588 jit_data->ctx = ctx;
1589 jit_data->image = image_ptr;
1590 jit_data->header = header;
1591 }
1592 prog->bpf_func = (void *)ctx.image;
1593 prog->jited = 1;
1594 prog->jited_len = prog_size;
1595
1596 if (!prog->is_func || extra_pass) {
1597 int i;
1598
1599
1600 for (i = 0; i <= prog->len; i++)
1601 ctx.offset[i] *= AARCH64_INSN_SIZE;
1602 bpf_prog_fill_jited_linfo(prog, ctx.offset + 1);
1603 out_off:
1604 kvfree(ctx.offset);
1605 kfree(jit_data);
1606 prog->aux->jit_data = NULL;
1607 }
1608 out:
1609 if (tmp_blinded)
1610 bpf_jit_prog_release_other(prog, prog == orig_prog ?
1611 tmp : orig_prog);
1612 return prog;
1613 }
1614
1615 bool bpf_jit_supports_kfunc_call(void)
1616 {
1617 return true;
1618 }
1619
1620 u64 bpf_jit_alloc_exec_limit(void)
1621 {
1622 return VMALLOC_END - VMALLOC_START;
1623 }
1624
1625 void *bpf_jit_alloc_exec(unsigned long size)
1626 {
1627
1628 return kasan_reset_tag(vmalloc(size));
1629 }
1630
1631 void bpf_jit_free_exec(void *addr)
1632 {
1633 return vfree(addr);
1634 }
1635
1636
1637 bool bpf_jit_supports_subprog_tailcalls(void)
1638 {
1639 return true;
1640 }
1641
1642 static void invoke_bpf_prog(struct jit_ctx *ctx, struct bpf_tramp_link *l,
1643 int args_off, int retval_off, int run_ctx_off,
1644 bool save_ret)
1645 {
1646 __le32 *branch;
1647 u64 enter_prog;
1648 u64 exit_prog;
1649 struct bpf_prog *p = l->link.prog;
1650 int cookie_off = offsetof(struct bpf_tramp_run_ctx, bpf_cookie);
1651
1652 if (p->aux->sleepable) {
1653 enter_prog = (u64)__bpf_prog_enter_sleepable;
1654 exit_prog = (u64)__bpf_prog_exit_sleepable;
1655 } else {
1656 enter_prog = (u64)__bpf_prog_enter;
1657 exit_prog = (u64)__bpf_prog_exit;
1658 }
1659
1660 if (l->cookie == 0) {
1661
1662 emit(A64_STR64I(A64_ZR, A64_SP, run_ctx_off + cookie_off), ctx);
1663 } else {
1664 emit_a64_mov_i64(A64_R(10), l->cookie, ctx);
1665 emit(A64_STR64I(A64_R(10), A64_SP, run_ctx_off + cookie_off),
1666 ctx);
1667 }
1668
1669
1670
1671
1672 emit_addr_mov_i64(A64_R(19), (const u64)p, ctx);
1673
1674
1675 emit(A64_MOV(1, A64_R(0), A64_R(19)), ctx);
1676
1677 emit(A64_ADD_I(1, A64_R(1), A64_SP, run_ctx_off), ctx);
1678
1679 emit_call(enter_prog, ctx);
1680
1681
1682
1683
1684 branch = ctx->image + ctx->idx;
1685 emit(A64_NOP, ctx);
1686
1687
1688 emit(A64_MOV(1, A64_R(20), A64_R(0)), ctx);
1689
1690 emit(A64_ADD_I(1, A64_R(0), A64_SP, args_off), ctx);
1691 if (!p->jited)
1692 emit_addr_mov_i64(A64_R(1), (const u64)p->insnsi, ctx);
1693
1694 emit_call((const u64)p->bpf_func, ctx);
1695
1696 if (save_ret)
1697 emit(A64_STR64I(A64_R(0), A64_SP, retval_off), ctx);
1698
1699 if (ctx->image) {
1700 int offset = &ctx->image[ctx->idx] - branch;
1701 *branch = cpu_to_le32(A64_CBZ(1, A64_R(0), offset));
1702 }
1703
1704
1705 emit(A64_MOV(1, A64_R(0), A64_R(19)), ctx);
1706
1707 emit(A64_MOV(1, A64_R(1), A64_R(20)), ctx);
1708
1709 emit(A64_ADD_I(1, A64_R(2), A64_SP, run_ctx_off), ctx);
1710
1711 emit_call(exit_prog, ctx);
1712 }
1713
1714 static void invoke_bpf_mod_ret(struct jit_ctx *ctx, struct bpf_tramp_links *tl,
1715 int args_off, int retval_off, int run_ctx_off,
1716 __le32 **branches)
1717 {
1718 int i;
1719
1720
1721
1722
1723 emit(A64_STR64I(A64_ZR, A64_SP, retval_off), ctx);
1724 for (i = 0; i < tl->nr_links; i++) {
1725 invoke_bpf_prog(ctx, tl->links[i], args_off, retval_off,
1726 run_ctx_off, true);
1727
1728
1729
1730 emit(A64_LDR64I(A64_R(10), A64_SP, retval_off), ctx);
1731
1732
1733
1734 branches[i] = ctx->image + ctx->idx;
1735 emit(A64_NOP, ctx);
1736 }
1737 }
1738
1739 static void save_args(struct jit_ctx *ctx, int args_off, int nargs)
1740 {
1741 int i;
1742
1743 for (i = 0; i < nargs; i++) {
1744 emit(A64_STR64I(i, A64_SP, args_off), ctx);
1745 args_off += 8;
1746 }
1747 }
1748
1749 static void restore_args(struct jit_ctx *ctx, int args_off, int nargs)
1750 {
1751 int i;
1752
1753 for (i = 0; i < nargs; i++) {
1754 emit(A64_LDR64I(i, A64_SP, args_off), ctx);
1755 args_off += 8;
1756 }
1757 }
1758
1759
1760
1761
1762
1763
1764
1765
1766
1767
1768
1769
1770 static int prepare_trampoline(struct jit_ctx *ctx, struct bpf_tramp_image *im,
1771 struct bpf_tramp_links *tlinks, void *orig_call,
1772 int nargs, u32 flags)
1773 {
1774 int i;
1775 int stack_size;
1776 int retaddr_off;
1777 int regs_off;
1778 int retval_off;
1779 int args_off;
1780 int nargs_off;
1781 int ip_off;
1782 int run_ctx_off;
1783 struct bpf_tramp_links *fentry = &tlinks[BPF_TRAMP_FENTRY];
1784 struct bpf_tramp_links *fexit = &tlinks[BPF_TRAMP_FEXIT];
1785 struct bpf_tramp_links *fmod_ret = &tlinks[BPF_TRAMP_MODIFY_RETURN];
1786 bool save_ret;
1787 __le32 **branches = NULL;
1788
1789
1790
1791
1792
1793
1794
1795
1796
1797
1798
1799
1800
1801
1802
1803
1804
1805
1806
1807
1808
1809
1810
1811
1812
1813
1814 stack_size = 0;
1815 run_ctx_off = stack_size;
1816
1817 stack_size += round_up(sizeof(struct bpf_tramp_run_ctx), 8);
1818
1819 ip_off = stack_size;
1820
1821 if (flags & BPF_TRAMP_F_IP_ARG)
1822 stack_size += 8;
1823
1824 nargs_off = stack_size;
1825
1826 stack_size += 8;
1827
1828 args_off = stack_size;
1829
1830 stack_size += nargs * 8;
1831
1832
1833 retval_off = stack_size;
1834 save_ret = flags & (BPF_TRAMP_F_CALL_ORIG | BPF_TRAMP_F_RET_FENTRY_RET);
1835 if (save_ret)
1836 stack_size += 8;
1837
1838
1839 regs_off = stack_size;
1840 stack_size += 16;
1841
1842
1843 stack_size = round_up(stack_size, 16);
1844
1845
1846 retaddr_off = stack_size + 8;
1847
1848
1849
1850
1851
1852
1853
1854 emit_bti(A64_BTI_JC, ctx);
1855
1856
1857 emit(A64_PUSH(A64_FP, A64_R(9), A64_SP), ctx);
1858 emit(A64_MOV(1, A64_FP, A64_SP), ctx);
1859
1860
1861 emit(A64_PUSH(A64_FP, A64_LR, A64_SP), ctx);
1862 emit(A64_MOV(1, A64_FP, A64_SP), ctx);
1863
1864
1865 emit(A64_SUB_I(1, A64_SP, A64_SP, stack_size), ctx);
1866
1867 if (flags & BPF_TRAMP_F_IP_ARG) {
1868
1869 emit_addr_mov_i64(A64_R(10), (const u64)orig_call, ctx);
1870 emit(A64_STR64I(A64_R(10), A64_SP, ip_off), ctx);
1871 }
1872
1873
1874 emit(A64_MOVZ(1, A64_R(10), nargs, 0), ctx);
1875 emit(A64_STR64I(A64_R(10), A64_SP, nargs_off), ctx);
1876
1877
1878 save_args(ctx, args_off, nargs);
1879
1880
1881 emit(A64_STR64I(A64_R(19), A64_SP, regs_off), ctx);
1882 emit(A64_STR64I(A64_R(20), A64_SP, regs_off + 8), ctx);
1883
1884 if (flags & BPF_TRAMP_F_CALL_ORIG) {
1885 emit_addr_mov_i64(A64_R(0), (const u64)im, ctx);
1886 emit_call((const u64)__bpf_tramp_enter, ctx);
1887 }
1888
1889 for (i = 0; i < fentry->nr_links; i++)
1890 invoke_bpf_prog(ctx, fentry->links[i], args_off,
1891 retval_off, run_ctx_off,
1892 flags & BPF_TRAMP_F_RET_FENTRY_RET);
1893
1894 if (fmod_ret->nr_links) {
1895 branches = kcalloc(fmod_ret->nr_links, sizeof(__le32 *),
1896 GFP_KERNEL);
1897 if (!branches)
1898 return -ENOMEM;
1899
1900 invoke_bpf_mod_ret(ctx, fmod_ret, args_off, retval_off,
1901 run_ctx_off, branches);
1902 }
1903
1904 if (flags & BPF_TRAMP_F_CALL_ORIG) {
1905 restore_args(ctx, args_off, nargs);
1906
1907 emit(A64_LDR64I(A64_R(10), A64_SP, retaddr_off), ctx);
1908 emit(A64_BLR(A64_R(10)), ctx);
1909
1910 emit(A64_STR64I(A64_R(0), A64_SP, retval_off), ctx);
1911
1912 im->ip_after_call = ctx->image + ctx->idx;
1913 emit(A64_NOP, ctx);
1914 }
1915
1916
1917 for (i = 0; i < fmod_ret->nr_links && ctx->image != NULL; i++) {
1918 int offset = &ctx->image[ctx->idx] - branches[i];
1919 *branches[i] = cpu_to_le32(A64_CBNZ(1, A64_R(10), offset));
1920 }
1921
1922 for (i = 0; i < fexit->nr_links; i++)
1923 invoke_bpf_prog(ctx, fexit->links[i], args_off, retval_off,
1924 run_ctx_off, false);
1925
1926 if (flags & BPF_TRAMP_F_CALL_ORIG) {
1927 im->ip_epilogue = ctx->image + ctx->idx;
1928 emit_addr_mov_i64(A64_R(0), (const u64)im, ctx);
1929 emit_call((const u64)__bpf_tramp_exit, ctx);
1930 }
1931
1932 if (flags & BPF_TRAMP_F_RESTORE_REGS)
1933 restore_args(ctx, args_off, nargs);
1934
1935
1936 emit(A64_LDR64I(A64_R(19), A64_SP, regs_off), ctx);
1937 emit(A64_LDR64I(A64_R(20), A64_SP, regs_off + 8), ctx);
1938
1939 if (save_ret)
1940 emit(A64_LDR64I(A64_R(0), A64_SP, retval_off), ctx);
1941
1942
1943 emit(A64_MOV(1, A64_SP, A64_FP), ctx);
1944
1945
1946 emit(A64_POP(A64_FP, A64_LR, A64_SP), ctx);
1947 emit(A64_POP(A64_FP, A64_R(9), A64_SP), ctx);
1948
1949 if (flags & BPF_TRAMP_F_SKIP_FRAME) {
1950
1951 emit(A64_MOV(1, A64_LR, A64_R(9)), ctx);
1952 emit(A64_RET(A64_R(9)), ctx);
1953 } else {
1954
1955 emit(A64_MOV(1, A64_R(10), A64_LR), ctx);
1956 emit(A64_MOV(1, A64_LR, A64_R(9)), ctx);
1957 emit(A64_RET(A64_R(10)), ctx);
1958 }
1959
1960 if (ctx->image)
1961 bpf_flush_icache(ctx->image, ctx->image + ctx->idx);
1962
1963 kfree(branches);
1964
1965 return ctx->idx;
1966 }
1967
1968 int arch_prepare_bpf_trampoline(struct bpf_tramp_image *im, void *image,
1969 void *image_end, const struct btf_func_model *m,
1970 u32 flags, struct bpf_tramp_links *tlinks,
1971 void *orig_call)
1972 {
1973 int ret;
1974 int nargs = m->nr_args;
1975 int max_insns = ((long)image_end - (long)image) / AARCH64_INSN_SIZE;
1976 struct jit_ctx ctx = {
1977 .image = NULL,
1978 .idx = 0,
1979 };
1980
1981
1982 if (nargs > 8)
1983 return -ENOTSUPP;
1984
1985 ret = prepare_trampoline(&ctx, im, tlinks, orig_call, nargs, flags);
1986 if (ret < 0)
1987 return ret;
1988
1989 if (ret > max_insns)
1990 return -EFBIG;
1991
1992 ctx.image = image;
1993 ctx.idx = 0;
1994
1995 jit_fill_hole(image, (unsigned int)(image_end - image));
1996 ret = prepare_trampoline(&ctx, im, tlinks, orig_call, nargs, flags);
1997
1998 if (ret > 0 && validate_code(&ctx) < 0)
1999 ret = -EINVAL;
2000
2001 if (ret > 0)
2002 ret *= AARCH64_INSN_SIZE;
2003
2004 return ret;
2005 }
2006
2007 static bool is_long_jump(void *ip, void *target)
2008 {
2009 long offset;
2010
2011
2012 if (!target)
2013 return false;
2014
2015 offset = (long)target - (long)ip;
2016 return offset < -SZ_128M || offset >= SZ_128M;
2017 }
2018
2019 static int gen_branch_or_nop(enum aarch64_insn_branch_type type, void *ip,
2020 void *addr, void *plt, u32 *insn)
2021 {
2022 void *target;
2023
2024 if (!addr) {
2025 *insn = aarch64_insn_gen_nop();
2026 return 0;
2027 }
2028
2029 if (is_long_jump(ip, addr))
2030 target = plt;
2031 else
2032 target = addr;
2033
2034 *insn = aarch64_insn_gen_branch_imm((unsigned long)ip,
2035 (unsigned long)target,
2036 type);
2037
2038 return *insn != AARCH64_BREAK_FAULT ? 0 : -EFAULT;
2039 }
2040
2041
2042
2043
2044
2045
2046
2047
2048
2049
2050
2051
2052
2053
2054
2055
2056
2057
2058
2059
2060
2061
2062
2063
2064
2065
2066
2067
2068
2069
2070
2071
2072
2073
2074
2075
2076
2077
2078
2079
2080
2081
2082
2083
2084
2085
2086
2087
2088
2089
2090
2091
2092
2093
2094
2095
2096
2097
2098
2099
2100
2101 int bpf_arch_text_poke(void *ip, enum bpf_text_poke_type poke_type,
2102 void *old_addr, void *new_addr)
2103 {
2104 int ret;
2105 u32 old_insn;
2106 u32 new_insn;
2107 u32 replaced;
2108 struct bpf_plt *plt = NULL;
2109 unsigned long size = 0UL;
2110 unsigned long offset = ~0UL;
2111 enum aarch64_insn_branch_type branch_type;
2112 char namebuf[KSYM_NAME_LEN];
2113 void *image = NULL;
2114 u64 plt_target = 0ULL;
2115 bool poking_bpf_entry;
2116
2117 if (!__bpf_address_lookup((unsigned long)ip, &size, &offset, namebuf))
2118
2119
2120
2121
2122 return -ENOTSUPP;
2123
2124 image = ip - offset;
2125
2126 poking_bpf_entry = (offset == 0UL);
2127
2128
2129 if (poking_bpf_entry) {
2130
2131 plt = image + size - PLT_TARGET_OFFSET;
2132
2133
2134
2135
2136
2137
2138 ip = image + POKE_OFFSET * AARCH64_INSN_SIZE;
2139 }
2140
2141
2142 if (WARN_ON((is_long_jump(ip, new_addr) || is_long_jump(ip, old_addr)) &&
2143 !poking_bpf_entry))
2144 return -EINVAL;
2145
2146 if (poke_type == BPF_MOD_CALL)
2147 branch_type = AARCH64_INSN_BRANCH_LINK;
2148 else
2149 branch_type = AARCH64_INSN_BRANCH_NOLINK;
2150
2151 if (gen_branch_or_nop(branch_type, ip, old_addr, plt, &old_insn) < 0)
2152 return -EFAULT;
2153
2154 if (gen_branch_or_nop(branch_type, ip, new_addr, plt, &new_insn) < 0)
2155 return -EFAULT;
2156
2157 if (is_long_jump(ip, new_addr))
2158 plt_target = (u64)new_addr;
2159 else if (is_long_jump(ip, old_addr))
2160
2161
2162
2163
2164
2165 plt_target = (u64)&dummy_tramp;
2166
2167 if (plt_target) {
2168
2169
2170
2171 if (set_memory_rw(PAGE_MASK & ((uintptr_t)&plt->target), 1))
2172 return -EFAULT;
2173 WRITE_ONCE(plt->target, plt_target);
2174 set_memory_ro(PAGE_MASK & ((uintptr_t)&plt->target), 1);
2175
2176
2177
2178
2179
2180
2181 }
2182
2183
2184
2185
2186 if (old_insn == new_insn)
2187 return 0;
2188
2189 mutex_lock(&text_mutex);
2190 if (aarch64_insn_read(ip, &replaced)) {
2191 ret = -EFAULT;
2192 goto out;
2193 }
2194
2195 if (replaced != old_insn) {
2196 ret = -EFAULT;
2197 goto out;
2198 }
2199
2200
2201
2202
2203
2204
2205
2206
2207
2208
2209
2210
2211
2212
2213
2214
2215 ret = aarch64_insn_patch_text_nosync(ip, new_insn);
2216 out:
2217 mutex_unlock(&text_mutex);
2218
2219 return ret;
2220 }