net/i40e: warn when writing global registers
[dpdk.git] / drivers / net / octeontx / octeontx_ethdev.c
index 706cf88..06aa0a2 100644 (file)
@@ -1,34 +1,7 @@
-/*
- *   BSD LICENSE
- *
- *   Copyright (C) Cavium Inc. 2017. All rights reserved.
- *
- *   Redistribution and use in source and binary forms, with or without
- *   modification, are permitted provided that the following conditions
- *   are met:
- *
- *     * Redistributions of source code must retain the above copyright
- *       notice, this list of conditions and the following disclaimer.
- *     * Redistributions in binary form must reproduce the above copyright
- *       notice, this list of conditions and the following disclaimer in
- *       the documentation and/or other materials provided with the
- *       distribution.
- *     * Neither the name of Cavium networks nor the names of its
- *       contributors may be used to endorse or promote products derived
- *       from this software without specific prior written permission.
- *
- *   THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- *   "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- *   LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- *   A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
- *   OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- *   SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
- *   LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
- *   DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- *   THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- *   (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- *   OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+/* SPDX-License-Identifier: BSD-3-Clause
+ * Copyright(c) 2017 Cavium, Inc
  */
+
 #include <stdio.h>
 #include <stdarg.h>
 #include <stdbool.h>
@@ -44,7 +17,7 @@
 #include <rte_kvargs.h>
 #include <rte_malloc.h>
 #include <rte_prefetch.h>
-#include <rte_vdev.h>
+#include <rte_bus_vdev.h>
 
 #include "octeontx_ethdev.h"
 #include "octeontx_rxtx.h"
@@ -54,6 +27,9 @@ struct octeontx_vdev_init_params {
        uint8_t nr_port;
 };
 
+uint16_t
+rte_octeontx_pchan_map[OCTEONTX_MAX_BGX_PORTS][OCTEONTX_MAX_LMAC_PER_BGX];
+
 enum octeontx_link_speed {
        OCTEONTX_LINK_SPEED_SGMII,
        OCTEONTX_LINK_SPEED_XAUI,
@@ -65,6 +41,27 @@ enum octeontx_link_speed {
        OCTEONTX_LINK_SPEED_RESERVE2
 };
 
+int otx_net_logtype_mbox;
+int otx_net_logtype_init;
+int otx_net_logtype_driver;
+
+RTE_INIT(otx_net_init_log);
+static void
+otx_net_init_log(void)
+{
+       otx_net_logtype_mbox = rte_log_register("pmd.net.octeontx.mbox");
+       if (otx_net_logtype_mbox >= 0)
+               rte_log_set_level(otx_net_logtype_mbox, RTE_LOG_NOTICE);
+
+       otx_net_logtype_init = rte_log_register("pmd.net.octeontx.init");
+       if (otx_net_logtype_init >= 0)
+               rte_log_set_level(otx_net_logtype_init, RTE_LOG_NOTICE);
+
+       otx_net_logtype_driver = rte_log_register("pmd.net.octeontx.driver");
+       if (otx_net_logtype_driver >= 0)
+               rte_log_set_level(otx_net_logtype_driver, RTE_LOG_NOTICE);
+}
+
 /* Parse integer from integer argument */
 static int
 parse_integer_arg(const char *key __rte_unused,
@@ -161,6 +158,14 @@ octeontx_port_close(struct octeontx_nic *nic)
        octeontx_log_dbg("port closed %d", nic->port_id);
 }
 
+static int
+octeontx_port_start(struct octeontx_nic *nic)
+{
+       PMD_INIT_FUNC_TRACE();
+
+       return octeontx_bgx_port_start(nic->port_id);
+}
+
 static int
 octeontx_port_stop(struct octeontx_nic *nic)
 {
@@ -191,7 +196,7 @@ octeontx_port_promisc_set(struct octeontx_nic *nic, int en)
                        nic->port_id, en ? "set" : "unset");
 }
 
-static void
+static int
 octeontx_port_stats(struct octeontx_nic *nic, struct rte_eth_stats *stats)
 {
        octeontx_mbox_bgx_port_stats_t bgx_stats;
@@ -200,8 +205,10 @@ octeontx_port_stats(struct octeontx_nic *nic, struct rte_eth_stats *stats)
        PMD_INIT_FUNC_TRACE();
 
        res = octeontx_bgx_port_stats(nic->port_id, &bgx_stats);
-       if (res < 0)
+       if (res < 0) {
                octeontx_log_err("failed to get port stats %d", nic->port_id);
+               return res;
+       }
 
        stats->ipackets = bgx_stats.rx_packets;
        stats->ibytes = bgx_stats.rx_bytes;
@@ -213,6 +220,8 @@ octeontx_port_stats(struct octeontx_nic *nic, struct rte_eth_stats *stats)
 
        octeontx_log_dbg("port%d stats inpkts=%" PRIx64 " outpkts=%" PRIx64 "",
                        nic->port_id, stats->ipackets, stats->opackets);
+
+       return 0;
 }
 
 static void
