diff --git a/drivers/net/veth.c b/drivers/net/veth.c
index 82c900d7ba7b..39bfa024861c 100644
--- a/drivers/net/veth.c
+++ b/drivers/net/veth.c
@@ -310,9 +310,10 @@ static bool veth_skb_is_eligible_for_gro(const struct net_device *dev,
 					 const struct net_device *rcv,
 					 const struct sk_buff *skb)
 {
-	return !(dev->features & NETIF_F_ALL_TSO) ||
+	return !netdev_feature_test_bits(NETIF_F_ALL_TSO, dev->features) ||
 		(skb->destructor == sock_wfree &&
-		 rcv->features & (NETIF_F_GRO_FRAGLIST | NETIF_F_GRO_UDP_FWD));
+		 netdev_feature_test_bits(NETIF_F_GRO_FRAGLIST |
+					  NETIF_F_GRO_UDP_FWD, rcv->features));
 }
 
 static netdev_tx_t veth_xmit(struct sk_buff *skb, struct net_device *dev)
@@ -993,7 +994,7 @@ static void veth_napi_del(struct net_device *dev)
 
 static bool veth_gro_requested(const struct net_device *dev)
 {
-	return !!(dev->wanted_features & NETIF_F_GRO);
+	return netdev_feature_test_bit(NETIF_F_GRO_BIT, dev->wanted_features);
 }
 
 static int veth_enable_xdp_range(struct net_device *dev, int start, int end,
@@ -1075,7 +1076,8 @@ static int veth_enable_xdp(struct net_device *dev)
 				/* user-space did not require GRO, but adding XDP
 				 * is supposed to get GRO working
 				 */
-				dev->features |= NETIF_F_GRO;
+				netdev_feature_set_bit(NETIF_F_GRO_BIT,
+						       &dev->features);
 				netdev_features_change(dev);
 			}
 		}
@@ -1104,7 +1106,8 @@ static void veth_disable_xdp(struct net_device *dev)
 		 * enabled it, clear it now
 		 */
 		if (!veth_gro_requested(dev) && netif_running(dev)) {
-			dev->features &= ~NETIF_F_GRO;
+			netdev_feature_clear_bit(NETIF_F_GRO_BIT,
+						 &dev->features);
 			netdev_features_change(dev);
 		}
 	}
@@ -1393,23 +1396,27 @@ static void veth_fix_features(struct net_device *dev,
 		struct veth_priv *peer_priv = netdev_priv(peer);
 
 		if (peer_priv->_xdp_prog)
-			*features &= ~NETIF_F_GSO_SOFTWARE;
+			netdev_feature_clear_bits(NETIF_F_GSO_SOFTWARE,
+						  features);
 	}
 	if (priv->_xdp_prog)
-		*features |= NETIF_F_GRO;
+		netdev_feature_set_bit(NETIF_F_GRO_BIT, features);
 }
 
 static int veth_set_features(struct net_device *dev,
 			     netdev_features_t features)
 {
-	netdev_features_t changed = features ^ dev->features;
 	struct veth_priv *priv = netdev_priv(dev);
+	netdev_features_t changed;
 	int err;
 
-	if (!(changed & NETIF_F_GRO) || !(dev->flags & IFF_UP) || priv->_xdp_prog)
+	netdev_feature_xor(&changed, features, dev->features);
+
+	if (!netdev_feature_test_bit(NETIF_F_GRO_BIT, changed) ||
+	    !(dev->flags & IFF_UP) || priv->_xdp_prog)
 		return 0;
 
-	if (features & NETIF_F_GRO) {
+	if (netdev_feature_test_bit(NETIF_F_GRO_BIT, features)) {
 		err = veth_napi_enable(dev);
 		if (err)
 			return err;
@@ -1486,7 +1493,8 @@ static int veth_xdp_set(struct net_device *dev, struct bpf_prog *prog,
 		}
 
 		if (!old_prog) {
-			peer->hw_features &= ~NETIF_F_GSO_SOFTWARE;
+			netdev_feature_clear_bits(NETIF_F_GSO_SOFTWARE,
+						  &peer->hw_features);
 			peer->max_mtu = max_mtu;
 		}
 	}
@@ -1497,7 +1505,8 @@ static int veth_xdp_set(struct net_device *dev, struct bpf_prog *prog,
 				veth_disable_xdp(dev);
 
 			if (peer) {
-				peer->hw_features |= NETIF_F_GSO_SOFTWARE;
+				netdev_feature_set_bits(NETIF_F_GSO_SOFTWARE,
+							&peer->hw_features);
 				peer->max_mtu = ETH_MAX_MTU;
 			}
 		}
@@ -1562,20 +1571,24 @@ static void veth_setup(struct net_device *dev)
 
 	dev->netdev_ops = &veth_netdev_ops;
 	dev->ethtool_ops = &veth_ethtool_ops;
-	dev->features |= NETIF_F_LLTX;
-	dev->features |= VETH_FEATURES;
-	dev->vlan_features = dev->features &
-			     ~(NETIF_F_HW_VLAN_CTAG_TX |
-			       NETIF_F_HW_VLAN_STAG_TX |
-			       NETIF_F_HW_VLAN_CTAG_RX |
-			       NETIF_F_HW_VLAN_STAG_RX);
+	netdev_feature_set_bit(NETIF_F_LLTX_BIT, &dev->features);
+	netdev_feature_set_bits(VETH_FEATURES, &dev->features);
+	netdev_feature_copy(&dev->vlan_features, dev->features);
+	netdev_feature_clear_bits(NETIF_F_HW_VLAN_CTAG_TX |
+				  NETIF_F_HW_VLAN_STAG_TX |
+				  NETIF_F_HW_VLAN_CTAG_RX |
+				  NETIF_F_HW_VLAN_STAG_RX,
+				  &dev->vlan_features);
 	dev->needs_free_netdev = true;
 	dev->priv_destructor = veth_dev_free;
 	dev->max_mtu = ETH_MAX_MTU;
 
-	dev->hw_features = VETH_FEATURES;
-	dev->hw_enc_features = VETH_FEATURES;
-	dev->mpls_features = NETIF_F_HW_CSUM | NETIF_F_GSO_SOFTWARE;
+	netdev_feature_zero(&dev->hw_features);
+	netdev_feature_set_bits(VETH_FEATURES, &dev->hw_features);
+	netdev_feature_copy(&dev->hw_enc_features, dev->hw_features);
+	netdev_feature_zero(&dev->mpls_features);
+	netdev_feature_set_bits(NETIF_F_HW_CSUM | NETIF_F_GSO_SOFTWARE,
+				&dev->mpls_features);
 }
 
 /*
@@ -1602,8 +1615,8 @@ static struct rtnl_link_ops veth_link_ops;
 
 static void veth_disable_gro(struct net_device *dev)
 {
-	dev->features &= ~NETIF_F_GRO;
-	dev->wanted_features &= ~NETIF_F_GRO;
+	netdev_feature_clear_bit(NETIF_F_GRO_BIT, &dev->features);
+	netdev_feature_clear_bit(NETIF_F_GRO_BIT, &dev->wanted_features);
 	netdev_update_features(dev);
 }
 
