Commit c7f1c639 authored by Gustavo A. R. Silva's avatar Gustavo A. R. Silva Committed by Khalid Elmously

usbip: vhci_sysfs: fix potential Spectre v1

pdev_nr and rhport can be controlled by user-space, hence leading to
a potential exploitation of the Spectre variant 1 vulnerability.

This issue was detected with the help of Smatch:
drivers/usb/usbip/vhci_sysfs.c:238 detach_store() warn: potential spectre issue 'vhcis'
drivers/usb/usbip/vhci_sysfs.c:328 attach_store() warn: potential spectre issue 'vhcis'
drivers/usb/usbip/vhci_sysfs.c:338 attach_store() warn: potential spectre issue 'vhci->vhci_hcd_ss->vdev'
drivers/usb/usbip/vhci_sysfs.c:340 attach_store() warn: potential spectre issue 'vhci->vhci_hcd_hs->vdev'

Fix this by sanitizing pdev_nr and rhport before using them to index
vhcis and vhci->vhci_hcd_ss->vdev respectively.

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

Cc: stable@vger.kernel.org
Signed-off-by: default avatarGustavo A. R. Silva <gustavo@embeddedor.com>
Acked-by: default avatarShuah Khan (Samsung OSG) <shuah@kernel.org>
Signed-off-by: default avatarGreg Kroah-Hartman <gregkh@linuxfoundation.org>

CVE-2017-5753

(backported from commit a0d6ec88)
[juergh:
 - Adjusted context.
 - Dropped the modification of valid_port() (not in Xenial) and modified
   the port checks in valid_args() and store_detach() instead().]
Signed-off-by: default avatarJuerg Haefliger <juergh@canonical.com>
Acked-by: default avatarStefan Bader <stefan.bader@canonical.com>
Acked-by: default avatarKleber Sacilotto de Souza <kleber.souza@canonical.com>
Signed-off-by: default avatarKhalid Elmously <khalid.elmously@canonical.com>
parent d22d2a88
......@@ -21,6 +21,9 @@
#include <linux/file.h>
#include <linux/net.h>
/* Hardening for Spectre-v1 */
#include <linux/nospec.h>
#include "usbip_common.h"
#include "vhci.h"
......@@ -127,6 +130,7 @@ static ssize_t store_detach(struct device *dev, struct device_attribute *attr,
dev_err(dev, "invalid port %u\n", rhport);
return -EINVAL;
}
rhport = array_index_nospec(rhport, VHCI_NPORTS);
err = vhci_port_disconnect(rhport);
if (err < 0)
......@@ -139,13 +143,14 @@ static ssize_t store_detach(struct device *dev, struct device_attribute *attr,
static DEVICE_ATTR(detach, S_IWUSR, NULL, store_detach);
/* Sysfs entry to establish a virtual connection */
static int valid_args(__u32 rhport, enum usb_device_speed speed)
static int valid_args(__u32 *rhport, enum usb_device_speed speed)
{
/* check rhport */
if (rhport >= VHCI_NPORTS) {
pr_err("port %u\n", rhport);
if (*rhport >= VHCI_NPORTS) {
pr_err("port %u\n", *rhport);
return -EINVAL;
}
*rhport = array_index_nospec(*rhport, VHCI_NPORTS);
/* check speed */
switch (speed) {
......@@ -197,7 +202,7 @@ static ssize_t store_attach(struct device *dev, struct device_attribute *attr,
rhport, sockfd, devid, speed);
/* check received parameters */
if (valid_args(rhport, speed) < 0)
if (valid_args(&rhport, speed) < 0)
return -EINVAL;
/* Extract socket from fd. */
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment