Commit 8c6fc097 authored by Jose Abreu's avatar Jose Abreu Committed by David S. Miller
Browse files

net: stmmac: gmac4+: Add Split Header support



GMAC4+ cores also support the Split Header feature.

Add the support for Split Header feature in the RX path following the
same implementation logic that XGMAC followed.

Signed-off-by: default avatarJose Abreu <Jose.Abreu@synopsys.com>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent a24cae70
Loading
Loading
Loading
Loading
+7 −0
Original line number Diff line number Diff line
@@ -14,6 +14,7 @@

/*  MAC registers */
#define GMAC_CONFIG			0x00000000
#define GMAC_EXT_CONFIG			0x00000004
#define GMAC_PACKET_FILTER		0x00000008
#define GMAC_HASH_TAB(x)		(0x10 + (x) * 4)
#define GMAC_VLAN_TAG			0x00000050
@@ -188,6 +189,11 @@ enum power_event {
#define GMAC_CONFIG_TE			BIT(1)
#define GMAC_CONFIG_RE			BIT(0)

/* MAC extended config */
#define GMAC_CONFIG_HDSMS		GENMASK(22, 20)
#define GMAC_CONFIG_HDSMS_SHIFT		20
#define GMAC_CONFIG_HDSMS_256		(0x2 << GMAC_CONFIG_HDSMS_SHIFT)

/* MAC HW features0 bitmap */
#define GMAC_HW_FEAT_SAVLANINS		BIT(27)
#define GMAC_HW_FEAT_ADDMAC		BIT(18)
@@ -211,6 +217,7 @@ enum power_event {
#define GMAC_HW_HASH_TB_SZ		GENMASK(25, 24)
#define GMAC_HW_FEAT_AVSEL		BIT(20)
#define GMAC_HW_TSOEN			BIT(18)
#define GMAC_HW_FEAT_SPHEN		BIT(17)
#define GMAC_HW_ADDR64			GENMASK(15, 14)
#define GMAC_HW_TXFIFOSIZE		GENMASK(10, 6)
#define GMAC_HW_RXFIFOSIZE		GENMASK(4, 0)
+18 −3
Original line number Diff line number Diff line
@@ -83,9 +83,10 @@ static int dwmac4_wrback_get_rx_status(void *data, struct stmmac_extra_stats *x,
	if (unlikely(rdes3 & RDES3_OWN))
		return dma_own;

	/* Verify rx error by looking at the last segment. */
	if (likely(!(rdes3 & RDES3_LAST_DESCRIPTOR)))
	if (unlikely(rdes3 & RDES3_CONTEXT_DESCRIPTOR))
		return discard_frame;
	if (likely(!(rdes3 & RDES3_LAST_DESCRIPTOR)))
		return rx_not_ls;

	if (unlikely(rdes3 & RDES3_ERROR_SUMMARY)) {
		if (unlikely(rdes3 & RDES3_GIANT_PACKET))
@@ -188,7 +189,7 @@ static void dwmac4_set_tx_owner(struct dma_desc *p)

static void dwmac4_set_rx_owner(struct dma_desc *p, int disable_rx_ic)
{
	p->des3 = cpu_to_le32(RDES3_OWN | RDES3_BUFFER1_VALID_ADDR);
	p->des3 |= cpu_to_le32(RDES3_OWN | RDES3_BUFFER1_VALID_ADDR);

	if (!disable_rx_ic)
		p->des3 |= cpu_to_le32(RDES3_INT_ON_COMPLETION_EN);
@@ -492,6 +493,18 @@ static void dwmac4_set_vlan(struct dma_desc *p, u32 type)
	p->des2 |= cpu_to_le32(type & TDES2_VLAN_TAG_MASK);
}

static int dwmac4_get_rx_header_len(struct dma_desc *p, unsigned int *len)
{
	*len = le32_to_cpu(p->des2) & RDES2_HL;
	return 0;
}

static void dwmac4_set_sec_addr(struct dma_desc *p, dma_addr_t addr)
{
	p->des2 = cpu_to_le32(lower_32_bits(addr));
	p->des3 = cpu_to_le32(upper_32_bits(addr) | RDES3_BUFFER2_VALID_ADDR);
}

const struct stmmac_desc_ops dwmac4_desc_ops = {
	.tx_status = dwmac4_wrback_get_tx_status,
	.rx_status = dwmac4_wrback_get_rx_status,
@@ -519,6 +532,8 @@ const struct stmmac_desc_ops dwmac4_desc_ops = {
	.set_sarc = dwmac4_set_sarc,
	.set_vlan_tag = dwmac4_set_vlan_tag,
	.set_vlan = dwmac4_set_vlan,
	.get_rx_header_len = dwmac4_get_rx_header_len,
	.set_sec_addr = dwmac4_set_sec_addr,
};

const struct stmmac_mode_ops dwmac4_ring_mode_ops = {
+1 −0
Original line number Diff line number Diff line
@@ -109,6 +109,7 @@
#define RDES2_L4_FILTER_MATCH		BIT(28)
#define RDES2_L3_L4_FILT_NB_MATCH_MASK	GENMASK(27, 26)
#define RDES2_L3_L4_FILT_NB_MATCH_SHIFT	26
#define RDES2_HL			GENMASK(9, 0)

/* RDES3 (write back format) */
#define RDES3_PACKET_SIZE_MASK		GENMASK(14, 0)
+19 −0
Original line number Diff line number Diff line
@@ -368,6 +368,7 @@ static void dwmac4_get_hw_feature(void __iomem *ioaddr,
	dma_cap->hash_tb_sz = (hw_cap & GMAC_HW_HASH_TB_SZ) >> 24;
	dma_cap->av = (hw_cap & GMAC_HW_FEAT_AVSEL) >> 20;
	dma_cap->tsoen = (hw_cap & GMAC_HW_TSOEN) >> 18;
	dma_cap->sphen = (hw_cap & GMAC_HW_FEAT_SPHEN) >> 17;

	dma_cap->addr64 = (hw_cap & GMAC_HW_ADDR64) >> 14;
	switch (dma_cap->addr64) {
@@ -460,6 +461,22 @@ static void dwmac4_set_bfsize(void __iomem *ioaddr, int bfsize, u32 chan)
	writel(value, ioaddr + DMA_CHAN_RX_CONTROL(chan));
}

static void dwmac4_enable_sph(void __iomem *ioaddr, bool en, u32 chan)
{
	u32 value = readl(ioaddr + GMAC_EXT_CONFIG);

	value &= ~GMAC_CONFIG_HDSMS;
	value |= GMAC_CONFIG_HDSMS_256; /* Segment max 256 bytes */
	writel(value, ioaddr + GMAC_EXT_CONFIG);

	value = readl(ioaddr + DMA_CHAN_CONTROL(chan));
	if (en)
		value |= DMA_CONTROL_SPH;
	else
		value &= ~DMA_CONTROL_SPH;
	writel(value, ioaddr + DMA_CHAN_CONTROL(chan));
}

const struct stmmac_dma_ops dwmac4_dma_ops = {
	.reset = dwmac4_dma_reset,
	.init = dwmac4_dma_init,
@@ -486,6 +503,7 @@ const struct stmmac_dma_ops dwmac4_dma_ops = {
	.enable_tso = dwmac4_enable_tso,
	.qmode = dwmac4_qmode,
	.set_bfsize = dwmac4_set_bfsize,
	.enable_sph = dwmac4_enable_sph,
};

const struct stmmac_dma_ops dwmac410_dma_ops = {
@@ -514,4 +532,5 @@ const struct stmmac_dma_ops dwmac410_dma_ops = {
	.enable_tso = dwmac4_enable_tso,
	.qmode = dwmac4_qmode,
	.set_bfsize = dwmac4_set_bfsize,
	.enable_sph = dwmac4_enable_sph,
};
+1 −0
Original line number Diff line number Diff line
@@ -110,6 +110,7 @@
#define DMA_CHAN_STATUS(x)		(DMA_CHANX_BASE_ADDR(x) + 0x60)

/* DMA Control X */
#define DMA_CONTROL_SPH			BIT(24)
#define DMA_CONTROL_MSS_MASK		GENMASK(13, 0)

/* DMA Tx Channel X Control register defines */