/*
 * INCA-IP internal switch ethernet driver.
 *
 * (C) Copyright 2003
 * Wolfgang Denk, DENX Software Engineering, wd@denx.de.
 *
 * See file CREDITS for list of people who contributed to this
 * project.
 *
 * This program is free software; you can redistribute it and/or
 * modify it under the terms of the GNU General Public License as
 * published by the Free Software Foundation; either version 2 of
 * the License, or (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.	 See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, Inc., 59 Temple Place, Suite 330, Boston,
 * MA 02111-1307 USA
 */


#include <common.h>

#if (CONFIG_COMMANDS & CFG_CMD_NET) && defined(CONFIG_NET_MULTI) \
	&& defined(CONFIG_INCA_IP_SWITCH)

#include <malloc.h>
#include <net.h>
#include <asm/inca-ip.h>
#include <asm/addrspace.h>


#define NUM_RX_DESC	PKTBUFSRX
#define NUM_TX_DESC	3
#define TOUT_LOOP	1000000


#define DELAY	udelay(10000)

#define DMA_WRITE_REG(reg, value) *((volatile u32 *)reg) = (u32)value;
#define DMA_READ_REG(reg, value)    value = (u32)*((volatile u32*)reg)
#define SW_WRITE_REG(reg, value)   \
         *((volatile u32*)reg) = (u32)value;\
         DELAY;\
         *((volatile u32*)reg) = (u32)value;

#define SW_READ_REG(reg, value)    \
         value = (u32)*((volatile u32*)reg);\
         DELAY;\
         value = (u32)*((volatile u32*)reg);

#define INCA_DMA_TX_POLLING_TIME       0x07
#define INCA_DMA_RX_POLLING_TIME       0x07

#define INCA_DMA_TX_HOLD   0x80000000
#define INCA_DMA_TX_EOP    0x40000000
#define INCA_DMA_TX_SOP    0x20000000
#define INCA_DMA_TX_ICPT   0x10000000
#define INCA_DMA_TX_IEOP   0x08000000

#define INCA_DMA_RX_C   0x80000000
#define INCA_DMA_RX_SOP 0x40000000
#define INCA_DMA_RX_EOP 0x20000000


typedef struct
{
	union
	{
		struct
		{
			volatile u32 HOLD                :1;
			volatile u32 ICpt                :1;
			volatile u32 IEop                :1;
			volatile u32 offset              :3;
			volatile u32 reserved0           :4;
			volatile u32 NFB                 :22;
		}field;

		volatile u32 word;
	}params;

	volatile u32 nextRxDescPtr;

	volatile u32 RxDataPtr;

	union
	{
		struct
		{
			volatile u32 C                   :1;
			volatile u32 Sop                 :1;
			volatile u32 Eop                 :1;
			volatile u32 reserved3           :12;
			volatile u32 NBT                 :17;
		}field;

		volatile u32 word;
	}status;

} inca_rx_descriptor_t;


typedef struct
{
	union
	{
		struct
		{
			volatile u32 HOLD                :1;
			volatile u32 Eop                 :1;
			volatile u32 Sop                 :1;
			volatile u32 ICpt                :1;
			volatile u32 IEop                :1;
			volatile u32 reserved0           :5;
			volatile u32 NBA                 :22;
		}field;

		volatile u32 word;
	}params;

	volatile u32 nextTxDescPtr;

	volatile u32 TxDataPtr;

	volatile u32 C                   :1;
	volatile u32 reserved3           :31;

} inca_tx_descriptor_t;


static inca_rx_descriptor_t rx_ring[NUM_RX_DESC] __attribute__ ((aligned(16)));
static inca_tx_descriptor_t tx_ring[NUM_TX_DESC] __attribute__ ((aligned(16)));

static int tx_new, rx_new, tx_hold, rx_hold;
static int tx_old_hold = -1;
static int initialized  = 0;


static int inca_switch_init(struct eth_device *dev, bd_t * bis);
static int inca_switch_send(struct eth_device *dev, volatile void *packet,
						  int length);
