diff options
Diffstat (limited to 'arch/powerpc/net/bpf_jit_comp64.c')
-rw-r--r-- | arch/powerpc/net/bpf_jit_comp64.c | 109 |
1 files changed, 1 insertions, 108 deletions
diff --git a/arch/powerpc/net/bpf_jit_comp64.c b/arch/powerpc/net/bpf_jit_comp64.c index 0ef3d9580e98..1bdb1aff0619 100644 --- a/arch/powerpc/net/bpf_jit_comp64.c +++ b/arch/powerpc/net/bpf_jit_comp64.c | |||
@@ -59,7 +59,7 @@ static inline bool bpf_has_stack_frame(struct codegen_context *ctx) | |||
59 | * [ prev sp ] <------------- | 59 | * [ prev sp ] <------------- |
60 | * [ ... ] | | 60 | * [ ... ] | |
61 | * sp (r1) ---> [ stack pointer ] -------------- | 61 | * sp (r1) ---> [ stack pointer ] -------------- |
62 | * [ nv gpr save area ] 8*8 | 62 | * [ nv gpr save area ] 6*8 |
63 | * [ tail_call_cnt ] 8 | 63 | * [ tail_call_cnt ] 8 |
64 | * [ local_tmp_var ] 8 | 64 | * [ local_tmp_var ] 8 |
65 | * [ unused red zone ] 208 bytes protected | 65 | * [ unused red zone ] 208 bytes protected |
@@ -88,21 +88,6 @@ static int bpf_jit_stack_offsetof(struct codegen_context *ctx, int reg) | |||
88 | BUG(); | 88 | BUG(); |
89 | } | 89 | } |
90 | 90 | ||
91 | static void bpf_jit_emit_skb_loads(u32 *image, struct codegen_context *ctx) | ||
92 | { | ||
93 | /* | ||
94 | * Load skb->len and skb->data_len | ||
95 | * r3 points to skb | ||
96 | */ | ||
97 | PPC_LWZ(b2p[SKB_HLEN_REG], 3, offsetof(struct sk_buff, len)); | ||
98 | PPC_LWZ(b2p[TMP_REG_1], 3, offsetof(struct sk_buff, data_len)); | ||
99 | /* header_len = len - data_len */ | ||
100 | PPC_SUB(b2p[SKB_HLEN_REG], b2p[SKB_HLEN_REG], b2p[TMP_REG_1]); | ||
101 | |||
102 | /* skb->data pointer */ | ||
103 | PPC_BPF_LL(b2p[SKB_DATA_REG], 3, offsetof(struct sk_buff, data)); | ||
104 | } | ||
105 | |||
106 | static void bpf_jit_build_prologue(u32 *image, struct codegen_context *ctx) | 91 | static void bpf_jit_build_prologue(u32 *image, struct codegen_context *ctx) |
107 | { | 92 | { |
108 | int i; | 93 | int i; |
@@ -145,18 +130,6 @@ static void bpf_jit_build_prologue(u32 *image, struct codegen_context *ctx) | |||
145 | if (bpf_is_seen_register(ctx, i)) | 130 | if (bpf_is_seen_register(ctx, i)) |
146 | PPC_BPF_STL(b2p[i], 1, bpf_jit_stack_offsetof(ctx, b2p[i])); | 131 | PPC_BPF_STL(b2p[i], 1, bpf_jit_stack_offsetof(ctx, b2p[i])); |
147 | 132 | ||
148 | /* | ||
149 | * Save additional non-volatile regs if we cache skb | ||
150 | * Also, setup skb data | ||
151 | */ | ||
152 | if (ctx->seen & SEEN_SKB) { | ||
153 | PPC_BPF_STL(b2p[SKB_HLEN_REG], 1, | ||
154 | bpf_jit_stack_offsetof(ctx, b2p[SKB_HLEN_REG])); | ||
155 | PPC_BPF_STL(b2p[SKB_DATA_REG], 1, | ||
156 | bpf_jit_stack_offsetof(ctx, b2p[SKB_DATA_REG])); | ||
157 | bpf_jit_emit_skb_loads(image, ctx); | ||
158 | } | ||
159 | |||
160 | /* Setup frame pointer to point to the bpf stack area */ | 133 | /* Setup frame pointer to point to the bpf stack area */ |
161 | if (bpf_is_seen_register(ctx, BPF_REG_FP)) | 134 | if (bpf_is_seen_register(ctx, BPF_REG_FP)) |
162 | PPC_ADDI(b2p[BPF_REG_FP], 1, | 135 | PPC_ADDI(b2p[BPF_REG_FP], 1, |
@@ -172,14 +145,6 @@ static void bpf_jit_emit_common_epilogue(u32 *image, struct codegen_context *ctx | |||
172 | if (bpf_is_seen_register(ctx, i)) | 145 | if (bpf_is_seen_register(ctx, i)) |
173 | PPC_BPF_LL(b2p[i], 1, bpf_jit_stack_offsetof(ctx, b2p[i])); | 146 | PPC_BPF_LL(b2p[i], 1, bpf_jit_stack_offsetof(ctx, b2p[i])); |
174 | 147 | ||
175 | /* Restore non-volatile registers used for skb cache */ | ||
176 | if (ctx->seen & SEEN_SKB) { | ||
177 | PPC_BPF_LL(b2p[SKB_HLEN_REG], 1, | ||
178 | bpf_jit_stack_offsetof(ctx, b2p[SKB_HLEN_REG])); | ||
179 | PPC_BPF_LL(b2p[SKB_DATA_REG], 1, | ||
180 | bpf_jit_stack_offsetof(ctx, b2p[SKB_DATA_REG])); | ||
181 | } | ||
182 | |||
183 | /* Tear down our stack frame */ | 148 | /* Tear down our stack frame */ |
184 | if (bpf_has_stack_frame(ctx)) { | 149 | if (bpf_has_stack_frame(ctx)) { |
185 | PPC_ADDI(1, 1, BPF_PPC_STACKFRAME + ctx->stack_size); | 150 | PPC_ADDI(1, 1, BPF_PPC_STACKFRAME + ctx->stack_size); |
@@ -753,23 +718,10 @@ emit_clear: | |||
753 | ctx->seen |= SEEN_FUNC; | 718 | ctx->seen |= SEEN_FUNC; |
754 | func = (u8 *) __bpf_call_base + imm; | 719 | func = (u8 *) __bpf_call_base + imm; |
755 | 720 | ||
756 | /* Save skb pointer if we need to re-cache skb data */ | ||
757 | if ((ctx->seen & SEEN_SKB) && | ||
758 | bpf_helper_changes_pkt_data(func)) | ||
759 | PPC_BPF_STL(3, 1, bpf_jit_stack_local(ctx)); | ||
760 | |||
761 | bpf_jit_emit_func_call(image, ctx, (u64)func); | 721 | bpf_jit_emit_func_call(image, ctx, (u64)func); |
762 | 722 | ||
763 | /* move return value from r3 to BPF_REG_0 */ | 723 | /* move return value from r3 to BPF_REG_0 */ |
764 | PPC_MR(b2p[BPF_REG_0], 3); | 724 | PPC_MR(b2p[BPF_REG_0], 3); |
765 | |||
766 | /* refresh skb cache */ | ||
767 | if ((ctx->seen & SEEN_SKB) && | ||
768 | bpf_helper_changes_pkt_data(func)) { | ||
769 | /* reload skb pointer to r3 */ | ||
770 | PPC_BPF_LL(3, 1, bpf_jit_stack_local(ctx)); | ||
771 | bpf_jit_emit_skb_loads(image, ctx); | ||
772 | } | ||
773 | break; | 725 | break; |
774 | 726 | ||
775 | /* | 727 | /* |
@@ -887,65 +839,6 @@ cond_branch: | |||
887 | break; | 839 | break; |
888 | 840 | ||
889 | /* | 841 | /* |
890 | * Loads from packet header/data | ||
891 | * Assume 32-bit input value in imm and X (src_reg) | ||
892 | */ | ||
893 | |||
894 | /* Absolute loads */ | ||
895 | case BPF_LD | BPF_W | BPF_ABS: | ||
896 | func = (u8 *)CHOOSE_LOAD_FUNC(imm, sk_load_word); | ||
897 | goto common_load_abs; | ||
898 | case BPF_LD | BPF_H | BPF_ABS: | ||
899 | func = (u8 *)CHOOSE_LOAD_FUNC(imm, sk_load_half); | ||
900 | goto common_load_abs; | ||
901 | case BPF_LD | BPF_B | BPF_ABS: | ||
902 | func = (u8 *)CHOOSE_LOAD_FUNC(imm, sk_load_byte); | ||
903 | common_load_abs: | ||
904 | /* | ||
905 | * Load from [imm] | ||
906 | * Load into r4, which can just be passed onto | ||
907 | * skb load helpers as the second parameter | ||
908 | */ | ||
909 | PPC_LI32(4, imm); | ||
910 | goto common_load; | ||
911 | |||
912 | /* Indirect loads */ | ||
913 | case BPF_LD | BPF_W | BPF_IND: | ||
914 | func = (u8 *)sk_load_word; | ||
915 | goto common_load_ind; | ||
916 | case BPF_LD | BPF_H | BPF_IND: | ||
917 | func = (u8 *)sk_load_half; | ||
918 | goto common_load_ind; | ||
919 | case BPF_LD | BPF_B | BPF_IND: | ||
920 | func = (u8 *)sk_load_byte; | ||
921 | common_load_ind: | ||
922 | /* | ||
923 | * Load from [src_reg + imm] | ||
924 | * Treat src_reg as a 32-bit value | ||
925 | */ | ||
926 | PPC_EXTSW(4, src_reg); | ||
927 | if (imm) { | ||
928 | if (imm >= -32768 && imm < 32768) | ||
929 | PPC_ADDI(4, 4, IMM_L(imm)); | ||
930 | else { | ||
931 | PPC_LI32(b2p[TMP_REG_1], imm); | ||
932 | PPC_ADD(4, 4, b2p[TMP_REG_1]); | ||
933 | } | ||
934 | } | ||
935 | |||
936 | common_load: | ||
937 | ctx->seen |= SEEN_SKB; | ||
938 | ctx->seen |= SEEN_FUNC; | ||
939 | bpf_jit_emit_func_call(image, ctx, (u64)func); | ||
940 | |||
941 | /* | ||
942 | * Helper returns 'lt' condition on error, and an | ||
943 | * appropriate return value in BPF_REG_0 | ||
944 | */ | ||
945 | PPC_BCC(COND_LT, exit_addr); | ||
946 | break; | ||
947 | |||
948 | /* | ||
949 | * Tail call | 842 | * Tail call |
950 | */ | 843 | */ |
951 | case BPF_JMP | BPF_TAIL_CALL: | 844 | case BPF_JMP | BPF_TAIL_CALL: |