ethdev: save VLAN filter setting
[dpdk.git] / lib / librte_ether / rte_ethdev.c
index 83898a8..76179fd 100644 (file)
@@ -1,7 +1,7 @@
 /*-
  *   BSD LICENSE
  *
- *   Copyright(c) 2010-2016 Intel Corporation. All rights reserved.
+ *   Copyright(c) 2010-2017 Intel Corporation. All rights reserved.
  *   All rights reserved.
  *
  *   Redistribution and use in source and binary forms, with or without
@@ -129,6 +129,7 @@ struct rte_eth_dev_callback {
        TAILQ_ENTRY(rte_eth_dev_callback) next; /**< Callbacks list */
        rte_eth_dev_cb_fn cb_fn;                /**< Callback address */
        void *cb_arg;                           /**< Parameter for callback */
+       void *ret_param;                        /**< Return parameter */
        enum rte_eth_event_type event;          /**< Interrupt event type */
        uint32_t active;                        /**< Callback is executing */
 };
@@ -178,9 +179,11 @@ rte_eth_dev_allocated(const char *name)
        unsigned i;
 
        for (i = 0; i < RTE_MAX_ETHPORTS; i++) {
-               if ((rte_eth_devices[i].state == RTE_ETH_DEV_ATTACHED) &&
-                   strcmp(rte_eth_devices[i].data->name, name) == 0)
-                       return &rte_eth_devices[i];
+               if (rte_eth_devices[i].state == RTE_ETH_DEV_ATTACHED &&
+                               rte_eth_devices[i].device) {
+                       if (!strcmp(rte_eth_devices[i].device->name, name))
+                               return &rte_eth_devices[i];
+               }
        }
        return NULL;
 }
@@ -310,7 +313,7 @@ rte_eth_dev_count(void)
 int
 rte_eth_dev_get_name_by_port(uint8_t port_id, char *name)
 {
-       char *tmp;
+       const char *tmp;
 
        RTE_ETH_VALID_PORTID_OR_ERR_RET(port_id, -EINVAL);
 
@@ -321,7 +324,7 @@ rte_eth_dev_get_name_by_port(uint8_t port_id, char *name)
 
        /* shouldn't check 'rte_eth_devices[i].data',
         * because it might be overwritten by VDEV PMD */
-       tmp = rte_eth_dev_data[port_id].name;
+       tmp = rte_eth_devices[port_id].device->name;
        strcpy(name, tmp);
        return 0;
 }
