All of lore.kernel.org
 help / color / mirror / Atom feed
From: Hauke Mehrtens <hauke@hauke-m.de>
To: johannes@sipsolutions.net
Cc: backports@vger.kernel.org, Hauke Mehrtens <hauke@hauke-m.de>
Subject: [PATCH 05/21] header: backport mii_ethtool_{get,set}_link_ksettings()
Date: Tue, 22 Aug 2017 00:28:01 +0200	[thread overview]
Message-ID: <20170821222817.17376-6-hauke@hauke-m.de> (raw)
In-Reply-To: <20170821222817.17376-1-hauke@hauke-m.de>

This function was added in kernel 4.10 and is needed by the usbnet
drivers.

These functions were added in upstream commit: bc8ee596afe8f3 ("net:
mii: add generic function to support ksetting support")

Signed-off-by: Hauke Mehrtens <hauke@hauke-m.de>
---
 backport/backport-include/linux/mii.h |   7 ++
 backport/compat/Makefile              |   1 +
 backport/compat/backport-4.10.c       | 223 ++++++++++++++++++++++++++++++++++
 dependencies                          |   4 +
 4 files changed, 235 insertions(+)
 create mode 100644 backport/compat/backport-4.10.c

diff --git a/backport/backport-include/linux/mii.h b/backport/backport-include/linux/mii.h
index 5b0ecf97..e5aad0f6 100644
--- a/backport/backport-include/linux/mii.h
+++ b/backport/backport-include/linux/mii.h
@@ -144,4 +144,11 @@ static inline u32 mii_lpa_to_ethtool_lpa_x(u32 lpa)
 }
 #endif
 
+#if LINUX_VERSION_IN_RANGE(4,6,0, 4,11,0)
+extern int mii_ethtool_get_link_ksettings(
+	struct mii_if_info *mii, struct ethtool_link_ksettings *cmd);
+extern int mii_ethtool_set_link_ksettings(
+	struct mii_if_info *mii, const struct ethtool_link_ksettings *cmd);
+#endif /* LINUX_VERSION_IN_RANGE(4,6,0, 4,11,0) */
+
 #endif /* __BACKPORT_LINUX_MII_H */
diff --git a/backport/compat/Makefile b/backport/compat/Makefile
index 95d1bd2f..1078357f 100644
--- a/backport/compat/Makefile
+++ b/backport/compat/Makefile
@@ -35,6 +35,7 @@ compat-$(CPTCFG_KERNEL_4_5) += backport-4.5.o
 compat-$(CPTCFG_KERNEL_4_6) += backport-4.6.o
 compat-$(CPTCFG_KERNEL_4_7) += backport-4.7.o
 compat-$(CPTCFG_KERNEL_4_8) += backport-4.8.o
+compat-$(CPTCFG_KERNEL_4_10) += backport-4.10.o
 
 compat-$(CPTCFG_BPAUTO_BUILD_CRYPTO_CCM) += crypto-ccm.o
 compat-$(CPTCFG_BPAUTO_CRYPTO_SKCIPHER) += crypto-skcipher.o
