Skip to contentSkip to conversation

Rework vdev probing to use rte_bus infrastructure

PATCH Superseded Jan Blunck 7 participants 91 messages Feb 15, 2017 – Apr 14, 2017

Subsystems (3)
lore
Share & tools
lore

Jan Blunck

author
#0 lore raw

cover Rework vdev probing to use rte_bus infrastructure

With the rte_bus infrastructure present in 17.02 it is possible to refactor the virtual device probing into a bus. This series also introduces the rte_vdev_device to better keep track of devices.

Jan Blunck (7):
eal: use different constructor priorities for initcalls
eal: probe legacy PCI devices before other bus devices
eal: move virtual device probing into a bus
eal: remove unused rte_eal_dev_init()
eal: Refactor vdev driver probe/remove
eal: add struct rte_vdev_device
eal: make virtual bus use rte_vdev_device

 lib/librte_eal/bsdapp/eal/eal.c           |   9 +-
 lib/librte_eal/common/eal_common_dev.c    |  28 ----
 lib/librte_eal/common/eal_common_vdev.c   | 245 ++++++++++++++++++++++++++----
 lib/librte_eal/common/include/rte_bus.h   |  17 ++-
 lib/librte_eal/common/include/rte_dev.h   |   5 -
 lib/librte_eal/common/include/rte_eal.h   |  12 +-
 lib/librte_eal/common/include/rte_tailq.h |   2 +-
 lib/librte_eal/common/include/rte_vdev.h  |   5 +
 lib/librte_eal/linuxapp/eal/eal.c         |   9 +-
 9 files changed, 253 insertions(+), 79 deletions(-)
Signature · 1 line
2.7.4
author
#1 lore raw

PATCH 1/7 eal: use different constructor priorities for initcalls

This introduces different initcall macros to allow for late registration of the virtual device bus.

---
 lib/librte_eal/common/include/rte_bus.h   | 17 ++++++++++++++++-
 lib/librte_eal/common/include/rte_eal.h   | 12 ++++++++++--
 lib/librte_eal/common/include/rte_tailq.h |  2 +-
 3 files changed, 27 insertions(+), 4 deletions(-)
lib/librte_eal/common/include/rte_bus.h +16 -1
index 7c36969..9f161f2 100644
@@ -50,6 +50,7 @@ extern "C" {
 #include <stdio.h>
 #include <sys/queue.h>
 
+#include <rte_eal.h>
 #include <rte_log.h>
 #include <rte_dev.h>
 
@@ -145,7 +146,21 @@ void rte_bus_dump(FILE *f);
  * The constructor has higher priority than PMD constructors.
  */
 #define RTE_REGISTER_BUS(nm, bus) \
-static void __attribute__((constructor(101), used)) businitfn_ ##nm(void) \
+RTE_EAL_INIT(businitfn_ ##nm); \
+static void businitfn_ ##nm(void) \
+{\
+	(bus).name = RTE_STR(nm);\
+	rte_bus_register(&bus); \
+}
+
+/**
+ * Helper for late Bus registration.
+ * The constructor still has higher priority than PMD constructors but has
+ * lower priority than RTE_REGISTER_BUS.
+ */
+#define RTE_REGISTER_BUS_LATE(nm, bus) \
+RTE_POST_EAL_INIT(businitfn_ ##nm); \
+static void businitfn_ ##nm(void) \
 {\
 	(bus).name = RTE_STR(nm);\
 	rte_bus_register(&bus); \
lib/librte_eal/common/include/rte_eal.h +10 -2
index 03fee50..3a6bd71 100644
@@ -258,8 +258,16 @@ static inline int rte_gettid(void)
 	return RTE_PER_LCORE(_thread_id);
 }
 
-#define RTE_INIT(func) \
-static void __attribute__((constructor, used)) func(void)
+#define RTE_EAL_INIT(func) \
+static void __attribute__((constructor(101), used)) func(void)
+
+#define RTE_POST_EAL_INIT(func) \
+static void __attribute__((constructor(102), used)) func(void)
+
+#define RTE_DEV_INIT(func) \
+static void __attribute__((constructor(103), used)) func(void)
+
+#define RTE_INIT(func) RTE_DEV_INIT(func)
 
 #ifdef __cplusplus
 }
lib/librte_eal/common/include/rte_tailq.h +1 -1
index 3aae098..07ceec1 100644
@@ -148,7 +148,7 @@ struct rte_tailq_head *rte_eal_tailq_lookup(const char *name);
 int rte_eal_tailq_register(struct rte_tailq_elem *t);
 
 #define EAL_REGISTER_TAILQ(t) \
-RTE_INIT(tailqinitfn_ ##t); \
+RTE_EAL_INIT(tailqinitfn_ ##t); \
 static void tailqinitfn_ ##t(void) \
 { \
 	if (rte_eal_tailq_register(&t) < 0) \
Signature · 1 line
2.7.4
#2 lore raw

Re: [PATCH 1/7] eal: use different constructor priorities for initcalls

Quoted 53 lines · Jan Blunck

This introduces different initcall macros to allow for late registration of the virtual device bus.

---
 lib/librte_eal/common/include/rte_bus.h   | 17 ++++++++++++++++-
 lib/librte_eal/common/include/rte_eal.h   | 12 ++++++++++--
 lib/librte_eal/common/include/rte_tailq.h |  2 +-
 3 files changed, 27 insertions(+), 4 deletions(-)
lib/librte_eal/common/include/rte_bus.h +16 -1
index 7c36969..9f161f2 100644
@@ -50,6 +50,7 @@ extern "C" {
 #include <stdio.h>
 #include <sys/queue.h>
 
+#include <rte_eal.h>
 #include <rte_log.h>
 #include <rte_dev.h>
 
@@ -145,7 +146,21 @@ void rte_bus_dump(FILE *f);
  * The constructor has higher priority than PMD constructors.
  */
 #define RTE_REGISTER_BUS(nm, bus) \
-static void __attribute__((constructor(101), used)) businitfn_ ##nm(void) \
+RTE_EAL_INIT(businitfn_ ##nm); \
+static void businitfn_ ##nm(void) \
+{\
+	(bus).name = RTE_STR(nm);\
+	rte_bus_register(&bus); \
+}
+
+/**
+ * Helper for late Bus registration.
+ * The constructor still has higher priority than PMD constructors but has
+ * lower priority than RTE_REGISTER_BUS.
+ */
+#define RTE_REGISTER_BUS_LATE(nm, bus) \
+RTE_POST_EAL_INIT(businitfn_ ##nm); \
+static void businitfn_ ##nm(void) \
 {\
 	(bus).name = RTE_STR(nm);\
 	rte_bus_register(&bus); \
lib/librte_eal/common/include/rte_eal.h +0 -0
index 03fee50..3a6bd71 100644
@@ -258,8 +258,16 @@ static inline int rte_gettid(void)
 	return RTE_PER_LCORE(_thread_id);
 }
 

lib/librte_eal/common/include/rte_eal.h static inline int rte_gettid(void) · line 268

Quoted 10 lines
lib/librte_eal/common/include/rte_eal.h +8 -2
-#define RTE_INIT(func) \
-static void __attribute__((constructor, used)) func(void)
+#define RTE_EAL_INIT(func) \
+static void __attribute__((constructor(101), used)) func(void)
+
+#define RTE_POST_EAL_INIT(func) \
+static void __attribute__((constructor(102), used)) func(void)
+
+#define RTE_DEV_INIT(func) \
+static void __attribute__((constructor(103), used)) func(void)

Shouldn't we simply allow this priority to be default to allow for some priority space between buses and default init?

Quoted 19 lines
lib/librte_eal/common/include/rte_eal.h +2 -0
+
+#define RTE_INIT(func) RTE_DEV_INIT(func)
 
 #ifdef __cplusplus
 }
lib/librte_eal/common/include/rte_tailq.h +1 -1
index 3aae098..07ceec1 100644
@@ -148,7 +148,7 @@ struct rte_tailq_head *rte_eal_tailq_lookup(const char *name);
 int rte_eal_tailq_register(struct rte_tailq_elem *t);
 
 #define EAL_REGISTER_TAILQ(t) \
-RTE_INIT(tailqinitfn_ ##t); \
+RTE_EAL_INIT(tailqinitfn_ ##t); \
 static void tailqinitfn_ ##t(void) \
 { \
 	if (rte_eal_tailq_register(&t) < 0) \
author
#3 lore raw

Re: [PATCH 1/7] eal: use different constructor priorities for initcalls

Quoted 8 lines · Shreyansh Jain
Quoted 7 lines · Jan Blunck
lib/librte_eal/common/include/rte_eal.h +0 -0
@@ -258,8 +258,16 @@ static inline int rte_gettid(void)
        return RTE_PER_LCORE(_thread_id);
 }
 
Quoted 15 lines

lib/librte_eal/common/include/rte_eal.h static inline int rte_gettid(void) · line 268

Quoted 10 lines
lib/librte_eal/common/include/rte_eal.h +8 -2
-#define RTE_INIT(func) \
-static void __attribute__((constructor, used)) func(void)
+#define RTE_EAL_INIT(func) \
+static void __attribute__((constructor(101), used)) func(void)
+
+#define RTE_POST_EAL_INIT(func) \
+static void __attribute__((constructor(102), used)) func(void)
+
+#define RTE_DEV_INIT(func) \
+static void __attribute__((constructor(103), used)) func(void)

Shouldn't we simply allow this priority to be default to allow for some priority space between buses and default init?

The absolute numbers are not that important. We can always adjust them. Important is the relative order. If you have a use-case for something that needs to be initialized before the devices but can't get initialized with the eal/post-eal then please speak up.

#4 lore raw

Re: [PATCH 1/7] eal: use different constructor priorities for initcalls

Quoted 25 lines · Jan Blunck
Quoted 8 lines · Shreyansh Jain
Quoted 7 lines · Jan Blunck
lib/librte_eal/common/include/rte_eal.h +0 -0
@@ -258,8 +258,16 @@ static inline int rte_gettid(void)
        return RTE_PER_LCORE(_thread_id);
 }
 
Quoted 15 lines

lib/librte_eal/common/include/rte_eal.h static inline int rte_gettid(void) · line 268

Quoted 10 lines
lib/librte_eal/common/include/rte_eal.h +8 -2
-#define RTE_INIT(func) \
-static void __attribute__((constructor, used)) func(void)
+#define RTE_EAL_INIT(func) \
+static void __attribute__((constructor(101), used)) func(void)
+
+#define RTE_POST_EAL_INIT(func) \
+static void __attribute__((constructor(102), used)) func(void)
+
+#define RTE_DEV_INIT(func) \
+static void __attribute__((constructor(103), used)) func(void)

Shouldn't we simply allow this priority to be default to allow for some priority space between buses and default init?

Quoted 5 lines

The absolute numbers are not that important. We can always adjust them. Important is the relative order. If you have a use-case for something that needs to be initialized before the devices but can't get initialized with the eal/post-eal then please speak up.

No use-case as of now.

author
#5 lore raw

PATCH 2/7 eal: probe legacy PCI devices before other bus devices

In reply to Jan Blunck

Make sure that the PCI devices are probed before the virtual devices after the legacy virtual device probing has been moved to a bus.

---
 lib/librte_eal/bsdapp/eal/eal.c   | 8 ++++----
 lib/librte_eal/linuxapp/eal/eal.c | 8 ++++----
 2 files changed, 8 insertions(+), 8 deletions(-)
lib/librte_eal/bsdapp/eal/eal.c +4 -4
index ee7c9de..a584447 100644
@@ -613,14 +613,14 @@ rte_eal_init(int argc, char **argv)
 	rte_eal_mp_remote_launch(sync_func, NULL, SKIP_MASTER);
 	rte_eal_mp_wait_lcore();
 
-	/* Probe all the buses and devices/drivers on them */
-	if (rte_bus_probe())
-		rte_panic("Cannot probe devices\n");
-
 	/* Probe & Initialize PCI devices */
 	if (rte_eal_pci_probe())
 		rte_panic("Cannot probe PCI\n");
 
+	/* Probe all the buses and devices/drivers on them */
+	if (rte_bus_probe())
+		rte_panic("Cannot probe devices\n");
+
 	if (rte_eal_dev_init() < 0)
 		rte_panic("Cannot init pmd devices\n");
 
lib/librte_eal/linuxapp/eal/eal.c +4 -4
index bf6b818..f77ff5c 100644
@@ -884,14 +884,14 @@ rte_eal_init(int argc, char **argv)
 	rte_eal_mp_remote_launch(sync_func, NULL, SKIP_MASTER);
 	rte_eal_mp_wait_lcore();
 
-	/* Probe all the buses and devices/drivers on them */
-	if (rte_bus_probe())
-		rte_panic("Cannot probe devices\n");
-
 	/* Probe & Initialize PCI devices */
 	if (rte_eal_pci_probe())
 		rte_panic("Cannot probe PCI\n");
 
+	/* Probe all the buses and devices/drivers on them */
+	if (rte_bus_probe())
+		rte_panic("Cannot probe devices\n");
+
 	if (rte_eal_dev_init() < 0)
 		rte_panic("Cannot init pmd devices\n");
 
Signature · 1 line
2.7.4
author
#7 lore raw

PATCH 3/7 eal: move virtual device probing into a bus

In reply to Jan Blunck

This is a refactoring of the virtual device probing which moves into into a proper bus structure.

---
 lib/librte_eal/common/eal_common_dev.c  | 22 -----------------
 lib/librte_eal/common/eal_common_vdev.c | 44 +++++++++++++++++++++++++++++++++
 2 files changed, 44 insertions(+), 22 deletions(-)
lib/librte_eal/common/eal_common_dev.c +0 -22
index 4f3b493..1ce90f6 100644
@@ -79,28 +79,6 @@ void rte_eal_device_remove(struct rte_device *dev)
 int
 rte_eal_dev_init(void)
 {
-	struct rte_devargs *devargs;
-
-	/*
-	 * Note that the dev_driver_list is populated here
-	 * from calls made to rte_eal_driver_register from constructor functions
-	 * embedded into PMD modules via the RTE_PMD_REGISTER_VDEV macro
-	 */
-
-	/* call the init function for each virtual device */
-	TAILQ_FOREACH(devargs, &devargs_list, next) {
-
-		if (devargs->type != RTE_DEVTYPE_VIRTUAL)
-			continue;
-
-		if (rte_eal_vdev_init(devargs->virt.drv_name,
-					devargs->args)) {
-			RTE_LOG(ERR, EAL, "failed to initialize %s device\n",
-					devargs->virt.drv_name);
-			return -1;
-		}
-	}
-
 	return 0;
 }
 
lib/librte_eal/common/eal_common_vdev.c +44 -0

55 lines not on this page · raw message

Signature · 1 line
2.7.4
#8 lore raw

Re: [PATCH 3/7] eal: move virtual device probing into a bus

Quoted 9 lines · Jan Blunck

This is a refactoring of the virtual device probing which moves into into a proper bus structure.

---
 lib/librte_eal/common/eal_common_dev.c  | 22 -----------------
 lib/librte_eal/common/eal_common_vdev.c | 44 +++++++++++++++++++++++++++++++++
 2 files changed, 44 insertions(+), 22 deletions(-)

[...]

Quoted 9 lines
lib/librte_eal/common/eal_common_vdev.c +0 -0
index 7d6e54f..523a3d6 100644
@@ -37,8 +37,10 @@
 #include <stdint.h>
 #include <sys/queue.h>
 

[...]

lib/librte_eal/common/eal_common_vdev.c rte_eal_vdev_uninit(const char *name) · line 168

Quoted 8 lines
lib/librte_eal/common/eal_common_vdev.c +7 -0
+
+static struct rte_bus rte_vdev_bus = {
+	.scan = vdev_scan,
+	.probe = vdev_probe,
+};
+
+RTE_REGISTER_BUS_LATE(virtual, rte_vdev_bus);

Does it matter if VDEV buses are registered before or after other buses? Either way, the callbacks would be called in the order specified in EAL.

#9 lore raw

Re: [PATCH 3/7] eal: move virtual device probing into a bus

Quoted 26 lines · Shreyansh Jain
Quoted 10 lines · Jan Blunck

This is a refactoring of the virtual device probing which moves into into a proper bus structure.

---
 lib/librte_eal/common/eal_common_dev.c  | 22 -----------------
 lib/librte_eal/common/eal_common_vdev.c | 44
+++++++++++++++++++++++++++++++++
 2 files changed, 44 insertions(+), 22 deletions(-)

[...]

Quoted 10 lines
lib/librte_eal/common/eal_common_vdev.c +0 -0
index 7d6e54f..523a3d6 100644
@@ -37,8 +37,10 @@
 #include <stdint.h>
 #include <sys/queue.h>
 

[...]

Quoted 14 lines

lib/librte_eal/common/eal_common_vdev.c rte_eal_vdev_uninit(const char *name) · line 168

Quoted 8 lines
lib/librte_eal/common/eal_common_vdev.c +7 -0
+
+static struct rte_bus rte_vdev_bus = {
+    .scan = vdev_scan,
+    .probe = vdev_probe,
+};
+
+RTE_REGISTER_BUS_LATE(virtual, rte_vdev_bus);

Does it matter if VDEV buses are registered before or after other buses? Either way, the callbacks would be called in the order specified in EAL.

Just ignore this comment - I am misunderstood something.

But another question: Is there specific reason VDEV should be registered/scanned *after* other devices? Is there some specific problem if we do otherwise? (I think this is should be done, but I don't have a specific reason).

#10 lore raw

Re: [PATCH 3/7] eal: move virtual device probing into a bus

Quoted 45 lines · Shreyansh Jain
Quoted 26 lines · Shreyansh Jain
Quoted 10 lines · Jan Blunck

This is a refactoring of the virtual device probing which moves into into a proper bus structure.

---
lib/librte_eal/common/eal_common_dev.c | 22 ----------------- lib/librte_eal/common/eal_common_vdev.c | 44
+++++++++++++++++++++++++++++++++

2 files changed, 44 insertions(+), 22 deletions(-)

[...]

Quoted 10 lines
lib/librte_eal/common/eal_common_vdev.c +0 -0
index 7d6e54f..523a3d6 100644
@@ -37,8 +37,10 @@
 #include <stdint.h>
 #include <sys/queue.h>
 

[...]

Quoted 14 lines

lib/librte_eal/common/eal_common_vdev.c rte_eal_vdev_uninit(const char *name) · line 168

Quoted 8 lines
lib/librte_eal/common/eal_common_vdev.c +7 -0
+
+static struct rte_bus rte_vdev_bus = {
+    .scan = vdev_scan,
+    .probe = vdev_probe,
+};
+
+RTE_REGISTER_BUS_LATE(virtual, rte_vdev_bus);

Does it matter if VDEV buses are registered before or after other buses? Either way, the callbacks would be called in the order specified in EAL.

Quoted 3 lines

Just ignore this comment - I am misunderstood something.

But another question: Is there specific reason VDEV should be registered/scanned *after* other devices? Is there some specific problem if we do otherwise? (I think this is should be done, but I don't have a specific reason).

Does the bonding driver which uses physical devices need to be registered after physical ones? In Pktgen I noticed the vdev after the physical ports and I could not blacklist them as the bonding driver needed them, which caused the bonding ports to have a greater port number. In the case of pktgen the bonding ports were up around 8 or 10 and caused the display to not show the bonding ports. This is really just a usability problem for the developer using Pktgen. I would like to see the vdev devices first, but as long as the drivers (like bonding) are fine with them being first.

Regards,
Keith

#11 lore raw

Re: [PATCH 3/7] eal: move virtual device probing into a bus

Quoted 60 lines

-----Original Message-----
From: Wiles, Keith [mailto:[email protected]]
Sent: Wednesday, February 15, 2017 7:53 PM
To: Shreyansh Jain <[email protected]>
Cc: Jan Blunck <[email protected]>; [email protected]
Subject: Re: [dpdk-dev] [PATCH 3/7] eal: move virtual device probing into a bus

Quoted 44 lines · Shreyansh Jain
Quoted 26 lines · Shreyansh Jain
Quoted 10 lines · Jan Blunck

This is a refactoring of the virtual device probing which moves into into a proper bus structure.

---
lib/librte_eal/common/eal_common_dev.c | 22 ----------------- lib/librte_eal/common/eal_common_vdev.c | 44
+++++++++++++++++++++++++++++++++

2 files changed, 44 insertions(+), 22 deletions(-)

[...]

Quoted 10 lines
lib/librte_eal/common/eal_common_vdev.c +0 -0
index 7d6e54f..523a3d6 100644
@@ -37,8 +37,10 @@
 #include <stdint.h>
 #include <sys/queue.h>
 

[...]

Quoted 14 lines

lib/librte_eal/common/eal_common_vdev.c rte_eal_vdev_uninit(const char *name) · line 168

Quoted 8 lines
lib/librte_eal/common/eal_common_vdev.c +7 -0
+
+static struct rte_bus rte_vdev_bus = {
+    .scan = vdev_scan,
+    .probe = vdev_probe,
+};
+
+RTE_REGISTER_BUS_LATE(virtual, rte_vdev_bus);

Does it matter if VDEV buses are registered before or after other buses? Either way, the callbacks would be called in the order specified in EAL.

Quoted 3 lines

Just ignore this comment - I am misunderstood something.

But another question: Is there specific reason VDEV should be

registered/scanned *after* other devices? Is there some specific problem if we do otherwise? (I think this is should be done, but I don't have a specific reason).

Quoted 8 lines

Does the bonding driver which uses physical devices need to be registered after physical ones? In Pktgen I noticed the vdev after the physical ports and I could not blacklist them as the bonding driver needed them, which caused the bonding ports to have a greater port number. In the case of pktgen the bonding ports were up around 8 or 10 and caused the display to not show the bonding ports. This is really just a usability problem for the developer using Pktgen. I would like to see the vdev devices first, but as long as the drivers (like bonding) are fine with them being first.

Ah, now I remember - there was a patch from Jerin for this. Probably he is the best person to comment here.
(I don't have much insight here).

Quoted 3 lines

Regards,
Keith

#12 lore raw

Re: [PATCH 3/7] eal: move virtual device probing into a bus

Quoted 69 lines · Shreyansh Jain
Quoted 60 lines

-----Original Message-----
From: Wiles, Keith [mailto:[email protected]]
Sent: Wednesday, February 15, 2017 7:53 PM
To: Shreyansh Jain <[email protected]>
Cc: Jan Blunck <[email protected]>; [email protected]
Subject: Re: [dpdk-dev] [PATCH 3/7] eal: move virtual device probing into a bus

Quoted 44 lines · Shreyansh Jain
Quoted 26 lines · Shreyansh Jain
Quoted 10 lines · Jan Blunck

This is a refactoring of the virtual device probing which moves into into a proper bus structure.

---
lib/librte_eal/common/eal_common_dev.c | 22 ----------------- lib/librte_eal/common/eal_common_vdev.c | 44
+++++++++++++++++++++++++++++++++

2 files changed, 44 insertions(+), 22 deletions(-)

[...]

Quoted 10 lines
lib/librte_eal/common/eal_common_vdev.c +0 -0
index 7d6e54f..523a3d6 100644
@@ -37,8 +37,10 @@
 #include <stdint.h>
 #include <sys/queue.h>
 

[...]

Quoted 14 lines

lib/librte_eal/common/eal_common_vdev.c rte_eal_vdev_uninit(const char *name) · line 168

Quoted 8 lines
lib/librte_eal/common/eal_common_vdev.c +7 -0
+
+static struct rte_bus rte_vdev_bus = {
+    .scan = vdev_scan,
+    .probe = vdev_probe,
+};
+
+RTE_REGISTER_BUS_LATE(virtual, rte_vdev_bus);

Does it matter if VDEV buses are registered before or after other buses? Either way, the callbacks would be called in the order specified in EAL.

Quoted 3 lines

Just ignore this comment - I am misunderstood something.

But another question: Is there specific reason VDEV should be

registered/scanned *after* other devices? Is there some specific problem if we do otherwise? (I think this is should be done, but I don't have a specific reason).

Quoted 8 lines

Does the bonding driver which uses physical devices need to be registered after physical ones? In Pktgen I noticed the vdev after the physical ports and I could not blacklist them as the bonding driver needed them, which caused the bonding ports to have a greater port number. In the case of pktgen the bonding ports were up around 8 or 10 and caused the display to not show the bonding ports. This is really just a usability problem for the developer using Pktgen. I would like to see the vdev devices first, but as long as the drivers (like bonding) are fine with them being first.

Quoted 3 lines

Ah, now I remember - there was a patch from Jerin for this. Probably he is the best person to comment here.
(I don't have much insight here).

commit f4ce209a8ce5f416b61c76cee773bc54749e2048

Author: Jerin Jacob <[email protected]>
Date:   Sun Nov 20 13:30:50 2016 +0530

eal: postpone vdev initialization

Some platform like octeontx may use pci and vdev based combined device to represent a logical dpdk functional device.In such case, postponing the vdev initialization after pci device initialization will provide the better view of the pci device resources in the system in vdev's probe function, and it allows better functional subsystem registration in vdev probe function.

As a bonus, This patch fixes a bond device
initialization use case.

example command to reproduce the issue:
./testpmd -c 0x2 --vdev 'eth_bond0,mode=0,
slave=0000:02:00.0,slave=0000:03:00.0' --
--port-topology=chained

root cause:
In existing case(vdev initialization and then pci initialization), creates three Ethernet ports with following port ids
0 - Bond device
1 - PCI device 0
2 - PCI devive 1

Since testpmd, calls the configure/start on all the ports on start up,it will translate to following illegal setup sequence

1)bond device configure/start
1.1) pci device0 stop/configure/start
1.2) pci device1 stop/configure/start
2)pci device 0 configure(illegal setup case,
as device in start state)

The fix changes the initialization sequence and allow initialization in following valid setup order
1) pcie device 0 configure/start
2) pcie device 1 configure/start
3) bond device 2 configure/start
3.1) pcie device 0/stop/configure/start 3.2) pcie device 1/stop/configure/start

#13 lore raw

Re: [PATCH 3/7] eal: move virtual device probing into a bus

Quoted 109 lines · Jerin Jacob
Quoted 69 lines · Shreyansh Jain
Quoted 60 lines

-----Original Message-----
From: Wiles, Keith [mailto:[email protected]]
Sent: Wednesday, February 15, 2017 7:53 PM
To: Shreyansh Jain <[email protected]>
Cc: Jan Blunck <[email protected]>; [email protected]
Subject: Re: [dpdk-dev] [PATCH 3/7] eal: move virtual device probing into a bus

Quoted 44 lines · Shreyansh Jain
Quoted 26 lines · Shreyansh Jain
Quoted 10 lines · Jan Blunck

This is a refactoring of the virtual device probing which moves into into a proper bus structure.

---
lib/librte_eal/common/eal_common_dev.c | 22 ----------------- lib/librte_eal/common/eal_common_vdev.c | 44
+++++++++++++++++++++++++++++++++

2 files changed, 44 insertions(+), 22 deletions(-)

[...]

Quoted 10 lines
lib/librte_eal/common/eal_common_vdev.c +0 -0
index 7d6e54f..523a3d6 100644
@@ -37,8 +37,10 @@
 #include <stdint.h>
 #include <sys/queue.h>
 

[...]

Quoted 14 lines

lib/librte_eal/common/eal_common_vdev.c rte_eal_vdev_uninit(const char *name) · line 168

Quoted 8 lines
lib/librte_eal/common/eal_common_vdev.c +7 -0
+
+static struct rte_bus rte_vdev_bus = {
+    .scan = vdev_scan,
+    .probe = vdev_probe,
+};
+
+RTE_REGISTER_BUS_LATE(virtual, rte_vdev_bus);

Does it matter if VDEV buses are registered before or after other buses? Either way, the callbacks would be called in the order specified in EAL.

Quoted 3 lines

Just ignore this comment - I am misunderstood something.

But another question: Is there specific reason VDEV should be

registered/scanned *after* other devices? Is there some specific problem if we do otherwise? (I think this is should be done, but I don't have a specific reason).

Quoted 8 lines

Does the bonding driver which uses physical devices need to be registered after physical ones? In Pktgen I noticed the vdev after the physical ports and I could not blacklist them as the bonding driver needed them, which caused the bonding ports to have a greater port number. In the case of pktgen the bonding ports were up around 8 or 10 and caused the display to not show the bonding ports. This is really just a usability problem for the developer using Pktgen. I would like to see the vdev devices first, but as long as the drivers (like bonding) are fine with them being first.

Quoted 3 lines

Ah, now I remember - there was a patch from Jerin for this. Probably he is the best person to comment here.
(I don't have much insight here).

commit f4ce209a8ce5f416b61c76cee773bc54749e2048

Author: Jerin Jacob <[email protected]>
Date:   Sun Nov 20 13:30:50 2016 +0530

eal: postpone vdev initialization

Some platform like octeontx may use pci and vdev based combined device to represent a logical dpdk functional device.In such case, postponing the vdev initialization after pci device initialization will provide the better view of the pci device resources in the system in vdev's probe function, and it allows better functional subsystem registration in vdev probe function.

As a bonus, This patch fixes a bond device
initialization use case.

example command to reproduce the issue:
./testpmd -c 0x2 --vdev 'eth_bond0,mode=0,
slave=0000:02:00.0,slave=0000:03:00.0' --
--port-topology=chained

root cause:
In existing case(vdev initialization and then pci initialization), creates three Ethernet ports with following port ids
0 - Bond device
1 - PCI device 0
2 - PCI devive 1

Quoted 2 lines

Since testpmd, calls the configure/start on all the ports on start up,it will translate to following illegal setup sequence

I guess I see this differently, meaning we modified the system to put vdev devices last only because we do not have clean way to startup the system for pdev/vdev devices. The application should be agnostic to the devices being started and the system needs to determine the correct order without a chicken and egg problem. The test-pmd application just starts from 0 to n to initialize devices, which he should be able to do in any order. It is possible the application could initialize the devices (pdev/vdev) in any order, which the current design would break if they tried to init the bonding driver first.

What happens if a vdev needs to be initialized before a pdev device?

Not saying we need to solve this problem now, but need to figure this out some how. Maybe we need a priority for pdev/vdev devices to determine init order????

Quoted 7 lines

1)bond device configure/start
1.1) pci device0 stop/configure/start
1.2) pci device1 stop/configure/start
2)pci device 0 configure(illegal setup case,
as device in start state)

Quoted 7 lines

The fix changes the initialization sequence and allow initialization in following valid setup order
1) pcie device 0 configure/start
2) pcie device 1 configure/start
3) bond device 2 configure/start
3.1) pcie device 0/stop/configure/start 3.2) pcie device 1/stop/configure/start

Regards,
Keith

author
#14 lore raw

Re: [PATCH 3/7] eal: move virtual device probing into a bus

Quoted 3 lines · Keith

I guess I see this differently, meaning we modified the system to put vdev devices last only because we do not have clean way to startup the system for pdev/vdev devices. The application should be agnostic to the devices being started and the system needs to determine the correct order without a chicken and egg problem. The test-pmd application just starts from 0 to n to initialize devices, which he should be able to do in any order. It is possible the application could initialize the devices (pdev/vdev) in any order, which the current design would break if they tried to init the bonding driver first.

Apart from the usability (vdevs always first) I wonder what kind of usecase you are after. If I understand you correctly you want to:
- probe the virtual devices first
- start/configure the virtual devices last

... and only in some cases. From what I understand this requires a domain specific way to model dependencies between ports, e.g. some standardized device arguments parsed by EAL, and combined with your requirement to assign the lowest port numbers for the vdev devices even a scheduler.

Maybe we could reduce complexity by doing some simple things instead:
if you present the ports in reverse order to the users the vdev come first. Probably this even increases usability because the most recent created port is the one that the user is anyway most interested in.

Quoted 2 lines

What happens if a vdev needs to be initialized before a pdev device?

This should never happen. The pdev devices offer a plain view on the "system", which means no topology at all. The vdev devices are devices that do not have a "system" representation, e.g. a library. I don't think the EAL should offer an alternative API to system programming in a way that you enumerate your PCI devices through a vdev that is accessing hardware through another library.

Quoted 2 lines

Not saying we need to solve this problem now, but need to figure this out some how. Maybe we need a priority for pdev/vdev devices to determine init order????

#15 lore raw

Re: [PATCH 3/7] eal: move virtual device probing into a bus

Quoted 13 lines · Jan Blunck
Quoted 3 lines · Keith

I guess I see this differently, meaning we modified the system to put vdev devices last only because we do not have clean way to startup the system for pdev/vdev devices. The application should be agnostic to the devices being started and the system needs to determine the correct order without a chicken and egg problem. The test-pmd application just starts from 0 to n to initialize devices, which he should be able to do in any order. It is possible the application could initialize the devices (pdev/vdev) in any order, which the current design would break if they tried to init the bonding driver first.

Apart from the usability (vdevs always first) I wonder what kind of usecase you are after. If I understand you correctly you want to:
- probe the virtual devices first
- start/configure the virtual devices last

Quoted 5 lines

... and only in some cases. From what I understand this requires a domain specific way to model dependencies between ports, e.g. some standardized device arguments parsed by EAL, and combined with your requirement to assign the lowest port numbers for the vdev devices even a scheduler.

I do not think moving vdev to the front is going to really solve my use case it, as it will create more problems then solve. The real case here is if the application developer inits devices out of order then he can hit the bonding driver bug. The current solution does not really fix the problem only bandaid the problem for the common ordered case.

Do we need to solve this problem, maybe not, but it needs to be documented or we need to provide a cleaner way for the application to startup all devices in the correct order. A possible way is to have callback to the application in the correct order for him to initialize the devices, but not a great solution per say.

Quoted 9 lines

Maybe we could reduce complexity by doing some simple things instead:
if you present the ports in reverse order to the users the vdev come first. Probably this even increases usability because the most recent created port is the one that the user is anyway most interested in.

Quoted 2 lines

What happens if a vdev needs to be initialized before a pdev device?

Quoted 9 lines

This should never happen. The pdev devices offer a plain view on the "system", which means no topology at all. The vdev devices are devices that do not have a "system" representation, e.g. a library. I don't think the EAL should offer an alternative API to system programming in a way that you enumerate your PCI devices through a vdev that is accessing hardware through another library.

Quoted 2 lines

Not saying we need to solve this problem now, but need to figure this out some how. Maybe we need a priority for pdev/vdev devices to determine init order????

Regards,
Keith

author
#16 lore raw

Re: [PATCH 3/7] eal: move virtual device probing into a bus

In reply to Wiles, Keith
Quoted 8 lines · Keith
Quoted 7 lines · Shreyansh Jain

Just ignore this comment - I am misunderstood something.