@@ -329,6 +332,7 @@ rte_eth_dev_get_name_by_port(uint8_t port_id, char *name)
 int
 rte_eth_dev_get_port_by_name(const char *name, uint8_t *port_id)
 {
+       int ret;
        int i;
 
        if (name == NULL) {
@@ -339,13 +343,14 @@ rte_eth_dev_get_port_by_name(const char *name, uint8_t *port_id)
        if (!nb_ports)
                return -ENODEV;
 
-       *port_id = RTE_MAX_ETHPORTS;
        RTE_ETH_FOREACH_DEV(i) {
-               if (!strncmp(name,
-                       rte_eth_dev_data[i].name, strlen(name))) {
+               if (!rte_eth_devices[i].device)
+                       continue;
 
+               ret = strncmp(name, rte_eth_devices[i].device->name,
+                               strlen(name));
+               if (ret == 0) {
                        *port_id = i;
-
                        return 0;
                }
        }
@@ -438,9 +443,10 @@ rte_eth_dev_detach(uint8_t port_id, char *name)
        if (rte_eth_dev_is_detachable(port_id))
                goto err;
 
-       snprintf(name, sizeof(rte_eth_devices[port_id].data->name),
-                "%s", rte_eth_devices[port_id].data->name);
-       ret = rte_eal_dev_detach(name);
+       snprintf(name, sizeof(rte_eth_devices[port_id].device->name),
+                "%s", rte_eth_devices[port_id].device->name);
+
+       ret = rte_eal_dev_detach(rte_eth_devices[port_id].device);
        if (ret < 0)
                goto err;
 
@@ -753,13 +759,13 @@ rte_eth_dev_configure(uint8_t port_id, uint16_t nb_rx_q, uint16_t nb_tx_q,
        if ((dev_conf->intr_conf.lsc == 1) &&
                (!(dev->data->dev_flags & RTE_ETH_DEV_INTR_LSC))) {
                        RTE_PMD_DEBUG_TRACE("driver %s does not support lsc\n",
-                                       dev->data->drv_name);
+                                       dev->device->driver->name);
                        return -EINVAL;
        }
        if ((dev_conf->intr_conf.rmv == 1) &&
            (!(dev->data->dev_flags & RTE_ETH_DEV_INTR_RMV))) {
                RTE_PMD_DEBUG_TRACE("driver %s does not support rmv\n",
-                                   dev->data->drv_name);
+                                   dev->device->driver->name);
                return -EINVAL;
        }
 
@@ -1900,7 +1906,7 @@ rte_eth_dev_info_get(uint8_t port_id, struct rte_eth_dev_info *dev_info)
 
        RTE_FUNC_PTR_OR_RET(*dev->dev_ops->dev_infos_get);
        (*dev->dev_ops->dev_infos_get)(dev, dev_info);
-       dev_info->driver_name = dev->data->drv_name;
+       dev_info->driver_name = dev->device->driver->name;
        dev_info->nb_rx_queues = dev->data->nb_rx_queues;
        dev_info->nb_tx_queues = dev->data->nb_tx_queues;
 }
@@ -1975,6 +1981,7 @@ int
 rte_eth_dev_vlan_filter(uint8_t port_id, uint16_t vlan_id, int on)
 {
        struct rte_eth_dev *dev;
+       int ret;
 
        RTE_ETH_VALID_PORTID_OR_ERR_RET(port_id, -ENODEV);
        dev = &rte_eth_devices[port_id];
@@ -1990,7 +1997,23 @@ rte_eth_dev_vlan_filter(uint8_t port_id, uint16_t vlan_id, int on)
        }
        RTE_FUNC_PTR_OR_ERR_RET(*dev->dev_ops->vlan_filter_set, -ENOTSUP);
 
-       return (*dev->dev_ops->vlan_filter_set)(dev, vlan_id, on);
+       ret = (*dev->dev_ops->vlan_filter_set)(dev, vlan_id, on);
+       if (ret == 0) {
+               struct rte_vlan_filter_conf *vfc;
+               int vidx;
+               int vbit;
+
+               vfc = &dev->data->vlan_filter_conf;
+               vidx = vlan_id / 64;
+               vbit = vlan_id % 64;
+
+               if (on)
+                       vfc->ids[vidx] |= UINT64_C(1) << vbit;
+               else
+                       vfc->ids[vidx] &= ~(UINT64_C(1) << vbit);
+       }
+
+       return ret;
 }
 
 int
@@ -2718,12 +2741,13 @@ rte_eth_dev_callback_unregister(uint8_t port_id,
        return ret;
 }
 
