Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit d2afb5bd authored by Giuseppe CAVALLARO's avatar Giuseppe CAVALLARO Committed by David S. Miller
Browse files

stmmac: fix the rx csum feature



For new GMACs it is possible to turn-on/off the COE.
In the current driver, when disabled the Rx-checksum
via ethtool, the tool reported that csum was disabled
but the HW continued to set the IPC. Indeed this is
because the fix_features allows this. So the patch
fixes this problem by adding the set_features.

Signed-off-by: default avatarGiuseppe Cavallaro <peppe.cavallaro@st.com>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent 8a3cf39b
Loading
Loading
Loading
Loading
+1 −0
Original line number Diff line number Diff line
@@ -445,6 +445,7 @@ struct mac_device_info {
	int multicast_filter_bins;
	int unicast_filter_entries;
	int mcast_bits_log2;
	unsigned int rx_csum;
};

struct mac_device_info *dwmac1000_setup(void __iomem *ioaddr, int mcbins,
+5 −1
Original line number Diff line number Diff line
@@ -58,7 +58,11 @@ static int dwmac1000_rx_ipc_enable(struct mac_device_info *hw)
	void __iomem *ioaddr = hw->pcsr;
	u32 value = readl(ioaddr + GMAC_CONTROL);

	if (hw->rx_csum)
		value |= GMAC_CONTROL_IPC;
	else
		value &= ~GMAC_CONTROL_IPC;

	writel(value, ioaddr + GMAC_CONTROL);

	value = readl(ioaddr + GMAC_CONTROL);
+25 −2
Original line number Diff line number Diff line
@@ -1673,6 +1673,7 @@ static int stmmac_hw_setup(struct net_device *dev)
	if (!ret) {
		pr_warn(" RX IPC Checksum Offload disabled\n");
		priv->plat->rx_coe = STMMAC_RX_COE_NONE;
		priv->hw->rx_csum = 0;
	}

	/* Enable the MAC Rx/Tx */
@@ -2111,7 +2112,7 @@ static int stmmac_rx(struct stmmac_priv *priv, int limit)
	unsigned int entry = priv->cur_rx % rxsize;
	unsigned int next_entry;
	unsigned int count = 0;
	int coe = priv->plat->rx_coe;
	int coe = priv->hw->rx_csum;

	if (netif_msg_rx_status(priv)) {
		pr_debug("%s: descriptor ring:\n", __func__);
@@ -2334,6 +2335,7 @@ static netdev_features_t stmmac_fix_features(struct net_device *dev,
		features &= ~NETIF_F_RXCSUM;
	else if (priv->plat->rx_coe == STMMAC_RX_COE_TYPE1)
		features &= ~NETIF_F_IPV6_CSUM;

	if (!priv->plat->tx_coe)
		features &= ~NETIF_F_ALL_CSUM;

@@ -2348,6 +2350,24 @@ static netdev_features_t stmmac_fix_features(struct net_device *dev,
	return features;
}

static int stmmac_set_features(struct net_device *netdev,
			       netdev_features_t features)
{
	struct stmmac_priv *priv = netdev_priv(netdev);

	/* Keep the COE Type in case of csum is supporting */
	if (features & NETIF_F_RXCSUM)
		priv->hw->rx_csum = priv->plat->rx_coe;
	else
		priv->hw->rx_csum = 0;
	/* No check needed because rx_coe has been set before and it will be
	 * fixed in case of issue.
	 */
	priv->hw->mac->rx_ipc(priv->hw);

	return 0;
}

/**
 *  stmmac_interrupt - main ISR
 *  @irq: interrupt number.
@@ -2628,6 +2648,7 @@ static const struct net_device_ops stmmac_netdev_ops = {
	.ndo_stop = stmmac_release,
	.ndo_change_mtu = stmmac_change_mtu,
	.ndo_fix_features = stmmac_fix_features,
	.ndo_set_features = stmmac_set_features,
	.ndo_set_rx_mode = stmmac_set_rx_mode,
	.ndo_tx_timeout = stmmac_tx_timeout,
	.ndo_do_ioctl = stmmac_ioctl,
@@ -2704,9 +2725,11 @@ static int stmmac_hw_init(struct stmmac_priv *priv)
	/* To use alternate (extended) or normal descriptor structures */
	stmmac_selec_desc_mode(priv);

	if (priv->plat->rx_coe)
	if (priv->plat->rx_coe) {
		priv->hw->rx_csum = priv->plat->rx_coe;
		pr_info(" RX Checksum Offload Engine supported (type %d)\n",
			priv->plat->rx_coe);
	}
	if (priv->plat->tx_coe)
		pr_info(" TX Checksum insertion supported\n");