diff options
| author | Markos Chandras <markos.chandras@imgtec.com> | 2014-06-23 05:38:56 -0400 |
|---|---|---|
| committer | Ralf Baechle <ralf@linux-mips.org> | 2014-06-26 05:48:22 -0400 |
| commit | e5bb48b0553d75918094c5a6f7b60a4359887218 (patch) | |
| tree | 77ac48000e90b3dc10e1ada667c17d500ff15502 /arch/mips/net | |
| parent | 10c4d614d2ffcfc17add01f9648c3e530fb308d1 (diff) | |
MIPS: bpf: Drop update_on_xread and always initialize the X register
Previously, update_on_xread() only set the reset flag if SEEN_X hasn't
been set already. However, SEEN_X is used to indicate that X is used
as destination or source register so there are some cases where X
is only used as source register and we really need to make sure that it
has been initialized in time. As a result of which, drop this function and
always set X to zero if it's used in any of the opcodes.
Signed-off-by: Markos Chandras <markos.chandras@imgtec.com>
Cc: David S. Miller <davem@davemloft.net>
Cc: Daniel Borkmann <dborkman@redhat.com>
Cc: Alexei Starovoitov <ast@plumgrid.com>
Cc: netdev@vger.kernel.org
Cc: linux-mips@linux-mips.org
Patchwork: https://patchwork.linux-mips.org/patch/7133/
Signed-off-by: Ralf Baechle <ralf@linux-mips.org>
Diffstat (limited to 'arch/mips/net')
| -rw-r--r-- | arch/mips/net/bpf_jit.c | 22 |
1 files changed, 1 insertions, 21 deletions
diff --git a/arch/mips/net/bpf_jit.c b/arch/mips/net/bpf_jit.c index 00c4c83972bb..1bcd599d9971 100644 --- a/arch/mips/net/bpf_jit.c +++ b/arch/mips/net/bpf_jit.c | |||
| @@ -119,8 +119,6 @@ | |||
| 119 | /* Arguments used by JIT */ | 119 | /* Arguments used by JIT */ |
| 120 | #define ARGS_USED_BY_JIT 2 /* only applicable to 64-bit */ | 120 | #define ARGS_USED_BY_JIT 2 /* only applicable to 64-bit */ |
| 121 | 121 | ||
| 122 | #define FLAG_NEED_X_RESET (1 << 0) | ||
| 123 | |||
| 124 | #define SBIT(x) (1 << (x)) /* Signed version of BIT() */ | 122 | #define SBIT(x) (1 << (x)) /* Signed version of BIT() */ |
| 125 | 123 | ||
| 126 | /** | 124 | /** |
| @@ -549,14 +547,6 @@ static inline u16 align_sp(unsigned int num) | |||
| 549 | return num; | 547 | return num; |
| 550 | } | 548 | } |
| 551 | 549 | ||
| 552 | static inline void update_on_xread(struct jit_ctx *ctx) | ||
| 553 | { | ||
| 554 | if (!(ctx->flags & SEEN_X)) | ||
| 555 | ctx->flags |= FLAG_NEED_X_RESET; | ||
| 556 | |||
| 557 | ctx->flags |= SEEN_X; | ||
| 558 | } | ||
| 559 | |||
| 560 | static bool is_load_to_a(u16 inst) | 550 | static bool is_load_to_a(u16 inst) |
| 561 | { | 551 | { |
| 562 | switch (inst) { | 552 | switch (inst) { |
| @@ -701,7 +691,7 @@ static void build_prologue(struct jit_ctx *ctx) | |||
| 701 | if (ctx->flags & SEEN_SKB) | 691 | if (ctx->flags & SEEN_SKB) |
| 702 | emit_reg_move(r_skb, MIPS_R_A0, ctx); | 692 | emit_reg_move(r_skb, MIPS_R_A0, ctx); |
| 703 | 693 | ||
| 704 | if (ctx->flags & FLAG_NEED_X_RESET) | 694 | if (ctx->flags & SEEN_X) |
| 705 | emit_jit_reg_move(r_X, r_zero, ctx); | 695 | emit_jit_reg_move(r_X, r_zero, ctx); |
| 706 | 696 | ||
| 707 | /* Do not leak kernel data to userspace */ | 697 | /* Do not leak kernel data to userspace */ |
| @@ -876,7 +866,6 @@ load_common: | |||
| 876 | /* A <- P[X + k:1] */ | 866 | /* A <- P[X + k:1] */ |
| 877 | load_order = 0; | 867 | load_order = 0; |
| 878 | load_ind: | 868 | load_ind: |
| 879 | update_on_xread(ctx); | ||
| 880 | ctx->flags |= SEEN_OFF | SEEN_X; | 869 | ctx->flags |= SEEN_OFF | SEEN_X; |
| 881 | emit_addiu(r_off, r_X, k, ctx); | 870 | emit_addiu(r_off, r_X, k, ctx); |
| 882 | goto load_common; | 871 | goto load_common; |
| @@ -972,7 +961,6 @@ load_ind: | |||
| 972 | break; | 961 | break; |
| 973 | case BPF_ALU | BPF_MUL | BPF_X: | 962 | case BPF_ALU | BPF_MUL | BPF_X: |
| 974 | /* A *= X */ | 963 | /* A *= X */ |
| 975 | update_on_xread(ctx); | ||
| 976 | ctx->flags |= SEEN_A | SEEN_X; | 964 | ctx->flags |= SEEN_A | SEEN_X; |
| 977 | emit_mul(r_A, r_A, r_X, ctx); | 965 | emit_mul(r_A, r_A, r_X, ctx); |
| 978 | break; | 966 | break; |
| @@ -1002,7 +990,6 @@ load_ind: | |||
| 1002 | break; | 990 | break; |
| 1003 | case BPF_ALU | BPF_DIV | BPF_X: | 991 | case BPF_ALU | BPF_DIV | BPF_X: |
| 1004 | /* A /= X */ | 992 | /* A /= X */ |
| 1005 | update_on_xread(ctx); | ||
| 1006 | ctx->flags |= SEEN_X | SEEN_A; | 993 | ctx->flags |= SEEN_X | SEEN_A; |
| 1007 | /* Check if r_X is zero */ | 994 | /* Check if r_X is zero */ |
| 1008 | emit_bcond(MIPS_COND_EQ, r_X, r_zero, | 995 | emit_bcond(MIPS_COND_EQ, r_X, r_zero, |
| @@ -1012,7 +999,6 @@ load_ind: | |||
| 1012 | break; | 999 | break; |
| 1013 | case BPF_ALU | BPF_MOD | BPF_X: | 1000 | case BPF_ALU | BPF_MOD | BPF_X: |
| 1014 | /* A %= X */ | 1001 | /* A %= X */ |
| 1015 | update_on_xread(ctx); | ||
| 1016 | ctx->flags |= SEEN_X | SEEN_A; | 1002 | ctx->flags |= SEEN_X | SEEN_A; |
| 1017 | /* Check if r_X is zero */ | 1003 | /* Check if r_X is zero */ |
| 1018 | emit_bcond(MIPS_COND_EQ, r_X, r_zero, | 1004 | emit_bcond(MIPS_COND_EQ, r_X, r_zero, |
| @@ -1027,7 +1013,6 @@ load_ind: | |||
| 1027 | break; | 1013 | break; |
| 1028 | case BPF_ALU | BPF_OR | BPF_X: | 1014 | case BPF_ALU | BPF_OR | BPF_X: |
| 1029 | /* A |= X */ | 1015 | /* A |= X */ |
| 1030 | update_on_xread(ctx); | ||
| 1031 | ctx->flags |= SEEN_A; | 1016 | ctx->flags |= SEEN_A; |
| 1032 | emit_ori(r_A, r_A, r_X, ctx); | 1017 | emit_ori(r_A, r_A, r_X, ctx); |
| 1033 | break; | 1018 | break; |
| @@ -1039,7 +1024,6 @@ load_ind: | |||
| 1039 | case BPF_ANC | SKF_AD_ALU_XOR_X: | 1024 | case BPF_ANC | SKF_AD_ALU_XOR_X: |
| 1040 | case BPF_ALU | BPF_XOR | BPF_X: | 1025 | case BPF_ALU | BPF_XOR | BPF_X: |
| 1041 | /* A ^= X */ | 1026 | /* A ^= X */ |
| 1042 | update_on_xread(ctx); | ||
| 1043 | ctx->flags |= SEEN_A; | 1027 | ctx->flags |= SEEN_A; |
| 1044 | emit_xor(r_A, r_A, r_X, ctx); | 1028 | emit_xor(r_A, r_A, r_X, ctx); |
| 1045 | break; | 1029 | break; |
| @@ -1050,7 +1034,6 @@ load_ind: | |||
| 1050 | break; | 1034 | break; |
| 1051 | case BPF_ALU | BPF_AND | BPF_X: | 1035 | case BPF_ALU | BPF_AND | BPF_X: |
| 1052 | /* A &= X */ | 1036 | /* A &= X */ |
| 1053 | update_on_xread(ctx); | ||
| 1054 | ctx->flags |= SEEN_A | SEEN_X; | 1037 | ctx->flags |= SEEN_A | SEEN_X; |
| 1055 | emit_and(r_A, r_A, r_X, ctx); | 1038 | emit_and(r_A, r_A, r_X, ctx); |
| 1056 | break; | 1039 | break; |
| @@ -1062,7 +1045,6 @@ load_ind: | |||
| 1062 | case BPF_ALU | BPF_LSH | BPF_X: | 1045 | case BPF_ALU | BPF_LSH | BPF_X: |
| 1063 | /* A <<= X */ | 1046 | /* A <<= X */ |
| 1064 | ctx->flags |= SEEN_A | SEEN_X; | 1047 | ctx->flags |= SEEN_A | SEEN_X; |
| 1065 | update_on_xread(ctx); | ||
| 1066 | emit_sllv(r_A, r_A, r_X, ctx); | 1048 | emit_sllv(r_A, r_A, r_X, ctx); |
| 1067 | break; | 1049 | break; |
| 1068 | case BPF_ALU | BPF_RSH | BPF_K: | 1050 | case BPF_ALU | BPF_RSH | BPF_K: |
| @@ -1072,7 +1054,6 @@ load_ind: | |||
| 1072 | break; | 1054 | break; |
| 1073 | case BPF_ALU | BPF_RSH | BPF_X: | 1055 | case BPF_ALU | BPF_RSH | BPF_X: |
| 1074 | ctx->flags |= SEEN_A | SEEN_X; | 1056 | ctx->flags |= SEEN_A | SEEN_X; |
| 1075 | update_on_xread(ctx); | ||
| 1076 | emit_srlv(r_A, r_A, r_X, ctx); | 1057 | emit_srlv(r_A, r_A, r_X, ctx); |
| 1077 | break; | 1058 | break; |
| 1078 | case BPF_ALU | BPF_NEG: | 1059 | case BPF_ALU | BPF_NEG: |
| @@ -1243,7 +1224,6 @@ jmp_cmp: | |||
| 1243 | case BPF_MISC | BPF_TXA: | 1224 | case BPF_MISC | BPF_TXA: |
| 1244 | /* A = X */ | 1225 | /* A = X */ |
| 1245 | ctx->flags |= SEEN_A | SEEN_X; | 1226 | ctx->flags |= SEEN_A | SEEN_X; |
| 1246 | update_on_xread(ctx); | ||
| 1247 | emit_jit_reg_move(r_A, r_X, ctx); | 1227 | emit_jit_reg_move(r_A, r_X, ctx); |
| 1248 | break; | 1228 | break; |
| 1249 | /* AUX */ | 1229 | /* AUX */ |