diff --git a/backport/compat/backport-4.10.c b/backport/compat/backport-4.10.c
new file mode 100644
index 00000000..b4d7edea
--- /dev/null
+++ b/backport/compat/backport-4.10.c
@@ -0,0 +1,223 @@
+/*
+ * Copyright(c) 2017 Hauke Mehrtens <hauke@hauke-m.de>
+ *
+ * Backport functionality introduced in Linux 4.10.
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation.
+ */
+#include <linux/kernel.h>
+#include <linux/module.h>
+#include <linux/netdevice.h>
+#include <linux/ethtool.h>
+#include <linux/mii.h>
+
+#if LINUX_VERSION_IS_GEQ(4,6,0)
+static u32 mii_get_an(struct mii_if_info *mii, u16 addr)
+{
+	int advert;
+
+	advert = mii->mdio_read(mii->dev, mii->phy_id, addr);
+
+	return mii_lpa_to_ethtool_lpa_t(advert);
+}
+
+/**
+ * mii_ethtool_set_link_ksettings - set settings that are specified in @cmd
+ * @mii: MII interfaces
+ * @cmd: requested ethtool_link_ksettings
+ *
+ * Returns 0 for success, negative on error.
+ */
+int mii_ethtool_set_link_ksettings(struct mii_if_info *mii,
+				   const struct ethtool_link_ksettings *cmd)
+{
+	struct net_device *dev = mii->dev;
+	u32 speed = cmd->base.speed;
+
+	if (speed != SPEED_10 &&
+	    speed != SPEED_100 &&
+	    speed != SPEED_1000)
+		return -EINVAL;
+	if (cmd->base.duplex != DUPLEX_HALF && cmd->base.duplex != DUPLEX_FULL)
+		return -EINVAL;
+	if (cmd->base.port != PORT_MII)
+		return -EINVAL;
+	if (cmd->base.phy_address != mii->phy_id)
+		return -EINVAL;
+	if (cmd->base.autoneg != AUTONEG_DISABLE &&
+	    cmd->base.autoneg != AUTONEG_ENABLE)
+		return -EINVAL;
+	if ((speed == SPEED_1000) && (!mii->supports_gmii))
+		return -EINVAL;
+
+	/* ignore supported, maxtxpkt, maxrxpkt */
+
+	if (cmd->base.autoneg == AUTONEG_ENABLE) {
+		u32 bmcr, advert, tmp;
+		u32 advert2 = 0, tmp2 = 0;
+		u32 advertising;
+
+		ethtool_convert_link_mode_to_legacy_u32(
+			&advertising, cmd->link_modes.advertising);
+
+		if ((advertising & (ADVERTISED_10baseT_Half |
+				    ADVERTISED_10baseT_Full |
+				    ADVERTISED_100baseT_Half |
+				    ADVERTISED_100baseT_Full |
+				    ADVERTISED_1000baseT_Half |
+				    ADVERTISED_1000baseT_Full)) == 0)
+			return -EINVAL;
+
+		/* advertise only what has been requested */
+		advert = mii->mdio_read(dev, mii->phy_id, MII_ADVERTISE);
+		tmp = advert & ~(ADVERTISE_ALL | ADVERTISE_100BASE4);
+		if (mii->supports_gmii) {
+			advert2 = mii->mdio_read(dev, mii->phy_id,
+						 MII_CTRL1000);
+			tmp2 = advert2 &
+				~(ADVERTISE_1000HALF | ADVERTISE_1000FULL);
+		}
+		tmp |= ethtool_adv_to_mii_adv_t(advertising);
+
+		if (mii->supports_gmii)
+			tmp2 |= ethtool_adv_to_mii_ctrl1000_t(advertising);
+		if (advert != tmp) {
+			mii->mdio_write(dev, mii->phy_id, MII_ADVERTISE, tmp);
+			mii->advertising = tmp;
+		}
+		if ((mii->supports_gmii) && (advert2 != tmp2))
+			mii->mdio_write(dev, mii->phy_id, MII_CTRL1000, tmp2);
+
+		/* turn on autonegotiation, and force a renegotiate */
+		bmcr = mii->mdio_read(dev, mii->phy_id, MII_BMCR);
+		bmcr |= (BMCR_ANENABLE | BMCR_ANRESTART);
+		mii->mdio_write(dev, mii->phy_id, MII_BMCR, bmcr);
+
+		mii->force_media = 0;
+	} else {
+		u32 bmcr, tmp;
+
+		/* turn off auto negotiation, set speed and duplexity */
+		bmcr = mii->mdio_read(dev, mii->phy_id, MII_BMCR);
+		tmp = bmcr & ~(BMCR_ANENABLE | BMCR_SPEED100 |
+			       BMCR_SPEED1000 | BMCR_FULLDPLX);
+		if (speed == SPEED_1000)
+			tmp |= BMCR_SPEED1000;
+		else if (speed == SPEED_100)
+			tmp |= BMCR_SPEED100;
+		if (cmd->base.duplex == DUPLEX_FULL) {
+			tmp |= BMCR_FULLDPLX;
+			mii->full_duplex = 1;
+		} else {
+			mii->full_duplex = 0;
+		}
+		if (bmcr != tmp)
+			mii->mdio_write(dev, mii->phy_id, MII_BMCR, tmp);
+
+		mii->force_media = 1;
+	}
+	return 0;
+}
+EXPORT_SYMBOL(mii_ethtool_set_link_ksettings);
+
+
+/**
+ * mii_ethtool_get_link_ksettings - get settings that are specified in @cmd
+ * @mii: MII interface
+ * @cmd: requested ethtool_link_ksettings
+ *
+ * The @cmd parameter is expected to have been cleared before calling
+ * mii_ethtool_get_link_ksettings().
+ *
+ * Returns 0 for success, negative on error.
+ */
+int mii_ethtool_get_link_ksettings(struct mii_if_info *mii,
+				   struct ethtool_link_ksettings *cmd)
+{
+	struct net_device *dev = mii->dev;
+	u16 bmcr, bmsr, ctrl1000 = 0, stat1000 = 0;
+	u32 nego, supported, advertising, lp_advertising;
+
+	supported = (SUPPORTED_10baseT_Half | SUPPORTED_10baseT_Full |
+		     SUPPORTED_100baseT_Half | SUPPORTED_100baseT_Full |
+		     SUPPORTED_Autoneg | SUPPORTED_TP | SUPPORTED_MII);
+	if (mii->supports_gmii)
+		supported |= SUPPORTED_1000baseT_Half |
+			SUPPORTED_1000baseT_Full;
+
+	/* only supports twisted-pair */
+	cmd->base.port = PORT_MII;
+
+	/* this isn't fully supported at higher layers */
+	cmd->base.phy_address = mii->phy_id;
+	cmd->base.mdio_support = ETH_MDIO_SUPPORTS_C22;
+
+	advertising = ADVERTISED_TP | ADVERTISED_MII;
+
+	bmcr = mii->mdio_read(dev, mii->phy_id, MII_BMCR);
+	bmsr = mii->mdio_read(dev, mii->phy_id, MII_BMSR);
+	if (mii->supports_gmii) {
+		ctrl1000 = mii->mdio_read(dev, mii->phy_id, MII_CTRL1000);
+		stat1000 = mii->mdio_read(dev, mii->phy_id, MII_STAT1000);
+	}
+	if (bmcr & BMCR_ANENABLE) {
+		advertising |= ADVERTISED_Autoneg;
+		cmd->base.autoneg = AUTONEG_ENABLE;
+
+		advertising |= mii_get_an(mii, MII_ADVERTISE);
+		if (mii->supports_gmii)
+			advertising |= mii_ctrl1000_to_ethtool_adv_t(ctrl1000);
+
+		if (bmsr & BMSR_ANEGCOMPLETE) {
+			lp_advertising = mii_get_an(mii, MII_LPA);
+			lp_advertising |=
+					mii_stat1000_to_ethtool_lpa_t(stat1000);
+		} else {
+			lp_advertising = 0;
+		}
+
+		nego = advertising & lp_advertising;
+
+		if (nego & (ADVERTISED_1000baseT_Full |
+			    ADVERTISED_1000baseT_Half)) {
+			cmd->base.speed = SPEED_1000;
+			cmd->base.duplex = !!(nego & ADVERTISED_1000baseT_Full);
+		} else if (nego & (ADVERTISED_100baseT_Full |
+				   ADVERTISED_100baseT_Half)) {
+			cmd->base.speed = SPEED_100;
+			cmd->base.duplex = !!(nego & ADVERTISED_100baseT_Full);
+		} else {
+			cmd->base.speed = SPEED_10;
+			cmd->base.duplex = !!(nego & ADVERTISED_10baseT_Full);
+		}
+	} else {
+		cmd->base.autoneg = AUTONEG_DISABLE;
+
+		cmd->base.speed = ((bmcr & BMCR_SPEED1000 &&
+				    (bmcr & BMCR_SPEED100) == 0) ?
+				   SPEED_1000 :
+				   ((bmcr & BMCR_SPEED100) ?
+				    SPEED_100 : SPEED_10));
+		cmd->base.duplex = (bmcr & BMCR_FULLDPLX) ?
+			DUPLEX_FULL : DUPLEX_HALF;
+
+		lp_advertising = 0;
+	}
+
+	mii->full_duplex = cmd->base.duplex;
+
+	ethtool_convert_legacy_u32_to_link_mode(cmd->link_modes.supported,
+						supported);
+	ethtool_convert_legacy_u32_to_link_mode(cmd->link_modes.advertising,
+						advertising);
+	ethtool_convert_legacy_u32_to_link_mode(cmd->link_modes.lp_advertising,
+						lp_advertising);
+
+	/* ignore maxtxpkt, maxrxpkt for now */
+
+	return 0;
+}
+EXPORT_SYMBOL(mii_ethtool_get_link_ksettings);
+#endif /* LINUX_VERSION_IS_GEQ(4,6,0) */
diff --git a/dependencies b/dependencies
index 43afe487..f97e12ad 100644
--- a/dependencies
+++ b/dependencies
@@ -153,3 +153,7 @@ LIBERTAS 4.3
 
 # some prototypes changed - might be fixable but I'm lazy
 NFC_WILINK 4.8
