Received: by 2002:ac0:bc90:0:0:0:0:0 with SMTP id a16csp5584139img; Wed, 27 Mar 2019 11:09:04 -0700 (PDT) X-Google-Smtp-Source: APXvYqxK0dHdNiVoj0RmxaYzKFeTCvVm0gg4JLWbhXu/IVRHPXpS7jW1/tQL3BsUe7wr+b+FFSTz X-Received: by 2002:aa7:8201:: with SMTP id k1mr36794652pfi.53.1553710144442; Wed, 27 Mar 2019 11:09:04 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1553710144; cv=none; d=google.com; s=arc-20160816; b=q0Wmr/MV1KabzPc8vhZsEiJicsYKEyJdL9DAD7q9r64y/UdIkAWsvq7Y9bflRg1Itu fxr3AT3I/fdig9cLkTVXsuK4UNu5F4N2zbTSh0qzhGuVBKyoEpOjKEI3kbKtXgkBeviY 9PCXSe66FO/m8O7TxP4oImFB67hijkaqXjMQnx5E6loplvJ45rPxLHkBs92SogW3/Yn1 HyLXw5OWxz+QpYQvmZB6Z1oZBOFTHOejpofh3RJ/l3HIQcYFXj8snmPau1bdbbxICBiX xIPw95uaCMatkQvXu0ajNTPEB5oAJQJO958EsQrUA+GRs1ZJeTPxLbGcNBetMl+VtJ9H kVEA== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=list-id:precedence:sender:content-transfer-encoding:mime-version :references:in-reply-to:message-id:date:subject:cc:to:from :dkim-signature; bh=BMqZuKF867ZADYjIswqhmdj92qdn9lP4CrR+3nLoP4w=; b=yWATG+z11tZ9NrmT6YbNTNf4OaDYDzyMV19ZRlQc/v7EjNIAoc0TNf4qq9M9+GgH5T jdpCpqal4gg8HTg7Iv1Bn/Mlk6CCPZ4KMmZmllZMTHN0rKP0aYeMpw0wZM8ic24+mjZH 56jJjnXY/GD7Rh9EFJLSjd5hdaNfLeN4jxvRdX9Oyk2LPIckYwUfG8CtUK+slEWOzJKT XP4TR/RA4Jk3gWs97p9/N2ozoBfzEMH85bIsKHsoGaLOWQu8314meL7cIWv+tTzJFxT7 2HBvjBz5sEjL9nYAY3jzEZZwtwAxnFGaYlQ8H8IJHlA5JLkxJDUDSp1Q7stQUXrXgrOZ YpKQ== ARC-Authentication-Results: i=1; mx.google.com; dkim=pass header.i=@kernel.org header.s=default header.b=J1KLjW7C; spf=pass (google.com: best guess record for domain of linux-kernel-owner@vger.kernel.org designates 209.132.180.67 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=pass (p=NONE sp=NONE dis=NONE) header.from=kernel.org Return-Path: Received: from vger.kernel.org (vger.kernel.org. [209.132.180.67]) by mx.google.com with ESMTP id t69si19122923pfa.7.2019.03.27.11.08.49; Wed, 27 Mar 2019 11:09:04 -0700 (PDT) Received-SPF: pass (google.com: best guess record for domain of linux-kernel-owner@vger.kernel.org designates 209.132.180.67 as permitted sender) client-ip=209.132.180.67; Authentication-Results: mx.google.com; dkim=pass header.i=@kernel.org header.s=default header.b=J1KLjW7C; spf=pass (google.com: best guess record for domain of linux-kernel-owner@vger.kernel.org designates 209.132.180.67 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=pass (p=NONE sp=NONE dis=NONE) header.from=kernel.org Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S2388219AbfC0SHf (ORCPT + 99 others); Wed, 27 Mar 2019 14:07:35 -0400 Received: from mail.kernel.org ([198.145.29.99]:49378 "EHLO mail.kernel.org" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S2387685AbfC0SHb (ORCPT ); Wed, 27 Mar 2019 14:07:31 -0400 Received: from sasha-vm.mshome.net (c-73-47-72-35.hsd1.nh.comcast.net [73.47.72.35]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by mail.kernel.org (Postfix) with ESMTPSA id 49FA32070B; Wed, 27 Mar 2019 18:07:29 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=kernel.org; s=default; t=1553710050; bh=tl42kwFAFR+iPHn8laL8wOEP4kiIf0qgujs/5nh7pQk=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=J1KLjW7CgWLYY77gDtyL1u3v1iwUFagi+syGiBeLS6BaB3M6V7MOXH8sVMZy/wejc HexcngFiOuXLdwyMYDV/YtfOKS8f7YubfJoZh5sH6MWxd5HDHKBGenAI1+RLnLxkEj C8iYnPnrbx2S5LvNsZpL3MWpLqOiL6ipcsuAY+RM= From: Sasha Levin To: linux-kernel@vger.kernel.org, stable@vger.kernel.org Cc: Breno Leitao , Michael Ellerman , Sasha Levin , linuxppc-dev@lists.ozlabs.org Subject: [PATCH AUTOSEL 5.0 174/262] powerpc/ptrace: Mitigate potential Spectre v1 Date: Wed, 27 Mar 2019 14:00:29 -0400 Message-Id: <20190327180158.10245-174-sashal@kernel.org> X-Mailer: git-send-email 2.19.1 In-Reply-To: <20190327180158.10245-1-sashal@kernel.org> References: <20190327180158.10245-1-sashal@kernel.org> MIME-Version: 1.0 X-Patchwork-Hint: Ignore Content-Transfer-Encoding: 8bit Sender: linux-kernel-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org From: Breno Leitao [ Upstream commit ebb0e13ead2ddc186a80b1b0235deeefc5a1a667 ] 'regno' is directly controlled by user space, hence leading to a potential exploitation of the Spectre variant 1 vulnerability. On PTRACE_SETREGS and PTRACE_GETREGS requests, user space passes the register number that would be read or written. This register number is called 'regno' which is part of the 'addr' syscall parameter. This 'regno' value is checked against the maximum pt_regs structure size, and then used to dereference it, which matches the initial part of a Spectre v1 (and Spectre v1.1) attack. The dereferenced value, then, is returned to userspace in the GETREGS case. This patch sanitizes 'regno' before using it to dereference pt_reg. Notice that given that speculation windows are large, the policy is to kill the speculation on the first load and not worry if it can be completed with a dependent load/store [1]. [1] https://marc.info/?l=linux-kernel&m=152449131114778&w=2 Signed-off-by: Breno Leitao Acked-by: Gustavo A. R. Silva Signed-off-by: Michael Ellerman Signed-off-by: Sasha Levin --- arch/powerpc/kernel/ptrace.c | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/arch/powerpc/kernel/ptrace.c b/arch/powerpc/kernel/ptrace.c index 53151698bfe0..d9ac7d94656e 100644 --- a/arch/powerpc/kernel/ptrace.c +++ b/arch/powerpc/kernel/ptrace.c @@ -33,6 +33,7 @@ #include #include #include +#include #include #include @@ -274,6 +275,8 @@ static int set_user_trap(struct task_struct *task, unsigned long trap) */ int ptrace_get_reg(struct task_struct *task, int regno, unsigned long *data) { + unsigned int regs_max; + if ((task->thread.regs == NULL) || !data) return -EIO; @@ -297,7 +300,9 @@ int ptrace_get_reg(struct task_struct *task, int regno, unsigned long *data) } #endif - if (regno < (sizeof(struct user_pt_regs) / sizeof(unsigned long))) { + regs_max = sizeof(struct user_pt_regs) / sizeof(unsigned long); + if (regno < regs_max) { + regno = array_index_nospec(regno, regs_max); *data = ((unsigned long *)task->thread.regs)[regno]; return 0; } @@ -321,6 +326,7 @@ int ptrace_put_reg(struct task_struct *task, int regno, unsigned long data) return set_user_dscr(task, data); if (regno <= PT_MAX_PUT_REG) { + regno = array_index_nospec(regno, PT_MAX_PUT_REG + 1); ((unsigned long *)task->thread.regs)[regno] = data; return 0; } -- 2.19.1