static int inca_switch_recv(struct eth_device *dev);
static void inca_switch_halt(struct eth_device *dev);
static void inca_init_switch_chip(void);
static void inca_dma_init(void);



int inca_switch_initialize(bd_t * bis)
{
	struct eth_device *dev;

#if 0
	printf("Entered inca_switch_initialize()\n");
#endif

	if (!(dev = (struct eth_device *) malloc (sizeof *dev)))
	{
		printf("Failed to allocate memory\n");
		return 0;
	}
	memset(dev, 0, sizeof(*dev));

	inca_dma_init();

	inca_init_switch_chip();

	sprintf(dev->name, "INCA-IP Switch");
	dev->init = inca_switch_init;
	dev->halt = inca_switch_halt;
	dev->send = inca_switch_send;
	dev->recv = inca_switch_recv;

	eth_register(dev);

#if 0
	printf("Leaving inca_switch_initialize()\n");
#endif

	return 1;
}


static int inca_switch_init(struct eth_device *dev, bd_t * bis)
{
	int i;
	u32 v, regValue;
	u16 wTmp;

#if 0
	printf("Entering inca_switch_init()\n");
#endif

		/* Set MAC address.
		 */
	wTmp = (u16)dev->enetaddr[0];
	regValue = (wTmp << 8) | dev->enetaddr[1];

	SW_WRITE_REG(INCA_IP_Switch_PMAC_SA1, regValue);

	wTmp = (u16)dev->enetaddr[2];
	regValue = (wTmp << 8) | dev->enetaddr[3];
	regValue = regValue << 16;
	wTmp = (u16)dev->enetaddr[4];
	regValue |= (wTmp<<8) | dev->enetaddr[5];

	SW_WRITE_REG(INCA_IP_Switch_PMAC_SA2, regValue);

		/* Initialize the descriptor rings.
		 */
	for (i = 0; i < NUM_RX_DESC; i++)
	{
		inca_rx_descriptor_t * rx_desc = KSEG1ADDR(&rx_ring[i]);
		memset(rx_desc, 0, sizeof(rx_ring[i]));

			/* Set maximum size of receive buffer.
			 */
		rx_desc->params.field.NFB = PKTSIZE_ALIGN;

			/* Set the offset of the receive buffer. Zero means
			 * that the offset mechanism is not used.
			 */
		rx_desc->params.field.offset = 0;

		/* Check if it is the last descriptor.
		 */
		if (i == (NUM_RX_DESC - 1))
		{
				/* Let the last descriptor point to the first
				 * one.
				 */
			rx_desc->nextRxDescPtr = KSEG1ADDR((u32)rx_ring);
		}
		else
		{
				/* Set the address of the next descriptor.
				 */
			rx_desc->nextRxDescPtr = (u32)KSEG1ADDR(&rx_ring[i+1]);
		}

		rx_desc->RxDataPtr = (u32)KSEG1ADDR(NetRxPackets[i]);
	}

#if 0
	printf("rx_ring = 0x%08X 0x%08X\n", (u32)rx_ring, (u32)&rx_ring[0]);
	printf("tx_ring = 0x%08X 0x%08X\n", (u32)tx_ring, (u32)&tx_ring[0]);
#endif

	for (i = 0; i < NUM_TX_DESC; i++)
	{
		inca_tx_descriptor_t * tx_desc = KSEG1ADDR(&tx_ring[i]);

		memset(tx_desc, 0, sizeof(tx_ring[i]));

		tx_desc->params.word       = 0;
		tx_desc->params.field.HOLD = 1;
		tx_desc->C                 = 1;

			/* Check if it is the last descriptor.
			 */
		if (i == (NUM_TX_DESC - 1))
		{
				/* Let the last descriptor point to the
				 * first one.
				 */
			tx_desc->nextTxDescPtr = KSEG1ADDR((u32)tx_ring);
		}
		else
		{
				/* Set the address of the next descriptor.
				 */
			tx_desc->nextTxDescPtr = (u32)KSEG1ADDR(&tx_ring[i+1]);
		}
	}

		/* Initialize RxDMA.
		 */
	DMA_READ_REG(INCA_IP_DMA_DMA_RXISR, v);
#if 0
	printf("RX status = 0x%08X\n", v);
#endif

		/* Writing to the FRDA of CHANNEL.
		 */
	DMA_WRITE_REG(INCA_IP_DMA_DMA_RXFRDA0, (u32)rx_ring);

		/* Writing to the COMMAND REG.
		 */
	DMA_WRITE_REG(INCA_IP_DMA_DMA_RXCCR0,
	              INCA_IP_DMA_DMA_RXCCR0_INIT);

		/* Initialize TxDMA.
		 */
	DMA_READ_REG(INCA_IP_DMA_DMA_TXISR, v);
#if 0
	printf("TX status = 0x%08X\n", v);
#endif

		/* Writing to the FRDA of CHANNEL.
		 */
	DMA_WRITE_REG(INCA_IP_DMA_DMA_TXFRDA0, (u32)tx_ring);

	tx_new = rx_new = 0;

	tx_hold = NUM_TX_DESC - 1;
	rx_hold = NUM_RX_DESC - 1;

#if 0
	rx_ring[rx_hold].params.field.HOLD = 1;
#endif
	   /* enable spanning tree forwarding, enable the CPU port */
	   /* ST_PT:
	         CPS (CPU port status)   0x3 (forwarding)
	         LPS (LAN port status)   0x3 (forwarding)
	         PPS (PC port status)    0x3 (forwarding)
	   */
	SW_WRITE_REG(INCA_IP_Switch_ST_PT,0x3f);

#if 0
	printf("Leaving inca_switch_init()\n");
#endif

	return 0;
}