@@ -336,6 +345,130 @@ octeontx_dev_configure(struct rte_eth_dev *dev)
        return 0;
 }
 
+static void
+octeontx_dev_close(struct rte_eth_dev *dev)
+{
+       struct octeontx_txq *txq = NULL;
+       struct octeontx_nic *nic = octeontx_pmd_priv(dev);
+       unsigned int i;
+       int ret;
+
+       PMD_INIT_FUNC_TRACE();
+
+       rte_event_dev_close(nic->evdev);
+
+       ret = octeontx_pko_channel_close(nic->base_ochan);
+       if (ret < 0) {
+               octeontx_log_err("failed to close channel %d VF%d %d %d",
+                            nic->base_ochan, nic->port_id, nic->num_tx_queues,
+                            ret);
+       }
+       /* Free txq resources for this port */
+       for (i = 0; i < nic->num_tx_queues; i++) {
+               txq = dev->data->tx_queues[i];
+               if (!txq)
+                       continue;
+
+               rte_free(txq);
+       }
+}
+
+static int
+octeontx_dev_start(struct rte_eth_dev *dev)
+{
+       struct octeontx_nic *nic = octeontx_pmd_priv(dev);
+       int ret;
+
+       ret = 0;
+
+       PMD_INIT_FUNC_TRACE();
+       /*
+        * Tx start
+        */
+       dev->tx_pkt_burst = octeontx_xmit_pkts;
+       ret = octeontx_pko_channel_start(nic->base_ochan);
+       if (ret < 0) {
+               octeontx_log_err("fail to conf VF%d no. txq %d chan %d ret %d",
+                          nic->port_id, nic->num_tx_queues, nic->base_ochan,
+                          ret);
+               goto error;
+       }
+
+       /*
+        * Rx start
+        */
+       dev->rx_pkt_burst = octeontx_recv_pkts;
+       ret = octeontx_pki_port_start(nic->port_id);
+       if (ret < 0) {
+               octeontx_log_err("fail to start Rx on port %d", nic->port_id);
+               goto channel_stop_error;
+       }
+
+       /*
+        * Start port
+        */
+       ret = octeontx_port_start(nic);
+       if (ret < 0) {
+               octeontx_log_err("failed start port %d", ret);
+               goto pki_port_stop_error;
+       }
+
+       PMD_TX_LOG(DEBUG, "pko: start channel %d no.of txq %d port %d",
+                       nic->base_ochan, nic->num_tx_queues, nic->port_id);
+
+       ret = rte_event_dev_start(nic->evdev);
+       if (ret < 0) {
+               octeontx_log_err("failed to start evdev: ret (%d)", ret);
+               goto pki_port_stop_error;
+       }
+
+       /* Success */
+       return ret;
+
+pki_port_stop_error:
+       octeontx_pki_port_stop(nic->port_id);
+channel_stop_error:
+       octeontx_pko_channel_stop(nic->base_ochan);
+error:
+       return ret;
+}
+
+static void
+octeontx_dev_stop(struct rte_eth_dev *dev)
+{
+       struct octeontx_nic *nic = octeontx_pmd_priv(dev);
+       int ret;
+
+       PMD_INIT_FUNC_TRACE();
+
+       rte_event_dev_stop(nic->evdev);
+
+       ret = octeontx_port_stop(nic);
+       if (ret < 0) {
+               octeontx_log_err("failed to req stop port %d res=%d",
+                                       nic->port_id, ret);
+               return;
+       }
+
+       ret = octeontx_pki_port_stop(nic->port_id);
+       if (ret < 0) {
+               octeontx_log_err("failed to stop pki port %d res=%d",
+                                       nic->port_id, ret);
+               return;
+       }
+
+       ret = octeontx_pko_channel_stop(nic->base_ochan);
+       if (ret < 0) {
+               octeontx_log_err("failed to stop channel %d VF%d %d %d",
+                            nic->base_ochan, nic->port_id, nic->num_tx_queues,
+                            ret);
+               return;
+       }
+
+       dev->tx_pkt_burst = NULL;
+       dev->rx_pkt_burst = NULL;
+}
+
 static void
 octeontx_dev_promisc_enable(struct rte_eth_dev *dev)
 {
@@ -436,19 +569,19 @@ octeontx_dev_link_update(struct rte_eth_dev *dev,
                break;
        }
 
-       link.link_duplex = ETH_LINK_AUTONEG;
-       link.link_autoneg = ETH_LINK_SPEED_AUTONEG;
+       link.link_duplex = ETH_LINK_FULL_DUPLEX;
+       link.link_autoneg = ETH_LINK_AUTONEG;
 
        return octeontx_atomic_write_link_status(dev, &link);
 }
 
