#include <rte_alarm.h>
#include <rte_malloc.h>
-#include <rte_ethdev.h>
+#include <rte_ethdev_driver.h>
#include <rte_ethdev_vdev.h>
#include <rte_devargs.h>
#include <rte_kvargs.h>
-#include <rte_vdev.h>
+#include <rte_bus_vdev.h>
#include "failsafe_private.h"
.link_speed = ETH_SPEED_NUM_10G,
.link_duplex = ETH_LINK_FULL_DUPLEX,
.link_status = ETH_LINK_UP,
- .link_autoneg = ETH_LINK_SPEED_AUTONEG,
+ .link_autoneg = ETH_LINK_AUTONEG,
};
static int
{
uint8_t nb_subs;
int ret;
+ int i;
ret = failsafe_args_count_subdevice(dev, params);
if (ret)
ERROR("Could not allocate sub_devices");
return -ENOMEM;
}
+ /* Initiate static sub devices linked list. */
+ for (i = 1; i < nb_subs; i++)
+ PRIV(dev)->subs[i - 1].next = PRIV(dev)->subs + i;
+ PRIV(dev)->subs[i - 1].next = PRIV(dev)->subs;
return 0;
}
rte_free(PRIV(dev)->subs);
}
+static void fs_hotplug_alarm(void *arg);
+
+int
+failsafe_hotplug_alarm_install(struct rte_eth_dev *dev)
+{
+ int ret;
+
+ if (dev == NULL)
+ return -EINVAL;
+ if (PRIV(dev)->pending_alarm)
+ return 0;
+ ret = rte_eal_alarm_set(hotplug_poll * 1000,
+ fs_hotplug_alarm,
+ dev);
+ if (ret) {
+ ERROR("Could not set up plug-in event detection");
+ return ret;
+ }
+ PRIV(dev)->pending_alarm = 1;
+ return 0;
+}
+
+int
+failsafe_hotplug_alarm_cancel(struct rte_eth_dev *dev)
+{
+ int ret = 0;
+
+ if (PRIV(dev)->pending_alarm) {
+ rte_errno = 0;
+ rte_eal_alarm_cancel(fs_hotplug_alarm, dev);
+ if (rte_errno) {
+ ERROR("rte_eal_alarm_cancel failed (errno: %s)",
+ strerror(rte_errno));
+ ret = -rte_errno;
+ } else {
+ PRIV(dev)->pending_alarm = 0;
+ }
+ }
+ return ret;
+}
+
+static void
+fs_hotplug_alarm(void *arg)
+{
+ struct rte_eth_dev *dev = arg;
+ struct sub_device *sdev;
+ int ret;
+ uint8_t i;
+
+ if (!PRIV(dev)->pending_alarm)
+ return;
+ PRIV(dev)->pending_alarm = 0;
+ FOREACH_SUBDEV(sdev, i, dev)
+ if (sdev->state != PRIV(dev)->state)
+ break;
+ /* if we have non-probed device */
+ if (i != PRIV(dev)->subs_tail) {
+ ret = failsafe_eth_dev_state_sync(dev);
+ if (ret)
+ ERROR("Unable to synchronize sub_device state");
+ }
+ failsafe_dev_remove(dev);
+ ret = failsafe_hotplug_alarm_install(dev);
+ if (ret)
+ ERROR("Unable to set up next alarm");
+}
+
static int
fs_eth_dev_create(struct rte_vdev_device *vdev)
{
dev->data->mac_addrs = &PRIV(dev)->mac_addrs[0];
dev->data->dev_link = eth_link;
PRIV(dev)->nb_mac_addr = 1;
+ TAILQ_INIT(&PRIV(dev)->flow_list);
dev->rx_pkt_burst = (eth_rx_burst_t)&failsafe_rx_burst;
dev->tx_pkt_burst = (eth_tx_burst_t)&failsafe_tx_burst;
ret = fs_sub_device_alloc(dev, params);
ret = failsafe_args_parse(dev, params);
if (ret)
goto free_subs;
+ ret = rte_eth_dev_owner_new(&priv->my_owner.id);
+ if (ret) {
+ ERROR("Failed to get unique owner identifier");
+ goto free_args;
+ }
+ snprintf(priv->my_owner.name, sizeof(priv->my_owner.name),
+ FAILSAFE_OWNER_NAME);
ret = failsafe_eal_init(dev);
if (ret)
goto free_args;
+ ret = failsafe_hotplug_alarm_install(dev);
+ if (ret) {
+ ERROR("Could not set up plug-in event detection");
+ goto free_args;
+ }
mac = &dev->data->mac_addrs[0];
if (mac_from_arg) {
/*
mac->addr_bytes[0], mac->addr_bytes[1],
mac->addr_bytes[2], mac->addr_bytes[3],
mac->addr_bytes[4], mac->addr_bytes[5]);
+ dev->data->dev_flags |= RTE_ETH_DEV_INTR_LSC;
+ PRIV(dev)->intr_handle = (struct rte_intr_handle){
+ .fd = -1,
+ .type = RTE_INTR_HANDLE_EXT,
+ };
return 0;
free_args:
failsafe_args_free(dev);