blob: ebd93c0288e3586ddfe949b91b5fb96cc68d1720 [file] [log] [blame]
Stefan Roese45993ea2006-11-29 15:42:37 +01001/*
2 * (C) Copyright 2003
3 * Ingo Assmus <ingo.assmus@keymile.com>
4 *
5 * based on - Driver for MV64460X ethernet ports
6 * Copyright (C) 2002 rabeeh@galileo.co.il
7 *
Wolfgang Denkd79de1d2013-07-08 09:37:19 +02008 * SPDX-License-Identifier: GPL-2.0+
Stefan Roese45993ea2006-11-29 15:42:37 +01009 */
10
11/*
12 * mv_eth.c - header file for the polled mode GT ethernet driver
13 */
14#include <common.h>
15#include <net.h>
16#include <malloc.h>
17#include <miiphy.h>
18
19#include "mv_eth.h"
20
21/* enable Debug outputs */
22
23#undef DEBUG_MV_ETH
24
25#ifdef DEBUG_MV_ETH
26#define DEBUG
27#define DP(x) x
28#else
29#define DP(x)
30#endif
31
32/* PHY DFCDL Registers */
Wolfgang Denkdd314e02006-11-30 01:54:07 +010033#define ETH_PHY_DFCDL_CONFIG0_REG 0x2100
34#define ETH_PHY_DFCDL_CONFIG1_REG 0x2104
35#define ETH_PHY_DFCDL_ADDR_REG 0x2110
36#define ETH_PHY_DFCDL_DATA0_REG 0x2114
Stefan Roese45993ea2006-11-29 15:42:37 +010037
Wolfgang Denkdd314e02006-11-30 01:54:07 +010038#define PHY_AUTONEGOTIATE_TIMEOUT 4000 /* 4000 ms autonegotiate timeout */
39#define PHY_UPDATE_TIMEOUT 10000
Stefan Roese45993ea2006-11-29 15:42:37 +010040
41#undef MV64460_CHECKSUM_OFFLOAD
42/*************************************************************************
Wolfgang Denkdd314e02006-11-30 01:54:07 +010043* The first part is the high level driver of the gigE ethernet ports. *
Stefan Roese45993ea2006-11-29 15:42:37 +010044*************************************************************************/
45
46/* Definition for configuring driver */
47/* #define UPDATE_STATS_BY_SOFTWARE */
48#undef MV64460_RX_QUEUE_FILL_ON_TASK
49
Stefan Roese45993ea2006-11-29 15:42:37 +010050/* Constants */
51#define MAGIC_ETH_RUNNING 8031971
Wolfgang Denkdd314e02006-11-30 01:54:07 +010052#define MV64460_INTERNAL_SRAM_SIZE _256K
Stefan Roese45993ea2006-11-29 15:42:37 +010053#define EXTRA_BYTES 32
Wolfgang Denkdd314e02006-11-30 01:54:07 +010054#define WRAP ETH_HLEN + 2 + 4 + 16
Stefan Roese45993ea2006-11-29 15:42:37 +010055#define BUFFER_MTU dev->mtu + WRAP
56#define INT_CAUSE_UNMASK_ALL 0x0007ffff
57#define INT_CAUSE_UNMASK_ALL_EXT 0x0011ffff
58#ifdef MV64460_RX_FILL_ON_TASK
59#define INT_CAUSE_MASK_ALL 0x00000000
60#define INT_CAUSE_CHECK_BITS INT_CAUSE_UNMASK_ALL
61#define INT_CAUSE_CHECK_BITS_EXT INT_CAUSE_UNMASK_ALL_EXT
62#endif
63
64/* Read/Write to/from MV64460 internal registers */
65#define MV_REG_READ(offset) my_le32_to_cpu(* (volatile unsigned int *) (INTERNAL_REG_BASE_ADDR + offset))
66#define MV_REG_WRITE(offset,data) *(volatile unsigned int *) (INTERNAL_REG_BASE_ADDR + offset) = my_cpu_to_le32 (data)
67#define MV_SET_REG_BITS(regOffset,bits) ((*((volatile unsigned int*)((INTERNAL_REG_BASE_ADDR) + (regOffset)))) |= ((unsigned int)my_cpu_to_le32(bits)))
68#define MV_RESET_REG_BITS(regOffset,bits) ((*((volatile unsigned int*)((INTERNAL_REG_BASE_ADDR) + (regOffset)))) &= ~((unsigned int)my_cpu_to_le32(bits)))
69
70#define my_cpu_to_le32(x) my_le32_to_cpu((x))
71
72/* Static function declarations */
73static int mv64460_eth_real_open (struct eth_device *eth);
74static int mv64460_eth_real_stop (struct eth_device *eth);
75static struct net_device_stats *mv64460_eth_get_stats (struct eth_device
76 *dev);
77static void eth_port_init_mac_tables (ETH_PORT eth_port_num);
78static void mv64460_eth_update_stat (struct eth_device *dev);
79bool db64460_eth_start (struct eth_device *eth);
80unsigned int eth_read_mib_counter (ETH_PORT eth_port_num,
81 unsigned int mib_offset);
82int mv64460_eth_receive (struct eth_device *dev);
83
84int mv64460_eth_xmit (struct eth_device *, volatile void *packet, int length);
85
Mike Frysinger5ff5fdb2010-07-27 18:35:08 -040086int mv_miiphy_read(const char *devname, unsigned char phy_addr,
Stefan Roese45993ea2006-11-29 15:42:37 +010087 unsigned char phy_reg, unsigned short *value);
Mike Frysinger5ff5fdb2010-07-27 18:35:08 -040088int mv_miiphy_write(const char *devname, unsigned char phy_addr,
Stefan Roese45993ea2006-11-29 15:42:37 +010089 unsigned char phy_reg, unsigned short value);
90
91int phy_setup_aneg (char *devname, unsigned char addr);
92
Wolfgang Denkdd314e02006-11-30 01:54:07 +010093#ifndef UPDATE_STATS_BY_SOFTWARE
Stefan Roese45993ea2006-11-29 15:42:37 +010094static void mv64460_eth_print_stat (struct eth_device *dev);
95#endif
Stefan Roese45993ea2006-11-29 15:42:37 +010096
97extern unsigned int INTERNAL_REG_BASE_ADDR;
98
99unsigned long my_le32_to_cpu (unsigned long x)
100{
101 return (((x & 0x000000ffU) << 24) |
102 ((x & 0x0000ff00U) << 8) |
103 ((x & 0x00ff0000U) >> 8) | ((x & 0xff000000U) >> 24));
104}
105
106/*************************************************
107 *Helper functions - used inside the driver only *
108 *************************************************/
109#ifdef DEBUG_MV_ETH
110void print_globals (struct eth_device *dev)
111{
112 printf ("Ethernet PRINT_Globals-Debug function\n");
113 printf ("Base Address for ETH_PORT_INFO: %08x\n",
114 (unsigned int) dev->priv);
115 printf ("Base Address for mv64460_eth_priv: %08x\n",
116 (unsigned int) &(((ETH_PORT_INFO *) dev->priv)->
117 port_private));
118
119 printf ("GT Internal Base Address: %08x\n",
120 INTERNAL_REG_BASE_ADDR);
Wolfgang Denkdd314e02006-11-30 01:54:07 +0100121 printf ("Base Address for TX-DESCs: %08x Number of allocated Buffers %d\n",
122 (unsigned int) ((ETH_PORT_INFO *) dev->priv)->p_tx_desc_area_base[0], MV64460_TX_QUEUE_SIZE);
123 printf ("Base Address for RX-DESCs: %08x Number of allocated Buffers %d\n",
124 (unsigned int) ((ETH_PORT_INFO *) dev->priv)->p_rx_desc_area_base[0], MV64460_RX_QUEUE_SIZE);
Stefan Roese45993ea2006-11-29 15:42:37 +0100125 printf ("Base Address for RX-Buffer: %08x allocated Bytes %d\n",
126 (unsigned int) ((ETH_PORT_INFO *) dev->priv)->
127 p_rx_buffer_base[0],
128 (MV64460_RX_QUEUE_SIZE * MV64460_RX_BUFFER_SIZE) + 32);
129 printf ("Base Address for TX-Buffer: %08x allocated Bytes %d\n",
130 (unsigned int) ((ETH_PORT_INFO *) dev->priv)->
131 p_tx_buffer_base[0],
132 (MV64460_TX_QUEUE_SIZE * MV64460_TX_BUFFER_SIZE) + 32);
133}
134#endif
135
Stefan Roese45993ea2006-11-29 15:42:37 +0100136/**********************************************************************
137 * mv64460_eth_print_phy_status
138 *
139 * Prints gigabit ethenret phy status
140 *
141 * Input : pointer to ethernet interface network device structure
142 * Output : N/A
143 **********************************************************************/
144void mv64460_eth_print_phy_status (struct eth_device *dev)
145{
146 struct mv64460_eth_priv *port_private;
147 unsigned int port_num;
148 ETH_PORT_INFO *ethernet_private = (ETH_PORT_INFO *) dev->priv;
149 unsigned int port_status, phy_reg_data;
150
151 port_private =
152 (struct mv64460_eth_priv *) ethernet_private->port_private;
153 port_num = port_private->port_num;
154
155 /* Check Link status on phy */
156 eth_port_read_smi_reg (port_num, 1, &phy_reg_data);
157 if (!(phy_reg_data & 0x20)) {
158 printf ("Ethernet port changed link status to DOWN\n");
159 } else {
160 port_status =
161 MV_REG_READ (MV64460_ETH_PORT_STATUS_REG (port_num));
162 printf ("Ethernet status port %d: Link up", port_num);
163 printf (", %s",
164 (port_status & BIT2) ? "Full Duplex" : "Half Duplex");
165 if (port_status & BIT4)
166 printf (", Speed 1 Gbps");
167 else
168 printf (", %s",
169 (port_status & BIT5) ? "Speed 100 Mbps" :
170 "Speed 10 Mbps");
171 printf ("\n");
172 }
173}
174
175/**********************************************************************
176 * u-boot entry functions for mv64460_eth
177 *
178 **********************************************************************/
179int db64460_eth_probe (struct eth_device *dev)
180{
181 return ((int) db64460_eth_start (dev));
182}
183
184int db64460_eth_poll (struct eth_device *dev)
185{
186 return mv64460_eth_receive (dev);
187}
188
Joe Hershbergere4e04882012-05-22 18:36:19 +0000189int db64460_eth_transmit(struct eth_device *dev, void *packet, int length)
Stefan Roese45993ea2006-11-29 15:42:37 +0100190{
191 mv64460_eth_xmit (dev, packet, length);
192 return 0;
193}
194
195void db64460_eth_disable (struct eth_device *dev)
196{
197 mv64460_eth_stop (dev);
198}
199
Stefan Roese45993ea2006-11-29 15:42:37 +0100200#define DFCDL(write,read) ((write << 6) | read)
Wolfgang Denkdd314e02006-11-30 01:54:07 +0100201unsigned int ethDfcdls[] = {
202 DFCDL(0,0), DFCDL(1,1), DFCDL(2,2), DFCDL(3,3),
203 DFCDL(4,4), DFCDL(5,5), DFCDL(6,6), DFCDL(7,7),
204 DFCDL(8,8), DFCDL(9,9), DFCDL(10,10), DFCDL(11,11),
205 DFCDL(12,12), DFCDL(13,13), DFCDL(14,14), DFCDL(15,15),
206 DFCDL(16,16), DFCDL(17,17), DFCDL(18,18), DFCDL(19,19),
207 DFCDL(20,20), DFCDL(21,21), DFCDL(22,22), DFCDL(23,23),
208 DFCDL(24,24), DFCDL(25,25), DFCDL(26,26), DFCDL(27,27),
209 DFCDL(28,28), DFCDL(29,29), DFCDL(30,30), DFCDL(31,31),
210 DFCDL(32,32), DFCDL(33,33), DFCDL(34,34), DFCDL(35,35),
211 DFCDL(36,36), DFCDL(37,37), DFCDL(38,38), DFCDL(39,39),
212 DFCDL(40,40), DFCDL(41,41), DFCDL(42,42), DFCDL(43,43),
213 DFCDL(44,44), DFCDL(45,45), DFCDL(46,46), DFCDL(47,47),
214 DFCDL(48,48), DFCDL(49,49), DFCDL(50,50), DFCDL(51,51),
215 DFCDL(52,52), DFCDL(53,53), DFCDL(54,54), DFCDL(55,55),
216 DFCDL(56,56), DFCDL(57,57), DFCDL(58,58), DFCDL(59,59),
217 DFCDL(60,60), DFCDL(61,61), DFCDL(62,62), DFCDL(63,63),
218};
Stefan Roese45993ea2006-11-29 15:42:37 +0100219
Wolfgang Denkdd314e02006-11-30 01:54:07 +0100220void mv_eth_phy_init (void)
Stefan Roese45993ea2006-11-29 15:42:37 +0100221{
Wolfgang Denkdd314e02006-11-30 01:54:07 +0100222 int i;
Stefan Roese45993ea2006-11-29 15:42:37 +0100223
Wolfgang Denkdd314e02006-11-30 01:54:07 +0100224 MV_REG_WRITE (ETH_PHY_DFCDL_ADDR_REG, 0);
Stefan Roese45993ea2006-11-29 15:42:37 +0100225
Wolfgang Denkdd314e02006-11-30 01:54:07 +0100226 for (i = 0; i < 64; i++) {
227 MV_REG_WRITE (ETH_PHY_DFCDL_DATA0_REG, ethDfcdls[i]);
228 }
Stefan Roese45993ea2006-11-29 15:42:37 +0100229
Wolfgang Denkdd314e02006-11-30 01:54:07 +0100230 MV_REG_WRITE (ETH_PHY_DFCDL_CONFIG0_REG, 0x300000);
Stefan Roese45993ea2006-11-29 15:42:37 +0100231}
232
233void mv6446x_eth_initialize (bd_t * bis)
234{
235 struct eth_device *dev;
236 ETH_PORT_INFO *ethernet_private;
237 struct mv64460_eth_priv *port_private;
238 int devnum, x, temp;
239 char *s, *e, buf[64];
240
Wolfgang Denkdd314e02006-11-30 01:54:07 +0100241 /* P3M750 only
242 * Set RGMII clock drives strength
243 */
Stefan Roese45993ea2006-11-29 15:42:37 +0100244 temp = MV_REG_READ(0x20A0);
245 temp |= 0x04000080;
246 MV_REG_WRITE(0x20A0, temp);
247
248 mv_eth_phy_init();
249
250 for (devnum = 0; devnum < MV_ETH_DEVS; devnum++) {
251 dev = calloc (sizeof (*dev), 1);
252 if (!dev) {
253 printf ("%s: mv_enet%d allocation failure, %s\n",
254 __FUNCTION__, devnum, "eth_device structure");
255 return;
256 }
257
Mike Frysinger6b300dc2011-11-10 14:11:04 +0000258 /* must be less than sizeof(dev->name) */
Stefan Roese45993ea2006-11-29 15:42:37 +0100259 sprintf (dev->name, "mv_enet%d", devnum);
260
261#ifdef DEBUG
262 printf ("Initializing %s\n", dev->name);
263#endif
264
265 /* Extract the MAC address from the environment */
266 switch (devnum) {
267 case 0:
268 s = "ethaddr";
269 break;
Stefan Roese45993ea2006-11-29 15:42:37 +0100270 case 1:
271 s = "eth1addr";
272 break;
Stefan Roese45993ea2006-11-29 15:42:37 +0100273 case 2:
274 s = "eth2addr";
275 break;
Stefan Roese45993ea2006-11-29 15:42:37 +0100276 default: /* this should never happen */
277 printf ("%s: Invalid device number %d\n",
278 __FUNCTION__, devnum);
279 return;
280 }
281
Wolfgang Denk76af2782010-07-24 21:55:43 +0200282 temp = getenv_f(s, buf, sizeof (buf));
Stefan Roese45993ea2006-11-29 15:42:37 +0100283 s = (temp > 0) ? buf : NULL;
284
285#ifdef DEBUG
286 printf ("Setting MAC %d to %s\n", devnum, s);
287#endif
288 for (x = 0; x < 6; ++x) {
289 dev->enetaddr[x] = s ? simple_strtoul (s, &e, 16) : 0;
290 if (s)
291 s = (*e) ? e + 1 : e;
292 }
293 /* ronen - set the MAC addr in the HW */
294 eth_port_uc_addr_set (devnum, dev->enetaddr, 0);
295
296 dev->init = (void *) db64460_eth_probe;
297 dev->halt = (void *) ethernet_phy_reset;
298 dev->send = (void *) db64460_eth_transmit;
299 dev->recv = (void *) db64460_eth_poll;
300
301 ethernet_private = calloc (sizeof (*ethernet_private), 1);
302 dev->priv = (void *)ethernet_private;
303 if (!ethernet_private) {
304 printf ("%s: %s allocation failure, %s\n",
305 __FUNCTION__, dev->name,
306 "Private Device Structure");
307 free (dev);
308 return;
309 }
310 /* start with an zeroed ETH_PORT_INFO */
311 memset (ethernet_private, 0, sizeof (ETH_PORT_INFO));
312 memcpy (ethernet_private->port_mac_addr, dev->enetaddr, 6);
313
314 /* set pointer to memory for stats data structure etc... */
315 port_private = calloc (sizeof (*ethernet_private), 1);
316 ethernet_private->port_private = (void *)port_private;
317 if (!port_private) {
318 printf ("%s: %s allocation failure, %s\n",
319 __FUNCTION__, dev->name,
320 "Port Private Device Structure");
321
322 free (ethernet_private);
323 free (dev);
324 return;
325 }
326
327 port_private->stats =
328 calloc (sizeof (struct net_device_stats), 1);
329 if (!port_private->stats) {
330 printf ("%s: %s allocation failure, %s\n",
331 __FUNCTION__, dev->name,
332 "Net stat Structure");
333
334 free (port_private);
335 free (ethernet_private);
336 free (dev);
337 return;
338 }
339 memset (ethernet_private->port_private, 0,
340 sizeof (struct mv64460_eth_priv));
341 switch (devnum) {
342 case 0:
343 ethernet_private->port_num = ETH_0;
344 break;
345 case 1:
346 ethernet_private->port_num = ETH_1;
347 break;
348 case 2:
349 ethernet_private->port_num = ETH_2;
350 break;
351 default:
352 printf ("Invalid device number %d\n", devnum);
353 break;
354 };
355
356 port_private->port_num = devnum;
357 /*
358 * Read MIB counter on the GT in order to reset them,
359 * then zero all the stats fields in memory
360 */
361 mv64460_eth_update_stat (dev);
362 memset (port_private->stats, 0,
363 sizeof (struct net_device_stats));
364 /* Extract the MAC address from the environment */
365 switch (devnum) {
366 case 0:
367 s = "ethaddr";
368 break;
Stefan Roese45993ea2006-11-29 15:42:37 +0100369 case 1:
370 s = "eth1addr";
371 break;
Stefan Roese45993ea2006-11-29 15:42:37 +0100372 case 2:
373 s = "eth2addr";
374 break;
Stefan Roese45993ea2006-11-29 15:42:37 +0100375 default: /* this should never happen */
376 printf ("%s: Invalid device number %d\n",
377 __FUNCTION__, devnum);
378 return;
379 }
380
Wolfgang Denk76af2782010-07-24 21:55:43 +0200381 temp = getenv_f(s, buf, sizeof (buf));
Stefan Roese45993ea2006-11-29 15:42:37 +0100382 s = (temp > 0) ? buf : NULL;
383
384#ifdef DEBUG
385 printf ("Setting MAC %d to %s\n", devnum, s);
386#endif
387 for (x = 0; x < 6; ++x) {
388 dev->enetaddr[x] = s ? simple_strtoul (s, &e, 16) : 0;
389 if (s)
390 s = (*e) ? e + 1 : e;
391 }
392
393 DP (printf ("Allocating descriptor and buffer rings\n"));
394
395 ethernet_private->p_rx_desc_area_base[0] =
396 (ETH_RX_DESC *) memalign (16,
397 RX_DESC_ALIGNED_SIZE *
398 MV64460_RX_QUEUE_SIZE + 1);
399 ethernet_private->p_tx_desc_area_base[0] =
400 (ETH_TX_DESC *) memalign (16,
401 TX_DESC_ALIGNED_SIZE *
402 MV64460_TX_QUEUE_SIZE + 1);
403
404 ethernet_private->p_rx_buffer_base[0] =
405 (char *) memalign (16,
406 MV64460_RX_QUEUE_SIZE *
407 MV64460_TX_BUFFER_SIZE + 1);
408 ethernet_private->p_tx_buffer_base[0] =
409 (char *) memalign (16,
410 MV64460_RX_QUEUE_SIZE *
411 MV64460_TX_BUFFER_SIZE + 1);
412
413#ifdef DEBUG_MV_ETH
414 /* DEBUG OUTPUT prints adresses of globals */
415 print_globals (dev);
416#endif
417 eth_register (dev);
418
419 miiphy_register(dev->name, mv_miiphy_read, mv_miiphy_write);
420 }
421 DP (printf ("%s: exit\n", __FUNCTION__));
422
423}
424
425/**********************************************************************
426 * mv64460_eth_open
427 *
428 * This function is called when openning the network device. The function
429 * should initialize all the hardware, initialize cyclic Rx/Tx
430 * descriptors chain and buffers and allocate an IRQ to the network
431 * device.
432 *
433 * Input : a pointer to the network device structure
434 * / / ronen - changed the output to match net/eth.c needs
435 * Output : nonzero of success , zero if fails.
436 * under construction
437 **********************************************************************/
438
439int mv64460_eth_open (struct eth_device *dev)
440{
441 return (mv64460_eth_real_open (dev));
442}
443
444/* Helper function for mv64460_eth_open */
445static int mv64460_eth_real_open (struct eth_device *dev)
446{
447
448 unsigned int queue;
449 ETH_PORT_INFO *ethernet_private;
450 struct mv64460_eth_priv *port_private;
451 unsigned int port_num;
Stefan Roese45993ea2006-11-29 15:42:37 +0100452 ushort reg_short;
453 int speed;
454 int duplex;
455 int i;
456 int reg;
457
458 ethernet_private = (ETH_PORT_INFO *) dev->priv;
459 /* ronen - when we update the MAC env params we only update dev->enetaddr
460 see ./net/eth.c eth_set_enetaddr() */
461 memcpy (ethernet_private->port_mac_addr, dev->enetaddr, 6);
462
Wolfgang Denkdd314e02006-11-30 01:54:07 +0100463 port_private = (struct mv64460_eth_priv *) ethernet_private->port_private;
Stefan Roese45993ea2006-11-29 15:42:37 +0100464 port_num = port_private->port_num;
465
466 /* Stop RX Queues */
Wolfgang Denkdd314e02006-11-30 01:54:07 +0100467 MV_REG_WRITE (MV64460_ETH_RECEIVE_QUEUE_COMMAND_REG (port_num), 0x0000ff00);
Stefan Roese45993ea2006-11-29 15:42:37 +0100468
469 /* Clear the ethernet port interrupts */
470 MV_REG_WRITE (MV64460_ETH_INTERRUPT_CAUSE_REG (port_num), 0);
471 MV_REG_WRITE (MV64460_ETH_INTERRUPT_CAUSE_EXTEND_REG (port_num), 0);
472
473 /* Unmask RX buffer and TX end interrupt */
474 MV_REG_WRITE (MV64460_ETH_INTERRUPT_MASK_REG (port_num),
475 INT_CAUSE_UNMASK_ALL);
476
477 /* Unmask phy and link status changes interrupts */
478 MV_REG_WRITE (MV64460_ETH_INTERRUPT_EXTEND_MASK_REG (port_num),
479 INT_CAUSE_UNMASK_ALL_EXT);
480
481 /* Set phy address of the port */
482 ethernet_private->port_phy_addr = 0x1 + (port_num << 1);
483 reg = ethernet_private->port_phy_addr;
484
485 /* Activate the DMA channels etc */
486 eth_port_init (ethernet_private);
487
488 /* "Allocate" setup TX rings */
489
490 for (queue = 0; queue < MV64460_TX_QUEUE_NUM; queue++) {
491 unsigned int size;
492
493 port_private->tx_ring_size[queue] = MV64460_TX_QUEUE_SIZE;
494 size = (port_private->tx_ring_size[queue] * TX_DESC_ALIGNED_SIZE); /*size = no of DESCs times DESC-size */
495 ethernet_private->tx_desc_area_size[queue] = size;
496
497 /* first clear desc area completely */
498 memset ((void *) ethernet_private->p_tx_desc_area_base[queue],
499 0, ethernet_private->tx_desc_area_size[queue]);
500
501 /* initialize tx desc ring with low level driver */
502 if (ether_init_tx_desc_ring
503 (ethernet_private, ETH_Q0,
504 port_private->tx_ring_size[queue],
505 MV64460_TX_BUFFER_SIZE /* Each Buffer is 1600 Byte */ ,
506 (unsigned int) ethernet_private->
507 p_tx_desc_area_base[queue],
508 (unsigned int) ethernet_private->
509 p_tx_buffer_base[queue]) == false)
510 printf ("### Error initializing TX Ring\n");
511 }
512
513 /* "Allocate" setup RX rings */
514 for (queue = 0; queue < MV64460_RX_QUEUE_NUM; queue++) {
515 unsigned int size;
516
517 /* Meantime RX Ring are fixed - but must be configurable by user */
518 port_private->rx_ring_size[queue] = MV64460_RX_QUEUE_SIZE;
519 size = (port_private->rx_ring_size[queue] *
520 RX_DESC_ALIGNED_SIZE);
521 ethernet_private->rx_desc_area_size[queue] = size;
522
523 /* first clear desc area completely */
524 memset ((void *) ethernet_private->p_rx_desc_area_base[queue],
525 0, ethernet_private->rx_desc_area_size[queue]);
526 if ((ether_init_rx_desc_ring
527 (ethernet_private, ETH_Q0,
528 port_private->rx_ring_size[queue],
529 MV64460_RX_BUFFER_SIZE /* Each Buffer is 1600 Byte */ ,
530 (unsigned int) ethernet_private->
531 p_rx_desc_area_base[queue],
532 (unsigned int) ethernet_private->
533 p_rx_buffer_base[queue])) == false)
534 printf ("### Error initializing RX Ring\n");
535 }
536
537 eth_port_start (ethernet_private);
538
539 /* Set maximum receive buffer to 9700 bytes */
540 MV_REG_WRITE (MV64460_ETH_PORT_SERIAL_CONTROL_REG (port_num),
541 (0x5 << 17) |
542 (MV_REG_READ
543 (MV64460_ETH_PORT_SERIAL_CONTROL_REG (port_num))
544 & 0xfff1ffff));
545
546 /*
547 * Set ethernet MTU for leaky bucket mechanism to 0 - this will
548 * disable the leaky bucket mechanism .
549 */
550
551 MV_REG_WRITE (MV64460_ETH_MAXIMUM_TRANSMIT_UNIT (port_num), 0);
Wolfgang Denkb1fe5262011-10-29 09:38:21 +0000552 MV_REG_READ (MV64460_ETH_PORT_STATUS_REG (port_num));
Stefan Roese45993ea2006-11-29 15:42:37 +0100553
554#if defined(CONFIG_PHY_RESET)
555 /*
556 * Reset the phy, only if its the first time through
557 * otherwise, just check the speeds & feeds
558 */
559 if (port_private->first_init == 0) {
560 port_private->first_init = 1;
561 ethernet_phy_reset (port_num);
562
563 /* Start/Restart autonegotiation */
564 phy_setup_aneg (dev->name, reg);
565 udelay (1000);
566 }
567#endif /* defined(CONFIG_PHY_RESET) */
568
Mike Frysingerd63ee712010-12-23 15:40:12 -0500569 miiphy_read (dev->name, reg, MII_BMSR, &reg_short);
Stefan Roese45993ea2006-11-29 15:42:37 +0100570
571 /*
572 * Wait if PHY is capable of autonegotiation and autonegotiation is not complete
573 */
Mike Frysingerd63ee712010-12-23 15:40:12 -0500574 if ((reg_short & BMSR_ANEGCAPABLE)
575 && !(reg_short & BMSR_ANEGCOMPLETE)) {
Stefan Roese45993ea2006-11-29 15:42:37 +0100576 puts ("Waiting for PHY auto negotiation to complete");
577 i = 0;
Mike Frysingerd63ee712010-12-23 15:40:12 -0500578 while (!(reg_short & BMSR_ANEGCOMPLETE)) {
Stefan Roese45993ea2006-11-29 15:42:37 +0100579 /*
580 * Timeout reached ?
581 */
582 if (i > PHY_AUTONEGOTIATE_TIMEOUT) {
583 puts (" TIMEOUT !\n");
584 break;
585 }
586
587 if ((i++ % 1000) == 0) {
588 putc ('.');
589 }
590 udelay (1000); /* 1 ms */
Mike Frysingerd63ee712010-12-23 15:40:12 -0500591 miiphy_read (dev->name, reg, MII_BMSR, &reg_short);
Stefan Roese45993ea2006-11-29 15:42:37 +0100592
593 }
594 puts (" done\n");
595 udelay (500000); /* another 500 ms (results in faster booting) */
596 }
597
598 speed = miiphy_speed (dev->name, reg);
599 duplex = miiphy_duplex (dev->name, reg);
600
601 printf ("ENET Speed is %d Mbps - %s duplex connection\n",
602 (int) speed, (duplex == HALF) ? "HALF" : "FULL");
603
604 port_private->eth_running = MAGIC_ETH_RUNNING;
605 return 1;
606}
607
Stefan Roese45993ea2006-11-29 15:42:37 +0100608static int mv64460_eth_free_tx_rings (struct eth_device *dev)
609{
610 unsigned int queue;
611 ETH_PORT_INFO *ethernet_private;
612 struct mv64460_eth_priv *port_private;
613 unsigned int port_num;
614 volatile ETH_TX_DESC *p_tx_curr_desc;
615
616 ethernet_private = (ETH_PORT_INFO *) dev->priv;
617 port_private =
618 (struct mv64460_eth_priv *) ethernet_private->port_private;
619 port_num = port_private->port_num;
620
621 /* Stop Tx Queues */
622 MV_REG_WRITE (MV64460_ETH_TRANSMIT_QUEUE_COMMAND_REG (port_num),
623 0x0000ff00);
624
625 /* Free TX rings */
626 DP (printf ("Clearing previously allocated TX queues... "));
627 for (queue = 0; queue < MV64460_TX_QUEUE_NUM; queue++) {
628 /* Free on TX rings */
629 for (p_tx_curr_desc =
630 ethernet_private->p_tx_desc_area_base[queue];
631 ((unsigned int) p_tx_curr_desc <= (unsigned int)
632 ethernet_private->p_tx_desc_area_base[queue] +
633 ethernet_private->tx_desc_area_size[queue]);
634 p_tx_curr_desc =
635 (ETH_TX_DESC *) ((unsigned int) p_tx_curr_desc +
636 TX_DESC_ALIGNED_SIZE)) {
637 /* this is inside for loop */
638 if (p_tx_curr_desc->return_info != 0) {
639 p_tx_curr_desc->return_info = 0;
640 DP (printf ("freed\n"));
641 }
642 }
643 DP (printf ("Done\n"));
644 }
645 return 0;
646}
647
648static int mv64460_eth_free_rx_rings (struct eth_device *dev)
649{
650 unsigned int queue;
651 ETH_PORT_INFO *ethernet_private;
652 struct mv64460_eth_priv *port_private;
653 unsigned int port_num;
654 volatile ETH_RX_DESC *p_rx_curr_desc;
655
656 ethernet_private = (ETH_PORT_INFO *) dev->priv;
657 port_private =
658 (struct mv64460_eth_priv *) ethernet_private->port_private;
659 port_num = port_private->port_num;
660
Stefan Roese45993ea2006-11-29 15:42:37 +0100661 /* Stop RX Queues */
662 MV_REG_WRITE (MV64460_ETH_RECEIVE_QUEUE_COMMAND_REG (port_num),
663 0x0000ff00);
664
665 /* Free RX rings */
666 DP (printf ("Clearing previously allocated RX queues... "));
667 for (queue = 0; queue < MV64460_RX_QUEUE_NUM; queue++) {
668 /* Free preallocated skb's on RX rings */
669 for (p_rx_curr_desc =
670 ethernet_private->p_rx_desc_area_base[queue];
671 (((unsigned int) p_rx_curr_desc <
672 ((unsigned int) ethernet_private->
673 p_rx_desc_area_base[queue] +
674 ethernet_private->rx_desc_area_size[queue])));
675 p_rx_curr_desc =
676 (ETH_RX_DESC *) ((unsigned int) p_rx_curr_desc +
677 RX_DESC_ALIGNED_SIZE)) {
678 if (p_rx_curr_desc->return_info != 0) {
679 p_rx_curr_desc->return_info = 0;
680 DP (printf ("freed\n"));
681 }
682 }
683 DP (printf ("Done\n"));
684 }
685 return 0;
686}
687
688/**********************************************************************
689 * mv64460_eth_stop
690 *
691 * This function is used when closing the network device.
692 * It updates the hardware,
693 * release all memory that holds buffers and descriptors and release the IRQ.
694 * Input : a pointer to the device structure
695 * Output : zero if success , nonzero if fails
696 *********************************************************************/
697
698int mv64460_eth_stop (struct eth_device *dev)
699{
Stefan Roese45993ea2006-11-29 15:42:37 +0100700 /* Disable all gigE address decoder */
701 MV_REG_WRITE (MV64460_ETH_BASE_ADDR_ENABLE_REG, 0x3f);
702 DP (printf ("%s Ethernet stop called ... \n", __FUNCTION__));
703 mv64460_eth_real_stop (dev);
704
705 return 0;
706};
707
708/* Helper function for mv64460_eth_stop */
709
710static int mv64460_eth_real_stop (struct eth_device *dev)
711{
712 ETH_PORT_INFO *ethernet_private;
713 struct mv64460_eth_priv *port_private;
714 unsigned int port_num;
715
716 ethernet_private = (ETH_PORT_INFO *) dev->priv;
717 port_private =
718 (struct mv64460_eth_priv *) ethernet_private->port_private;
719 port_num = port_private->port_num;
720
721 mv64460_eth_free_tx_rings (dev);
722 mv64460_eth_free_rx_rings (dev);
723
724 eth_port_reset (ethernet_private->port_num);
725 /* Disable ethernet port interrupts */
726 MV_REG_WRITE (MV64460_ETH_INTERRUPT_CAUSE_REG (port_num), 0);
727 MV_REG_WRITE (MV64460_ETH_INTERRUPT_CAUSE_EXTEND_REG (port_num), 0);
728 /* Mask RX buffer and TX end interrupt */
729 MV_REG_WRITE (MV64460_ETH_INTERRUPT_MASK_REG (port_num), 0);
730 /* Mask phy and link status changes interrupts */
731 MV_REG_WRITE (MV64460_ETH_INTERRUPT_EXTEND_MASK_REG (port_num), 0);
732 MV_RESET_REG_BITS (MV64460_CPU_INTERRUPT0_MASK_HIGH,
733 BIT0 << port_num);
734 /* Print Network statistics */
Wolfgang Denkdd314e02006-11-30 01:54:07 +0100735#ifndef UPDATE_STATS_BY_SOFTWARE
Stefan Roese45993ea2006-11-29 15:42:37 +0100736 /*
737 * Print statistics (only if ethernet is running),
738 * then zero all the stats fields in memory
739 */
740 if (port_private->eth_running == MAGIC_ETH_RUNNING) {
741 port_private->eth_running = 0;
742 mv64460_eth_print_stat (dev);
743 }
744 memset (port_private->stats, 0, sizeof (struct net_device_stats));
745#endif
746 DP (printf ("\nEthernet stopped ... \n"));
747 return 0;
748}
749
Stefan Roese45993ea2006-11-29 15:42:37 +0100750/**********************************************************************
751 * mv64460_eth_start_xmit
752 *
753 * This function is queues a packet in the Tx descriptor for
754 * required port.
755 *
756 * Input : skb - a pointer to socket buffer
Wolfgang Denkdd314e02006-11-30 01:54:07 +0100757 * dev - a pointer to the required port
Stefan Roese45993ea2006-11-29 15:42:37 +0100758 *
759 * Output : zero upon success
760 **********************************************************************/
761
762int mv64460_eth_xmit (struct eth_device *dev, volatile void *dataPtr,
763 int dataSize)
764{
765 ETH_PORT_INFO *ethernet_private;
766 struct mv64460_eth_priv *port_private;
Stefan Roese45993ea2006-11-29 15:42:37 +0100767 PKT_INFO pkt_info;
768 ETH_FUNC_RET_STATUS status;
769 struct net_device_stats *stats;
770 ETH_FUNC_RET_STATUS release_result;
771
772 ethernet_private = (ETH_PORT_INFO *) dev->priv;
773 port_private =
774 (struct mv64460_eth_priv *) ethernet_private->port_private;
Stefan Roese45993ea2006-11-29 15:42:37 +0100775
776 stats = port_private->stats;
777
778 /* Update packet info data structure */
779 pkt_info.cmd_sts = ETH_TX_FIRST_DESC | ETH_TX_LAST_DESC; /* DMA owned, first last */
780 pkt_info.byte_cnt = dataSize;
781 pkt_info.buf_ptr = (unsigned int) dataPtr;
782 pkt_info.return_info = 0;
783
784 status = eth_port_send (ethernet_private, ETH_Q0, &pkt_info);
785 if ((status == ETH_ERROR) || (status == ETH_QUEUE_FULL)) {
786 printf ("Error on transmitting packet ..");
787 if (status == ETH_QUEUE_FULL)
788 printf ("ETH Queue is full. \n");
789 if (status == ETH_QUEUE_LAST_RESOURCE)
790 printf ("ETH Queue: using last available resource. \n");
Wolfgang Denkdd314e02006-11-30 01:54:07 +0100791 return 1;
Stefan Roese45993ea2006-11-29 15:42:37 +0100792 }
793
794 /* Update statistics and start of transmittion time */
795 stats->tx_bytes += dataSize;
796 stats->tx_packets++;
797
798 /* Check if packet(s) is(are) transmitted correctly (release everything) */
799 do {
800 release_result =
801 eth_tx_return_desc (ethernet_private, ETH_Q0,
802 &pkt_info);
803 switch (release_result) {
804 case ETH_OK:
805 DP (printf ("descriptor released\n"));
806 if (pkt_info.cmd_sts & BIT0) {
807 printf ("Error in TX\n");
808 stats->tx_errors++;
809 }
810 break;
811 case ETH_RETRY:
812 DP (printf ("transmission still in process\n"));
813 break;
814
815 case ETH_ERROR:
816 printf ("routine can not access Tx desc ring\n");
817 break;
818
819 case ETH_END_OF_JOB:
820 DP (printf ("the routine has nothing to release\n"));
821 break;
822 default: /* should not happen */
823 break;
824 }
825 } while (release_result == ETH_OK);
826
Wolfgang Denkdd314e02006-11-30 01:54:07 +0100827 return 0; /* success */
Stefan Roese45993ea2006-11-29 15:42:37 +0100828}
829
830/**********************************************************************
831 * mv64460_eth_receive
832 *
833 * This function is forward packets that are received from the port's
834 * queues toward kernel core or FastRoute them to another interface.
835 *
836 * Input : dev - a pointer to the required interface
Wolfgang Denkdd314e02006-11-30 01:54:07 +0100837 * max - maximum number to receive (0 means unlimted)
Stefan Roese45993ea2006-11-29 15:42:37 +0100838 *
839 * Output : number of served packets
840 **********************************************************************/
841
842int mv64460_eth_receive (struct eth_device *dev)
843{
844 ETH_PORT_INFO *ethernet_private;
845 struct mv64460_eth_priv *port_private;
Stefan Roese45993ea2006-11-29 15:42:37 +0100846 PKT_INFO pkt_info;
847 struct net_device_stats *stats;
848
849 ethernet_private = (ETH_PORT_INFO *) dev->priv;
850 port_private = (struct mv64460_eth_priv *) ethernet_private->port_private;
Stefan Roese45993ea2006-11-29 15:42:37 +0100851 stats = port_private->stats;
852
853 while ((eth_port_receive (ethernet_private, ETH_Q0, &pkt_info) == ETH_OK)) {
854#ifdef DEBUG_MV_ETH
855 if (pkt_info.byte_cnt != 0) {
856 printf ("%s: Received %d byte Packet @ 0x%x\n",
857 __FUNCTION__, pkt_info.byte_cnt,
858 pkt_info.buf_ptr);
859 if(pkt_info.buf_ptr != 0){
860 for(i=0; i < pkt_info.byte_cnt; i++){
861 if((i % 4) == 0){
862 printf("\n0x");
863 }
864 printf("%02x", ((char*)pkt_info.buf_ptr)[i]);
865 }
866 printf("\n");
867 }
868 }
869#endif
870 /* Update statistics. Note byte count includes 4 byte CRC count */
871 stats->rx_packets++;
872 stats->rx_bytes += pkt_info.byte_cnt;
873
874 /*
875 * In case received a packet without first / last bits on OR the error
876 * summary bit is on, the packets needs to be dropeed.
877 */
878 if (((pkt_info.
879 cmd_sts & (ETH_RX_FIRST_DESC | ETH_RX_LAST_DESC)) !=
880 (ETH_RX_FIRST_DESC | ETH_RX_LAST_DESC))
881 || (pkt_info.cmd_sts & ETH_ERROR_SUMMARY)) {
882 stats->rx_dropped++;
883
884 printf ("Received packet spread on multiple descriptors\n");
885
886 /* Is this caused by an error ? */
887 if (pkt_info.cmd_sts & ETH_ERROR_SUMMARY) {
888 stats->rx_errors++;
889 }
890
891 /* free these descriptors again without forwarding them to the higher layers */
892 pkt_info.buf_ptr &= ~0x7; /* realign buffer again */
893 pkt_info.byte_cnt = 0x0000; /* Reset Byte count */
894
895 if (eth_rx_return_buff
896 (ethernet_private, ETH_Q0, &pkt_info) != ETH_OK) {
897 printf ("Error while returning the RX Desc to Ring\n");
898 } else {
899 DP (printf ("RX Desc returned to Ring\n"));
900 }
901 /* /free these descriptors again */
902 } else {
903
904/* !!! call higher layer processing */
905#ifdef DEBUG_MV_ETH
906 printf ("\nNow send it to upper layer protocols (NetReceive) ...\n");
907#endif
908 /* let the upper layer handle the packet */
909 NetReceive ((uchar *) pkt_info.buf_ptr,
910 (int) pkt_info.byte_cnt);
911
912/* **************************************************************** */
913/* free descriptor */
914 pkt_info.buf_ptr &= ~0x7; /* realign buffer again */
915 pkt_info.byte_cnt = 0x0000; /* Reset Byte count */
916 DP (printf ("RX: pkt_info.buf_ptr = %x\n", pkt_info.buf_ptr));
917 if (eth_rx_return_buff
918 (ethernet_private, ETH_Q0, &pkt_info) != ETH_OK) {
919 printf ("Error while returning the RX Desc to Ring\n");
920 } else {
921 DP (printf ("RX: Desc returned to Ring\n"));
922 }
923
924/* **************************************************************** */
925
926 }
927 }
928 mv64460_eth_get_stats (dev); /* update statistics */
929 return 1;
930}
931
932/**********************************************************************
933 * mv64460_eth_get_stats
934 *
935 * Returns a pointer to the interface statistics.
936 *
937 * Input : dev - a pointer to the required interface
938 *
939 * Output : a pointer to the interface's statistics
940 **********************************************************************/
941
942static struct net_device_stats *mv64460_eth_get_stats (struct eth_device *dev)
943{
944 ETH_PORT_INFO *ethernet_private;
945 struct mv64460_eth_priv *port_private;
Stefan Roese45993ea2006-11-29 15:42:37 +0100946
947 ethernet_private = (ETH_PORT_INFO *) dev->priv;
948 port_private =
949 (struct mv64460_eth_priv *) ethernet_private->port_private;
Stefan Roese45993ea2006-11-29 15:42:37 +0100950
951 mv64460_eth_update_stat (dev);
952
953 return port_private->stats;
954}
955
Stefan Roese45993ea2006-11-29 15:42:37 +0100956/**********************************************************************
957 * mv64460_eth_update_stat
958 *
959 * Update the statistics structure in the private data structure
960 *
961 * Input : pointer to ethernet interface network device structure
962 * Output : N/A
963 **********************************************************************/
964
965static void mv64460_eth_update_stat (struct eth_device *dev)
966{
967 ETH_PORT_INFO *ethernet_private;
968 struct mv64460_eth_priv *port_private;
969 struct net_device_stats *stats;
Stefan Roese45993ea2006-11-29 15:42:37 +0100970
971 ethernet_private = (ETH_PORT_INFO *) dev->priv;
972 port_private =
973 (struct mv64460_eth_priv *) ethernet_private->port_private;
Stefan Roese45993ea2006-11-29 15:42:37 +0100974 stats = port_private->stats;
975
976 /* These are false updates */
977 stats->rx_packets += (unsigned long)
978 eth_read_mib_counter (ethernet_private->port_num,
979 ETH_MIB_GOOD_FRAMES_RECEIVED);
980 stats->tx_packets += (unsigned long)
981 eth_read_mib_counter (ethernet_private->port_num,
982 ETH_MIB_GOOD_FRAMES_SENT);
983 stats->rx_bytes += (unsigned long)
984 eth_read_mib_counter (ethernet_private->port_num,
985 ETH_MIB_GOOD_OCTETS_RECEIVED_LOW);
986 /*
987 * Ideally this should be as follows -
988 *
989 * stats->rx_bytes += stats->rx_bytes +
990 * ((unsigned long) ethReadMibCounter (ethernet_private->port_num ,
991 * ETH_MIB_GOOD_OCTETS_RECEIVED_HIGH) << 32);
992 *
993 * But the unsigned long in PowerPC and MIPS are 32bit. So the next read
994 * is just a dummy read for proper work of the GigE port
995 */
Wolfgang Denkb1fe5262011-10-29 09:38:21 +0000996 (void)eth_read_mib_counter (ethernet_private->port_num,
Stefan Roese45993ea2006-11-29 15:42:37 +0100997 ETH_MIB_GOOD_OCTETS_RECEIVED_HIGH);
998 stats->tx_bytes += (unsigned long)
999 eth_read_mib_counter (ethernet_private->port_num,
1000 ETH_MIB_GOOD_OCTETS_SENT_LOW);
Wolfgang Denkb1fe5262011-10-29 09:38:21 +00001001 (void)eth_read_mib_counter (ethernet_private->port_num,
Stefan Roese45993ea2006-11-29 15:42:37 +01001002 ETH_MIB_GOOD_OCTETS_SENT_HIGH);
1003 stats->rx_errors += (unsigned long)
1004 eth_read_mib_counter (ethernet_private->port_num,
1005 ETH_MIB_MAC_RECEIVE_ERROR);
1006
1007 /* Rx dropped is for received packet with CRC error */
1008 stats->rx_dropped +=
1009 (unsigned long) eth_read_mib_counter (ethernet_private->
1010 port_num,
1011 ETH_MIB_BAD_CRC_EVENT);
1012 stats->multicast += (unsigned long)
1013 eth_read_mib_counter (ethernet_private->port_num,
1014 ETH_MIB_MULTICAST_FRAMES_RECEIVED);
1015 stats->collisions +=
1016 (unsigned long) eth_read_mib_counter (ethernet_private->
1017 port_num,
1018 ETH_MIB_COLLISION) +
1019 (unsigned long) eth_read_mib_counter (ethernet_private->
1020 port_num,
1021 ETH_MIB_LATE_COLLISION);
1022 /* detailed rx errors */
1023 stats->rx_length_errors +=
1024 (unsigned long) eth_read_mib_counter (ethernet_private->
1025 port_num,
1026 ETH_MIB_UNDERSIZE_RECEIVED)
1027 +
1028 (unsigned long) eth_read_mib_counter (ethernet_private->
1029 port_num,
1030 ETH_MIB_OVERSIZE_RECEIVED);
1031 /* detailed tx errors */
1032}
1033
Wolfgang Denkdd314e02006-11-30 01:54:07 +01001034#ifndef UPDATE_STATS_BY_SOFTWARE
Stefan Roese45993ea2006-11-29 15:42:37 +01001035/**********************************************************************
1036 * mv64460_eth_print_stat
1037 *
1038 * Update the statistics structure in the private data structure
1039 *
1040 * Input : pointer to ethernet interface network device structure
1041 * Output : N/A
1042 **********************************************************************/
1043
1044static void mv64460_eth_print_stat (struct eth_device *dev)
1045{
1046 ETH_PORT_INFO *ethernet_private;
1047 struct mv64460_eth_priv *port_private;
1048 struct net_device_stats *stats;
Stefan Roese45993ea2006-11-29 15:42:37 +01001049
1050 ethernet_private = (ETH_PORT_INFO *) dev->priv;
1051 port_private =
1052 (struct mv64460_eth_priv *) ethernet_private->port_private;
Stefan Roese45993ea2006-11-29 15:42:37 +01001053 stats = port_private->stats;
1054
1055 /* These are false updates */
1056 printf ("\n### Network statistics: ###\n");
1057 printf ("--------------------------\n");
1058 printf (" Packets received: %ld\n", stats->rx_packets);
1059 printf (" Packets send: %ld\n", stats->tx_packets);
1060 printf (" Received bytes: %ld\n", stats->rx_bytes);
1061 printf (" Send bytes: %ld\n", stats->tx_bytes);
1062 if (stats->rx_errors != 0)
1063 printf (" Rx Errors: %ld\n",
1064 stats->rx_errors);
1065 if (stats->rx_dropped != 0)
1066 printf (" Rx dropped (CRC Errors): %ld\n",
1067 stats->rx_dropped);
1068 if (stats->multicast != 0)
1069 printf (" Rx mulicast frames: %ld\n",
1070 stats->multicast);
1071 if (stats->collisions != 0)
1072 printf (" No. of collisions: %ld\n",
1073 stats->collisions);
1074 if (stats->rx_length_errors != 0)
1075 printf (" Rx length errors: %ld\n",
1076 stats->rx_length_errors);
1077}
1078#endif
1079
1080/**************************************************************************
1081 *network_start - Network Kick Off Routine UBoot
1082 *Inputs :
1083 *Outputs :
1084 **************************************************************************/
1085
1086bool db64460_eth_start (struct eth_device *dev)
1087{
1088 return (mv64460_eth_open (dev)); /* calls real open */
1089}
1090
1091/*************************************************************************
1092**************************************************************************
1093**************************************************************************
Wolfgang Denkdd314e02006-11-30 01:54:07 +01001094* The second part is the low level driver of the gigE ethernet ports. *
Stefan Roese45993ea2006-11-29 15:42:37 +01001095**************************************************************************
1096**************************************************************************
1097*************************************************************************/
1098/*
1099 * based on Linux code
Stefan Roese88fbf932010-04-15 16:07:28 +02001100 * arch/powerpc/galileo/EVB64460/mv64460_eth.c - Driver for MV64460X ethernet ports
Stefan Roese45993ea2006-11-29 15:42:37 +01001101 * Copyright (C) 2002 rabeeh@galileo.co.il
1102
Wolfgang Denkd79de1d2013-07-08 09:37:19 +02001103 * SPDX-License-Identifier: GPL-2.0+
Stefan Roese45993ea2006-11-29 15:42:37 +01001104 */
1105
1106/********************************************************************************
1107 * Marvell's Gigabit Ethernet controller low level driver
1108 *
1109 * DESCRIPTION:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01001110 * This file introduce low level API to Marvell's Gigabit Ethernet
Stefan Roese45993ea2006-11-29 15:42:37 +01001111 * controller. This Gigabit Ethernet Controller driver API controls
1112 * 1) Operations (i.e. port init, start, reset etc').
1113 * 2) Data flow (i.e. port send, receive etc').
1114 * Each Gigabit Ethernet port is controlled via ETH_PORT_INFO
1115 * struct.
1116 * This struct includes user configuration information as well as
1117 * driver internal data needed for its operations.
1118 *
1119 * Supported Features:
1120 * - This low level driver is OS independent. Allocating memory for
1121 * the descriptor rings and buffers are not within the scope of
1122 * this driver.
1123 * - The user is free from Rx/Tx queue managing.
1124 * - This low level driver introduce functionality API that enable
1125 * the to operate Marvell's Gigabit Ethernet Controller in a
1126 * convenient way.
1127 * - Simple Gigabit Ethernet port operation API.
1128 * - Simple Gigabit Ethernet port data flow API.
1129 * - Data flow and operation API support per queue functionality.
1130 * - Support cached descriptors for better performance.
1131 * - Enable access to all four DRAM banks and internal SRAM memory
1132 * spaces.
1133 * - PHY access and control API.
1134 * - Port control register configuration API.
1135 * - Full control over Unicast and Multicast MAC configurations.
1136 *
1137 * Operation flow:
1138 *
1139 * Initialization phase
1140 * This phase complete the initialization of the ETH_PORT_INFO
1141 * struct.
1142 * User information regarding port configuration has to be set
1143 * prior to calling the port initialization routine. For example,
1144 * the user has to assign the port_phy_addr field which is board
1145 * depended parameter.
1146 * In this phase any port Tx/Rx activity is halted, MIB counters
1147 * are cleared, PHY address is set according to user parameter and
1148 * access to DRAM and internal SRAM memory spaces.
1149 *
1150 * Driver ring initialization
1151 * Allocating memory for the descriptor rings and buffers is not
1152 * within the scope of this driver. Thus, the user is required to
1153 * allocate memory for the descriptors ring and buffers. Those
1154 * memory parameters are used by the Rx and Tx ring initialization
1155 * routines in order to curve the descriptor linked list in a form
1156 * of a ring.
1157 * Note: Pay special attention to alignment issues when using
1158 * cached descriptors/buffers. In this phase the driver store
1159 * information in the ETH_PORT_INFO struct regarding each queue
1160 * ring.
1161 *
1162 * Driver start
1163 * This phase prepares the Ethernet port for Rx and Tx activity.
1164 * It uses the information stored in the ETH_PORT_INFO struct to
1165 * initialize the various port registers.
1166 *
1167 * Data flow:
1168 * All packet references to/from the driver are done using PKT_INFO
1169 * struct.
1170 * This struct is a unified struct used with Rx and Tx operations.
1171 * This way the user is not required to be familiar with neither
1172 * Tx nor Rx descriptors structures.
1173 * The driver's descriptors rings are management by indexes.
1174 * Those indexes controls the ring resources and used to indicate
1175 * a SW resource error:
1176 * 'current'
1177 * This index points to the current available resource for use. For
1178 * example in Rx process this index will point to the descriptor
1179 * that will be passed to the user upon calling the receive routine.
1180 * In Tx process, this index will point to the descriptor
1181 * that will be assigned with the user packet info and transmitted.
1182 * 'used'
1183 * This index points to the descriptor that need to restore its
1184 * resources. For example in Rx process, using the Rx buffer return
1185 * API will attach the buffer returned in packet info to the
1186 * descriptor pointed by 'used'. In Tx process, using the Tx
1187 * descriptor return will merely return the user packet info with
1188 * the command status of the transmitted buffer pointed by the
1189 * 'used' index. Nevertheless, it is essential to use this routine
1190 * to update the 'used' index.
1191 * 'first'
1192 * This index supports Tx Scatter-Gather. It points to the first
1193 * descriptor of a packet assembled of multiple buffers. For example
1194 * when in middle of Such packet we have a Tx resource error the
1195 * 'curr' index get the value of 'first' to indicate that the ring
1196 * returned to its state before trying to transmit this packet.
1197 *
1198 * Receive operation:
1199 * The eth_port_receive API set the packet information struct,
1200 * passed by the caller, with received information from the
1201 * 'current' SDMA descriptor.
1202 * It is the user responsibility to return this resource back
1203 * to the Rx descriptor ring to enable the reuse of this source.
1204 * Return Rx resource is done using the eth_rx_return_buff API.
1205 *
1206 * Transmit operation:
1207 * The eth_port_send API supports Scatter-Gather which enables to
1208 * send a packet spanned over multiple buffers. This means that
1209 * for each packet info structure given by the user and put into
1210 * the Tx descriptors ring, will be transmitted only if the 'LAST'
1211 * bit will be set in the packet info command status field. This
1212 * API also consider restriction regarding buffer alignments and
1213 * sizes.
1214 * The user must return a Tx resource after ensuring the buffer
1215 * has been transmitted to enable the Tx ring indexes to update.
1216 *
1217 * BOARD LAYOUT
1218 * This device is on-board. No jumper diagram is necessary.
1219 *
1220 * EXTERNAL INTERFACE
1221 *
Wolfgang Denkdd314e02006-11-30 01:54:07 +01001222 * Prior to calling the initialization routine eth_port_init() the user
Stefan Roese45993ea2006-11-29 15:42:37 +01001223 * must set the following fields under ETH_PORT_INFO struct:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01001224 * port_num User Ethernet port number.
1225 * port_phy_addr User PHY address of Ethernet port.
1226 * port_mac_addr[6] User defined port MAC address.
1227 * port_config User port configuration value.
1228 * port_config_extend User port config extend value.
1229 * port_sdma_config User port SDMA config value.
1230 * port_serial_control User port serial control value.
1231 * *port_virt_to_phys () User function to cast virtual addr to CPU bus addr.
1232 * *port_private User scratch pad for user specific data structures.
Stefan Roese45993ea2006-11-29 15:42:37 +01001233 *
Wolfgang Denkdd314e02006-11-30 01:54:07 +01001234 * This driver introduce a set of default values:
1235 * PORT_CONFIG_VALUE Default port configuration value
1236 * PORT_CONFIG_EXTEND_VALUE Default port extend configuration value
1237 * PORT_SDMA_CONFIG_VALUE Default sdma control value
1238 * PORT_SERIAL_CONTROL_VALUE Default port serial control value
Stefan Roese45993ea2006-11-29 15:42:37 +01001239 *
1240 * This driver data flow is done using the PKT_INFO struct which is
1241 * a unified struct for Rx and Tx operations:
1242 * byte_cnt Tx/Rx descriptor buffer byte count.
1243 * l4i_chk CPU provided TCP Checksum. For Tx operation only.
1244 * cmd_sts Tx/Rx descriptor command status.
1245 * buf_ptr Tx/Rx descriptor buffer pointer.
1246 * return_info Tx/Rx user resource return information.
1247 *
1248 *
1249 * EXTERNAL SUPPORT REQUIREMENTS
1250 *
1251 * This driver requires the following external support:
1252 *
1253 * D_CACHE_FLUSH_LINE (address, address offset)
1254 *
1255 * This macro applies assembly code to flush and invalidate cache
1256 * line.
Wolfgang Denkdd314e02006-11-30 01:54:07 +01001257 * address - address base.
Stefan Roese45993ea2006-11-29 15:42:37 +01001258 * address offset - address offset
1259 *
1260 *
1261 * CPU_PIPE_FLUSH
1262 *
1263 * This macro applies assembly code to flush the CPU pipeline.
1264 *
1265 *******************************************************************************/
1266/* includes */
1267
1268/* defines */
1269/* SDMA command macros */
1270#define ETH_ENABLE_TX_QUEUE(tx_queue, eth_port) \
1271 MV_REG_WRITE(MV64460_ETH_TRANSMIT_QUEUE_COMMAND_REG(eth_port), (1 << tx_queue))
1272
1273#define ETH_DISABLE_TX_QUEUE(tx_queue, eth_port) \
1274 MV_REG_WRITE(MV64460_ETH_TRANSMIT_QUEUE_COMMAND_REG(eth_port),\
1275 (1 << (8 + tx_queue)))
1276
1277#define ETH_ENABLE_RX_QUEUE(rx_queue, eth_port) \
1278MV_REG_WRITE(MV64460_ETH_RECEIVE_QUEUE_COMMAND_REG(eth_port), (1 << rx_queue))
1279
1280#define ETH_DISABLE_RX_QUEUE(rx_queue, eth_port) \
1281MV_REG_WRITE(MV64460_ETH_RECEIVE_QUEUE_COMMAND_REG(eth_port), (1 << (8 + rx_queue)))
1282
1283#define CURR_RFD_GET(p_curr_desc, queue) \
1284 ((p_curr_desc) = p_eth_port_ctrl->p_rx_curr_desc_q[queue])
1285
1286#define CURR_RFD_SET(p_curr_desc, queue) \
1287 (p_eth_port_ctrl->p_rx_curr_desc_q[queue] = (p_curr_desc))
1288
1289#define USED_RFD_GET(p_used_desc, queue) \
1290 ((p_used_desc) = p_eth_port_ctrl->p_rx_used_desc_q[queue])
1291
1292#define USED_RFD_SET(p_used_desc, queue)\
1293(p_eth_port_ctrl->p_rx_used_desc_q[queue] = (p_used_desc))
1294
1295
1296#define CURR_TFD_GET(p_curr_desc, queue) \
1297 ((p_curr_desc) = p_eth_port_ctrl->p_tx_curr_desc_q[queue])
1298
1299#define CURR_TFD_SET(p_curr_desc, queue) \
1300 (p_eth_port_ctrl->p_tx_curr_desc_q[queue] = (p_curr_desc))
1301
1302#define USED_TFD_GET(p_used_desc, queue) \
1303 ((p_used_desc) = p_eth_port_ctrl->p_tx_used_desc_q[queue])
1304
1305#define USED_TFD_SET(p_used_desc, queue) \
1306 (p_eth_port_ctrl->p_tx_used_desc_q[queue] = (p_used_desc))
1307
1308#define FIRST_TFD_GET(p_first_desc, queue) \
1309 ((p_first_desc) = p_eth_port_ctrl->p_tx_first_desc_q[queue])
1310
1311#define FIRST_TFD_SET(p_first_desc, queue) \
1312 (p_eth_port_ctrl->p_tx_first_desc_q[queue] = (p_first_desc))
1313
1314
1315/* Macros that save access to desc in order to find next desc pointer */
1316#define RX_NEXT_DESC_PTR(p_rx_desc, queue) (ETH_RX_DESC*)(((((unsigned int)p_rx_desc - (unsigned int)p_eth_port_ctrl->p_rx_desc_area_base[queue]) + RX_DESC_ALIGNED_SIZE) % p_eth_port_ctrl->rx_desc_area_size[queue]) + (unsigned int)p_eth_port_ctrl->p_rx_desc_area_base[queue])
1317
1318#define TX_NEXT_DESC_PTR(p_tx_desc, queue) (ETH_TX_DESC*)(((((unsigned int)p_tx_desc - (unsigned int)p_eth_port_ctrl->p_tx_desc_area_base[queue]) + TX_DESC_ALIGNED_SIZE) % p_eth_port_ctrl->tx_desc_area_size[queue]) + (unsigned int)p_eth_port_ctrl->p_tx_desc_area_base[queue])
1319
1320#define LINK_UP_TIMEOUT 100000
1321#define PHY_BUSY_TIMEOUT 10000000
1322
1323/* locals */
1324
1325/* PHY routines */
1326static void ethernet_phy_set (ETH_PORT eth_port_num, int phy_addr);
1327static int ethernet_phy_get (ETH_PORT eth_port_num);
1328
1329/* Ethernet Port routines */
1330static void eth_set_access_control (ETH_PORT eth_port_num,
1331 ETH_WIN_PARAM * param);
1332static bool eth_port_uc_addr (ETH_PORT eth_port_num, unsigned char uc_nibble,
1333 ETH_QUEUE queue, int option);
1334#if 0 /* FIXME */
1335static bool eth_port_smc_addr (ETH_PORT eth_port_num,
1336 unsigned char mc_byte,
1337 ETH_QUEUE queue, int option);
1338static bool eth_port_omc_addr (ETH_PORT eth_port_num,
1339 unsigned char crc8,
1340 ETH_QUEUE queue, int option);
1341#endif
1342
1343static void eth_b_copy (unsigned int src_addr, unsigned int dst_addr,
1344 int byte_count);
1345
1346void eth_dbg (ETH_PORT_INFO * p_eth_port_ctrl);
1347
1348
1349typedef enum _memory_bank { BANK0, BANK1, BANK2, BANK3 } MEMORY_BANK;
1350u32 mv_get_dram_bank_base_addr (MEMORY_BANK bank)
1351{
1352 u32 result = 0;
1353 u32 enable = MV_REG_READ (MV64460_BASE_ADDR_ENABLE);
1354
1355 if (enable & (1 << bank))
1356 return 0;
1357 if (bank == BANK0)
1358 result = MV_REG_READ (MV64460_CS_0_BASE_ADDR);
1359 if (bank == BANK1)
1360 result = MV_REG_READ (MV64460_CS_1_BASE_ADDR);
1361 if (bank == BANK2)
1362 result = MV_REG_READ (MV64460_CS_2_BASE_ADDR);
1363 if (bank == BANK3)
1364 result = MV_REG_READ (MV64460_CS_3_BASE_ADDR);
1365 result &= 0x0000ffff;
1366 result = result << 16;
1367 return result;
1368}
1369
1370u32 mv_get_dram_bank_size (MEMORY_BANK bank)
1371{
1372 u32 result = 0;
1373 u32 enable = MV_REG_READ (MV64460_BASE_ADDR_ENABLE);
1374
1375 if (enable & (1 << bank))
1376 return 0;
1377 if (bank == BANK0)
1378 result = MV_REG_READ (MV64460_CS_0_SIZE);
1379 if (bank == BANK1)
1380 result = MV_REG_READ (MV64460_CS_1_SIZE);
1381 if (bank == BANK2)
1382 result = MV_REG_READ (MV64460_CS_2_SIZE);
1383 if (bank == BANK3)
1384 result = MV_REG_READ (MV64460_CS_3_SIZE);
1385 result += 1;
1386 result &= 0x0000ffff;
1387 result = result << 16;
1388 return result;
1389}
1390
1391u32 mv_get_internal_sram_base (void)
1392{
1393 u32 result;
1394
1395 result = MV_REG_READ (MV64460_INTEGRATED_SRAM_BASE_ADDR);
1396 result &= 0x0000ffff;
1397 result = result << 16;
1398 return result;
1399}
1400
1401/*******************************************************************************
1402* eth_port_init - Initialize the Ethernet port driver
1403*
1404* DESCRIPTION:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01001405* This function prepares the ethernet port to start its activity:
1406* 1) Completes the ethernet port driver struct initialization toward port
1407* start routine.
1408* 2) Resets the device to a quiescent state in case of warm reboot.
1409* 3) Enable SDMA access to all four DRAM banks as well as internal SRAM.
1410* 4) Clean MAC tables. The reset status of those tables is unknown.
1411* 5) Set PHY address.
1412* Note: Call this routine prior to eth_port_start routine and after setting
1413* user values in the user fields of Ethernet port control struct (i.e.
1414* port_phy_addr).
Stefan Roese45993ea2006-11-29 15:42:37 +01001415*
1416* INPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01001417* ETH_PORT_INFO *p_eth_port_ctrl Ethernet port control struct
Stefan Roese45993ea2006-11-29 15:42:37 +01001418*
1419* OUTPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01001420* See description.
Stefan Roese45993ea2006-11-29 15:42:37 +01001421*
1422* RETURN:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01001423* None.
Stefan Roese45993ea2006-11-29 15:42:37 +01001424*
1425*******************************************************************************/
1426static void eth_port_init (ETH_PORT_INFO * p_eth_port_ctrl)
1427{
1428 int queue;
1429 ETH_WIN_PARAM win_param;
1430
1431 p_eth_port_ctrl->port_config = PORT_CONFIG_VALUE;
1432 p_eth_port_ctrl->port_config_extend = PORT_CONFIG_EXTEND_VALUE;
1433 p_eth_port_ctrl->port_sdma_config = PORT_SDMA_CONFIG_VALUE;
1434 p_eth_port_ctrl->port_serial_control = PORT_SERIAL_CONTROL_VALUE;
1435
1436 p_eth_port_ctrl->port_rx_queue_command = 0;
1437 p_eth_port_ctrl->port_tx_queue_command = 0;
1438
1439 /* Zero out SW structs */
1440 for (queue = 0; queue < MAX_RX_QUEUE_NUM; queue++) {
1441 CURR_RFD_SET ((ETH_RX_DESC *) 0x00000000, queue);
1442 USED_RFD_SET ((ETH_RX_DESC *) 0x00000000, queue);
1443 p_eth_port_ctrl->rx_resource_err[queue] = false;
1444 }
1445
1446 for (queue = 0; queue < MAX_TX_QUEUE_NUM; queue++) {
1447 CURR_TFD_SET ((ETH_TX_DESC *) 0x00000000, queue);
1448 USED_TFD_SET ((ETH_TX_DESC *) 0x00000000, queue);
1449 FIRST_TFD_SET ((ETH_TX_DESC *) 0x00000000, queue);
1450 p_eth_port_ctrl->tx_resource_err[queue] = false;
1451 }
1452
1453 eth_port_reset (p_eth_port_ctrl->port_num);
1454
1455 /* Set access parameters for DRAM bank 0 */
1456 win_param.win = ETH_WIN0; /* Use Ethernet window 0 */
Wolfgang Denkdd314e02006-11-30 01:54:07 +01001457 win_param.target = ETH_TARGET_DRAM; /* Window target - DDR */
Stefan Roese45993ea2006-11-29 15:42:37 +01001458 win_param.attributes = EBAR_ATTR_DRAM_CS0; /* Enable DRAM bank */
1459#ifndef CONFIG_NOT_COHERENT_CACHE
1460 win_param.attributes |= EBAR_ATTR_DRAM_CACHE_COHERENCY_WB;
1461#endif
1462 win_param.high_addr = 0;
1463 /* Get bank base */
1464 win_param.base_addr = mv_get_dram_bank_base_addr (BANK0);
Wolfgang Denkdd314e02006-11-30 01:54:07 +01001465 win_param.size = mv_get_dram_bank_size (BANK0); /* Get bank size */
Stefan Roese45993ea2006-11-29 15:42:37 +01001466 if (win_param.size == 0)
1467 win_param.enable = 0;
1468 else
1469 win_param.enable = 1; /* Enable the access */
1470 win_param.access_ctrl = EWIN_ACCESS_FULL; /* Enable full access */
1471
1472 /* Set the access control for address window (EPAPR) READ & WRITE */
1473 eth_set_access_control (p_eth_port_ctrl->port_num, &win_param);
1474
1475 /* Set access parameters for DRAM bank 1 */
1476 win_param.win = ETH_WIN1; /* Use Ethernet window 1 */
1477 win_param.target = ETH_TARGET_DRAM; /* Window target - DDR */
1478 win_param.attributes = EBAR_ATTR_DRAM_CS1; /* Enable DRAM bank */
1479#ifndef CONFIG_NOT_COHERENT_CACHE
1480 win_param.attributes |= EBAR_ATTR_DRAM_CACHE_COHERENCY_WB;
1481#endif
1482 win_param.high_addr = 0;
1483 /* Get bank base */
1484 win_param.base_addr = mv_get_dram_bank_base_addr (BANK1);
Wolfgang Denkdd314e02006-11-30 01:54:07 +01001485 win_param.size = mv_get_dram_bank_size (BANK1); /* Get bank size */
Stefan Roese45993ea2006-11-29 15:42:37 +01001486 if (win_param.size == 0)
1487 win_param.enable = 0;
1488 else
1489 win_param.enable = 1; /* Enable the access */
1490 win_param.access_ctrl = EWIN_ACCESS_FULL; /* Enable full access */
1491
1492 /* Set the access control for address window (EPAPR) READ & WRITE */
1493 eth_set_access_control (p_eth_port_ctrl->port_num, &win_param);
1494
1495 /* Set access parameters for DRAM bank 2 */
1496 win_param.win = ETH_WIN2; /* Use Ethernet window 2 */
1497 win_param.target = ETH_TARGET_DRAM; /* Window target - DDR */
1498 win_param.attributes = EBAR_ATTR_DRAM_CS2; /* Enable DRAM bank */
1499#ifndef CONFIG_NOT_COHERENT_CACHE
1500 win_param.attributes |= EBAR_ATTR_DRAM_CACHE_COHERENCY_WB;
1501#endif
1502 win_param.high_addr = 0;
1503 /* Get bank base */
1504 win_param.base_addr = mv_get_dram_bank_base_addr (BANK2);
Wolfgang Denkdd314e02006-11-30 01:54:07 +01001505 win_param.size = mv_get_dram_bank_size (BANK2); /* Get bank size */
Stefan Roese45993ea2006-11-29 15:42:37 +01001506 if (win_param.size == 0)
1507 win_param.enable = 0;
1508 else
1509 win_param.enable = 1; /* Enable the access */
1510 win_param.access_ctrl = EWIN_ACCESS_FULL; /* Enable full access */
1511
1512 /* Set the access control for address window (EPAPR) READ & WRITE */
1513 eth_set_access_control (p_eth_port_ctrl->port_num, &win_param);
1514
1515 /* Set access parameters for DRAM bank 3 */
1516 win_param.win = ETH_WIN3; /* Use Ethernet window 3 */
1517 win_param.target = ETH_TARGET_DRAM; /* Window target - DDR */
1518 win_param.attributes = EBAR_ATTR_DRAM_CS3; /* Enable DRAM bank */
1519#ifndef CONFIG_NOT_COHERENT_CACHE
1520 win_param.attributes |= EBAR_ATTR_DRAM_CACHE_COHERENCY_WB;
1521#endif
1522 win_param.high_addr = 0;
1523 /* Get bank base */
1524 win_param.base_addr = mv_get_dram_bank_base_addr (BANK3);
Wolfgang Denkdd314e02006-11-30 01:54:07 +01001525 win_param.size = mv_get_dram_bank_size (BANK3); /* Get bank size */
Stefan Roese45993ea2006-11-29 15:42:37 +01001526 if (win_param.size == 0)
1527 win_param.enable = 0;
1528 else
1529 win_param.enable = 1; /* Enable the access */
1530 win_param.access_ctrl = EWIN_ACCESS_FULL; /* Enable full access */
1531
1532 /* Set the access control for address window (EPAPR) READ & WRITE */
1533 eth_set_access_control (p_eth_port_ctrl->port_num, &win_param);
1534
1535 /* Set access parameters for Internal SRAM */
1536 win_param.win = ETH_WIN4; /* Use Ethernet window 0 */
1537 win_param.target = EBAR_TARGET_CBS; /* Target - Internal SRAM */
1538 win_param.attributes = EBAR_ATTR_CBS_SRAM | EBAR_ATTR_CBS_SRAM_BLOCK0;
1539 win_param.high_addr = 0;
1540 win_param.base_addr = mv_get_internal_sram_base (); /* Get base addr */
1541 win_param.size = MV64460_INTERNAL_SRAM_SIZE; /* Get bank size */
1542 win_param.enable = 1; /* Enable the access */
1543 win_param.access_ctrl = EWIN_ACCESS_FULL; /* Enable full access */
1544
1545 /* Set the access control for address window (EPAPR) READ & WRITE */
1546 eth_set_access_control (p_eth_port_ctrl->port_num, &win_param);
1547
1548 eth_port_init_mac_tables (p_eth_port_ctrl->port_num);
1549
1550 ethernet_phy_set (p_eth_port_ctrl->port_num,
1551 p_eth_port_ctrl->port_phy_addr);
1552
1553 return;
1554
1555}
1556
1557/*******************************************************************************
1558* eth_port_start - Start the Ethernet port activity.
1559*
1560* DESCRIPTION:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01001561* This routine prepares the Ethernet port for Rx and Tx activity:
1562* 1. Initialize Tx and Rx Current Descriptor Pointer for each queue that
1563* has been initialized a descriptor's ring (using ether_init_tx_desc_ring
1564* for Tx and ether_init_rx_desc_ring for Rx)
1565* 2. Initialize and enable the Ethernet configuration port by writing to
1566* the port's configuration and command registers.
1567* 3. Initialize and enable the SDMA by writing to the SDMA's
Stefan Roese45993ea2006-11-29 15:42:37 +01001568* configuration and command registers.
Wolfgang Denkdd314e02006-11-30 01:54:07 +01001569* After completing these steps, the ethernet port SDMA can starts to
1570* perform Rx and Tx activities.
Stefan Roese45993ea2006-11-29 15:42:37 +01001571*
Wolfgang Denkdd314e02006-11-30 01:54:07 +01001572* Note: Each Rx and Tx queue descriptor's list must be initialized prior
1573* to calling this function (use ether_init_tx_desc_ring for Tx queues and
1574* ether_init_rx_desc_ring for Rx queues).
Stefan Roese45993ea2006-11-29 15:42:37 +01001575*
1576* INPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01001577* ETH_PORT_INFO *p_eth_port_ctrl Ethernet port control struct
Stefan Roese45993ea2006-11-29 15:42:37 +01001578*
1579* OUTPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01001580* Ethernet port is ready to receive and transmit.
Stefan Roese45993ea2006-11-29 15:42:37 +01001581*
1582* RETURN:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01001583* false if the port PHY is not up.
1584* true otherwise.
Stefan Roese45993ea2006-11-29 15:42:37 +01001585*
1586*******************************************************************************/
1587static bool eth_port_start (ETH_PORT_INFO * p_eth_port_ctrl)
1588{
1589 int queue;
1590 volatile ETH_TX_DESC *p_tx_curr_desc;
1591 volatile ETH_RX_DESC *p_rx_curr_desc;
1592 unsigned int phy_reg_data;
1593 ETH_PORT eth_port_num = p_eth_port_ctrl->port_num;
1594
Stefan Roese45993ea2006-11-29 15:42:37 +01001595 /* Assignment of Tx CTRP of given queue */
1596 for (queue = 0; queue < MAX_TX_QUEUE_NUM; queue++) {
1597 CURR_TFD_GET (p_tx_curr_desc, queue);
1598 MV_REG_WRITE ((MV64460_ETH_TX_CURRENT_QUEUE_DESC_PTR_0
1599 (eth_port_num)
1600 + (4 * queue)),
1601 ((unsigned int) p_tx_curr_desc));
1602
1603 }
1604
1605 /* Assignment of Rx CRDP of given queue */
1606 for (queue = 0; queue < MAX_RX_QUEUE_NUM; queue++) {
1607 CURR_RFD_GET (p_rx_curr_desc, queue);
1608 MV_REG_WRITE ((MV64460_ETH_RX_CURRENT_QUEUE_DESC_PTR_0
1609 (eth_port_num)
1610 + (4 * queue)),
1611 ((unsigned int) p_rx_curr_desc));
1612
1613 if (p_rx_curr_desc != NULL)
1614 /* Add the assigned Ethernet address to the port's address table */
1615 eth_port_uc_addr_set (p_eth_port_ctrl->port_num,
1616 p_eth_port_ctrl->port_mac_addr,
1617 queue);
1618 }
1619
1620 /* Assign port configuration and command. */
1621 MV_REG_WRITE (MV64460_ETH_PORT_CONFIG_REG (eth_port_num),
1622 p_eth_port_ctrl->port_config);
1623
1624 MV_REG_WRITE (MV64460_ETH_PORT_CONFIG_EXTEND_REG (eth_port_num),
1625 p_eth_port_ctrl->port_config_extend);
1626
1627 MV_REG_WRITE (MV64460_ETH_PORT_SERIAL_CONTROL_REG (eth_port_num),
1628 p_eth_port_ctrl->port_serial_control);
1629
1630 MV_SET_REG_BITS (MV64460_ETH_PORT_SERIAL_CONTROL_REG (eth_port_num),
1631 ETH_SERIAL_PORT_ENABLE);
1632
1633 /* Assign port SDMA configuration */
1634 MV_REG_WRITE (MV64460_ETH_SDMA_CONFIG_REG (eth_port_num),
1635 p_eth_port_ctrl->port_sdma_config);
1636
1637 MV_REG_WRITE (MV64460_ETH_TX_QUEUE_0_TOKEN_BUCKET_COUNT
1638 (eth_port_num), 0x3fffffff);
1639 MV_REG_WRITE (MV64460_ETH_TX_QUEUE_0_TOKEN_BUCKET_CONFIG
1640 (eth_port_num), 0x03fffcff);
1641 /* Turn off the port/queue bandwidth limitation */
1642 MV_REG_WRITE (MV64460_ETH_MAXIMUM_TRANSMIT_UNIT (eth_port_num), 0x0);
1643
1644 /* Enable port Rx. */
1645 MV_REG_WRITE (MV64460_ETH_RECEIVE_QUEUE_COMMAND_REG (eth_port_num),
1646 p_eth_port_ctrl->port_rx_queue_command);
1647
1648 /* Check if link is up */
1649 eth_port_read_smi_reg (eth_port_num, 1, &phy_reg_data);
1650
1651 if (!(phy_reg_data & 0x20))
1652 return false;
1653
1654 return true;
1655}
1656
1657/*******************************************************************************
1658* eth_port_uc_addr_set - This function Set the port Unicast address.
1659*
1660* DESCRIPTION:
1661* This function Set the port Ethernet MAC address.
1662*
1663* INPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01001664* ETH_PORT eth_port_num Port number.
1665* char * p_addr Address to be set
1666* ETH_QUEUE queue Rx queue number for this MAC address.
Stefan Roese45993ea2006-11-29 15:42:37 +01001667*
1668* OUTPUT:
1669* Set MAC address low and high registers. also calls eth_port_uc_addr()
Wolfgang Denkdd314e02006-11-30 01:54:07 +01001670* To set the unicast table with the proper information.
Stefan Roese45993ea2006-11-29 15:42:37 +01001671*
1672* RETURN:
1673* N/A.
1674*
1675*******************************************************************************/
1676static void eth_port_uc_addr_set (ETH_PORT eth_port_num,
1677 unsigned char *p_addr, ETH_QUEUE queue)
1678{
1679 unsigned int mac_h;
1680 unsigned int mac_l;
1681
1682 mac_l = (p_addr[4] << 8) | (p_addr[5]);
1683 mac_h = (p_addr[0] << 24) | (p_addr[1] << 16) |
1684 (p_addr[2] << 8) | (p_addr[3] << 0);
1685
1686 MV_REG_WRITE (MV64460_ETH_MAC_ADDR_LOW (eth_port_num), mac_l);
1687 MV_REG_WRITE (MV64460_ETH_MAC_ADDR_HIGH (eth_port_num), mac_h);
1688
1689 /* Accept frames of this address */
1690 eth_port_uc_addr (eth_port_num, p_addr[5], queue, ACCEPT_MAC_ADDR);
1691
1692 return;
1693}
1694
1695/*******************************************************************************
1696* eth_port_uc_addr - This function Set the port unicast address table
1697*
1698* DESCRIPTION:
1699* This function locates the proper entry in the Unicast table for the
1700* specified MAC nibble and sets its properties according to function
1701* parameters.
1702*
1703* INPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01001704* ETH_PORT eth_port_num Port number.
Stefan Roese45993ea2006-11-29 15:42:37 +01001705* unsigned char uc_nibble Unicast MAC Address last nibble.
Wolfgang Denkdd314e02006-11-30 01:54:07 +01001706* ETH_QUEUE queue Rx queue number for this MAC address.
1707* int option 0 = Add, 1 = remove address.
Stefan Roese45993ea2006-11-29 15:42:37 +01001708*
1709* OUTPUT:
1710* This function add/removes MAC addresses from the port unicast address
1711* table.
1712*
1713* RETURN:
1714* true is output succeeded.
1715* false if option parameter is invalid.
1716*
1717*******************************************************************************/
1718static bool eth_port_uc_addr (ETH_PORT eth_port_num,
1719 unsigned char uc_nibble,
1720 ETH_QUEUE queue, int option)
1721{
1722 unsigned int unicast_reg;
1723 unsigned int tbl_offset;
1724 unsigned int reg_offset;
1725
1726 /* Locate the Unicast table entry */
1727 uc_nibble = (0xf & uc_nibble);
1728 tbl_offset = (uc_nibble / 4) * 4; /* Register offset from unicast table base */
1729 reg_offset = uc_nibble % 4; /* Entry offset within the above register */
1730
1731 switch (option) {
1732 case REJECT_MAC_ADDR:
1733 /* Clear accepts frame bit at specified unicast DA table entry */
1734 unicast_reg =
1735 MV_REG_READ ((MV64460_ETH_DA_FILTER_UNICAST_TABLE_BASE
1736 (eth_port_num)
1737 + tbl_offset));
1738
1739 unicast_reg &= (0x0E << (8 * reg_offset));
1740
1741 MV_REG_WRITE ((MV64460_ETH_DA_FILTER_UNICAST_TABLE_BASE
1742 (eth_port_num)
1743 + tbl_offset), unicast_reg);
1744 break;
1745
1746 case ACCEPT_MAC_ADDR:
1747 /* Set accepts frame bit at unicast DA filter table entry */
1748 unicast_reg =
1749 MV_REG_READ ((MV64460_ETH_DA_FILTER_UNICAST_TABLE_BASE
1750 (eth_port_num)
1751 + tbl_offset));
1752
1753 unicast_reg |= ((0x01 | queue) << (8 * reg_offset));
1754
1755 MV_REG_WRITE ((MV64460_ETH_DA_FILTER_UNICAST_TABLE_BASE
1756 (eth_port_num)
1757 + tbl_offset), unicast_reg);
1758
1759 break;
1760
1761 default:
1762 return false;
1763 }
1764 return true;
1765}
1766
1767#if 0 /* FIXME */
1768/*******************************************************************************
1769* eth_port_mc_addr - Multicast address settings.
1770*
1771* DESCRIPTION:
1772* This API controls the MV device MAC multicast support.
1773* The MV device supports multicast using two tables:
1774* 1) Special Multicast Table for MAC addresses of the form
1775* 0x01-00-5E-00-00-XX (where XX is between 0x00 and 0x_fF).
1776* The MAC DA[7:0] bits are used as a pointer to the Special Multicast
1777* Table entries in the DA-Filter table.
1778* In this case, the function calls eth_port_smc_addr() routine to set the
1779* Special Multicast Table.
1780* 2) Other Multicast Table for multicast of another type. A CRC-8bit
1781* is used as an index to the Other Multicast Table entries in the
1782* DA-Filter table.
1783* In this case, the function calculates the CRC-8bit value and calls
1784* eth_port_omc_addr() routine to set the Other Multicast Table.
1785* INPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01001786* ETH_PORT eth_port_num Port number.
1787* unsigned char *p_addr Unicast MAC Address.
1788* ETH_QUEUE queue Rx queue number for this MAC address.
1789* int option 0 = Add, 1 = remove address.
Stefan Roese45993ea2006-11-29 15:42:37 +01001790*
1791* OUTPUT:
1792* See description.
1793*
1794* RETURN:
1795* true is output succeeded.
1796* false if add_address_table_entry( ) failed.
1797*
1798*******************************************************************************/
1799static void eth_port_mc_addr (ETH_PORT eth_port_num,
1800 unsigned char *p_addr,
1801 ETH_QUEUE queue, int option)
1802{
1803 unsigned int mac_h;
1804 unsigned int mac_l;
1805 unsigned char crc_result = 0;
1806 int mac_array[48];
1807 int crc[8];
1808 int i;
1809
Stefan Roese45993ea2006-11-29 15:42:37 +01001810 if ((p_addr[0] == 0x01) &&
1811 (p_addr[1] == 0x00) &&
Wolfgang Denkdd314e02006-11-30 01:54:07 +01001812 (p_addr[2] == 0x5E) && (p_addr[3] == 0x00) && (p_addr[4] == 0x00)) {
Stefan Roese45993ea2006-11-29 15:42:37 +01001813
1814 eth_port_smc_addr (eth_port_num, p_addr[5], queue, option);
Wolfgang Denkdd314e02006-11-30 01:54:07 +01001815 } else {
Stefan Roese45993ea2006-11-29 15:42:37 +01001816 /* Calculate CRC-8 out of the given address */
1817 mac_h = (p_addr[0] << 8) | (p_addr[1]);
1818 mac_l = (p_addr[2] << 24) | (p_addr[3] << 16) |
1819 (p_addr[4] << 8) | (p_addr[5] << 0);
1820
1821 for (i = 0; i < 32; i++)
1822 mac_array[i] = (mac_l >> i) & 0x1;
1823 for (i = 32; i < 48; i++)
1824 mac_array[i] = (mac_h >> (i - 32)) & 0x1;
1825
Stefan Roese45993ea2006-11-29 15:42:37 +01001826 crc[0] = mac_array[45] ^ mac_array[43] ^ mac_array[40] ^
1827 mac_array[39] ^ mac_array[35] ^ mac_array[34] ^
1828 mac_array[31] ^ mac_array[30] ^ mac_array[28] ^
1829 mac_array[23] ^ mac_array[21] ^ mac_array[19] ^
1830 mac_array[18] ^ mac_array[16] ^ mac_array[14] ^
1831 mac_array[12] ^ mac_array[8] ^ mac_array[7] ^
1832 mac_array[6] ^ mac_array[0];
1833
1834 crc[1] = mac_array[46] ^ mac_array[45] ^ mac_array[44] ^
1835 mac_array[43] ^ mac_array[41] ^ mac_array[39] ^
1836 mac_array[36] ^ mac_array[34] ^ mac_array[32] ^
1837 mac_array[30] ^ mac_array[29] ^ mac_array[28] ^
1838 mac_array[24] ^ mac_array[23] ^ mac_array[22] ^
1839 mac_array[21] ^ mac_array[20] ^ mac_array[18] ^
1840 mac_array[17] ^ mac_array[16] ^ mac_array[15] ^
1841 mac_array[14] ^ mac_array[13] ^ mac_array[12] ^
1842 mac_array[9] ^ mac_array[6] ^ mac_array[1] ^
1843 mac_array[0];
1844
1845 crc[2] = mac_array[47] ^ mac_array[46] ^ mac_array[44] ^
1846 mac_array[43] ^ mac_array[42] ^ mac_array[39] ^
1847 mac_array[37] ^ mac_array[34] ^ mac_array[33] ^
1848 mac_array[29] ^ mac_array[28] ^ mac_array[25] ^
1849 mac_array[24] ^ mac_array[22] ^ mac_array[17] ^
1850 mac_array[15] ^ mac_array[13] ^ mac_array[12] ^
1851 mac_array[10] ^ mac_array[8] ^ mac_array[6] ^
1852 mac_array[2] ^ mac_array[1] ^ mac_array[0];
1853
1854 crc[3] = mac_array[47] ^ mac_array[45] ^ mac_array[44] ^
1855 mac_array[43] ^ mac_array[40] ^ mac_array[38] ^
1856 mac_array[35] ^ mac_array[34] ^ mac_array[30] ^
1857 mac_array[29] ^ mac_array[26] ^ mac_array[25] ^
1858 mac_array[23] ^ mac_array[18] ^ mac_array[16] ^
1859 mac_array[14] ^ mac_array[13] ^ mac_array[11] ^
1860 mac_array[9] ^ mac_array[7] ^ mac_array[3] ^
1861 mac_array[2] ^ mac_array[1];
1862
1863 crc[4] = mac_array[46] ^ mac_array[45] ^ mac_array[44] ^
1864 mac_array[41] ^ mac_array[39] ^ mac_array[36] ^
1865 mac_array[35] ^ mac_array[31] ^ mac_array[30] ^
1866 mac_array[27] ^ mac_array[26] ^ mac_array[24] ^
1867 mac_array[19] ^ mac_array[17] ^ mac_array[15] ^
1868 mac_array[14] ^ mac_array[12] ^ mac_array[10] ^
1869 mac_array[8] ^ mac_array[4] ^ mac_array[3] ^
1870 mac_array[2];
1871
1872 crc[5] = mac_array[47] ^ mac_array[46] ^ mac_array[45] ^
1873 mac_array[42] ^ mac_array[40] ^ mac_array[37] ^
1874 mac_array[36] ^ mac_array[32] ^ mac_array[31] ^
1875 mac_array[28] ^ mac_array[27] ^ mac_array[25] ^
1876 mac_array[20] ^ mac_array[18] ^ mac_array[16] ^
1877 mac_array[15] ^ mac_array[13] ^ mac_array[11] ^
1878 mac_array[9] ^ mac_array[5] ^ mac_array[4] ^
1879 mac_array[3];
1880
1881 crc[6] = mac_array[47] ^ mac_array[46] ^ mac_array[43] ^
1882 mac_array[41] ^ mac_array[38] ^ mac_array[37] ^
1883 mac_array[33] ^ mac_array[32] ^ mac_array[29] ^
1884 mac_array[28] ^ mac_array[26] ^ mac_array[21] ^
1885 mac_array[19] ^ mac_array[17] ^ mac_array[16] ^
1886 mac_array[14] ^ mac_array[12] ^ mac_array[10] ^
1887 mac_array[6] ^ mac_array[5] ^ mac_array[4];
1888
1889 crc[7] = mac_array[47] ^ mac_array[44] ^ mac_array[42] ^
1890 mac_array[39] ^ mac_array[38] ^ mac_array[34] ^
1891 mac_array[33] ^ mac_array[30] ^ mac_array[29] ^
1892 mac_array[27] ^ mac_array[22] ^ mac_array[20] ^
1893 mac_array[18] ^ mac_array[17] ^ mac_array[15] ^
1894 mac_array[13] ^ mac_array[11] ^ mac_array[7] ^
1895 mac_array[6] ^ mac_array[5];
1896
1897 for (i = 0; i < 8; i++)
1898 crc_result = crc_result | (crc[i] << i);
1899
1900 eth_port_omc_addr (eth_port_num, crc_result, queue, option);
1901 }
1902 return;
1903}
1904
1905/*******************************************************************************
1906* eth_port_smc_addr - Special Multicast address settings.
1907*
1908* DESCRIPTION:
1909* This routine controls the MV device special MAC multicast support.
1910* The Special Multicast Table for MAC addresses supports MAC of the form
1911* 0x01-00-5E-00-00-XX (where XX is between 0x00 and 0x_fF).
1912* The MAC DA[7:0] bits are used as a pointer to the Special Multicast
1913* Table entries in the DA-Filter table.
1914* This function set the Special Multicast Table appropriate entry
1915* according to the argument given.
1916*
1917* INPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01001918* ETH_PORT eth_port_num Port number.
1919* unsigned char mc_byte Multicast addr last byte (MAC DA[7:0] bits).
1920* ETH_QUEUE queue Rx queue number for this MAC address.
1921* int option 0 = Add, 1 = remove address.
Stefan Roese45993ea2006-11-29 15:42:37 +01001922*
1923* OUTPUT:
1924* See description.
1925*
1926* RETURN:
1927* true is output succeeded.
1928* false if option parameter is invalid.
1929*
1930*******************************************************************************/
1931static bool eth_port_smc_addr (ETH_PORT eth_port_num,
1932 unsigned char mc_byte,
1933 ETH_QUEUE queue, int option)
1934{
1935 unsigned int smc_table_reg;
1936 unsigned int tbl_offset;
1937 unsigned int reg_offset;
1938
1939 /* Locate the SMC table entry */
Wolfgang Denkdd314e02006-11-30 01:54:07 +01001940 tbl_offset = (mc_byte / 4) * 4; /* Register offset from SMC table base */
Stefan Roese45993ea2006-11-29 15:42:37 +01001941 reg_offset = mc_byte % 4; /* Entry offset within the above register */
1942 queue &= 0x7;
1943
1944 switch (option) {
1945 case REJECT_MAC_ADDR:
1946 /* Clear accepts frame bit at specified Special DA table entry */
1947 smc_table_reg =
1948 MV_REG_READ ((MV64460_ETH_DA_FILTER_SPECIAL_MULTICAST_TABLE_BASE (eth_port_num) + tbl_offset));
1949 smc_table_reg &= (0x0E << (8 * reg_offset));
1950
1951 MV_REG_WRITE ((MV64460_ETH_DA_FILTER_SPECIAL_MULTICAST_TABLE_BASE (eth_port_num) + tbl_offset), smc_table_reg);
1952 break;
1953
1954 case ACCEPT_MAC_ADDR:
1955 /* Set accepts frame bit at specified Special DA table entry */
1956 smc_table_reg =
1957 MV_REG_READ ((MV64460_ETH_DA_FILTER_SPECIAL_MULTICAST_TABLE_BASE (eth_port_num) + tbl_offset));
1958 smc_table_reg |= ((0x01 | queue) << (8 * reg_offset));
1959
1960 MV_REG_WRITE ((MV64460_ETH_DA_FILTER_SPECIAL_MULTICAST_TABLE_BASE (eth_port_num) + tbl_offset), smc_table_reg);
1961 break;
1962
1963 default:
1964 return false;
1965 }
1966 return true;
1967}
1968
1969/*******************************************************************************
1970* eth_port_omc_addr - Multicast address settings.
1971*
1972* DESCRIPTION:
1973* This routine controls the MV device Other MAC multicast support.
1974* The Other Multicast Table is used for multicast of another type.
1975* A CRC-8bit is used as an index to the Other Multicast Table entries
1976* in the DA-Filter table.
1977* The function gets the CRC-8bit value from the calling routine and
1978* set the Other Multicast Table appropriate entry according to the
1979* CRC-8 argument given.
1980*
1981* INPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01001982* ETH_PORT eth_port_num Port number.
1983* unsigned char crc8 A CRC-8bit (Polynomial: x^8+x^2+x^1+1).
1984* ETH_QUEUE queue Rx queue number for this MAC address.
1985* int option 0 = Add, 1 = remove address.
Stefan Roese45993ea2006-11-29 15:42:37 +01001986*
1987* OUTPUT:
1988* See description.
1989*
1990* RETURN:
1991* true is output succeeded.
1992* false if option parameter is invalid.
1993*
1994*******************************************************************************/
1995static bool eth_port_omc_addr (ETH_PORT eth_port_num,
1996 unsigned char crc8,
1997 ETH_QUEUE queue, int option)
1998{
1999 unsigned int omc_table_reg;
2000 unsigned int tbl_offset;
2001 unsigned int reg_offset;
2002
2003 /* Locate the OMC table entry */
2004 tbl_offset = (crc8 / 4) * 4; /* Register offset from OMC table base */
2005 reg_offset = crc8 % 4; /* Entry offset within the above register */
2006 queue &= 0x7;
2007
2008 switch (option) {
2009 case REJECT_MAC_ADDR:
2010 /* Clear accepts frame bit at specified Other DA table entry */
2011 omc_table_reg =
2012 MV_REG_READ ((MV64460_ETH_DA_FILTER_OTHER_MULTICAST_TABLE_BASE (eth_port_num) + tbl_offset));
2013 omc_table_reg &= (0x0E << (8 * reg_offset));
2014
2015 MV_REG_WRITE ((MV64460_ETH_DA_FILTER_OTHER_MULTICAST_TABLE_BASE (eth_port_num) + tbl_offset), omc_table_reg);
2016 break;
2017
2018 case ACCEPT_MAC_ADDR:
2019 /* Set accepts frame bit at specified Other DA table entry */
2020 omc_table_reg =
2021 MV_REG_READ ((MV64460_ETH_DA_FILTER_OTHER_MULTICAST_TABLE_BASE (eth_port_num) + tbl_offset));
2022 omc_table_reg |= ((0x01 | queue) << (8 * reg_offset));
2023
2024 MV_REG_WRITE ((MV64460_ETH_DA_FILTER_OTHER_MULTICAST_TABLE_BASE (eth_port_num) + tbl_offset), omc_table_reg);
2025 break;
2026
2027 default:
2028 return false;
2029 }
2030 return true;
2031}
2032#endif
2033
2034/*******************************************************************************
2035* eth_port_init_mac_tables - Clear all entrance in the UC, SMC and OMC tables
2036*
2037* DESCRIPTION:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002038* Go through all the DA filter tables (Unicast, Special Multicast & Other
2039* Multicast) and set each entry to 0.
Stefan Roese45993ea2006-11-29 15:42:37 +01002040*
2041* INPUT:
2042* ETH_PORT eth_port_num Ethernet Port number. See ETH_PORT enum.
2043*
2044* OUTPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002045* Multicast and Unicast packets are rejected.
Stefan Roese45993ea2006-11-29 15:42:37 +01002046*
2047* RETURN:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002048* None.
Stefan Roese45993ea2006-11-29 15:42:37 +01002049*
2050*******************************************************************************/
2051static void eth_port_init_mac_tables (ETH_PORT eth_port_num)
2052{
2053 int table_index;
2054
2055 /* Clear DA filter unicast table (Ex_dFUT) */
2056 for (table_index = 0; table_index <= 0xC; table_index += 4)
2057 MV_REG_WRITE ((MV64460_ETH_DA_FILTER_UNICAST_TABLE_BASE
2058 (eth_port_num) + table_index), 0);
2059
2060 for (table_index = 0; table_index <= 0xFC; table_index += 4) {
2061 /* Clear DA filter special multicast table (Ex_dFSMT) */
2062 MV_REG_WRITE ((MV64460_ETH_DA_FILTER_SPECIAL_MULTICAST_TABLE_BASE (eth_port_num) + table_index), 0);
2063 /* Clear DA filter other multicast table (Ex_dFOMT) */
2064 MV_REG_WRITE ((MV64460_ETH_DA_FILTER_OTHER_MULTICAST_TABLE_BASE (eth_port_num) + table_index), 0);
2065 }
2066}
2067
2068/*******************************************************************************
2069* eth_clear_mib_counters - Clear all MIB counters
2070*
2071* DESCRIPTION:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002072* This function clears all MIB counters of a specific ethernet port.
2073* A read from the MIB counter will reset the counter.
Stefan Roese45993ea2006-11-29 15:42:37 +01002074*
2075* INPUT:
2076* ETH_PORT eth_port_num Ethernet Port number. See ETH_PORT enum.
2077*
2078* OUTPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002079* After reading all MIB counters, the counters resets.
Stefan Roese45993ea2006-11-29 15:42:37 +01002080*
2081* RETURN:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002082* MIB counter value.
Stefan Roese45993ea2006-11-29 15:42:37 +01002083*
2084*******************************************************************************/
2085static void eth_clear_mib_counters (ETH_PORT eth_port_num)
2086{
2087 int i;
Stefan Roese45993ea2006-11-29 15:42:37 +01002088
2089 /* Perform dummy reads from MIB counters */
2090 for (i = ETH_MIB_GOOD_OCTETS_RECEIVED_LOW; i < ETH_MIB_LATE_COLLISION;
Wolfgang Denkb1fe5262011-10-29 09:38:21 +00002091 i += 4) {
2092 (void)MV_REG_READ ((MV64460_ETH_MIB_COUNTERS_BASE
Stefan Roese45993ea2006-11-29 15:42:37 +01002093 (eth_port_num) + i));
Wolfgang Denkb1fe5262011-10-29 09:38:21 +00002094 }
Stefan Roese45993ea2006-11-29 15:42:37 +01002095
2096 return;
2097}
2098
2099/*******************************************************************************
2100* eth_read_mib_counter - Read a MIB counter
2101*
2102* DESCRIPTION:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002103* This function reads a MIB counter of a specific ethernet port.
2104* NOTE - If read from ETH_MIB_GOOD_OCTETS_RECEIVED_LOW, then the
2105* following read must be from ETH_MIB_GOOD_OCTETS_RECEIVED_HIGH
2106* register. The same applies for ETH_MIB_GOOD_OCTETS_SENT_LOW and
2107* ETH_MIB_GOOD_OCTETS_SENT_HIGH
Stefan Roese45993ea2006-11-29 15:42:37 +01002108*
2109* INPUT:
2110* ETH_PORT eth_port_num Ethernet Port number. See ETH_PORT enum.
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002111* unsigned int mib_offset MIB counter offset (use ETH_MIB_... macros).
Stefan Roese45993ea2006-11-29 15:42:37 +01002112*
2113* OUTPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002114* After reading the MIB counter, the counter resets.
Stefan Roese45993ea2006-11-29 15:42:37 +01002115*
2116* RETURN:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002117* MIB counter value.
Stefan Roese45993ea2006-11-29 15:42:37 +01002118*
2119*******************************************************************************/
2120unsigned int eth_read_mib_counter (ETH_PORT eth_port_num,
2121 unsigned int mib_offset)
2122{
2123 return (MV_REG_READ (MV64460_ETH_MIB_COUNTERS_BASE (eth_port_num)
2124 + mib_offset));
2125}
2126
2127/*******************************************************************************
2128* ethernet_phy_set - Set the ethernet port PHY address.
2129*
2130* DESCRIPTION:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002131* This routine set the ethernet port PHY address according to given
2132* parameter.
Stefan Roese45993ea2006-11-29 15:42:37 +01002133*
2134* INPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002135* ETH_PORT eth_port_num Ethernet Port number. See ETH_PORT enum.
Stefan Roese45993ea2006-11-29 15:42:37 +01002136*
2137* OUTPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002138* Set PHY Address Register with given PHY address parameter.
Stefan Roese45993ea2006-11-29 15:42:37 +01002139*
2140* RETURN:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002141* None.
Stefan Roese45993ea2006-11-29 15:42:37 +01002142*
2143*******************************************************************************/
2144static void ethernet_phy_set (ETH_PORT eth_port_num, int phy_addr)
2145{
2146 unsigned int reg_data;
2147
2148 reg_data = MV_REG_READ (MV64460_ETH_PHY_ADDR_REG);
2149
2150 reg_data &= ~(0x1F << (5 * eth_port_num));
2151 reg_data |= (phy_addr << (5 * eth_port_num));
2152
2153 MV_REG_WRITE (MV64460_ETH_PHY_ADDR_REG, reg_data);
2154
2155 return;
2156}
2157
2158/*******************************************************************************
2159 * ethernet_phy_get - Get the ethernet port PHY address.
2160 *
2161 * DESCRIPTION:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002162 * This routine returns the given ethernet port PHY address.
Stefan Roese45993ea2006-11-29 15:42:37 +01002163 *
2164 * INPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002165 * ETH_PORT eth_port_num Ethernet Port number. See ETH_PORT enum.
Stefan Roese45993ea2006-11-29 15:42:37 +01002166 *
2167 * OUTPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002168 * None.
Stefan Roese45993ea2006-11-29 15:42:37 +01002169 *
2170 * RETURN:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002171 * PHY address.
Stefan Roese45993ea2006-11-29 15:42:37 +01002172 *
2173 *******************************************************************************/
2174static int ethernet_phy_get (ETH_PORT eth_port_num)
2175{
2176 unsigned int reg_data;
2177
2178 reg_data = MV_REG_READ (MV64460_ETH_PHY_ADDR_REG);
2179
2180 return ((reg_data >> (5 * eth_port_num)) & 0x1f);
2181}
2182
2183/***********************************************************/
2184/* (Re)start autonegotiation */
2185/***********************************************************/
2186int phy_setup_aneg (char *devname, unsigned char addr)
2187{
2188 unsigned short ctl, adv;
2189
2190 /* Setup standard advertise */
Mike Frysingerd63ee712010-12-23 15:40:12 -05002191 miiphy_read (devname, addr, MII_ADVERTISE, &adv);
2192 adv |= (LPA_LPACK | LPA_RFAULT | LPA_100BASE4 |
2193 LPA_100FULL | LPA_100HALF | LPA_10FULL |
2194 LPA_10HALF);
2195 miiphy_write (devname, addr, MII_ADVERTISE, adv);
Stefan Roese45993ea2006-11-29 15:42:37 +01002196
Mike Frysingerd63ee712010-12-23 15:40:12 -05002197 miiphy_read (devname, addr, MII_CTRL1000, &adv);
Stefan Roese45993ea2006-11-29 15:42:37 +01002198 adv |= (0x0300);
Mike Frysingerd63ee712010-12-23 15:40:12 -05002199 miiphy_write (devname, addr, MII_CTRL1000, adv);
Stefan Roese45993ea2006-11-29 15:42:37 +01002200
2201 /* Start/Restart aneg */
Mike Frysingerd63ee712010-12-23 15:40:12 -05002202 miiphy_read (devname, addr, MII_BMCR, &ctl);
2203 ctl |= (BMCR_ANENABLE | BMCR_ANRESTART);
2204 miiphy_write (devname, addr, MII_BMCR, ctl);
Stefan Roese45993ea2006-11-29 15:42:37 +01002205
2206 return 0;
2207}
2208
2209/*******************************************************************************
2210 * ethernet_phy_reset - Reset Ethernet port PHY.
2211 *
2212 * DESCRIPTION:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002213 * This routine utilize the SMI interface to reset the ethernet port PHY.
2214 * The routine waits until the link is up again or link up is timeout.
Stefan Roese45993ea2006-11-29 15:42:37 +01002215 *
2216 * INPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002217 * ETH_PORT eth_port_num Ethernet Port number. See ETH_PORT enum.
Stefan Roese45993ea2006-11-29 15:42:37 +01002218 *
2219 * OUTPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002220 * The ethernet port PHY renew its link.
Stefan Roese45993ea2006-11-29 15:42:37 +01002221 *
2222 * RETURN:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002223 * None.
Stefan Roese45993ea2006-11-29 15:42:37 +01002224 *
2225 *******************************************************************************/
2226static bool ethernet_phy_reset (ETH_PORT eth_port_num)
2227{
2228 unsigned int time_out = 50;
2229 unsigned int phy_reg_data;
2230
2231 eth_port_read_smi_reg (eth_port_num, 20, &phy_reg_data);
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002232 phy_reg_data |= 0x0083; /* Set bit 7 to 1 for different RGMII timing */
Stefan Roese45993ea2006-11-29 15:42:37 +01002233 eth_port_write_smi_reg (eth_port_num, 20, phy_reg_data);
2234
2235 /* Reset the PHY */
2236 eth_port_read_smi_reg (eth_port_num, 0, &phy_reg_data);
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002237 phy_reg_data |= 0x8000; /* Set bit 15 to reset the PHY */
Stefan Roese45993ea2006-11-29 15:42:37 +01002238 eth_port_write_smi_reg (eth_port_num, 0, phy_reg_data);
2239
2240 /* Poll on the PHY LINK */
2241 do {
2242 eth_port_read_smi_reg (eth_port_num, 1, &phy_reg_data);
2243
2244 if (time_out-- == 0)
2245 return false;
2246 }
2247 while (!(phy_reg_data & 0x20));
2248
2249 return true;
2250}
2251
2252/*******************************************************************************
2253 * eth_port_reset - Reset Ethernet port
2254 *
2255 * DESCRIPTION:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002256 * This routine resets the chip by aborting any SDMA engine activity and
2257 * clearing the MIB counters. The Receiver and the Transmit unit are in
2258 * idle state after this command is performed and the port is disabled.
Stefan Roese45993ea2006-11-29 15:42:37 +01002259 *
2260 * INPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002261 * ETH_PORT eth_port_num Ethernet Port number. See ETH_PORT enum.
Stefan Roese45993ea2006-11-29 15:42:37 +01002262 *
2263 * OUTPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002264 * Channel activity is halted.
Stefan Roese45993ea2006-11-29 15:42:37 +01002265 *
2266 * RETURN:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002267 * None.
Stefan Roese45993ea2006-11-29 15:42:37 +01002268 *
2269 *******************************************************************************/
2270static void eth_port_reset (ETH_PORT eth_port_num)
2271{
2272 unsigned int reg_data;
2273
2274 /* Stop Tx port activity. Check port Tx activity. */
2275 reg_data =
2276 MV_REG_READ (MV64460_ETH_TRANSMIT_QUEUE_COMMAND_REG
2277 (eth_port_num));
2278
2279 if (reg_data & 0xFF) {
2280 /* Issue stop command for active channels only */
2281 MV_REG_WRITE (MV64460_ETH_TRANSMIT_QUEUE_COMMAND_REG
2282 (eth_port_num), (reg_data << 8));
2283
2284 /* Wait for all Tx activity to terminate. */
2285 do {
2286 /* Check port cause register that all Tx queues are stopped */
2287 reg_data =
2288 MV_REG_READ
2289 (MV64460_ETH_TRANSMIT_QUEUE_COMMAND_REG
2290 (eth_port_num));
2291 }
2292 while (reg_data & 0xFF);
2293 }
2294
2295 /* Stop Rx port activity. Check port Rx activity. */
2296 reg_data =
2297 MV_REG_READ (MV64460_ETH_RECEIVE_QUEUE_COMMAND_REG
2298 (eth_port_num));
2299
2300 if (reg_data & 0xFF) {
2301 /* Issue stop command for active channels only */
2302 MV_REG_WRITE (MV64460_ETH_RECEIVE_QUEUE_COMMAND_REG
2303 (eth_port_num), (reg_data << 8));
2304
2305 /* Wait for all Rx activity to terminate. */
2306 do {
2307 /* Check port cause register that all Rx queues are stopped */
2308 reg_data =
2309 MV_REG_READ
2310 (MV64460_ETH_RECEIVE_QUEUE_COMMAND_REG
2311 (eth_port_num));
2312 }
2313 while (reg_data & 0xFF);
2314 }
2315
2316 /* Clear all MIB counters */
2317 eth_clear_mib_counters (eth_port_num);
2318
2319 /* Reset the Enable bit in the Configuration Register */
2320 reg_data =
2321 MV_REG_READ (MV64460_ETH_PORT_SERIAL_CONTROL_REG
2322 (eth_port_num));
2323 reg_data &= ~ETH_SERIAL_PORT_ENABLE;
2324 MV_REG_WRITE (MV64460_ETH_PORT_SERIAL_CONTROL_REG (eth_port_num),
2325 reg_data);
2326
2327 return;
2328}
2329
2330#if 0 /* Not needed here */
2331/*******************************************************************************
2332 * ethernet_set_config_reg - Set specified bits in configuration register.
2333 *
2334 * DESCRIPTION:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002335 * This function sets specified bits in the given ethernet
2336 * configuration register.
Stefan Roese45993ea2006-11-29 15:42:37 +01002337 *
2338 * INPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002339 * ETH_PORT eth_port_num Ethernet Port number. See ETH_PORT enum.
2340 * unsigned int value 32 bit value.
Stefan Roese45993ea2006-11-29 15:42:37 +01002341 *
2342 * OUTPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002343 * The set bits in the value parameter are set in the configuration
2344 * register.
Stefan Roese45993ea2006-11-29 15:42:37 +01002345 *
2346 * RETURN:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002347 * None.
Stefan Roese45993ea2006-11-29 15:42:37 +01002348 *
2349 *******************************************************************************/
2350static void ethernet_set_config_reg (ETH_PORT eth_port_num,
2351 unsigned int value)
2352{
2353 unsigned int eth_config_reg;
2354
2355 eth_config_reg =
2356 MV_REG_READ (MV64460_ETH_PORT_CONFIG_REG (eth_port_num));
2357 eth_config_reg |= value;
2358 MV_REG_WRITE (MV64460_ETH_PORT_CONFIG_REG (eth_port_num),
2359 eth_config_reg);
2360
2361 return;
2362}
2363#endif
2364
2365#if 0 /* FIXME */
2366/*******************************************************************************
2367 * ethernet_reset_config_reg - Reset specified bits in configuration register.
2368 *
2369 * DESCRIPTION:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002370 * This function resets specified bits in the given Ethernet
2371 * configuration register.
Stefan Roese45993ea2006-11-29 15:42:37 +01002372 *
2373 * INPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002374 * ETH_PORT eth_port_num Ethernet Port number. See ETH_PORT enum.
2375 * unsigned int value 32 bit value.
Stefan Roese45993ea2006-11-29 15:42:37 +01002376 *
2377 * OUTPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002378 * The set bits in the value parameter are reset in the configuration
2379 * register.
Stefan Roese45993ea2006-11-29 15:42:37 +01002380 *
2381 * RETURN:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002382 * None.
Stefan Roese45993ea2006-11-29 15:42:37 +01002383 *
2384 *******************************************************************************/
2385static void ethernet_reset_config_reg (ETH_PORT eth_port_num,
2386 unsigned int value)
2387{
2388 unsigned int eth_config_reg;
2389
2390 eth_config_reg = MV_REG_READ (MV64460_ETH_PORT_CONFIG_EXTEND_REG
2391 (eth_port_num));
2392 eth_config_reg &= ~value;
2393 MV_REG_WRITE (MV64460_ETH_PORT_CONFIG_EXTEND_REG (eth_port_num),
2394 eth_config_reg);
2395
2396 return;
2397}
2398#endif
2399
2400#if 0 /* Not needed here */
2401/*******************************************************************************
2402 * ethernet_get_config_reg - Get the port configuration register
2403 *
2404 * DESCRIPTION:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002405 * This function returns the configuration register value of the given
2406 * ethernet port.
Stefan Roese45993ea2006-11-29 15:42:37 +01002407 *
2408 * INPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002409 * ETH_PORT eth_port_num Ethernet Port number. See ETH_PORT enum.
Stefan Roese45993ea2006-11-29 15:42:37 +01002410 *
2411 * OUTPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002412 * None.
Stefan Roese45993ea2006-11-29 15:42:37 +01002413 *
2414 * RETURN:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002415 * Port configuration register value.
Stefan Roese45993ea2006-11-29 15:42:37 +01002416 *
2417 *******************************************************************************/
2418static unsigned int ethernet_get_config_reg (ETH_PORT eth_port_num)
2419{
2420 unsigned int eth_config_reg;
2421
2422 eth_config_reg = MV_REG_READ (MV64460_ETH_PORT_CONFIG_EXTEND_REG
2423 (eth_port_num));
2424 return eth_config_reg;
2425}
2426
2427#endif
2428
2429/*******************************************************************************
2430 * eth_port_read_smi_reg - Read PHY registers
2431 *
2432 * DESCRIPTION:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002433 * This routine utilize the SMI interface to interact with the PHY in
2434 * order to perform PHY register read.
Stefan Roese45993ea2006-11-29 15:42:37 +01002435 *
2436 * INPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002437 * ETH_PORT eth_port_num Ethernet Port number. See ETH_PORT enum.
2438 * unsigned int phy_reg PHY register address offset.
2439 * unsigned int *value Register value buffer.
Stefan Roese45993ea2006-11-29 15:42:37 +01002440 *
2441 * OUTPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002442 * Write the value of a specified PHY register into given buffer.
Stefan Roese45993ea2006-11-29 15:42:37 +01002443 *
2444 * RETURN:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002445 * false if the PHY is busy or read data is not in valid state.
2446 * true otherwise.
Stefan Roese45993ea2006-11-29 15:42:37 +01002447 *
2448 *******************************************************************************/
2449static bool eth_port_read_smi_reg (ETH_PORT eth_port_num,
2450 unsigned int phy_reg, unsigned int *value)
2451{
2452 unsigned int reg_value;
2453 unsigned int time_out = PHY_BUSY_TIMEOUT;
2454 int phy_addr;
2455
2456 phy_addr = ethernet_phy_get (eth_port_num);
2457
2458 /* first check that it is not busy */
2459 do {
2460 reg_value = MV_REG_READ (MV64460_ETH_SMI_REG);
2461 if (time_out-- == 0) {
2462 return false;
2463 }
2464 }
2465 while (reg_value & ETH_SMI_BUSY);
2466
2467 /* not busy */
2468
2469 MV_REG_WRITE (MV64460_ETH_SMI_REG,
2470 (phy_addr << 16) | (phy_reg << 21) |
2471 ETH_SMI_OPCODE_READ);
2472
2473 time_out = PHY_BUSY_TIMEOUT; /* initialize the time out var again */
2474
2475 do {
2476 reg_value = MV_REG_READ (MV64460_ETH_SMI_REG);
2477 if (time_out-- == 0) {
2478 return false;
2479 }
2480 }
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002481 while ((reg_value & ETH_SMI_READ_VALID) != ETH_SMI_READ_VALID); /* Bit set equ operation done */
Stefan Roese45993ea2006-11-29 15:42:37 +01002482
2483 /* Wait for the data to update in the SMI register */
2484#define PHY_UPDATE_TIMEOUT 10000
2485 for (time_out = 0; time_out < PHY_UPDATE_TIMEOUT; time_out++);
2486
2487 reg_value = MV_REG_READ (MV64460_ETH_SMI_REG);
2488
2489 *value = reg_value & 0xffff;
2490
2491 return true;
2492}
2493
Mike Frysinger5ff5fdb2010-07-27 18:35:08 -04002494int mv_miiphy_read(const char *devname, unsigned char phy_addr,
Stefan Roese45993ea2006-11-29 15:42:37 +01002495 unsigned char phy_reg, unsigned short *value)
2496{
2497 unsigned int reg_value;
2498 unsigned int time_out = PHY_BUSY_TIMEOUT;
2499
2500 /* first check that it is not busy */
2501 do {
2502 reg_value = MV_REG_READ (MV64460_ETH_SMI_REG);
2503 if (time_out-- == 0) {
2504 return false;
2505 }
2506 }
2507 while (reg_value & ETH_SMI_BUSY);
2508
2509 /* not busy */
2510 MV_REG_WRITE (MV64460_ETH_SMI_REG,
2511 (phy_addr << 16) | (phy_reg << 21) |
2512 ETH_SMI_OPCODE_READ);
2513
2514 time_out = PHY_BUSY_TIMEOUT; /* initialize the time out var again */
2515
2516 do {
2517 reg_value = MV_REG_READ (MV64460_ETH_SMI_REG);
2518 if (time_out-- == 0) {
2519 return false;
2520 }
2521 }
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002522 while ((reg_value & ETH_SMI_READ_VALID) != ETH_SMI_READ_VALID); /* Bit set equ operation done */
Stefan Roese45993ea2006-11-29 15:42:37 +01002523
2524 /* Wait for the data to update in the SMI register */
2525 for (time_out = 0; time_out < PHY_UPDATE_TIMEOUT; time_out++);
2526
2527 reg_value = MV_REG_READ (MV64460_ETH_SMI_REG);
2528
2529 *value = reg_value & 0xffff;
2530
2531 return 0;
2532}
2533
2534/*******************************************************************************
2535 * eth_port_write_smi_reg - Write to PHY registers
2536 *
2537 * DESCRIPTION:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002538 * This routine utilize the SMI interface to interact with the PHY in
2539 * order to perform writes to PHY registers.
Stefan Roese45993ea2006-11-29 15:42:37 +01002540 *
2541 * INPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002542 * ETH_PORT eth_port_num Ethernet Port number. See ETH_PORT enum.
2543 * unsigned int phy_reg PHY register address offset.
2544 * unsigned int value Register value.
Stefan Roese45993ea2006-11-29 15:42:37 +01002545 *
2546 * OUTPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002547 * Write the given value to the specified PHY register.
Stefan Roese45993ea2006-11-29 15:42:37 +01002548 *
2549 * RETURN:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002550 * false if the PHY is busy.
2551 * true otherwise.
Stefan Roese45993ea2006-11-29 15:42:37 +01002552 *
2553 *******************************************************************************/
2554static bool eth_port_write_smi_reg (ETH_PORT eth_port_num,
2555 unsigned int phy_reg, unsigned int value)
2556{
2557 unsigned int reg_value;
2558 unsigned int time_out = PHY_BUSY_TIMEOUT;
2559 int phy_addr;
2560
2561 phy_addr = ethernet_phy_get (eth_port_num);
2562
2563 /* first check that it is not busy */
2564 do {
2565 reg_value = MV_REG_READ (MV64460_ETH_SMI_REG);
2566 if (time_out-- == 0) {
2567 return false;
2568 }
2569 }
2570 while (reg_value & ETH_SMI_BUSY);
2571
2572 /* not busy */
2573 MV_REG_WRITE (MV64460_ETH_SMI_REG,
2574 (phy_addr << 16) | (phy_reg << 21) |
2575 ETH_SMI_OPCODE_WRITE | (value & 0xffff));
2576 return true;
2577}
2578
Mike Frysinger5ff5fdb2010-07-27 18:35:08 -04002579int mv_miiphy_write(const char *devname, unsigned char phy_addr,
Stefan Roese45993ea2006-11-29 15:42:37 +01002580 unsigned char phy_reg, unsigned short value)
2581{
2582 unsigned int reg_value;
2583 unsigned int time_out = PHY_BUSY_TIMEOUT;
2584
2585 /* first check that it is not busy */
2586 do {
2587 reg_value = MV_REG_READ (MV64460_ETH_SMI_REG);
2588 if (time_out-- == 0) {
2589 return false;
2590 }
2591 }
2592 while (reg_value & ETH_SMI_BUSY);
2593
2594 /* not busy */
2595 MV_REG_WRITE (MV64460_ETH_SMI_REG,
2596 (phy_addr << 16) | (phy_reg << 21) |
2597 ETH_SMI_OPCODE_WRITE | (value & 0xffff));
2598 return 0;
2599}
2600
2601/*******************************************************************************
2602 * eth_set_access_control - Config address decode parameters for Ethernet unit
2603 *
2604 * DESCRIPTION:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002605 * This function configures the address decode parameters for the Gigabit
2606 * Ethernet Controller according the given parameters struct.
Stefan Roese45993ea2006-11-29 15:42:37 +01002607 *
2608 * INPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002609 * ETH_PORT eth_port_num Ethernet Port number. See ETH_PORT enum.
2610 * ETH_WIN_PARAM *param Address decode parameter struct.
Stefan Roese45993ea2006-11-29 15:42:37 +01002611 *
2612 * OUTPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002613 * An access window is opened using the given access parameters.
Stefan Roese45993ea2006-11-29 15:42:37 +01002614 *
2615 * RETURN:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002616 * None.
Stefan Roese45993ea2006-11-29 15:42:37 +01002617 *
2618 *******************************************************************************/
2619static void eth_set_access_control (ETH_PORT eth_port_num,
2620 ETH_WIN_PARAM * param)
2621{
2622 unsigned int access_prot_reg;
2623
2624 /* Set access control register */
2625 access_prot_reg = MV_REG_READ (MV64460_ETH_ACCESS_PROTECTION_REG
2626 (eth_port_num));
2627 access_prot_reg &= (~(3 << (param->win * 2))); /* clear window permission */
2628 access_prot_reg |= (param->access_ctrl << (param->win * 2));
2629 MV_REG_WRITE (MV64460_ETH_ACCESS_PROTECTION_REG (eth_port_num),
2630 access_prot_reg);
2631
2632 /* Set window Size reg (SR) */
2633 MV_REG_WRITE ((MV64460_ETH_SIZE_REG_0 +
2634 (ETH_SIZE_REG_GAP * param->win)),
2635 (((param->size / 0x10000) - 1) << 16));
2636
2637 /* Set window Base address reg (BA) */
2638 MV_REG_WRITE ((MV64460_ETH_BAR_0 + (ETH_BAR_GAP * param->win)),
2639 (param->target | param->attributes | param->base_addr));
2640 /* High address remap reg (HARR) */
2641 if (param->win < 4)
2642 MV_REG_WRITE ((MV64460_ETH_HIGH_ADDR_REMAP_REG_0 +
2643 (ETH_HIGH_ADDR_REMAP_REG_GAP * param->win)),
2644 param->high_addr);
2645
2646 /* Base address enable reg (BARER) */
2647 if (param->enable == 1)
2648 MV_RESET_REG_BITS (MV64460_ETH_BASE_ADDR_ENABLE_REG,
2649 (1 << param->win));
2650 else
2651 MV_SET_REG_BITS (MV64460_ETH_BASE_ADDR_ENABLE_REG,
2652 (1 << param->win));
2653}
2654
2655/*******************************************************************************
2656 * ether_init_rx_desc_ring - Curve a Rx chain desc list and buffer in memory.
2657 *
2658 * DESCRIPTION:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002659 * This function prepares a Rx chained list of descriptors and packet
2660 * buffers in a form of a ring. The routine must be called after port
2661 * initialization routine and before port start routine.
2662 * The Ethernet SDMA engine uses CPU bus addresses to access the various
2663 * devices in the system (i.e. DRAM). This function uses the ethernet
2664 * struct 'virtual to physical' routine (set by the user) to set the ring
2665 * with physical addresses.
Stefan Roese45993ea2006-11-29 15:42:37 +01002666 *
2667 * INPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002668 * ETH_PORT_INFO *p_eth_port_ctrl Ethernet Port Control srtuct.
2669 * ETH_QUEUE rx_queue Number of Rx queue.
2670 * int rx_desc_num Number of Rx descriptors
2671 * int rx_buff_size Size of Rx buffer
2672 * unsigned int rx_desc_base_addr Rx descriptors memory area base addr.
2673 * unsigned int rx_buff_base_addr Rx buffer memory area base addr.
Stefan Roese45993ea2006-11-29 15:42:37 +01002674 *
2675 * OUTPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002676 * The routine updates the Ethernet port control struct with information
2677 * regarding the Rx descriptors and buffers.
Stefan Roese45993ea2006-11-29 15:42:37 +01002678 *
2679 * RETURN:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002680 * false if the given descriptors memory area is not aligned according to
2681 * Ethernet SDMA specifications.
2682 * true otherwise.
Stefan Roese45993ea2006-11-29 15:42:37 +01002683 *
2684 *******************************************************************************/
2685static bool ether_init_rx_desc_ring (ETH_PORT_INFO * p_eth_port_ctrl,
2686 ETH_QUEUE rx_queue,
2687 int rx_desc_num,
2688 int rx_buff_size,
2689 unsigned int rx_desc_base_addr,
2690 unsigned int rx_buff_base_addr)
2691{
2692 ETH_RX_DESC *p_rx_desc;
2693 ETH_RX_DESC *p_rx_prev_desc; /* pointer to link with the last descriptor */
2694 unsigned int buffer_addr;
2695 int ix; /* a counter */
2696
Stefan Roese45993ea2006-11-29 15:42:37 +01002697 p_rx_desc = (ETH_RX_DESC *) rx_desc_base_addr;
2698 p_rx_prev_desc = p_rx_desc;
2699 buffer_addr = rx_buff_base_addr;
2700
2701 /* Rx desc Must be 4LW aligned (i.e. Descriptor_Address[3:0]=0000). */
2702 if (rx_buff_base_addr & 0xF)
2703 return false;
2704
2705 /* Rx buffers are limited to 64K bytes and Minimum size is 8 bytes */
2706 if ((rx_buff_size < 8) || (rx_buff_size > RX_BUFFER_MAX_SIZE))
2707 return false;
2708
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002709 /* Rx buffers must be 64-bit aligned. */
Stefan Roese45993ea2006-11-29 15:42:37 +01002710 if ((rx_buff_base_addr + rx_buff_size) & 0x7)
2711 return false;
2712
2713 /* initialize the Rx descriptors ring */
2714 for (ix = 0; ix < rx_desc_num; ix++) {
2715 p_rx_desc->buf_size = rx_buff_size;
2716 p_rx_desc->byte_cnt = 0x0000;
2717 p_rx_desc->cmd_sts =
2718 ETH_BUFFER_OWNED_BY_DMA | ETH_RX_ENABLE_INTERRUPT;
2719 p_rx_desc->next_desc_ptr =
2720 ((unsigned int) p_rx_desc) + RX_DESC_ALIGNED_SIZE;
2721 p_rx_desc->buf_ptr = buffer_addr;
2722 p_rx_desc->return_info = 0x00000000;
2723 D_CACHE_FLUSH_LINE (p_rx_desc, 0);
2724 buffer_addr += rx_buff_size;
2725 p_rx_prev_desc = p_rx_desc;
2726 p_rx_desc = (ETH_RX_DESC *)
2727 ((unsigned int) p_rx_desc + RX_DESC_ALIGNED_SIZE);
2728 }
2729
2730 /* Closing Rx descriptors ring */
2731 p_rx_prev_desc->next_desc_ptr = (rx_desc_base_addr);
2732 D_CACHE_FLUSH_LINE (p_rx_prev_desc, 0);
2733
2734 /* Save Rx desc pointer to driver struct. */
2735 CURR_RFD_SET ((ETH_RX_DESC *) rx_desc_base_addr, rx_queue);
2736 USED_RFD_SET ((ETH_RX_DESC *) rx_desc_base_addr, rx_queue);
2737
2738 p_eth_port_ctrl->p_rx_desc_area_base[rx_queue] =
2739 (ETH_RX_DESC *) rx_desc_base_addr;
2740 p_eth_port_ctrl->rx_desc_area_size[rx_queue] =
2741 rx_desc_num * RX_DESC_ALIGNED_SIZE;
2742
2743 p_eth_port_ctrl->port_rx_queue_command |= (1 << rx_queue);
2744
2745 return true;
2746}
2747
2748/*******************************************************************************
2749 * ether_init_tx_desc_ring - Curve a Tx chain desc list and buffer in memory.
2750 *
2751 * DESCRIPTION:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002752 * This function prepares a Tx chained list of descriptors and packet
2753 * buffers in a form of a ring. The routine must be called after port
2754 * initialization routine and before port start routine.
2755 * The Ethernet SDMA engine uses CPU bus addresses to access the various
2756 * devices in the system (i.e. DRAM). This function uses the ethernet
2757 * struct 'virtual to physical' routine (set by the user) to set the ring
2758 * with physical addresses.
Stefan Roese45993ea2006-11-29 15:42:37 +01002759 *
2760 * INPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002761 * ETH_PORT_INFO *p_eth_port_ctrl Ethernet Port Control srtuct.
2762 * ETH_QUEUE tx_queue Number of Tx queue.
2763 * int tx_desc_num Number of Tx descriptors
2764 * int tx_buff_size Size of Tx buffer
2765 * unsigned int tx_desc_base_addr Tx descriptors memory area base addr.
2766 * unsigned int tx_buff_base_addr Tx buffer memory area base addr.
Stefan Roese45993ea2006-11-29 15:42:37 +01002767 *
2768 * OUTPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002769 * The routine updates the Ethernet port control struct with information
2770 * regarding the Tx descriptors and buffers.
Stefan Roese45993ea2006-11-29 15:42:37 +01002771 *
2772 * RETURN:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002773 * false if the given descriptors memory area is not aligned according to
2774 * Ethernet SDMA specifications.
2775 * true otherwise.
Stefan Roese45993ea2006-11-29 15:42:37 +01002776 *
2777 *******************************************************************************/
2778static bool ether_init_tx_desc_ring (ETH_PORT_INFO * p_eth_port_ctrl,
2779 ETH_QUEUE tx_queue,
2780 int tx_desc_num,
2781 int tx_buff_size,
2782 unsigned int tx_desc_base_addr,
2783 unsigned int tx_buff_base_addr)
2784{
2785
2786 ETH_TX_DESC *p_tx_desc;
2787 ETH_TX_DESC *p_tx_prev_desc;
2788 unsigned int buffer_addr;
2789 int ix; /* a counter */
2790
Stefan Roese45993ea2006-11-29 15:42:37 +01002791 /* save the first desc pointer to link with the last descriptor */
2792 p_tx_desc = (ETH_TX_DESC *) tx_desc_base_addr;
2793 p_tx_prev_desc = p_tx_desc;
2794 buffer_addr = tx_buff_base_addr;
2795
2796 /* Tx desc Must be 4LW aligned (i.e. Descriptor_Address[3:0]=0000). */
2797 if (tx_buff_base_addr & 0xF)
2798 return false;
2799
2800 /* Tx buffers are limited to 64K bytes and Minimum size is 8 bytes */
2801 if ((tx_buff_size > TX_BUFFER_MAX_SIZE)
2802 || (tx_buff_size < TX_BUFFER_MIN_SIZE))
2803 return false;
2804
2805 /* Initialize the Tx descriptors ring */
2806 for (ix = 0; ix < tx_desc_num; ix++) {
2807 p_tx_desc->byte_cnt = 0x0000;
2808 p_tx_desc->l4i_chk = 0x0000;
2809 p_tx_desc->cmd_sts = 0x00000000;
2810 p_tx_desc->next_desc_ptr =
2811 ((unsigned int) p_tx_desc) + TX_DESC_ALIGNED_SIZE;
2812
2813 p_tx_desc->buf_ptr = buffer_addr;
2814 p_tx_desc->return_info = 0x00000000;
2815 D_CACHE_FLUSH_LINE (p_tx_desc, 0);
2816 buffer_addr += tx_buff_size;
2817 p_tx_prev_desc = p_tx_desc;
2818 p_tx_desc = (ETH_TX_DESC *)
2819 ((unsigned int) p_tx_desc + TX_DESC_ALIGNED_SIZE);
2820
2821 }
2822 /* Closing Tx descriptors ring */
2823 p_tx_prev_desc->next_desc_ptr = tx_desc_base_addr;
2824 D_CACHE_FLUSH_LINE (p_tx_prev_desc, 0);
2825 /* Set Tx desc pointer in driver struct. */
2826 CURR_TFD_SET ((ETH_TX_DESC *) tx_desc_base_addr, tx_queue);
2827 USED_TFD_SET ((ETH_TX_DESC *) tx_desc_base_addr, tx_queue);
2828
2829 /* Init Tx ring base and size parameters */
2830 p_eth_port_ctrl->p_tx_desc_area_base[tx_queue] =
2831 (ETH_TX_DESC *) tx_desc_base_addr;
2832 p_eth_port_ctrl->tx_desc_area_size[tx_queue] =
2833 (tx_desc_num * TX_DESC_ALIGNED_SIZE);
2834
2835 /* Add the queue to the list of Tx queues of this port */
2836 p_eth_port_ctrl->port_tx_queue_command |= (1 << tx_queue);
2837
2838 return true;
2839}
2840
2841/*******************************************************************************
2842 * eth_port_send - Send an Ethernet packet
2843 *
2844 * DESCRIPTION:
2845 * This routine send a given packet described by p_pktinfo parameter. It
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002846 * supports transmitting of a packet spaned over multiple buffers. The
2847 * routine updates 'curr' and 'first' indexes according to the packet
2848 * segment passed to the routine. In case the packet segment is first,
2849 * the 'first' index is update. In any case, the 'curr' index is updated.
2850 * If the routine get into Tx resource error it assigns 'curr' index as
2851 * 'first'. This way the function can abort Tx process of multiple
2852 * descriptors per packet.
Stefan Roese45993ea2006-11-29 15:42:37 +01002853 *
2854 * INPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002855 * ETH_PORT_INFO *p_eth_port_ctrl Ethernet Port Control srtuct.
2856 * ETH_QUEUE tx_queue Number of Tx queue.
2857 * PKT_INFO *p_pkt_info User packet buffer.
Stefan Roese45993ea2006-11-29 15:42:37 +01002858 *
2859 * OUTPUT:
2860 * Tx ring 'curr' and 'first' indexes are updated.
2861 *
2862 * RETURN:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002863 * ETH_QUEUE_FULL in case of Tx resource error.
Stefan Roese45993ea2006-11-29 15:42:37 +01002864 * ETH_ERROR in case the routine can not access Tx desc ring.
2865 * ETH_QUEUE_LAST_RESOURCE if the routine uses the last Tx resource.
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002866 * ETH_OK otherwise.
Stefan Roese45993ea2006-11-29 15:42:37 +01002867 *
2868 *******************************************************************************/
2869static ETH_FUNC_RET_STATUS eth_port_send (ETH_PORT_INFO * p_eth_port_ctrl,
2870 ETH_QUEUE tx_queue,
2871 PKT_INFO * p_pkt_info)
2872{
2873 volatile ETH_TX_DESC *p_tx_desc_first;
2874 volatile ETH_TX_DESC *p_tx_desc_curr;
2875 volatile ETH_TX_DESC *p_tx_next_desc_curr;
2876 volatile ETH_TX_DESC *p_tx_desc_used;
2877 unsigned int command_status;
2878
2879 /* Do not process Tx ring in case of Tx ring resource error */
2880 if (p_eth_port_ctrl->tx_resource_err[tx_queue] == true)
2881 return ETH_QUEUE_FULL;
2882
2883 /* Get the Tx Desc ring indexes */
2884 CURR_TFD_GET (p_tx_desc_curr, tx_queue);
2885 USED_TFD_GET (p_tx_desc_used, tx_queue);
2886
2887 if (p_tx_desc_curr == NULL)
2888 return ETH_ERROR;
2889
2890 /* The following parameters are used to save readings from memory */
2891 p_tx_next_desc_curr = TX_NEXT_DESC_PTR (p_tx_desc_curr, tx_queue);
2892 command_status = p_pkt_info->cmd_sts | ETH_ZERO_PADDING | ETH_GEN_CRC;
2893
2894 if (command_status & (ETH_TX_FIRST_DESC)) {
2895 /* Update first desc */
2896 FIRST_TFD_SET (p_tx_desc_curr, tx_queue);
2897 p_tx_desc_first = p_tx_desc_curr;
2898 } else {
2899 FIRST_TFD_GET (p_tx_desc_first, tx_queue);
2900 command_status |= ETH_BUFFER_OWNED_BY_DMA;
2901 }
2902
2903 /* Buffers with a payload smaller than 8 bytes must be aligned to 64-bit */
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002904 /* boundary. We use the memory allocated for Tx descriptor. This memory */
Stefan Roese45993ea2006-11-29 15:42:37 +01002905 /* located in TX_BUF_OFFSET_IN_DESC offset within the Tx descriptor. */
2906 if (p_pkt_info->byte_cnt <= 8) {
2907 printf ("You have failed in the < 8 bytes errata - fixme\n"); /* RABEEH - TBD */
2908 return ETH_ERROR;
2909
2910 p_tx_desc_curr->buf_ptr =
2911 (unsigned int) p_tx_desc_curr + TX_BUF_OFFSET_IN_DESC;
2912 eth_b_copy (p_pkt_info->buf_ptr, p_tx_desc_curr->buf_ptr,
2913 p_pkt_info->byte_cnt);
2914 } else
2915 p_tx_desc_curr->buf_ptr = p_pkt_info->buf_ptr;
2916
2917 p_tx_desc_curr->byte_cnt = p_pkt_info->byte_cnt;
2918 p_tx_desc_curr->return_info = p_pkt_info->return_info;
2919
2920 if (p_pkt_info->cmd_sts & (ETH_TX_LAST_DESC)) {
2921 /* Set last desc with DMA ownership and interrupt enable. */
2922 p_tx_desc_curr->cmd_sts = command_status |
2923 ETH_BUFFER_OWNED_BY_DMA | ETH_TX_ENABLE_INTERRUPT;
2924
2925 if (p_tx_desc_curr != p_tx_desc_first)
2926 p_tx_desc_first->cmd_sts |= ETH_BUFFER_OWNED_BY_DMA;
2927
2928 /* Flush CPU pipe */
2929
2930 D_CACHE_FLUSH_LINE ((unsigned int) p_tx_desc_curr, 0);
2931 D_CACHE_FLUSH_LINE ((unsigned int) p_tx_desc_first, 0);
2932 CPU_PIPE_FLUSH;
2933
2934 /* Apply send command */
2935 ETH_ENABLE_TX_QUEUE (tx_queue, p_eth_port_ctrl->port_num);
2936
2937 /* Finish Tx packet. Update first desc in case of Tx resource error */
2938 p_tx_desc_first = p_tx_next_desc_curr;
2939 FIRST_TFD_SET (p_tx_desc_first, tx_queue);
2940
2941 } else {
2942 p_tx_desc_curr->cmd_sts = command_status;
2943 D_CACHE_FLUSH_LINE ((unsigned int) p_tx_desc_curr, 0);
2944 }
2945
2946 /* Check for ring index overlap in the Tx desc ring */
2947 if (p_tx_next_desc_curr == p_tx_desc_used) {
2948 /* Update the current descriptor */
2949 CURR_TFD_SET (p_tx_desc_first, tx_queue);
2950
2951 p_eth_port_ctrl->tx_resource_err[tx_queue] = true;
2952 return ETH_QUEUE_LAST_RESOURCE;
2953 } else {
2954 /* Update the current descriptor */
2955 CURR_TFD_SET (p_tx_next_desc_curr, tx_queue);
2956 return ETH_OK;
2957 }
2958}
2959
2960/*******************************************************************************
2961 * eth_tx_return_desc - Free all used Tx descriptors
2962 *
2963 * DESCRIPTION:
2964 * This routine returns the transmitted packet information to the caller.
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002965 * It uses the 'first' index to support Tx desc return in case a transmit
2966 * of a packet spanned over multiple buffer still in process.
2967 * In case the Tx queue was in "resource error" condition, where there are
2968 * no available Tx resources, the function resets the resource error flag.
Stefan Roese45993ea2006-11-29 15:42:37 +01002969 *
2970 * INPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002971 * ETH_PORT_INFO *p_eth_port_ctrl Ethernet Port Control srtuct.
2972 * ETH_QUEUE tx_queue Number of Tx queue.
2973 * PKT_INFO *p_pkt_info User packet buffer.
Stefan Roese45993ea2006-11-29 15:42:37 +01002974 *
2975 * OUTPUT:
2976 * Tx ring 'first' and 'used' indexes are updated.
2977 *
2978 * RETURN:
2979 * ETH_ERROR in case the routine can not access Tx desc ring.
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002980 * ETH_RETRY in case there is transmission in process.
Stefan Roese45993ea2006-11-29 15:42:37 +01002981 * ETH_END_OF_JOB if the routine has nothing to release.
Wolfgang Denkdd314e02006-11-30 01:54:07 +01002982 * ETH_OK otherwise.
Stefan Roese45993ea2006-11-29 15:42:37 +01002983 *
2984 *******************************************************************************/
2985static ETH_FUNC_RET_STATUS eth_tx_return_desc (ETH_PORT_INFO *
2986 p_eth_port_ctrl,
2987 ETH_QUEUE tx_queue,
2988 PKT_INFO * p_pkt_info)
2989{
2990 volatile ETH_TX_DESC *p_tx_desc_used = NULL;
2991 volatile ETH_TX_DESC *p_tx_desc_first = NULL;
2992 unsigned int command_status;
2993
Stefan Roese45993ea2006-11-29 15:42:37 +01002994 /* Get the Tx Desc ring indexes */
2995 USED_TFD_GET (p_tx_desc_used, tx_queue);
2996 FIRST_TFD_GET (p_tx_desc_first, tx_queue);
2997
Stefan Roese45993ea2006-11-29 15:42:37 +01002998 /* Sanity check */
2999 if (p_tx_desc_used == NULL)
3000 return ETH_ERROR;
3001
3002 command_status = p_tx_desc_used->cmd_sts;
3003
3004 /* Still transmitting... */
3005 if (command_status & (ETH_BUFFER_OWNED_BY_DMA)) {
3006 D_CACHE_FLUSH_LINE ((unsigned int) p_tx_desc_used, 0);
3007 return ETH_RETRY;
3008 }
3009
3010 /* Stop release. About to overlap the current available Tx descriptor */
3011 if ((p_tx_desc_used == p_tx_desc_first) &&
3012 (p_eth_port_ctrl->tx_resource_err[tx_queue] == false)) {
3013 D_CACHE_FLUSH_LINE ((unsigned int) p_tx_desc_used, 0);
3014 return ETH_END_OF_JOB;
3015 }
3016
3017 /* Pass the packet information to the caller */
3018 p_pkt_info->cmd_sts = command_status;
3019 p_pkt_info->return_info = p_tx_desc_used->return_info;
3020 p_tx_desc_used->return_info = 0;
3021
3022 /* Update the next descriptor to release. */
3023 USED_TFD_SET (TX_NEXT_DESC_PTR (p_tx_desc_used, tx_queue), tx_queue);
3024
3025 /* Any Tx return cancels the Tx resource error status */
3026 if (p_eth_port_ctrl->tx_resource_err[tx_queue] == true)
3027 p_eth_port_ctrl->tx_resource_err[tx_queue] = false;
3028
3029 D_CACHE_FLUSH_LINE ((unsigned int) p_tx_desc_used, 0);
3030
3031 return ETH_OK;
3032
3033}
3034
3035/*******************************************************************************
3036 * eth_port_receive - Get received information from Rx ring.
3037 *
3038 * DESCRIPTION:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01003039 * This routine returns the received data to the caller. There is no
Stefan Roese45993ea2006-11-29 15:42:37 +01003040 * data copying during routine operation. All information is returned
3041 * using pointer to packet information struct passed from the caller.
Wolfgang Denkdd314e02006-11-30 01:54:07 +01003042 * If the routine exhausts Rx ring resources then the resource error flag
3043 * is set.
Stefan Roese45993ea2006-11-29 15:42:37 +01003044 *
3045 * INPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01003046 * ETH_PORT_INFO *p_eth_port_ctrl Ethernet Port Control srtuct.
3047 * ETH_QUEUE rx_queue Number of Rx queue.
3048 * PKT_INFO *p_pkt_info User packet buffer.
Stefan Roese45993ea2006-11-29 15:42:37 +01003049 *
3050 * OUTPUT:
3051 * Rx ring current and used indexes are updated.
3052 *
3053 * RETURN:
3054 * ETH_ERROR in case the routine can not access Rx desc ring.
3055 * ETH_QUEUE_FULL if Rx ring resources are exhausted.
3056 * ETH_END_OF_JOB if there is no received data.
Wolfgang Denkdd314e02006-11-30 01:54:07 +01003057 * ETH_OK otherwise.
Stefan Roese45993ea2006-11-29 15:42:37 +01003058 *
3059 *******************************************************************************/
3060static ETH_FUNC_RET_STATUS eth_port_receive (ETH_PORT_INFO * p_eth_port_ctrl,
3061 ETH_QUEUE rx_queue,
3062 PKT_INFO * p_pkt_info)
3063{
3064 volatile ETH_RX_DESC *p_rx_curr_desc;
3065 volatile ETH_RX_DESC *p_rx_next_curr_desc;
3066 volatile ETH_RX_DESC *p_rx_used_desc;
3067 unsigned int command_status;
3068
3069 /* Do not process Rx ring in case of Rx ring resource error */
3070 if (p_eth_port_ctrl->rx_resource_err[rx_queue] == true) {
3071 printf ("\nRx Queue is full ...\n");
3072 return ETH_QUEUE_FULL;
3073 }
3074
3075 /* Get the Rx Desc ring 'curr and 'used' indexes */
3076 CURR_RFD_GET (p_rx_curr_desc, rx_queue);
3077 USED_RFD_GET (p_rx_used_desc, rx_queue);
3078
3079 /* Sanity check */
3080 if (p_rx_curr_desc == NULL)
3081 return ETH_ERROR;
3082
3083 /* The following parameters are used to save readings from memory */
3084 p_rx_next_curr_desc = RX_NEXT_DESC_PTR (p_rx_curr_desc, rx_queue);
3085 command_status = p_rx_curr_desc->cmd_sts;
3086
3087 /* Nothing to receive... */
3088 if (command_status & (ETH_BUFFER_OWNED_BY_DMA)) {
Wolfgang Denkdd314e02006-11-30 01:54:07 +01003089/* DP(printf("Rx: command_status: %08x\n", command_status)); */
Stefan Roese45993ea2006-11-29 15:42:37 +01003090 D_CACHE_FLUSH_LINE ((unsigned int) p_rx_curr_desc, 0);
3091/* DP(printf("\nETH_END_OF_JOB ...\n"));*/
3092 return ETH_END_OF_JOB;
3093 }
3094
3095 p_pkt_info->byte_cnt = (p_rx_curr_desc->byte_cnt) - RX_BUF_OFFSET;
3096 p_pkt_info->cmd_sts = command_status;
3097 p_pkt_info->buf_ptr = (p_rx_curr_desc->buf_ptr) + RX_BUF_OFFSET;
3098 p_pkt_info->return_info = p_rx_curr_desc->return_info;
Wolfgang Denkdd314e02006-11-30 01:54:07 +01003099 p_pkt_info->l4i_chk = p_rx_curr_desc->buf_size; /* IP fragment indicator */
Stefan Roese45993ea2006-11-29 15:42:37 +01003100
3101 /* Clean the return info field to indicate that the packet has been */
Wolfgang Denkdd314e02006-11-30 01:54:07 +01003102 /* moved to the upper layers */
Stefan Roese45993ea2006-11-29 15:42:37 +01003103 p_rx_curr_desc->return_info = 0;
3104
3105 /* Update 'curr' in data structure */
3106 CURR_RFD_SET (p_rx_next_curr_desc, rx_queue);
3107
3108 /* Rx descriptors resource exhausted. Set the Rx ring resource error flag */
3109 if (p_rx_next_curr_desc == p_rx_used_desc)
3110 p_eth_port_ctrl->rx_resource_err[rx_queue] = true;
3111
3112 D_CACHE_FLUSH_LINE ((unsigned int) p_rx_curr_desc, 0);
3113 CPU_PIPE_FLUSH;
3114
3115 return ETH_OK;
3116}
3117
3118/*******************************************************************************
3119 * eth_rx_return_buff - Returns a Rx buffer back to the Rx ring.
3120 *
3121 * DESCRIPTION:
3122 * This routine returns a Rx buffer back to the Rx ring. It retrieves the
Wolfgang Denkdd314e02006-11-30 01:54:07 +01003123 * next 'used' descriptor and attached the returned buffer to it.
3124 * In case the Rx ring was in "resource error" condition, where there are
3125 * no available Rx resources, the function resets the resource error flag.
Stefan Roese45993ea2006-11-29 15:42:37 +01003126 *
3127 * INPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01003128 * ETH_PORT_INFO *p_eth_port_ctrl Ethernet Port Control srtuct.
3129 * ETH_QUEUE rx_queue Number of Rx queue.
3130 * PKT_INFO *p_pkt_info Information on the returned buffer.
Stefan Roese45993ea2006-11-29 15:42:37 +01003131 *
3132 * OUTPUT:
3133 * New available Rx resource in Rx descriptor ring.
3134 *
3135 * RETURN:
3136 * ETH_ERROR in case the routine can not access Rx desc ring.
Wolfgang Denkdd314e02006-11-30 01:54:07 +01003137 * ETH_OK otherwise.
Stefan Roese45993ea2006-11-29 15:42:37 +01003138 *
3139 *******************************************************************************/
3140static ETH_FUNC_RET_STATUS eth_rx_return_buff (ETH_PORT_INFO *
3141 p_eth_port_ctrl,
3142 ETH_QUEUE rx_queue,
3143 PKT_INFO * p_pkt_info)
3144{
3145 volatile ETH_RX_DESC *p_used_rx_desc; /* Where to return Rx resource */
3146
3147 /* Get 'used' Rx descriptor */
3148 USED_RFD_GET (p_used_rx_desc, rx_queue);
3149
3150 /* Sanity check */
3151 if (p_used_rx_desc == NULL)
3152 return ETH_ERROR;
3153
3154 p_used_rx_desc->buf_ptr = p_pkt_info->buf_ptr;
3155 p_used_rx_desc->return_info = p_pkt_info->return_info;
3156 p_used_rx_desc->byte_cnt = p_pkt_info->byte_cnt;
3157 p_used_rx_desc->buf_size = MV64460_RX_BUFFER_SIZE; /* Reset Buffer size */
3158
3159 /* Flush the write pipe */
3160 CPU_PIPE_FLUSH;
3161
3162 /* Return the descriptor to DMA ownership */
3163 p_used_rx_desc->cmd_sts =
3164 ETH_BUFFER_OWNED_BY_DMA | ETH_RX_ENABLE_INTERRUPT;
3165
3166 /* Flush descriptor and CPU pipe */
3167 D_CACHE_FLUSH_LINE ((unsigned int) p_used_rx_desc, 0);
3168 CPU_PIPE_FLUSH;
3169
3170 /* Move the used descriptor pointer to the next descriptor */
3171 USED_RFD_SET (RX_NEXT_DESC_PTR (p_used_rx_desc, rx_queue), rx_queue);
3172
3173 /* Any Rx return cancels the Rx resource error status */
3174 if (p_eth_port_ctrl->rx_resource_err[rx_queue] == true)
3175 p_eth_port_ctrl->rx_resource_err[rx_queue] = false;
3176
3177 return ETH_OK;
3178}
3179
3180/*******************************************************************************
3181 * eth_port_set_rx_coal - Sets coalescing interrupt mechanism on RX path
3182 *
3183 * DESCRIPTION:
3184 * This routine sets the RX coalescing interrupt mechanism parameter.
3185 * This parameter is a timeout counter, that counts in 64 t_clk
3186 * chunks ; that when timeout event occurs a maskable interrupt
3187 * occurs.
3188 * The parameter is calculated using the tClk of the MV-643xx chip
3189 * , and the required delay of the interrupt in usec.
3190 *
3191 * INPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01003192 * ETH_PORT eth_port_num Ethernet port number
3193 * unsigned int t_clk t_clk of the MV-643xx chip in HZ units
3194 * unsigned int delay Delay in usec
Stefan Roese45993ea2006-11-29 15:42:37 +01003195 *
3196 * OUTPUT:
3197 * Interrupt coalescing mechanism value is set in MV-643xx chip.
3198 *
3199 * RETURN:
3200 * The interrupt coalescing value set in the gigE port.
3201 *
3202 *******************************************************************************/
3203#if 0 /* FIXME */
3204static unsigned int eth_port_set_rx_coal (ETH_PORT eth_port_num,
3205 unsigned int t_clk,
3206 unsigned int delay)
3207{
3208 unsigned int coal;
3209
3210 coal = ((t_clk / 1000000) * delay) / 64;
3211 /* Set RX Coalescing mechanism */
3212 MV_REG_WRITE (MV64460_ETH_SDMA_CONFIG_REG (eth_port_num),
3213 ((coal & 0x3fff) << 8) |
3214 (MV_REG_READ
3215 (MV64460_ETH_SDMA_CONFIG_REG (eth_port_num))
3216 & 0xffc000ff));
3217 return coal;
3218}
3219
3220#endif
3221/*******************************************************************************
3222 * eth_port_set_tx_coal - Sets coalescing interrupt mechanism on TX path
3223 *
3224 * DESCRIPTION:
3225 * This routine sets the TX coalescing interrupt mechanism parameter.
3226 * This parameter is a timeout counter, that counts in 64 t_clk
3227 * chunks ; that when timeout event occurs a maskable interrupt
3228 * occurs.
3229 * The parameter is calculated using the t_cLK frequency of the
3230 * MV-643xx chip and the required delay in the interrupt in uSec
3231 *
3232 * INPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01003233 * ETH_PORT eth_port_num Ethernet port number
3234 * unsigned int t_clk t_clk of the MV-643xx chip in HZ units
3235 * unsigned int delay Delay in uSeconds
Stefan Roese45993ea2006-11-29 15:42:37 +01003236 *
3237 * OUTPUT:
3238 * Interrupt coalescing mechanism value is set in MV-643xx chip.
3239 *
3240 * RETURN:
3241 * The interrupt coalescing value set in the gigE port.
3242 *
3243 *******************************************************************************/
3244#if 0 /* FIXME */
3245static unsigned int eth_port_set_tx_coal (ETH_PORT eth_port_num,
3246 unsigned int t_clk,
3247 unsigned int delay)
3248{
3249 unsigned int coal;
3250
3251 coal = ((t_clk / 1000000) * delay) / 64;
3252 /* Set TX Coalescing mechanism */
3253 MV_REG_WRITE (MV64460_ETH_TX_FIFO_URGENT_THRESHOLD_REG (eth_port_num),
3254 coal << 4);
3255 return coal;
3256}
3257#endif
3258
3259/*******************************************************************************
3260 * eth_b_copy - Copy bytes from source to destination
3261 *
3262 * DESCRIPTION:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01003263 * This function supports the eight bytes limitation on Tx buffer size.
3264 * The routine will zero eight bytes starting from the destination address
3265 * followed by copying bytes from the source address to the destination.
Stefan Roese45993ea2006-11-29 15:42:37 +01003266 *
3267 * INPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01003268 * unsigned int src_addr 32 bit source address.
3269 * unsigned int dst_addr 32 bit destination address.
3270 * int byte_count Number of bytes to copy.
Stefan Roese45993ea2006-11-29 15:42:37 +01003271 *
3272 * OUTPUT:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01003273 * See description.
Stefan Roese45993ea2006-11-29 15:42:37 +01003274 *
3275 * RETURN:
Wolfgang Denkdd314e02006-11-30 01:54:07 +01003276 * None.
Stefan Roese45993ea2006-11-29 15:42:37 +01003277 *
3278 *******************************************************************************/
3279static void eth_b_copy (unsigned int src_addr, unsigned int dst_addr,
3280 int byte_count)
3281{
3282 /* Zero the dst_addr area */
3283 *(unsigned int *) dst_addr = 0x0;
3284
3285 while (byte_count != 0) {
3286 *(char *) dst_addr = *(char *) src_addr;
3287 dst_addr++;
3288 src_addr++;
3289 byte_count--;
3290 }
3291}