-static void
+static int
 octeontx_dev_stats_get(struct rte_eth_dev *dev, struct rte_eth_stats *stats)
 {
        struct octeontx_nic *nic = octeontx_pmd_priv(dev);
 
        PMD_INIT_FUNC_TRACE();
-       octeontx_port_stats(nic, stats);
+       return octeontx_port_stats(nic, stats);
 }
 
 static void
@@ -794,6 +927,7 @@ octeontx_dev_rx_queue_setup(struct rte_eth_dev *dev, uint16_t qidx,
                        pki_hash.tag_slc = 1;
                        pki_hash.tag_dlf = 1;
                        pki_hash.tag_slf = 1;
+                       pki_hash.tag_prt = 1;
                        octeontx_pki_port_hash_config(port, &pki_hash);
                }
 
@@ -805,7 +939,7 @@ octeontx_dev_rx_queue_setup(struct rte_eth_dev *dev, uint16_t qidx,
                pki_qos.qpg_qos = PKI_QPG_QOS_NONE;
                pki_qos.num_entry = 1;
                pki_qos.drop_policy = 0;
-               pki_qos.tag_type = 2L;
+               pki_qos.tag_type = 0L;
                pki_qos.qos_entry[0].port_add = 0;
                pki_qos.qos_entry[0].gaura = gaura;
                pki_qos.qos_entry[0].ggrp_ok = ev_queues;
@@ -861,10 +995,24 @@ octeontx_dev_supported_ptypes_get(struct rte_eth_dev *dev)
        return NULL;
 }
 
+static int
+octeontx_pool_ops(struct rte_eth_dev *dev, const char *pool)
+{
+       RTE_SET_USED(dev);
+
+       if (!strcmp(pool, "octeontx_fpavf"))
+               return 0;
+
+       return -ENOTSUP;
+}
+
 /* Initialize and register driver with DPDK Application */
 static const struct eth_dev_ops octeontx_dev_ops = {
        .dev_configure           = octeontx_dev_configure,
        .dev_infos_get           = octeontx_dev_info,
+       .dev_close               = octeontx_dev_close,
+       .dev_start               = octeontx_dev_start,
+       .dev_stop                = octeontx_dev_stop,
        .promiscuous_enable      = octeontx_dev_promisc_enable,
        .promiscuous_disable     = octeontx_dev_promisc_disable,
        .link_update             = octeontx_dev_link_update,
@@ -878,6 +1026,7 @@ static const struct eth_dev_ops octeontx_dev_ops = {
        .rx_queue_setup          = octeontx_dev_rx_queue_setup,
        .rx_queue_release        = octeontx_dev_rx_queue_release,
        .dev_supported_ptypes_get = octeontx_dev_supported_ptypes_get,
+       .pool_ops_supported      = octeontx_pool_ops,
 };
 
 /* Create Ethdev interface per BGX LMAC ports */
@@ -900,6 +1049,8 @@ octeontx_create(struct rte_vdev_device *dev, int port, uint8_t evdev,
                if (eth_dev == NULL)
                        return -ENODEV;
 
+               eth_dev->tx_pkt_burst = octeontx_xmit_pkts;
+               eth_dev->rx_pkt_burst = octeontx_recv_pkts;
                return 0;
        }
 
@@ -991,6 +1142,9 @@ octeontx_create(struct rte_vdev_device *dev, int port, uint8_t evdev,
                                nic->num_tx_queues);
        PMD_INIT_LOG(DEBUG, "speed %d mtu %d", nic->speed, nic->mtu);
 
+       rte_octeontx_pchan_map[(nic->base_ochan >> 8) & 0x7]
+               [(nic->base_ochan >> 4) & 0xF] = data->port_id;
+
        return data->port_id;
 
 err: