Commit 7a3d3279 authored by Ian MacDonald's avatar Ian MacDonald Committed by Jakub Kicinski
Browse files

net: thunderbolt: Allow reading link settings



In order to use Thunderbolt networking as part of bonding device it
needs to support ->get_link_ksettings() ethtool operation, so that the
bonding driver can read the link speed and the related attributes. Add
support for this to the driver.

Signed-off-by: default avatarIan MacDonald <ian@netstatz.com>
Reviewed-by: default avatarAndrew Lunn <andrew@lunn.ch>
Signed-off-by: default avatarMika Westerberg <mika.westerberg@linux.intel.com>
Link: https://patch.msgid.link/20260115115646.328898-5-mika.westerberg@linux.intel.com


Signed-off-by: default avatarJakub Kicinski <kuba@kernel.org>
parent 2e62e556
Loading
Loading
Loading
Loading
+49 −0
Original line number Diff line number Diff line
@@ -10,6 +10,7 @@
 */

#include <linux/atomic.h>
#include <linux/ethtool.h>
#include <linux/highmem.h>
#include <linux/if_vlan.h>
#include <linux/jhash.h>
@@ -1265,6 +1266,53 @@ static const struct net_device_ops tbnet_netdev_ops = {
	.ndo_get_stats64 = tbnet_get_stats64,
};

static int tbnet_get_link_ksettings(struct net_device *dev,
				    struct ethtool_link_ksettings *cmd)
{
	const struct tbnet *net = netdev_priv(dev);
	const struct tb_xdomain *xd = net->xd;
	int speed;

	ethtool_link_ksettings_zero_link_mode(cmd, supported);
	ethtool_link_ksettings_zero_link_mode(cmd, advertising);

	/* Figure out the current link speed and width */
	switch (xd->link_speed) {
	case 40:
		speed = SPEED_80000;
		break;

	case 20:
		if (xd->link_width == 2)
			speed = SPEED_40000;
		else
			speed = SPEED_20000;
		break;

	case 10:
		if (xd->link_width == 2) {
			speed = SPEED_20000;
			break;
		}
		fallthrough;

	default:
		speed = SPEED_10000;
		break;
	}

	cmd->base.speed = speed;
	cmd->base.duplex = DUPLEX_FULL;
	cmd->base.autoneg = AUTONEG_DISABLE;
	cmd->base.port = PORT_OTHER;

	return 0;
}

static const struct ethtool_ops tbnet_ethtool_ops = {
	.get_link_ksettings = tbnet_get_link_ksettings,
};

static void tbnet_generate_mac(struct net_device *dev)
{
	const struct tbnet *net = netdev_priv(dev);
@@ -1315,6 +1363,7 @@ static int tbnet_probe(struct tb_service *svc, const struct tb_service_id *id)

	strcpy(dev->name, "thunderbolt%d");
	dev->netdev_ops = &tbnet_netdev_ops;
	dev->ethtool_ops = &tbnet_ethtool_ops;

	/* ThunderboltIP takes advantage of TSO packets but instead of
	 * segmenting them we just split the packet into Thunderbolt