But another question: Is there specific reason VDEV should be registered/scanned *after* other devices? Is there some specific problem if we do otherwise? (I think this is should be done, but I don't have a specific reason).

Just for context: the vdev's are probed after the physical devices because of commit f4ce209a ("eal: postpone vdev initialization").

Quoted 2 lines

Does the bonding driver which uses physical devices need to be registered after physical ones? In Pktgen I noticed the vdev after the physical ports and I could not blacklist them as the bonding driver needed them, which caused the bonding ports to have a greater port number. In the case of pktgen the bonding ports were up around 8 or 10 and caused the display to not show the bonding ports. This is really just a usability problem for the developer using Pktgen. I would like to see the vdev devices first, but as long as the drivers (like bonding) are fine with them being first.

The bonding devargs might specify slaves that get attached during device probe. If the referenced devices are physical interfaces we need to probe them first. This is really a chicken-egg-problem.

Maybe you could improve the usability in your case and sort the virtual devices first or even hide enslaved ports?

#17 lore raw

Re: [PATCH 3/7] eal: move virtual device probing into a bus

Quoted 19 lines · Jan Blunck
Quoted 8 lines · Keith
Quoted 7 lines · Shreyansh Jain

Just ignore this comment - I am misunderstood something.

But another question: Is there specific reason VDEV should be registered/scanned *after* other devices? Is there some specific problem if we do otherwise? (I think this is should be done, but I don't have a specific reason).

Just for context: the vdev's are probed after the physical devices because of commit f4ce209a ("eal: postpone vdev initialization").

Quoted 2 lines

Does the bonding driver which uses physical devices need to be registered after physical ones? In Pktgen I noticed the vdev after the physical ports and I could not blacklist them as the bonding driver needed them, which caused the bonding ports to have a greater port number. In the case of pktgen the bonding ports were up around 8 or 10 and caused the display to not show the bonding ports. This is really just a usability problem for the developer using Pktgen. I would like to see the vdev devices first, but as long as the drivers (like bonding) are fine with them being first.

Quoted 6 lines

The bonding devargs might specify slaves that get attached during device probe. If the referenced devices are physical interfaces we need to probe them first. This is really a chicken-egg-problem.

Maybe you could improve the usability in your case and sort the virtual devices first or even hide enslaved ports?

The port numbering comes from DPDK and I use that directly, was trying to avoid a translation of real port to Pktgen port :-(

Regards,
Keith

#18 lore raw

Re: [PATCH 3/7] eal: move virtual device probing into a bus

Quoted 26 lines · Keith
Quoted 24 lines · Jan Blunck
Quoted 8 lines · Keith
Quoted 7 lines · Shreyansh Jain

Just ignore this comment - I am misunderstood something.

But another question: Is there specific reason VDEV should be registered/scanned *after* other devices? Is there some specific problem if we do otherwise? (I think this is should be done, but I don't have a specific reason).

Just for context: the vdev's are probed after the physical devices because of commit f4ce209a ("eal: postpone vdev initialization").

Quoted 2 lines

Does the bonding driver which uses physical devices need to be registered after physical ones? In Pktgen I noticed the vdev after the physical ports and I could not blacklist them as the bonding driver needed them, which caused the bonding ports to have a greater port number. In the case of pktgen the bonding ports were up around 8 or 10 and caused the display to not show the bonding ports. This is really just a usability problem for the developer using Pktgen. I would like to see the vdev devices first, but as long as the drivers (like bonding) are fine with them being first.

The bonding devargs might specify slaves that get attached during device probe. If the referenced devices are physical interfaces we need to probe them first. This is really a chicken-egg-problem.

Quoted 8 lines
Quoted 2 lines

Maybe you could improve the usability in your case and sort the virtual devices first or even hide enslaved ports?

The port numbering comes from DPDK and I use that directly, was trying to avoid a translation of real port to Pktgen port :-(

Regards,
Keith

Looking at the bonding driver it does not attempt to access the physical ports until bond_ethdev_configure call (I believe). This means the vdev devices should be following the same flow and moving them to before the physical probes would be fine, right?

Regards,
Keith

author
#19 lore raw

Re: [PATCH 3/7] eal: move virtual device probing into a bus

In reply to Shreyansh Jain
Quoted 14 lines · Shreyansh Jain

lib/librte_eal/common/eal_common_vdev.c rte_eal_vdev_uninit(const char *name) · line 168

Quoted 10 lines · Jan Blunck
lib/librte_eal/common/eal_common_vdev.c +7 -0
+
+static struct rte_bus rte_vdev_bus = {
+       .scan = vdev_scan,
+       .probe = vdev_probe,
+};
+
+RTE_REGISTER_BUS_LATE(virtual, rte_vdev_bus);

Does it matter if VDEV buses are registered before or after other buses?

Yes, it does. Also see commit f4ce209a ("eal: postpone vdev initialization").

Quoted 2 lines

Either way, the callbacks would be called in the order specified in EAL.

They are called in order of registration. That is why this defers the registration of the vdev bus.

#20 lore raw

Re: [PATCH 3/7] eal: move virtual device probing into a bus

Quoted 16 lines · Jan Blunck
Quoted 14 lines · Shreyansh Jain

lib/librte_eal/common/eal_common_vdev.c rte_eal_vdev_uninit(const char *name) · line 168

Quoted 10 lines · Jan Blunck
lib/librte_eal/common/eal_common_vdev.c +7 -0
+
+static struct rte_bus rte_vdev_bus = {
+       .scan = vdev_scan,
+       .probe = vdev_probe,
+};
+
+RTE_REGISTER_BUS_LATE(virtual, rte_vdev_bus);

Does it matter if VDEV buses are registered before or after other buses?

Quoted 7 lines

Yes, it does. Also see commit f4ce209a ("eal: postpone vdev initialization").

Quoted 2 lines

Either way, the callbacks would be called in the order specified in EAL.

They are called in order of registration. That is why this defers the registration of the vdev bus.

Agree - I realized the problem in my statement after I had sent the email.

author
#21 lore raw

PATCH 4/7 eal: remove unused rte_eal_dev_init()

In reply to Jan Blunck
---
 lib/librte_eal/bsdapp/eal/eal.c         | 3 ---
 lib/librte_eal/common/eal_common_dev.c  | 6 ------
 lib/librte_eal/common/include/rte_dev.h | 5 -----
 lib/librte_eal/linuxapp/eal/eal.c       | 3 ---
 4 files changed, 17 deletions(-)
lib/librte_eal/bsdapp/eal/eal.c +0 -3
index a584447..3d29fcb 100644
@@ -621,9 +621,6 @@ rte_eal_init(int argc, char **argv)
 	if (rte_bus_probe())
 		rte_panic("Cannot probe devices\n");
 
-	if (rte_eal_dev_init() < 0)
-		rte_panic("Cannot init pmd devices\n");
-
 	rte_eal_mcfg_complete();
 
 	return fctret;
lib/librte_eal/common/eal_common_dev.c +0 -6
index 1ce90f6..4bde430 100644
@@ -76,12 +76,6 @@ void rte_eal_device_remove(struct rte_device *dev)
 	TAILQ_REMOVE(&dev_device_list, dev, next);
 }
 
-int
-rte_eal_dev_init(void)
-{
-	return 0;
-}
-
 int rte_eal_dev_attach(const char *name, const char *devargs)
 {
 	struct rte_pci_addr addr;
lib/librte_eal/common/include/rte_dev.h +0 -5
index b17791f..4251099 100644
@@ -171,11 +171,6 @@ void rte_eal_driver_register(struct rte_driver *driver);
 void rte_eal_driver_unregister(struct rte_driver *driver);
 
 /**
- * Initalize all the registered drivers in this process
- */
-int rte_eal_dev_init(void);
-
-/**
  * Initialize a driver specified by name.
  *
  * @param name
lib/librte_eal/linuxapp/eal/eal.c +0 -3
index f77ff5c..88479de 100644
@@ -892,9 +892,6 @@ rte_eal_init(int argc, char **argv)
 	if (rte_bus_probe())
 		rte_panic("Cannot probe devices\n");
 
-	if (rte_eal_dev_init() < 0)
-		rte_panic("Cannot init pmd devices\n");
-
 	rte_eal_mcfg_complete();
 
 	return fctret;
Signature · 1 line
2.7.4
#22 lore raw

Re: [PATCH 4/7] eal: remove unused rte_eal_dev_init()

Quoted 1 line · Jan Blunck

<...>

lib/librte_eal/common/eal_common_dev.c void rte_eal_device_remove(struct rte_device *dev) · line 84

Quoted 6 lines
lib/librte_eal/common/eal_common_dev.c +0 -6
-int
-rte_eal_dev_init(void)
-{
-	return 0;
-}
-

API should be removed from .map files too (rte_eal_version.map).

author
#23 lore raw

PATCH 5/7 eal: Refactor vdev driver probe/remove

In reply to Jan Blunck

This is a preparation for the introduction of the struct rte_vdev_device.

---
 lib/librte_eal/common/eal_common_vdev.c | 44 ++++++++++++++++++++++++---------
 1 file changed, 33 insertions(+), 11 deletions(-)
lib/librte_eal/common/eal_common_vdev.c +33 -11
index 523a3d6..6ba3c91 100644
@@ -61,14 +61,11 @@ rte_eal_vdrv_unregister(struct rte_vdev_driver *driver)
 	TAILQ_REMOVE(&vdev_driver_list, driver, next);
 }
 
-int
-rte_eal_vdev_init(const char *name, const char *args)
+static int
+vdev_probe_all_drivers(const char *name, const char *args)
 {
 	struct rte_vdev_driver *driver;
 
-	if (name == NULL)
-		return -EINVAL;
-
 	TAILQ_FOREACH(driver, &vdev_driver_list, next) {
 		/*
 		 * search a driver prefix in virtual device name.
@@ -89,18 +86,29 @@ rte_eal_vdev_init(const char *name, const char *args)
 			return driver->probe(name, args);
 	}
 
-	RTE_LOG(ERR, EAL, "no driver found for %s\n", name);
-	return -EINVAL;
+	return 1;
 }
 
 int
-rte_eal_vdev_uninit(const char *name)
+rte_eal_vdev_init(const char *name, const char *args)
 {
-	struct rte_vdev_driver *driver;
+	int ret;
 
 	if (name == NULL)
 		return -EINVAL;
 
+	ret = vdev_probe_all_drivers(name, args);
+	if (ret  > 0)
+		RTE_LOG(ERR, EAL, "no driver found for %s\n", name);
+
+	return ret;
+}
+
+static int
+vdev_remove_driver(const char *name)
+{
+	struct rte_vdev_driver *driver;
+
 	TAILQ_FOREACH(driver, &vdev_driver_list, next) {
 		/*
 		 * search a driver prefix in virtual device name.
@@ -121,8 +129,22 @@ rte_eal_vdev_uninit(const char *name)
 			return driver->remove(name);
 	}
 
-	RTE_LOG(ERR, EAL, "no driver found for %s\n", name);
-	return -EINVAL;
+	return 1;
+}
+
+int
+rte_eal_vdev_uninit(const char *name)
+{
+	int ret;
+
+	if (name == NULL)
+		return -EINVAL;
+
+	ret = vdev_remove_driver(name);
+	if (ret > 0)
+		RTE_LOG(ERR, EAL, "no driver found for %s\n", name);
+
+	return ret;
 }
 
 static int
Signature · 1 line
2.7.4
author
#24 lore raw

PATCH 6/7 eal: add struct rte_vdev_device

In reply to Jan Blunck

This adds the rte_vdev_device structure which embeds a generic rte_device.

---
 lib/librte_eal/common/eal_common_vdev.c  | 5 +++++
 lib/librte_eal/common/include/rte_vdev.h | 5 +++++
 2 files changed, 10 insertions(+)
lib/librte_eal/common/eal_common_vdev.c +5 -0
index 6ba3c91..61677de 100644
@@ -42,6 +42,11 @@
 #include <rte_common.h>
 #include <rte_devargs.h>
 
+/** Double linked list of virtual device drivers. */
+TAILQ_HEAD(vdev_device_list, rte_vdev_device);
+
+static struct vdev_device_list vdev_device_list =
+	TAILQ_HEAD_INITIALIZER(vdev_device_list);
 struct vdev_driver_list vdev_driver_list =
 	TAILQ_HEAD_INITIALIZER(vdev_driver_list);
 
lib/librte_eal/common/include/rte_vdev.h +5 -0
index 784e837..8f98372 100644
@@ -40,6 +40,11 @@ extern "C" {
 #include <sys/queue.h>
 #include <rte_dev.h>
 
+struct rte_vdev_device {
+	TAILQ_ENTRY(rte_vdev_device) next;      /**< Next attached vdev */
+	struct rte_device device;               /**< Inherit core device */
+};
+
 /** Double linked list of virtual device drivers. */
 TAILQ_HEAD(vdev_driver_list, rte_vdev_driver);
 
Signature · 1 line
2.7.4
#25 lore raw

Re: [PATCH 6/7] eal: add struct rte_vdev_device

Quoted 3 lines · Jan Blunck

This adds the rte_vdev_device structure which embeds a generic rte_device.

<...>

lib/librte_eal/common/include/rte_vdev.h extern "C" { · line 45

Quoted 4 lines
lib/librte_eal/common/include/rte_vdev.h +3 -0
+struct rte_vdev_device {
+	TAILQ_ENTRY(rte_vdev_device) next;      /**< Next attached vdev */
+	struct rte_device device;               /**< Inherit core device */

What do you think adding a name field here ?

"dev->device.devargs->virt.drv_name" used a few times, since probing virtual devices done based on name.

This is device name, and accessing it via "devargs->virt.drv_name" is not that clear. It is possible to create a name field here, set it during probe or init to point devargs field and use it wherever required, does it make sense?

Quoted 6 lines
lib/librte_eal/common/include/rte_vdev.h +2 -0
+};
+
 /** Double linked list of virtual device drivers. */
 TAILQ_HEAD(vdev_driver_list, rte_vdev_driver);
author
#26 lore raw

Re: [PATCH 6/7] eal: add struct rte_vdev_device

Quoted 14 lines · Ferruh Yigit
Quoted 3 lines · Jan Blunck

This adds the rte_vdev_device structure which embeds a generic rte_device.

<...>

lib/librte_eal/common/include/rte_vdev.h extern "C" { · line 45

Quoted 4 lines
lib/librte_eal/common/include/rte_vdev.h +3 -0
+struct rte_vdev_device {
+     TAILQ_ENTRY(rte_vdev_device) next;      /**< Next attached vdev */
+     struct rte_device device;               /**< Inherit core device */

What do you think adding a name field here ?

Quoted 8 lines

"dev->device.devargs->virt.drv_name" used a few times, since probing virtual devices done based on name.

This is device name, and accessing it via "devargs->virt.drv_name" is not that clear. It is possible to create a name field here, set it during probe or init to point devargs field and use it wherever required, does it make sense?

Why don't we add such a thing to the generic rte_device instead? While we are at it we might want to also add a driver private data field.

Thoughts?

author
#27 lore raw

PATCH 7/7 eal: make virtual bus use rte_vdev_device

In reply to Jan Blunck

This allows the virtual bus to be rescanned and probed by tracking the creation of rte_vdev_device.

---
 lib/librte_eal/common/eal_common_vdev.c | 194 +++++++++++++++++++++++++-------
 1 file changed, 154 insertions(+), 40 deletions(-)
lib/librte_eal/common/eal_common_vdev.c +154 -40
index 61677de..5909c85 100644
@@ -67,9 +67,12 @@ rte_eal_vdrv_unregister(struct rte_vdev_driver *driver)
 }
 
 static int
-vdev_probe_all_drivers(const char *name, const char *args)
+vdev_probe_all_drivers(struct rte_vdev_device *dev)
 {
+	char *name = dev->device.devargs->virt.drv_name;
+	char *args = dev->device.devargs->args;
 	struct rte_vdev_driver *driver;
+	int ret;
 
 	TAILQ_FOREACH(driver, &vdev_driver_list, next) {
 		/*
@@ -79,90 +82,202 @@ vdev_probe_all_drivers(const char *name, const char *args)
 		 * So use strncmp to compare.
 		 */
 		if (!strncmp(driver->driver.name, name,
-			    strlen(driver->driver.name)))
-			return driver->probe(name, args);
+			    strlen(driver->driver.name))) {
+			dev->device.driver = &driver->driver;
+			ret = driver->probe(name, args);
+			if (ret)
+				dev->device.driver = NULL;
+			return ret;
+		}
 	}
 
 	/* Give new names precedence over aliases. */
 	TAILQ_FOREACH(driver, &vdev_driver_list, next) {
 		if (driver->driver.alias &&
 		    !strncmp(driver->driver.alias, name,
-			    strlen(driver->driver.alias)))
-			return driver->probe(name, args);
+			    strlen(driver->driver.alias))) {
+			dev->device.driver = &driver->driver;
+			ret = driver->probe(name, args);
+			if (ret)
+				dev->device.driver = NULL;
+			return ret;
+		}
 	}
 
 	return 1;
 }
 
+static struct rte_vdev_device *
+find_vdev(const char *name)
+{
+	struct rte_vdev_device *dev;
+
+	if (!name)
+		return NULL;
+
+	TAILQ_FOREACH(dev, &vdev_device_list, next) {
+		if (!strncmp(dev->device.devargs->virt.drv_name, name,
+			strlen(name)))
+			return dev;
+	}
+
+	return NULL;
+}
+
+static struct rte_devargs *
+alloc_devargs(const char *name, const char *args)
+{
+	struct rte_devargs *devargs;
+	int ret;
+
+	devargs = calloc(1, sizeof(*devargs));
+	if (!devargs)
+		return NULL;
+
+	devargs->type = RTE_DEVTYPE_VIRTUAL;
+	if (args)
+		devargs->args = strdup(args);
+
+	ret = snprintf(devargs->virt.drv_name,
+			       sizeof(devargs->virt.drv_name), "%s", name);
+	if (ret < 0 || ret >= (int)sizeof(devargs->virt.drv_name)) {
+		free(devargs->args);
+		free(devargs);
+		return NULL;
+	}
+
+	return devargs;
+}
+
 int
 rte_eal_vdev_init(const char *name, const char *args)
 {
+	struct rte_vdev_device *dev;
+	struct rte_devargs *devargs;
 	int ret;
 
 	if (name == NULL)
 		return -EINVAL;
 
-	ret = vdev_probe_all_drivers(name, args);
-	if (ret  > 0)
-		RTE_LOG(ERR, EAL, "no driver found for %s\n", name);
+	dev = find_vdev(name);
+	if (dev)
+		return -EEXIST;
+
+	devargs = alloc_devargs(name, args);
+	if (!devargs)
+		return -ENOMEM;
+
+	dev = calloc(1, sizeof(*dev));
+	if (!dev) {
+		ret = -ENOMEM;
+		goto fail;
+	}
+
+	dev->device.devargs = devargs;
+	dev->device.numa_node = -1;
+
+	ret = vdev_probe_all_drivers(dev);
+	if (ret) {
+		if (ret > 0)
+			RTE_LOG(ERR, EAL, "no driver found for %s\n", name);
+		goto fail;
+	}
+
+	TAILQ_INSERT_TAIL(&devargs_list, devargs, next);
+
+	rte_eal_device_insert(&dev->device);
+	TAILQ_INSERT_TAIL(&vdev_device_list, dev, next);
+	return 0;
 
+fail:
+	free(devargs->args);
+	free(devargs);
+	free(dev);
 	return ret;
 }
 
 static int
-vdev_remove_driver(const char *name)
+vdev_remove_driver(struct rte_vdev_device *dev)
 {
-	struct rte_vdev_driver *driver;
+	char *name = dev->device.devargs->virt.drv_name;
+	const struct rte_vdev_driver *driver;
 
-	TAILQ_FOREACH(driver, &vdev_driver_list, next) {
-		/*
-		 * search a driver prefix in virtual device name.
-		 * For example, if the driver is pcap PMD, driver->name
-		 * will be "net_pcap", but "name" will be "net_pcapN".
-		 * So use strncmp to compare.
-		 */
-		if (!strncmp(driver->driver.name, name,
-			     strlen(driver->driver.name)))
-			return driver->remove(name);
-	}
-
-	/* Give new names precedence over aliases. */
-	TAILQ_FOREACH(driver, &vdev_driver_list, next) {
-		if (driver->driver.alias &&
-		    !strncmp(driver->driver.alias, name,
-			    strlen(driver->driver.alias)))
-			return driver->remove(name);
+	if (!dev->device.driver) {
+		RTE_LOG(DEBUG, EAL, "no driver attach to device %s\n", name);
+		return 1;
 	}
 
-	return 1;
+	driver = container_of(dev->device.driver, const struct rte_vdev_driver,
+		driver);
+	return driver->remove(name);
 }
 
 int
 rte_eal_vdev_uninit(const char *name)
 {
+	struct rte_vdev_device *dev;
+	struct rte_devargs *devargs;
 	int ret;
 
 	if (name == NULL)
 		return -EINVAL;
 
-	ret = vdev_remove_driver(name);
-	if (ret > 0)
-		RTE_LOG(ERR, EAL, "no driver found for %s\n", name);
+	dev = find_vdev(name);
+	if (!dev)
+		return -ENOENT;
 
-	return ret;
+	devargs = dev->device.devargs;
+
+	ret = vdev_remove_driver(dev);
+	if (ret)
+		return ret;
+
+	TAILQ_REMOVE(&vdev_device_list, dev, next);
+	rte_eal_device_remove(&dev->device);
+
+	TAILQ_REMOVE(&devargs_list, devargs, next);
+
+	free(devargs->args);
+	free(devargs);
+	free(dev);
+	return 0;
 }
 
 static int
 vdev_scan(void)
 {
-	/* for virtual devices we don't need to scan anything */
+	struct rte_vdev_device *dev;
+	struct rte_devargs *devargs;
+
+	/* for virtual devices we scan the devargs_list populated via cmdline */
+
+	TAILQ_FOREACH(devargs, &devargs_list, next) {
+
+		if (devargs->type != RTE_DEVTYPE_VIRTUAL)
+			continue;
+
+		dev = find_vdev(devargs->virt.drv_name);
+		if (dev)
+			continue;
+
+		dev = calloc(1, sizeof(*dev));
+		if (!dev)
+			return -1;
+
+		dev->device.devargs = devargs;
+		dev->device.numa_node = -1;
+
+		rte_eal_device_insert(&dev->device);
+		TAILQ_INSERT_TAIL(&vdev_device_list, dev, next);
+	}
+
 	return 0;
 }
 
 static int
 vdev_probe(void)
 {
-	struct rte_devargs *devargs;
+	struct rte_vdev_device *dev;
 
 	/*
 	 * Note that the dev_driver_list is populated here
@@ -171,15 +286,14 @@ vdev_probe(void)
 	 */
 
 	/* call the init function for each virtual device */
-	TAILQ_FOREACH(devargs, &devargs_list, next) {
+	TAILQ_FOREACH(dev, &vdev_device_list, next) {
 
-		if (devargs->type != RTE_DEVTYPE_VIRTUAL)
+		if (dev->device.driver)
 			continue;
 
-		if (rte_eal_vdev_init(devargs->virt.drv_name,
-				      devargs->args)) {
+		if (vdev_probe_all_drivers(dev)) {
 			RTE_LOG(ERR, EAL, "failed to initialize %s device\n",
-				devargs->virt.drv_name);
+				dev->device.devargs->virt.drv_name);
 			return -1;
 		}
 	}
Signature · 1 line
2.7.4
#28 lore raw

Re: [PATCH 7/7] eal: make virtual bus use rte_vdev_device

Quoted 4 lines · Jan Blunck

This allows the virtual bus to be rescanned and probed by tracking the creation of rte_vdev_device.

<...>

lib/librte_eal/common/eal_common_vdev.c vdev_probe_all_drivers(const char *name, const char *args) · line 177

Quoted 3 lines
lib/librte_eal/common/eal_common_vdev.c +3 -0
+
+	dev->device.devargs = devargs;
+	dev->device.numa_node = -1;

SOCKET_ID_ANY can be used instead of -1

Tested-by on the v1 series
#29 lore raw
In reply to Jan Blunck
Quoted 4 lines · Jan Blunck

With the rte_bus infrastructure present in 17.02 it is possible to refactor the virtual device probing into a bus. This series also introduces the rte_vdev_device to better keep track of devices.

Quoted 8 lines

Jan Blunck (7):
eal: use different constructor priorities for initcalls
eal: probe legacy PCI devices before other bus devices
eal: move virtual device probing into a bus
eal: remove unused rte_eal_dev_init()
eal: Refactor vdev driver probe/remove
eal: add struct rte_vdev_device
eal: make virtual bus use rte_vdev_device

It looks like this patchset depends [1], worth mentioning here.

[1]
http://dpdk.org/dev/patchwork/patch/20416/
http://dpdk.org/dev/patchwork/patch/20417/

Overall, after dependent patches get:

author
#30 lore raw

v2 cover Rework vdev probing to use rte_bus infrastructure

In reply to Jan Blunck

With the rte_bus infrastructure present in 17.02 it is possible to refactor the virtual device probing into a bus. This series also introduces the rte_vdev_device to better keep track of devices.

This patchset depends on:
http://dpdk.org/dev/patchwork/patch/20416/
http://dpdk.org/dev/patchwork/patch/20417/

Changes since version 1:
* addition of rte_vdev_device_name() helper
* removed rte_eal_dev_init() from *.map files
* use SOCKET_ID_ANY

Jan Blunck (8):
eal: use different constructor priorities for initcalls
eal: probe legacy PCI devices before other bus devices
eal: move virtual device probing into a bus
eal: remove unused rte_eal_dev_init()
eal: Refactor vdev driver probe/remove
eal: add struct rte_vdev_device
eal: add virtual device name helper function
eal: make virtual bus use rte_vdev_device

 lib/librte_eal/bsdapp/eal/eal.c                 |   9 +-
 lib/librte_eal/bsdapp/eal/rte_eal_version.map   |   7 +-
 lib/librte_eal/common/eal_common_dev.c          |  28 ---
 lib/librte_eal/common/eal_common_vdev.c         | 252 +++++++++++++++++++++---
 lib/librte_eal/common/include/rte_bus.h         |  17 +-
 lib/librte_eal/common/include/rte_dev.h         |   5 -
 lib/librte_eal/common/include/rte_eal.h         |  12 +-
 lib/librte_eal/common/include/rte_tailq.h       |   2 +-
 lib/librte_eal/common/include/rte_vdev.h        |   7 +
 lib/librte_eal/linuxapp/eal/eal.c               |   9 +-
 lib/librte_eal/linuxapp/eal/rte_eal_version.map |   1 -
 11 files changed, 268 insertions(+), 81 deletions(-)
Signature · 1 line
2.7.4
author
#31 lore raw

PATCH v2 1/8 eal: use different constructor priorities for initcalls

This introduces different initcall macros to allow for late registration of the virtual device bus.

---
 lib/librte_eal/common/include/rte_bus.h   | 17 ++++++++++++++++-
 lib/librte_eal/common/include/rte_eal.h   | 12 ++++++++++--
 lib/librte_eal/common/include/rte_tailq.h |  2 +-
 3 files changed, 27 insertions(+), 4 deletions(-)
lib/librte_eal/common/include/rte_bus.h +16 -1
index 7c36969..9f161f2 100644
@@ -50,6 +50,7 @@ extern "C" {
 #include <stdio.h>
 #include <sys/queue.h>
 
+#include <rte_eal.h>
 #include <rte_log.h>
 #include <rte_dev.h>
 
@@ -145,7 +146,21 @@ void rte_bus_dump(FILE *f);
  * The constructor has higher priority than PMD constructors.
  */
 #define RTE_REGISTER_BUS(nm, bus) \
-static void __attribute__((constructor(101), used)) businitfn_ ##nm(void) \
+RTE_EAL_INIT(businitfn_ ##nm); \
+static void businitfn_ ##nm(void) \
+{\
+	(bus).name = RTE_STR(nm);\
+	rte_bus_register(&bus); \
+}
+
+/**
+ * Helper for late Bus registration.
+ * The constructor still has higher priority than PMD constructors but has
+ * lower priority than RTE_REGISTER_BUS.
+ */
+#define RTE_REGISTER_BUS_LATE(nm, bus) \
+RTE_POST_EAL_INIT(businitfn_ ##nm); \
+static void businitfn_ ##nm(void) \
 {\
 	(bus).name = RTE_STR(nm);\
 	rte_bus_register(&bus); \
lib/librte_eal/common/include/rte_eal.h +10 -2
index 03fee50..3a6bd71 100644
@@ -258,8 +258,16 @@ static inline int rte_gettid(void)
 	return RTE_PER_LCORE(_thread_id);
 }
 
-#define RTE_INIT(func) \
-static void __attribute__((constructor, used)) func(void)
+#define RTE_EAL_INIT(func) \
+static void __attribute__((constructor(101), used)) func(void)
+
+#define RTE_POST_EAL_INIT(func) \
+static void __attribute__((constructor(102), used)) func(void)
+
+#define RTE_DEV_INIT(func) \
+static void __attribute__((constructor(103), used)) func(void)
+
+#define RTE_INIT(func) RTE_DEV_INIT(func)
 
 #ifdef __cplusplus
 }
lib/librte_eal/common/include/rte_tailq.h +1 -1
index 3aae098..07ceec1 100644
@@ -148,7 +148,7 @@ struct rte_tailq_head *rte_eal_tailq_lookup(const char *name);
 int rte_eal_tailq_register(struct rte_tailq_elem *t);
 
 #define EAL_REGISTER_TAILQ(t) \
-RTE_INIT(tailqinitfn_ ##t); \
+RTE_EAL_INIT(tailqinitfn_ ##t); \
 static void tailqinitfn_ ##t(void) \
 { \
 	if (rte_eal_tailq_register(&t) < 0) \
Signature · 1 line
2.7.4
#32 lore raw

Re: [PATCH v2 1/8] eal: use different constructor priorities for initcalls

Quoted 5 lines · Jan Blunck

This introduces different initcall macros to allow for late registration of the virtual device bus.

<...>

lib/librte_eal/common/include/rte_eal.h static inline int rte_gettid(void) · line 270

Quoted 13 lines
lib/librte_eal/common/include/rte_eal.h +10 -2
-#define RTE_INIT(func) \
-static void __attribute__((constructor, used)) func(void)
+#define RTE_EAL_INIT(func) \
+static void __attribute__((constructor(101), used)) func(void)
+
+#define RTE_POST_EAL_INIT(func) \
+static void __attribute__((constructor(102), used)) func(void)
+
+#define RTE_DEV_INIT(func) \
+static void __attribute__((constructor(103), used)) func(void)
+
+#define RTE_INIT(func) RTE_DEV_INIT(func)

Does it make sense to give some gaps among priorities, 101, 102, 103 --> 100, 200 , 300

When new priorities added (not sure if that ever will happen), is changing previous priorities cause a ABI breakage?

author
#33 lore raw

PATCH v2 2/8 eal: probe legacy PCI devices before other bus devices

In reply to Jan Blunck

Make sure that the PCI devices are probed before the virtual devices after the legacy virtual device probing has been moved to a bus.

---
 lib/librte_eal/bsdapp/eal/eal.c   | 8 ++++----
 lib/librte_eal/linuxapp/eal/eal.c | 8 ++++----
 2 files changed, 8 insertions(+), 8 deletions(-)
lib/librte_eal/bsdapp/eal/eal.c +4 -4
index ee7c9de..a584447 100644
@@ -613,14 +613,14 @@ rte_eal_init(int argc, char **argv)
 	rte_eal_mp_remote_launch(sync_func, NULL, SKIP_MASTER);
 	rte_eal_mp_wait_lcore();
 
-	/* Probe all the buses and devices/drivers on them */
-	if (rte_bus_probe())
-		rte_panic("Cannot probe devices\n");
-
 	/* Probe & Initialize PCI devices */
 	if (rte_eal_pci_probe())
 		rte_panic("Cannot probe PCI\n");
 
+	/* Probe all the buses and devices/drivers on them */
+	if (rte_bus_probe())
+		rte_panic("Cannot probe devices\n");
+
 	if (rte_eal_dev_init() < 0)
 		rte_panic("Cannot init pmd devices\n");
 
lib/librte_eal/linuxapp/eal/eal.c +4 -4
index bf6b818..f77ff5c 100644
@@ -884,14 +884,14 @@ rte_eal_init(int argc, char **argv)
 	rte_eal_mp_remote_launch(sync_func, NULL, SKIP_MASTER);
 	rte_eal_mp_wait_lcore();
 
-	/* Probe all the buses and devices/drivers on them */
-	if (rte_bus_probe())
-		rte_panic("Cannot probe devices\n");
-
 	/* Probe & Initialize PCI devices */
 	if (rte_eal_pci_probe())
 		rte_panic("Cannot probe PCI\n");
 
+	/* Probe all the buses and devices/drivers on them */
+	if (rte_bus_probe())
+		rte_panic("Cannot probe devices\n");
+
 	if (rte_eal_dev_init() < 0)
 		rte_panic("Cannot init pmd devices\n");
 
Signature · 1 line
2.7.4
author
#34 lore raw

PATCH v2 3/8 eal: move virtual device probing into a bus

In reply to Jan Blunck

This is a refactoring of the virtual device probing which moves into into a proper bus structure.

---
 lib/librte_eal/common/eal_common_dev.c  | 22 -----------------
 lib/librte_eal/common/eal_common_vdev.c | 44 +++++++++++++++++++++++++++++++++
 2 files changed, 44 insertions(+), 22 deletions(-)
lib/librte_eal/common/eal_common_dev.c +0 -22
index 4f3b493..1ce90f6 100644
@@ -79,28 +79,6 @@ void rte_eal_device_remove(struct rte_device *dev)
 int
 rte_eal_dev_init(void)
 {
-	struct rte_devargs *devargs;
-
-	/*
-	 * Note that the dev_driver_list is populated here
-	 * from calls made to rte_eal_driver_register from constructor functions
-	 * embedded into PMD modules via the RTE_PMD_REGISTER_VDEV macro
-	 */
-
-	/* call the init function for each virtual device */
-	TAILQ_FOREACH(devargs, &devargs_list, next) {
-
-		if (devargs->type != RTE_DEVTYPE_VIRTUAL)
-			continue;
-
-		if (rte_eal_vdev_init(devargs->virt.drv_name,
-					devargs->args)) {
-			RTE_LOG(ERR, EAL, "failed to initialize %s device\n",
-					devargs->virt.drv_name);
-			return -1;
-		}
-	}
-
 	return 0;
 }
 
lib/librte_eal/common/eal_common_vdev.c +44 -0

55 lines not on this page · raw message

Signature · 1 line
2.7.4
author
#35 lore raw

PATCH v2 4/8 eal: remove unused rte_eal_dev_init()

In reply to Jan Blunck
---
 lib/librte_eal/bsdapp/eal/eal.c                 | 3 ---
 lib/librte_eal/bsdapp/eal/rte_eal_version.map   | 1 -
 lib/librte_eal/common/eal_common_dev.c          | 6 ------
 lib/librte_eal/common/include/rte_dev.h         | 5 -----
 lib/librte_eal/linuxapp/eal/eal.c               | 3 ---
 lib/librte_eal/linuxapp/eal/rte_eal_version.map | 1 -
 6 files changed, 19 deletions(-)
lib/librte_eal/bsdapp/eal/eal.c +0 -3
index a584447..3d29fcb 100644
@@ -621,9 +621,6 @@ rte_eal_init(int argc, char **argv)
 	if (rte_bus_probe())
 		rte_panic("Cannot probe devices\n");
 
-	if (rte_eal_dev_init() < 0)
-		rte_panic("Cannot init pmd devices\n");
-
 	rte_eal_mcfg_complete();
 
 	return fctret;
lib/librte_eal/bsdapp/eal/rte_eal_version.map +0 -1
index 2cf1ac8..0116085 100644
@@ -22,7 +22,6 @@ DPDK_2.0 {
 	rte_dump_tailq;
 	rte_eal_alarm_cancel;
 	rte_eal_alarm_set;
-	rte_eal_dev_init;
 	rte_eal_devargs_add;
 	rte_eal_devargs_dump;
 	rte_eal_devargs_type_count;
lib/librte_eal/common/eal_common_dev.c +0 -6
index 1ce90f6..4bde430 100644
@@ -76,12 +76,6 @@ void rte_eal_device_remove(struct rte_device *dev)
 	TAILQ_REMOVE(&dev_device_list, dev, next);
 }
 
-int
-rte_eal_dev_init(void)
-{
-	return 0;
-}
-
 int rte_eal_dev_attach(const char *name, const char *devargs)
 {
 	struct rte_pci_addr addr;
lib/librte_eal/common/include/rte_dev.h +0 -5
index b17791f..4251099 100644
@@ -171,11 +171,6 @@ void rte_eal_driver_register(struct rte_driver *driver);
 void rte_eal_driver_unregister(struct rte_driver *driver);
 
 /**
- * Initalize all the registered drivers in this process
- */
-int rte_eal_dev_init(void);
-
-/**
  * Initialize a driver specified by name.
  *
  * @param name
lib/librte_eal/linuxapp/eal/eal.c +0 -3
index f77ff5c..88479de 100644
@@ -892,9 +892,6 @@ rte_eal_init(int argc, char **argv)
 	if (rte_bus_probe())
 		rte_panic("Cannot probe devices\n");
 
-	if (rte_eal_dev_init() < 0)
-		rte_panic("Cannot init pmd devices\n");
-
 	rte_eal_mcfg_complete();
 
 	return fctret;
lib/librte_eal/linuxapp/eal/rte_eal_version.map +0 -1
index 3c68ff5..41b0cb4 100644
@@ -22,7 +22,6 @@ DPDK_2.0 {
 	rte_dump_tailq;
 	rte_eal_alarm_cancel;
 	rte_eal_alarm_set;
-	rte_eal_dev_init;
 	rte_eal_devargs_add;
 	rte_eal_devargs_dump;
 	rte_eal_devargs_type_count;
Signature · 1 line
2.7.4
author
#36 lore raw

PATCH v2 5/8 eal: Refactor vdev driver probe/remove

In reply to Jan Blunck

This is a preparation for the introduction of the struct rte_vdev_device.

---
 lib/librte_eal/common/eal_common_vdev.c | 44 ++++++++++++++++++++++++---------
 1 file changed, 33 insertions(+), 11 deletions(-)
lib/librte_eal/common/eal_common_vdev.c +33 -11
index 523a3d6..6ba3c91 100644
@@ -61,14 +61,11 @@ rte_eal_vdrv_unregister(struct rte_vdev_driver *driver)
 	TAILQ_REMOVE(&vdev_driver_list, driver, next);
 }
 
-int
-rte_eal_vdev_init(const char *name, const char *args)
+static int
+vdev_probe_all_drivers(const char *name, const char *args)
 {
 	struct rte_vdev_driver *driver;
 
-	if (name == NULL)
-		return -EINVAL;
-
 	TAILQ_FOREACH(driver, &vdev_driver_list, next) {
 		/*
 		 * search a driver prefix in virtual device name.
@@ -89,18 +86,29 @@ rte_eal_vdev_init(const char *name, const char *args)
 			return driver->probe(name, args);
 	}
 
-	RTE_LOG(ERR, EAL, "no driver found for %s\n", name);
-	return -EINVAL;
+	return 1;
 }
 
 int
-rte_eal_vdev_uninit(const char *name)
+rte_eal_vdev_init(const char *name, const char *args)
 {
-	struct rte_vdev_driver *driver;
+	int ret;
 
 	if (name == NULL)
 		return -EINVAL;
 
+	ret = vdev_probe_all_drivers(name, args);
+	if (ret  > 0)
+		RTE_LOG(ERR, EAL, "no driver found for %s\n", name);
+
+	return ret;
+}
+
+static int
+vdev_remove_driver(const char *name)
+{
+	struct rte_vdev_driver *driver;
+
 	TAILQ_FOREACH(driver, &vdev_driver_list, next) {
 		/*
 		 * search a driver prefix in virtual device name.
@@ -121,8 +129,22 @@ rte_eal_vdev_uninit(const char *name)
 			return driver->remove(name);
 	}
 
-	RTE_LOG(ERR, EAL, "no driver found for %s\n", name);
-	return -EINVAL;
+	return 1;
+}
+
+int
+rte_eal_vdev_uninit(const char *name)
+{
+	int ret;
+
+	if (name == NULL)
+		return -EINVAL;
+
+	ret = vdev_remove_driver(name);
+	if (ret > 0)
+		RTE_LOG(ERR, EAL, "no driver found for %s\n", name);
+
+	return ret;
 }
 
 static int
Signature · 1 line
2.7.4
author
#37 lore raw

PATCH v2 6/8 eal: add struct rte_vdev_device

In reply to Jan Blunck

This adds the rte_vdev_device structure which embeds a generic rte_device.

---
 lib/librte_eal/common/eal_common_vdev.c  | 5 +++++
 lib/librte_eal/common/include/rte_vdev.h | 5 +++++
 2 files changed, 10 insertions(+)
lib/librte_eal/common/eal_common_vdev.c +5 -0
index 6ba3c91..61677de 100644
@@ -42,6 +42,11 @@
 #include <rte_common.h>
 #include <rte_devargs.h>
 
+/** Double linked list of virtual device drivers. */
+TAILQ_HEAD(vdev_device_list, rte_vdev_device);
+
+static struct vdev_device_list vdev_device_list =
+	TAILQ_HEAD_INITIALIZER(vdev_device_list);
 struct vdev_driver_list vdev_driver_list =
 	TAILQ_HEAD_INITIALIZER(vdev_driver_list);
 
lib/librte_eal/common/include/rte_vdev.h +5 -0
index 784e837..8f98372 100644
@@ -40,6 +40,11 @@ extern "C" {
 #include <sys/queue.h>
 #include <rte_dev.h>
 
+struct rte_vdev_device {
+	TAILQ_ENTRY(rte_vdev_device) next;      /**< Next attached vdev */
+	struct rte_device device;               /**< Inherit core device */
+};
+
 /** Double linked list of virtual device drivers. */
 TAILQ_HEAD(vdev_driver_list, rte_vdev_driver);
 
Signature · 1 line
2.7.4
author
#38 lore raw

PATCH v2 7/8 eal: add virtual device name helper function

In reply to Jan Blunck

This adds the rte_vdev_device_name() helper function to retrieve the rte_vdev_device name which makes moving the name of the low-level device into struct rte_device easier in the future.

---
 lib/librte_eal/bsdapp/eal/rte_eal_version.map | 6 ++++++
 lib/librte_eal/common/eal_common_vdev.c       | 6 ++++++
 lib/librte_eal/common/include/rte_vdev.h      | 2 ++
 3 files changed, 14 insertions(+)
lib/librte_eal/bsdapp/eal/rte_eal_version.map +6 -0
index 0116085..4afa1c5 100644
@@ -184,3 +184,9 @@ DPDK_17.02 {
 	rte_bus_unregister;
 
 } DPDK_16.11;
+
+DPDK_17.05 {
+	global:
+
+	rte_vdev_device_name;
+} DPDK_17.02;
lib/librte_eal/common/eal_common_vdev.c +6 -0
index 61677de..a9798d0 100644
@@ -66,6 +66,12 @@ rte_eal_vdrv_unregister(struct rte_vdev_driver *driver)
 	TAILQ_REMOVE(&vdev_driver_list, driver, next);
 }
 
+const char *
+rte_vdev_device_name(const struct rte_vdev_device *dev)
+{
+	return dev->device.devargs->virt.drv_name;
+}
+
 static int
 vdev_probe_all_drivers(const char *name, const char *args)
 {
lib/librte_eal/common/include/rte_vdev.h +2 -0
index 8f98372..ffa48bd 100644
@@ -45,6 +45,8 @@ struct rte_vdev_device {
 	struct rte_device device;               /**< Inherit core device */
 };
 
+const char *rte_vdev_device_name(const struct rte_vdev_device *dev);
+
 /** Double linked list of virtual device drivers. */
 TAILQ_HEAD(vdev_driver_list, rte_vdev_driver);
 
Signature · 1 line
2.7.4
#39 lore raw

Re: [PATCH v2 7/8] eal: add virtual device name helper function

Quoted 5 lines · Jan Blunck

This adds the rte_vdev_device_name() helper function to retrieve the rte_vdev_device name which makes moving the name of the low-level device into struct rte_device easier in the future.

<...>

lib/librte_eal/common/eal_common_vdev.c rte_eal_vdrv_unregister(struct rte_vdev_driver *driver) · line 73

Quoted 5 lines
lib/librte_eal/common/eal_common_vdev.c +5 -0
+const char *
+rte_vdev_device_name(const struct rte_vdev_device *dev)
+{
+	return dev->device.devargs->virt.drv_name;
+}

Can this function be static?

author
#40 lore raw

PATCH v2 8/8 eal: make virtual bus use rte_vdev_device

In reply to Jan Blunck

This allows the virtual bus to be rescanned and probed by tracking the creation of rte_vdev_device.

---
 lib/librte_eal/common/eal_common_vdev.c | 195 +++++++++++++++++++++++++-------
 1 file changed, 155 insertions(+), 40 deletions(-)
lib/librte_eal/common/eal_common_vdev.c +155 -40
index a9798d0..531c61b 100644
@@ -41,6 +41,7 @@
 #include <rte_vdev.h>
 #include <rte_common.h>
 #include <rte_devargs.h>
+#include <rte_memory.h>
 
 /** Double linked list of virtual device drivers. */
 TAILQ_HEAD(vdev_device_list, rte_vdev_device);
@@ -73,9 +74,12 @@ rte_vdev_device_name(const struct rte_vdev_device *dev)
 }
 
 static int
-vdev_probe_all_drivers(const char *name, const char *args)
+vdev_probe_all_drivers(struct rte_vdev_device *dev)
 {
+	const char *name = rte_vdev_device_name(dev);
+	char *args = dev->device.devargs->args;
 	struct rte_vdev_driver *driver;
+	int ret;
 
 	TAILQ_FOREACH(driver, &vdev_driver_list, next) {
 		/*
@@ -85,90 +89,202 @@ vdev_probe_all_drivers(const char *name, const char *args)
 		 * So use strncmp to compare.
 		 */
 		if (!strncmp(driver->driver.name, name,
-			    strlen(driver->driver.name)))
-			return driver->probe(name, args);
+			    strlen(driver->driver.name))) {
+			dev->device.driver = &driver->driver;
+			ret = driver->probe(name, args);
+			if (ret)
+				dev->device.driver = NULL;
+			return ret;
+		}
 	}
 
 	/* Give new names precedence over aliases. */
 	TAILQ_FOREACH(driver, &vdev_driver_list, next) {
 		if (driver->driver.alias &&
 		    !strncmp(driver->driver.alias, name,
-			    strlen(driver->driver.alias)))
-			return driver->probe(name, args);
+			    strlen(driver->driver.alias))) {
+			dev->device.driver = &driver->driver;
+			ret = driver->probe(name, args);
+			if (ret)
+				dev->device.driver = NULL;
+			return ret;
+		}
 	}
 
 	return 1;
 }
 
+static struct rte_vdev_device *
+find_vdev(const char *name)
+{
+	struct rte_vdev_device *dev;
+
+	if (!name)
+		return NULL;
+
+	TAILQ_FOREACH(dev, &vdev_device_list, next) {
+		const char *devname = rte_vdev_device_name(dev);
+		if (!strncmp(devname, name, strlen(name)))
+			return dev;
+	}
+
+	return NULL;
+}
+
+static struct rte_devargs *
+alloc_devargs(const char *name, const char *args)
+{
+	struct rte_devargs *devargs;
+	int ret;
+
+	devargs = calloc(1, sizeof(*devargs));
+	if (!devargs)
+		return NULL;
+
+	devargs->type = RTE_DEVTYPE_VIRTUAL;
+	if (args)
+		devargs->args = strdup(args);
+
+	ret = snprintf(devargs->virt.drv_name,
+			       sizeof(devargs->virt.drv_name), "%s", name);
+	if (ret < 0 || ret >= (int)sizeof(devargs->virt.drv_name)) {
+		free(devargs->args);
+		free(devargs);
+		return NULL;
+	}
+
+	return devargs;
+}
+
 int
 rte_eal_vdev_init(const char *name, const char *args)
 {
+	struct rte_vdev_device *dev;
+	struct rte_devargs *devargs;
 	int ret;
 
 	if (name == NULL)
 		return -EINVAL;
 
-	ret = vdev_probe_all_drivers(name, args);
-	if (ret  > 0)
-		RTE_LOG(ERR, EAL, "no driver found for %s\n", name);
+	dev = find_vdev(name);
+	if (dev)
+		return -EEXIST;
+
+	devargs = alloc_devargs(name, args);
+	if (!devargs)
+		return -ENOMEM;
+
+	dev = calloc(1, sizeof(*dev));
+	if (!dev) {
+		ret = -ENOMEM;
+		goto fail;
+	}
+
+	dev->device.devargs = devargs;
+	dev->device.numa_node = SOCKET_ID_ANY;
+
+	ret = vdev_probe_all_drivers(dev);
+	if (ret) {
+		if (ret > 0)
+			RTE_LOG(ERR, EAL, "no driver found for %s\n", name);
+		goto fail;
+	}
+
+	TAILQ_INSERT_TAIL(&devargs_list, devargs, next);
+
+	rte_eal_device_insert(&dev->device);
+	TAILQ_INSERT_TAIL(&vdev_device_list, dev, next);
+	return 0;
 
+fail:
+	free(devargs->args);
+	free(devargs);
+	free(dev);
 	return ret;
 }
 
 static int
-vdev_remove_driver(const char *name)
+vdev_remove_driver(struct rte_vdev_device *dev)
 {
-	struct rte_vdev_driver *driver;
+	const char *name = rte_vdev_device_name(dev);
+	const struct rte_vdev_driver *driver;
 
-	TAILQ_FOREACH(driver, &vdev_driver_list, next) {
-		/*
-		 * search a driver prefix in virtual device name.
-		 * For example, if the driver is pcap PMD, driver->name
-		 * will be "net_pcap", but "name" will be "net_pcapN".
-		 * So use strncmp to compare.
-		 */
-		if (!strncmp(driver->driver.name, name,
-			     strlen(driver->driver.name)))
-			return driver->remove(name);
-	}
-
-	/* Give new names precedence over aliases. */
-	TAILQ_FOREACH(driver, &vdev_driver_list, next) {
-		if (driver->driver.alias &&
-		    !strncmp(driver->driver.alias, name,
-			    strlen(driver->driver.alias)))
-			return driver->remove(name);
+	if (!dev->device.driver) {
+		RTE_LOG(DEBUG, EAL, "no driver attach to device %s\n", name);
+		return 1;
 	}
 
-	return 1;
+	driver = container_of(dev->device.driver, const struct rte_vdev_driver,
+		driver);
+	return driver->remove(name);
 }
 
 int
 rte_eal_vdev_uninit(const char *name)
 {
+	struct rte_vdev_device *dev;
+	struct rte_devargs *devargs;
 	int ret;
 
 	if (name == NULL)
 		return -EINVAL;
 
-	ret = vdev_remove_driver(name);
-	if (ret > 0)
-		RTE_LOG(ERR, EAL, "no driver found for %s\n", name);
+	dev = find_vdev(name);
+	if (!dev)
+		return -ENOENT;
 
-	return ret;
+	devargs = dev->device.devargs;
+
+	ret = vdev_remove_driver(dev);
+	if (ret)
+		return ret;
+
+	TAILQ_REMOVE(&vdev_device_list, dev, next);
+	rte_eal_device_remove(&dev->device);
+
+	TAILQ_REMOVE(&devargs_list, devargs, next);
+
+	free(devargs->args);
+	free(devargs);
+	free(dev);
+	return 0;
 }
 
 static int
 vdev_scan(void)
 {
-	/* for virtual devices we don't need to scan anything */
+	struct rte_vdev_device *dev;
+	struct rte_devargs *devargs;
+
+	/* for virtual devices we scan the devargs_list populated via cmdline */
+
+	TAILQ_FOREACH(devargs, &devargs_list, next) {
+
+		if (devargs->type != RTE_DEVTYPE_VIRTUAL)
+			continue;
+
+		dev = find_vdev(devargs->virt.drv_name);
+		if (dev)
+			continue;
+
+		dev = calloc(1, sizeof(*dev));
+		if (!dev)
+			return -1;
+
+		dev->device.devargs = devargs;
+		dev->device.numa_node = SOCKET_ID_ANY;
+
+		rte_eal_device_insert(&dev->device);
+		TAILQ_INSERT_TAIL(&vdev_device_list, dev, next);
+	}
+
 	return 0;
 }
 
 static int
 vdev_probe(void)
 {
-	struct rte_devargs *devargs;
+	struct rte_vdev_device *dev;
 
 	/*
 	 * Note that the dev_driver_list is populated here
@@ -177,15 +293,14 @@ vdev_probe(void)
 	 */
 
 	/* call the init function for each virtual device */
-	TAILQ_FOREACH(devargs, &devargs_list, next) {
+	TAILQ_FOREACH(dev, &vdev_device_list, next) {
 
-		if (devargs->type != RTE_DEVTYPE_VIRTUAL)
+		if (dev->device.driver)
 			continue;
 
-		if (rte_eal_vdev_init(devargs->virt.drv_name,
-				      devargs->args)) {
+		if (vdev_probe_all_drivers(dev)) {
 			RTE_LOG(ERR, EAL, "failed to initialize %s device\n",
-				devargs->virt.drv_name);
+				rte_vdev_device_name(dev));
 			return -1;
 		}
 	}
Signature · 1 line
2.7.4
#41 lore raw
In reply to Jan Blunck
Quoted 4 lines · Jan Blunck

With the rte_bus infrastructure present in 17.02 it is possible to refactor the virtual device probing into a bus. This series also introduces the rte_vdev_device to better keep track of devices.

Quoted 9 lines

This patchset depends on:
http://dpdk.org/dev/patchwork/patch/20416/
http://dpdk.org/dev/patchwork/patch/20417/

Changes since version 1:
* addition of rte_vdev_device_name() helper
* removed rte_eal_dev_init() from *.map files
* use SOCKET_ID_ANY

Series Acked-by: Shreyansh Jain <[email protected]>

author
#42 lore raw

v3 cover Rework vdev probing to use rte_bus infrastructure

In reply to Jan Blunck

With the rte_bus infrastructure present in 17.02 it is possible to refactor the virtual device probing into a bus. This series also introduces the rte_vdev_device to better keep track of devices.

This patchset depends on:
http://dpdk.org/dev/patchwork/patch/20416/
http://dpdk.org/dev/patchwork/patch/20417/

Changes since version 2:
* implicit bus registration through rte_eal_vdrv_register()
* explicit delay probing of virtual bus in rte_bus_probe()
* addition of rte_vdev_device_args() helper
* make virtual driver probe and remove take rte_vdev_device

Changes since version 1:
* addition of rte_vdev_device_name() helper
* removed rte_eal_dev_init() from *.map files
* use SOCKET_ID_ANY

Jan Blunck (10):
eal: probe legacy PCI devices before other bus devices
eal: probe new virtual bus after other bus devices
eal: move virtual device probing into a bus
eal: remove unused rte_eal_dev_init()
eal: Refactor vdev driver probe/remove
eal: add struct rte_vdev_device
eal: add virtual device name helper function
eal: add virtual device arguments helper function
eal: make virtual bus use rte_vdev_device
eal: make virtual driver probe and remove take rte_vdev_device

 drivers/crypto/null/null_crypto_pmd.c           |  18 +-
 drivers/net/af_packet/rte_eth_af_packet.c       |  11 +-
 drivers/net/bonding/rte_eth_bond_pmd.c          |  13 +-
 drivers/net/mpipe/mpipe_tilegx.c                |  10 +-
 drivers/net/null/rte_eth_null.c                 |  13 +-
 drivers/net/pcap/rte_eth_pcap.c                 |  12 +-
 drivers/net/ring/rte_eth_ring.c                 |   9 +-
 drivers/net/tap/rte_eth_tap.c                   |  10 +-
 drivers/net/vhost/rte_eth_vhost.c               |  10 +-
 drivers/net/virtio/virtio_user_ethdev.c         |  18 +-
 drivers/net/xenvirt/rte_eth_xenvirt.c           |   9 +-
 lib/librte_eal/bsdapp/eal/eal.c                 |   9 +-
 lib/librte_eal/bsdapp/eal/rte_eal_version.map   |   1 -
 lib/librte_eal/common/eal_common_bus.c          |  16 +-
 lib/librte_eal/common/eal_common_dev.c          |  28 ---
 lib/librte_eal/common/eal_common_vdev.c         | 259 +++++++++++++++++++++---
 lib/librte_eal/common/include/rte_dev.h         |   5 -
 lib/librte_eal/common/include/rte_vdev.h        |  26 ++-
 lib/librte_eal/linuxapp/eal/eal.c               |   9 +-
 lib/librte_eal/linuxapp/eal/rte_eal_version.map |   1 -
 20 files changed, 355 insertions(+), 132 deletions(-)
Signature · 1 line
2.7.4
author
#43 lore raw

PATCH v3 1/10 eal: probe legacy PCI devices before other bus devices

Make sure that the PCI devices are probed before the virtual devices after the legacy virtual device probing has been moved to a bus.

---
 lib/librte_eal/bsdapp/eal/eal.c   | 8 ++++----
 lib/librte_eal/linuxapp/eal/eal.c | 8 ++++----
 2 files changed, 8 insertions(+), 8 deletions(-)
lib/librte_eal/bsdapp/eal/eal.c +4 -4
index ee7c9de..a584447 100644
@@ -613,14 +613,14 @@ rte_eal_init(int argc, char **argv)
 	rte_eal_mp_remote_launch(sync_func, NULL, SKIP_MASTER);
 	rte_eal_mp_wait_lcore();
 
-	/* Probe all the buses and devices/drivers on them */
-	if (rte_bus_probe())
-		rte_panic("Cannot probe devices\n");
-
 	/* Probe & Initialize PCI devices */
 	if (rte_eal_pci_probe())
 		rte_panic("Cannot probe PCI\n");
 
+	/* Probe all the buses and devices/drivers on them */
+	if (rte_bus_probe())
+		rte_panic("Cannot probe devices\n");
+
 	if (rte_eal_dev_init() < 0)
 		rte_panic("Cannot init pmd devices\n");
 
lib/librte_eal/linuxapp/eal/eal.c +4 -4
index bf6b818..f77ff5c 100644
@@ -884,14 +884,14 @@ rte_eal_init(int argc, char **argv)
 	rte_eal_mp_remote_launch(sync_func, NULL, SKIP_MASTER);
 	rte_eal_mp_wait_lcore();
 
-	/* Probe all the buses and devices/drivers on them */
-	if (rte_bus_probe())
-		rte_panic("Cannot probe devices\n");
-
 	/* Probe & Initialize PCI devices */
 	if (rte_eal_pci_probe())
 		rte_panic("Cannot probe PCI\n");
 
+	/* Probe all the buses and devices/drivers on them */
+	if (rte_bus_probe())
+		rte_panic("Cannot probe devices\n");
+
 	if (rte_eal_dev_init() < 0)
 		rte_panic("Cannot init pmd devices\n");
 
Signature · 1 line
2.7.4
author
#44 lore raw

PATCH v3 2/10 eal: probe new virtual bus after other bus devices

In reply to Jan Blunck

Also see commit f4ce209a ("eal: postpone vdev initialization").

---
 lib/librte_eal/common/eal_common_bus.c | 16 +++++++++++++++-
 1 file changed, 15 insertions(+), 1 deletion(-)
lib/librte_eal/common/eal_common_bus.c +15 -1
index 4638e78..8f9baf8 100644
@@ -86,9 +86,14 @@ int
 rte_bus_probe(void)
 {
 	int ret;
-	struct rte_bus *bus;
+	struct rte_bus *bus, *vbus = NULL;
 
 	TAILQ_FOREACH(bus, &rte_bus_list, next) {
+		if (!strcmp(bus->name, "virtual")) {
+			vbus = bus;
+			continue;
+		}
+
 		ret = bus->probe();
 		if (ret) {
 			RTE_LOG(ERR, EAL, "Bus (%s) probe failed.\n",
@@ -97,6 +102,15 @@ rte_bus_probe(void)
 		}
 	}
 
+	if (vbus) {
+		ret = vbus->probe();
+		if (ret) {
+			RTE_LOG(ERR, EAL, "Bus (%s) probe failed.\n",
+				vbus->name);
+			return ret;
+		}
+	}
+
 	return 0;
 }
 
Signature · 1 line
2.7.4
#45 lore raw

Re: [PATCH v3 02/10] eal: probe new virtual bus after other bus devices

Quoted 30 lines · Jan Blunck

Also see commit f4ce209a ("eal: postpone vdev initialization").

---
 lib/librte_eal/common/eal_common_bus.c | 16 +++++++++++++++-
 1 file changed, 15 insertions(+), 1 deletion(-)
lib/librte_eal/common/eal_common_bus.c +6 -1
index 4638e78..8f9baf8 100644
@@ -86,9 +86,14 @@ int
 rte_bus_probe(void)
 {
 	int ret;
-	struct rte_bus *bus;
+	struct rte_bus *bus, *vbus = NULL;
 
 	TAILQ_FOREACH(bus, &rte_bus_list, next) {
+		if (!strcmp(bus->name, "virtual")) {
+			vbus = bus;
+			continue;
+		}
+
 		ret = bus->probe();
 		if (ret) {
 			RTE_LOG(ERR, EAL, "Bus (%s) probe failed.\n",
@@ -97,6 +102,15 @@ rte_bus_probe(void)
 		}
 	}

lib/librte_eal/common/eal_common_bus.c rte_bus_probe(void) · line 113

Quoted 10 lines
lib/librte_eal/common/eal_common_bus.c +9 -0
 
+	if (vbus) {
+		ret = vbus->probe();
+		if (ret) {
+			RTE_LOG(ERR, EAL, "Bus (%s) probe failed.\n",
+				vbus->name);
+			return ret;
+		}
+	}
+

This has probably changed to do away with priority of RTE_REGISTER_* macro.

This is based on an assumption that there is only a single 'virtual' bus and no driver ever registers another bus with the same name.

The problem originates from the fact that rte_bus_register is _not_ checking for duplicate entries while registering. (Apparently, it would be a problem in case of RTE_* macros as well).

I think that should be fixed.

If we are in sync, I will push a patch.

Quoted 4 lines
lib/librte_eal/common/eal_common_bus.c +0 -0
 	return 0;
 }
 
author
#46 lore raw

Re: [PATCH v3 02/10] eal: probe new virtual bus after other bus devices

Quoted 51 lines · Shreyansh Jain
Quoted 32 lines · Jan Blunck

Also see commit f4ce209a ("eal: postpone vdev initialization").

---
 lib/librte_eal/common/eal_common_bus.c | 16 +++++++++++++++-
 1 file changed, 15 insertions(+), 1 deletion(-)
lib/librte_eal/common/eal_common_bus.c +6 -1
index 4638e78..8f9baf8 100644
@@ -86,9 +86,14 @@ int
 rte_bus_probe(void)
 {
        int ret;
-       struct rte_bus *bus;
+       struct rte_bus *bus, *vbus = NULL;
 
        TAILQ_FOREACH(bus, &rte_bus_list, next) {
+               if (!strcmp(bus->name, "virtual")) {
+                       vbus = bus;
+                       continue;
+               }
+
                ret = bus->probe();
                if (ret) {
                        RTE_LOG(ERR, EAL, "Bus (%s) probe failed.\n",
@@ -97,6 +102,15 @@ rte_bus_probe(void)
                }
        }

lib/librte_eal/common/eal_common_bus.c rte_bus_probe(void) · line 113

Quoted 10 lines
lib/librte_eal/common/eal_common_bus.c +9 -0
 
+       if (vbus) {
+               ret = vbus->probe();
+               if (ret) {
+                       RTE_LOG(ERR, EAL, "Bus (%s) probe failed.\n",
+                               vbus->name);
+                       return ret;
+               }
+       }
+

This has probably changed to do away with priority of RTE_REGISTER_* macro.

This is based on an assumption that there is only a single 'virtual' bus and no driver ever registers another bus with the same name.

Quoted 8 lines

The problem originates from the fact that rte_bus_register is _not_ checking for duplicate entries while registering. (Apparently, it would be a problem in case of RTE_* macros as well).

I think that should be fixed.

If we are in sync, I will push a patch.

Indeed. The buses should have a unique name.

author
#47 lore raw

PATCH v3 3/10 eal: move virtual device probing into a bus

In reply to Jan Blunck

This is a refactoring of the virtual device probing which moves into into a proper bus structure.

---
 lib/librte_eal/common/eal_common_dev.c  | 22 -------------
 lib/librte_eal/common/eal_common_vdev.c | 58 +++++++++++++++++++++++++++++++++
 2 files changed, 58 insertions(+), 22 deletions(-)
lib/librte_eal/common/eal_common_dev.c +0 -22
index 4f3b493..1ce90f6 100644
@@ -79,28 +79,6 @@ void rte_eal_device_remove(struct rte_device *dev)
 int
 rte_eal_dev_init(void)
 {
-	struct rte_devargs *devargs;
-
-	/*
-	 * Note that the dev_driver_list is populated here
-	 * from calls made to rte_eal_driver_register from constructor functions
-	 * embedded into PMD modules via the RTE_PMD_REGISTER_VDEV macro
-	 */
-
-	/* call the init function for each virtual device */
-	TAILQ_FOREACH(devargs, &devargs_list, next) {
-
-		if (devargs->type != RTE_DEVTYPE_VIRTUAL)
-			continue;
-
-		if (rte_eal_vdev_init(devargs->virt.drv_name,
-					devargs->args)) {
-			RTE_LOG(ERR, EAL, "failed to initialize %s device\n",
-					devargs->virt.drv_name);
-			return -1;
-		}
-	}
-
 	return 0;
 }
 
lib/librte_eal/common/eal_common_vdev.c +58 -0

77 lines not on this page · raw message

Signature · 1 line
2.7.4
author
#48 lore raw

PATCH v3 4/10 eal: remove unused rte_eal_dev_init()

In reply to Jan Blunck
---
 lib/librte_eal/bsdapp/eal/eal.c                 | 3 ---
 lib/librte_eal/bsdapp/eal/rte_eal_version.map   | 1 -
 lib/librte_eal/common/eal_common_dev.c          | 6 ------
 lib/librte_eal/common/include/rte_dev.h         | 5 -----
 lib/librte_eal/linuxapp/eal/eal.c               | 3 ---
 lib/librte_eal/linuxapp/eal/rte_eal_version.map | 1 -
 6 files changed, 19 deletions(-)
lib/librte_eal/bsdapp/eal/eal.c +0 -3
index a584447..3d29fcb 100644
@@ -621,9 +621,6 @@ rte_eal_init(int argc, char **argv)
 	if (rte_bus_probe())
 		rte_panic("Cannot probe devices\n");
 
-	if (rte_eal_dev_init() < 0)
-		rte_panic("Cannot init pmd devices\n");
-
 	rte_eal_mcfg_complete();
 
 	return fctret;
lib/librte_eal/bsdapp/eal/rte_eal_version.map +0 -1
index 67f2ffb..b1996e0 100644
@@ -22,7 +22,6 @@ DPDK_2.0 {
 	rte_dump_tailq;
 	rte_eal_alarm_cancel;
 	rte_eal_alarm_set;
-	rte_eal_dev_init;
 	rte_eal_devargs_add;
 	rte_eal_devargs_dump;
 	rte_eal_devargs_type_count;
lib/librte_eal/common/eal_common_dev.c +0 -6
index 1ce90f6..4bde430 100644
@@ -76,12 +76,6 @@ void rte_eal_device_remove(struct rte_device *dev)
 	TAILQ_REMOVE(&dev_device_list, dev, next);
 }
 
-int
-rte_eal_dev_init(void)
-{
-	return 0;
-}
-
 int rte_eal_dev_attach(const char *name, const char *devargs)
 {
 	struct rte_pci_addr addr;
lib/librte_eal/common/include/rte_dev.h +0 -5
index b17791f..4251099 100644
@@ -171,11 +171,6 @@ void rte_eal_driver_register(struct rte_driver *driver);
 void rte_eal_driver_unregister(struct rte_driver *driver);
 
 /**
- * Initalize all the registered drivers in this process
- */
-int rte_eal_dev_init(void);
-
-/**
  * Initialize a driver specified by name.
  *
  * @param name
lib/librte_eal/linuxapp/eal/eal.c +0 -3
index f77ff5c..88479de 100644
@@ -892,9 +892,6 @@ rte_eal_init(int argc, char **argv)
 	if (rte_bus_probe())
 		rte_panic("Cannot probe devices\n");
 
-	if (rte_eal_dev_init() < 0)
-		rte_panic("Cannot init pmd devices\n");
-
 	rte_eal_mcfg_complete();
 
 	return fctret;
lib/librte_eal/linuxapp/eal/rte_eal_version.map +0 -1
index 9c134b4..2ada2f0 100644
@@ -22,7 +22,6 @@ DPDK_2.0 {
 	rte_dump_tailq;
 	rte_eal_alarm_cancel;
 	rte_eal_alarm_set;
-	rte_eal_dev_init;
 	rte_eal_devargs_add;
 	rte_eal_devargs_dump;
 	rte_eal_devargs_type_count;
Signature · 1 line
2.7.4
author
#49 lore raw

PATCH v3 5/10 eal: Refactor vdev driver probe/remove

In reply to Jan Blunck

This is a preparation for the introduction of the struct rte_vdev_device.

---
 lib/librte_eal/common/eal_common_vdev.c | 44 ++++++++++++++++++++++++---------
 1 file changed, 33 insertions(+), 11 deletions(-)
lib/librte_eal/common/eal_common_vdev.c +33 -11
index 0fcfdd7..5a267ee 100644
@@ -65,14 +65,11 @@ rte_eal_vdrv_unregister(struct rte_vdev_driver *driver)
 	TAILQ_REMOVE(&vdev_driver_list, driver, next);
 }
 
-int
-rte_eal_vdev_init(const char *name, const char *args)
+static int
+vdev_probe_all_drivers(const char *name, const char *args)
 {
 	struct rte_vdev_driver *driver;
 
-	if (name == NULL)
-		return -EINVAL;
-
 	TAILQ_FOREACH(driver, &vdev_driver_list, next) {
 		/*
 		 * search a driver prefix in virtual device name.
@@ -93,18 +90,29 @@ rte_eal_vdev_init(const char *name, const char *args)
 			return driver->probe(name, args);
 	}
 
-	RTE_LOG(ERR, EAL, "no driver found for %s\n", name);
-	return -EINVAL;
+	return 1;
 }
 
 int
-rte_eal_vdev_uninit(const char *name)
+rte_eal_vdev_init(const char *name, const char *args)
 {
-	struct rte_vdev_driver *driver;
+	int ret;
 
 	if (name == NULL)
 		return -EINVAL;
 
+	ret = vdev_probe_all_drivers(name, args);
+	if (ret  > 0)
+		RTE_LOG(ERR, EAL, "no driver found for %s\n", name);
+
+	return ret;
+}
+
+static int
+vdev_remove_driver(const char *name)
+{
+	struct rte_vdev_driver *driver;
+
 	TAILQ_FOREACH(driver, &vdev_driver_list, next) {
 		/*
 		 * search a driver prefix in virtual device name.
@@ -125,8 +133,22 @@ rte_eal_vdev_uninit(const char *name)
 			return driver->remove(name);
 	}
 
-	RTE_LOG(ERR, EAL, "no driver found for %s\n", name);
-	return -EINVAL;
+	return 1;
+}
+
+int
+rte_eal_vdev_uninit(const char *name)
+{
+	int ret;
+
+	if (name == NULL)
+		return -EINVAL;
+
+	ret = vdev_remove_driver(name);
+	if (ret > 0)
+		RTE_LOG(ERR, EAL, "no driver found for %s\n", name);
+
+	return ret;
 }
 
 static int
Signature · 1 line
2.7.4
author
#50 lore raw

PATCH v3 6/10 eal: add struct rte_vdev_device

In reply to Jan Blunck

This adds the rte_vdev_device structure which embeds a generic rte_device.

---
 lib/librte_eal/common/eal_common_vdev.c  | 5 +++++
 lib/librte_eal/common/include/rte_vdev.h | 5 +++++
 2 files changed, 10 insertions(+)
lib/librte_eal/common/eal_common_vdev.c +5 -0
index 5a267ee..c88cae9 100644
@@ -42,6 +42,11 @@
 #include <rte_common.h>
 #include <rte_devargs.h>
 
+/** Double linked list of virtual device drivers. */
+TAILQ_HEAD(vdev_device_list, rte_vdev_device);
+
+static struct vdev_device_list vdev_device_list =
+	TAILQ_HEAD_INITIALIZER(vdev_device_list);
 struct vdev_driver_list vdev_driver_list =
 	TAILQ_HEAD_INITIALIZER(vdev_driver_list);
 
lib/librte_eal/common/include/rte_vdev.h +5 -0
index 784e837..8f98372 100644
@@ -40,6 +40,11 @@ extern "C" {
 #include <sys/queue.h>
 #include <rte_dev.h>
 
+struct rte_vdev_device {
+	TAILQ_ENTRY(rte_vdev_device) next;      /**< Next attached vdev */
+	struct rte_device device;               /**< Inherit core device */
+};
+
 /** Double linked list of virtual device drivers. */
 TAILQ_HEAD(vdev_driver_list, rte_vdev_driver);
 
Signature · 1 line
2.7.4
author
#51 lore raw

PATCH v3 7/10 eal: add virtual device name helper function

In reply to Jan Blunck

This adds the rte_vdev_device_name() helper function to retrieve the rte_vdev_device name which makes moving the name of the low-level device into struct rte_device easier in the future.

---
 lib/librte_eal/common/include/rte_vdev.h | 9 +++++++++
 1 file changed, 9 insertions(+)
lib/librte_eal/common/include/rte_vdev.h +9 -0
index 8f98372..abdefab 100644
@@ -39,12 +39,21 @@ extern "C" {
 
 #include <sys/queue.h>
 #include <rte_dev.h>
+#include <rte_devargs.h>
 
 struct rte_vdev_device {
 	TAILQ_ENTRY(rte_vdev_device) next;      /**< Next attached vdev */
 	struct rte_device device;               /**< Inherit core device */
 };
 
+static inline const char *
+rte_vdev_device_name(const struct rte_vdev_device *dev)
+{
+	if (dev && dev->device.devargs)
+		return dev->device.devargs->virt.drv_name;
+	return NULL;
+}
+
 /** Double linked list of virtual device drivers. */
 TAILQ_HEAD(vdev_driver_list, rte_vdev_driver);
 
Signature · 1 line
2.7.4
author
#52 lore raw

PATCH v3 8/10 eal: add virtual device arguments helper function

In reply to Jan Blunck

This adds the rte_vdev_device_args() helper function to prepare for changing the virtual drivers probe() functions take a rte_vdev_device pointer instead of the name+args strings.

---
 lib/librte_eal/common/include/rte_vdev.h | 8 ++++++++
 1 file changed, 8 insertions(+)
lib/librte_eal/common/include/rte_vdev.h +8 -0
index abdefab..81f6beb 100644
@@ -54,6 +54,14 @@ rte_vdev_device_name(const struct rte_vdev_device *dev)
 	return NULL;
 }
 
+static inline const char *
+rte_vdev_device_args(const struct rte_vdev_device *dev)
+{
+	if (dev && dev->device.devargs)
+		return dev->device.devargs->args;
+	return "";
+}
+
 /** Double linked list of virtual device drivers. */
 TAILQ_HEAD(vdev_driver_list, rte_vdev_driver);
 
Signature · 1 line
2.7.4
author
#53 lore raw

PATCH v3 9/10 eal: make virtual bus use rte_vdev_device

In reply to Jan Blunck

This allows the virtual bus to be rescanned and probed by tracking the creation of rte_vdev_device.

---
 lib/librte_eal/common/eal_common_vdev.c | 195 +++++++++++++++++++++++++-------
 1 file changed, 155 insertions(+), 40 deletions(-)
lib/librte_eal/common/eal_common_vdev.c +155 -40
index c88cae9..7215b50 100644
@@ -41,6 +41,7 @@
 #include <rte_vdev.h>
 #include <rte_common.h>
 #include <rte_devargs.h>
+#include <rte_memory.h>
 
 /** Double linked list of virtual device drivers. */
 TAILQ_HEAD(vdev_device_list, rte_vdev_device);
@@ -71,9 +72,12 @@ rte_eal_vdrv_unregister(struct rte_vdev_driver *driver)
 }
 
 static int
-vdev_probe_all_drivers(const char *name, const char *args)
+vdev_probe_all_drivers(struct rte_vdev_device *dev)
 {
+	const char *name = rte_vdev_device_name(dev);
+	const char *args = rte_vdev_device_args(dev);
 	struct rte_vdev_driver *driver;
+	int ret;
 
 	TAILQ_FOREACH(driver, &vdev_driver_list, next) {
 		/*
@@ -83,90 +87,202 @@ vdev_probe_all_drivers(const char *name, const char *args)
 		 * So use strncmp to compare.
 		 */
 		if (!strncmp(driver->driver.name, name,
-			    strlen(driver->driver.name)))
-			return driver->probe(name, args);
+			    strlen(driver->driver.name))) {
+			dev->device.driver = &driver->driver;
+			ret = driver->probe(name, args);
+			if (ret)
+				dev->device.driver = NULL;
+			return ret;
+		}
 	}
 
 	/* Give new names precedence over aliases. */
 	TAILQ_FOREACH(driver, &vdev_driver_list, next) {
 		if (driver->driver.alias &&
 		    !strncmp(driver->driver.alias, name,
-			    strlen(driver->driver.alias)))
-			return driver->probe(name, args);
+			    strlen(driver->driver.alias))) {
+			dev->device.driver = &driver->driver;
+			ret = driver->probe(name, args);
+			if (ret)
+				dev->device.driver = NULL;
+			return ret;
+		}
 	}
 
 	return 1;
 }
 
+static struct rte_vdev_device *
+find_vdev(const char *name)
+{
+	struct rte_vdev_device *dev;
+
+	if (!name)
+		return NULL;
+
+	TAILQ_FOREACH(dev, &vdev_device_list, next) {
+		const char *devname = rte_vdev_device_name(dev);
+		if (!strncmp(devname, name, strlen(name)))
+			return dev;
+	}
+
+	return NULL;
+}
+
+static struct rte_devargs *
+alloc_devargs(const char *name, const char *args)
+{
+	struct rte_devargs *devargs;
+	int ret;
+
+	devargs = calloc(1, sizeof(*devargs));
+	if (!devargs)
+		return NULL;
+
+	devargs->type = RTE_DEVTYPE_VIRTUAL;
+	if (args)
+		devargs->args = strdup(args);
+
+	ret = snprintf(devargs->virt.drv_name,
+			       sizeof(devargs->virt.drv_name), "%s", name);
+	if (ret < 0 || ret >= (int)sizeof(devargs->virt.drv_name)) {
+		free(devargs->args);
+		free(devargs);
+		return NULL;
+	}
+
+	return devargs;
+}
+
 int
 rte_eal_vdev_init(const char *name, const char *args)
 {
+	struct rte_vdev_device *dev;
+	struct rte_devargs *devargs;
 	int ret;
 
 	if (name == NULL)
 		return -EINVAL;
 
-	ret = vdev_probe_all_drivers(name, args);
-	if (ret  > 0)
-		RTE_LOG(ERR, EAL, "no driver found for %s\n", name);
+	dev = find_vdev(name);
+	if (dev)
+		return -EEXIST;
+
+	devargs = alloc_devargs(name, args);
+	if (!devargs)
+		return -ENOMEM;
+
+	dev = calloc(1, sizeof(*dev));
+	if (!dev) {
+		ret = -ENOMEM;
+		goto fail;
+	}
+
+	dev->device.devargs = devargs;
+	dev->device.numa_node = SOCKET_ID_ANY;
+
+	ret = vdev_probe_all_drivers(dev);
+	if (ret) {
+		if (ret > 0)
+			RTE_LOG(ERR, EAL, "no driver found for %s\n", name);
+		goto fail;
+	}
+
+	TAILQ_INSERT_TAIL(&devargs_list, devargs, next);
+
+	rte_eal_device_insert(&dev->device);
+	TAILQ_INSERT_TAIL(&vdev_device_list, dev, next);
+	return 0;
 
+fail:
+	free(devargs->args);
+	free(devargs);
+	free(dev);
 	return ret;
 }
 
 static int
-vdev_remove_driver(const char *name)
+vdev_remove_driver(struct rte_vdev_device *dev)
 {
-	struct rte_vdev_driver *driver;
+	const char *name = rte_vdev_device_name(dev);
+	const struct rte_vdev_driver *driver;
 
-	TAILQ_FOREACH(driver, &vdev_driver_list, next) {
-		/*
-		 * search a driver prefix in virtual device name.
-		 * For example, if the driver is pcap PMD, driver->name
-		 * will be "net_pcap", but "name" will be "net_pcapN".
-		 * So use strncmp to compare.
-		 */
-		if (!strncmp(driver->driver.name, name,
-			     strlen(driver->driver.name)))
-			return driver->remove(name);
-	}
-
-	/* Give new names precedence over aliases. */
-	TAILQ_FOREACH(driver, &vdev_driver_list, next) {
-		if (driver->driver.alias &&
-		    !strncmp(driver->driver.alias, name,
-			    strlen(driver->driver.alias)))
-			return driver->remove(name);
+	if (!dev->device.driver) {
+		RTE_LOG(DEBUG, EAL, "no driver attach to device %s\n", name);
+		return 1;
 	}
 
-	return 1;
+	driver = container_of(dev->device.driver, const struct rte_vdev_driver,
+		driver);
+	return driver->remove(name);
 }
 
 int
 rte_eal_vdev_uninit(const char *name)
 {
+	struct rte_vdev_device *dev;
+	struct rte_devargs *devargs;
 	int ret;
 
 	if (name == NULL)
 		return -EINVAL;
 
-	ret = vdev_remove_driver(name);
-	if (ret > 0)
-		RTE_LOG(ERR, EAL, "no driver found for %s\n", name);
+	dev = find_vdev(name);
+	if (!dev)
+		return -ENOENT;
 
-	return ret;
+	devargs = dev->device.devargs;
+
+	ret = vdev_remove_driver(dev);
+	if (ret)
+		return ret;
+
+	TAILQ_REMOVE(&vdev_device_list, dev, next);
+	rte_eal_device_remove(&dev->device);
+
+	TAILQ_REMOVE(&devargs_list, devargs, next);
+
+	free(devargs->args);
+	free(devargs);
+	free(dev);
+	return 0;
 }
 
 static int
 vdev_scan(void)
 {
-	/* for virtual devices we don't need to scan anything */
+	struct rte_vdev_device *dev;
+	struct rte_devargs *devargs;
+
+	/* for virtual devices we scan the devargs_list populated via cmdline */
+
+	TAILQ_FOREACH(devargs, &devargs_list, next) {
+
+		if (devargs->type != RTE_DEVTYPE_VIRTUAL)
+			continue;
+
+		dev = find_vdev(devargs->virt.drv_name);
+		if (dev)
+			continue;
+
+		dev = calloc(1, sizeof(*dev));
+		if (!dev)
+			return -1;
+
+		dev->device.devargs = devargs;
+		dev->device.numa_node = SOCKET_ID_ANY;
+
+		rte_eal_device_insert(&dev->device);
+		TAILQ_INSERT_TAIL(&vdev_device_list, dev, next);
+	}
+
 	return 0;
 }
 
 static int
 vdev_probe(void)
 {
-	struct rte_devargs *devargs;
+	struct rte_vdev_device *dev;
 
 	/*
 	 * Note that the dev_driver_list is populated here
@@ -175,15 +291,14 @@ vdev_probe(void)
 	 */
 
 	/* call the init function for each virtual device */
-	TAILQ_FOREACH(devargs, &devargs_list, next) {
+	TAILQ_FOREACH(dev, &vdev_device_list, next) {
 
-		if (devargs->type != RTE_DEVTYPE_VIRTUAL)
+		if (dev->device.driver)
 			continue;
 
-		if (rte_eal_vdev_init(devargs->virt.drv_name,
-				      devargs->args)) {
+		if (vdev_probe_all_drivers(dev)) {
 			RTE_LOG(ERR, EAL, "failed to initialize %s device\n",
-				devargs->virt.drv_name);
+				rte_vdev_device_name(dev));
 			return -1;
 		}
 	}
Signature · 1 line
2.7.4
author
#54 lore raw

PATCH v3 10/10 eal: make virtual driver probe and remove take rte_vdev_device

In reply to Jan Blunck

This is a preparation to embed the generic rte_device into the rte_eth_dev also for virtual devices.

---
 drivers/crypto/null/null_crypto_pmd.c     | 18 ++++++++++++------
 drivers/net/af_packet/rte_eth_af_packet.c | 11 ++++++-----
 drivers/net/bonding/rte_eth_bond_pmd.c    | 13 +++++++++----
 drivers/net/mpipe/mpipe_tilegx.c          | 10 ++++++----
 drivers/net/null/rte_eth_null.c           | 13 ++++++++-----
 drivers/net/pcap/rte_eth_pcap.c           | 12 +++++++-----
 drivers/net/ring/rte_eth_ring.c           |  9 +++++++--
 drivers/net/tap/rte_eth_tap.c             | 10 +++++++---
 drivers/net/vhost/rte_eth_vhost.c         | 10 +++++++---
 drivers/net/virtio/virtio_user_ethdev.c   | 18 +++++++-----------
 drivers/net/xenvirt/rte_eth_xenvirt.c     |  9 +++++----
 lib/librte_eal/common/eal_common_vdev.c   |  7 +++----
 lib/librte_eal/common/include/rte_vdev.h  |  4 ++--
 13 files changed, 86 insertions(+), 58 deletions(-)
drivers/crypto/null/null_crypto_pmd.c +12 -6
index ed5a9fc..51d6de0 100644
@@ -218,8 +218,7 @@ cryptodev_null_create(struct rte_crypto_vdev_init_params *init_params)
 
 /** Initialise null crypto device */
 static int
-cryptodev_null_probe(const char *name,
-		const char *input_args)
+cryptodev_null_probe(struct rte_vdev_device *dev)
 {
 	struct rte_crypto_vdev_init_params init_params = {
 		RTE_CRYPTODEV_VDEV_DEFAULT_MAX_NB_QUEUE_PAIRS,
@@ -228,10 +227,11 @@ cryptodev_null_probe(const char *name,
 		{0}
 	};
 
-	rte_cryptodev_parse_vdev_init_params(&init_params, input_args);
+	rte_cryptodev_parse_vdev_init_params(&init_params,
+		rte_vdev_device_args(dev));
 
-	RTE_LOG(INFO, PMD, "Initialising %s on NUMA node %d\n", name,
-			init_params.socket_id);
+	RTE_LOG(INFO, PMD, "Initialising %s on NUMA node %d\n",
+		rte_vdev_device_name(dev), init_params.socket_id);
 	if (init_params.name[0] != '\0')
 		RTE_LOG(INFO, PMD, "  User defined name = %s\n",
 			init_params.name);
@@ -256,9 +256,15 @@ cryptodev_null_remove(const char *name)
 	return 0;
 }
 
+static int
+cryptodev_null_remove_dev(struct rte_vdev_device *dev)
+{
+	return cryptodev_null_remove(rte_vdev_device_name(dev));
+}
+
 static struct rte_vdev_driver cryptodev_null_pmd_drv = {
 	.probe = cryptodev_null_probe,
-	.remove = cryptodev_null_remove
+	.remove = cryptodev_null_remove_dev,
 };
 
 RTE_PMD_REGISTER_VDEV(CRYPTODEV_NAME_NULL_PMD, cryptodev_null_pmd_drv);
drivers/net/af_packet/rte_eth_af_packet.c +6 -5
index 2f87553..77536e8 100644
@@ -923,8 +923,9 @@ rte_eth_from_packet(const char *name,
 }
 
 static int
-rte_pmd_af_packet_probe(const char *name, const char *params)
+rte_pmd_af_packet_probe(struct rte_vdev_device *dev)
 {
+	const char *name = rte_vdev_device_name(dev);
 	unsigned numa_node;
 	int ret = 0;
 	struct rte_kvargs *kvlist;
@@ -934,7 +935,7 @@ rte_pmd_af_packet_probe(const char *name, const char *params)
 
 	numa_node = rte_socket_id();
 
-	kvlist = rte_kvargs_parse(params, valid_arguments);
+	kvlist = rte_kvargs_parse(rte_vdev_device_args(dev), valid_arguments);
 	if (kvlist == NULL) {
 		ret = -1;
 		goto exit;
@@ -961,7 +962,7 @@ rte_pmd_af_packet_probe(const char *name, const char *params)
 }
 
 static int
-rte_pmd_af_packet_remove(const char *name)
+rte_pmd_af_packet_remove(struct rte_vdev_device *dev)
 {
 	struct rte_eth_dev *eth_dev = NULL;
 	struct pmd_internals *internals;
@@ -970,11 +971,11 @@ rte_pmd_af_packet_remove(const char *name)
 	RTE_LOG(INFO, PMD, "Closing AF_PACKET ethdev on numa socket %u\n",
 			rte_socket_id());
 
-	if (name == NULL)
+	if (dev == NULL)
 		return -1;
 
 	/* find the ethdev entry */
-	eth_dev = rte_eth_dev_allocated(name);
+	eth_dev = rte_eth_dev_allocated(rte_vdev_device_name(dev));
 	if (eth_dev == NULL)
 		return -1;
 
drivers/net/bonding/rte_eth_bond_pmd.c +9 -4
index f3ac9e2..6c03920 100644
@@ -2230,16 +2230,19 @@ const struct eth_dev_ops default_dev_ops = {
 };
 
 static int
-bond_probe(const char *name, const char *params)
+bond_probe(struct rte_vdev_device *dev)
 {
+	const char *name;
 	struct bond_dev_private *internals;
 	struct rte_kvargs *kvlist;
 	uint8_t bonding_mode, socket_id;
 	int  arg_count, port_id;
 
+	name = rte_vdev_device_name(dev);
 	RTE_LOG(INFO, EAL, "Initializing pmd_bond for %s\n", name);
 
-	kvlist = rte_kvargs_parse(params, pmd_bond_init_valid_arguments);
+	kvlist = rte_kvargs_parse(rte_vdev_device_args(dev),
+		pmd_bond_init_valid_arguments);
 	if (kvlist == NULL)
 		return -1;
 
@@ -2297,13 +2300,15 @@ bond_probe(const char *name, const char *params)
 }
 
 static int
-bond_remove(const char *name)
+bond_remove(struct rte_vdev_device *dev)
 {
+	const char *name;
 	int  ret;
 
-	if (name == NULL)
+	if (!dev)
 		return -EINVAL;
 
+	name = rte_vdev_device_name(dev);
 	RTE_LOG(INFO, EAL, "Uninitializing pmd_bond for %s\n", name);
 
 	/* free link bonding eth device */
drivers/net/mpipe/mpipe_tilegx.c +6 -4
index 7bbd168..572c0a5 100644
@@ -1622,15 +1622,17 @@ rte_pmd_mpipe_probe_common(struct rte_vdev_driver *drv, const char *ifname,
 }
 
 static int
-rte_pmd_mpipe_xgbe_probe(const char *ifname, const char *params __rte_unused)
+rte_pmd_mpipe_xgbe_probe(struct rte_vdev_device *dev)
 {
-	return rte_pmd_mpipe_probe_common(&pmd_mpipe_xgbe_drv, ifname, params);
+	return rte_pmd_mpipe_probe_common(&pmd_mpipe_xgbe_drv,
+		rte_vdev_device_name(dev), rte_vdev_device_args(dev));
 }
 
 static int
-rte_pmd_mpipe_gbe_probe(const char *ifname, const char *params __rte_unused)
+rte_pmd_mpipe_gbe_probe(struct rte_vdev_device *dev)
 {
-	return rte_pmd_mpipe_probe_common(&pmd_mpipe_gbe_drv, ifname, params);
+	return rte_pmd_mpipe_probe_common(&pmd_mpipe_gbe_drv,
+		rte_vdev_device_name(dev), rte_vdev_device_args(dev));
 }
 
 static struct rte_vdev_driver pmd_mpipe_xgbe_drv = {
drivers/net/null/rte_eth_null.c +8 -5
index 57203e2..f4242b0 100644
@@ -608,17 +608,20 @@ get_packet_copy_arg(const char *key __rte_unused,
 }
 
 static int
-rte_pmd_null_probe(const char *name, const char *params)
+rte_pmd_null_probe(struct rte_vdev_device *dev)
 {
+	const char *name, *params;
 	unsigned numa_node;
 	unsigned packet_size = default_packet_size;
 	unsigned packet_copy = default_packet_copy;
 	struct rte_kvargs *kvlist = NULL;
 	int ret;
 
-	if (name == NULL)
+	if (!dev)
 		return -EINVAL;
 
+	name = rte_vdev_device_name(dev);
+	params = rte_vdev_device_args(dev);
 	RTE_LOG(INFO, PMD, "Initializing pmd_null for %s\n", name);
 
 	numa_node = rte_socket_id();
@@ -660,18 +663,18 @@ rte_pmd_null_probe(const char *name, const char *params)
 }
 
 static int
-rte_pmd_null_remove(const char *name)
+rte_pmd_null_remove(struct rte_vdev_device *dev)
 {
 	struct rte_eth_dev *eth_dev = NULL;
 
-	if (name == NULL)
+	if (!dev)
 		return -EINVAL;
 
 	RTE_LOG(INFO, PMD, "Closing null ethdev on numa socket %u\n",
 			rte_socket_id());
 
 	/* find the ethdev entry */
-	eth_dev = rte_eth_dev_allocated(name);
+	eth_dev = rte_eth_dev_allocated(rte_vdev_device_name(dev));
 	if (eth_dev == NULL)
 		return -1;
 
drivers/net/pcap/rte_eth_pcap.c +7 -5
index 7f0b650..ab9cde1 100644
@@ -936,8 +936,9 @@ eth_from_pcaps(const char *name, struct pmd_devargs *rx_queues,
 }
 
 static int
-pmd_pcap_probe(const char *name, const char *params)
+pmd_pcap_probe(struct rte_vdev_device *dev)
 {
+	const char *name;
 	unsigned int is_rx_pcap = 0, is_tx_pcap = 0;
 	struct rte_kvargs *kvlist;
 	struct pmd_devargs pcaps = {0};
@@ -945,13 +946,14 @@ pmd_pcap_probe(const char *name, const char *params)
 	int single_iface = 0;
 	int ret;
 
+	name = rte_vdev_device_name(dev);
 	RTE_LOG(INFO, PMD, "Initializing pmd_pcap for %s\n", name);
 
 	gettimeofday(&start_time, NULL);
 	start_cycles = rte_get_timer_cycles();
 	hz = rte_get_timer_hz();
 
-	kvlist = rte_kvargs_parse(params, valid_arguments);
+	kvlist = rte_kvargs_parse(rte_vdev_device_args(dev), valid_arguments);
 	if (kvlist == NULL)
 		return -1;
 
@@ -1035,18 +1037,18 @@ pmd_pcap_probe(const char *name, const char *params)
 }
 
 static int
-pmd_pcap_remove(const char *name)
+pmd_pcap_remove(struct rte_vdev_device *dev)
 {
 	struct rte_eth_dev *eth_dev = NULL;
 
 	RTE_LOG(INFO, PMD, "Closing pcap ethdev on numa socket %u\n",
 			rte_socket_id());
 
-	if (name == NULL)
+	if (!dev)
 		return -1;
 
 	/* reserve an ethdev entry */
-	eth_dev = rte_eth_dev_allocated(name);
+	eth_dev = rte_eth_dev_allocated(rte_vdev_device_name(dev));
 	if (eth_dev == NULL)
 		return -1;
 
drivers/net/ring/rte_eth_ring.c +7 -2
index 6f9cc1a..62606e7 100644
@@ -502,12 +502,16 @@ static int parse_kvlist (const char *key __rte_unused, const char *value, void *
 }
 
 static int
-rte_pmd_ring_probe(const char *name, const char *params)
+rte_pmd_ring_probe(struct rte_vdev_device *dev)
 {
+	const char *name, *params;
 	struct rte_kvargs *kvlist = NULL;
 	int ret = 0;
 	struct node_action_list *info = NULL;
 
+	name = rte_vdev_device_name(dev);
+	params = rte_vdev_device_args(dev);
+
 	RTE_LOG(INFO, PMD, "Initializing pmd_ring for %s\n", name);
 
 	if (params == NULL || params[0] == '\0') {
@@ -577,8 +581,9 @@ rte_pmd_ring_probe(const char *name, const char *params)
 }
 
 static int
-rte_pmd_ring_remove(const char *name)
+rte_pmd_ring_remove(struct rte_vdev_device *dev)
 {
+	const char *name = rte_vdev_device_name(dev);
 	struct rte_eth_dev *eth_dev = NULL;
 	struct pmd_internals *internals = NULL;
 	struct ring_queue *r = NULL;
drivers/net/tap/rte_eth_tap.c +7 -3
index efc4426..941150f 100644
@@ -741,13 +741,17 @@ set_interface_speed(const char *key __rte_unused,
 /* Open a TAP interface device.
  */
 static int
-rte_pmd_tap_probe(const char *name, const char *params)
+rte_pmd_tap_probe(struct rte_vdev_device *dev)
 {
+	const char *name, *params;
 	int ret;
 	struct rte_kvargs *kvlist = NULL;
 	int speed;
 	char tap_name[RTE_ETH_NAME_MAX_LEN];
 
+	name = rte_vdev_device_name(dev);
+	params = rte_vdev_device_args(dev);
+
 	speed = ETH_SPEED_NUM_10G;
 	snprintf(tap_name, sizeof(tap_name), "%s%d",
 		 DEFAULT_TAP_NAME, tap_unit++);
@@ -797,7 +801,7 @@ rte_pmd_tap_probe(const char *name, const char *params)
 /* detach a TAP device.
  */
 static int
-rte_pmd_tap_remove(const char *name)
+rte_pmd_tap_remove(struct rte_vdev_device *dev)
 {
 	struct rte_eth_dev *eth_dev = NULL;
 	struct pmd_internals *internals;
@@ -807,7 +811,7 @@ rte_pmd_tap_remove(const char *name)
 		rte_socket_id());
 
 	/* find the ethdev entry */
-	eth_dev = rte_eth_dev_allocated(name);
+	eth_dev = rte_eth_dev_allocated(rte_vdev_device_name(dev));
 	if (!eth_dev)
 		return 0;
 
drivers/net/vhost/rte_eth_vhost.c +7 -3
index e98cffd..d0d0474 100644
@@ -1156,8 +1156,9 @@ open_int(const char *key __rte_unused, const char *value, void *extra_args)
 }
 
 static int
-rte_pmd_vhost_probe(const char *name, const char *params)
+rte_pmd_vhost_probe(struct rte_vdev_device *dev)
 {
+	const char *name;
 	struct rte_kvargs *kvlist = NULL;
 	int ret = 0;
 	char *iface_name;
@@ -1166,9 +1167,10 @@ rte_pmd_vhost_probe(const char *name, const char *params)
 	int client_mode = 0;
 	int dequeue_zero_copy = 0;
 
+	name = rte_vdev_device_name(dev);
 	RTE_LOG(INFO, PMD, "Initializing pmd_vhost for %s\n", name);
 
-	kvlist = rte_kvargs_parse(params, valid_arguments);
+	kvlist = rte_kvargs_parse(rte_vdev_device_args(dev), valid_arguments);
 	if (kvlist == NULL)
 		return -1;
 
@@ -1219,11 +1221,13 @@ rte_pmd_vhost_probe(const char *name, const char *params)
 }
 
 static int
-rte_pmd_vhost_remove(const char *name)
+rte_pmd_vhost_remove(struct rte_vdev_device *dev)
 {
+	const char *name;
 	struct rte_eth_dev *eth_dev = NULL;
 	unsigned int i;
 
+	name = rte_vdev_device_name(dev);
 	RTE_LOG(INFO, PMD, "Un-Initializing pmd_vhost for %s\n", name);
 
 	/* find an ethdev entry */
drivers/net/virtio/virtio_user_ethdev.c +7 -11
index 0b226ac..42ad8a2 100644
@@ -338,7 +338,7 @@ virtio_user_eth_dev_free(struct rte_eth_dev *eth_dev)
  * Returns 0 on success.
  */
 static int
-virtio_user_pmd_probe(const char *name, const char *params)
+virtio_user_pmd_probe(struct rte_vdev_device *dev)
 {
 	struct rte_kvargs *kvlist = NULL;
 	struct rte_eth_dev *eth_dev;
@@ -350,13 +350,7 @@ virtio_user_pmd_probe(const char *name, const char *params)
 	char *mac_addr = NULL;
 	int ret = -1;
 
-	if (!params || params[0] == '\0') {
-		PMD_INIT_LOG(ERR, "arg %s is mandatory for virtio_user",
-			  VIRTIO_USER_ARG_QUEUE_SIZE);
-		goto end;
-	}
-
-	kvlist = rte_kvargs_parse(params, valid_args);
+	kvlist = rte_kvargs_parse(rte_vdev_device_args(dev), valid_args);
 	if (!kvlist) {
 		PMD_INIT_LOG(ERR, "error when parsing param");
 		goto end;
@@ -418,7 +412,7 @@ virtio_user_pmd_probe(const char *name, const char *params)
 		goto end;
 	}
 
-	eth_dev = virtio_user_eth_dev_alloc(name);
+	eth_dev = virtio_user_eth_dev_alloc(rte_vdev_device_name(dev));
 	if (!eth_dev) {
 		PMD_INIT_LOG(ERR, "virtio_user fails to alloc device");
 		goto end;
@@ -452,15 +446,17 @@ virtio_user_pmd_probe(const char *name, const char *params)
 
 /** Called by rte_eth_dev_detach() */
 static int
-virtio_user_pmd_remove(const char *name)
+virtio_user_pmd_remove(struct rte_vdev_device *vdev)
 {
+	const char *name;
 	struct rte_eth_dev *eth_dev;
 	struct virtio_hw *hw;
 	struct virtio_user_dev *dev;
 
-	if (!name)
+	if (!vdev)
 		return -EINVAL;
 
+	name = rte_vdev_device_name(vdev);
 	PMD_DRV_LOG(INFO, "Un-Initializing %s", name);
 	eth_dev = rte_eth_dev_allocated(name);
 	if (!eth_dev)
drivers/net/xenvirt/rte_eth_xenvirt.c +5 -4
index 19bc09a..6ec8c08 100644
@@ -726,7 +726,7 @@ eth_dev_xenvirt_free(const char *name, const unsigned numa_node)
 
 /*TODO: Support multiple process model */
 static int
-rte_pmd_xenvirt_probe(const char *name, const char *params)
+rte_pmd_xenvirt_probe(struct rte_vdev_device *dev)
 {
 	if (virtio_idx == 0) {
 		if (xenstore_init() != 0) {
@@ -738,14 +738,15 @@ rte_pmd_xenvirt_probe(const char *name, const char *params)
 			return -1;
 		}
 	}
-	eth_dev_xenvirt_create(name, params, rte_socket_id(), DEV_CREATE);
+	eth_dev_xenvirt_create(rte_vdev_device_name(dev),
+		rte_vdev_device_args(dev), rte_socket_id(), DEV_CREATE);
 	return 0;
 }
 
 static int
-rte_pmd_xenvirt_remove(const char *name)
+rte_pmd_xenvirt_remove(struct rte_vdev_device *dev)
 {
-	eth_dev_xenvirt_free(name, rte_socket_id());
+	eth_dev_xenvirt_free(rte_vdev_device_name(dev), rte_socket_id());
 
 	if (virtio_idx == 0) {
 		if (xenstore_uninit() != 0)
lib/librte_eal/common/eal_common_vdev.c +3 -4
index 7215b50..3ee24b1 100644
@@ -75,7 +75,6 @@ static int
 vdev_probe_all_drivers(struct rte_vdev_device *dev)
 {
 	const char *name = rte_vdev_device_name(dev);
-	const char *args = rte_vdev_device_args(dev);
 	struct rte_vdev_driver *driver;
 	int ret;
 
@@ -89,7 +88,7 @@ vdev_probe_all_drivers(struct rte_vdev_device *dev)
 		if (!strncmp(driver->driver.name, name,
 			    strlen(driver->driver.name))) {
 			dev->device.driver = &driver->driver;
-			ret = driver->probe(name, args);
+			ret = driver->probe(dev);
 			if (ret)
 				dev->device.driver = NULL;
 			return ret;
@@ -102,7 +101,7 @@ vdev_probe_all_drivers(struct rte_vdev_device *dev)
 		    !strncmp(driver->driver.alias, name,
 			    strlen(driver->driver.alias))) {
 			dev->device.driver = &driver->driver;
-			ret = driver->probe(name, args);
+			ret = driver->probe(dev);
 			if (ret)
 				dev->device.driver = NULL;
 			return ret;
@@ -214,7 +213,7 @@ vdev_remove_driver(struct rte_vdev_device *dev)
 
 	driver = container_of(dev->device.driver, const struct rte_vdev_driver,
 		driver);
-	return driver->remove(name);
+	return driver->remove(dev);
 }
 
 int
lib/librte_eal/common/include/rte_vdev.h +2 -2
index 81f6beb..8db2c00 100644
@@ -68,12 +68,12 @@ TAILQ_HEAD(vdev_driver_list, rte_vdev_driver);
 /**
  * Probe function called for each virtual device driver once.
  */
-typedef int (rte_vdev_probe_t)(const char *name, const char *args);
+typedef int (rte_vdev_probe_t)(struct rte_vdev_device *dev);
 
 /**
  * Remove function called for each virtual device driver once.
  */
-typedef int (rte_vdev_remove_t)(const char *name);
+typedef int (rte_vdev_remove_t)(struct rte_vdev_device *dev);
 
 /**
  * A virtual device driver abstraction.
Signature · 1 line
2.7.4
author
#55 lore raw
In reply to Jan Blunck
Quoted 10 lines · Jan Blunck

With the rte_bus infrastructure present in 17.02 it is possible to refactor the virtual device probing into a bus. This series also introduces the rte_vdev_device to better keep track of devices.

This patchset depends on:
http://dpdk.org/dev/patchwork/patch/20416/
http://dpdk.org/dev/patchwork/patch/20417/

Changes since version 2:
* implicit bus registration through rte_eal_vdrv_register()

On a second thought I don't think that this is correct though since it opens up the possibility of racing an alternative "virtual" bus. I don't think that this is a good thing though. I'll fix this in v4.

Thoughts?

Thanks,
Jan

Quoted 46 lines

* explicit delay probing of virtual bus in rte_bus_probe()
* addition of rte_vdev_device_args() helper
* make virtual driver probe and remove take rte_vdev_device

Changes since version 1:
* addition of rte_vdev_device_name() helper
* removed rte_eal_dev_init() from *.map files
* use SOCKET_ID_ANY

Jan Blunck (10):
eal: probe legacy PCI devices before other bus devices
eal: probe new virtual bus after other bus devices
eal: move virtual device probing into a bus
eal: remove unused rte_eal_dev_init()
eal: Refactor vdev driver probe/remove
eal: add struct rte_vdev_device
eal: add virtual device name helper function
eal: add virtual device arguments helper function
eal: make virtual bus use rte_vdev_device
eal: make virtual driver probe and remove take rte_vdev_device

 drivers/crypto/null/null_crypto_pmd.c           |  18 +-
 drivers/net/af_packet/rte_eth_af_packet.c       |  11 +-
 drivers/net/bonding/rte_eth_bond_pmd.c          |  13 +-
 drivers/net/mpipe/mpipe_tilegx.c                |  10 +-
 drivers/net/null/rte_eth_null.c                 |  13 +-
 drivers/net/pcap/rte_eth_pcap.c                 |  12 +-
 drivers/net/ring/rte_eth_ring.c                 |   9 +-
 drivers/net/tap/rte_eth_tap.c                   |  10 +-
 drivers/net/vhost/rte_eth_vhost.c               |  10 +-
 drivers/net/virtio/virtio_user_ethdev.c         |  18 +-
 drivers/net/xenvirt/rte_eth_xenvirt.c           |   9 +-
 lib/librte_eal/bsdapp/eal/eal.c                 |   9 +-
 lib/librte_eal/bsdapp/eal/rte_eal_version.map   |   1 -
 lib/librte_eal/common/eal_common_bus.c          |  16 +-
 lib/librte_eal/common/eal_common_dev.c          |  28 ---
 lib/librte_eal/common/eal_common_vdev.c         | 259 +++++++++++++++++++++---
 lib/librte_eal/common/include/rte_dev.h         |   5 -
 lib/librte_eal/common/include/rte_vdev.h        |  26 ++-
 lib/librte_eal/linuxapp/eal/eal.c               |   9 +-
 lib/librte_eal/linuxapp/eal/rte_eal_version.map |   1 -
 20 files changed, 355 insertions(+), 132 deletions(-)

--
2.7.4

#56 lore raw
Quoted 9 lines · Jan Blunck
Quoted 8 lines · Jan Blunck

With the rte_bus infrastructure present in 17.02 it is possible to refactor the virtual device probing into a bus. This series also introduces the rte_vdev_device to better keep track of devices.

This patchset depends on:
http://dpdk.org/dev/patchwork/patch/20416/
http://dpdk.org/dev/patchwork/patch/20417/

Quoted 8 lines
Quoted 2 lines

Changes since version 2:
* implicit bus registration through rte_eal_vdrv_register()

On a second thought I don't think that this is correct though since it opens up the possibility of racing an alternative "virtual" bus. I don't think that this is a good thing though. I'll fix this in v4.

Thoughts?

I prefer the RTE_REGISTER* way.
The issue of duplicate bus remains whether we use the macro or the implicit way.

If you use RTE_*, do you think that duplicate registration issue is worth fixing?
(It would mean rte_bus_register to return error which the caller would then need to handle).

Quoted 51 lines

Thanks,
Jan

Quoted 46 lines

* explicit delay probing of virtual bus in rte_bus_probe()
* addition of rte_vdev_device_args() helper
* make virtual driver probe and remove take rte_vdev_device

Changes since version 1:
* addition of rte_vdev_device_name() helper
* removed rte_eal_dev_init() from *.map files
* use SOCKET_ID_ANY

Jan Blunck (10):
eal: probe legacy PCI devices before other bus devices
eal: probe new virtual bus after other bus devices
eal: move virtual device probing into a bus
eal: remove unused rte_eal_dev_init()
eal: Refactor vdev driver probe/remove
eal: add struct rte_vdev_device
eal: add virtual device name helper function
eal: add virtual device arguments helper function
eal: make virtual bus use rte_vdev_device
eal: make virtual driver probe and remove take rte_vdev_device

 drivers/crypto/null/null_crypto_pmd.c           |  18 +-
 drivers/net/af_packet/rte_eth_af_packet.c       |  11 +-
 drivers/net/bonding/rte_eth_bond_pmd.c          |  13 +-
 drivers/net/mpipe/mpipe_tilegx.c                |  10 +-
 drivers/net/null/rte_eth_null.c                 |  13 +-
 drivers/net/pcap/rte_eth_pcap.c                 |  12 +-
 drivers/net/ring/rte_eth_ring.c                 |   9 +-
 drivers/net/tap/rte_eth_tap.c                   |  10 +-
 drivers/net/vhost/rte_eth_vhost.c               |  10 +-
 drivers/net/virtio/virtio_user_ethdev.c         |  18 +-
 drivers/net/xenvirt/rte_eth_xenvirt.c           |   9 +-
 lib/librte_eal/bsdapp/eal/eal.c                 |   9 +-
 lib/librte_eal/bsdapp/eal/rte_eal_version.map   |   1 -
 lib/librte_eal/common/eal_common_bus.c          |  16 +-
 lib/librte_eal/common/eal_common_dev.c          |  28 ---
 lib/librte_eal/common/eal_common_vdev.c         | 259 +++++++++++++++++++++---
 lib/librte_eal/common/include/rte_dev.h         |   5 -
 lib/librte_eal/common/include/rte_vdev.h        |  26 ++-
 lib/librte_eal/linuxapp/eal/eal.c               |   9 +-
 lib/librte_eal/linuxapp/eal/rte_eal_version.map |   1 -
 20 files changed, 355 insertions(+), 132 deletions(-)

--
2.7.4

author
#57 lore raw
Quoted 25 lines · Shreyansh Jain
Quoted 17 lines · Jan Blunck
Quoted 6 lines · Jan Blunck

With the rte_bus infrastructure present in 17.02 it is possible to refactor
the virtual device probing into a bus. This series also introduces the rte_vdev_device to better keep track of devices.

Quoted 6 lines

This patchset depends on:
http://dpdk.org/dev/patchwork/patch/20416/
http://dpdk.org/dev/patchwork/patch/20417/

Changes since version 2:
* implicit bus registration through rte_eal_vdrv_register()

Quoted 5 lines

On a second thought I don't think that this is correct though since it opens up the possibility of racing an alternative "virtual" bus. I don't think that this is a good thing though. I'll fix this in v4.

Thoughts?

Quoted 9 lines

I prefer the RTE_REGISTER* way.
The issue of duplicate bus remains whether we use the macro or the implicit way.

If you use RTE_*, do you think that duplicate registration issue is worth fixing?
(It would mean rte_bus_register to return error which the caller would then need to handle).

I don't think that there is a good way to handle this if we use the library constructors. It is better to fail the registration of the bus and log the error via RTE_LOG(). That introduces a dependency on the initialization of the logging system to be available before the library constructors run (before main()).

#58 lore raw
Quoted 46 lines

-----Original Message-----
From: [email protected] [mailto:[email protected]] On Behalf Of Jan Blunck
Sent: Tuesday, February 28, 2017 2:49 PM
To: Shreyansh Jain <[email protected]>
Cc: dev <[email protected]>; David Marchand <[email protected]>; Ferruh Yigit <[email protected]>
Subject: Re: [PATCH v3 00/10] Rework vdev probing to use rte_bus infrastructure

Quoted 25 lines · Shreyansh Jain
Quoted 17 lines · Jan Blunck
Quoted 6 lines · Jan Blunck

With the rte_bus infrastructure present in 17.02 it is possible to refactor
the virtual device probing into a bus. This series also introduces the rte_vdev_device to better keep track of devices.

Quoted 6 lines

This patchset depends on:
http://dpdk.org/dev/patchwork/patch/20416/
http://dpdk.org/dev/patchwork/patch/20417/

Changes since version 2:
* implicit bus registration through rte_eal_vdrv_register()

Quoted 5 lines

On a second thought I don't think that this is correct though since it opens up the possibility of racing an alternative "virtual" bus. I don't think that this is a good thing though. I'll fix this in v4.

Thoughts?

Quoted 9 lines

I prefer the RTE_REGISTER* way.
The issue of duplicate bus remains whether we use the macro or the implicit way.

If you use RTE_*, do you think that duplicate registration issue is worth fixing?
(It would mean rte_bus_register to return error which the caller would then need to handle).

Quoted 5 lines

I don't think that there is a good way to handle this if we use the library constructors. It is better to fail the registration of the bus and log the error via RTE_LOG(). That introduces a dependency on the initialization of the logging system to be available before the library constructors run (before main()).

Agree. Log dependency is the tricky part. Log subsystem is in turn dependent on users input for level.

author
#59 lore raw

v4 cover Rework vdev probing to use rte_bus infrastructure

In reply to Jan Blunck

With the rte_bus infrastructure present in 17.02 it is possible to refactor the virtual device probing into a bus. This series also introduces the rte_vdev_device to better keep track of devices.

This patchset depends on:
http://dpdk.org/dev/patchwork/patch/20416/
http://dpdk.org/dev/patchwork/patch/20417/

Changes since version 3:
* revert implicit registration changes

Changes since version 2:
* implicit bus registration through rte_eal_vdrv_register()
* explicit delay probing of virtual bus in rte_bus_probe()
* addition of rte_vdev_device_args() helper
* make virtual driver probe and remove take rte_vdev_device

Changes since version 1:
* addition of rte_vdev_device_name() helper
* removed rte_eal_dev_init() from *.map files
* use SOCKET_ID_ANY

Jan Blunck (10):
eal: probe legacy PCI devices before other bus devices
eal: probe new virtual bus after other bus devices
eal: move virtual device probing into a bus
eal: remove unused rte_eal_dev_init()
eal: Refactor vdev driver probe/remove
eal: add struct rte_vdev_device
eal: add virtual device name helper function
eal: add virtual device arguments helper function
eal: make virtual bus use rte_vdev_device
eal: make virtual driver probe and remove take rte_vdev_device

 drivers/crypto/null/null_crypto_pmd.c           |  18 +-
 drivers/net/af_packet/rte_eth_af_packet.c       |  11 +-
 drivers/net/bonding/rte_eth_bond_pmd.c          |  13 +-
 drivers/net/mpipe/mpipe_tilegx.c                |  10 +-
 drivers/net/null/rte_eth_null.c                 |  13 +-
 drivers/net/pcap/rte_eth_pcap.c                 |  12 +-
 drivers/net/ring/rte_eth_ring.c                 |   9 +-
 drivers/net/tap/rte_eth_tap.c                   |  10 +-
 drivers/net/vhost/rte_eth_vhost.c               |  10 +-
 drivers/net/virtio/virtio_user_ethdev.c         |  18 +-
 drivers/net/xenvirt/rte_eth_xenvirt.c           |   9 +-
 lib/librte_eal/bsdapp/eal/eal.c                 |   9 +-
 lib/librte_eal/bsdapp/eal/rte_eal_version.map   |   1 -
 lib/librte_eal/common/eal_common_bus.c          |  16 +-
 lib/librte_eal/common/eal_common_dev.c          |  28 ---
 lib/librte_eal/common/eal_common_vdev.c         | 245 +++++++++++++++++++++---
 lib/librte_eal/common/include/rte_dev.h         |   5 -
 lib/librte_eal/common/include/rte_vdev.h        |  26 ++-
 lib/librte_eal/linuxapp/eal/eal.c               |   9 +-
 lib/librte_eal/linuxapp/eal/rte_eal_version.map |   1 -
 20 files changed, 341 insertions(+), 132 deletions(-)
Signature · 1 line
2.7.4
author
#60 lore raw

PATCH v4 1/10 eal: probe legacy PCI devices before other bus devices

Make sure that the PCI devices are probed before the virtual devices after the legacy virtual device probing has been moved to a bus.

---
 lib/librte_eal/bsdapp/eal/eal.c   | 8 ++++----
 lib/librte_eal/linuxapp/eal/eal.c | 8 ++++----
 2 files changed, 8 insertions(+), 8 deletions(-)
lib/librte_eal/bsdapp/eal/eal.c +4 -4
index ee7c9de..a584447 100644
@@ -613,14 +613,14 @@ rte_eal_init(int argc, char **argv)
 	rte_eal_mp_remote_launch(sync_func, NULL, SKIP_MASTER);
 	rte_eal_mp_wait_lcore();
 
-	/* Probe all the buses and devices/drivers on them */
-	if (rte_bus_probe())
-		rte_panic("Cannot probe devices\n");
-
 	/* Probe & Initialize PCI devices */
 	if (rte_eal_pci_probe())
 		rte_panic("Cannot probe PCI\n");
 
+	/* Probe all the buses and devices/drivers on them */
+	if (rte_bus_probe())
+		rte_panic("Cannot probe devices\n");
+
 	if (rte_eal_dev_init() < 0)
 		rte_panic("Cannot init pmd devices\n");
 
lib/librte_eal/linuxapp/eal/eal.c +4 -4
index bf6b818..f77ff5c 100644
@@ -884,14 +884,14 @@ rte_eal_init(int argc, char **argv)
 	rte_eal_mp_remote_launch(sync_func, NULL, SKIP_MASTER);
 	rte_eal_mp_wait_lcore();
 
-	/* Probe all the buses and devices/drivers on them */
-	if (rte_bus_probe())
-		rte_panic("Cannot probe devices\n");
-
 	/* Probe & Initialize PCI devices */
 	if (rte_eal_pci_probe())
 		rte_panic("Cannot probe PCI\n");
 
+	/* Probe all the buses and devices/drivers on them */
+	if (rte_bus_probe())
+		rte_panic("Cannot probe devices\n");
+
 	if (rte_eal_dev_init() < 0)
 		rte_panic("Cannot init pmd devices\n");
 
Signature · 1 line
2.7.4
author
#61 lore raw

PATCH v4 2/10 eal: probe new virtual bus after other bus devices

In reply to Jan Blunck

Also see commit f4ce209a8ce5 ("eal: postpone vdev initialization").

---
 lib/librte_eal/common/eal_common_bus.c | 16 +++++++++++++++-
 1 file changed, 15 insertions(+), 1 deletion(-)
lib/librte_eal/common/eal_common_bus.c +15 -1
index 4638e78..8f9baf8 100644
@@ -86,9 +86,14 @@ int
 rte_bus_probe(void)
 {
 	int ret;
-	struct rte_bus *bus;
+	struct rte_bus *bus, *vbus = NULL;
 
 	TAILQ_FOREACH(bus, &rte_bus_list, next) {
+		if (!strcmp(bus->name, "virtual")) {
+			vbus = bus;
+			continue;
+		}
+
 		ret = bus->probe();
 		if (ret) {
 			RTE_LOG(ERR, EAL, "Bus (%s) probe failed.\n",
@@ -97,6 +102,15 @@ rte_bus_probe(void)
 		}
 	}
 
+	if (vbus) {
+		ret = vbus->probe();
+		if (ret) {
+			RTE_LOG(ERR, EAL, "Bus (%s) probe failed.\n",
+				vbus->name);
+			return ret;
+		}
+	}
+
 	return 0;
 }
 
Signature · 1 line
2.7.4
#62 lore raw

Re: [PATCH v4 02/10] eal: probe new virtual bus after other bus devices

2017-03-06 11:56, Jan Blunck:

lib/librte_eal/common/eal_common_bus.c int · line 95

Quoted 12 lines
lib/librte_eal/common/eal_common_bus.c +5 -1
@@ -86,9 +86,14 @@ int
 rte_bus_probe(void)
 {
 	int ret;
-	struct rte_bus *bus;
+	struct rte_bus *bus, *vbus = NULL;
 
 	TAILQ_FOREACH(bus, &rte_bus_list, next) {
+		if (!strcmp(bus->name, "virtual")) {
+			vbus = bus;
+			continue;
+		}

Why this special handling?

[...]

lib/librte_eal/common/eal_common_bus.c rte_bus_probe(void) · line 112

Quoted 8 lines
lib/librte_eal/common/eal_common_bus.c +8 -0
+	if (vbus) {
+		ret = vbus->probe();
+		if (ret) {
+			RTE_LOG(ERR, EAL, "Bus (%s) probe failed.\n",
+				vbus->name);
+			return ret;
+		}
+	}

We should not have any special code in this function.

author
#63 lore raw

PATCH v4 3/10 eal: move virtual device probing into a bus

In reply to Jan Blunck

This is a refactoring of the virtual device probing which moves into into a proper bus structure.

---
 lib/librte_eal/common/eal_common_dev.c  | 22 -----------------
 lib/librte_eal/common/eal_common_vdev.c | 44 +++++++++++++++++++++++++++++++++
 2 files changed, 44 insertions(+), 22 deletions(-)
lib/librte_eal/common/eal_common_dev.c +0 -22
index 4f3b493..1ce90f6 100644
@@ -79,28 +79,6 @@ void rte_eal_device_remove(struct rte_device *dev)
 int
 rte_eal_dev_init(void)
 {
-	struct rte_devargs *devargs;
-
-	/*
-	 * Note that the dev_driver_list is populated here
-	 * from calls made to rte_eal_driver_register from constructor functions
-	 * embedded into PMD modules via the RTE_PMD_REGISTER_VDEV macro
-	 */
-
-	/* call the init function for each virtual device */
-	TAILQ_FOREACH(devargs, &devargs_list, next) {
-
-		if (devargs->type != RTE_DEVTYPE_VIRTUAL)
-			continue;
-
-		if (rte_eal_vdev_init(devargs->virt.drv_name,
-					devargs->args)) {
-			RTE_LOG(ERR, EAL, "failed to initialize %s device\n",
-					devargs->virt.drv_name);
-			return -1;
-		}
-	}
-
 	return 0;
 }
 
lib/librte_eal/common/eal_common_vdev.c +44 -0

55 lines not on this page · raw message

Signature · 1 line
2.7.4
#64 lore raw

Re: [PATCH v4 03/10] eal: move virtual device probing into a bus

2017-03-06 11:56, Jan Blunck:

lib/librte_eal/common/eal_common_vdev.c rte_eal_vdev_uninit(const char *name) · line 133

Quoted 6 lines
lib/librte_eal/common/eal_common_vdev.c +6 -0
+static int
+vdev_scan(void)
+{
+	/* for virtual devices we don't need to scan anything */
+	return 0;
+}

The vdev_scan could save the devargs.
The vdev args are the equivalent of PCI BDF.

author
#65 lore raw

Re: [PATCH v4 03/10] eal: move virtual device probing into a bus

Quoted 10 lines · Thomas Monjalon

2017-03-06 11:56, Jan Blunck:

lib/librte_eal/common/eal_common_vdev.c rte_eal_vdev_uninit(const char *name) · line 133

Quoted 6 lines
lib/librte_eal/common/eal_common_vdev.c +6 -0
+static int
+vdev_scan(void)
+{
+     /* for virtual devices we don't need to scan anything */
+     return 0;
+}

The vdev_scan could save the devargs.
The vdev args are the equivalent of PCI BDF.

In a later patch ("eal: make virtual bus use rte_vdev_device") the vdev_scan() is creating the list of devices based on the devargs.

author
#66 lore raw

PATCH v4 4/10 eal: remove unused rte_eal_dev_init()

In reply to Jan Blunck
---
 lib/librte_eal/bsdapp/eal/eal.c                 | 3 ---
 lib/librte_eal/bsdapp/eal/rte_eal_version.map   | 1 -
 lib/librte_eal/common/eal_common_dev.c          | 6 ------
 lib/librte_eal/common/include/rte_dev.h         | 5 -----
 lib/librte_eal/linuxapp/eal/eal.c               | 3 ---
 lib/librte_eal/linuxapp/eal/rte_eal_version.map | 1 -
 6 files changed, 19 deletions(-)
lib/librte_eal/bsdapp/eal/eal.c +0 -3
index a584447..3d29fcb 100644
@@ -621,9 +621,6 @@ rte_eal_init(int argc, char **argv)
 	if (rte_bus_probe())
 		rte_panic("Cannot probe devices\n");
 
-	if (rte_eal_dev_init() < 0)
-		rte_panic("Cannot init pmd devices\n");
-
 	rte_eal_mcfg_complete();
 
 	return fctret;
lib/librte_eal/bsdapp/eal/rte_eal_version.map +0 -1
index 67f2ffb..b1996e0 100644
@@ -22,7 +22,6 @@ DPDK_2.0 {
 	rte_dump_tailq;
 	rte_eal_alarm_cancel;
 	rte_eal_alarm_set;
-	rte_eal_dev_init;
 	rte_eal_devargs_add;
 	rte_eal_devargs_dump;
 	rte_eal_devargs_type_count;
lib/librte_eal/common/eal_common_dev.c +0 -6
index 1ce90f6..4bde430 100644
@@ -76,12 +76,6 @@ void rte_eal_device_remove(struct rte_device *dev)
 	TAILQ_REMOVE(&dev_device_list, dev, next);
 }
 
-int
-rte_eal_dev_init(void)
-{
-	return 0;
-}
-
 int rte_eal_dev_attach(const char *name, const char *devargs)
 {
 	struct rte_pci_addr addr;
lib/librte_eal/common/include/rte_dev.h +0 -5
index b17791f..4251099 100644
@@ -171,11 +171,6 @@ void rte_eal_driver_register(struct rte_driver *driver);
 void rte_eal_driver_unregister(struct rte_driver *driver);
 
 /**
- * Initalize all the registered drivers in this process
- */
-int rte_eal_dev_init(void);
-
-/**
  * Initialize a driver specified by name.
  *
  * @param name
lib/librte_eal/linuxapp/eal/eal.c +0 -3
index f77ff5c..88479de 100644
@@ -892,9 +892,6 @@ rte_eal_init(int argc, char **argv)
 	if (rte_bus_probe())
 		rte_panic("Cannot probe devices\n");
 
-	if (rte_eal_dev_init() < 0)
-		rte_panic("Cannot init pmd devices\n");
-
 	rte_eal_mcfg_complete();
 
 	return fctret;
lib/librte_eal/linuxapp/eal/rte_eal_version.map +0 -1
index 9c134b4..2ada2f0 100644
@@ -22,7 +22,6 @@ DPDK_2.0 {
 	rte_dump_tailq;
 	rte_eal_alarm_cancel;
 	rte_eal_alarm_set;
-	rte_eal_dev_init;
 	rte_eal_devargs_add;
 	rte_eal_devargs_dump;
 	rte_eal_devargs_type_count;
Signature · 1 line
2.7.4
author
#67 lore raw

PATCH v4 5/10 eal: Refactor vdev driver probe/remove

In reply to Jan Blunck

This is a preparation for the introduction of the struct rte_vdev_device.

---
 lib/librte_eal/common/eal_common_vdev.c | 44 ++++++++++++++++++++++++---------
 1 file changed, 33 insertions(+), 11 deletions(-)
lib/librte_eal/common/eal_common_vdev.c +33 -11
index b1f490c..07974c5 100644
@@ -61,14 +61,11 @@ rte_eal_vdrv_unregister(struct rte_vdev_driver *driver)
 	TAILQ_REMOVE(&vdev_driver_list, driver, next);
 }
 
-int
-rte_eal_vdev_init(const char *name, const char *args)
+static int
+vdev_probe_all_drivers(const char *name, const char *args)
 {
 	struct rte_vdev_driver *driver;
 
-	if (name == NULL)
-		return -EINVAL;
-
 	TAILQ_FOREACH(driver, &vdev_driver_list, next) {
 		/*
 		 * search a driver prefix in virtual device name.
@@ -89,18 +86,29 @@ rte_eal_vdev_init(const char *name, const char *args)
 			return driver->probe(name, args);
 	}
 
-	RTE_LOG(ERR, EAL, "no driver found for %s\n", name);
-	return -EINVAL;
+	return 1;
 }
 
 int
-rte_eal_vdev_uninit(const char *name)
+rte_eal_vdev_init(const char *name, const char *args)
 {
-	struct rte_vdev_driver *driver;
+	int ret;
 
 	if (name == NULL)
 		return -EINVAL;
 
+	ret = vdev_probe_all_drivers(name, args);
+	if (ret  > 0)
+		RTE_LOG(ERR, EAL, "no driver found for %s\n", name);
+
+	return ret;
+}
+
+static int
+vdev_remove_driver(const char *name)
+{
+	struct rte_vdev_driver *driver;
+
 	TAILQ_FOREACH(driver, &vdev_driver_list, next) {
 		/*
 		 * search a driver prefix in virtual device name.
@@ -121,8 +129,22 @@ rte_eal_vdev_uninit(const char *name)
 			return driver->remove(name);
 	}
 
-	RTE_LOG(ERR, EAL, "no driver found for %s\n", name);
-	return -EINVAL;
+	return 1;
+}
+
+int
+rte_eal_vdev_uninit(const char *name)
+{
+	int ret;
+
+	if (name == NULL)
+		return -EINVAL;
+
+	ret = vdev_remove_driver(name);
+	if (ret > 0)
+		RTE_LOG(ERR, EAL, "no driver found for %s\n", name);
+
+	return ret;
 }
 
 static int
Signature · 1 line
2.7.4
author
#68 lore raw

PATCH v4 6/10 eal: add struct rte_vdev_device

In reply to Jan Blunck

This adds the rte_vdev_device structure which embeds a generic rte_device.

---
 lib/librte_eal/common/eal_common_vdev.c  | 5 +++++
 lib/librte_eal/common/include/rte_vdev.h | 5 +++++
 2 files changed, 10 insertions(+)
lib/librte_eal/common/eal_common_vdev.c +5 -0
index 07974c5..f884c7b 100644
@@ -42,6 +42,11 @@
 #include <rte_common.h>
 #include <rte_devargs.h>
 
+/** Double linked list of virtual device drivers. */
+TAILQ_HEAD(vdev_device_list, rte_vdev_device);
+
+static struct vdev_device_list vdev_device_list =
+	TAILQ_HEAD_INITIALIZER(vdev_device_list);
 struct vdev_driver_list vdev_driver_list =
 	TAILQ_HEAD_INITIALIZER(vdev_driver_list);
 
lib/librte_eal/common/include/rte_vdev.h +5 -0
index 784e837..8f98372 100644
@@ -40,6 +40,11 @@ extern "C" {
 #include <sys/queue.h>
 #include <rte_dev.h>
 
+struct rte_vdev_device {
+	TAILQ_ENTRY(rte_vdev_device) next;      /**< Next attached vdev */
+	struct rte_device device;               /**< Inherit core device */
+};
+
 /** Double linked list of virtual device drivers. */
 TAILQ_HEAD(vdev_driver_list, rte_vdev_driver);
 
Signature · 1 line
2.7.4
author
#69 lore raw

PATCH v4 7/10 eal: add virtual device name helper function

In reply to Jan Blunck

This adds the rte_vdev_device_name() helper function to retrieve the rte_vdev_device name which makes moving the name of the low-level device into struct rte_device easier in the future.

---
 lib/librte_eal/common/include/rte_vdev.h | 9 +++++++++
 1 file changed, 9 insertions(+)
lib/librte_eal/common/include/rte_vdev.h +9 -0
index 8f98372..abdefab 100644
@@ -39,12 +39,21 @@ extern "C" {
 
 #include <sys/queue.h>
 #include <rte_dev.h>
+#include <rte_devargs.h>
 
 struct rte_vdev_device {
 	TAILQ_ENTRY(rte_vdev_device) next;      /**< Next attached vdev */
 	struct rte_device device;               /**< Inherit core device */
 };
 
+static inline const char *
+rte_vdev_device_name(const struct rte_vdev_device *dev)
+{
+	if (dev && dev->device.devargs)
+		return dev->device.devargs->virt.drv_name;
+	return NULL;
+}
+
 /** Double linked list of virtual device drivers. */
 TAILQ_HEAD(vdev_driver_list, rte_vdev_driver);
 
Signature · 1 line
2.7.4
author
#70 lore raw

PATCH v4 8/10 eal: add virtual device arguments helper function

In reply to Jan Blunck

This adds the rte_vdev_device_args() helper function to prepare for changing the virtual drivers probe() functions take a rte_vdev_device pointer instead of the name+args strings.

---
 lib/librte_eal/common/include/rte_vdev.h | 8 ++++++++
 1 file changed, 8 insertions(+)
lib/librte_eal/common/include/rte_vdev.h +8 -0
index abdefab..81f6beb 100644
@@ -54,6 +54,14 @@ rte_vdev_device_name(const struct rte_vdev_device *dev)
 	return NULL;
 }
 
+static inline const char *
+rte_vdev_device_args(const struct rte_vdev_device *dev)
+{
+	if (dev && dev->device.devargs)
+		return dev->device.devargs->args;
+	return "";
+}
+
 /** Double linked list of virtual device drivers. */
 TAILQ_HEAD(vdev_driver_list, rte_vdev_driver);
 
Signature · 1 line
2.7.4
author
#71 lore raw

PATCH v4 9/10 eal: make virtual bus use rte_vdev_device

In reply to Jan Blunck

This allows the virtual bus to be rescanned and probed by tracking the creation of rte_vdev_device.

---
 lib/librte_eal/common/eal_common_vdev.c | 195 +++++++++++++++++++++++++-------
 1 file changed, 155 insertions(+), 40 deletions(-)
lib/librte_eal/common/eal_common_vdev.c +155 -40
index f884c7b..d7a586b 100644
@@ -41,6 +41,7 @@
 #include <rte_vdev.h>
 #include <rte_common.h>
 #include <rte_devargs.h>
+#include <rte_memory.h>
 
 /** Double linked list of virtual device drivers. */
 TAILQ_HEAD(vdev_device_list, rte_vdev_device);
@@ -67,9 +68,12 @@ rte_eal_vdrv_unregister(struct rte_vdev_driver *driver)
 }
 
 static int
-vdev_probe_all_drivers(const char *name, const char *args)
+vdev_probe_all_drivers(struct rte_vdev_device *dev)
 {
+	const char *name = rte_vdev_device_name(dev);
+	const char *args = rte_vdev_device_args(dev);
 	struct rte_vdev_driver *driver;
+	int ret;
 
 	TAILQ_FOREACH(driver, &vdev_driver_list, next) {
 		/*
@@ -79,90 +83,202 @@ vdev_probe_all_drivers(const char *name, const char *args)
 		 * So use strncmp to compare.
 		 */
 		if (!strncmp(driver->driver.name, name,
-			    strlen(driver->driver.name)))
-			return driver->probe(name, args);
+			    strlen(driver->driver.name))) {
+			dev->device.driver = &driver->driver;
+			ret = driver->probe(name, args);
+			if (ret)
+				dev->device.driver = NULL;
+			return ret;
+		}
 	}
 
 	/* Give new names precedence over aliases. */
 	TAILQ_FOREACH(driver, &vdev_driver_list, next) {
 		if (driver->driver.alias &&
 		    !strncmp(driver->driver.alias, name,
-			    strlen(driver->driver.alias)))
-			return driver->probe(name, args);
+			    strlen(driver->driver.alias))) {
+			dev->device.driver = &driver->driver;
+			ret = driver->probe(name, args);
+			if (ret)
+				dev->device.driver = NULL;
+			return ret;
+		}
 	}
 
 	return 1;
 }
 
+static struct rte_vdev_device *
+find_vdev(const char *name)
+{
+	struct rte_vdev_device *dev;
+
+	if (!name)
+		return NULL;
+
+	TAILQ_FOREACH(dev, &vdev_device_list, next) {
+		const char *devname = rte_vdev_device_name(dev);
+		if (!strncmp(devname, name, strlen(name)))
+			return dev;
+	}
+
+	return NULL;
+}
+
+static struct rte_devargs *
+alloc_devargs(const char *name, const char *args)
+{
+	struct rte_devargs *devargs;
+	int ret;
+
+	devargs = calloc(1, sizeof(*devargs));
+	if (!devargs)
+		return NULL;
+
+	devargs->type = RTE_DEVTYPE_VIRTUAL;
+	if (args)
+		devargs->args = strdup(args);
+
+	ret = snprintf(devargs->virt.drv_name,
+			       sizeof(devargs->virt.drv_name), "%s", name);
+	if (ret < 0 || ret >= (int)sizeof(devargs->virt.drv_name)) {
+		free(devargs->args);
+		free(devargs);
+		return NULL;
+	}
+
+	return devargs;
+}
+
 int
 rte_eal_vdev_init(const char *name, const char *args)
 {
+	struct rte_vdev_device *dev;
+	struct rte_devargs *devargs;
 	int ret;
 
 	if (name == NULL)
 		return -EINVAL;
 
-	ret = vdev_probe_all_drivers(name, args);
-	if (ret  > 0)
-		RTE_LOG(ERR, EAL, "no driver found for %s\n", name);
+	dev = find_vdev(name);
+	if (dev)
+		return -EEXIST;
+
+	devargs = alloc_devargs(name, args);
+	if (!devargs)
+		return -ENOMEM;
+
+	dev = calloc(1, sizeof(*dev));
+	if (!dev) {
+		ret = -ENOMEM;
+		goto fail;
+	}
+
+	dev->device.devargs = devargs;
+	dev->device.numa_node = SOCKET_ID_ANY;
+
+	ret = vdev_probe_all_drivers(dev);
+	if (ret) {
+		if (ret > 0)
+			RTE_LOG(ERR, EAL, "no driver found for %s\n", name);
+		goto fail;
+	}
+
+	TAILQ_INSERT_TAIL(&devargs_list, devargs, next);
+
+	rte_eal_device_insert(&dev->device);
+	TAILQ_INSERT_TAIL(&vdev_device_list, dev, next);
+	return 0;
 
+fail:
+	free(devargs->args);
+	free(devargs);
+	free(dev);
 	return ret;
 }
 
 static int
-vdev_remove_driver(const char *name)
+vdev_remove_driver(struct rte_vdev_device *dev)
 {
-	struct rte_vdev_driver *driver;
+	const char *name = rte_vdev_device_name(dev);
+	const struct rte_vdev_driver *driver;
 
-	TAILQ_FOREACH(driver, &vdev_driver_list, next) {
-		/*
-		 * search a driver prefix in virtual device name.
-		 * For example, if the driver is pcap PMD, driver->name
-		 * will be "net_pcap", but "name" will be "net_pcapN".
-		 * So use strncmp to compare.
-		 */
-		if (!strncmp(driver->driver.name, name,
-			     strlen(driver->driver.name)))
-			return driver->remove(name);
-	}
-
-	/* Give new names precedence over aliases. */
-	TAILQ_FOREACH(driver, &vdev_driver_list, next) {
-		if (driver->driver.alias &&
-		    !strncmp(driver->driver.alias, name,
-			    strlen(driver->driver.alias)))
-			return driver->remove(name);
+	if (!dev->device.driver) {
+		RTE_LOG(DEBUG, EAL, "no driver attach to device %s\n", name);
+		return 1;
 	}
 
-	return 1;
+	driver = container_of(dev->device.driver, const struct rte_vdev_driver,
+		driver);
+	return driver->remove(name);
 }
 
 int
 rte_eal_vdev_uninit(const char *name)
 {
+	struct rte_vdev_device *dev;
+	struct rte_devargs *devargs;
 	int ret;
 
 	if (name == NULL)
 		return -EINVAL;
 
-	ret = vdev_remove_driver(name);
-	if (ret > 0)
-		RTE_LOG(ERR, EAL, "no driver found for %s\n", name);
+	dev = find_vdev(name);
+	if (!dev)
+		return -ENOENT;
 
-	return ret;
+	devargs = dev->device.devargs;
+
+	ret = vdev_remove_driver(dev);
+	if (ret)
+		return ret;
+
+	TAILQ_REMOVE(&vdev_device_list, dev, next);
+	rte_eal_device_remove(&dev->device);
+
+	TAILQ_REMOVE(&devargs_list, devargs, next);
+
+	free(devargs->args);
+	free(devargs);
+	free(dev);
+	return 0;
 }
 
 static int
 vdev_scan(void)
 {
-	/* for virtual devices we don't need to scan anything */
+	struct rte_vdev_device *dev;
+	struct rte_devargs *devargs;
+
+	/* for virtual devices we scan the devargs_list populated via cmdline */
+
+	TAILQ_FOREACH(devargs, &devargs_list, next) {
+
+		if (devargs->type != RTE_DEVTYPE_VIRTUAL)
+			continue;
+
+		dev = find_vdev(devargs->virt.drv_name);
+		if (dev)
+			continue;
+
+		dev = calloc(1, sizeof(*dev));
+		if (!dev)
+			return -1;
+
+		dev->device.devargs = devargs;
+		dev->device.numa_node = SOCKET_ID_ANY;
+
+		rte_eal_device_insert(&dev->device);
+		TAILQ_INSERT_TAIL(&vdev_device_list, dev, next);
+	}
+
 	return 0;
 }
 
 static int
 vdev_probe(void)
 {
-	struct rte_devargs *devargs;
+	struct rte_vdev_device *dev;
 
 	/*
 	 * Note that the dev_driver_list is populated here
@@ -171,15 +287,14 @@ vdev_probe(void)
 	 */
 
 	/* call the init function for each virtual device */
-	TAILQ_FOREACH(devargs, &devargs_list, next) {
+	TAILQ_FOREACH(dev, &vdev_device_list, next) {
 
-		if (devargs->type != RTE_DEVTYPE_VIRTUAL)
+		if (dev->device.driver)
 			continue;
 
-		if (rte_eal_vdev_init(devargs->virt.drv_name,
-				      devargs->args)) {
+		if (vdev_probe_all_drivers(dev)) {
 			RTE_LOG(ERR, EAL, "failed to initialize %s device\n",
-				devargs->virt.drv_name);
+				rte_vdev_device_name(dev));
 			return -1;
 		}
 	}
Signature · 1 line
2.7.4
#72 lore raw

Re: [PATCH v4 09/10] eal: make virtual bus use rte_vdev_device

2017-03-06 11:56, Jan Blunck:

Quoted 6 lines

This allows the virtual bus to be rescanned and probed by tracking the creation of rte_vdev_device.

There are a lot of strcmp in this patch. Maybe it should be abstracted in a "match" function. It would allow bringing new vdev rules in future.

author
#73 lore raw

Re: [PATCH v4 09/10] eal: make virtual bus use rte_vdev_device

Quoted 9 lines · Thomas Monjalon

2017-03-06 11:56, Jan Blunck:

Quoted 6 lines

This allows the virtual bus to be rescanned and probed by tracking the creation of rte_vdev_device.

There are a lot of strcmp in this patch.

Are you sure that you are referring to this patch? There is a single strcmp added here in the find_vdev() helper.

Quoted 2 lines

Maybe it should be abstracted in a "match" function. It would allow bringing new vdev rules in future.

Technically that is possible. If I remember correctly we agreed that matching based on the alias is scheduled for removal in a future release. Therefore I believe it is better to keep this in the virtual bus layer implementation instead of moving it down to the PMDs by introducing a driver specific "match" function.

author
#74 lore raw

PATCH v4 10/10 eal: make virtual driver probe and remove take rte_vdev_device

In reply to Jan Blunck

This is a preparation to embed the generic rte_device into the rte_eth_dev also for virtual devices.

---
 drivers/crypto/null/null_crypto_pmd.c     | 18 ++++++++++++------
 drivers/net/af_packet/rte_eth_af_packet.c | 11 ++++++-----
 drivers/net/bonding/rte_eth_bond_pmd.c    | 13 +++++++++----
 drivers/net/mpipe/mpipe_tilegx.c          | 10 ++++++----
 drivers/net/null/rte_eth_null.c           | 13 ++++++++-----
 drivers/net/pcap/rte_eth_pcap.c           | 12 +++++++-----
 drivers/net/ring/rte_eth_ring.c           |  9 +++++++--
 drivers/net/tap/rte_eth_tap.c             | 10 +++++++---
 drivers/net/vhost/rte_eth_vhost.c         | 10 +++++++---
 drivers/net/virtio/virtio_user_ethdev.c   | 18 +++++++-----------
 drivers/net/xenvirt/rte_eth_xenvirt.c     |  9 +++++----
 lib/librte_eal/common/eal_common_vdev.c   |  7 +++----
 lib/librte_eal/common/include/rte_vdev.h  |  4 ++--
 13 files changed, 86 insertions(+), 58 deletions(-)
drivers/crypto/null/null_crypto_pmd.c +12 -6
index ed5a9fc..51d6de0 100644
@@ -218,8 +218,7 @@ cryptodev_null_create(struct rte_crypto_vdev_init_params *init_params)
 
 /** Initialise null crypto device */
 static int
-cryptodev_null_probe(const char *name,
-		const char *input_args)
+cryptodev_null_probe(struct rte_vdev_device *dev)
 {
 	struct rte_crypto_vdev_init_params init_params = {
 		RTE_CRYPTODEV_VDEV_DEFAULT_MAX_NB_QUEUE_PAIRS,
@@ -228,10 +227,11 @@ cryptodev_null_probe(const char *name,
 		{0}
 	};
 
-	rte_cryptodev_parse_vdev_init_params(&init_params, input_args);
+	rte_cryptodev_parse_vdev_init_params(&init_params,
+		rte_vdev_device_args(dev));
 
-	RTE_LOG(INFO, PMD, "Initialising %s on NUMA node %d\n", name,
-			init_params.socket_id);
+	RTE_LOG(INFO, PMD, "Initialising %s on NUMA node %d\n",
+		rte_vdev_device_name(dev), init_params.socket_id);
 	if (init_params.name[0] != '\0')
 		RTE_LOG(INFO, PMD, "  User defined name = %s\n",
 			init_params.name);
@@ -256,9 +256,15 @@ cryptodev_null_remove(const char *name)
 	return 0;
 }
 
+static int
+cryptodev_null_remove_dev(struct rte_vdev_device *dev)
+{
+	return cryptodev_null_remove(rte_vdev_device_name(dev));
+}
+
 static struct rte_vdev_driver cryptodev_null_pmd_drv = {
 	.probe = cryptodev_null_probe,
-	.remove = cryptodev_null_remove
+	.remove = cryptodev_null_remove_dev,
 };
 
 RTE_PMD_REGISTER_VDEV(CRYPTODEV_NAME_NULL_PMD, cryptodev_null_pmd_drv);
drivers/net/af_packet/rte_eth_af_packet.c +6 -5
index 2f87553..77536e8 100644
@@ -923,8 +923,9 @@ rte_eth_from_packet(const char *name,
 }
 
 static int
-rte_pmd_af_packet_probe(const char *name, const char *params)
+rte_pmd_af_packet_probe(struct rte_vdev_device *dev)
 {
+	const char *name = rte_vdev_device_name(dev);
 	unsigned numa_node;
 	int ret = 0;
 	struct rte_kvargs *kvlist;
@@ -934,7 +935,7 @@ rte_pmd_af_packet_probe(const char *name, const char *params)
 
 	numa_node = rte_socket_id();
 
-	kvlist = rte_kvargs_parse(params, valid_arguments);
+	kvlist = rte_kvargs_parse(rte_vdev_device_args(dev), valid_arguments);
 	if (kvlist == NULL) {
 		ret = -1;
 		goto exit;
@@ -961,7 +962,7 @@ rte_pmd_af_packet_probe(const char *name, const char *params)
 }
 
 static int
-rte_pmd_af_packet_remove(const char *name)
+rte_pmd_af_packet_remove(struct rte_vdev_device *dev)
 {
 	struct rte_eth_dev *eth_dev = NULL;
 	struct pmd_internals *internals;
@@ -970,11 +971,11 @@ rte_pmd_af_packet_remove(const char *name)
 	RTE_LOG(INFO, PMD, "Closing AF_PACKET ethdev on numa socket %u\n",
 			rte_socket_id());
 
-	if (name == NULL)
+	if (dev == NULL)
 		return -1;
 
 	/* find the ethdev entry */
-	eth_dev = rte_eth_dev_allocated(name);
+	eth_dev = rte_eth_dev_allocated(rte_vdev_device_name(dev));
 	if (eth_dev == NULL)
 		return -1;
 
drivers/net/bonding/rte_eth_bond_pmd.c +9 -4
index f3ac9e2..6c03920 100644
@@ -2230,16 +2230,19 @@ const struct eth_dev_ops default_dev_ops = {
 };
 
 static int
-bond_probe(const char *name, const char *params)
+bond_probe(struct rte_vdev_device *dev)
 {
+	const char *name;
 	struct bond_dev_private *internals;
 	struct rte_kvargs *kvlist;
 	uint8_t bonding_mode, socket_id;
 	int  arg_count, port_id;
 
+	name = rte_vdev_device_name(dev);
 	RTE_LOG(INFO, EAL, "Initializing pmd_bond for %s\n", name);
 
-	kvlist = rte_kvargs_parse(params, pmd_bond_init_valid_arguments);
+	kvlist = rte_kvargs_parse(rte_vdev_device_args(dev),
+		pmd_bond_init_valid_arguments);
 	if (kvlist == NULL)
 		return -1;
 
@@ -2297,13 +2300,15 @@ bond_probe(const char *name, const char *params)
 }
 
 static int
-bond_remove(const char *name)
+bond_remove(struct rte_vdev_device *dev)
 {
+	const char *name;
 	int  ret;
 
-	if (name == NULL)
+	if (!dev)
 		return -EINVAL;
 
+	name = rte_vdev_device_name(dev);
 	RTE_LOG(INFO, EAL, "Uninitializing pmd_bond for %s\n", name);
 
 	/* free link bonding eth device */
drivers/net/mpipe/mpipe_tilegx.c +6 -4
index 60d5f81..e6f73ba 100644
@@ -1642,15 +1642,17 @@ static struct rte_vdev_driver pmd_mpipe_gbe_drv = {
 };
 
 static int
-rte_pmd_mpipe_xgbe_probe(const char *ifname, const char *params __rte_unused)
+rte_pmd_mpipe_xgbe_probe(struct rte_vdev_device *dev)
 {
-	return rte_pmd_mpipe_probe_common(&pmd_mpipe_xgbe_drv, ifname, params);
+	return rte_pmd_mpipe_probe_common(&pmd_mpipe_xgbe_drv,
+		rte_vdev_device_name(dev), rte_vdev_device_args(dev));
 }
 
 static int
-rte_pmd_mpipe_gbe_probe(const char *ifname, const char *params __rte_unused)
+rte_pmd_mpipe_gbe_probe(struct rte_vdev_device *dev)
 {
-	return rte_pmd_mpipe_probe_common(&pmd_mpipe_gbe_drv, ifname, params);
+	return rte_pmd_mpipe_probe_common(&pmd_mpipe_gbe_drv,
+		rte_vdev_device_name(dev), rte_vdev_device_args(dev));
 }
 
 RTE_PMD_REGISTER_VDEV(net_mpipe_xgbe, pmd_mpipe_xgbe_drv);
drivers/net/null/rte_eth_null.c +8 -5
index 57203e2..f4242b0 100644
@@ -608,17 +608,20 @@ get_packet_copy_arg(const char *key __rte_unused,
 }
 
 static int
-rte_pmd_null_probe(const char *name, const char *params)
+rte_pmd_null_probe(struct rte_vdev_device *dev)
 {
+	const char *name, *params;
 	unsigned numa_node;
 	unsigned packet_size = default_packet_size;
 	unsigned packet_copy = default_packet_copy;
 	struct rte_kvargs *kvlist = NULL;
 	int ret;
 
-	if (name == NULL)
+	if (!dev)
 		return -EINVAL;
 
+	name = rte_vdev_device_name(dev);
+	params = rte_vdev_device_args(dev);
 	RTE_LOG(INFO, PMD, "Initializing pmd_null for %s\n", name);
 
 	numa_node = rte_socket_id();
@@ -660,18 +663,18 @@ rte_pmd_null_probe(const char *name, const char *params)
 }
 
 static int
-rte_pmd_null_remove(const char *name)
+rte_pmd_null_remove(struct rte_vdev_device *dev)
 {
 	struct rte_eth_dev *eth_dev = NULL;
 
-	if (name == NULL)
+	if (!dev)
 		return -EINVAL;
 
 	RTE_LOG(INFO, PMD, "Closing null ethdev on numa socket %u\n",
 			rte_socket_id());
 
 	/* find the ethdev entry */
-	eth_dev = rte_eth_dev_allocated(name);
+	eth_dev = rte_eth_dev_allocated(rte_vdev_device_name(dev));
 	if (eth_dev == NULL)
 		return -1;
 
drivers/net/pcap/rte_eth_pcap.c +7 -5
index 7f0b650..ab9cde1 100644
@@ -936,8 +936,9 @@ eth_from_pcaps(const char *name, struct pmd_devargs *rx_queues,
 }
 
 static int
-pmd_pcap_probe(const char *name, const char *params)
+pmd_pcap_probe(struct rte_vdev_device *dev)
 {
+	const char *name;
 	unsigned int is_rx_pcap = 0, is_tx_pcap = 0;
 	struct rte_kvargs *kvlist;
 	struct pmd_devargs pcaps = {0};
@@ -945,13 +946,14 @@ pmd_pcap_probe(const char *name, const char *params)
 	int single_iface = 0;
 	int ret;
 
+	name = rte_vdev_device_name(dev);
 	RTE_LOG(INFO, PMD, "Initializing pmd_pcap for %s\n", name);
 
 	gettimeofday(&start_time, NULL);
 	start_cycles = rte_get_timer_cycles();
 	hz = rte_get_timer_hz();
 
-	kvlist = rte_kvargs_parse(params, valid_arguments);
+	kvlist = rte_kvargs_parse(rte_vdev_device_args(dev), valid_arguments);
 	if (kvlist == NULL)
 		return -1;
 
@@ -1035,18 +1037,18 @@ pmd_pcap_probe(const char *name, const char *params)
 }
 
 static int
-pmd_pcap_remove(const char *name)
+pmd_pcap_remove(struct rte_vdev_device *dev)
 {
 	struct rte_eth_dev *eth_dev = NULL;
 
 	RTE_LOG(INFO, PMD, "Closing pcap ethdev on numa socket %u\n",
 			rte_socket_id());
 
-	if (name == NULL)
+	if (!dev)
 		return -1;
 
 	/* reserve an ethdev entry */
-	eth_dev = rte_eth_dev_allocated(name);
+	eth_dev = rte_eth_dev_allocated(rte_vdev_device_name(dev));
 	if (eth_dev == NULL)
 		return -1;
 
drivers/net/ring/rte_eth_ring.c +7 -2
index 6f9cc1a..62606e7 100644
@@ -502,12 +502,16 @@ static int parse_kvlist (const char *key __rte_unused, const char *value, void *
 }
 
 static int
-rte_pmd_ring_probe(const char *name, const char *params)
+rte_pmd_ring_probe(struct rte_vdev_device *dev)
 {
+	const char *name, *params;
 	struct rte_kvargs *kvlist = NULL;
 	int ret = 0;
 	struct node_action_list *info = NULL;
 
+	name = rte_vdev_device_name(dev);
+	params = rte_vdev_device_args(dev);
+
 	RTE_LOG(INFO, PMD, "Initializing pmd_ring for %s\n", name);
 
 	if (params == NULL || params[0] == '\0') {
@@ -577,8 +581,9 @@ rte_pmd_ring_probe(const char *name, const char *params)
 }
 
 static int
-rte_pmd_ring_remove(const char *name)
+rte_pmd_ring_remove(struct rte_vdev_device *dev)
 {
+	const char *name = rte_vdev_device_name(dev);
 	struct rte_eth_dev *eth_dev = NULL;
 	struct pmd_internals *internals = NULL;
 	struct ring_queue *r = NULL;
drivers/net/tap/rte_eth_tap.c +7 -3
index efc4426..941150f 100644
@@ -741,13 +741,17 @@ set_interface_speed(const char *key __rte_unused,
 /* Open a TAP interface device.
  */
 static int
-rte_pmd_tap_probe(const char *name, const char *params)
+rte_pmd_tap_probe(struct rte_vdev_device *dev)
 {
+	const char *name, *params;
 	int ret;
 	struct rte_kvargs *kvlist = NULL;
 	int speed;
 	char tap_name[RTE_ETH_NAME_MAX_LEN];
 
+	name = rte_vdev_device_name(dev);
+	params = rte_vdev_device_args(dev);
+
 	speed = ETH_SPEED_NUM_10G;
 	snprintf(tap_name, sizeof(tap_name), "%s%d",
 		 DEFAULT_TAP_NAME, tap_unit++);
@@ -797,7 +801,7 @@ rte_pmd_tap_probe(const char *name, const char *params)
 /* detach a TAP device.
  */
 static int
-rte_pmd_tap_remove(const char *name)
+rte_pmd_tap_remove(struct rte_vdev_device *dev)
 {
 	struct rte_eth_dev *eth_dev = NULL;
 	struct pmd_internals *internals;
@@ -807,7 +811,7 @@ rte_pmd_tap_remove(const char *name)
 		rte_socket_id());
 
 	/* find the ethdev entry */
-	eth_dev = rte_eth_dev_allocated(name);
+	eth_dev = rte_eth_dev_allocated(rte_vdev_device_name(dev));
 	if (!eth_dev)
 		return 0;
 
drivers/net/vhost/rte_eth_vhost.c +7 -3
index e98cffd..d0d0474 100644
@@ -1156,8 +1156,9 @@ open_int(const char *key __rte_unused, const char *value, void *extra_args)
 }
 
 static int
-rte_pmd_vhost_probe(const char *name, const char *params)
+rte_pmd_vhost_probe(struct rte_vdev_device *dev)
 {
+	const char *name;
 	struct rte_kvargs *kvlist = NULL;
 	int ret = 0;
 	char *iface_name;
@@ -1166,9 +1167,10 @@ rte_pmd_vhost_probe(const char *name, const char *params)
 	int client_mode = 0;
 	int dequeue_zero_copy = 0;
 
+	name = rte_vdev_device_name(dev);
 	RTE_LOG(INFO, PMD, "Initializing pmd_vhost for %s\n", name);
 
-	kvlist = rte_kvargs_parse(params, valid_arguments);
+	kvlist = rte_kvargs_parse(rte_vdev_device_args(dev), valid_arguments);
 	if (kvlist == NULL)
 		return -1;
 
@@ -1219,11 +1221,13 @@ rte_pmd_vhost_probe(const char *name, const char *params)
 }
 
 static int
-rte_pmd_vhost_remove(const char *name)
+rte_pmd_vhost_remove(struct rte_vdev_device *dev)
 {
+	const char *name;
 	struct rte_eth_dev *eth_dev = NULL;
 	unsigned int i;
 
+	name = rte_vdev_device_name(dev);
 	RTE_LOG(INFO, PMD, "Un-Initializing pmd_vhost for %s\n", name);
 
 	/* find an ethdev entry */
drivers/net/virtio/virtio_user_ethdev.c +7 -11
index 0b226ac..42ad8a2 100644
@@ -338,7 +338,7 @@ virtio_user_eth_dev_free(struct rte_eth_dev *eth_dev)
  * Returns 0 on success.
  */
 static int
-virtio_user_pmd_probe(const char *name, const char *params)
+virtio_user_pmd_probe(struct rte_vdev_device *dev)
 {
 	struct rte_kvargs *kvlist = NULL;
 	struct rte_eth_dev *eth_dev;
@@ -350,13 +350,7 @@ virtio_user_pmd_probe(const char *name, const char *params)
 	char *mac_addr = NULL;
 	int ret = -1;
 
-	if (!params || params[0] == '\0') {
-		PMD_INIT_LOG(ERR, "arg %s is mandatory for virtio_user",
-			  VIRTIO_USER_ARG_QUEUE_SIZE);
-		goto end;
-	}
-
-	kvlist = rte_kvargs_parse(params, valid_args);
+	kvlist = rte_kvargs_parse(rte_vdev_device_args(dev), valid_args);
 	if (!kvlist) {
 		PMD_INIT_LOG(ERR, "error when parsing param");
 		goto end;
@@ -418,7 +412,7 @@ virtio_user_pmd_probe(const char *name, const char *params)
 		goto end;
 	}
 
-	eth_dev = virtio_user_eth_dev_alloc(name);
+	eth_dev = virtio_user_eth_dev_alloc(rte_vdev_device_name(dev));
 	if (!eth_dev) {
 		PMD_INIT_LOG(ERR, "virtio_user fails to alloc device");
 		goto end;
@@ -452,15 +446,17 @@ virtio_user_pmd_probe(const char *name, const char *params)
 
 /** Called by rte_eth_dev_detach() */
 static int
-virtio_user_pmd_remove(const char *name)
+virtio_user_pmd_remove(struct rte_vdev_device *vdev)
 {
+	const char *name;
 	struct rte_eth_dev *eth_dev;
 	struct virtio_hw *hw;
 	struct virtio_user_dev *dev;
 
-	if (!name)
+	if (!vdev)
 		return -EINVAL;
 
+	name = rte_vdev_device_name(vdev);
 	PMD_DRV_LOG(INFO, "Un-Initializing %s", name);
 	eth_dev = rte_eth_dev_allocated(name);
 	if (!eth_dev)
drivers/net/xenvirt/rte_eth_xenvirt.c +5 -4
index 19bc09a..6ec8c08 100644
@@ -726,7 +726,7 @@ eth_dev_xenvirt_free(const char *name, const unsigned numa_node)
 
 /*TODO: Support multiple process model */
 static int
-rte_pmd_xenvirt_probe(const char *name, const char *params)
+rte_pmd_xenvirt_probe(struct rte_vdev_device *dev)
 {
 	if (virtio_idx == 0) {
 		if (xenstore_init() != 0) {
@@ -738,14 +738,15 @@ rte_pmd_xenvirt_probe(const char *name, const char *params)
 			return -1;
 		}
 	}
-	eth_dev_xenvirt_create(name, params, rte_socket_id(), DEV_CREATE);
+	eth_dev_xenvirt_create(rte_vdev_device_name(dev),
+		rte_vdev_device_args(dev), rte_socket_id(), DEV_CREATE);
 	return 0;
 }
 
 static int
-rte_pmd_xenvirt_remove(const char *name)
+rte_pmd_xenvirt_remove(struct rte_vdev_device *dev)
 {
-	eth_dev_xenvirt_free(name, rte_socket_id());
+	eth_dev_xenvirt_free(rte_vdev_device_name(dev), rte_socket_id());
 
 	if (virtio_idx == 0) {
 		if (xenstore_uninit() != 0)
lib/librte_eal/common/eal_common_vdev.c +3 -4
index d7a586b..58e9fed 100644
@@ -71,7 +71,6 @@ static int
 vdev_probe_all_drivers(struct rte_vdev_device *dev)
 {
 	const char *name = rte_vdev_device_name(dev);
-	const char *args = rte_vdev_device_args(dev);
 	struct rte_vdev_driver *driver;
 	int ret;
 
@@ -85,7 +84,7 @@ vdev_probe_all_drivers(struct rte_vdev_device *dev)
 		if (!strncmp(driver->driver.name, name,
 			    strlen(driver->driver.name))) {
 			dev->device.driver = &driver->driver;
-			ret = driver->probe(name, args);
+			ret = driver->probe(dev);
 			if (ret)
 				dev->device.driver = NULL;
 			return ret;
@@ -98,7 +97,7 @@ vdev_probe_all_drivers(struct rte_vdev_device *dev)
 		    !strncmp(driver->driver.alias, name,
 			    strlen(driver->driver.alias))) {
 			dev->device.driver = &driver->driver;
-			ret = driver->probe(name, args);
+			ret = driver->probe(dev);
 			if (ret)
 				dev->device.driver = NULL;
 			return ret;
@@ -210,7 +209,7 @@ vdev_remove_driver(struct rte_vdev_device *dev)
 
 	driver = container_of(dev->device.driver, const struct rte_vdev_driver,
 		driver);
-	return driver->remove(name);
+	return driver->remove(dev);
 }
 
 int
lib/librte_eal/common/include/rte_vdev.h +2 -2
index 81f6beb..8db2c00 100644
@@ -68,12 +68,12 @@ TAILQ_HEAD(vdev_driver_list, rte_vdev_driver);
 /**
  * Probe function called for each virtual device driver once.
  */
-typedef int (rte_vdev_probe_t)(const char *name, const char *args);
+typedef int (rte_vdev_probe_t)(struct rte_vdev_device *dev);
 
 /**
  * Remove function called for each virtual device driver once.
  */
-typedef int (rte_vdev_remove_t)(const char *name);
+typedef int (rte_vdev_remove_t)(struct rte_vdev_device *dev);
 
 /**
  * A virtual device driver abstraction.
Signature · 1 line
2.7.4
#75 lore raw
In reply to Jan Blunck

2017-03-06 11:56, Jan Blunck:

Quoted 25 lines

Jan Blunck (10):
eal: probe legacy PCI devices before other bus devices
eal: probe new virtual bus after other bus devices
eal: move virtual device probing into a bus
eal: remove unused rte_eal_dev_init()
eal: Refactor vdev driver probe/remove
eal: add struct rte_vdev_device
eal: add virtual device name helper function
eal: add virtual device arguments helper function
eal: make virtual bus use rte_vdev_device
eal: make virtual driver probe and remove take rte_vdev_device

 drivers/crypto/null/null_crypto_pmd.c           |  18 +-
 drivers/net/af_packet/rte_eth_af_packet.c       |  11 +-
 drivers/net/bonding/rte_eth_bond_pmd.c          |  13 +-
 drivers/net/mpipe/mpipe_tilegx.c                |  10 +-
 drivers/net/null/rte_eth_null.c                 |  13 +-
 drivers/net/pcap/rte_eth_pcap.c                 |  12 +-
 drivers/net/ring/rte_eth_ring.c                 |   9 +-
 drivers/net/tap/rte_eth_tap.c                   |  10 +-
 drivers/net/vhost/rte_eth_vhost.c               |  10 +-
 drivers/net/virtio/virtio_user_ethdev.c         |  18 +-
 drivers/net/xenvirt/rte_eth_xenvirt.c           |   9 +-
 lib/librte_eal/bsdapp/eal/eal.c                 |   9 +-
 lib/librte_eal/bsdapp/eal/rte_eal_version.map   |   1 -
Quoted 8 lines
 lib/librte_eal/common/eal_common_bus.c          |  16 +-
 lib/librte_eal/common/eal_common_dev.c          |  28 ---
 lib/librte_eal/common/eal_common_vdev.c         | 245 +++++++++++++++++++++---
 lib/librte_eal/common/include/rte_dev.h         |   5 -
 lib/librte_eal/common/include/rte_vdev.h        |  26 ++-
 lib/librte_eal/linuxapp/eal/eal.c               |   9 +-
 lib/librte_eal/linuxapp/eal/rte_eal_version.map |   1 -
 20 files changed, 341 insertions(+), 132 deletions(-)

When it will be merged, it would be nice to move the vdev bus files to drivers/bus/vdev/.

author
#76 lore raw
Quoted 35 lines · Thomas Monjalon

2017-03-06 11:56, Jan Blunck:

Quoted 25 lines

Jan Blunck (10):
eal: probe legacy PCI devices before other bus devices
eal: probe new virtual bus after other bus devices
eal: move virtual device probing into a bus
eal: remove unused rte_eal_dev_init()
eal: Refactor vdev driver probe/remove
eal: add struct rte_vdev_device
eal: add virtual device name helper function
eal: add virtual device arguments helper function
eal: make virtual bus use rte_vdev_device
eal: make virtual driver probe and remove take rte_vdev_device

 drivers/crypto/null/null_crypto_pmd.c           |  18 +-
 drivers/net/af_packet/rte_eth_af_packet.c       |  11 +-
 drivers/net/bonding/rte_eth_bond_pmd.c          |  13 +-
 drivers/net/mpipe/mpipe_tilegx.c                |  10 +-
 drivers/net/null/rte_eth_null.c                 |  13 +-
 drivers/net/pcap/rte_eth_pcap.c                 |  12 +-
 drivers/net/ring/rte_eth_ring.c                 |   9 +-
 drivers/net/tap/rte_eth_tap.c                   |  10 +-
 drivers/net/vhost/rte_eth_vhost.c               |  10 +-
 drivers/net/virtio/virtio_user_ethdev.c         |  18 +-
 drivers/net/xenvirt/rte_eth_xenvirt.c           |   9 +-
 lib/librte_eal/bsdapp/eal/eal.c                 |   9 +-
 lib/librte_eal/bsdapp/eal/rte_eal_version.map   |   1 -
Quoted 8 lines
 lib/librte_eal/common/eal_common_bus.c          |  16 +-
 lib/librte_eal/common/eal_common_dev.c          |  28 ---
 lib/librte_eal/common/eal_common_vdev.c         | 245 +++++++++++++++++++++---
 lib/librte_eal/common/include/rte_dev.h         |   5 -
 lib/librte_eal/common/include/rte_vdev.h        |  26 ++-
 lib/librte_eal/linuxapp/eal/eal.c               |   9 +-
 lib/librte_eal/linuxapp/eal/rte_eal_version.map |   1 -
 20 files changed, 341 insertions(+), 132 deletions(-)
Quoted 2 lines

When it will be merged, it would be nice to move the vdev bus files to drivers/bus/vdev/.

Correct. I'll send a follow up which is moving the code to the new path.

#77 lore raw

v5 cover Rework vdev probing to use rte_bus infrastructure

In reply to Jan Blunck

I have rebased the work done by Jan to introduce the virtual device subsystem using the new rte_bus API.
I also fixed a few outstanding compilation issues, related to PMDs introduced during this release.
Additionally, a few virtual devices had not been ported to use the new rte_vdev_device that had been introduced in previous versions.

This patchset depends on:
http://dpdk.org/dev/patchwork/patch/20416/
http://dpdk.org/dev/patchwork/patch/20417/

Changes since version 4:
* Fix compilation issues for several virtual devices

Gaetan Rivet (3):
net/kni: use generic vdev for probe and remove
crypto: use generic vdev for probe and remove
event: use generic vdev for probe and remove

Jan Blunck (9):
eal: probe new virtual bus after other bus devices
eal: move virtual device probing into a bus
eal: remove unused rte_eal_dev_init()
eal: Refactor vdev driver probe/remove
eal: add struct rte_vdev_device
eal: add virtual device name helper function
eal: add virtual device arguments helper function
eal: make virtual bus use rte_vdev_device
eal: make virtual driver probe and remove take rte_vdev_device

 drivers/crypto/aesni_gcm/aesni_gcm_pmd.c        |  20 +-
 drivers/crypto/aesni_mb/rte_aesni_mb_pmd.c      |  21 +-
 drivers/crypto/armv8/rte_armv8_pmd.c            |  21 +-
 drivers/crypto/kasumi/rte_kasumi_pmd.c          |  22 +-
 drivers/crypto/null/null_crypto_pmd.c           |  18 +-
 drivers/crypto/openssl/rte_openssl_pmd.c        |  22 +-
 drivers/crypto/scheduler/scheduler_pmd.c        |  17 +-
 drivers/crypto/snow3g/rte_snow3g_pmd.c          |  22 +-
 drivers/crypto/zuc/rte_zuc_pmd.c                |  22 +-
 drivers/event/octeontx/ssovf_evdev.c            |  11 +-
 drivers/event/skeleton/skeleton_eventdev.c      |  10 +-
 drivers/event/sw/sw_evdev.c                     |  11 +-
 drivers/net/af_packet/rte_eth_af_packet.c       |  11 +-
 drivers/net/bonding/rte_eth_bond_pmd.c          |  13 +-
 drivers/net/kni/rte_eth_kni.c                   |  12 +-
 drivers/net/null/rte_eth_null.c                 |  13 +-
 drivers/net/pcap/rte_eth_pcap.c                 |  12 +-
 drivers/net/ring/rte_eth_ring.c                 |   9 +-
 drivers/net/tap/rte_eth_tap.c                   |  10 +-
 drivers/net/vhost/rte_eth_vhost.c               |  10 +-
 drivers/net/virtio/virtio_user_ethdev.c         |  18 +-
 drivers/net/xenvirt/rte_eth_xenvirt.c           |   9 +-
 lib/librte_eal/bsdapp/eal/eal.c                 |   3 -
 lib/librte_eal/bsdapp/eal/rte_eal_version.map   |   1 -
 lib/librte_eal/common/eal_common_bus.c          |  16 +-
 lib/librte_eal/common/eal_common_dev.c          |  29 ---
 lib/librte_eal/common/eal_common_vdev.c         | 262 +++++++++++++++++++++---
 lib/librte_eal/common/include/rte_dev.h         |   5 -
 lib/librte_eal/common/include/rte_vdev.h        |  26 ++-
 lib/librte_eal/linuxapp/eal/eal.c               |   3 -
 lib/librte_eal/linuxapp/eal/rte_eal_version.map |   1 -
 31 files changed, 492 insertions(+), 188 deletions(-)
Signature · 1 line
2.1.4
#78 lore raw

PATCH v5 1/12 eal: probe new virtual bus after other bus devices

From: Jan Blunck <[email protected]>

Also see commit f4ce209a8ce5 ("eal: postpone vdev initialization").

---
 lib/librte_eal/common/eal_common_bus.c | 16 +++++++++++++++-
 1 file changed, 15 insertions(+), 1 deletion(-)
lib/librte_eal/common/eal_common_bus.c +15 -1
index 4638e78..8f9baf8 100644
@@ -86,9 +86,14 @@ int
 rte_bus_probe(void)
 {
 	int ret;
-	struct rte_bus *bus;
+	struct rte_bus *bus, *vbus = NULL;
 
 	TAILQ_FOREACH(bus, &rte_bus_list, next) {
+		if (!strcmp(bus->name, "virtual")) {
+			vbus = bus;
+			continue;
+		}
+
 		ret = bus->probe();
 		if (ret) {
 			RTE_LOG(ERR, EAL, "Bus (%s) probe failed.\n",
@@ -97,6 +102,15 @@ rte_bus_probe(void)
 		}
 	}
 
+	if (vbus) {
+		ret = vbus->probe();
+		if (ret) {
+			RTE_LOG(ERR, EAL, "Bus (%s) probe failed.\n",
+				vbus->name);
+			return ret;
+		}
+	}
+
 	return 0;
 }
 
Signature · 1 line
2.1.4
#79 lore raw

PATCH v5 2/12 eal: move virtual device probing into a bus

In reply to Gaetan Rivet

From: Jan Blunck <[email protected]>

This is a refactoring of the virtual device probing which moves into into a proper bus structure.

---
 lib/librte_eal/common/eal_common_dev.c  | 25 +-------------
 lib/librte_eal/common/eal_common_vdev.c | 61 +++++++++++++++++++++++++++++++++
 2 files changed, 62 insertions(+), 24 deletions(-)
lib/librte_eal/common/eal_common_dev.c +1 -24
index d7d1f3d..522aad3 100644
@@ -81,30 +81,7 @@ void rte_eal_device_remove(struct rte_device *dev)
 int
 rte_eal_dev_init(void)
 {
-	struct rte_devargs *devargs;
-	int ret = 0;
-
-	/*
-	 * Note that the dev_driver_list is populated here
-	 * from calls made to rte_eal_driver_register from constructor functions
-	 * embedded into PMD modules via the RTE_PMD_REGISTER_VDEV macro
-	 */
-
-	/* call the init function for each virtual device */
-	TAILQ_FOREACH(devargs, &devargs_list, next) {
-
-		if (devargs->type != RTE_DEVTYPE_VIRTUAL)
-			continue;
-
-		if (rte_eal_vdev_init(devargs->virt.drv_name,
-					devargs->args)) {
-			RTE_LOG(ERR, EAL, "failed to initialize %s device\n",
-					devargs->virt.drv_name);
-			ret = -1;
-		}
-	}
-
-	return ret;
+	return 0;
 }
 
 int rte_eal_dev_attach(const char *name, const char *devargs)
lib/librte_eal/common/eal_common_vdev.c +61 -0

80 lines not on this page · raw message

Signature · 1 line
2.1.4
#80 lore raw

PATCH v5 3/12 eal: remove unused rte_eal_dev_init()

In reply to Gaetan Rivet

From: Jan Blunck <[email protected]>

---
 lib/librte_eal/bsdapp/eal/eal.c                 | 3 ---
 lib/librte_eal/bsdapp/eal/rte_eal_version.map   | 1 -
 lib/librte_eal/common/eal_common_dev.c          | 6 ------
 lib/librte_eal/common/include/rte_dev.h         | 5 -----
 lib/librte_eal/linuxapp/eal/eal.c               | 3 ---
 lib/librte_eal/linuxapp/eal/rte_eal_version.map | 1 -
 6 files changed, 19 deletions(-)
lib/librte_eal/bsdapp/eal/eal.c +0 -3
index 7321ac6..41aa0b5 100644
@@ -660,9 +660,6 @@ rte_eal_init(int argc, char **argv)
 		return -1;
 	}
 
-	if (rte_eal_dev_init() < 0)
-		rte_eal_init_alert("Cannot init pmd devices\n");
-
 	rte_eal_mcfg_complete();
 
 	return fctret;
lib/librte_eal/bsdapp/eal/rte_eal_version.map +0 -1
index ca12d89..1bb3c9e 100644
@@ -20,7 +20,6 @@ DPDK_2.0 {
 	rte_dump_tailq;
 	rte_eal_alarm_cancel;
 	rte_eal_alarm_set;
-	rte_eal_dev_init;
 	rte_eal_devargs_add;
 	rte_eal_devargs_dump;
 	rte_eal_devargs_type_count;
lib/librte_eal/common/eal_common_dev.c +0 -6
index 522aad3..01e37c4 100644
@@ -78,12 +78,6 @@ void rte_eal_device_remove(struct rte_device *dev)
 	TAILQ_REMOVE(&dev_device_list, dev, next);
 }
 
-int
-rte_eal_dev_init(void)
-{
-	return 0;
-}
-
 int rte_eal_dev_attach(const char *name, const char *devargs)
 {
 	int ret = 1;
lib/librte_eal/common/include/rte_dev.h +0 -5
index b17791f..4251099 100644
@@ -171,11 +171,6 @@ void rte_eal_driver_register(struct rte_driver *driver);
 void rte_eal_driver_unregister(struct rte_driver *driver);
 
 /**
- * Initalize all the registered drivers in this process
- */
-int rte_eal_dev_init(void);
-
-/**
  * Initialize a driver specified by name.
  *
  * @param name
lib/librte_eal/linuxapp/eal/eal.c +0 -3
index 7cf33d6..a869ee3 100644
@@ -939,9 +939,6 @@ rte_eal_init(int argc, char **argv)
 		return -1;
 	}
 
-	if (rte_eal_dev_init() < 0)
-		rte_eal_init_alert("Cannot init pmd devices\n");
-
 	rte_eal_mcfg_complete();
 
 	return fctret;
lib/librte_eal/linuxapp/eal/rte_eal_version.map +0 -1
index 94da1e7..dbc419b 100644
@@ -20,7 +20,6 @@ DPDK_2.0 {
 	rte_dump_tailq;
 	rte_eal_alarm_cancel;
 	rte_eal_alarm_set;
-	rte_eal_dev_init;
 	rte_eal_devargs_add;
 	rte_eal_devargs_dump;
 	rte_eal_devargs_type_count;
Signature · 1 line
2.1.4
#81 lore raw

PATCH v5 4/12 eal: Refactor vdev driver probe/remove

In reply to Gaetan Rivet

From: Jan Blunck <[email protected]>

This is a preparation for the introduction of the struct rte_vdev_device.

---
 lib/librte_eal/common/eal_common_vdev.c | 44 ++++++++++++++++++++++++---------
 1 file changed, 33 insertions(+), 11 deletions(-)
lib/librte_eal/common/eal_common_vdev.c +33 -11
index a94c4c6..c255073 100644
@@ -66,14 +66,11 @@ rte_eal_vdrv_unregister(struct rte_vdev_driver *driver)
 	TAILQ_REMOVE(&vdev_driver_list, driver, next);
 }
 
-int
-rte_eal_vdev_init(const char *name, const char *args)
+static int
+vdev_probe_all_drivers(const char *name, const char *args)
 {
 	struct rte_vdev_driver *driver;
 
-	if (name == NULL)
-		return -EINVAL;
-
 	TAILQ_FOREACH(driver, &vdev_driver_list, next) {
 		/*
 		 * search a driver prefix in virtual device name.
@@ -94,18 +91,29 @@ rte_eal_vdev_init(const char *name, const char *args)
 			return driver->probe(name, args);
 	}
 
-	RTE_LOG(ERR, EAL, "no driver found for %s\n", name);
-	return -EINVAL;
+	return 1;
 }
 
 int
-rte_eal_vdev_uninit(const char *name)
+rte_eal_vdev_init(const char *name, const char *args)
 {
-	struct rte_vdev_driver *driver;
+	int ret;
 
 	if (name == NULL)
 		return -EINVAL;
 
+	ret = vdev_probe_all_drivers(name, args);
+	if (ret  > 0)
+		RTE_LOG(ERR, EAL, "no driver found for %s\n", name);
+
+	return ret;
+}
+
+static int
+vdev_remove_driver(const char *name)
+{
+	struct rte_vdev_driver *driver;
+
 	TAILQ_FOREACH(driver, &vdev_driver_list, next) {
 		/*
 		 * search a driver prefix in virtual device name.
@@ -126,8 +134,22 @@ rte_eal_vdev_uninit(const char *name)
 			return driver->remove(name);
 	}
 
-	RTE_LOG(ERR, EAL, "no driver found for %s\n", name);
-	return -EINVAL;
+	return 1;
+}
+
+int
+rte_eal_vdev_uninit(const char *name)
+{
+	int ret;
+
+	if (name == NULL)
+		return -EINVAL;
+
+	ret = vdev_remove_driver(name);
+	if (ret > 0)
+		RTE_LOG(ERR, EAL, "no driver found for %s\n", name);
+
+	return ret;
 }
 
 static int
Signature · 1 line
2.1.4
#82 lore raw

PATCH v5 5/12 eal: add struct rte_vdev_device

In reply to Gaetan Rivet

From: Jan Blunck <[email protected]>

This adds the rte_vdev_device structure which embeds a generic rte_device.

---
 lib/librte_eal/common/eal_common_vdev.c  | 5 +++++
 lib/librte_eal/common/include/rte_vdev.h | 5 +++++
 2 files changed, 10 insertions(+)
lib/librte_eal/common/eal_common_vdev.c +5 -0
index c255073..e3a75fd 100644
@@ -43,6 +43,11 @@
 #include <rte_common.h>
 #include <rte_devargs.h>
 
+/** Double linked list of virtual device drivers. */
+TAILQ_HEAD(vdev_device_list, rte_vdev_device);
+
+static struct vdev_device_list vdev_device_list =
+	TAILQ_HEAD_INITIALIZER(vdev_device_list);
 struct vdev_driver_list vdev_driver_list =
 	TAILQ_HEAD_INITIALIZER(vdev_driver_list);
 
lib/librte_eal/common/include/rte_vdev.h +5 -0
index 784e837..8f98372 100644
@@ -40,6 +40,11 @@ extern "C" {
 #include <sys/queue.h>
 #include <rte_dev.h>
 
+struct rte_vdev_device {
+	TAILQ_ENTRY(rte_vdev_device) next;      /**< Next attached vdev */
+	struct rte_device device;               /**< Inherit core device */
+};
+
 /** Double linked list of virtual device drivers. */
 TAILQ_HEAD(vdev_driver_list, rte_vdev_driver);
 
Signature · 1 line
2.1.4
#83 lore raw

PATCH v5 6/12 eal: add virtual device name helper function

In reply to Gaetan Rivet

From: Jan Blunck <[email protected]>

This adds the rte_vdev_device_name() helper function to retrieve the rte_vdev_device name which makes moving the name of the low-level device into struct rte_device easier in the future.

---
 lib/librte_eal/common/include/rte_vdev.h | 9 +++++++++
 1 file changed, 9 insertions(+)
lib/librte_eal/common/include/rte_vdev.h +9 -0
index 8f98372..abdefab 100644
@@ -39,12 +39,21 @@ extern "C" {
 
 #include <sys/queue.h>
 #include <rte_dev.h>
+#include <rte_devargs.h>
 
 struct rte_vdev_device {
 	TAILQ_ENTRY(rte_vdev_device) next;      /**< Next attached vdev */
 	struct rte_device device;               /**< Inherit core device */
 };
 
+static inline const char *
+rte_vdev_device_name(const struct rte_vdev_device *dev)
+{
+	if (dev && dev->device.devargs)
+		return dev->device.devargs->virt.drv_name;
+	return NULL;
+}
+
 /** Double linked list of virtual device drivers. */
 TAILQ_HEAD(vdev_driver_list, rte_vdev_driver);
 
Signature · 1 line
2.1.4
#84 lore raw

PATCH v5 7/12 eal: add virtual device arguments helper function

In reply to Gaetan Rivet

From: Jan Blunck <[email protected]>

This adds the rte_vdev_device_args() helper function to prepare for changing the virtual drivers probe() functions take a rte_vdev_device pointer instead of the name+args strings.

---
 lib/librte_eal/common/include/rte_vdev.h | 8 ++++++++
 1 file changed, 8 insertions(+)
lib/librte_eal/common/include/rte_vdev.h +8 -0
index abdefab..81f6beb 100644
@@ -54,6 +54,14 @@ rte_vdev_device_name(const struct rte_vdev_device *dev)
 	return NULL;
 }
 
+static inline const char *
+rte_vdev_device_args(const struct rte_vdev_device *dev)
+{
+	if (dev && dev->device.devargs)
+		return dev->device.devargs->args;
+	return "";
+}
+
 /** Double linked list of virtual device drivers. */
 TAILQ_HEAD(vdev_driver_list, rte_vdev_driver);
 
Signature · 1 line
2.1.4
#85 lore raw

PATCH v5 8/12 eal: make virtual bus use rte_vdev_device

In reply to Gaetan Rivet

From: Jan Blunck <[email protected]>

This allows the virtual bus to be rescanned and probed by tracking the creation of rte_vdev_device.

---
 lib/librte_eal/common/eal_common_vdev.c | 195 +++++++++++++++++++++++++-------
 1 file changed, 155 insertions(+), 40 deletions(-)
lib/librte_eal/common/eal_common_vdev.c +155 -40
index e3a75fd..70da608 100644
@@ -42,6 +42,7 @@
 #include <rte_vdev.h>
 #include <rte_common.h>
 #include <rte_devargs.h>
+#include <rte_memory.h>
 
 /** Double linked list of virtual device drivers. */
 TAILQ_HEAD(vdev_device_list, rte_vdev_device);
@@ -72,9 +73,12 @@ rte_eal_vdrv_unregister(struct rte_vdev_driver *driver)
 }
 
 static int
-vdev_probe_all_drivers(const char *name, const char *args)
+vdev_probe_all_drivers(struct rte_vdev_device *dev)
 {
+	const char *name = rte_vdev_device_name(dev);
+	const char *args = rte_vdev_device_args(dev);
 	struct rte_vdev_driver *driver;
+	int ret;
 
 	TAILQ_FOREACH(driver, &vdev_driver_list, next) {
 		/*
@@ -84,90 +88,202 @@ vdev_probe_all_drivers(const char *name, const char *args)
 		 * So use strncmp to compare.
 		 */
 		if (!strncmp(driver->driver.name, name,
-			    strlen(driver->driver.name)))
-			return driver->probe(name, args);
+			    strlen(driver->driver.name))) {
+			dev->device.driver = &driver->driver;
+			ret = driver->probe(name, args);
+			if (ret)
+				dev->device.driver = NULL;
+			return ret;
+		}
 	}
 
 	/* Give new names precedence over aliases. */
 	TAILQ_FOREACH(driver, &vdev_driver_list, next) {
 		if (driver->driver.alias &&
 		    !strncmp(driver->driver.alias, name,
-			    strlen(driver->driver.alias)))
-			return driver->probe(name, args);
+			    strlen(driver->driver.alias))) {
+			dev->device.driver = &driver->driver;
+			ret = driver->probe(name, args);
+			if (ret)
+				dev->device.driver = NULL;
+			return ret;
+		}
 	}
 
 	return 1;
 }
 
+static struct rte_vdev_device *
+find_vdev(const char *name)
+{
+	struct rte_vdev_device *dev;
+
+	if (!name)
+		return NULL;
+
+	TAILQ_FOREACH(dev, &vdev_device_list, next) {
+		const char *devname = rte_vdev_device_name(dev);
+		if (!strncmp(devname, name, strlen(name)))
+			return dev;
+	}
+
+	return NULL;
+}
+
+static struct rte_devargs *
+alloc_devargs(const char *name, const char *args)
+{
+	struct rte_devargs *devargs;
+	int ret;
+
+	devargs = calloc(1, sizeof(*devargs));
+	if (!devargs)
+		return NULL;
+
+	devargs->type = RTE_DEVTYPE_VIRTUAL;
+	if (args)
+		devargs->args = strdup(args);
+
+	ret = snprintf(devargs->virt.drv_name,
+			       sizeof(devargs->virt.drv_name), "%s", name);
+	if (ret < 0 || ret >= (int)sizeof(devargs->virt.drv_name)) {
+		free(devargs->args);
+		free(devargs);
+		return NULL;
+	}
+
+	return devargs;
+}
+
 int
 rte_eal_vdev_init(const char *name, const char *args)
 {
+	struct rte_vdev_device *dev;
+	struct rte_devargs *devargs;
 	int ret;
 
 	if (name == NULL)
 		return -EINVAL;
 
-	ret = vdev_probe_all_drivers(name, args);
-	if (ret  > 0)
-		RTE_LOG(ERR, EAL, "no driver found for %s\n", name);
+	dev = find_vdev(name);
+	if (dev)
+		return -EEXIST;
+
+	devargs = alloc_devargs(name, args);
+	if (!devargs)
+		return -ENOMEM;
+
+	dev = calloc(1, sizeof(*dev));
+	if (!dev) {
+		ret = -ENOMEM;
+		goto fail;
+	}
+
+	dev->device.devargs = devargs;
+	dev->device.numa_node = SOCKET_ID_ANY;
+
+	ret = vdev_probe_all_drivers(dev);
+	if (ret) {
+		if (ret > 0)
+			RTE_LOG(ERR, EAL, "no driver found for %s\n", name);
+		goto fail;
+	}
+
+	TAILQ_INSERT_TAIL(&devargs_list, devargs, next);
+
+	rte_eal_device_insert(&dev->device);
+	TAILQ_INSERT_TAIL(&vdev_device_list, dev, next);
+	return 0;
 
+fail:
+	free(devargs->args);
+	free(devargs);
+	free(dev);
 	return ret;
 }
 
 static int
-vdev_remove_driver(const char *name)
+vdev_remove_driver(struct rte_vdev_device *dev)
 {
-	struct rte_vdev_driver *driver;
+	const char *name = rte_vdev_device_name(dev);
+	const struct rte_vdev_driver *driver;
 
-	TAILQ_FOREACH(driver, &vdev_driver_list, next) {
-		/*
-		 * search a driver prefix in virtual device name.
-		 * For example, if the driver is pcap PMD, driver->name
-		 * will be "net_pcap", but "name" will be "net_pcapN".
-		 * So use strncmp to compare.
-		 */
-		if (!strncmp(driver->driver.name, name,
-			     strlen(driver->driver.name)))
-			return driver->remove(name);
-	}
-
-	/* Give new names precedence over aliases. */
-	TAILQ_FOREACH(driver, &vdev_driver_list, next) {
-		if (driver->driver.alias &&
-		    !strncmp(driver->driver.alias, name,
-			    strlen(driver->driver.alias)))
-			return driver->remove(name);
+	if (!dev->device.driver) {
+		RTE_LOG(DEBUG, EAL, "no driver attach to device %s\n", name);
+		return 1;
 	}
 
-	return 1;
+	driver = container_of(dev->device.driver, const struct rte_vdev_driver,
+		driver);
+	return driver->remove(name);
 }
 
 int
 rte_eal_vdev_uninit(const char *name)
 {
+	struct rte_vdev_device *dev;
+	struct rte_devargs *devargs;
 	int ret;
 
 	if (name == NULL)
 		return -EINVAL;
 
-	ret = vdev_remove_driver(name);
-	if (ret > 0)
-		RTE_LOG(ERR, EAL, "no driver found for %s\n", name);
+	dev = find_vdev(name);
+	if (!dev)
+		return -ENOENT;
 
-	return ret;
+	devargs = dev->device.devargs;
+
+	ret = vdev_remove_driver(dev);
+	if (ret)
+		return ret;
+
+	TAILQ_REMOVE(&vdev_device_list, dev, next);
+	rte_eal_device_remove(&dev->device);
+
+	TAILQ_REMOVE(&devargs_list, devargs, next);
+
+	free(devargs->args);
+	free(devargs);
+	free(dev);
+	return 0;
 }
 
 static int
 vdev_scan(void)
 {
-	/* for virtual devices we don't need to scan anything */
+	struct rte_vdev_device *dev;
+	struct rte_devargs *devargs;
+
+	/* for virtual devices we scan the devargs_list populated via cmdline */
+
+	TAILQ_FOREACH(devargs, &devargs_list, next) {
+
+		if (devargs->type != RTE_DEVTYPE_VIRTUAL)
+			continue;
+
+		dev = find_vdev(devargs->virt.drv_name);
+		if (dev)
+			continue;
+
+		dev = calloc(1, sizeof(*dev));
+		if (!dev)
+			return -1;
+
+		dev->device.devargs = devargs;
+		dev->device.numa_node = SOCKET_ID_ANY;
+
+		rte_eal_device_insert(&dev->device);
+		TAILQ_INSERT_TAIL(&vdev_device_list, dev, next);
+	}
+
 	return 0;
 }
 
 static int
 vdev_probe(void)
 {
-	struct rte_devargs *devargs;
+	struct rte_vdev_device *dev;
 
 	/*
 	 * Note that the dev_driver_list is populated here
@@ -176,15 +292,14 @@ vdev_probe(void)
 	 */
 
 	/* call the init function for each virtual device */
-	TAILQ_FOREACH(devargs, &devargs_list, next) {
+	TAILQ_FOREACH(dev, &vdev_device_list, next) {
 
-		if (devargs->type != RTE_DEVTYPE_VIRTUAL)
+		if (dev->device.driver)
 			continue;
 
-		if (rte_eal_vdev_init(devargs->virt.drv_name,
-				      devargs->args)) {
+		if (vdev_probe_all_drivers(dev)) {
 			RTE_LOG(ERR, EAL, "failed to initialize %s device\n",
-				devargs->virt.drv_name);
+				rte_vdev_device_name(dev));
 			return -1;
 		}
 	}
Signature · 1 line
2.1.4
#86 lore raw

PATCH v5 9/12 eal: make virtual driver probe and remove take rte_vdev_device

In reply to Gaetan Rivet

From: Jan Blunck <[email protected]>

This is a preparation to embed the generic rte_device into the rte_eth_dev also for virtual devices.

---
 drivers/crypto/null/null_crypto_pmd.c     | 18 ++++++++++++------
 drivers/net/af_packet/rte_eth_af_packet.c | 11 ++++++-----
 drivers/net/bonding/rte_eth_bond_pmd.c    | 13 +++++++++----
 drivers/net/null/rte_eth_null.c           | 13 ++++++++-----
 drivers/net/pcap/rte_eth_pcap.c           | 12 +++++++-----
 drivers/net/ring/rte_eth_ring.c           |  9 +++++++--
 drivers/net/tap/rte_eth_tap.c             | 10 +++++++---
 drivers/net/vhost/rte_eth_vhost.c         | 10 +++++++---
 drivers/net/virtio/virtio_user_ethdev.c   | 18 +++++++-----------
 drivers/net/xenvirt/rte_eth_xenvirt.c     |  9 +++++----
 lib/librte_eal/common/eal_common_vdev.c   |  7 +++----
 lib/librte_eal/common/include/rte_vdev.h  |  4 ++--
 12 files changed, 80 insertions(+), 54 deletions(-)
drivers/crypto/null/null_crypto_pmd.c +12 -6
index f68ec8d..a44c61a 100644
@@ -218,8 +218,7 @@ cryptodev_null_create(struct rte_crypto_vdev_init_params *init_params)
 
 /** Initialise null crypto device */
 static int
-cryptodev_null_probe(const char *name,
-		const char *input_args)
+cryptodev_null_probe(struct rte_vdev_device *dev)
 {
 	struct rte_crypto_vdev_init_params init_params = {
 		RTE_CRYPTODEV_VDEV_DEFAULT_MAX_NB_QUEUE_PAIRS,
@@ -228,10 +227,11 @@ cryptodev_null_probe(const char *name,
 		{0}
 	};
 
-	rte_cryptodev_parse_vdev_init_params(&init_params, input_args);
+	rte_cryptodev_parse_vdev_init_params(&init_params,
+		rte_vdev_device_args(dev));
 
-	RTE_LOG(INFO, PMD, "Initialising %s on NUMA node %d\n", name,
-			init_params.socket_id);
+	RTE_LOG(INFO, PMD, "Initialising %s on NUMA node %d\n",
+		rte_vdev_device_name(dev), init_params.socket_id);
 	if (init_params.name[0] != '\0')
 		RTE_LOG(INFO, PMD, "  User defined name = %s\n",
 			init_params.name);
@@ -256,9 +256,15 @@ cryptodev_null_remove(const char *name)
 	return 0;
 }
 
+static int
+cryptodev_null_remove_dev(struct rte_vdev_device *dev)
+{
+	return cryptodev_null_remove(rte_vdev_device_name(dev));
+}
+
 static struct rte_vdev_driver cryptodev_null_pmd_drv = {
 	.probe = cryptodev_null_probe,
-	.remove = cryptodev_null_remove
+	.remove = cryptodev_null_remove_dev,
 };
 
 RTE_PMD_REGISTER_VDEV(CRYPTODEV_NAME_NULL_PMD, cryptodev_null_pmd_drv);
drivers/net/af_packet/rte_eth_af_packet.c +6 -5
index 2f87553..77536e8 100644
@@ -923,8 +923,9 @@ rte_eth_from_packet(const char *name,
 }
 
 static int
-rte_pmd_af_packet_probe(const char *name, const char *params)
+rte_pmd_af_packet_probe(struct rte_vdev_device *dev)
 {
+	const char *name = rte_vdev_device_name(dev);
 	unsigned numa_node;
 	int ret = 0;
 	struct rte_kvargs *kvlist;
@@ -934,7 +935,7 @@ rte_pmd_af_packet_probe(const char *name, const char *params)
 
 	numa_node = rte_socket_id();
 
-	kvlist = rte_kvargs_parse(params, valid_arguments);
+	kvlist = rte_kvargs_parse(rte_vdev_device_args(dev), valid_arguments);
 	if (kvlist == NULL) {
 		ret = -1;
 		goto exit;
@@ -961,7 +962,7 @@ rte_pmd_af_packet_probe(const char *name, const char *params)
 }
 
 static int
-rte_pmd_af_packet_remove(const char *name)
+rte_pmd_af_packet_remove(struct rte_vdev_device *dev)
 {
 	struct rte_eth_dev *eth_dev = NULL;
 	struct pmd_internals *internals;
@@ -970,11 +971,11 @@ rte_pmd_af_packet_remove(const char *name)
 	RTE_LOG(INFO, PMD, "Closing AF_PACKET ethdev on numa socket %u\n",
 			rte_socket_id());
 
-	if (name == NULL)
+	if (dev == NULL)
 		return -1;
 
 	/* find the ethdev entry */
-	eth_dev = rte_eth_dev_allocated(name);
+	eth_dev = rte_eth_dev_allocated(rte_vdev_device_name(dev));
 	if (eth_dev == NULL)
 		return -1;
 
drivers/net/bonding/rte_eth_bond_pmd.c +9 -4
index 77d3bee..340d793 100644
@@ -2240,16 +2240,19 @@ const struct eth_dev_ops default_dev_ops = {
 };
 
 static int
-bond_probe(const char *name, const char *params)
+bond_probe(struct rte_vdev_device *dev)
 {
+	const char *name;
 	struct bond_dev_private *internals;
 	struct rte_kvargs *kvlist;
 	uint8_t bonding_mode, socket_id;
 	int  arg_count, port_id;
 
+	name = rte_vdev_device_name(dev);
 	RTE_LOG(INFO, EAL, "Initializing pmd_bond for %s\n", name);
 
-	kvlist = rte_kvargs_parse(params, pmd_bond_init_valid_arguments);
+	kvlist = rte_kvargs_parse(rte_vdev_device_args(dev),
+		pmd_bond_init_valid_arguments);
 	if (kvlist == NULL)
 		return -1;
 
@@ -2307,13 +2310,15 @@ bond_probe(const char *name, const char *params)
 }
 
 static int
-bond_remove(const char *name)
+bond_remove(struct rte_vdev_device *dev)
 {
+	const char *name;
 	int  ret;
 
-	if (name == NULL)
+	if (!dev)
 		return -EINVAL;
 
+	name = rte_vdev_device_name(dev);
 	RTE_LOG(INFO, EAL, "Uninitializing pmd_bond for %s\n", name);
 
 	/* free link bonding eth device */
drivers/net/null/rte_eth_null.c +8 -5
index 7e14da0..a7b57bc 100644
@@ -606,17 +606,20 @@ get_packet_copy_arg(const char *key __rte_unused,
 }
 
 static int
-rte_pmd_null_probe(const char *name, const char *params)
+rte_pmd_null_probe(struct rte_vdev_device *dev)
 {
+	const char *name, *params;
 	unsigned numa_node;
 	unsigned packet_size = default_packet_size;
 	unsigned packet_copy = default_packet_copy;
 	struct rte_kvargs *kvlist = NULL;
 	int ret;
 
-	if (name == NULL)
+	if (!dev)
 		return -EINVAL;
 
+	name = rte_vdev_device_name(dev);
+	params = rte_vdev_device_args(dev);
 	RTE_LOG(INFO, PMD, "Initializing pmd_null for %s\n", name);
 
 	numa_node = rte_socket_id();
@@ -658,18 +661,18 @@ rte_pmd_null_probe(const char *name, const char *params)
 }
 
 static int
-rte_pmd_null_remove(const char *name)
+rte_pmd_null_remove(struct rte_vdev_device *dev)
 {
 	struct rte_eth_dev *eth_dev = NULL;
 
-	if (name == NULL)
+	if (!dev)
 		return -EINVAL;
 
 	RTE_LOG(INFO, PMD, "Closing null ethdev on numa socket %u\n",
 			rte_socket_id());
 
 	/* find the ethdev entry */
-	eth_dev = rte_eth_dev_allocated(name);
+	eth_dev = rte_eth_dev_allocated(rte_vdev_device_name(dev));
 	if (eth_dev == NULL)
 		return -1;
 
drivers/net/pcap/rte_eth_pcap.c +7 -5
index 075e3be..05cbd47 100644
@@ -936,8 +936,9 @@ eth_from_pcaps(const char *name, struct pmd_devargs *rx_queues,
 }
 
 static int
-pmd_pcap_probe(const char *name, const char *params)
+pmd_pcap_probe(struct rte_vdev_device *dev)
 {
+	const char *name;
 	unsigned int is_rx_pcap = 0, is_tx_pcap = 0;
 	struct rte_kvargs *kvlist;
 	struct pmd_devargs pcaps = {0};
@@ -945,13 +946,14 @@ pmd_pcap_probe(const char *name, const char *params)
 	int single_iface = 0;
 	int ret;
 
+	name = rte_vdev_device_name(dev);
 	RTE_LOG(INFO, PMD, "Initializing pmd_pcap for %s\n", name);
 
 	gettimeofday(&start_time, NULL);
 	start_cycles = rte_get_timer_cycles();
 	hz = rte_get_timer_hz();
 
-	kvlist = rte_kvargs_parse(params, valid_arguments);
+	kvlist = rte_kvargs_parse(rte_vdev_device_args(dev), valid_arguments);
 	if (kvlist == NULL)
 		return -1;
 
@@ -1035,18 +1037,18 @@ pmd_pcap_probe(const char *name, const char *params)
 }
 
 static int
-pmd_pcap_remove(const char *name)
+pmd_pcap_remove(struct rte_vdev_device *dev)
 {
 	struct rte_eth_dev *eth_dev = NULL;
 
 	RTE_LOG(INFO, PMD, "Closing pcap ethdev on numa socket %u\n",
 			rte_socket_id());
 
-	if (name == NULL)
+	if (!dev)
 		return -1;
 
 	/* reserve an ethdev entry */
-	eth_dev = rte_eth_dev_allocated(name);
+	eth_dev = rte_eth_dev_allocated(rte_vdev_device_name(dev));
 	if (eth_dev == NULL)
 		return -1;
 
drivers/net/ring/rte_eth_ring.c +7 -2
index 77ef3a1..4bae895 100644
@@ -502,12 +502,16 @@ static int parse_kvlist (const char *key __rte_unused, const char *value, void *
 }
 
 static int
-rte_pmd_ring_probe(const char *name, const char *params)
+rte_pmd_ring_probe(struct rte_vdev_device *dev)
 {
+	const char *name, *params;
 	struct rte_kvargs *kvlist = NULL;
 	int ret = 0;
 	struct node_action_list *info = NULL;
 
+	name = rte_vdev_device_name(dev);
+	params = rte_vdev_device_args(dev);
+
 	RTE_LOG(INFO, PMD, "Initializing pmd_ring for %s\n", name);
 
 	if (params == NULL || params[0] == '\0') {
@@ -577,8 +581,9 @@ rte_pmd_ring_probe(const char *name, const char *params)
 }
 
 static int
-rte_pmd_ring_remove(const char *name)
+rte_pmd_ring_remove(struct rte_vdev_device *dev)
 {
+	const char *name = rte_vdev_device_name(dev);
 	struct rte_eth_dev *eth_dev = NULL;
 	struct pmd_internals *internals = NULL;
 	struct ring_queue *r = NULL;
drivers/net/tap/rte_eth_tap.c +7 -3
index 347a807..698e14b 100644
@@ -1288,14 +1288,18 @@ set_remote_iface(const char *key __rte_unused,
 /* Open a TAP interface device.
  */
 static int
-rte_pmd_tap_probe(const char *name, const char *params)
+rte_pmd_tap_probe(struct rte_vdev_device *dev)
 {
+	const char *name, *params;
 	int ret;
 	struct rte_kvargs *kvlist = NULL;
 	int speed;
 	char tap_name[RTE_ETH_NAME_MAX_LEN];
 	char remote_iface[RTE_ETH_NAME_MAX_LEN];
 
+	name = rte_vdev_device_name(dev);
+	params = rte_vdev_device_args(dev);
+
 	speed = ETH_SPEED_NUM_10G;
 	snprintf(tap_name, sizeof(tap_name), "%s%d",
 		 DEFAULT_TAP_NAME, tap_unit++);
@@ -1355,7 +1359,7 @@ rte_pmd_tap_probe(const char *name, const char *params)
 /* detach a TAP device.
  */
 static int
-rte_pmd_tap_remove(const char *name)
+rte_pmd_tap_remove(struct rte_vdev_device *dev)
 {
 	struct rte_eth_dev *eth_dev = NULL;
 	struct pmd_internals *internals;
@@ -1365,7 +1369,7 @@ rte_pmd_tap_remove(const char *name)
 		rte_socket_id());
 
 	/* find the ethdev entry */
-	eth_dev = rte_eth_dev_allocated(name);
+	eth_dev = rte_eth_dev_allocated(rte_vdev_device_name(dev));
 	if (!eth_dev)
 		return 0;
 
drivers/net/vhost/rte_eth_vhost.c +7 -3
index 41ce5fc..cdd8c31 100644
@@ -1132,8 +1132,9 @@ open_int(const char *key __rte_unused, const char *value, void *extra_args)
 }
 
 static int
-rte_pmd_vhost_probe(const char *name, const char *params)
+rte_pmd_vhost_probe(struct rte_vdev_device *dev)
 {
+	const char *name;
 	struct rte_kvargs *kvlist = NULL;
 	int ret = 0;
 	char *iface_name;
@@ -1142,9 +1143,10 @@ rte_pmd_vhost_probe(const char *name, const char *params)
 	int client_mode = 0;
 	int dequeue_zero_copy = 0;
 
+	name = rte_vdev_device_name(dev);
 	RTE_LOG(INFO, PMD, "Initializing pmd_vhost for %s\n", name);
 
-	kvlist = rte_kvargs_parse(params, valid_arguments);
+	kvlist = rte_kvargs_parse(rte_vdev_device_args(dev), valid_arguments);
 	if (kvlist == NULL)
 		return -1;
 
@@ -1195,11 +1197,13 @@ rte_pmd_vhost_probe(const char *name, const char *params)
 }
 
 static int
-rte_pmd_vhost_remove(const char *name)
+rte_pmd_vhost_remove(struct rte_vdev_device *dev)
 {
+	const char *name;
 	struct rte_eth_dev *eth_dev = NULL;
 	unsigned int i;
 
+	name = rte_vdev_device_name(dev);
 	RTE_LOG(INFO, PMD, "Un-Initializing pmd_vhost for %s\n", name);
 
 	/* find an ethdev entry */
drivers/net/virtio/virtio_user_ethdev.c +7 -11
index 35717f7..46276ee 100644
@@ -402,7 +402,7 @@ virtio_user_eth_dev_free(struct rte_eth_dev *eth_dev)
  * Returns 0 on success.
  */
 static int
-virtio_user_pmd_probe(const char *name, const char *params)
+virtio_user_pmd_probe(struct rte_vdev_device *dev)
 {
 	struct rte_kvargs *kvlist = NULL;
 	struct rte_eth_dev *eth_dev;
@@ -415,13 +415,7 @@ virtio_user_pmd_probe(const char *name, const char *params)
 	char *mac_addr = NULL;
 	int ret = -1;
 
-	if (!params || params[0] == '\0') {
-		PMD_INIT_LOG(ERR, "arg %s is mandatory for virtio_user",
-			  VIRTIO_USER_ARG_QUEUE_SIZE);
-		goto end;
-	}
-
-	kvlist = rte_kvargs_parse(params, valid_args);
+	kvlist = rte_kvargs_parse(rte_vdev_device_args(dev), valid_args);
 	if (!kvlist) {
 		PMD_INIT_LOG(ERR, "error when parsing param");
 		goto end;
@@ -506,7 +500,7 @@ virtio_user_pmd_probe(const char *name, const char *params)
 		goto end;
 	}
 
-	eth_dev = virtio_user_eth_dev_alloc(name);
+	eth_dev = virtio_user_eth_dev_alloc(rte_vdev_device_name(dev));
 	if (!eth_dev) {
 		PMD_INIT_LOG(ERR, "virtio_user fails to alloc device");
 		goto end;
@@ -542,15 +536,17 @@ virtio_user_pmd_probe(const char *name, const char *params)
 
 /** Called by rte_eth_dev_detach() */
 static int
-virtio_user_pmd_remove(const char *name)
+virtio_user_pmd_remove(struct rte_vdev_device *vdev)
 {
+	const char *name;
 	struct rte_eth_dev *eth_dev;
 	struct virtio_hw *hw;
 	struct virtio_user_dev *dev;
 
-	if (!name)
+	if (!vdev)
 		return -EINVAL;
 
+	name = rte_vdev_device_name(vdev);
 	PMD_DRV_LOG(INFO, "Un-Initializing %s", name);
 	eth_dev = rte_eth_dev_allocated(name);
 	if (!eth_dev)
drivers/net/xenvirt/rte_eth_xenvirt.c +5 -4
index 19bc09a..6ec8c08 100644
@@ -726,7 +726,7 @@ eth_dev_xenvirt_free(const char *name, const unsigned numa_node)
 
 /*TODO: Support multiple process model */
 static int
-rte_pmd_xenvirt_probe(const char *name, const char *params)
+rte_pmd_xenvirt_probe(struct rte_vdev_device *dev)
 {
 	if (virtio_idx == 0) {
 		if (xenstore_init() != 0) {
@@ -738,14 +738,15 @@ rte_pmd_xenvirt_probe(const char *name, const char *params)
 			return -1;
 		}
 	}
-	eth_dev_xenvirt_create(name, params, rte_socket_id(), DEV_CREATE);
+	eth_dev_xenvirt_create(rte_vdev_device_name(dev),
+		rte_vdev_device_args(dev), rte_socket_id(), DEV_CREATE);
 	return 0;
 }
 
 static int
-rte_pmd_xenvirt_remove(const char *name)
+rte_pmd_xenvirt_remove(struct rte_vdev_device *dev)
 {
-	eth_dev_xenvirt_free(name, rte_socket_id());
+	eth_dev_xenvirt_free(rte_vdev_device_name(dev), rte_socket_id());
 
 	if (virtio_idx == 0) {
 		if (xenstore_uninit() != 0)
lib/librte_eal/common/eal_common_vdev.c +3 -4
index 70da608..22fe2ca 100644
@@ -76,7 +76,6 @@ static int
 vdev_probe_all_drivers(struct rte_vdev_device *dev)
 {
 	const char *name = rte_vdev_device_name(dev);
-	const char *args = rte_vdev_device_args(dev);
 	struct rte_vdev_driver *driver;
 	int ret;
 
@@ -90,7 +89,7 @@ vdev_probe_all_drivers(struct rte_vdev_device *dev)
 		if (!strncmp(driver->driver.name, name,
 			    strlen(driver->driver.name))) {
 			dev->device.driver = &driver->driver;
-			ret = driver->probe(name, args);
+			ret = driver->probe(dev);
 			if (ret)
 				dev->device.driver = NULL;
 			return ret;
@@ -103,7 +102,7 @@ vdev_probe_all_drivers(struct rte_vdev_device *dev)
 		    !strncmp(driver->driver.alias, name,
 			    strlen(driver->driver.alias))) {
 			dev->device.driver = &driver->driver;
-			ret = driver->probe(name, args);
+			ret = driver->probe(dev);
 			if (ret)
 				dev->device.driver = NULL;
 			return ret;
@@ -215,7 +214,7 @@ vdev_remove_driver(struct rte_vdev_device *dev)
 
 	driver = container_of(dev->device.driver, const struct rte_vdev_driver,
 		driver);
-	return driver->remove(name);
+	return driver->remove(dev);
 }
 
 int
lib/librte_eal/common/include/rte_vdev.h +2 -2
index 81f6beb..8db2c00 100644
@@ -68,12 +68,12 @@ TAILQ_HEAD(vdev_driver_list, rte_vdev_driver);
 /**
  * Probe function called for each virtual device driver once.
  */
-typedef int (rte_vdev_probe_t)(const char *name, const char *args);
+typedef int (rte_vdev_probe_t)(struct rte_vdev_device *dev);
 
 /**
  * Remove function called for each virtual device driver once.
  */
-typedef int (rte_vdev_remove_t)(const char *name);
+typedef int (rte_vdev_remove_t)(struct rte_vdev_device *dev);
 
 /**
  * A virtual device driver abstraction.
Signature · 1 line
2.1.4
#87 lore raw

PATCH v5 10/12 net/kni: use generic vdev for probe and remove

In reply to Gaetan Rivet
---
 drivers/net/kni/rte_eth_kni.c | 12 +++++++++---
 1 file changed, 9 insertions(+), 3 deletions(-)
drivers/net/kni/rte_eth_kni.c +9 -3
index 59205e7..e3ce572 100644
@@ -393,7 +393,7 @@ eth_kni_create(const char *name, struct eth_kni_args *args,
 
 	eth_dev->data = data;
 	eth_dev->dev_ops = &eth_kni_ops;
-	eth_dev->driver = NULL;
+	eth_dev->device->driver = NULL;
 
 	data->dev_flags = RTE_ETH_DEV_DETACHABLE;
 	data->kdrv = RTE_KDRV_NONE;
@@ -442,12 +442,16 @@ eth_kni_kvargs_process(struct eth_kni_args *args, const char *params)
 }
 
 static int
-eth_kni_probe(const char *name, const char *params)
+eth_kni_probe(struct rte_vdev_device *vdev)
 {
 	struct rte_eth_dev *eth_dev;
 	struct eth_kni_args args;
+	const char *name;
+	const char *params;
 	int ret;
 
+	name = rte_vdev_device_name(vdev);
+	params = rte_vdev_device_args(vdev);
 	RTE_LOG(INFO, PMD, "Initializing eth_kni for %s\n", name);
 
 	ret = eth_kni_kvargs_process(&args, params);
@@ -475,11 +479,13 @@ eth_kni_probe(const char *name, const char *params)
 }
 
 static int
-eth_kni_remove(const char *name)
+eth_kni_remove(struct rte_vdev_device *vdev)
 {
 	struct rte_eth_dev *eth_dev;
 	struct pmd_internals *internals;
+	const char *name;
 
+	name = rte_vdev_device_name(vdev);
 	RTE_LOG(INFO, PMD, "Un-Initializing eth_kni for %s\n", name);
 
 	/* find the ethdev entry */
Signature · 1 line
2.1.4
#88 lore raw

PATCH v5 11/12 crypto: use generic vdev for probe and remove

In reply to Gaetan Rivet
---
 drivers/crypto/aesni_gcm/aesni_gcm_pmd.c   | 20 ++++++++++++++------
 drivers/crypto/aesni_mb/rte_aesni_mb_pmd.c | 21 ++++++++++++++-------
 drivers/crypto/armv8/rte_armv8_pmd.c       | 21 ++++++++++++++-------
 drivers/crypto/kasumi/rte_kasumi_pmd.c     | 22 +++++++++++++++-------
 drivers/crypto/openssl/rte_openssl_pmd.c   | 22 +++++++++++++++-------
 drivers/crypto/scheduler/scheduler_pmd.c   | 17 +++++++++++------
 drivers/crypto/snow3g/rte_snow3g_pmd.c     | 22 +++++++++++++++-------
 drivers/crypto/zuc/rte_zuc_pmd.c           | 22 +++++++++++++++-------
 8 files changed, 113 insertions(+), 54 deletions(-)
drivers/crypto/aesni_gcm/aesni_gcm_pmd.c +14 -6
index ceec765..1705896 100644
@@ -429,10 +429,11 @@ aesni_gcm_pmd_enqueue_burst(void *queue_pair,
 	return nb_enqueued;
 }
 
-static int aesni_gcm_remove(const char *name);
+static int aesni_gcm_remove(struct rte_vdev_device *vdev);
 
 static int
-aesni_gcm_create(struct rte_crypto_vdev_init_params *init_params)
+aesni_gcm_create(struct rte_vdev_device *vdev,
+		 struct rte_crypto_vdev_init_params *init_params)
 {
 	struct rte_cryptodev *dev;
 	struct aesni_gcm_private *internals;
@@ -483,12 +484,12 @@ aesni_gcm_create(struct rte_crypto_vdev_init_params *init_params)
 init_error:
 	GCM_LOG_ERR("driver %s: create failed", init_params->name);
 
-	aesni_gcm_remove(init_params->name);
+	aesni_gcm_remove(vdev);
 	return -EFAULT;
 }
 
 static int
-aesni_gcm_probe(const char *name, const char *input_args)
+aesni_gcm_probe(struct rte_vdev_device *vdev)
 {
 	struct rte_crypto_vdev_init_params init_params = {
 		RTE_CRYPTODEV_VDEV_DEFAULT_MAX_NB_QUEUE_PAIRS,
@@ -496,7 +497,11 @@ aesni_gcm_probe(const char *name, const char *input_args)
 		rte_socket_id(),
 		{0}
 	};
+	const char *name;
+	const char *input_args;
 
+	name = rte_vdev_device_name(vdev);
+	input_args = rte_vdev_device_args(vdev);
 	rte_cryptodev_parse_vdev_init_params(&init_params, input_args);
 
 	RTE_LOG(INFO, PMD, "Initialising %s on NUMA node %d\n", name,
@@ -509,12 +514,15 @@ aesni_gcm_probe(const char *name, const char *input_args)
 	RTE_LOG(INFO, PMD, "  Max number of sessions = %d\n",
 			init_params.max_nb_sessions);
 
-	return aesni_gcm_create(&init_params);
+	return aesni_gcm_create(vdev, &init_params);
 }
 
 static int
-aesni_gcm_remove(const char *name)
+aesni_gcm_remove(struct rte_vdev_device *vdev)
 {
+	const char *name;
+
+	name = rte_vdev_device_name(vdev);
 	if (name == NULL)
 		return -EINVAL;
 
drivers/crypto/aesni_mb/rte_aesni_mb_pmd.c +14 -7
index be15d22..37b22ec 100644
@@ -669,10 +669,11 @@ aesni_mb_pmd_dequeue_burst(void *queue_pair, struct rte_crypto_op **ops,
 	return processed_jobs;
 }
 
-static int cryptodev_aesni_mb_remove(const char *name);
+static int cryptodev_aesni_mb_remove(struct rte_vdev_device *vdev);
 
 static int
-cryptodev_aesni_mb_create(struct rte_crypto_vdev_init_params *init_params)
+cryptodev_aesni_mb_create(struct rte_vdev_device *vdev,
+			  struct rte_crypto_vdev_init_params *init_params)
 {
 	struct rte_cryptodev *dev;
 	struct aesni_mb_private *internals;
@@ -750,13 +751,12 @@ cryptodev_aesni_mb_create(struct rte_crypto_vdev_init_params *init_params)
 	MB_LOG_ERR("driver %s: cryptodev_aesni_create failed",
 			init_params->name);
 
-	cryptodev_aesni_mb_remove(init_params->name);
+	cryptodev_aesni_mb_remove(vdev);
 	return -EFAULT;
 }
 
 static int
-cryptodev_aesni_mb_probe(const char *name,
-		const char *input_args)
+cryptodev_aesni_mb_probe(struct rte_vdev_device *vdev)
 {
 	struct rte_crypto_vdev_init_params init_params = {
 		RTE_CRYPTODEV_VDEV_DEFAULT_MAX_NB_QUEUE_PAIRS,
@@ -764,7 +764,11 @@ cryptodev_aesni_mb_probe(const char *name,
 		rte_socket_id(),
 		""
 	};
+	const char *name;
+	const char *input_args;
 
+	name = rte_vdev_device_name(vdev);
+	input_args = rte_vdev_device_args(vdev);
 	rte_cryptodev_parse_vdev_init_params(&init_params, input_args);
 
 	RTE_LOG(INFO, PMD, "Initialising %s on NUMA node %d\n", name,
@@ -777,12 +781,15 @@ cryptodev_aesni_mb_probe(const char *name,
 	RTE_LOG(INFO, PMD, "  Max number of sessions = %d\n",
 			init_params.max_nb_sessions);
 
-	return cryptodev_aesni_mb_create(&init_params);
+	return cryptodev_aesni_mb_create(vdev, &init_params);
 }
 
 static int
-cryptodev_aesni_mb_remove(const char *name)
+cryptodev_aesni_mb_remove(struct rte_vdev_device *vdev)
 {
+	const char *name;
+
+	name = rte_vdev_device_name(vdev);
 	if (name == NULL)
 		return -EINVAL;
 
drivers/crypto/armv8/rte_armv8_pmd.c +14 -7
index 6376e9e..bf56bc6 100644
@@ -44,7 +44,7 @@
 
 #include "rte_armv8_pmd_private.h"
 
-static int cryptodev_armv8_crypto_uninit(const char *name);
+static int cryptodev_armv8_crypto_uninit(struct rte_vdev_device *vdev);
 
 /**
  * Pointers to the supported combined mode crypto functions are stored
@@ -773,7 +773,8 @@ armv8_crypto_pmd_dequeue_burst(void *queue_pair, struct rte_crypto_op **ops,
 
 /** Create ARMv8 crypto device */
 static int
-cryptodev_armv8_crypto_create(struct rte_crypto_vdev_init_params *init_params)
+cryptodev_armv8_crypto_create(struct rte_vdev_device *vdev,
+			      struct rte_crypto_vdev_init_params *init_params)
 {
 	struct rte_cryptodev *dev;
 	struct armv8_crypto_private *internals;
@@ -845,14 +846,13 @@ cryptodev_armv8_crypto_create(struct rte_crypto_vdev_init_params *init_params)
 		"driver %s: cryptodev_armv8_crypto_create failed",
 		init_params->name);
 
-	cryptodev_armv8_crypto_uninit(init_params->name);
+	cryptodev_armv8_crypto_uninit(vdev);
 	return -EFAULT;
 }
 
 /** Initialise ARMv8 crypto device */
 static int
-cryptodev_armv8_crypto_init(const char *name,
-		const char *input_args)
+cryptodev_armv8_crypto_init(struct rte_vdev_device *vdev)
 {
 	struct rte_crypto_vdev_init_params init_params = {
 		RTE_CRYPTODEV_VDEV_DEFAULT_MAX_NB_QUEUE_PAIRS,
@@ -860,7 +860,11 @@ cryptodev_armv8_crypto_init(const char *name,
 		rte_socket_id(),
 		{0}
 	};
+	const char *name;
+	const char *input_args;
 
+	name = rte_vdev_device_name(vdev);
+	input_args = rte_vdev_device_args(vdev);
 	rte_cryptodev_parse_vdev_init_params(&init_params, input_args);
 
 	RTE_LOG(INFO, PMD, "Initialising %s on NUMA node %d\n", name,
@@ -874,13 +878,16 @@ cryptodev_armv8_crypto_init(const char *name,
 	RTE_LOG(INFO, PMD, "  Max number of sessions = %d\n",
 			init_params.max_nb_sessions);
 
-	return cryptodev_armv8_crypto_create(&init_params);
+	return cryptodev_armv8_crypto_create(vdev, &init_params);
 }
 
 /** Uninitialise ARMv8 crypto device */
 static int
-cryptodev_armv8_crypto_uninit(const char *name)
+cryptodev_armv8_crypto_uninit(struct rte_vdev_device *vdev)
 {
+	const char *name;
+
+	name = rte_vdev_device_name(vdev);
 	if (name == NULL)
 		return -EINVAL;
 
drivers/crypto/kasumi/rte_kasumi_pmd.c +15 -7
index 55bdb29..42fdd33 100644
@@ -548,10 +548,11 @@ kasumi_pmd_dequeue_burst(void *queue_pair,
 	return nb_dequeued;
 }
 
-static int cryptodev_kasumi_remove(const char *name);
+static int cryptodev_kasumi_remove(struct rte_vdev_device *vdev);
 
 static int
-cryptodev_kasumi_create(struct rte_crypto_vdev_init_params *init_params)
+cryptodev_kasumi_create(struct rte_vdev_device *vdev,
+			struct rte_crypto_vdev_init_params *init_params)
 {
 	struct rte_cryptodev *dev;
 	struct kasumi_private *internals;
@@ -606,13 +607,12 @@ cryptodev_kasumi_create(struct rte_crypto_vdev_init_params *init_params)
 	KASUMI_LOG_ERR("driver %s: cryptodev_kasumi_create failed",
 			init_params->name);
 
-	cryptodev_kasumi_remove(init_params->name);
+	cryptodev_kasumi_remove(vdev);
 	return -EFAULT;
 }
 
 static int
-cryptodev_kasumi_probe(const char *name,
-		const char *input_args)
+cryptodev_kasumi_probe(struct rte_vdev_device *vdev)
 {
 	struct rte_crypto_vdev_init_params init_params = {
 		RTE_CRYPTODEV_VDEV_DEFAULT_MAX_NB_QUEUE_PAIRS,
@@ -620,6 +620,11 @@ cryptodev_kasumi_probe(const char *name,
 		rte_socket_id(),
 		{0}
 	};
+	const char *name;
+	const char *input_args;
+
+	name = rte_vdev_device_name(vdev);
+	input_args = rte_vdev_device_args(vdev);
 
 	rte_cryptodev_parse_vdev_init_params(&init_params, input_args);
 
@@ -633,12 +638,15 @@ cryptodev_kasumi_probe(const char *name,
 	RTE_LOG(INFO, PMD, "  Max number of sessions = %d\n",
 			init_params.max_nb_sessions);
 
-	return cryptodev_kasumi_create(&init_params);
+	return cryptodev_kasumi_create(vdev, &init_params);
 }
 
 static int
-cryptodev_kasumi_remove(const char *name)
+cryptodev_kasumi_remove(struct rte_vdev_device *vdev)
 {
+	const char *name;
+
+	name = rte_vdev_device_name(vdev);
 	if (name == NULL)
 		return -EINVAL;
 
drivers/crypto/openssl/rte_openssl_pmd.c +15 -7
index 5046eac..f3c8f83 100644
@@ -44,7 +44,7 @@
 
 #define DES_BLOCK_SIZE 8
 
-static int cryptodev_openssl_remove(const char *name);
+static int cryptodev_openssl_remove(struct rte_vdev_device *vdev);
 
 /*----------------------------------------------------------------------------*/
 
@@ -1264,7 +1264,8 @@ openssl_pmd_dequeue_burst(void *queue_pair, struct rte_crypto_op **ops,
 
 /** Create OPENSSL crypto device */
 static int
-cryptodev_openssl_create(struct rte_crypto_vdev_init_params *init_params)
+cryptodev_openssl_create(struct rte_vdev_device *vdev,
+			 struct rte_crypto_vdev_init_params *init_params)
 {
 	struct rte_cryptodev *dev;
 	struct openssl_private *internals;
@@ -1312,14 +1313,13 @@ cryptodev_openssl_create(struct rte_crypto_vdev_init_params *init_params)
 	OPENSSL_LOG_ERR("driver %s: cryptodev_openssl_create failed",
 			init_params->name);
 
-	cryptodev_openssl_remove(init_params->name);
+	cryptodev_openssl_remove(vdev);
 	return -EFAULT;
 }
 
 /** Initialise OPENSSL crypto device */
 static int
-cryptodev_openssl_probe(const char *name,
-		const char *input_args)
+cryptodev_openssl_probe(struct rte_vdev_device *vdev)
 {
 	struct rte_crypto_vdev_init_params init_params = {
 		RTE_CRYPTODEV_VDEV_DEFAULT_MAX_NB_QUEUE_PAIRS,
@@ -1327,6 +1327,11 @@ cryptodev_openssl_probe(const char *name,
 		rte_socket_id(),
 		{0}
 	};
+	const char *name;
+	const char *input_args;
+
+	name = rte_vdev_device_name(vdev);
+	input_args = rte_vdev_device_args(vdev);
 
 	rte_cryptodev_parse_vdev_init_params(&init_params, input_args);
 
@@ -1340,13 +1345,16 @@ cryptodev_openssl_probe(const char *name,
 	RTE_LOG(INFO, PMD, "  Max number of sessions = %d\n",
 			init_params.max_nb_sessions);
 
-	return cryptodev_openssl_create(&init_params);
+	return cryptodev_openssl_create(vdev, &init_params);
 }
 
 /** Uninitialise OPENSSL crypto device */
 static int
-cryptodev_openssl_remove(const char *name)
+cryptodev_openssl_remove(struct rte_vdev_device *vdev)
 {
+	const char *name;
+
+	name = rte_vdev_device_name(vdev);
 	if (name == NULL)
 		return -EINVAL;
 
drivers/crypto/scheduler/scheduler_pmd.c +11 -6
index b189fbd..7d9e376 100644
@@ -193,14 +193,16 @@ cryptodev_scheduler_create(const char *name,
 }
 
 static int
-cryptodev_scheduler_remove(const char *name)
+cryptodev_scheduler_remove(struct rte_vdev_device *vdev)
 {
+	const char *name;
 	struct rte_cryptodev *dev;
 	struct scheduler_ctx *sched_ctx;
 
-	if (name == NULL)
+	if (vdev == NULL)
 		return -EINVAL;
 
+	name = rte_vdev_device_name(vdev);
 	dev = rte_cryptodev_pmd_get_named_dev(name);
 	if (dev == NULL)
 		return -EINVAL;
@@ -413,7 +415,7 @@ scheduler_parse_init_params(struct scheduler_init_params *params,
 }
 
 static int
-cryptodev_scheduler_probe(const char *name, const char *input_args)
+cryptodev_scheduler_probe(struct rte_vdev_device *vdev)
 {
 	struct scheduler_init_params init_params = {
 		.def_p = {
@@ -428,9 +430,11 @@ cryptodev_scheduler_probe(const char *name, const char *input_args)
 		.enable_ordering = 0
 	};
 
-	scheduler_parse_init_params(&init_params, input_args);
+	scheduler_parse_init_params(&init_params,
+				    rte_vdev_device_args(vdev));
 
-	RTE_LOG(INFO, PMD, "Initialising %s on NUMA node %d\n", name,
+	RTE_LOG(INFO, PMD, "Initialising %s on NUMA node %d\n",
+			rte_vdev_device_name(vdev),
 			init_params.def_p.socket_id);
 	RTE_LOG(INFO, PMD, "  Max number of queue pairs = %d\n",
 			init_params.def_p.max_nb_queue_pairs);
@@ -440,7 +444,8 @@ cryptodev_scheduler_probe(const char *name, const char *input_args)
 		RTE_LOG(INFO, PMD, "  User defined name = %s\n",
 			init_params.def_p.name);
 
-	return cryptodev_scheduler_create(name, &init_params);
+	return cryptodev_scheduler_create(rte_vdev_device_name(vdev),
+					  &init_params);
 }
 
 static struct rte_vdev_driver cryptodev_scheduler_pmd_drv = {
drivers/crypto/snow3g/rte_snow3g_pmd.c +15 -7
index 1042b31..a31eaa8 100644
@@ -539,10 +539,11 @@ snow3g_pmd_dequeue_burst(void *queue_pair,
 	return nb_dequeued;
 }
 
-static int cryptodev_snow3g_remove(const char *name);
+static int cryptodev_snow3g_remove(struct rte_vdev_device *vdev);
 
 static int
-cryptodev_snow3g_create(struct rte_crypto_vdev_init_params *init_params)
+cryptodev_snow3g_create(struct rte_vdev_device *vdev,
+			struct rte_crypto_vdev_init_params *init_params)
 {
 	struct rte_cryptodev *dev;
 	struct snow3g_private *internals;
@@ -595,13 +596,12 @@ cryptodev_snow3g_create(struct rte_crypto_vdev_init_params *init_params)
 	SNOW3G_LOG_ERR("driver %s: cryptodev_snow3g_create failed",
 			init_params->name);
 
-	cryptodev_snow3g_remove(init_params->name);
+	cryptodev_snow3g_remove(vdev);
 	return -EFAULT;
 }
 
 static int
-cryptodev_snow3g_probe(const char *name,
-		const char *input_args)
+cryptodev_snow3g_probe(struct rte_vdev_device *vdev)
 {
 	struct rte_crypto_vdev_init_params init_params = {
 		RTE_CRYPTODEV_VDEV_DEFAULT_MAX_NB_QUEUE_PAIRS,
@@ -609,6 +609,11 @@ cryptodev_snow3g_probe(const char *name,
 		rte_socket_id(),
 		{0}
 	};
+	const char *name;
+	const char *input_args;
+
+	name = rte_vdev_device_name(vdev);
+	input_args = rte_vdev_device_args(vdev);
 
 	rte_cryptodev_parse_vdev_init_params(&init_params, input_args);
 
@@ -622,12 +627,15 @@ cryptodev_snow3g_probe(const char *name,
 	RTE_LOG(INFO, PMD, "  Max number of sessions = %d\n",
 			init_params.max_nb_sessions);
 
-	return cryptodev_snow3g_create(&init_params);
+	return cryptodev_snow3g_create(vdev, &init_params);
 }
 
 static int
-cryptodev_snow3g_remove(const char *name)
+cryptodev_snow3g_remove(struct rte_vdev_device *vdev)
 {
+	const char *name;
+
+	name = rte_vdev_device_name(vdev);
 	if (name == NULL)
 		return -EINVAL;
 
drivers/crypto/zuc/rte_zuc_pmd.c +15 -7
index 06ff503..5eec933 100644
@@ -439,10 +439,11 @@ zuc_pmd_dequeue_burst(void *queue_pair,
 	return nb_dequeued;
 }
 
-static int cryptodev_zuc_remove(const char *name);
+static int cryptodev_zuc_remove(struct rte_vdev_device *vdev);
 
 static int
-cryptodev_zuc_create(struct rte_crypto_vdev_init_params *init_params)
+cryptodev_zuc_create(struct rte_vdev_device *vdev,
+		     struct rte_crypto_vdev_init_params *init_params)
 {
 	struct rte_cryptodev *dev;
 	struct zuc_private *internals;
@@ -495,13 +496,12 @@ cryptodev_zuc_create(struct rte_crypto_vdev_init_params *init_params)
 	ZUC_LOG_ERR("driver %s: cryptodev_zuc_create failed",
 			init_params->name);
 
-	cryptodev_zuc_remove(init_params->name);
+	cryptodev_zuc_remove(vdev);
 	return -EFAULT;
 }
 
 static int
-cryptodev_zuc_probe(const char *name,
-		const char *input_args)
+cryptodev_zuc_probe(struct rte_vdev_device *vdev)
 {
 	struct rte_crypto_vdev_init_params init_params = {
 		RTE_CRYPTODEV_VDEV_DEFAULT_MAX_NB_QUEUE_PAIRS,
@@ -509,6 +509,11 @@ cryptodev_zuc_probe(const char *name,
 		rte_socket_id(),
 		{0}
 	};
+	const char *name;
+	const char *input_args;
+
+	name = rte_vdev_device_name(vdev);
+	input_args = rte_vdev_device_args(vdev);
 
 	rte_cryptodev_parse_vdev_init_params(&init_params, input_args);
 
@@ -522,12 +527,15 @@ cryptodev_zuc_probe(const char *name,
 	RTE_LOG(INFO, PMD, "  Max number of sessions = %d\n",
 			init_params.max_nb_sessions);
 
-	return cryptodev_zuc_create(&init_params);
+	return cryptodev_zuc_create(vdev, &init_params);
 }
 
 static int
-cryptodev_zuc_remove(const char *name)
+cryptodev_zuc_remove(struct rte_vdev_device *vdev)
 {
+	const char *name;
+
+	name = rte_vdev_device_name(vdev);
 	if (name == NULL)
 		return -EINVAL;
 
Signature · 1 line
2.1.4
#89 lore raw

PATCH v5 12/12 event: use generic vdev for probe and remove

In reply to Gaetan Rivet
---
 drivers/event/octeontx/ssovf_evdev.c       | 11 +++++++----
 drivers/event/skeleton/skeleton_eventdev.c | 10 ++++++++--
 drivers/event/sw/sw_evdev.c                | 11 +++++++++--
 3 files changed, 24 insertions(+), 8 deletions(-)
drivers/event/octeontx/ssovf_evdev.c +7 -4
index 6479c80..c80a443 100644
@@ -488,17 +488,17 @@ static const struct rte_eventdev_ops ssovf_ops = {
 };
 
 static int
-ssovf_vdev_probe(const char *name, const char *params)
+ssovf_vdev_probe(struct rte_vdev_device *vdev)
 {
 	struct octeontx_ssovf_info oinfo;
 	struct ssovf_mbox_dev_info info;
 	struct ssovf_evdev *edev;
 	struct rte_eventdev *eventdev;
 	static int ssovf_init_once;
+	const char *name;
 	int ret;
 
-	RTE_SET_USED(params);
-
+	name = rte_vdev_device_name(vdev);
 	/* More than one instance is not supported */
 	if (ssovf_init_once) {
 		ssovf_log_err("Request to create >1 %s instance", name);
@@ -563,8 +563,11 @@ ssovf_vdev_probe(const char *name, const char *params)
 }
 
 static int
-ssovf_vdev_remove(const char *name)
+ssovf_vdev_remove(struct rte_vdev_device *vdev)
 {
+	const char *name;
+
+	name = rte_vdev_device_name(vdev);
 	ssovf_log_info("Closing %s", name);
 	return rte_event_pmd_vdev_uninit(name);
 }
drivers/event/skeleton/skeleton_eventdev.c +8 -2
index d2da7d8..800bd76 100644
@@ -468,16 +468,22 @@ skeleton_eventdev_create(const char *name, int socket_id)
 }
 
 static int
-skeleton_eventdev_probe(const char *name, __rte_unused const char *input_args)
+skeleton_eventdev_probe(struct rte_vdev_device *vdev)
 {
+	const char *name;
+
+	name = rte_vdev_device_name(vdev);
 	RTE_LOG(INFO, PMD, "Initializing %s on NUMA node %d\n", name,
 			rte_socket_id());
 	return skeleton_eventdev_create(name, rte_socket_id());
 }
 
 static int
-skeleton_eventdev_remove(const char *name)
+skeleton_eventdev_remove(struct rte_vdev_device *vdev)
 {
+	const char *name;
+
+	name = rte_vdev_device_name(vdev);
 	PMD_DRV_LOG(INFO, "Closing %s on NUMA node %d", name, rte_socket_id());
 
 	return rte_event_pmd_vdev_uninit(name);
drivers/event/sw/sw_evdev.c +9 -2
index 0caf8ba..a31aaa6 100644
@@ -696,7 +696,7 @@ set_credit_quanta(const char *key __rte_unused, const char *value, void *opaque)
 }
 
 static int
-sw_probe(const char *name, const char *params)
+sw_probe(struct rte_vdev_device *vdev)
 {
 	static const struct rte_eventdev_ops evdev_sw_ops = {
 			.dev_configure = sw_dev_configure,
@@ -727,12 +727,16 @@ sw_probe(const char *name, const char *params)
 		CREDIT_QUANTA_ARG,
 		NULL
 	};
+	const char *name;
+	const char *params;
 	struct rte_eventdev *dev;
 	struct sw_evdev *sw;
 	int socket_id = rte_socket_id();
 	int sched_quanta  = SW_DEFAULT_SCHED_QUANTA;
 	int credit_quanta = SW_DEFAULT_CREDIT_QUANTA;
 
+	name = rte_vdev_device_name(vdev);
+	params = rte_vdev_device_args(vdev);
 	if (params != NULL && params[0] != '\0') {
 		struct rte_kvargs *kvlist = rte_kvargs_parse(params, args);
 
@@ -806,8 +810,11 @@ sw_probe(const char *name, const char *params)
 }
 
 static int
-sw_remove(const char *name)
+sw_remove(struct rte_vdev_device *vdev)
 {
+	const char *name;
+
+	name = rte_vdev_device_name(vdev);
 	if (name == NULL)
 		return -EINVAL;
 
Signature · 1 line
2.1.4
#90 lore raw
In reply to Gaetan Rivet

2017-04-11 17:44, Gaetan Rivet:

Quoted 19 lines

I have rebased the work done by Jan to introduce the virtual device subsystem using the new rte_bus API.
I also fixed a few outstanding compilation issues, related to PMDs introduced during this release.
Additionally, a few virtual devices had not been ported to use the new rte_vdev_device that had been introduced in previous versions.

This patchset depends on:
http://dpdk.org/dev/patchwork/patch/20416/
http://dpdk.org/dev/patchwork/patch/20417/

Changes since version 4:
* Fix compilation issues for several virtual devices

Gaetan Rivet (3):
net/kni: use generic vdev for probe and remove
crypto: use generic vdev for probe and remove
event: use generic vdev for probe and remove

Quoted 10 lines

Jan Blunck (9):
eal: probe new virtual bus after other bus devices
eal: move virtual device probing into a bus
eal: remove unused rte_eal_dev_init()
eal: Refactor vdev driver probe/remove
eal: add struct rte_vdev_device
eal: add virtual device name helper function
eal: add virtual device arguments helper function
eal: make virtual bus use rte_vdev_device
eal: make virtual driver probe and remove take rte_vdev_device

The 3 additional patches from Gaetan are squashed with the EAL change to fix compilation of every drivers.

Applied, thanks

The vdev bus still needs to be registered with RTE_REGISTER_BUS.