Commit 6c75f0a2 authored by Jim Harris's avatar Jim Harris Committed by Tomasz Zawadzki
Browse files

env_dpdk: save hotplug timeout timestamps separate from rte_devargs



DPDK recently clarified some semantics on the rte_devargs 'data'
and 'args' fields.  This actually breaks our use of the 'data'
field to store the 2 second timeout timestamp for delaying
attach to newly inserted devices.  Investigating this further,
it does not seem our use of the 'data' field was valid - it just
happened to work until now.

We could use the 'args' field now.  But knowing whether to use
'args' or 'data' would then be dependent on the DPDK version.
We cannot use RTE_VERSION_NUM to decide, because this is a
compile time decision, and it is possible in shared library
use cases that we could actually link and execute against a
different version of DPDK than we built against.

So instead we will create our own env_devargs structure that
will store these allowed_at timestamps. Currently it's just
a linked list (which is exactly how DPDK does it) - we could
make it more optimal with a hash table down the road, but this
code only executes when we are doing PCI enumeration so it is
not performance critical.

Fixes #1904.

Signed-off-by: default avatarJim Harris <james.r.harris@intel.com>
Change-Id: I3ee5d65ba90635b5a96b97dd0f4ab72a093fe8f7
Reviewed-on: https://review.spdk.io/gerrit/c/spdk/spdk/+/7506


Community-CI: Broadcom CI
Community-CI: Mellanox Build Bot
Tested-by: default avatarSPDK CI Jenkins <sys_sgci@intel.com>
Reviewed-by: default avatarAleksey Marchuk <alexeymar@mellanox.com>
Reviewed-by: default avatarBen Walker <benjamin.walker@intel.com>
Reviewed-by: default avatarShuhei Matsumoto <shuhei.matsumoto.xt@hitachi.com>
Reviewed-by: default avatarChangpeng Liu <changpeng.liu@intel.com>
Reviewed-by: default avatar <dongx.yi@intel.com>
parent 204e6278
Loading
Loading
Loading
Loading
+1 −1
Original line number Diff line number Diff line
@@ -39,6 +39,6 @@ APP = led

C_SRCS := led.c

SPDK_LIB_LIST = vmd log
SPDK_LIB_LIST = vmd log util

include $(SPDK_ROOT_DIR)/mk/spdk.app.mk
+1 −1
Original line number Diff line number Diff line
@@ -39,6 +39,6 @@ APP = lsvmd

C_SRCS := lsvmd.c

SPDK_LIB_LIST = vmd log
SPDK_LIB_LIST = vmd log util

include $(SPDK_ROOT_DIR)/mk/spdk.app.mk
+46 −2
Original line number Diff line number Diff line
@@ -37,6 +37,7 @@
#include <rte_devargs.h>
#include "spdk/env.h"
#include "spdk/log.h"
#include "spdk/string.h"

#define SYSFS_PCI_DRIVERS	"/sys/bus/pci/drivers"

@@ -63,6 +64,28 @@ static TAILQ_HEAD(, spdk_pci_device) g_pci_hotplugged_devices =
	TAILQ_HEAD_INITIALIZER(g_pci_hotplugged_devices);
static TAILQ_HEAD(, spdk_pci_driver) g_pci_drivers = TAILQ_HEAD_INITIALIZER(g_pci_drivers);

struct env_devargs {
	struct rte_bus	*bus;
	char		name[128];
	uint64_t	allowed_at;
	TAILQ_ENTRY(env_devargs) link;
};
static TAILQ_HEAD(, env_devargs) g_env_devargs = TAILQ_HEAD_INITIALIZER(g_env_devargs);

static struct env_devargs *
find_env_devargs(struct rte_bus *bus, const char *name)
{
	struct env_devargs *da;

	TAILQ_FOREACH(da, &g_env_devargs, link) {
		if (bus == da->bus && !strcmp(name, da->name)) {
			return da;
		}
	}

	return NULL;
}

static int
map_bar_rte(struct spdk_pci_device *device, uint32_t bar,
	    void **mapped_addr, uint64_t *phys_addr, uint64_t *size)
@@ -460,13 +483,34 @@ pci_device_init(struct rte_pci_driver *_drv,
static void
set_allowed_at(struct rte_devargs *rte_da, uint64_t tsc)
{
	rte_da->data = (void *)(tsc);
	struct env_devargs *env_da;

	env_da = find_env_devargs(rte_da->bus, rte_da->name);
	if (env_da == NULL) {
		env_da = calloc(1, sizeof(*env_da));
		if (env_da == NULL) {
			SPDK_ERRLOG("could not set_allowed_at for device %s\n", rte_da->name);
			return;
		}
		env_da->bus = rte_da->bus;
		spdk_strcpy_pad(env_da->name, rte_da->name, sizeof(env_da->name), 0);
		TAILQ_INSERT_TAIL(&g_env_devargs, env_da, link);
	}

	env_da->allowed_at = tsc;
}

static uint64_t
get_allowed_at(struct rte_devargs *rte_da)
{
	return (uint64_t)rte_da->data;
	struct env_devargs *env_da;

	env_da = find_env_devargs(rte_da->bus, rte_da->name);
	if (env_da) {
		return env_da->allowed_at;
	} else {
		return 0;
	}
}

int