History

xen/netfront: force data bouncing when backend is untrusted

Bounce all data on the skbs to be transmitted into zeroed pages if the backend is untrusted. This avoids leaking data present in the pages shared with the backend but not part of the skb fragments. This requires introducing a new helper in order to allocate skbs with a size multiple of XEN_PAGE_SIZE so we don't leak contiguous data on the granted pages. Reporting whether the backend is to be trusted can be done using a module parameter, or from the xenstore frontend path as set by the toolstack when adding the device. This is CVE-2022-33741, part of XSA-403.

Roger Pau Monne committed 4 years ago

Commit 44910011 parent 307c8de1 file · +47 −2Browse files

Unified · Split

drivers/net/xen-netfront.c+47−2
@@ -66,6 +66,10 @@ module_param_named(max_queues, xennet_max_queues, uint, 0644); · 65 unmodified lines
66MODULE_PARM_DESC(max_queues,66MODULE_PARM_DESC(max_queues,
67 "Maximum number of queues per virtual interface");67 "Maximum number of queues per virtual interface");
68 68
69static bool __read_mostly xennet_trusted = true;
70module_param_named(trusted, xennet_trusted, bool, 0644);
71MODULE_PARM_DESC(trusted, "Is the backend trusted");
72
69#define XENNET_TIMEOUT (5 * HZ)73#define XENNET_TIMEOUT (5 * HZ)
70 74
71static const struct ethtool_ops xennet_ethtool_ops;75static const struct ethtool_ops xennet_ethtool_ops;
@@ -173,6 +177,9 @@ struct netfront_info { · 101 unmodified lines
173 /* Is device behaving sane? */177 /* Is device behaving sane? */
174 bool broken;178 bool broken;
175 179
180 /* Should skbs be bounced into a zeroed buffer? */
181 bool bounce;
182
176 atomic_t rx_gso_checksum_fixup;183 atomic_t rx_gso_checksum_fixup;
177};184};
178 185
@@ -666,6 +673,33 @@ static int xennet_xdp_xmit(struct net_device *dev, int n, · 487 unmodified lines
666 return nxmit;673 return nxmit;
667}674}
668 675
676struct sk_buff *bounce_skb(const struct sk_buff *skb)
677{
678 unsigned int headerlen = skb_headroom(skb);
679 /* Align size to allocate full pages and avoid contiguous data leaks */
680 unsigned int size = ALIGN(skb_end_offset(skb) + skb->data_len,
681 XEN_PAGE_SIZE);
682 struct sk_buff *n = alloc_skb(size, GFP_ATOMIC | __GFP_ZERO);
683
684 if (!n)
685 return NULL;
686
687 if (!IS_ALIGNED((uintptr_t)n->head, XEN_PAGE_SIZE)) {
688 WARN_ONCE(1, "misaligned skb allocated\n");
689 kfree_skb(n);
690 return NULL;
691 }
692
693 /* Set the data pointer */
694 skb_reserve(n, headerlen);
695 /* Set the tail pointer and length */
696 skb_put(n, skb->len);
697
698 BUG_ON(skb_copy_bits(skb, -headerlen, n->head, headerlen + skb->len));
699
700 skb_copy_header(n, skb);
701 return n;
702}
669 703
670#define MAX_XEN_SKB_FRAGS (65536 / XEN_PAGE_SIZE + 1)704#define MAX_XEN_SKB_FRAGS (65536 / XEN_PAGE_SIZE + 1)
671 705
@@ -719,9 +753,13 @@ static netdev_tx_t xennet_start_xmit(struct sk_buff *skb, struct net_device *dev · 47 unmodified lines
719 753
720 /* The first req should be at least ETH_HLEN size or the packet will be754 /* The first req should be at least ETH_HLEN size or the packet will be
721 * dropped by netback.755 * dropped by netback.
756 *
757 * If the backend is not trusted bounce all data to zeroed pages to
758 * avoid exposing contiguous data on the granted page not belonging to
759 * the skb.
722 */760 */
723 if (unlikely(PAGE_SIZE - offset < ETH_HLEN)) {761 if (np->bounce || unlikely(PAGE_SIZE - offset < ETH_HLEN)) {
724 nskb = skb_copy(skb, GFP_ATOMIC);762 nskb = bounce_skb(skb);
725 if (!nskb)763 if (!nskb)
726 goto drop;764 goto drop;
727 dev_consume_skb_any(skb);765 dev_consume_skb_any(skb);
@@ -2215,6 +2253,10 @@ static int talk_to_netback(struct xenbus_device *dev, · 1487 unmodified lines
2215 2253
2216 info->netdev->irq = 0;2254 info->netdev->irq = 0;
2217 2255
2256 /* Check if backend is trusted. */
2257 info->bounce = !xennet_trusted ||
2258 !xenbus_read_unsigned(dev->nodename, "trusted", 1);
2259
2218 /* Check if backend supports multiple queues */2260 /* Check if backend supports multiple queues */
2219 max_queues = xenbus_read_unsigned(info->xbdev->otherend,2261 max_queues = xenbus_read_unsigned(info->xbdev->otherend,
2220 "multi-queue-max-queues", 1);2262 "multi-queue-max-queues", 1);
@@ -2382,6 +2424,9 @@ static int xennet_connect(struct net_device *dev) · 161 unmodified lines
2382 return err;2424 return err;
2383 if (np->netback_has_xdp_headroom)2425 if (np->netback_has_xdp_headroom)
2384 pr_info("backend supports XDP headroom\n");2426 pr_info("backend supports XDP headroom\n");
2427 if (np->bounce)
2428 dev_info(&np->xbdev->dev,
2429 "bouncing transmitted data to zeroed pages\n");
2385 2430
2386 /* talk_to_netback() sets the correct number of queues */2431 /* talk_to_netback() sets the correct number of queues */
2387 num_queues = dev->real_num_tx_queues;2432 num_queues = dev->real_num_tx_queues;