static int inca_switch_send(struct eth_device *dev, volatile void *packet,
						  int length)
{
	int                    i;
	int                    res         = -1;
	u32                    command;
	u32                    regValue;
	inca_tx_descriptor_t * tx_desc     = KSEG1ADDR(&tx_ring[tx_new]);

#if 0
	printf("Entered inca_switch_send()\n");
#endif

	if (length <= 0)
	{
		printf ("%s: bad packet size: %d\n", dev->name, length);
		goto Done;
	}
	
	for(i = 0; tx_desc->C == 0; i++)
	{
		if (i >= TOUT_LOOP)
		{
			printf("%s: tx error buffer not ready\n", dev->name);
			goto Done;
		}
	}

	if (tx_old_hold >= 0)
	{
		KSEG1ADDR(&tx_ring[tx_old_hold])->params.field.HOLD = 1;
	}
	tx_old_hold = tx_hold;

	tx_desc->params.word =
	                (INCA_DMA_TX_SOP | INCA_DMA_TX_EOP | INCA_DMA_TX_HOLD);

	tx_desc->C = 0;
	tx_desc->TxDataPtr = (u32)packet;
	tx_desc->params.field.NBA = length;

	KSEG1ADDR(&tx_ring[tx_hold])->params.field.HOLD = 0;

	tx_hold = tx_new;
	tx_new  = (tx_new + 1) % NUM_TX_DESC;


	if (! initialized)
	{
		command = INCA_IP_DMA_DMA_TXCCR0_INIT;
		initialized = 1;
	}
	else
	{
		command = INCA_IP_DMA_DMA_TXCCR0_HR;
	}
	
	DMA_READ_REG(INCA_IP_DMA_DMA_TXCCR0, regValue);
	regValue |= command;
#if 0
	printf("regValue = 0x%x\n", regValue);
#endif
	DMA_WRITE_REG(INCA_IP_DMA_DMA_TXCCR0, regValue);

#if 1
	for(i = 0; KSEG1ADDR(&tx_ring[tx_hold])->C == 0; i++)
	{
		if (i >= TOUT_LOOP)
		{
			printf("%s: tx buffer not ready\n", dev->name);
			goto Done;
		}
	}
#endif
	res = length;
Done:
#if 0
	printf("Leaving inca_switch_send()\n");
#endif
	return res;
}