-void
+int
 _rte_eth_dev_callback_process(struct rte_eth_dev *dev,
-       enum rte_eth_event_type event, void *cb_arg)
+       enum rte_eth_event_type event, void *cb_arg, void *ret_param)
 {
        struct rte_eth_dev_callback *cb_lst;
        struct rte_eth_dev_callback dev_cb;
+       int rc = 0;
 
        rte_spinlock_lock(&rte_eth_dev_cb_lock);
        TAILQ_FOREACH(cb_lst, &(dev->link_intr_cbs), next) {
@@ -2733,14 +2757,17 @@ _rte_eth_dev_callback_process(struct rte_eth_dev *dev,
                cb_lst->active = 1;
                if (cb_arg != NULL)
                        dev_cb.cb_arg = cb_arg;
+               if (ret_param != NULL)
+                       dev_cb.ret_param = ret_param;
 
                rte_spinlock_unlock(&rte_eth_dev_cb_lock);
-               dev_cb.cb_fn(dev->data->port_id, dev_cb.event,
-                                               dev_cb.cb_arg);
+               rc = dev_cb.cb_fn(dev->data->port_id, dev_cb.event,
+                               dev_cb.cb_arg, dev_cb.ret_param);
                rte_spinlock_lock(&rte_eth_dev_cb_lock);
                cb_lst->active = 0;
        }
        rte_spinlock_unlock(&rte_eth_dev_cb_lock);
+       return rc;
 }
 
 int
@@ -2789,7 +2816,7 @@ rte_eth_dma_zone_reserve(const struct rte_eth_dev *dev, const char *ring_name,
        const struct rte_memzone *mz;
 
        snprintf(z_name, sizeof(z_name), "%s_%s_%d_%d",
-                dev->data->drv_name, ring_name,
+                dev->device->driver->name, ring_name,
                 dev->data->port_id, queue_id);
 
        mz = rte_memzone_lookup(z_name);
@@ -2872,128 +2899,6 @@ rte_eth_dev_rx_intr_disable(uint8_t port_id,
        return (*dev->dev_ops->rx_queue_intr_disable)(dev, queue_id);
 }
 
-#ifdef RTE_NIC_BYPASS
-int rte_eth_dev_bypass_init(uint8_t port_id)
-{
-       struct rte_eth_dev *dev;
-
-       RTE_ETH_VALID_PORTID_OR_ERR_RET(port_id, -ENODEV);
-
-       dev = &rte_eth_devices[port_id];
-       RTE_FUNC_PTR_OR_ERR_RET(*dev->dev_ops->bypass_init, -ENOTSUP);
-       (*dev->dev_ops->bypass_init)(dev);
-       return 0;
-}
-
-int
-rte_eth_dev_bypass_state_show(uint8_t port_id, uint32_t *state)
-{
-       struct rte_eth_dev *dev;
-
-       RTE_ETH_VALID_PORTID_OR_ERR_RET(port_id, -ENODEV);
-
-       dev = &rte_eth_devices[port_id];
-       RTE_FUNC_PTR_OR_ERR_RET(*dev->dev_ops->bypass_state_show, -ENOTSUP);
-       (*dev->dev_ops->bypass_state_show)(dev, state);
-       return 0;
-}
-
-int
-rte_eth_dev_bypass_state_set(uint8_t port_id, uint32_t *new_state)
-{
-       struct rte_eth_dev *dev;
-
-       RTE_ETH_VALID_PORTID_OR_ERR_RET(port_id, -ENODEV);
-
-       dev = &rte_eth_devices[port_id];
-       RTE_FUNC_PTR_OR_ERR_RET(*dev->dev_ops->bypass_state_set, -ENOTSUP);
-       (*dev->dev_ops->bypass_state_set)(dev, new_state);
-       return 0;
-}
-
-int
-rte_eth_dev_bypass_event_show(uint8_t port_id, uint32_t event, uint32_t *state)
-{
-       struct rte_eth_dev *dev;
-
-       RTE_ETH_VALID_PORTID_OR_ERR_RET(port_id, -ENODEV);
-
-       dev = &rte_eth_devices[port_id];
-       RTE_FUNC_PTR_OR_ERR_RET(*dev->dev_ops->bypass_state_show, -ENOTSUP);
-       (*dev->dev_ops->bypass_event_show)(dev, event, state);
-       return 0;
-}
-
-int
-rte_eth_dev_bypass_event_store(uint8_t port_id, uint32_t event, uint32_t state)
-{
-       struct rte_eth_dev *dev;
-
-       RTE_ETH_VALID_PORTID_OR_ERR_RET(port_id, -ENODEV);
-
-       dev = &rte_eth_devices[port_id];
-
-       RTE_FUNC_PTR_OR_ERR_RET(*dev->dev_ops->bypass_event_set, -ENOTSUP);
-       (*dev->dev_ops->bypass_event_set)(dev, event, state);
-       return 0;
-}
-
-int
-rte_eth_dev_wd_timeout_store(uint8_t port_id, uint32_t timeout)
-{
-       struct rte_eth_dev *dev;
-
-       RTE_ETH_VALID_PORTID_OR_ERR_RET(port_id, -ENODEV);
-
-       dev = &rte_eth_devices[port_id];
-
-       RTE_FUNC_PTR_OR_ERR_RET(*dev->dev_ops->bypass_wd_timeout_set, -ENOTSUP);
-       (*dev->dev_ops->bypass_wd_timeout_set)(dev, timeout);
-       return 0;
-}
-
-int
-rte_eth_dev_bypass_ver_show(uint8_t port_id, uint32_t *ver)
-{
-       struct rte_eth_dev *dev;
-
-       RTE_ETH_VALID_PORTID_OR_ERR_RET(port_id, -ENODEV);
-
-       dev = &rte_eth_devices[port_id];
-
-       RTE_FUNC_PTR_OR_ERR_RET(*dev->dev_ops->bypass_ver_show, -ENOTSUP);
-       (*dev->dev_ops->bypass_ver_show)(dev, ver);
-       return 0;
-}
-
-int
-rte_eth_dev_bypass_wd_timeout_show(uint8_t port_id, uint32_t *wd_timeout)
-{
-       struct rte_eth_dev *dev;
-
-       RTE_ETH_VALID_PORTID_OR_ERR_RET(port_id, -ENODEV);
-
-       dev = &rte_eth_devices[port_id];
-
-       RTE_FUNC_PTR_OR_ERR_RET(*dev->dev_ops->bypass_wd_timeout_show, -ENOTSUP);
-       (*dev->dev_ops->bypass_wd_timeout_show)(dev, wd_timeout);
-       return 0;
-}
-
-int
-rte_eth_dev_bypass_wd_reset(uint8_t port_id)
-{
-       struct rte_eth_dev *dev;
-
-       RTE_ETH_VALID_PORTID_OR_ERR_RET(port_id, -ENODEV);
-
-       dev = &rte_eth_devices[port_id];
-
-       RTE_FUNC_PTR_OR_ERR_RET(*dev->dev_ops->bypass_wd_reset, -ENOTSUP);
-       (*dev->dev_ops->bypass_wd_reset)(dev);
-       return 0;
-}
-#endif
 
 int
 rte_eth_dev_filter_supported(uint8_t port_id, enum rte_filter_type filter_type)
@@ -3472,3 +3377,40 @@ rte_eth_dev_l2_tunnel_offload_set(uint8_t port_id,
                                -ENOTSUP);
        return (*dev->dev_ops->l2_tunnel_offload_set)(dev, l2_tunnel, mask, en);
 }
+
+static void
+rte_eth_dev_adjust_nb_desc(uint16_t *nb_desc,
+                          const struct rte_eth_desc_lim *desc_lim)
+{
+       if (desc_lim->nb_align != 0)
+               *nb_desc = RTE_ALIGN_CEIL(*nb_desc, desc_lim->nb_align);
+
+       if (desc_lim->nb_max != 0)
+               *nb_desc = RTE_MIN(*nb_desc, desc_lim->nb_max);
+
+       *nb_desc = RTE_MAX(*nb_desc, desc_lim->nb_min);
+}
+
+int
+rte_eth_dev_adjust_nb_rx_tx_desc(uint8_t port_id,
+                                uint16_t *nb_rx_desc,
+                                uint16_t *nb_tx_desc)
+{
+       struct rte_eth_dev *dev;
+       struct rte_eth_dev_info dev_info;
+
+       RTE_ETH_VALID_PORTID_OR_ERR_RET(port_id, -ENODEV);
+
+       dev = &rte_eth_devices[port_id];
+       RTE_FUNC_PTR_OR_ERR_RET(*dev->dev_ops->dev_infos_get, -ENOTSUP);
+
+       rte_eth_dev_info_get(port_id, &dev_info);
+
+       if (nb_rx_desc != NULL)
+               rte_eth_dev_adjust_nb_desc(nb_rx_desc, &dev_info.rx_desc_lim);
+
+       if (nb_tx_desc != NULL)
+               rte_eth_dev_adjust_nb_desc(nb_tx_desc, &dev_info.tx_desc_lim);
+
+       return 0;
+}