-----------------------
 Ethernet Driver Guide
-----------------------

The networking stack in Das U-Boot is designed for multiple network devices
to be easily added and controlled at runtime.  This guide is meant for people
who wish to review the net driver stack with an eye towards implementing your
own ethernet device driver.  Here we will describe a new pseudo 'APE' driver.

------------------
 Driver Functions
------------------

All functions you will be implementing in this document have the return value
meaning of 0 for success and non-zero for failure.

 ----------
  Register
 ----------

When U-Boot initializes, it will call the common function eth_initialize().
This will in turn call the board-specific board_eth_init() (or if that fails,
the cpu-specific cpu_eth_init()).  These board-specific functions can do random
system handling, but ultimately they will call the driver-specific register
function which in turn takes care of initializing that particular instance.

Keep in mind that you should code the driver to avoid storing state in global
data as someone might want to hook up two of the same devices to one board.
Any such information that is specific to an interface should be stored in a
private, driver-defined data structure and pointed to by eth->priv (see below).

So the call graph at this stage would look something like:
board_init()
	eth_initialize()
		board_eth_init() / cpu_eth_init()
			driver_register()
				initialize eth_device
				eth_register()

At this point in time, the only thing you need to worry about is the driver's
register function.  The pseudo code would look something like:
int ape_register(bd_t *bis, int iobase)
{
	struct ape_priv *priv;
	struct eth_device *dev;

	priv = malloc(sizeof(*priv));
	if (priv == NULL)
		return 1;

	dev = malloc(sizeof(*dev));
	if (dev == NULL) {
		free(priv);
		return 1;
	}

	/* setup whatever private state you need */

	memset(dev, 0, sizeof(*dev));
	sprintf(dev->name, "APE");

	/* if your device has dedicated hardware storage for the
	 * MAC, read it and initialize dev->enetaddr with it
	 */
	ape_mac_read(dev->enetaddr);

	dev->iobase = iobase;
	dev->priv = priv;
	dev->init = ape_init;
	dev->halt = ape_halt;
	dev->send = ape_send;
	dev->recv = ape_recv;

	eth_register(dev);

#ifdef CONFIG_CMD_MII)
	miiphy_register(dev->name, ape_mii_read, ape_mii_write);
#endif

	return 1;
}

The exact arguments needed to initialize your device are up to you.  If you
need to pass more/less arguments, that's fine.  You should also add the
prototype for your new register function to include/netdev.h.

The return value for this function should be as follows:
< 0 - failure (hardware failure, not probe failure)
>=0 - number of interfaces detected

You might notice that many drivers seem to use xxx_initialize() rather than
xxx_register().  This is the old naming convention and should be avoided as it
causes confusion with the driver-specific init function.

Other than locating the MAC address in dedicated hardware storage, you should
not touch the hardware in anyway.  That step is handled in the driver-specific
init function.  Remember that we are only registering the device here, we are
not checking its state or doing random probing.

 -----------
  Callbacks
 -----------

Now that we've registered with the ethernet layer, we can start getting some
real work done.  You will need four functions:
	int ape_init(struct eth_device *dev, bd_t *bis);
	int ape_send(struct eth_device *dev, volatile void *packet, int length);
	int ape_recv(struct eth_device *dev);
	int ape_halt(struct eth_device *dev);

The init function checks the hardware (probing/identifying) and gets it ready
for send/recv operations.  You often do things here such as resetting the MAC
and/or PHY, and waiting for the link to autonegotiate.  You should also take
the opportunity to program the device's MAC address with the dev->enetaddr
member.  This allows the rest of U-Boot to dynamically change the MAC address
and have the new settings be respected.

The send function does what you think -- transmit the specified packet whose
size is specified by length (in bytes).  You should not return until the
transmission is complete, and you should leave the state such that the send
function can be called multiple times in a row.

The recv function should process packets as long as the hardware has them
readily available before returning.  i.e. you should drain the hardware fifo.
The common code sets up packet buffers for you already (NetRxPackets), so there
is no need to allocate your own.  For each packet you receive, you should call
the NetReceive() function on it with the packet length.  So the pseudo code
here would look something like:
int ape_recv(struct eth_device *dev)
{
	int length, i = 0;
	...
	while (packets_are_available()) {
		...
		length = ape_get_packet(&NetRxPackets[i]);
		...
		NetReceive(&NetRxPackets[i], length);
		...
		if (++i >= PKTBUFSRX)
			i = 0;
		...
	}
	...
	return 0;
}

The halt function should turn off / disable the hardware and place it back in
its reset state.

So the call graph at this stage would look something like:
some net operation (ping / tftp / whatever...)
	eth_init()
		dev->init()
	eth_send()
		dev->send()
	eth_rx()
		dev->recv()
	eth_halt()
		dev->halt()

-----------------------------
 CONFIG_MII / CONFIG_CMD_MII
-----------------------------

If your device supports banging arbitrary values on the MII bus (pretty much
every device does), you should add support for the mii command.  Doing so is
fairly trivial and makes debugging mii issues a lot easier at runtime.

After you have called eth_register() in your driver's register function, add
a call to miiphy_register() like so:
#if defined(CONFIG_MII) || defined(CONFIG_CMD_MII)
	miiphy_register(dev->name, mii_read, mii_write);
#endif

And then define the mii_read and mii_write functions if you haven't already.
Their syntax is straightforward:
	int mii_read(char *devname, uchar addr, uchar reg, ushort *val);
	int mii_write(char *devname, uchar addr, uchar reg, ushort val);

The read function should read the register 'reg' from the phy at address 'addr'
and store the result in the pointer 'val'.  The implementation for the write
function should logically follow.