static int inca_switch_recv(struct eth_device *dev)
{
	int                    length  = 0;
	inca_rx_descriptor_t * rx_desc;

#if 0
	printf("Entered inca_switch_recv()\n");
#endif

	for (;;)
	{
		rx_desc = KSEG1ADDR(&rx_ring[rx_new]);

		if (rx_desc->status.field.C == 0)
		{
			break;
		}

#if 0
		rx_ring[rx_new].params.field.HOLD = 1;
#endif

		if (! rx_desc->status.field.Eop)
		{
			printf("Partly received packet!!!\n");
			break;
		}

		length = rx_desc->status.field.NBT;
		rx_desc->status.word &=
		         ~(INCA_DMA_RX_EOP | INCA_DMA_RX_SOP | INCA_DMA_RX_C);
#if 0
{
  int i;
  for (i=0;i<length - 4;i++) {
    if (i % 16 == 0) printf("\n%04x: ", i);
    printf("%02X ", NetRxPackets[rx_new][i]);
  }
  printf("\n");
}
#endif

		if (length)
		{
#if 0
			printf("Received %d bytes\n", length);
#endif
			NetReceive((void*)KSEG1ADDR(NetRxPackets[rx_new]),
			            length - 4);
		}
		else
		{
#if 1
			printf("Zero length!!!\n");
#endif
		}


		KSEG1ADDR(&rx_ring[rx_hold])->params.field.HOLD = 0;

		rx_hold = rx_new;

		rx_new = (rx_new + 1) % NUM_RX_DESC;
	}

#if 0
	printf("Leaving inca_switch_recv()\n");
#endif

	return length;
}


static void inca_switch_halt(struct eth_device *dev)
{
#if 0
	printf("Entered inca_switch_halt()\n");
#endif

#if 1
	initialized = 0;
#endif
#if 1
		/* Disable forwarding to the CPU port.
		 */
	SW_WRITE_REG(INCA_IP_Switch_ST_PT,0xf);

		/* Close RxDMA channel.
		 */
	DMA_WRITE_REG(INCA_IP_DMA_DMA_RXCCR0, INCA_IP_DMA_DMA_RXCCR0_OFF);

		/* Close TxDMA channel.
		 */
	DMA_WRITE_REG(INCA_IP_DMA_DMA_TXCCR0, INCA_IP_DMA_DMA_TXCCR0_OFF);


#endif
#if 0
	printf("Leaving inca_switch_halt()\n");
#endif
}


