[PATCH, RFC] mv643xx_eth: move sram window setting code into the driver

Lennert Buytenhek buytenh at wantstofly.org
Thu Sep 4 00:00:49 EST 2008


This gets rid of a big mv643xx_eth annoyance of mine where the driver
exports the offsets of some of its internal registers via a header
file, and the Pegasos platform code ioremaps the peripheral directly
and pokes into peripheral registers directly without involving the
driver at all.

I don't have the hardware, though, so I'd appreciate it if someone
with a Pegasos board could test this (and possibly try some followup
patches if it doesn't work).  (You might need to apply some of the
other mv643xx_eth patches that I just sent to netdev@ -- I'll happily
provide a rolled-up patch on request.)

Signed-off-by: Lennert Buytenhek <buytenh at marvell.com>
---
 arch/powerpc/platforms/chrp/pegasos_eth.c |   48 +++++++++++--------------
 drivers/net/mv643xx_eth.c                 |   56 +++++++++++++++++++++++------
 include/linux/mv643xx_eth.h               |   21 +++++++----
 3 files changed, 80 insertions(+), 45 deletions(-)

diff --git a/arch/powerpc/platforms/chrp/pegasos_eth.c b/arch/powerpc/platforms/chrp/pegasos_eth.c
index 130ff72..1adec8e 100644
--- a/arch/powerpc/platforms/chrp/pegasos_eth.c
+++ b/arch/powerpc/platforms/chrp/pegasos_eth.c
@@ -21,8 +21,8 @@
 #define PEGASOS2_SRAM_BASE 			(0xf2000000)
 #define PEGASOS2_SRAM_SIZE			(256*1024)
 
-#define PEGASOS2_SRAM_BASE_ETH0			(PEGASOS2_SRAM_BASE)
-#define PEGASOS2_SRAM_BASE_ETH1			(PEGASOS2_SRAM_BASE_ETH0 + (PEGASOS2_SRAM_SIZE / 2) )
+#define PEGASOS2_SRAM_OFF_ETH0			(0)
+#define PEGASOS2_SRAM_OFF_ETH1			(PEGASOS2_SRAM_SIZE / 2)
 
 
 #define PEGASOS2_SRAM_RXRING_SIZE		(PEGASOS2_SRAM_SIZE/4)
@@ -40,6 +40,14 @@ static struct resource mv643xx_eth_shared_resources[] = {
 	},
 };
 
