summaryrefslogtreecommitdiff
path: root/net/core
diff options
context:
space:
mode:
authorTakashi Iwai <tiwai@suse.de>2026-04-09 09:31:21 +0300
committerTakashi Iwai <tiwai@suse.de>2026-04-09 09:32:17 +0300
commit3f44bccdd6605d5d156c02ea2f861dcd30ef5dcd (patch)
tree799286d69c8ea6060573bce2efdc10ea089ed356 /net/core
parent292286b2d229fb732421429b027d38ac3f969383 (diff)
parent00afb1811fa638dacf125dd1c343b7a181624dfd (diff)
downloadlinux-3f44bccdd6605d5d156c02ea2f861dcd30ef5dcd.tar.xz
Merge branch 'for-linus' into for-next
Pull 7.0-devel branch for further development of HD-audio codec quirks. Signed-off-by: Takashi Iwai <tiwai@suse.de>
Diffstat (limited to 'net/core')
-rw-r--r--net/core/dev.c33
-rw-r--r--net/core/rtnetlink.c28
-rw-r--r--net/core/skmsg.c13
3 files changed, 58 insertions, 16 deletions
diff --git a/net/core/dev.c b/net/core/dev.c
index 14a83f2035b9..831129f2a69b 100644
--- a/net/core/dev.c
+++ b/net/core/dev.c
@@ -3769,6 +3769,22 @@ static netdev_features_t dflt_features_check(struct sk_buff *skb,
return vlan_features_check(skb, features);
}
+static bool skb_gso_has_extension_hdr(const struct sk_buff *skb)
+{
+ if (!skb->encapsulation)
+ return ((skb_shinfo(skb)->gso_type & SKB_GSO_TCPV6 ||
+ (skb_shinfo(skb)->gso_type & SKB_GSO_UDP_L4 &&
+ vlan_get_protocol(skb) == htons(ETH_P_IPV6))) &&
+ skb_transport_header_was_set(skb) &&
+ skb_network_header_len(skb) != sizeof(struct ipv6hdr));
+ else
+ return (!skb_inner_network_header_was_set(skb) ||
+ ((skb_shinfo(skb)->gso_type & SKB_GSO_TCPV6 ||
+ (skb_shinfo(skb)->gso_type & SKB_GSO_UDP_L4 &&
+ inner_ip_hdr(skb)->version == 6)) &&
+ skb_inner_network_header_len(skb) != sizeof(struct ipv6hdr)));
+}
+
static netdev_features_t gso_features_check(const struct sk_buff *skb,
struct net_device *dev,
netdev_features_t features)
@@ -3805,10 +3821,15 @@ static netdev_features_t gso_features_check(const struct sk_buff *skb,
* segmentation-offloads.rst).
*/
if (skb_shinfo(skb)->gso_type & SKB_GSO_TCPV4) {
- struct iphdr *iph = skb->encapsulation ?
- inner_ip_hdr(skb) : ip_hdr(skb);
+ const struct iphdr *iph;
+ struct iphdr _iph;
+ int nhoff = skb->encapsulation ?
+ skb_inner_network_offset(skb) :
+ skb_network_offset(skb);
+
+ iph = skb_header_pointer(skb, nhoff, sizeof(_iph), &_iph);
- if (!(iph->frag_off & htons(IP_DF)))
+ if (!iph || !(iph->frag_off & htons(IP_DF)))
features &= ~dev->mangleid_features;
}
@@ -3816,11 +3837,7 @@ static netdev_features_t gso_features_check(const struct sk_buff *skb,
* so neither does TSO that depends on it.
*/
if (features & NETIF_F_IPV6_CSUM &&
- (skb_shinfo(skb)->gso_type & SKB_GSO_TCPV6 ||
- (skb_shinfo(skb)->gso_type & SKB_GSO_UDP_L4 &&
- vlan_get_protocol(skb) == htons(ETH_P_IPV6))) &&
- skb_transport_header_was_set(skb) &&
- skb_network_header_len(skb) != sizeof(struct ipv6hdr))
+ skb_gso_has_extension_hdr(skb))
features &= ~(NETIF_F_IPV6_CSUM | NETIF_F_TSO6 | NETIF_F_GSO_UDP_L4);
return features;
diff --git a/net/core/rtnetlink.c b/net/core/rtnetlink.c
index dad4b1054955..fae8034efbff 100644
--- a/net/core/rtnetlink.c
+++ b/net/core/rtnetlink.c
@@ -629,6 +629,9 @@ int rtnl_link_register(struct rtnl_link_ops *ops)
unlock:
mutex_unlock(&link_ops_mutex);
+ if (err)
+ cleanup_srcu_struct(&ops->srcu);
+
return err;
}
EXPORT_SYMBOL_GPL(rtnl_link_register);
@@ -707,11 +710,14 @@ static size_t rtnl_link_get_slave_info_data_size(const struct net_device *dev)
goto out;
ops = master_dev->rtnl_link_ops;
- if (!ops || !ops->get_slave_size)
+ if (!ops)
+ goto out;
+ size += nla_total_size(strlen(ops->kind) + 1); /* IFLA_INFO_SLAVE_KIND */
+ if (!ops->get_slave_size)
goto out;
/* IFLA_INFO_SLAVE_DATA + nested data */
- size = nla_total_size(sizeof(struct nlattr)) +
- ops->get_slave_size(master_dev, dev);
+ size += nla_total_size(sizeof(struct nlattr)) +
+ ops->get_slave_size(master_dev, dev);
out:
rcu_read_unlock();
@@ -1267,6 +1273,21 @@ static size_t rtnl_dpll_pin_size(const struct net_device *dev)
return size;
}
+static size_t rtnl_dev_parent_size(const struct net_device *dev)
+{
+ size_t size = 0;
+
+ /* IFLA_PARENT_DEV_NAME */
+ if (dev->dev.parent)
+ size += nla_total_size(strlen(dev_name(dev->dev.parent)) + 1);
+
+ /* IFLA_PARENT_DEV_BUS_NAME */
+ if (dev->dev.parent && dev->dev.parent->bus)
+ size += nla_total_size(strlen(dev->dev.parent->bus->name) + 1);
+
+ return size;
+}
+
static noinline size_t if_nlmsg_size(const struct net_device *dev,
u32 ext_filter_mask)
{
@@ -1328,6 +1349,7 @@ static noinline size_t if_nlmsg_size(const struct net_device *dev,
+ nla_total_size(8) /* IFLA_MAX_PACING_OFFLOAD_HORIZON */
+ nla_total_size(2) /* IFLA_HEADROOM */
+ nla_total_size(2) /* IFLA_TAILROOM */
+ + rtnl_dev_parent_size(dev)
+ 0;
if (!(ext_filter_mask & RTEXT_FILTER_SKIP_STATS))
diff --git a/net/core/skmsg.c b/net/core/skmsg.c
index 3261793abe83..6187a83bd741 100644
--- a/net/core/skmsg.c
+++ b/net/core/skmsg.c
@@ -1267,17 +1267,20 @@ out:
static void sk_psock_verdict_data_ready(struct sock *sk)
{
- struct socket *sock = sk->sk_socket;
- const struct proto_ops *ops;
+ const struct proto_ops *ops = NULL;
+ struct socket *sock;
int copied;
trace_sk_data_ready(sk);
- if (unlikely(!sock))
- return;
- ops = READ_ONCE(sock->ops);
+ rcu_read_lock();
+ sock = READ_ONCE(sk->sk_socket);
+ if (likely(sock))
+ ops = READ_ONCE(sock->ops);
+ rcu_read_unlock();
if (!ops || !ops->read_skb)
return;
+
copied = ops->read_skb(sk, sk_psock_verdict_recv);
if (copied >= 0) {
struct sk_psock *psock;