]> git.proxmox.com Git - pve-kernel.git/blame - patches/kernel/0226-UBUNTU-SAUCE-bpf-reject-out-of-bounds-stack-pointer-.patch
KPTI: add follow-up fixes
[pve-kernel.git] / patches / kernel / 0226-UBUNTU-SAUCE-bpf-reject-out-of-bounds-stack-pointer-.patch
CommitLineData
321d628a
FG
1From 3c5659ffcc9d2497045dda465a35720f78314e87 Mon Sep 17 00:00:00 2001
2From: Jann Horn <jannh@google.com>
3Date: Thu, 4 Jan 2018 08:01:21 -0600
e4cdf2a5 4Subject: [PATCH 226/241] UBUNTU: SAUCE: bpf: reject out-of-bounds stack
321d628a
FG
5 pointer calculation
6MIME-Version: 1.0
7Content-Type: text/plain; charset=UTF-8
8Content-Transfer-Encoding: 8bit
9
10Reject programs that compute wildly out-of-bounds stack pointers.
11Otherwise, pointers can be computed with an offset that doesn't fit into an
12`int`, causing security issues in the stack memory access check (as well as
13signed integer overflow during offset addition).
14
15This is a fix specifically for the v4.9 stable tree because the mainline
16code looks very different at this point.
17
18Fixes: 7bca0a9702edf ("bpf: enhance verifier to understand stack pointer arithmetic")
19Signed-off-by: Jann Horn <jannh@google.com>
20Acked-by: Daniel Borkmann <daniel@iogearbox.net>
21CVE-2017-17863
22Link: https://www.spinics.net/lists/stable/msg206985.html
23Signed-off-by: Seth Forshee <seth.forshee@canonical.com>
24Signed-off-by: Andy Whitcroft <apw@canonical.com>
25Signed-off-by: Kleber Sacilotto de Souza <kleber.souza@canonical.com>
26(cherry picked from commit 1c26ffd0e9b24d512824cabc6687a14d4777d0f3)
27Signed-off-by: Fabian Grünbichler <f.gruenbichler@proxmox.com>
28---
29 kernel/bpf/verifier.c | 22 ++++++++++++++++++++--
30 1 file changed, 20 insertions(+), 2 deletions(-)
31
32diff --git a/kernel/bpf/verifier.c b/kernel/bpf/verifier.c
33index 3940019b9740..4321625fe32a 100644
34--- a/kernel/bpf/verifier.c
35+++ b/kernel/bpf/verifier.c
36@@ -2122,10 +2122,28 @@ static int check_alu_op(struct bpf_verifier_env *env, struct bpf_insn *insn)
37 ((BPF_SRC(insn->code) == BPF_X &&
38 regs[insn->src_reg].type == CONST_IMM) ||
39 BPF_SRC(insn->code) == BPF_K)) {
40- if (BPF_SRC(insn->code) == BPF_X)
41+ if (BPF_SRC(insn->code) == BPF_X) {
42+ /* check in case the register contains a big
43+ * 64-bit value
44+ */
45+ if (regs[insn->src_reg].imm < -MAX_BPF_STACK ||
46+ regs[insn->src_reg].imm > MAX_BPF_STACK) {
47+ verbose("R%d value too big in R%d pointer arithmetic\n",
48+ insn->src_reg, insn->dst_reg);
49+ return -EACCES;
50+ }
51 dst_reg->imm += regs[insn->src_reg].imm;
52- else
53+ } else {
54+ /* safe against overflow: addition of 32-bit
55+ * numbers in 64-bit representation
56+ */
57 dst_reg->imm += insn->imm;
58+ }
59+ if (dst_reg->imm > 0 || dst_reg->imm < -MAX_BPF_STACK) {
60+ verbose("R%d out-of-bounds pointer arithmetic\n",
61+ insn->dst_reg);
62+ return -EACCES;
63+ }
64 return 0;
65 } else if (opcode == BPF_ADD &&
66 BPF_CLASS(insn->code) == BPF_ALU64 &&
67--
682.14.2
69