linux/drivers/staging/octeon/ethernet.c
<<
>>
Prefs
   1/**********************************************************************
   2 * Author: Cavium Networks
   3 *
   4 * Contact: support@caviumnetworks.com
   5 * This file is part of the OCTEON SDK
   6 *
   7 * Copyright (c) 2003-2007 Cavium Networks
   8 *
   9 * This file is free software; you can redistribute it and/or modify
  10 * it under the terms of the GNU General Public License, Version 2, as
  11 * published by the Free Software Foundation.
  12 *
  13 * This file is distributed in the hope that it will be useful, but
  14 * AS-IS and WITHOUT ANY WARRANTY; without even the implied warranty
  15 * of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE, TITLE, or
  16 * NONINFRINGEMENT.  See the GNU General Public License for more
  17 * details.
  18 *
  19 * You should have received a copy of the GNU General Public License
  20 * along with this file; if not, write to the Free Software
  21 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
  22 * or visit http://www.gnu.org/licenses/.
  23 *
  24 * This file may also be available under a different license from Cavium.
  25 * Contact Cavium Networks for more information
  26**********************************************************************/
  27#include <linux/kernel.h>
  28#include <linux/init.h>
  29#include <linux/module.h>
  30#include <linux/netdevice.h>
  31#include <linux/etherdevice.h>
  32#include <linux/phy.h>
  33#include <linux/slab.h>
  34
  35#include <net/dst.h>
  36
  37#include <asm/octeon/octeon.h>
  38
  39#include "ethernet-defines.h"
  40#include "octeon-ethernet.h"
  41#include "ethernet-mem.h"
  42#include "ethernet-rx.h"
  43#include "ethernet-tx.h"
  44#include "ethernet-mdio.h"
  45#include "ethernet-util.h"
  46
  47#include <asm/octeon/cvmx-pip.h>
  48#include <asm/octeon/cvmx-pko.h>
  49#include <asm/octeon/cvmx-fau.h>
  50#include <asm/octeon/cvmx-ipd.h>
  51#include <asm/octeon/cvmx-helper.h>
  52
  53#include <asm/octeon/cvmx-gmxx-defs.h>
  54#include <asm/octeon/cvmx-smix-defs.h>
  55
  56#if defined(CONFIG_CAVIUM_OCTEON_NUM_PACKET_BUFFERS) \
  57        && CONFIG_CAVIUM_OCTEON_NUM_PACKET_BUFFERS
  58int num_packet_buffers = CONFIG_CAVIUM_OCTEON_NUM_PACKET_BUFFERS;
  59#else
  60int num_packet_buffers = 1024;
  61#endif
  62module_param(num_packet_buffers, int, 0444);
  63MODULE_PARM_DESC(num_packet_buffers, "\n"
  64        "\tNumber of packet buffers to allocate and store in the\n"
  65        "\tFPA. By default, 1024 packet buffers are used unless\n"
  66        "\tCONFIG_CAVIUM_OCTEON_NUM_PACKET_BUFFERS is defined.");
  67
  68int pow_receive_group = 15;
  69module_param(pow_receive_group, int, 0444);
  70MODULE_PARM_DESC(pow_receive_group, "\n"
  71        "\tPOW group to receive packets from. All ethernet hardware\n"
  72        "\twill be configured to send incomming packets to this POW\n"
  73        "\tgroup. Also any other software can submit packets to this\n"
  74        "\tgroup for the kernel to process.");
  75
  76int pow_send_group = -1;
  77module_param(pow_send_group, int, 0644);
  78MODULE_PARM_DESC(pow_send_group, "\n"
  79        "\tPOW group to send packets to other software on. This\n"
  80        "\tcontrols the creation of the virtual device pow0.\n"
  81        "\talways_use_pow also depends on this value.");
  82
  83int always_use_pow;
  84module_param(always_use_pow, int, 0444);
  85MODULE_PARM_DESC(always_use_pow, "\n"
  86        "\tWhen set, always send to the pow group. This will cause\n"
  87        "\tpackets sent to real ethernet devices to be sent to the\n"
  88        "\tPOW group instead of the hardware. Unless some other\n"
  89        "\tapplication changes the config, packets will still be\n"
  90        "\treceived from the low level hardware. Use this option\n"
  91        "\tto allow a CVMX app to intercept all packets from the\n"
  92        "\tlinux kernel. You must specify pow_send_group along with\n"
  93        "\tthis option.");
  94
  95char pow_send_list[128] = "";
  96module_param_string(pow_send_list, pow_send_list, sizeof(pow_send_list), 0444);
  97MODULE_PARM_DESC(pow_send_list, "\n"
  98        "\tComma separated list of ethernet devices that should use the\n"
  99        "\tPOW for transmit instead of the actual ethernet hardware. This\n"
 100        "\tis a per port version of always_use_pow. always_use_pow takes\n"
 101        "\tprecedence over this list. For example, setting this to\n"
 102        "\t\"eth2,spi3,spi7\" would cause these three devices to transmit\n"
 103        "\tusing the pow_send_group.");
 104
 105int max_rx_cpus = -1;
 106module_param(max_rx_cpus, int, 0444);
 107MODULE_PARM_DESC(max_rx_cpus, "\n"
 108        "\t\tThe maximum number of CPUs to use for packet reception.\n"
 109        "\t\tUse -1 to use all available CPUs.");
 110
 111int rx_napi_weight = 32;
 112module_param(rx_napi_weight, int, 0444);
 113MODULE_PARM_DESC(rx_napi_weight, "The NAPI WEIGHT parameter.");
 114
 115/*
 116 * The offset from mac_addr_base that should be used for the next port
 117 * that is configured.  By convention, if any mgmt ports exist on the
 118 * chip, they get the first mac addresses, The ports controlled by
 119 * this driver are numbered sequencially following any mgmt addresses
 120 * that may exist.
 121 */
 122static unsigned int cvm_oct_mac_addr_offset;
 123
 124/**
 125 * cvm_oct_poll_queue - Workqueue for polling operations.
 126 */
 127struct workqueue_struct *cvm_oct_poll_queue;
 128
 129/**
 130 * cvm_oct_poll_queue_stopping - flag to indicate polling should stop.
 131 *
 132 * Set to one right before cvm_oct_poll_queue is destroyed.
 133 */
 134atomic_t cvm_oct_poll_queue_stopping = ATOMIC_INIT(0);
 135
 136/**
 137 * Array of every ethernet device owned by this driver indexed by
 138 * the ipd input port number.
 139 */
 140struct net_device *cvm_oct_device[TOTAL_NUMBER_OF_PORTS];
 141
 142u64 cvm_oct_tx_poll_interval;
 143
 144static void cvm_oct_rx_refill_worker(struct work_struct *work);
 145static DECLARE_DELAYED_WORK(cvm_oct_rx_refill_work, cvm_oct_rx_refill_worker);
 146
 147static void cvm_oct_rx_refill_worker(struct work_struct *work)
 148{
 149        /*
 150         * FPA 0 may have been drained, try to refill it if we need
 151         * more than num_packet_buffers / 2, otherwise normal receive
 152         * processing will refill it.  If it were drained, no packets
 153         * could be received so cvm_oct_napi_poll would never be
 154         * invoked to do the refill.
 155         */
 156        cvm_oct_rx_refill_pool(num_packet_buffers / 2);
 157
 158        if (!atomic_read(&cvm_oct_poll_queue_stopping))
 159                queue_delayed_work(cvm_oct_poll_queue,
 160                                   &cvm_oct_rx_refill_work, HZ);
 161}
 162
 163static void cvm_oct_periodic_worker(struct work_struct *work)
 164{
 165        struct octeon_ethernet *priv = container_of(work,
 166                                                    struct octeon_ethernet,
 167                                                    port_periodic_work.work);
 168
 169        if (priv->poll)
 170                priv->poll(cvm_oct_device[priv->port]);
 171
 172        cvm_oct_device[priv->port]->netdev_ops->ndo_get_stats(cvm_oct_device[priv->port]);
 173
 174        if (!atomic_read(&cvm_oct_poll_queue_stopping))
 175                queue_delayed_work(cvm_oct_poll_queue, &priv->port_periodic_work, HZ);
 176 }
 177
 178static __init void cvm_oct_configure_common_hw(void)
 179{
 180        /* Setup the FPA */
 181        cvmx_fpa_enable();
 182        cvm_oct_mem_fill_fpa(CVMX_FPA_PACKET_POOL, CVMX_FPA_PACKET_POOL_SIZE,
 183                             num_packet_buffers);
 184        cvm_oct_mem_fill_fpa(CVMX_FPA_WQE_POOL, CVMX_FPA_WQE_POOL_SIZE,
 185                             num_packet_buffers);
 186        if (CVMX_FPA_OUTPUT_BUFFER_POOL != CVMX_FPA_PACKET_POOL)
 187                cvm_oct_mem_fill_fpa(CVMX_FPA_OUTPUT_BUFFER_POOL,
 188                                     CVMX_FPA_OUTPUT_BUFFER_POOL_SIZE, 128);
 189
 190        if (USE_RED)
 191                cvmx_helper_setup_red(num_packet_buffers / 4,
 192                                      num_packet_buffers / 8);
 193
 194}
 195
 196/**
 197 * cvm_oct_free_work- Free a work queue entry
 198 *
 199 * @work_queue_entry: Work queue entry to free
 200 *
 201 * Returns Zero on success, Negative on failure.
 202 */
 203int cvm_oct_free_work(void *work_queue_entry)
 204{
 205        cvmx_wqe_t *work = work_queue_entry;
 206
 207        int segments = work->word2.s.bufs;
 208        union cvmx_buf_ptr segment_ptr = work->packet_ptr;
 209
 210        while (segments--) {
 211                union cvmx_buf_ptr next_ptr = *(union cvmx_buf_ptr *)
 212                        cvmx_phys_to_ptr(segment_ptr.s.addr - 8);
 213                if (unlikely(!segment_ptr.s.i))
 214                        cvmx_fpa_free(cvm_oct_get_buffer_ptr(segment_ptr),
 215                                      segment_ptr.s.pool,
 216                                      DONT_WRITEBACK(CVMX_FPA_PACKET_POOL_SIZE /
 217                                                     128));
 218                segment_ptr = next_ptr;
 219        }
 220        cvmx_fpa_free(work, CVMX_FPA_WQE_POOL, DONT_WRITEBACK(1));
 221
 222        return 0;
 223}
 224EXPORT_SYMBOL(cvm_oct_free_work);
 225
 226/**
 227 * cvm_oct_common_get_stats - get the low level ethernet statistics
 228 * @dev:    Device to get the statistics from
 229 *
 230 * Returns Pointer to the statistics
 231 */
 232static struct net_device_stats *cvm_oct_common_get_stats(struct net_device *dev)
 233{
 234        cvmx_pip_port_status_t rx_status;
 235        cvmx_pko_port_status_t tx_status;
 236        struct octeon_ethernet *priv = netdev_priv(dev);
 237
 238        if (priv->port < CVMX_PIP_NUM_INPUT_PORTS) {
 239                if (octeon_is_simulation()) {
 240                        /* The simulator doesn't support statistics */
 241                        memset(&rx_status, 0, sizeof(rx_status));
 242                        memset(&tx_status, 0, sizeof(tx_status));
 243                } else {
 244                        cvmx_pip_get_port_status(priv->port, 1, &rx_status);
 245                        cvmx_pko_get_port_status(priv->port, 1, &tx_status);
 246                }
 247
 248                priv->stats.rx_packets += rx_status.inb_packets;
 249                priv->stats.tx_packets += tx_status.packets;
 250                priv->stats.rx_bytes += rx_status.inb_octets;
 251                priv->stats.tx_bytes += tx_status.octets;
 252                priv->stats.multicast += rx_status.multicast_packets;
 253                priv->stats.rx_crc_errors += rx_status.inb_errors;
 254                priv->stats.rx_frame_errors += rx_status.fcs_align_err_packets;
 255
 256                /*
 257                 * The drop counter must be incremented atomically
 258                 * since the RX tasklet also increments it.
 259                 */
 260#ifdef CONFIG_64BIT
 261                atomic64_add(rx_status.dropped_packets,
 262                             (atomic64_t *)&priv->stats.rx_dropped);
 263#else
 264                atomic_add(rx_status.dropped_packets,
 265                             (atomic_t *)&priv->stats.rx_dropped);
 266#endif
 267        }
 268
 269        return &priv->stats;
 270}
 271
 272/**
 273 * cvm_oct_common_change_mtu - change the link MTU
 274 * @dev:     Device to change
 275 * @new_mtu: The new MTU
 276 *
 277 * Returns Zero on success
 278 */
 279static int cvm_oct_common_change_mtu(struct net_device *dev, int new_mtu)
 280{
 281        struct octeon_ethernet *priv = netdev_priv(dev);
 282        int interface = INTERFACE(priv->port);
 283        int index = INDEX(priv->port);
 284#if defined(CONFIG_VLAN_8021Q) || defined(CONFIG_VLAN_8021Q_MODULE)
 285        int vlan_bytes = 4;
 286#else
 287        int vlan_bytes = 0;
 288#endif
 289
 290        /*
 291         * Limit the MTU to make sure the ethernet packets are between
 292         * 64 bytes and 65535 bytes.
 293         */
 294        if ((new_mtu + 14 + 4 + vlan_bytes < 64)
 295            || (new_mtu + 14 + 4 + vlan_bytes > 65392)) {
 296                pr_err("MTU must be between %d and %d.\n",
 297                       64 - 14 - 4 - vlan_bytes, 65392 - 14 - 4 - vlan_bytes);
 298                return -EINVAL;
 299        }
 300        dev->mtu = new_mtu;
 301
 302        if ((interface < 2)
 303            && (cvmx_helper_interface_get_mode(interface) !=
 304                CVMX_HELPER_INTERFACE_MODE_SPI)) {
 305                /* Add ethernet header and FCS, and VLAN if configured. */
 306                int max_packet = new_mtu + 14 + 4 + vlan_bytes;
 307
 308                if (OCTEON_IS_MODEL(OCTEON_CN3XXX)
 309                    || OCTEON_IS_MODEL(OCTEON_CN58XX)) {
 310                        /* Signal errors on packets larger than the MTU */
 311                        cvmx_write_csr(CVMX_GMXX_RXX_FRM_MAX(index, interface),
 312                                       max_packet);
 313                } else {
 314                        /*
 315                         * Set the hardware to truncate packets larger
 316                         * than the MTU and smaller the 64 bytes.
 317                         */
 318                        union cvmx_pip_frm_len_chkx frm_len_chk;
 319                        frm_len_chk.u64 = 0;
 320                        frm_len_chk.s.minlen = 64;
 321                        frm_len_chk.s.maxlen = max_packet;
 322                        cvmx_write_csr(CVMX_PIP_FRM_LEN_CHKX(interface),
 323                                       frm_len_chk.u64);
 324                }
 325                /*
 326                 * Set the hardware to truncate packets larger than
 327                 * the MTU. The jabber register must be set to a
 328                 * multiple of 8 bytes, so round up.
 329                 */
 330                cvmx_write_csr(CVMX_GMXX_RXX_JABBER(index, interface),
 331                               (max_packet + 7) & ~7u);
 332        }
 333        return 0;
 334}
 335
 336/**
 337 * cvm_oct_common_set_multicast_list - set the multicast list
 338 * @dev:    Device to work on
 339 */
 340static void cvm_oct_common_set_multicast_list(struct net_device *dev)
 341{
 342        union cvmx_gmxx_prtx_cfg gmx_cfg;
 343        struct octeon_ethernet *priv = netdev_priv(dev);
 344        int interface = INTERFACE(priv->port);
 345        int index = INDEX(priv->port);
 346
 347        if ((interface < 2)
 348            && (cvmx_helper_interface_get_mode(interface) !=
 349                CVMX_HELPER_INTERFACE_MODE_SPI)) {
 350                union cvmx_gmxx_rxx_adr_ctl control;
 351                control.u64 = 0;
 352                control.s.bcst = 1;     /* Allow broadcast MAC addresses */
 353
 354                if (!netdev_mc_empty(dev) || (dev->flags & IFF_ALLMULTI) ||
 355                    (dev->flags & IFF_PROMISC))
 356                        /* Force accept multicast packets */
 357                        control.s.mcst = 2;
 358                else
 359                        /* Force reject multicat packets */
 360                        control.s.mcst = 1;
 361
 362                if (dev->flags & IFF_PROMISC)
 363                        /*
 364                         * Reject matches if promisc. Since CAM is
 365                         * shut off, should accept everything.
 366                         */
 367                        control.s.cam_mode = 0;
 368                else
 369                        /* Filter packets based on the CAM */
 370                        control.s.cam_mode = 1;
 371
 372                gmx_cfg.u64 =
 373                    cvmx_read_csr(CVMX_GMXX_PRTX_CFG(index, interface));
 374                cvmx_write_csr(CVMX_GMXX_PRTX_CFG(index, interface),
 375                               gmx_cfg.u64 & ~1ull);
 376
 377                cvmx_write_csr(CVMX_GMXX_RXX_ADR_CTL(index, interface),
 378                               control.u64);
 379                if (dev->flags & IFF_PROMISC)
 380                        cvmx_write_csr(CVMX_GMXX_RXX_ADR_CAM_EN
 381                                       (index, interface), 0);
 382                else
 383                        cvmx_write_csr(CVMX_GMXX_RXX_ADR_CAM_EN
 384                                       (index, interface), 1);
 385
 386                cvmx_write_csr(CVMX_GMXX_PRTX_CFG(index, interface),
 387                               gmx_cfg.u64);
 388        }
 389}
 390
 391/**
 392 * cvm_oct_common_set_mac_address - set the hardware MAC address for a device
 393 * @dev:    The device in question.
 394 * @addr:   Address structure to change it too.
 395
 396 * Returns Zero on success
 397 */
 398static int cvm_oct_common_set_mac_address(struct net_device *dev, void *addr)
 399{
 400        struct octeon_ethernet *priv = netdev_priv(dev);
 401        union cvmx_gmxx_prtx_cfg gmx_cfg;
 402        int interface = INTERFACE(priv->port);
 403        int index = INDEX(priv->port);
 404
 405        memcpy(dev->dev_addr, addr + 2, 6);
 406
 407        if ((interface < 2)
 408            && (cvmx_helper_interface_get_mode(interface) !=
 409                CVMX_HELPER_INTERFACE_MODE_SPI)) {
 410                int i;
 411                uint8_t *ptr = addr;
 412                uint64_t mac = 0;
 413                for (i = 0; i < 6; i++)
 414                        mac = (mac << 8) | (uint64_t) (ptr[i + 2]);
 415
 416                gmx_cfg.u64 =
 417                    cvmx_read_csr(CVMX_GMXX_PRTX_CFG(index, interface));
 418                cvmx_write_csr(CVMX_GMXX_PRTX_CFG(index, interface),
 419                               gmx_cfg.u64 & ~1ull);
 420
 421                cvmx_write_csr(CVMX_GMXX_SMACX(index, interface), mac);
 422                cvmx_write_csr(CVMX_GMXX_RXX_ADR_CAM0(index, interface),
 423                               ptr[2]);
 424                cvmx_write_csr(CVMX_GMXX_RXX_ADR_CAM1(index, interface),
 425                               ptr[3]);
 426                cvmx_write_csr(CVMX_GMXX_RXX_ADR_CAM2(index, interface),
 427                               ptr[4]);
 428                cvmx_write_csr(CVMX_GMXX_RXX_ADR_CAM3(index, interface),
 429                               ptr[5]);
 430                cvmx_write_csr(CVMX_GMXX_RXX_ADR_CAM4(index, interface),
 431                               ptr[6]);
 432                cvmx_write_csr(CVMX_GMXX_RXX_ADR_CAM5(index, interface),
 433                               ptr[7]);
 434                cvm_oct_common_set_multicast_list(dev);
 435                cvmx_write_csr(CVMX_GMXX_PRTX_CFG(index, interface),
 436                               gmx_cfg.u64);
 437        }
 438        return 0;
 439}
 440
 441/**
 442 * cvm_oct_common_init - per network device initialization
 443 * @dev:    Device to initialize
 444 *
 445 * Returns Zero on success
 446 */
 447int cvm_oct_common_init(struct net_device *dev)
 448{
 449        struct octeon_ethernet *priv = netdev_priv(dev);
 450        struct sockaddr sa;
 451        u64 mac = ((u64)(octeon_bootinfo->mac_addr_base[0] & 0xff) << 40) |
 452                ((u64)(octeon_bootinfo->mac_addr_base[1] & 0xff) << 32) |
 453                ((u64)(octeon_bootinfo->mac_addr_base[2] & 0xff) << 24) |
 454                ((u64)(octeon_bootinfo->mac_addr_base[3] & 0xff) << 16) |
 455                ((u64)(octeon_bootinfo->mac_addr_base[4] & 0xff) << 8) |
 456                (u64)(octeon_bootinfo->mac_addr_base[5] & 0xff);
 457
 458        mac += cvm_oct_mac_addr_offset;
 459        sa.sa_data[0] = (mac >> 40) & 0xff;
 460        sa.sa_data[1] = (mac >> 32) & 0xff;
 461        sa.sa_data[2] = (mac >> 24) & 0xff;
 462        sa.sa_data[3] = (mac >> 16) & 0xff;
 463        sa.sa_data[4] = (mac >> 8) & 0xff;
 464        sa.sa_data[5] = mac & 0xff;
 465
 466        if (cvm_oct_mac_addr_offset >= octeon_bootinfo->mac_addr_count)
 467                printk(KERN_DEBUG "%s: Using MAC outside of the assigned range:"
 468                        " %pM\n", dev->name, sa.sa_data);
 469        cvm_oct_mac_addr_offset++;
 470
 471        /*
 472         * Force the interface to use the POW send if always_use_pow
 473         * was specified or it is in the pow send list.
 474         */
 475        if ((pow_send_group != -1)
 476            && (always_use_pow || strstr(pow_send_list, dev->name)))
 477                priv->queue = -1;
 478
 479        if (priv->queue != -1) {
 480                dev->features |= NETIF_F_SG;
 481                if (USE_HW_TCPUDP_CHECKSUM)
 482                        dev->features |= NETIF_F_IP_CSUM;
 483        }
 484
 485        /* We do our own locking, Linux doesn't need to */
 486        dev->features |= NETIF_F_LLTX;
 487        SET_ETHTOOL_OPS(dev, &cvm_oct_ethtool_ops);
 488
 489        cvm_oct_phy_setup_device(dev);
 490        dev->netdev_ops->ndo_set_mac_address(dev, &sa);
 491        dev->netdev_ops->ndo_change_mtu(dev, dev->mtu);
 492
 493        /*
 494         * Zero out stats for port so we won't mistakenly show
 495         * counters from the bootloader.
 496         */
 497        memset(dev->netdev_ops->ndo_get_stats(dev), 0,
 498               sizeof(struct net_device_stats));
 499
 500        return 0;
 501}
 502
 503void cvm_oct_common_uninit(struct net_device *dev)
 504{
 505        struct octeon_ethernet *priv = netdev_priv(dev);
 506
 507        if (priv->phydev)
 508                phy_disconnect(priv->phydev);
 509}
 510
 511static const struct net_device_ops cvm_oct_npi_netdev_ops = {
 512        .ndo_init               = cvm_oct_common_init,
 513        .ndo_uninit             = cvm_oct_common_uninit,
 514        .ndo_start_xmit         = cvm_oct_xmit,
 515        .ndo_set_rx_mode        = cvm_oct_common_set_multicast_list,
 516        .ndo_set_mac_address    = cvm_oct_common_set_mac_address,
 517        .ndo_do_ioctl           = cvm_oct_ioctl,
 518        .ndo_change_mtu         = cvm_oct_common_change_mtu,
 519        .ndo_get_stats          = cvm_oct_common_get_stats,
 520#ifdef CONFIG_NET_POLL_CONTROLLER
 521        .ndo_poll_controller    = cvm_oct_poll_controller,
 522#endif
 523};
 524static const struct net_device_ops cvm_oct_xaui_netdev_ops = {
 525        .ndo_init               = cvm_oct_xaui_init,
 526        .ndo_uninit             = cvm_oct_xaui_uninit,
 527        .ndo_open               = cvm_oct_xaui_open,
 528        .ndo_stop               = cvm_oct_xaui_stop,
 529        .ndo_start_xmit         = cvm_oct_xmit,
 530        .ndo_set_rx_mode        = cvm_oct_common_set_multicast_list,
 531        .ndo_set_mac_address    = cvm_oct_common_set_mac_address,
 532        .ndo_do_ioctl           = cvm_oct_ioctl,
 533        .ndo_change_mtu         = cvm_oct_common_change_mtu,
 534        .ndo_get_stats          = cvm_oct_common_get_stats,
 535#ifdef CONFIG_NET_POLL_CONTROLLER
 536        .ndo_poll_controller    = cvm_oct_poll_controller,
 537#endif
 538};
 539static const struct net_device_ops cvm_oct_sgmii_netdev_ops = {
 540        .ndo_init               = cvm_oct_sgmii_init,
 541        .ndo_uninit             = cvm_oct_sgmii_uninit,
 542        .ndo_open               = cvm_oct_sgmii_open,
 543        .ndo_stop               = cvm_oct_sgmii_stop,
 544        .ndo_start_xmit         = cvm_oct_xmit,
 545        .ndo_set_rx_mode        = cvm_oct_common_set_multicast_list,
 546        .ndo_set_mac_address    = cvm_oct_common_set_mac_address,
 547        .ndo_do_ioctl           = cvm_oct_ioctl,
 548        .ndo_change_mtu         = cvm_oct_common_change_mtu,
 549        .ndo_get_stats          = cvm_oct_common_get_stats,
 550#ifdef CONFIG_NET_POLL_CONTROLLER
 551        .ndo_poll_controller    = cvm_oct_poll_controller,
 552#endif
 553};
 554static const struct net_device_ops cvm_oct_spi_netdev_ops = {
 555        .ndo_init               = cvm_oct_spi_init,
 556        .ndo_uninit             = cvm_oct_spi_uninit,
 557        .ndo_start_xmit         = cvm_oct_xmit,
 558        .ndo_set_rx_mode        = cvm_oct_common_set_multicast_list,
 559        .ndo_set_mac_address    = cvm_oct_common_set_mac_address,
 560        .ndo_do_ioctl           = cvm_oct_ioctl,
 561        .ndo_change_mtu         = cvm_oct_common_change_mtu,
 562        .ndo_get_stats          = cvm_oct_common_get_stats,
 563#ifdef CONFIG_NET_POLL_CONTROLLER
 564        .ndo_poll_controller    = cvm_oct_poll_controller,
 565#endif
 566};
 567static const struct net_device_ops cvm_oct_rgmii_netdev_ops = {
 568        .ndo_init               = cvm_oct_rgmii_init,
 569        .ndo_uninit             = cvm_oct_rgmii_uninit,
 570        .ndo_open               = cvm_oct_rgmii_open,
 571        .ndo_stop               = cvm_oct_rgmii_stop,
 572        .ndo_start_xmit         = cvm_oct_xmit,
 573        .ndo_set_rx_mode        = cvm_oct_common_set_multicast_list,
 574        .ndo_set_mac_address    = cvm_oct_common_set_mac_address,
 575        .ndo_do_ioctl           = cvm_oct_ioctl,
 576        .ndo_change_mtu         = cvm_oct_common_change_mtu,
 577        .ndo_get_stats          = cvm_oct_common_get_stats,
 578#ifdef CONFIG_NET_POLL_CONTROLLER
 579        .ndo_poll_controller    = cvm_oct_poll_controller,
 580#endif
 581};
 582static const struct net_device_ops cvm_oct_pow_netdev_ops = {
 583        .ndo_init               = cvm_oct_common_init,
 584        .ndo_start_xmit         = cvm_oct_xmit_pow,
 585        .ndo_set_rx_mode        = cvm_oct_common_set_multicast_list,
 586        .ndo_set_mac_address    = cvm_oct_common_set_mac_address,
 587        .ndo_do_ioctl           = cvm_oct_ioctl,
 588        .ndo_change_mtu         = cvm_oct_common_change_mtu,
 589        .ndo_get_stats          = cvm_oct_common_get_stats,
 590#ifdef CONFIG_NET_POLL_CONTROLLER
 591        .ndo_poll_controller    = cvm_oct_poll_controller,
 592#endif
 593};
 594
 595extern void octeon_mdiobus_force_mod_depencency(void);
 596
 597static int __init cvm_oct_init_module(void)
 598{
 599        int num_interfaces;
 600        int interface;
 601        int fau = FAU_NUM_PACKET_BUFFERS_TO_FREE;
 602        int qos;
 603
 604        octeon_mdiobus_force_mod_depencency();
 605        pr_notice("cavium-ethernet %s\n", OCTEON_ETHERNET_VERSION);
 606
 607        if (OCTEON_IS_MODEL(OCTEON_CN52XX))
 608                cvm_oct_mac_addr_offset = 2; /* First two are the mgmt ports. */
 609        else if (OCTEON_IS_MODEL(OCTEON_CN56XX))
 610                cvm_oct_mac_addr_offset = 1; /* First one is the mgmt port. */
 611        else
 612                cvm_oct_mac_addr_offset = 0;
 613
 614        cvm_oct_poll_queue = create_singlethread_workqueue("octeon-ethernet");
 615        if (cvm_oct_poll_queue == NULL) {
 616                pr_err("octeon-ethernet: Cannot create workqueue");
 617                return -ENOMEM;
 618        }
 619
 620        cvm_oct_configure_common_hw();
 621
 622        cvmx_helper_initialize_packet_io_global();
 623
 624        /* Change the input group for all ports before input is enabled */
 625        num_interfaces = cvmx_helper_get_number_of_interfaces();
 626        for (interface = 0; interface < num_interfaces; interface++) {
 627                int num_ports = cvmx_helper_ports_on_interface(interface);
 628                int port;
 629
 630                for (port = cvmx_helper_get_ipd_port(interface, 0);
 631                     port < cvmx_helper_get_ipd_port(interface, num_ports);
 632                     port++) {
 633                        union cvmx_pip_prt_tagx pip_prt_tagx;
 634                        pip_prt_tagx.u64 =
 635                            cvmx_read_csr(CVMX_PIP_PRT_TAGX(port));
 636                        pip_prt_tagx.s.grp = pow_receive_group;
 637                        cvmx_write_csr(CVMX_PIP_PRT_TAGX(port),
 638                                       pip_prt_tagx.u64);
 639                }
 640        }
 641
 642        cvmx_helper_ipd_and_packet_input_enable();
 643
 644        memset(cvm_oct_device, 0, sizeof(cvm_oct_device));
 645
 646        /*
 647         * Initialize the FAU used for counting packet buffers that
 648         * need to be freed.
 649         */
 650        cvmx_fau_atomic_write32(FAU_NUM_PACKET_BUFFERS_TO_FREE, 0);
 651
 652        /* Initialize the FAU used for counting tx SKBs that need to be freed */
 653        cvmx_fau_atomic_write32(FAU_TOTAL_TX_TO_CLEAN, 0);
 654
 655        if ((pow_send_group != -1)) {
 656                struct net_device *dev;
 657                pr_info("\tConfiguring device for POW only access\n");
 658                dev = alloc_etherdev(sizeof(struct octeon_ethernet));
 659                if (dev) {
 660                        /* Initialize the device private structure. */
 661                        struct octeon_ethernet *priv = netdev_priv(dev);
 662
 663                        dev->netdev_ops = &cvm_oct_pow_netdev_ops;
 664                        priv->imode = CVMX_HELPER_INTERFACE_MODE_DISABLED;
 665                        priv->port = CVMX_PIP_NUM_INPUT_PORTS;
 666                        priv->queue = -1;
 667                        strcpy(dev->name, "pow%d");
 668                        for (qos = 0; qos < 16; qos++)
 669                                skb_queue_head_init(&priv->tx_free_list[qos]);
 670
 671                        if (register_netdev(dev) < 0) {
 672                                pr_err("Failed to register ethernet device for POW\n");
 673                                free_netdev(dev);
 674                        } else {
 675                                cvm_oct_device[CVMX_PIP_NUM_INPUT_PORTS] = dev;
 676                                pr_info("%s: POW send group %d, receive group %d\n",
 677                                        dev->name, pow_send_group,
 678                                        pow_receive_group);
 679                        }
 680                } else {
 681                        pr_err("Failed to allocate ethernet device for POW\n");
 682                }
 683        }
 684
 685        num_interfaces = cvmx_helper_get_number_of_interfaces();
 686        for (interface = 0; interface < num_interfaces; interface++) {
 687                cvmx_helper_interface_mode_t imode =
 688                    cvmx_helper_interface_get_mode(interface);
 689                int num_ports = cvmx_helper_ports_on_interface(interface);
 690                int port;
 691
 692                for (port = cvmx_helper_get_ipd_port(interface, 0);
 693                     port < cvmx_helper_get_ipd_port(interface, num_ports);
 694                     port++) {
 695                        struct octeon_ethernet *priv;
 696                        struct net_device *dev =
 697                            alloc_etherdev(sizeof(struct octeon_ethernet));
 698                        if (!dev) {
 699                                pr_err("Failed to allocate ethernet device for port %d\n", port);
 700                                continue;
 701                        }
 702
 703                        /* Initialize the device private structure. */
 704                        priv = netdev_priv(dev);
 705
 706                        INIT_DELAYED_WORK(&priv->port_periodic_work,
 707                                          cvm_oct_periodic_worker);
 708                        priv->imode = imode;
 709                        priv->port = port;
 710                        priv->queue = cvmx_pko_get_base_queue(priv->port);
 711                        priv->fau = fau - cvmx_pko_get_num_queues(port) * 4;
 712                        for (qos = 0; qos < 16; qos++)
 713                                skb_queue_head_init(&priv->tx_free_list[qos]);
 714                        for (qos = 0; qos < cvmx_pko_get_num_queues(port);
 715                             qos++)
 716                                cvmx_fau_atomic_write32(priv->fau + qos * 4, 0);
 717
 718                        switch (priv->imode) {
 719
 720                        /* These types don't support ports to IPD/PKO */
 721                        case CVMX_HELPER_INTERFACE_MODE_DISABLED:
 722                        case CVMX_HELPER_INTERFACE_MODE_PCIE:
 723                        case CVMX_HELPER_INTERFACE_MODE_PICMG:
 724                                break;
 725
 726                        case CVMX_HELPER_INTERFACE_MODE_NPI:
 727                                dev->netdev_ops = &cvm_oct_npi_netdev_ops;
 728                                strcpy(dev->name, "npi%d");
 729                                break;
 730
 731                        case CVMX_HELPER_INTERFACE_MODE_XAUI:
 732                                dev->netdev_ops = &cvm_oct_xaui_netdev_ops;
 733                                strcpy(dev->name, "xaui%d");
 734                                break;
 735
 736                        case CVMX_HELPER_INTERFACE_MODE_LOOP:
 737                                dev->netdev_ops = &cvm_oct_npi_netdev_ops;
 738                                strcpy(dev->name, "loop%d");
 739                                break;
 740
 741                        case CVMX_HELPER_INTERFACE_MODE_SGMII:
 742                                dev->netdev_ops = &cvm_oct_sgmii_netdev_ops;
 743                                strcpy(dev->name, "eth%d");
 744                                break;
 745
 746                        case CVMX_HELPER_INTERFACE_MODE_SPI:
 747                                dev->netdev_ops = &cvm_oct_spi_netdev_ops;
 748                                strcpy(dev->name, "spi%d");
 749                                break;
 750
 751                        case CVMX_HELPER_INTERFACE_MODE_RGMII:
 752                        case CVMX_HELPER_INTERFACE_MODE_GMII:
 753                                dev->netdev_ops = &cvm_oct_rgmii_netdev_ops;
 754                                strcpy(dev->name, "eth%d");
 755                                break;
 756                        }
 757
 758                        if (!dev->netdev_ops) {
 759                                free_netdev(dev);
 760                        } else if (register_netdev(dev) < 0) {
 761                                pr_err("Failed to register ethernet device "
 762                                         "for interface %d, port %d\n",
 763                                         interface, priv->port);
 764                                free_netdev(dev);
 765                        } else {
 766                                cvm_oct_device[priv->port] = dev;
 767                                fau -=
 768                                    cvmx_pko_get_num_queues(priv->port) *
 769                                    sizeof(uint32_t);
 770                                queue_delayed_work(cvm_oct_poll_queue,
 771                                                   &priv->port_periodic_work, HZ);
 772                        }
 773                }
 774        }
 775
 776        cvm_oct_tx_initialize();
 777        cvm_oct_rx_initialize();
 778
 779        /*
 780         * 150 uS: about 10 1500-byte packtes at 1GE.
 781         */
 782        cvm_oct_tx_poll_interval = 150 * (octeon_get_clock_rate() / 1000000);
 783
 784        queue_delayed_work(cvm_oct_poll_queue, &cvm_oct_rx_refill_work, HZ);
 785
 786        return 0;
 787}
 788
 789static void __exit cvm_oct_cleanup_module(void)
 790{
 791        int port;
 792
 793        /* Disable POW interrupt */
 794        cvmx_write_csr(CVMX_POW_WQ_INT_THRX(pow_receive_group), 0);
 795
 796        cvmx_ipd_disable();
 797
 798        /* Free the interrupt handler */
 799        free_irq(OCTEON_IRQ_WORKQ0 + pow_receive_group, cvm_oct_device);
 800
 801        atomic_inc_return(&cvm_oct_poll_queue_stopping);
 802        cancel_delayed_work_sync(&cvm_oct_rx_refill_work);
 803
 804        cvm_oct_rx_shutdown();
 805        cvm_oct_tx_shutdown();
 806
 807        cvmx_pko_disable();
 808
 809        /* Free the ethernet devices */
 810        for (port = 0; port < TOTAL_NUMBER_OF_PORTS; port++) {
 811                if (cvm_oct_device[port]) {
 812                        struct net_device *dev = cvm_oct_device[port];
 813                        struct octeon_ethernet *priv = netdev_priv(dev);
 814                        cancel_delayed_work_sync(&priv->port_periodic_work);
 815
 816                        cvm_oct_tx_shutdown_dev(dev);
 817                        unregister_netdev(dev);
 818                        free_netdev(dev);
 819                        cvm_oct_device[port] = NULL;
 820                }
 821        }
 822
 823        destroy_workqueue(cvm_oct_poll_queue);
 824
 825        cvmx_pko_shutdown();
 826
 827        cvmx_ipd_free_ptr();
 828
 829        /* Free the HW pools */
 830        cvm_oct_mem_empty_fpa(CVMX_FPA_PACKET_POOL, CVMX_FPA_PACKET_POOL_SIZE,
 831                              num_packet_buffers);
 832        cvm_oct_mem_empty_fpa(CVMX_FPA_WQE_POOL, CVMX_FPA_WQE_POOL_SIZE,
 833                              num_packet_buffers);
 834        if (CVMX_FPA_OUTPUT_BUFFER_POOL != CVMX_FPA_PACKET_POOL)
 835                cvm_oct_mem_empty_fpa(CVMX_FPA_OUTPUT_BUFFER_POOL,
 836                                      CVMX_FPA_OUTPUT_BUFFER_POOL_SIZE, 128);
 837}
 838
 839MODULE_LICENSE("GPL");
 840MODULE_AUTHOR("Cavium Networks <support@caviumnetworks.com>");
 841MODULE_DESCRIPTION("Cavium Networks Octeon ethernet driver.");
 842module_init(cvm_oct_init_module);
 843module_exit(cvm_oct_cleanup_module);
 844