From: Alfredo Cardigliano <cardigliano@ntop.org>
To: Alfredo Cardigliano <cardigliano@ntop.org>,
John McNamara <john.mcnamara@intel.com>,
Marko Kovacevic <marko.kovacevic@intel.com>
Cc: dev@dpdk.org
Subject: [dpdk-dev] [PATCH v2 10/17] net/ionic: add basic port operations
Date: Tue, 15 Oct 2019 10:22:28 +0200 [thread overview]
Message-ID: <20191015082235.28639-11-cardigliano@ntop.org> (raw)
In-Reply-To: <20191015082235.28639-1-cardigliano@ntop.org>
Add support for port start/stop and handle basic features
including mtu and link up/down.
Signed-off-by: Alfredo Cardigliano <cardigliano@ntop.org>
Reviewed-by: Shannon Nelson <snelson@pensando.io>
---
doc/guides/nics/features/ionic.ini | 4 +
drivers/net/ionic/ionic.h | 1 +
drivers/net/ionic/ionic_dev.h | 3 +
drivers/net/ionic/ionic_ethdev.c | 316 +++++++++++++++++++++++++++++
drivers/net/ionic/ionic_lif.c | 268 ++++++++++++++++++++++++
drivers/net/ionic/ionic_lif.h | 9 +
drivers/net/ionic/ionic_osdep.h | 2 +
7 files changed, 603 insertions(+)
diff --git a/doc/guides/nics/features/ionic.ini b/doc/guides/nics/features/ionic.ini
index 6915d9c42..c69e5cbed 100644
--- a/doc/guides/nics/features/ionic.ini
+++ b/doc/guides/nics/features/ionic.ini
@@ -4,6 +4,10 @@
; Refer to default.ini for the full list of available PMD features.
;
[Features]
+Speed capabilities = Y
+Link status = Y
+Link status event = Y
+MTU update = Y
Linux UIO = Y
Linux VFIO = Y
x86-64 = Y
diff --git a/drivers/net/ionic/ionic.h b/drivers/net/ionic/ionic.h
index 53836be64..05f1df061 100644
--- a/drivers/net/ionic/ionic.h
+++ b/drivers/net/ionic/ionic.h
@@ -54,6 +54,7 @@ struct ionic_adapter {
uint32_t nlifs;
uint32_t max_ntxqs_per_lif;
uint32_t max_nrxqs_per_lif;
+ uint32_t max_mac_addrs;
uint32_t link_speed;
uint32_t nintrs;
bool intrs[IONIC_INTR_CTRL_REGS_MAX];
diff --git a/drivers/net/ionic/ionic_dev.h b/drivers/net/ionic/ionic_dev.h
index ada07edff..02fcfdee8 100644
--- a/drivers/net/ionic/ionic_dev.h
+++ b/drivers/net/ionic/ionic_dev.h
@@ -20,6 +20,9 @@
*/
#define IONIC_API_VERSION "3"
+#define IONIC_MIN_MTU RTE_ETHER_MIN_MTU
+#define IONIC_MAX_MTU 9194
+
#define IONIC_MAX_RING_DESC 32768
#define IONIC_MIN_RING_DESC 16
diff --git a/drivers/net/ionic/ionic_ethdev.c b/drivers/net/ionic/ionic_ethdev.c
index 8e692da45..a0ab38435 100644
--- a/drivers/net/ionic/ionic_ethdev.c
+++ b/drivers/net/ionic/ionic_ethdev.c
@@ -18,6 +18,17 @@
static int eth_ionic_dev_init(struct rte_eth_dev *eth_dev, void *init_params);
static int eth_ionic_dev_uninit(struct rte_eth_dev *eth_dev);
+static int ionic_dev_info_get(struct rte_eth_dev *eth_dev,
+ struct rte_eth_dev_info *dev_info);
+static int ionic_dev_configure(struct rte_eth_dev *dev);
+static int ionic_dev_mtu_set(struct rte_eth_dev *dev, uint16_t mtu);
+static int ionic_dev_start(struct rte_eth_dev *dev);
+static void ionic_dev_stop(struct rte_eth_dev *dev);
+static void ionic_dev_close(struct rte_eth_dev *dev);
+static int ionic_dev_set_link_up(struct rte_eth_dev *dev);
+static int ionic_dev_set_link_down(struct rte_eth_dev *dev);
+static int ionic_dev_link_update(struct rte_eth_dev *eth_dev,
+ int wait_to_complete);
int ionic_logtype_init;
int ionic_logtype_driver;
@@ -30,6 +41,15 @@ static const struct rte_pci_id pci_id_ionic_map[] = {
};
static const struct eth_dev_ops ionic_eth_dev_ops = {
+ .dev_infos_get = ionic_dev_info_get,
+ .dev_configure = ionic_dev_configure,
+ .mtu_set = ionic_dev_mtu_set,
+ .dev_start = ionic_dev_start,
+ .dev_stop = ionic_dev_stop,
+ .dev_close = ionic_dev_close,
+ .link_update = ionic_dev_link_update,
+ .dev_set_link_up = ionic_dev_set_link_up,
+ .dev_set_link_down = ionic_dev_set_link_down,
};
/*
@@ -40,6 +60,104 @@ static LIST_HEAD(ionic_pci_adapters_list, ionic_adapter) ionic_pci_adapters =
LIST_HEAD_INITIALIZER(ionic_pci_adapters);
static rte_spinlock_t ionic_pci_adapters_lock = RTE_SPINLOCK_INITIALIZER;
+/*
+ * Set device link up, enable tx.
+ */
+static int
+ionic_dev_set_link_up(struct rte_eth_dev *eth_dev)
+{
+ struct ionic_lif *lif = IONIC_ETH_DEV_TO_LIF(eth_dev);
+ struct ionic_adapter *adapter = lif->adapter;
+ struct ionic_dev *idev = &adapter->idev;
+ int err;
+
+ ionic_init_print_call();
+
+ ionic_dev_cmd_port_state(idev, IONIC_PORT_ADMIN_STATE_UP);
+
+ err = ionic_dev_cmd_wait_check(idev, IONIC_DEVCMD_TIMEOUT);
+
+ if (err) {
+ ionic_init_print(WARNING, "Failed to bring port UP\n");
+ return err;
+ }
+
+ return 0;
+}
+
+/*
+ * Set device link down, disable tx.
+ */
+static int
+ionic_dev_set_link_down(struct rte_eth_dev *eth_dev)
+{
+ struct ionic_lif *lif = IONIC_ETH_DEV_TO_LIF(eth_dev);
+ struct ionic_adapter *adapter = lif->adapter;
+ struct ionic_dev *idev = &adapter->idev;
+ int err;
+
+ ionic_init_print_call();
+
+ ionic_dev_cmd_port_state(idev, IONIC_PORT_ADMIN_STATE_DOWN);
+
+ err = ionic_dev_cmd_wait_check(idev, IONIC_DEVCMD_TIMEOUT);
+
+ if (err) {
+ ionic_init_print(WARNING, "Failed to bring port DOWN\n");
+ return err;
+ }
+
+ return 0;
+}
+
+static int
+ionic_dev_link_update(struct rte_eth_dev *eth_dev,
+ int wait_to_complete __rte_unused)
+{
+ struct ionic_lif *lif = IONIC_ETH_DEV_TO_LIF(eth_dev);
+ struct ionic_adapter *adapter = lif->adapter;
+ struct rte_eth_link link;
+
+ ionic_init_print_call();
+
+ /* Initialize */
+ memset(&link, 0, sizeof(link));
+ link.link_autoneg = ETH_LINK_AUTONEG;
+
+ if (!adapter->link_up) {
+ /* Interface is down */
+ link.link_status = ETH_LINK_DOWN;
+ link.link_duplex = ETH_LINK_HALF_DUPLEX;
+ link.link_speed = ETH_SPEED_NUM_NONE;
+ } else {
+ /* Interface is up */
+ link.link_status = ETH_LINK_UP;
+ link.link_duplex = ETH_LINK_FULL_DUPLEX;
+ switch (adapter->link_speed) {
+ case 10000:
+ link.link_speed = ETH_SPEED_NUM_10G;
+ break;
+ case 25000:
+ link.link_speed = ETH_SPEED_NUM_25G;
+ break;
+ case 40000:
+ link.link_speed = ETH_SPEED_NUM_40G;
+ break;
+ case 50000:
+ link.link_speed = ETH_SPEED_NUM_50G;
+ break;
+ case 100000:
+ link.link_speed = ETH_SPEED_NUM_100G;
+ break;
+ default:
+ link.link_speed = ETH_SPEED_NUM_NONE;
+ break;
+ }
+ }
+
+ return rte_eth_linkstatus_set(eth_dev, &link);
+}
+
/**
* Interrupt handler triggered by NIC for handling
* specific interrupt.
@@ -64,6 +182,184 @@ ionic_dev_interrupt_handler(void *param)
}
}
+static int
+ionic_dev_mtu_set(struct rte_eth_dev *eth_dev, uint16_t mtu)
+{
+ struct ionic_lif *lif = IONIC_ETH_DEV_TO_LIF(eth_dev);
+ /*
+ * Size = MTU + Ethernet header + VLAN + QinQ
+ * Also add ETHER_CRC_LEN if the adapter is able to keep CRC
+ */
+ uint32_t frame_size = mtu + RTE_ETHER_HDR_LEN + 4 + 4;
+ int err;
+
+ ionic_init_print_call();
+
+ /* Check that mtu is within the allowed range */
+ if (mtu < IONIC_MIN_MTU || mtu > IONIC_MAX_MTU)
+ return -EINVAL;
+
+ err = ionic_lif_change_mtu(lif, mtu);
+
+ if (err)
+ return err;
+
+ /* Update max frame size */
+ eth_dev->data->dev_conf.rxmode.max_rx_pkt_len = frame_size;
+
+ return 0;
+}
+
+static int
+ionic_dev_info_get(struct rte_eth_dev *eth_dev,
+ struct rte_eth_dev_info *dev_info)
+{
+ struct ionic_lif *lif = IONIC_ETH_DEV_TO_LIF(eth_dev);
+ struct ionic_adapter *adapter = lif->adapter;
+ struct ionic_identity *ident = &adapter->ident;
+
+ ionic_init_print_call();
+
+ dev_info->max_rx_queues = (uint16_t)
+ ident->lif.eth.config.queue_count[IONIC_QTYPE_RXQ];
+ dev_info->max_tx_queues = (uint16_t)
+ ident->lif.eth.config.queue_count[IONIC_QTYPE_TXQ];
+ /* Also add ETHER_CRC_LEN if the adapter is able to keep CRC */
+ dev_info->min_rx_bufsize = IONIC_MIN_MTU + RTE_ETHER_HDR_LEN;
+ dev_info->max_rx_pktlen = IONIC_MAX_MTU + RTE_ETHER_HDR_LEN;
+ dev_info->max_mac_addrs = adapter->max_mac_addrs;
+
+ dev_info->speed_capa =
+ ETH_LINK_SPEED_10G |
+ ETH_LINK_SPEED_25G |
+ ETH_LINK_SPEED_40G |
+ ETH_LINK_SPEED_50G |
+ ETH_LINK_SPEED_100G;
+
+ return 0;
+}
+
+static int
+ionic_dev_configure(struct rte_eth_dev *eth_dev)
+{
+ struct ionic_lif *lif = IONIC_ETH_DEV_TO_LIF(eth_dev);
+ int err;
+
+ ionic_init_print_call();
+
+ err = ionic_lif_configure(lif);
+
+ if (err) {
+ ionic_drv_print(ERR, "Cannot configure LIF: %d", err);
+ return err;
+ }
+
+ return 0;
+}
+
+static inline uint32_t
+ionic_parse_link_speeds(uint16_t link_speeds)
+{
+ if (link_speeds & ETH_LINK_SPEED_100G)
+ return 100000;
+ else if (link_speeds & ETH_LINK_SPEED_50G)
+ return 50000;
+ else if (link_speeds & ETH_LINK_SPEED_40G)
+ return 40000;
+ else if (link_speeds & ETH_LINK_SPEED_25G)
+ return 25000;
+ else if (link_speeds & ETH_LINK_SPEED_10G)
+ return 10000;
+ else
+ return 0;
+}
+
+/*
+ * Configure device link speed and setup link.
+ * It returns 0 on success.
+ */
+static int
+ionic_dev_start(struct rte_eth_dev *eth_dev)
+{
+ struct rte_eth_conf *dev_conf = ð_dev->data->dev_conf;
+ struct ionic_lif *lif = IONIC_ETH_DEV_TO_LIF(eth_dev);
+ struct ionic_adapter *adapter = lif->adapter;
+ struct ionic_dev *idev = &adapter->idev;
+ uint32_t allowed_speeds;
+ int err;
+
+ ionic_init_print_call();
+
+ err = ionic_lif_start(lif);
+
+ if (err) {
+ ionic_drv_print(ERR, "Cannot start LIF: %d", err);
+ return err;
+ }
+
+ if (eth_dev->data->dev_conf.link_speeds & ETH_LINK_SPEED_FIXED) {
+ uint32_t speed = ionic_parse_link_speeds(dev_conf->link_speeds);
+
+ if (speed)
+ ionic_dev_cmd_port_speed(idev, speed);
+ }
+
+ allowed_speeds =
+ ETH_LINK_SPEED_FIXED |
+ ETH_LINK_SPEED_10G |
+ ETH_LINK_SPEED_25G |
+ ETH_LINK_SPEED_40G |
+ ETH_LINK_SPEED_50G |
+ ETH_LINK_SPEED_100G;
+
+ if (dev_conf->link_speeds & ~allowed_speeds) {
+ ionic_init_print(ERR, "Invalid link setting");
+ return -EINVAL;
+ }
+
+ ionic_dev_link_update(eth_dev, 0);
+
+ return 0;
+}
+
+/*
+ * Stop device: disable rx and tx functions to allow for reconfiguring.
+ */
+static void
+ionic_dev_stop(struct rte_eth_dev *eth_dev)
+{
+ struct ionic_lif *lif = IONIC_ETH_DEV_TO_LIF(eth_dev);
+ int err;
+
+ ionic_init_print_call();
+
+ err = ionic_lif_stop(lif);
+
+ if (err) {
+ ionic_drv_print(ERR, "Cannot stop LIF: %d", err);
+ return;
+ }
+}
+
+/*
+ * Reset and stop device.
+ */
+static void
+ionic_dev_close(struct rte_eth_dev *eth_dev)
+{
+ struct ionic_lif *lif = IONIC_ETH_DEV_TO_LIF(eth_dev);
+ int err;
+
+ ionic_init_print_call();
+
+ err = ionic_lif_stop(lif);
+
+ if (err) {
+ ionic_drv_print(ERR, "Cannot stop LIF: %d", err);
+ return;
+ }
+}
+
static int
eth_ionic_dev_init(struct rte_eth_dev *eth_dev, void *init_params)
{
@@ -87,6 +383,20 @@ eth_ionic_dev_init(struct rte_eth_dev *eth_dev, void *init_params)
lif->adapter = adapter;
adapter->lifs[adapter->nlifs] = lif;
+ ionic_init_print(DEBUG, "Up to %u MAC addresses supported",
+ adapter->max_mac_addrs);
+
+ /* Allocate memory for storing MAC addresses */
+ eth_dev->data->mac_addrs = rte_zmalloc("ionic",
+ RTE_ETHER_ADDR_LEN * adapter->max_mac_addrs, 0);
+
+ if (eth_dev->data->mac_addrs == NULL) {
+ ionic_init_print(ERR, "Failed to allocate %u bytes needed to "
+ "store MAC addresses",
+ RTE_ETHER_ADDR_LEN * adapter->max_mac_addrs);
+ return -ENOMEM;
+ }
+
err = ionic_lif_alloc(lif);
if (err) {
@@ -102,6 +412,10 @@ eth_ionic_dev_init(struct rte_eth_dev *eth_dev, void *init_params)
return err;
}
+ /* Copy the MAC address */
+ rte_ether_addr_copy((struct rte_ether_addr *)lif->mac_addr,
+ ð_dev->data->mac_addrs[0]);
+
ionic_init_print(DEBUG, "Port %u initialized", eth_dev->data->port_id);
return 0;
@@ -297,6 +611,8 @@ eth_ionic_pci_probe(struct rte_pci_driver *pci_drv __rte_unused,
return err;
}
+ adapter->max_mac_addrs = adapter->ident.lif.eth.max_ucast_filters;
+
adapter->nlifs = 0;
for (i = 0; i < adapter->ident.dev.nlifs; i++) {
snprintf(name, sizeof(name), "net_%s_lif_%lu",
diff --git a/drivers/net/ionic/ionic_lif.c b/drivers/net/ionic/ionic_lif.c
index 491db56d4..b6b730cef 100644
--- a/drivers/net/ionic/ionic_lif.c
+++ b/drivers/net/ionic/ionic_lif.c
@@ -10,6 +10,9 @@
#include "ionic_lif.h"
#include "ionic_ethdev.h"
+static int ionic_lif_addr_add(struct ionic_lif *lif, const uint8_t *addr);
+static int ionic_lif_addr_del(struct ionic_lif *lif, const uint8_t *addr);
+
int
ionic_qcq_enable(struct ionic_qcq *qcq)
{
@@ -60,6 +63,105 @@ ionic_qcq_disable(struct ionic_qcq *qcq)
return ionic_adminq_post_wait(lif, &ctx);
}
+int
+ionic_lif_stop(struct ionic_lif *lif)
+{
+ /* Carrier OFF here */
+
+ return 0;
+}
+
+void
+ionic_lif_reset(struct ionic_lif *lif)
+{
+ struct ionic_dev *idev = &lif->adapter->idev;
+
+ ionic_drv_print_call();
+
+ ionic_dev_cmd_lif_reset(idev, lif->index);
+ ionic_dev_cmd_wait_check(idev, IONIC_DEVCMD_TIMEOUT);
+}
+
+static int
+ionic_lif_addr_add(struct ionic_lif *lif, const uint8_t *addr)
+{
+ ionic_init_print(INFO, "%s: stubbed\n", __func__);
+
+ return 0;
+}
+
+static int
+ionic_lif_addr_del(struct ionic_lif *lif, const uint8_t *addr)
+{
+ ionic_init_print(INFO, "%s: stubbed\n", __func__);
+
+ return 0;
+}
+
+static void
+ionic_lif_rx_mode(struct ionic_lif *lif, uint32_t rx_mode)
+{
+ struct ionic_admin_ctx ctx = {
+ .pending_work = true,
+ .cmd.rx_mode_set = {
+ .opcode = IONIC_CMD_RX_MODE_SET,
+ .lif_index = lif->index,
+ .rx_mode = rx_mode,
+ },
+ };
+ int err;
+
+ if (rx_mode & IONIC_RX_MODE_F_UNICAST)
+ ionic_init_print(DEBUG, "rx_mode IONIC_RX_MODE_F_UNICAST");
+ if (rx_mode & IONIC_RX_MODE_F_MULTICAST)
+ ionic_init_print(DEBUG, "rx_mode IONIC_RX_MODE_F_MULTICAST");
+ if (rx_mode & IONIC_RX_MODE_F_BROADCAST)
+ ionic_init_print(DEBUG, "rx_mode IONIC_RX_MODE_F_BROADCAST");
+ if (rx_mode & IONIC_RX_MODE_F_PROMISC)
+ ionic_init_print(DEBUG, "rx_mode IONIC_RX_MODE_F_PROMISC");
+ if (rx_mode & IONIC_RX_MODE_F_ALLMULTI)
+ ionic_init_print(DEBUG, "rx_mode IONIC_RX_MODE_F_ALLMULTI");
+
+ err = ionic_adminq_post_wait(lif, &ctx);
+
+ if (err)
+ ionic_init_print(ERR, "Failure setting RX mode");
+}
+
+static void
+ionic_set_rx_mode(struct ionic_lif *lif, uint32_t rx_mode)
+{
+ if (lif->rx_mode != rx_mode) {
+ lif->rx_mode = rx_mode;
+ ionic_lif_rx_mode(lif, rx_mode);
+ }
+}
+
+
+int
+ionic_lif_change_mtu(struct ionic_lif *lif, int new_mtu)
+{
+ struct ionic_admin_ctx ctx = {
+ .pending_work = true,
+ .cmd.lif_setattr = {
+ .opcode = IONIC_CMD_LIF_SETATTR,
+ .index = lif->index,
+ .attr = IONIC_LIF_ATTR_MTU,
+ .mtu = new_mtu,
+ },
+ };
+ int err;
+
+ err = ionic_adminq_post_wait(lif, &ctx);
+
+ if (err)
+ return err;
+
+ lif->mtu = new_mtu;
+
+ return 0;
+}
+
int
ionic_intr_alloc(struct ionic_lif *lif, struct ionic_intr_info *intr)
{
@@ -595,6 +697,124 @@ ionic_lif_notifyq_init(struct ionic_lif *lif)
return 0;
}
+int
+ionic_lif_set_features(struct ionic_lif *lif)
+{
+ struct ionic_admin_ctx ctx = {
+ .pending_work = true,
+ .cmd.lif_setattr = {
+ .opcode = IONIC_CMD_LIF_SETATTR,
+ .index = lif->index,
+ .attr = IONIC_LIF_ATTR_FEATURES,
+ .features = lif->features,
+ },
+ };
+ int err;
+
+ err = ionic_adminq_post_wait(lif, &ctx);
+ if (err)
+ return err;
+
+ lif->hw_features = (ctx.cmd.lif_setattr.features &
+ ctx.comp.lif_setattr.features);
+
+ if (lif->hw_features & IONIC_ETH_HW_VLAN_TX_TAG)
+ ionic_init_print(DEBUG, "feature IONIC_ETH_HW_VLAN_TX_TAG");
+ if (lif->hw_features & IONIC_ETH_HW_VLAN_RX_STRIP)
+ ionic_init_print(DEBUG, "feature IONIC_ETH_HW_VLAN_RX_STRIP");
+ if (lif->hw_features & IONIC_ETH_HW_VLAN_RX_FILTER)
+ ionic_init_print(DEBUG, "feature IONIC_ETH_HW_VLAN_RX_FILTER");
+ if (lif->hw_features & IONIC_ETH_HW_RX_HASH)
+ ionic_init_print(DEBUG, "feature IONIC_ETH_HW_RX_HASH");
+ if (lif->hw_features & IONIC_ETH_HW_TX_SG)
+ ionic_init_print(DEBUG, "feature IONIC_ETH_HW_TX_SG");
+ if (lif->hw_features & IONIC_ETH_HW_RX_SG)
+ ionic_init_print(DEBUG, "feature IONIC_ETH_HW_RX_SG");
+ if (lif->hw_features & IONIC_ETH_HW_TX_CSUM)
+ ionic_init_print(DEBUG, "feature IONIC_ETH_HW_TX_CSUM");
+ if (lif->hw_features & IONIC_ETH_HW_RX_CSUM)
+ ionic_init_print(DEBUG, "feature IONIC_ETH_HW_RX_CSUM");
+ if (lif->hw_features & IONIC_ETH_HW_TSO)
+ ionic_init_print(DEBUG, "feature IONIC_ETH_HW_TSO");
+ if (lif->hw_features & IONIC_ETH_HW_TSO_IPV6)
+ ionic_init_print(DEBUG, "feature IONIC_ETH_HW_TSO_IPV6");
+ if (lif->hw_features & IONIC_ETH_HW_TSO_ECN)
+ ionic_init_print(DEBUG, "feature IONIC_ETH_HW_TSO_ECN");
+ if (lif->hw_features & IONIC_ETH_HW_TSO_GRE)
+ ionic_init_print(DEBUG, "feature IONIC_ETH_HW_TSO_GRE");
+ if (lif->hw_features & IONIC_ETH_HW_TSO_GRE_CSUM)
+ ionic_init_print(DEBUG, "feature IONIC_ETH_HW_TSO_GRE_CSUM");
+ if (lif->hw_features & IONIC_ETH_HW_TSO_IPXIP4)
+ ionic_init_print(DEBUG, "feature IONIC_ETH_HW_TSO_IPXIP4");
+ if (lif->hw_features & IONIC_ETH_HW_TSO_IPXIP6)
+ ionic_init_print(DEBUG, "feature IONIC_ETH_HW_TSO_IPXIP6");
+ if (lif->hw_features & IONIC_ETH_HW_TSO_UDP)
+ ionic_init_print(DEBUG, "feature IONIC_ETH_HW_TSO_UDP");
+ if (lif->hw_features & IONIC_ETH_HW_TSO_UDP_CSUM)
+ ionic_init_print(DEBUG, "feature IONIC_ETH_HW_TSO_UDP_CSUM");
+
+ return 0;
+}
+
+static int
+ionic_station_set(struct ionic_lif *lif)
+{
+ struct ionic_admin_ctx ctx = {
+ .pending_work = true,
+ .cmd.lif_getattr = {
+ .opcode = IONIC_CMD_LIF_GETATTR,
+ .index = lif->index,
+ .attr = IONIC_LIF_ATTR_MAC,
+ },
+ };
+ int err;
+
+ ionic_init_print_call();
+
+ err = ionic_adminq_post_wait(lif, &ctx);
+
+ if (err)
+ return err;
+
+ if (!rte_is_zero_ether_addr((struct rte_ether_addr *)
+ lif->mac_addr)) {
+ ionic_init_print(INFO, "deleting station MAC addr");
+
+ ionic_lif_addr_del(lif, lif->mac_addr);
+ }
+
+ memcpy(lif->mac_addr, ctx.comp.lif_getattr.mac, ETH_ALEN);
+
+ if (rte_is_zero_ether_addr((struct rte_ether_addr *)lif->mac_addr)) {
+ ionic_init_print(NOTICE, "empty MAC addr (VF?)");
+ return 0;
+ }
+
+ ionic_init_print(DEBUG, "adding station MAC addr");
+
+ ionic_lif_addr_add(lif, lif->mac_addr);
+
+ return 0;
+}
+
+static void
+ionic_lif_set_name(struct ionic_lif *lif)
+{
+ struct ionic_admin_ctx ctx = {
+ .pending_work = true,
+ .cmd.lif_setattr = {
+ .opcode = IONIC_CMD_LIF_SETATTR,
+ .index = lif->index,
+ .attr = IONIC_LIF_ATTR_NAME,
+ },
+ };
+
+ snprintf(ctx.cmd.lif_setattr.name, sizeof(ctx.cmd.lif_setattr.name),
+ "%d", lif->port_id);
+
+ ionic_adminq_post_wait(lif, &ctx);
+}
+
int
ionic_lif_init(struct ionic_lif *lif)
{
@@ -620,10 +840,27 @@ ionic_lif_init(struct ionic_lif *lif)
if (err)
goto err_out_adminq_deinit;
+ lif->features = 0;
+
+ err = ionic_lif_set_features(lif);
+
+ if (err)
+ goto err_out_notifyq_deinit;
+
+ err = ionic_station_set(lif);
+
+ if (err)
+ goto err_out_notifyq_deinit;
+
+ ionic_lif_set_name(lif);
+
lif->state |= IONIC_LIF_F_INITED;
return 0;
+err_out_notifyq_deinit:
+ ionic_lif_qcq_deinit(lif, lif->notifyqcq);
+
err_out_adminq_deinit:
ionic_lif_qcq_deinit(lif, lif->adminqcq);
@@ -642,6 +879,37 @@ ionic_lif_deinit(struct ionic_lif *lif)
lif->state &= ~IONIC_LIF_F_INITED;
}
+int
+ionic_lif_configure(struct ionic_lif *lif)
+{
+ lif->port_id = lif->eth_dev->data->port_id;
+
+ return 0;
+}
+
+int
+ionic_lif_start(struct ionic_lif *lif)
+{
+ uint32_t rx_mode = 0;
+
+ ionic_init_print(DEBUG, "Setting RX mode on port %u",
+ lif->port_id);
+
+ rx_mode |= IONIC_RX_MODE_F_UNICAST;
+ rx_mode |= IONIC_RX_MODE_F_MULTICAST;
+ rx_mode |= IONIC_RX_MODE_F_BROADCAST;
+
+ lif->rx_mode = 0; /* set by ionic_set_rx_mode */
+
+ ionic_set_rx_mode(lif, rx_mode);
+
+ ionic_link_status_check(lif);
+
+ /* Carrier ON here */
+
+ return 0;
+}
+
int
ionic_lif_identify(struct ionic_adapter *adapter)
{
diff --git a/drivers/net/ionic/ionic_lif.h b/drivers/net/ionic/ionic_lif.h
index 326cb17d5..f7c51c9ec 100644
--- a/drivers/net/ionic/ionic_lif.h
+++ b/drivers/net/ionic/ionic_lif.h
@@ -44,6 +44,7 @@ struct ionic_lif {
struct ionic_adapter *adapter;
struct rte_eth_dev *eth_dev;
uint16_t port_id; /**< Device port identifier */
+ uint16_t mtu;
uint32_t index;
uint32_t hw_index;
uint32_t state;
@@ -54,7 +55,11 @@ struct ionic_lif {
struct ionic_qcq *notifyqcq;
struct ionic_doorbell __iomem *kern_dbpage;
uint64_t last_eid;
+ uint64_t features;
+ uint32_t hw_features;
+ uint32_t rx_mode;
char name[IONIC_LIF_NAME_MAX_SZ];
+ uint8_t mac_addr[ETH_ALEN];
uint32_t info_sz;
struct ionic_lif_info *info;
rte_iova_t info_pa;
@@ -84,11 +89,15 @@ bool ionic_adminq_service(struct ionic_cq *cq, uint32_t cq_desc_index,
int ionic_qcq_service(struct ionic_qcq *qcq, int budget, ionic_cq_cb cb,
void *cb_arg);
+int ionic_lif_change_mtu(struct ionic_lif *lif, int new_mtu);
+
void ionic_qcq_free(struct ionic_qcq *qcq);
int ionic_qcq_enable(struct ionic_qcq *qcq);
int ionic_qcq_disable(struct ionic_qcq *qcq);
+int ionic_lif_set_features(struct ionic_lif *lif);
+
int ionic_notifyq_handler(struct ionic_lif *lif, int budget);
#endif /* _IONIC_LIF_H_ */
diff --git a/drivers/net/ionic/ionic_osdep.h b/drivers/net/ionic/ionic_osdep.h
index 5b8baa67b..39a9cefa9 100644
--- a/drivers/net/ionic/ionic_osdep.h
+++ b/drivers/net/ionic/ionic_osdep.h
@@ -28,6 +28,8 @@
#define BIT_ULL(nr) (1ULL << (nr))
#define BITS_TO_LONGS(nr) div_round_up(nr, 8 * sizeof(long))
+#define ETH_ALEN 6
+
#ifndef PAGE_SHIFT
#define PAGE_SHIFT 12
#define PAGE_SIZE (1 << PAGE_SHIFT)
--
2.17.1
next prev parent reply other threads:[~2019-10-15 8:24 UTC|newest]
Thread overview: 33+ messages / expand[flat|nested] mbox.gz Atom feed top
2019-10-15 8:22 [dpdk-dev] [PATCH v2 00/17] Introduces net/ionic PMD Alfredo Cardigliano
2019-10-15 8:22 ` [dpdk-dev] [PATCH v2 01/17] net/ionic: add skeleton Alfredo Cardigliano
2019-12-02 16:06 ` Ferruh Yigit
2019-10-15 8:22 ` [dpdk-dev] [PATCH v2 02/17] net/ionic: add hardware structures definitions Alfredo Cardigliano
2019-12-02 16:07 ` Ferruh Yigit
2019-12-02 16:33 ` Stephen Hemminger
2019-12-04 16:26 ` Alfredo Cardigliano
2019-10-15 8:22 ` [dpdk-dev] [PATCH v2 03/17] net/ionic: add log Alfredo Cardigliano
2019-12-02 16:07 ` Ferruh Yigit
2019-10-15 8:22 ` [dpdk-dev] [PATCH v2 04/17] net/ionic: register and initialize the adapter Alfredo Cardigliano
2019-12-02 16:09 ` Ferruh Yigit
2019-12-08 19:25 ` Alfredo Cardigliano
2019-12-09 9:12 ` Ferruh Yigit
2019-12-02 16:35 ` Stephen Hemminger
2019-10-15 8:22 ` [dpdk-dev] [PATCH v2 05/17] net/ionic: add port management commands Alfredo Cardigliano
2019-10-15 8:22 ` [dpdk-dev] [PATCH v2 06/17] net/ionic: add basic lif support Alfredo Cardigliano
2019-10-15 8:22 ` [dpdk-dev] [PATCH v2 07/17] net/ionic: add doorbells Alfredo Cardigliano
2019-10-15 8:22 ` [dpdk-dev] [PATCH v2 08/17] net/ionic: add adminq support Alfredo Cardigliano
2019-12-02 16:15 ` Ferruh Yigit
2019-10-15 8:22 ` [dpdk-dev] [PATCH v2 09/17] net/ionic: add notifyq support Alfredo Cardigliano
2019-10-15 8:22 ` Alfredo Cardigliano [this message]
2019-12-02 16:11 ` [dpdk-dev] [PATCH v2 10/17] net/ionic: add basic port operations Ferruh Yigit
2019-10-15 8:22 ` [dpdk-dev] [PATCH v2 11/17] net/ionic: add RX filters support Alfredo Cardigliano
2019-10-15 8:22 ` [dpdk-dev] [PATCH v2 12/17] net/ionic: add Flow Control support Alfredo Cardigliano
2019-10-15 8:22 ` [dpdk-dev] [PATCH v2 13/17] net/ionic: add RX and TX handling Alfredo Cardigliano
2019-12-02 16:13 ` Ferruh Yigit
2019-10-15 8:22 ` [dpdk-dev] [PATCH v2 14/17] net/ionic: add RSS support Alfredo Cardigliano
2019-10-15 8:22 ` [dpdk-dev] [PATCH v2 15/17] net/ionic: add stats Alfredo Cardigliano
2019-12-02 16:14 ` Ferruh Yigit
2019-10-15 8:22 ` [dpdk-dev] [PATCH v2 16/17] net/ionic: add TX checksum support Alfredo Cardigliano
2019-12-02 16:15 ` Ferruh Yigit
2019-10-15 8:22 ` [dpdk-dev] [PATCH v2 17/17] net/ionic: read fw version Alfredo Cardigliano
2019-10-15 13:09 ` [dpdk-dev] [PATCH v2 00/17] Introduces net/ionic PMD Ferruh Yigit
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20191015082235.28639-11-cardigliano@ntop.org \
--to=cardigliano@ntop.org \
--cc=dev@dpdk.org \
--cc=john.mcnamara@intel.com \
--cc=marko.kovacevic@intel.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).