static void inca_init_switch_chip(void)
{
	u32 regValue;

		/* To workaround a problem with collision counter
		 * (see Errata sheet).
		 */
	SW_WRITE_REG(INCA_IP_Switch_PC_TX_CTL, 0x00000001);
	SW_WRITE_REG(INCA_IP_Switch_LAN_TX_CTL, 0x00000001);

#if 1
	   /* init MDIO configuration: 
	         MDS (Poll speed):       0x01 (4ms)
	         PHY_LAN_ADDR:           0x06
	         PHY_PC_ADDR:            0x05
	         UEP (Use External PHY): 0x00 (Internal PHY is used)
	         PS (Port Select):       0x00 (PT/UMM for LAN)
	         PT (PHY Test):          0x00 (no test mode)
	         UMM (Use MDIO Mode):    0x00 (state machine is disabled)
	   */
	SW_WRITE_REG(INCA_IP_Switch_MDIO_CFG, 0x4c50);

	   /* init PHY: 
	         SL (Auto Neg. Speed for LAN)
	         SP (Auto Neg. Speed for PC)
	         LL (Link Status for LAN)
	         LP (Link Status for PC)
	         DL (Duplex Status for LAN)
	         DP (Duplex Status for PC)
	         PL (Auto Neg. Pause Status for LAN)
	         PP (Auto Neg. Pause Status for PC)
	   */
	SW_WRITE_REG (INCA_IP_Switch_EPHY, 0xff);

	   /* MDIO_ACC:
	         RA (Request/Ack)  0x01 (Request)
	         RW (Read/Write)   0x01 (Write)
	         PHY_ADDR          0x05 (PC)
	         REG_ADDR          0x00 (PHY_BCR: basic control register)
	         PHY_DATA          0x8000
	                              Reset                   - software reset
	                              LB (loop back)          - normal
	                              SS (speed select)       - 10 Mbit/s
	                              ANE (auto neg. enable)  - disable
	                              PD (power down)         - normal
	                              ISO (isolate)           - normal
	                              RAN (restart auto neg.) - normal
	                              DM (duplex mode)        - half duplex
	                              CT (collision test)     - enable
	   */
	SW_WRITE_REG(INCA_IP_Switch_MDIO_ACC, 0xc0a08000);

	   /* MDIO_ACC:
	         RA (Request/Ack)  0x01 (Request)
	         RW (Read/Write)   0x01 (Write)
	         PHY_ADDR          0x06 (LAN)
	         REG_ADDR          0x00 (PHY_BCR: basic control register)
	         PHY_DATA          0x8000
	                              Reset                   - software reset
	                              LB (loop back)          - normal
	                              SS (speed select)       - 10 Mbit/s
	                              ANE (auto neg. enable)  - disable
	                              PD (power down)         - normal
	                              ISO (isolate)           - normal
	                              RAN (restart auto neg.) - normal
	                              DM (duplex mode)        - half duplex
	                              CT (collision test)     - enable
	   */
	SW_WRITE_REG(INCA_IP_Switch_MDIO_ACC, 0xc0c08000);
#endif

		/* Make sure the CPU port is disabled for now. We
		 * don't want packets to get stacked for us until
		 * we enable DMA and are prepared to receive them.
		 */
	SW_WRITE_REG(INCA_IP_Switch_ST_PT,0xf);

	SW_READ_REG(INCA_IP_Switch_ARL_CTL, regValue);

		/* CRC GEN is enabled.
		 */
	regValue |= 0x00000200;
	SW_WRITE_REG(INCA_IP_Switch_ARL_CTL, regValue);

		/* ADD TAG is disabled.
		 */
	SW_READ_REG(INCA_IP_Switch_PMAC_HD_CTL, regValue);
	regValue &= ~0x00000002;
	SW_WRITE_REG(INCA_IP_Switch_PMAC_HD_CTL, regValue);
}


static void inca_dma_init(void)
{
		/* Switch off all DMA channels.
		 */
	DMA_WRITE_REG(INCA_IP_DMA_DMA_RXCCR0, INCA_IP_DMA_DMA_RXCCR0_OFF);
	DMA_WRITE_REG(INCA_IP_DMA_DMA_RXCCR1, INCA_IP_DMA_DMA_RXCCR1_OFF);

	DMA_WRITE_REG(INCA_IP_DMA_DMA_TXCCR0, INCA_IP_DMA_DMA_RXCCR0_OFF);
	DMA_WRITE_REG(INCA_IP_DMA_DMA_TXCCR1, INCA_IP_DMA_DMA_TXCCR1_OFF);
	DMA_WRITE_REG(INCA_IP_DMA_DMA_TXCCR2, INCA_IP_DMA_DMA_TXCCR2_OFF);

		/* Setup TX channel polling time.
		 */
	DMA_WRITE_REG(INCA_IP_DMA_DMA_TXPOLL, INCA_DMA_TX_POLLING_TIME);

		/* Setup RX channel polling time.
		 */
	DMA_WRITE_REG(INCA_IP_DMA_DMA_RXPOLL, INCA_DMA_RX_POLLING_TIME);

		/* ERRATA: write reset value into the DMA RX IMR register.
		 */
	DMA_WRITE_REG(INCA_IP_DMA_DMA_RXIMR, 0xFFFFFFFF);

		/* Just in case: disable all transmit interrupts also.
		 */
	DMA_WRITE_REG(INCA_IP_DMA_DMA_TXIMR, 0xFFFFFFFF);

	DMA_WRITE_REG(INCA_IP_DMA_DMA_TXISR, 0xFFFFFFFF);
	DMA_WRITE_REG(INCA_IP_DMA_DMA_RXISR, 0xFFFFFFFF);
}

#endif

	/* End of file.
	 */

