| From f7e9a5f8467d8ed675f455284328e4ae79b76704 Mon Sep 17 00:00:00 2001 |
| From: Jiong Wang <jiong.wang@netronome.com> |
| Date: Fri, 22 Feb 2019 22:36:04 +0000 |
| Subject: nfp: bpf: fix ALU32 high bits clearance bug |
| |
| [ Upstream commit f036ebd9bfbe1e91a3d855e85e05fc5ff156b641 ] |
| |
| NFP BPF JIT compiler is doing a couple of small optimizations when jitting |
| ALU imm instructions, some of these optimizations could save code-gen, for |
| example: |
| |
| A & -1 = A |
| A | 0 = A |
| A ^ 0 = A |
| |
| However, for ALU32, high 32-bit of the 64-bit register should still be |
| cleared according to ISA semantics. |
| |
| Fixes: cd7df56ed3e6 ("nfp: add BPF to NFP code translator") |
| Reviewed-by: Jakub Kicinski <jakub.kicinski@netronome.com> |
| Signed-off-by: Jiong Wang <jiong.wang@netronome.com> |
| Signed-off-by: Daniel Borkmann <daniel@iogearbox.net> |
| Signed-off-by: Sasha Levin <sashal@kernel.org> |
| --- |
| .../net/ethernet/netronome/nfp/nfp_bpf_jit.c | 17 ++++++----------- |
| 1 file changed, 6 insertions(+), 11 deletions(-) |
| |
| diff --git a/drivers/net/ethernet/netronome/nfp/nfp_bpf_jit.c b/drivers/net/ethernet/netronome/nfp/nfp_bpf_jit.c |
| index 6bfcd6eb74ca..73087770d72f 100644 |
| --- a/drivers/net/ethernet/netronome/nfp/nfp_bpf_jit.c |
| +++ b/drivers/net/ethernet/netronome/nfp/nfp_bpf_jit.c |
| @@ -756,15 +756,10 @@ wrp_alu64_reg(struct nfp_prog *nfp_prog, struct nfp_insn_meta *meta, |
| |
| static int |
| wrp_alu32_imm(struct nfp_prog *nfp_prog, struct nfp_insn_meta *meta, |
| - enum alu_op alu_op, bool skip) |
| + enum alu_op alu_op) |
| { |
| const struct bpf_insn *insn = &meta->insn; |
| |
| - if (skip) { |
| - meta->skip = true; |
| - return 0; |
| - } |
| - |
| wrp_alu_imm(nfp_prog, insn->dst_reg * 2, alu_op, insn->imm); |
| wrp_immed(nfp_prog, reg_both(insn->dst_reg * 2 + 1), 0); |
| |
| @@ -1017,7 +1012,7 @@ static int xor_reg(struct nfp_prog *nfp_prog, struct nfp_insn_meta *meta) |
| |
| static int xor_imm(struct nfp_prog *nfp_prog, struct nfp_insn_meta *meta) |
| { |
| - return wrp_alu32_imm(nfp_prog, meta, ALU_OP_XOR, !meta->insn.imm); |
| + return wrp_alu32_imm(nfp_prog, meta, ALU_OP_XOR); |
| } |
| |
| static int and_reg(struct nfp_prog *nfp_prog, struct nfp_insn_meta *meta) |
| @@ -1027,7 +1022,7 @@ static int and_reg(struct nfp_prog *nfp_prog, struct nfp_insn_meta *meta) |
| |
| static int and_imm(struct nfp_prog *nfp_prog, struct nfp_insn_meta *meta) |
| { |
| - return wrp_alu32_imm(nfp_prog, meta, ALU_OP_AND, !~meta->insn.imm); |
| + return wrp_alu32_imm(nfp_prog, meta, ALU_OP_AND); |
| } |
| |
| static int or_reg(struct nfp_prog *nfp_prog, struct nfp_insn_meta *meta) |
| @@ -1037,7 +1032,7 @@ static int or_reg(struct nfp_prog *nfp_prog, struct nfp_insn_meta *meta) |
| |
| static int or_imm(struct nfp_prog *nfp_prog, struct nfp_insn_meta *meta) |
| { |
| - return wrp_alu32_imm(nfp_prog, meta, ALU_OP_OR, !meta->insn.imm); |
| + return wrp_alu32_imm(nfp_prog, meta, ALU_OP_OR); |
| } |
| |
| static int add_reg(struct nfp_prog *nfp_prog, struct nfp_insn_meta *meta) |
| @@ -1047,7 +1042,7 @@ static int add_reg(struct nfp_prog *nfp_prog, struct nfp_insn_meta *meta) |
| |
| static int add_imm(struct nfp_prog *nfp_prog, struct nfp_insn_meta *meta) |
| { |
| - return wrp_alu32_imm(nfp_prog, meta, ALU_OP_ADD, !meta->insn.imm); |
| + return wrp_alu32_imm(nfp_prog, meta, ALU_OP_ADD); |
| } |
| |
| static int sub_reg(struct nfp_prog *nfp_prog, struct nfp_insn_meta *meta) |
| @@ -1057,7 +1052,7 @@ static int sub_reg(struct nfp_prog *nfp_prog, struct nfp_insn_meta *meta) |
| |
| static int sub_imm(struct nfp_prog *nfp_prog, struct nfp_insn_meta *meta) |
| { |
| - return wrp_alu32_imm(nfp_prog, meta, ALU_OP_SUB, !meta->insn.imm); |
| + return wrp_alu32_imm(nfp_prog, meta, ALU_OP_SUB); |
| } |
| |
| static int shl_imm(struct nfp_prog *nfp_prog, struct nfp_insn_meta *meta) |
| -- |
| 2.19.1 |
| |