+static struct mv643xx_eth_shared_platform_data mv643xx_eth_shared_pd = {
+	.sram_mbus_target_id	= 0x02,
+	.sram_mbus_target_attr	= 0x00,
+	.sram_mbus_addr		= PEGASOS2_SRAM_BASE,
+	.sram_size		= PEGASOS2_SRAM_SIZE,
+	.sram_cpu_phys_addr	= PEGASOS2_SRAM_BASE,
+};
+
 static struct platform_device mv643xx_eth_shared_device = {
 	.name		= MV643XX_ETH_SHARED_NAME,
 	.id		= 0,
@@ -61,12 +69,12 @@ static struct mv643xx_eth_platform_data eth0_pd = {
 	.shared		= &mv643xx_eth_shared_device,
 	.port_number	= 0,
 
-	.tx_sram_addr = PEGASOS2_SRAM_BASE_ETH0,
-	.tx_sram_size = PEGASOS2_SRAM_TXRING_SIZE,
+	.sram_tx_offset = PEGASOS2_SRAM_OFF_ETH0,
+	.sram_tx_size = PEGASOS2_SRAM_TXRING_SIZE,
 	.tx_queue_size = PEGASOS2_SRAM_TXRING_SIZE/16,
 
-	.rx_sram_addr = PEGASOS2_SRAM_BASE_ETH0 + PEGASOS2_SRAM_TXRING_SIZE,
-	.rx_sram_size = PEGASOS2_SRAM_RXRING_SIZE,
+	.sram_rx_offset = PEGASOS2_SRAM_OFF_ETH0 + PEGASOS2_SRAM_TXRING_SIZE,
+	.sram_tx_size = PEGASOS2_SRAM_RXRING_SIZE,
 	.rx_queue_size = PEGASOS2_SRAM_RXRING_SIZE/16,
 };
 
@@ -93,12 +101,12 @@ static struct mv643xx_eth_platform_data eth1_pd = {
 	.shared		= &mv643xx_eth_shared_device,
 	.port_number	= 1,
 
-	.tx_sram_addr = PEGASOS2_SRAM_BASE_ETH1,
-	.tx_sram_size = PEGASOS2_SRAM_TXRING_SIZE,
+	.sram_tx_offset = PEGASOS2_SRAM_OFF_ETH1,
+	.sram_tx_size = PEGASOS2_SRAM_TXRING_SIZE,
 	.tx_queue_size = PEGASOS2_SRAM_TXRING_SIZE/16,
 
-	.rx_sram_addr = PEGASOS2_SRAM_BASE_ETH1 + PEGASOS2_SRAM_TXRING_SIZE,
-	.rx_sram_size = PEGASOS2_SRAM_RXRING_SIZE,
+	.sram_rx_offset = PEGASOS2_SRAM_OFF_ETH1 + PEGASOS2_SRAM_TXRING_SIZE,
+	.sram_rx_size = PEGASOS2_SRAM_RXRING_SIZE,
 	.rx_queue_size = PEGASOS2_SRAM_RXRING_SIZE/16,
 };
 
@@ -123,16 +131,13 @@ static struct platform_device *mv643xx_eth_pd_devs[] __initdata = {
 #define MV_READ(offset,val) 	{ val = readl(mv643xx_reg_base + offset); }
 #define MV_WRITE(offset,data) writel(data, mv643xx_reg_base + offset)
 
-static void __iomem *mv643xx_reg_base;
-
 static int Enable_SRAM(void)
 {
+	void __iomem *mv643xx_reg_base;
 	u32 ALong;
 
-	if (mv643xx_reg_base == NULL)
-		mv643xx_reg_base = ioremap(PEGASOS2_MARVELL_REGBASE,
-					PEGASOS2_MARVELL_REGSIZE);
-
+	mv643xx_reg_base = ioremap(PEGASOS2_MARVELL_REGBASE,
+				PEGASOS2_MARVELL_REGSIZE);
 	if (mv643xx_reg_base == NULL)
 		return -ENOMEM;
 
@@ -149,23 +154,12 @@ static int Enable_SRAM(void)
 	ALong &= ~(1 << 19);
 	MV_WRITE(MV64340_BASE_ADDR_ENABLE, ALong);
 
-	ALong = 0x02;
-	ALong |= PEGASOS2_SRAM_BASE & 0xffff0000;
-	MV_WRITE(MV643XX_ETH_BAR_4, ALong);
-
-	MV_WRITE(MV643XX_ETH_SIZE_REG_4, (PEGASOS2_SRAM_SIZE-1) & 0xffff0000);
-
-	MV_READ(MV643XX_ETH_BASE_ADDR_ENABLE_REG, ALong);
-	ALong &= ~(1 << 4);
-	MV_WRITE(MV643XX_ETH_BASE_ADDR_ENABLE_REG, ALong);
-
 #ifdef BE_VERBOSE
 	printk("Pegasos II/Marvell MV64361: register unmapped\n");
 	printk("Pegasos II/Marvell MV64361: SRAM at %p, size=%x\n", (void*) PEGASOS2_SRAM_BASE, PEGASOS2_SRAM_SIZE);
 #endif
 
 	iounmap(mv643xx_reg_base);
-	mv643xx_reg_base = NULL;
 
 	return 1;
 }
diff --git a/drivers/net/mv643xx_eth.c b/drivers/net/mv643xx_eth.c
index d513a04..a3ffd1c 100644
--- a/drivers/net/mv643xx_eth.c
+++ b/drivers/net/mv643xx_eth.c
@@ -262,8 +262,10 @@ struct mv643xx_eth_shared_private {
 	wait_queue_head_t smi_busy_wait;
 
 	/*
-	 * Per-port MBUS window access register value.
+	 * MBUS-related data.
 	 */
+	u32 sram_mbus_addr;
+	unsigned long sram_cpu_phys_addr;
 	u32 win_protect;
 
 	/*
@@ -369,8 +371,9 @@ struct mv643xx_eth_private {
 	 * RX state.
 	 */
 	int default_rx_ring_size;
-	unsigned long rx_desc_sram_addr;
+	u32 rx_desc_sram_mbus;
 	int rx_desc_sram_size;
+	unsigned long rx_desc_sram_phys;
 	int rxq_count;
 	struct timer_list rx_oom;
 	struct rx_queue rxq[8];
@@ -379,8 +382,9 @@ struct mv643xx_eth_private {
 	 * TX state.
 	 */
 	int default_tx_ring_size;
-	unsigned long tx_desc_sram_addr;
+	u32 tx_desc_sram_mbus;
 	int tx_desc_sram_size;
+	unsigned long tx_desc_sram_phys;
 	int txq_count;
 	struct tx_queue txq[8];
 };
@@ -1573,9 +1577,9 @@ static int rxq_init(struct mv643xx_eth_private *mp, int index)
 	size = rxq->rx_ring_size * sizeof(struct rx_desc);
 
 	if (index == 0 && size <= mp->rx_desc_sram_size) {
-		rxq->rx_desc_area = ioremap(mp->rx_desc_sram_addr,
+		rxq->rx_desc_area = ioremap(mp->rx_desc_sram_phys,
 						mp->rx_desc_sram_size);
-		rxq->rx_desc_dma = mp->rx_desc_sram_addr;
+		rxq->rx_desc_dma = mp->rx_desc_sram_mbus;
 	} else {
 		rxq->rx_desc_area = dma_alloc_coherent(NULL, size,
 							&rxq->rx_desc_dma,
@@ -1673,9 +1677,9 @@ static int txq_init(struct mv643xx_eth_private *mp, int index)
 	size = txq->tx_ring_size * sizeof(struct tx_desc);
 
 	if (index == 0 && size <= mp->tx_desc_sram_size) {
-		txq->tx_desc_area = ioremap(mp->tx_desc_sram_addr,
+		txq->tx_desc_area = ioremap(mp->tx_desc_sram_phys,
 						mp->tx_desc_sram_size);
-		txq->tx_desc_dma = mp->tx_desc_sram_addr;
+		txq->tx_desc_dma = mp->tx_desc_sram_mbus;
 	} else {
 		txq->tx_desc_area = dma_alloc_coherent(NULL, size,
 							&txq->tx_desc_dma,
@@ -2299,6 +2303,26 @@ mv643xx_eth_conf_mbus_windows(struct mv643xx_eth_shared_private *msp,
 	msp->win_protect = win_protect;
 }
 
+static void
+mv643xx_eth_conf_sram_mbus_windows(struct mv643xx_eth_shared_private *msp,
+				   u8 sram_mbus_target_id, u8 sram_mbus_attr,
+				   u32 sram_mbus_addr, u32 sram_size)
+{
+	void __iomem *base = msp->base;
+	u32 win_enable;
+
+	writel((sram_mbus_addr & 0xffff0000) |
+		(sram_mbus_attr << 8) |
+		sram_mbus_target_id, base + WINDOW_BASE(4));
+	writel((sram_size - 1) & 0xffff0000, base + WINDOW_SIZE(4));
+
+	win_enable = readl(base + WINDOW_BAR_ENABLE);
+	win_enable &= ~(1 << 4);
+	writel(win_enable, base + WINDOW_BAR_ENABLE);
+
+	msp->win_protect |= 3 << (2 * 4);
+}
+
 static void infer_hw_params(struct mv643xx_eth_shared_private *msp)
 {
 	/*
@@ -2391,6 +2415,13 @@ static int mv643xx_eth_shared_probe(struct platform_device *pdev)
 	 */
 	if (pd != NULL && pd->dram != NULL)
 		mv643xx_eth_conf_mbus_windows(msp, pd->dram);
+	if (pd != NULL && pd->sram_mbus_addr) {
+		msp->sram_mbus_addr = pd->sram_mbus_addr;
+		msp->sram_cpu_phys_addr = pd->sram_cpu_phys_addr;
+		mv643xx_eth_conf_sram_mbus_windows(msp,
+			pd->sram_mbus_target_id, pd->sram_mbus_attr,
+			pd->sram_mbus_addr, pd->sram_size);
+	}
 
 	/*
 	 * Detect hardware parameters.
@@ -2457,6 +2488,7 @@ static int phy_addr_get(struct mv643xx_eth_private *mp)
 static void set_params(struct mv643xx_eth_private *mp,
 		       struct mv643xx_eth_platform_data *pd)
 {
+	struct mv643xx_eth_shared_private *msp = mp->shared;
 	struct net_device *dev = mp->dev;
 
 	if (is_valid_ether_addr(pd->mac_addr))
@@ -2467,16 +2499,18 @@ static void set_params(struct mv643xx_eth_private *mp,
 	mp->default_rx_ring_size = DEFAULT_RX_QUEUE_SIZE;
 	if (pd->rx_queue_size)
 		mp->default_rx_ring_size = pd->rx_queue_size;
-	mp->rx_desc_sram_addr = pd->rx_sram_addr;
-	mp->rx_desc_sram_size = pd->rx_sram_size;
+	mp->rx_desc_sram_phys = msp->sram_cpu_phys_addr + pd->sram_rx_offset;
+	mp->rx_desc_sram_mbus = msp->sram_mbus_addr + pd->sram_rx_offset;
+	mp->rx_desc_sram_size = pd->sram_rx_size;
 
 	mp->rxq_count = pd->rx_queue_count ? : 1;
 
 	mp->default_tx_ring_size = DEFAULT_TX_QUEUE_SIZE;
 	if (pd->tx_queue_size)
 		mp->default_tx_ring_size = pd->tx_queue_size;
-	mp->tx_desc_sram_addr = pd->tx_sram_addr;
-	mp->tx_desc_sram_size = pd->tx_sram_size;
+	mp->tx_desc_sram_phys = msp->sram_cpu_phys_addr + pd->sram_tx_offset;
+	mp->tx_desc_sram_mbus = msp->sram_mbus_addr + pd->sram_tx_offset;
+	mp->tx_desc_sram_size = pd->sram_rx_size;
 
 	mp->txq_count = pd->tx_queue_count ? : 1;
 }
diff --git a/include/linux/mv643xx_eth.h b/include/linux/mv643xx_eth.h
index cbbbe9b..9daa4db 100644
--- a/include/linux/mv643xx_eth.h
+++ b/include/linux/mv643xx_eth.h
@@ -11,14 +11,21 @@
 #define MV643XX_ETH_NAME		"mv643xx_eth_port"
 #define MV643XX_ETH_SHARED_REGS		0x2000
 #define MV643XX_ETH_SHARED_REGS_SIZE	0x2000
-#define MV643XX_ETH_BAR_4		0x2220
-#define MV643XX_ETH_SIZE_REG_4		0x2224
-#define MV643XX_ETH_BASE_ADDR_ENABLE_REG	0x2290
 
 struct mv643xx_eth_shared_platform_data {
 	struct mbus_dram_target_info	*dram;
 	struct platform_device	*shared_smi;
 	unsigned int		t_clk;
+
+	/*
+	 * MBUS target data for controller on-chip SRAM (if there
+	 * is any).
+	 */
+	u8			sram_mbus_target_id;
+	u8			sram_mbus_attr;
+	u32			sram_mbus_addr;
+	u32			sram_size;
+	unsigned long		sram_cpu_phys_addr;
 };
 
 #define MV643XX_ETH_PHY_ADDR_DEFAULT	0
@@ -68,10 +75,10 @@ struct mv643xx_eth_platform_data {
 	 * and sufficient to contain all descriptors for the requested
 	 * ring sizes.
 	 */
-	unsigned long		rx_sram_addr;
-	int			rx_sram_size;
-	unsigned long		tx_sram_addr;
-	int			tx_sram_size;
+	int			sram_rx_offset;
+	int			sram_rx_size;
+	int			sram_tx_offset;
+	int			sram_tx_size;
 };
 
 
-- 
1.5.6.4



More information about the Linuxppc-dev mailing list