+
+# struct ethtool_link_ksettings is missing, I'm lazy
+USB_USBNET 4.6
+USB_NET_RNDIS_WLAN 4.6
-- 
2.11.0

--
To unsubscribe from this list: send the line "unsubscribe backports" in

  parent reply	other threads:[~2017-08-21 22:28 UTC|newest]

Thread overview: 48+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2017-08-21 22:27 [PATCH 00/21] backports: multiple changes for kernel 3.13-rc6 Hauke Mehrtens
2017-08-21 22:27 ` [PATCH 01/21] copy: do not copy files removed in kernel 4.13 Hauke Mehrtens
2017-09-06 14:56   ` Johannes Berg
2017-08-21 22:27 ` [PATCH 02/21] patches: header fix for st-nci not needed any more Hauke Mehrtens
2017-08-21 22:27 ` [PATCH 03/21] header: skbuff: add skb_put_zero(), skb_put_data() and skb_put_u8() Hauke Mehrtens
2017-08-21 22:28 ` [PATCH 04/21] header: skbuff: fix signature of skb_put(), skb_push() and () Hauke Mehrtens
2017-08-21 22:28 ` Hauke Mehrtens [this message]
2017-08-21 22:28 ` [PATCH 06/21] patches: adapt the stat64 usage for usbnet Hauke Mehrtens
2017-08-21 22:28 ` [PATCH 07/21] header: add module_param_hw_array() Hauke Mehrtens
2017-09-06 15:00   ` Johannes Berg
2017-08-21 22:28 ` [PATCH 08/21] header: backport devm_acpi_dev_add_driver_gpios() Hauke Mehrtens
2017-09-06 15:01   ` Johannes Berg
2017-09-06 21:58     ` Hauke Mehrtens
2017-09-08  9:25       ` Johannes Berg
2017-09-08  9:28         ` Johannes Berg
2017-08-21 22:28 ` [PATCH 09/21] header: add get_random_u32() Hauke Mehrtens
2017-08-21 22:28 ` [PATCH 10/21] header: rename wait_queue_entry_t to wait_queue_t Hauke Mehrtens
2017-08-21 22:28 ` [PATCH 11/21] backport: add __print_array() Hauke Mehrtens
2017-08-21 22:28 ` [PATCH 12/21] compat: avoid usage of kvzalloc() in rhashtable.c Hauke Mehrtens
2017-09-06 15:05   ` Johannes Berg
2017-09-06 22:12     ` Hauke Mehrtens
2017-09-08  9:25       ` Johannes Berg
2017-08-21 22:28 ` [PATCH 13/21] patch: Allow usage of pci_error_handlers->reset_notify Hauke Mehrtens
2017-08-21 22:28 ` [PATCH 14/21] header: add offsetofend() Hauke Mehrtens
2017-08-21 22:28 ` [PATCH 15/21] dependencies: add deps for struct acpi_gpio_mapping Hauke Mehrtens
2017-08-21 22:28 ` [PATCH 16/21] patches: brcmfmac: fix netdev destructor Hauke Mehrtens
2017-09-06 15:05   ` Johannes Berg
2017-09-07  7:48     ` Arend van Spriel
2017-09-07  9:04       ` compilation errors in ath10k driver with latest backports git KAVITA MATHUR
2017-09-07  9:17         ` Arend van Spriel
2017-09-13 19:36   ` [PATCH 16/21] patches: brcmfmac: fix netdev destructor Arend van Spriel
2017-09-14  7:21     ` Johannes Berg
2017-09-17 22:00       ` Hauke Mehrtens
2017-09-18  7:16         ` Arend van Spriel
2017-08-21 22:28 ` [PATCH 17/21] patches: backport the probe_new for i2c drivers Hauke Mehrtens
2017-08-21 22:28 ` [PATCH 18/21] patches: adapt signature of proto_ops->accept Hauke Mehrtens
2017-08-21 22:28 ` [PATCH 19/21] header: add linux/refcount.h Hauke Mehrtens
2017-08-21 22:28 ` [PATCH 20/21] header: add dma_wmb() Hauke Mehrtens
2017-08-21 22:28 ` [PATCH 21/21] copy-list: add quantenna qtnfmac driver Hauke Mehrtens
2017-09-06 15:10   ` Johannes Berg
2017-09-06 15:13     ` Johannes Berg
2017-09-06 22:14       ` Hauke Mehrtens
2017-09-06 15:14     ` Johannes Berg
2017-09-05  9:00 ` [PATCH 00/21] backports: multiple changes for kernel 3.13-rc6 Johannes Berg
2017-09-05 21:41   ` Hauke Mehrtens
2017-09-06  7:23     ` Johannes Berg
2017-09-13 20:00   ` Arend van Spriel
2017-09-17 22:07     ` Hauke Mehrtens

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20170821222817.17376-6-hauke@hauke-m.de \
    --to=hauke@hauke-m.de \
    --cc=backports@vger.kernel.org \
    --cc=johannes@sipsolutions.net \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.