[dpdk-dev] [PATCH v3 1/3] eal: add functions parsing EAL arguments

Jacek Piasecki jacekx.piasecki at intel.com
Tue Jun 27 12:52:38 CEST 2017


From: Kuba Kozak <kubax.kozak at intel.com>

added function rte_eal_configure which configure
Environment Abstraction Layer (EAL) using
configuration structure.

Signed-off-by: Kuba Kozak <kubax.kozak at intel.com>
Suggested-by: Bruce Richardson <bruce.richardson at intel.com>
---
This patch depends on cfgfile patchset with:
"cfgfile: remove EAL dependency"
"cfgfile: add new functions to API"
"cfgfile: rework of load function"
"test/cfgfile: add new unit test"
---
 config/common_base                              |   1 +
 lib/Makefile                                    |   6 +-
 lib/librte_eal/bsdapp/eal/Makefile              |   4 +
 lib/librte_eal/bsdapp/eal/eal.c                 | 249 ++++++++++++++---
 lib/librte_eal/bsdapp/eal/rte_eal_version.map   |   4 +
 lib/librte_eal/common/eal_common_cpuflags.c     |  14 +-
 lib/librte_eal/common/eal_common_lcore.c        |  11 +-
 lib/librte_eal/common/eal_common_options.c      |   5 +
 lib/librte_eal/common/include/rte_eal.h         |  21 ++
 lib/librte_eal/linuxapp/eal/Makefile            |   3 +
 lib/librte_eal/linuxapp/eal/eal.c               | 353 ++++++++++++++++++------
 lib/librte_eal/linuxapp/eal/rte_eal_version.map |   4 +
 mk/rte.app.mk                                   |   2 +-
 13 files changed, 543 insertions(+), 134 deletions(-)

diff --git a/config/common_base b/config/common_base
index f6aafd1..c1d0e69 100644
--- a/config/common_base
+++ b/config/common_base
@@ -569,6 +569,7 @@ CONFIG_RTE_LIBRTE_TIMER_DEBUG=n
 # Compile librte_cfgfile
 #
 CONFIG_RTE_LIBRTE_CFGFILE=y
+CONFIG_RTE_LIBRTE_CFGFILE_DEBUG=n
 
 #
 # Compile librte_cmdline
diff --git a/lib/Makefile b/lib/Makefile
index 07e1fd0..fc5df3a 100644
--- a/lib/Makefile
+++ b/lib/Makefile
@@ -32,7 +32,11 @@
 include $(RTE_SDK)/mk/rte.vars.mk
 
 DIRS-y += librte_compat
+DIRS-$(CONFIG_RTE_LIBRTE_CFGFILE) += librte_cfgfile
 DIRS-$(CONFIG_RTE_LIBRTE_EAL) += librte_eal
+ifeq ($(CONFIG_RTE_LIBRTE_CFGFILE),y)
+DEPDIRS-librte_eal := librte_cfgfile
+endif
 DIRS-$(CONFIG_RTE_LIBRTE_RING) += librte_ring
 DEPDIRS-librte_ring := librte_eal
 DIRS-$(CONFIG_RTE_LIBRTE_MEMPOOL) += librte_mempool
@@ -41,8 +45,6 @@ DIRS-$(CONFIG_RTE_LIBRTE_MBUF) += librte_mbuf
 DEPDIRS-librte_mbuf := librte_eal librte_mempool
 DIRS-$(CONFIG_RTE_LIBRTE_TIMER) += librte_timer
 DEPDIRS-librte_timer := librte_eal
-DIRS-$(CONFIG_RTE_LIBRTE_CFGFILE) += librte_cfgfile
-DEPDIRS-librte_cfgfile := librte_eal
 DIRS-$(CONFIG_RTE_LIBRTE_CMDLINE) += librte_cmdline
 DEPDIRS-librte_cmdline := librte_eal
 DIRS-$(CONFIG_RTE_LIBRTE_ETHER) += librte_ether
diff --git a/lib/librte_eal/bsdapp/eal/Makefile b/lib/librte_eal/bsdapp/eal/Makefile
index a0f9950..d70eefb 100644
--- a/lib/librte_eal/bsdapp/eal/Makefile
+++ b/lib/librte_eal/bsdapp/eal/Makefile
@@ -50,6 +50,10 @@ EXPORT_MAP := rte_eal_version.map
 
 LIBABIVER := 4
 
+ifeq ($(CONFIG_RTE_LIBRTE_CFGFILE),y)
+LDLIBS += -lrte_cfgfile
+endif
+
 # specific to bsdapp exec-env
 SRCS-$(CONFIG_RTE_EXEC_ENV_BSDAPP) := eal.c
 SRCS-$(CONFIG_RTE_EXEC_ENV_BSDAPP) += eal_memory.c
diff --git a/lib/librte_eal/bsdapp/eal/eal.c b/lib/librte_eal/bsdapp/eal/eal.c
index 05f0c1f..7baf848 100644
--- a/lib/librte_eal/bsdapp/eal/eal.c
+++ b/lib/librte_eal/bsdapp/eal/eal.c
@@ -73,6 +73,7 @@
 #include <rte_version.h>
 #include <rte_atomic.h>
 #include <malloc_heap.h>
+#include <rte_cfgfile.h>
 
 #include "eal_private.h"
 #include "eal_thread.h"
@@ -309,6 +310,18 @@ eal_get_hugepage_mem_size(void)
 
 /* Parse the arguments for --log-level only */
 static void
+eal_log_level_cfg(struct rte_cfgfile *cfg)
+{
+	const char *entry;
+
+	entry = rte_cfgfile_get_entry(cfg, "DPDK", OPT_LOG_LEVEL);
+	if (entry)
+		eal_parse_common_option(OPT_LOG_LEVEL_NUM, entry,
+				&internal_config);
+}
+
+/* Parse the arguments for --log-level only */
+static void
 eal_log_level_parse(int argc, char **argv)
 {
 	int opt;
@@ -347,6 +360,58 @@ eal_log_level_parse(int argc, char **argv)
 	optarg = old_optarg;
 }
 
+/* Parse single argument */
+static int
+eal_parse_option(int opt, char *optarg, int option_index, char *prgname)
+{
+	int ret;
+
+	/* getopt is not happy, stop right now */
+	if (opt == '?') {
+		eal_usage(prgname);
+		ret = -1;
+		goto out;
+	}
+
+	ret = eal_parse_common_option(opt, optarg, &internal_config);
+	/* common parser is not happy */
+	if (ret < 0) {
+		eal_usage(prgname);
+		ret = -1;
+		goto out;
+	}
+	/* common parser handled this option */
+	if (ret == 0)
+		return 0;
+
+	switch (opt) {
+	case 'h':
+		eal_usage(prgname);
+		exit(EXIT_SUCCESS);
+		break;
+
+	default:
+		if (opt < OPT_LONG_MIN_NUM && isprint(opt)) {
+			RTE_LOG(ERR, EAL, "Option %c is not supported "
+				"on FreeBSD\n", opt);
+		} else if (opt >= OPT_LONG_MIN_NUM &&
+			   opt < OPT_LONG_MAX_NUM) {
+			RTE_LOG(ERR, EAL, "Option %s is not supported "
+				"on FreeBSD\n",
+				eal_long_options[option_index].name);
+		} else {
+			RTE_LOG(ERR, EAL, "Option %d is not supported "
+				"on FreeBSD\n", opt);
+		}
+		eal_usage(prgname);
+		ret = -1;
+		goto out;
+	}
+	return 0;
+out:
+	return ret;
+}
+
 /* Parse the argument given in the command line of the application */
 static int
 eal_parse_args(int argc, char **argv)
@@ -367,45 +432,9 @@ eal_parse_args(int argc, char **argv)
 	while ((opt = getopt_long(argc, argvopt, eal_short_options,
 				  eal_long_options, &option_index)) != EOF) {
 
-		/* getopt is not happy, stop right now */
-		if (opt == '?') {
-			eal_usage(prgname);
-			ret = -1;
-			goto out;
-		}
-
-		ret = eal_parse_common_option(opt, optarg, &internal_config);
-		/* common parser is not happy */
-		if (ret < 0) {
-			eal_usage(prgname);
-			ret = -1;
-			goto out;
-		}
-		/* common parser handled this option */
-		if (ret == 0)
-			continue;
-
-		switch (opt) {
-		case 'h':
-			eal_usage(prgname);
-			exit(EXIT_SUCCESS);
-		default:
-			if (opt < OPT_LONG_MIN_NUM && isprint(opt)) {
-				RTE_LOG(ERR, EAL, "Option %c is not supported "
-					"on FreeBSD\n", opt);
-			} else if (opt >= OPT_LONG_MIN_NUM &&
-				   opt < OPT_LONG_MAX_NUM) {
-				RTE_LOG(ERR, EAL, "Option %s is not supported "
-					"on FreeBSD\n",
-					eal_long_options[option_index].name);
-			} else {
-				RTE_LOG(ERR, EAL, "Option %d is not supported "
-					"on FreeBSD\n", opt);
-			}
-			eal_usage(prgname);
-			ret = -1;
+		ret = eal_parse_option(opt, optarg, option_index, prgname);
+		if (ret < 0)
 			goto out;
-		}
 	}
 
 	if (eal_adjust_config(&internal_config) != 0) {
@@ -677,3 +706,147 @@ rte_eal_process_type(void)
 {
 	return rte_config.process_type;
 }
+
+#ifdef RTE_LIBRTE_CFGFILE
+#define vdev_buff_size		200
+#define sectionname_size	20
+static int
+parse_vdev_devices(struct rte_cfgfile *cfg)
+{
+	char sectionname[sectionname_size];
+	char buffer1[vdev_buff_size];
+	int vdev_nb = 0;
+	int n_entries;
+	int i;
+
+	/* ----------- parsing VDEVS */
+	snprintf(sectionname, sectionname_size, "DPDK.vdev%d", vdev_nb);
+
+	for (vdev_nb = 1; rte_cfgfile_has_section(cfg, sectionname);
+			vdev_nb++) {
+		n_entries = rte_cfgfile_section_num_entries(cfg, sectionname);
+
+		struct rte_cfgfile_entry entries[n_entries];
+
+		if (n_entries != rte_cfgfile_section_entries(cfg, sectionname,
+				entries, n_entries)) {
+			rte_eal_init_alert("Unexpected fault.");
+			rte_errno = EFAULT;
+			return -1;
+		}
+
+		buffer1[0] = 0;
+		for (i = 0; i < n_entries; i++) {
+			if (strlen(entries[i].value)) {
+
+				if ((strlen(buffer1) +
+						strlen(entries[i].name) +
+						strlen(entries[i].value) + 3)
+						>= vdev_buff_size)
+					goto buff_size_err;
+				strcat(buffer1, entries[i].name);
+				strcat(buffer1, "=");
+				strcat(buffer1, entries[i].value);
+			} else {
+				if ((strlen(buffer1) +
+						strlen(entries[i].name) + 2)
+						>= vdev_buff_size)
+					goto buff_size_err;
+				strcat(buffer1, entries[i].name);
+			}
+
+			if (i < (n_entries - 1))
+				strcat(buffer1, ",");
+		}
+
+		/* parsing vdev */
+		if (rte_eal_devargs_add(RTE_DEVTYPE_VIRTUAL,
+				buffer1) < 0) {
+			return -1;
+		}
+		snprintf(sectionname, sectionname_size, "DPDK.vdev%d", vdev_nb);
+	}
+	/* ----------- parsing VDEVS */
+	return 0;
+
+buff_size_err:
+	printf("parse_vdev_devices(): buffer size is to small\n");
+	return -1;
+}
+
+static void
+eal_getopt(const char *str, int *opt, int *option_index)
+{
+	int i;
+
+	*opt = '?';
+	*option_index = 0;
+
+	if (strlen(str) == 1) {
+		*opt = *str;
+		return;
+	}
+
+	for (i = 0; eal_long_options[i].name != NULL; i++) {
+		if (strcmp(str, eal_long_options[i].name) == 0) {
+			*opt = eal_long_options[i].val;
+			*option_index = i;
+			break;
+		}
+	}
+}
+
+int
+rte_eal_configure(struct rte_cfgfile *cfg, char *prgname)
+{
+	int n_entries;
+	int i;
+	int opt;
+	int option_index;
+
+	if (cfg == NULL) {
+		rte_errno = -EINVAL;
+		return -1;
+	}
+
+	n_entries = rte_cfgfile_section_num_entries(cfg, "DPDK");
+
+	if (n_entries < 1) {
+		printf("No DPDK section entries in cfgfile object\n");
+		return 0;
+	}
+
+	struct rte_cfgfile_entry entries[n_entries];
+
+	if (n_entries !=
+			rte_cfgfile_section_entries(cfg, "DPDK", entries,
+					n_entries)) {
+		rte_eal_init_alert("Unexpected fault.");
+		rte_errno = EFAULT;
+		return -1;
+	}
+
+	eal_reset_internal_config(&internal_config);
+
+	/* set log level as early as possible */
+	eal_log_level_cfg(cfg);
+
+	for (i = 0; i < n_entries; i++) {
+		eal_getopt(entries[i].name, &opt, &option_index);
+
+		if (eal_parse_option(opt, entries[i].value,
+				option_index, prgname) != 0) {
+			rte_eal_init_alert("Invalid config file arguments.");
+			rte_errno = EINVAL;
+			return -1;
+		}
+	}
+
+	if (parse_vdev_devices(cfg) < 0) {
+		rte_eal_init_alert("Couldn't parse vdevs");
+		rte_errno = ENOMEM;
+		return -1;
+	}
+	return 0;
+}
+#endif
diff --git a/lib/librte_eal/bsdapp/eal/rte_eal_version.map b/lib/librte_eal/bsdapp/eal/rte_eal_version.map
index 2e48a73..a939b03 100644
--- a/lib/librte_eal/bsdapp/eal/rte_eal_version.map
+++ b/lib/librte_eal/bsdapp/eal/rte_eal_version.map
@@ -193,3 +193,7 @@ DPDK_17.05 {
 	vfio_get_group_no;
 
 } DPDK_17.02;
+
+DPDK_17.08 {
+	rte_eal_configure;
+} DPDK_17.05;
diff --git a/lib/librte_eal/common/eal_common_cpuflags.c b/lib/librte_eal/common/eal_common_cpuflags.c
index 9a2d080..6a365f3 100644
--- a/lib/librte_eal/common/eal_common_cpuflags.c
+++ b/lib/librte_eal/common/eal_common_cpuflags.c
@@ -50,12 +50,18 @@ rte_cpu_check_supported(void)
 int
 rte_cpu_is_supported(void)
 {
+	static int run_once;
+	static int ret;
 	/* This is generated at compile-time by the build system */
 	static const enum rte_cpu_flag_t compile_time_flags[] = {
 			RTE_COMPILE_TIME_CPUFLAGS
 	};
 	unsigned count = RTE_DIM(compile_time_flags), i;
-	int ret;
+
+	/* No need to calculate this function again if we know the result */
+	if (run_once)
+		return ret;
+	run_once = 1;
 
 	for (i = 0; i < count; i++) {
 		ret = rte_cpu_get_flag_enabled(compile_time_flags[i]);
@@ -64,16 +70,16 @@ rte_cpu_is_supported(void)
 			fprintf(stderr,
 				"ERROR: CPU feature flag lookup failed with error %d\n",
 				ret);
-			return 0;
+			return ret = 0;
 		}
 		if (!ret) {
 			fprintf(stderr,
 			        "ERROR: This system does not support \"%s\".\n"
 			        "Please check that RTE_MACHINE is set correctly.\n",
 			        rte_cpu_get_flag_name(compile_time_flags[i]));
-			return 0;
+			return ret = 0;
 		}
 	}
 
-	return 1;
+	return ret = 1;
 }
diff --git a/lib/librte_eal/common/eal_common_lcore.c b/lib/librte_eal/common/eal_common_lcore.c
index 84fa0cb..ce3ef34 100644
--- a/lib/librte_eal/common/eal_common_lcore.c
+++ b/lib/librte_eal/common/eal_common_lcore.c
@@ -53,11 +53,18 @@
 int
 rte_eal_cpu_init(void)
 {
+	static int run_once;
+	static int ret;
 	/* pointer to global configuration */
 	struct rte_config *config = rte_eal_get_configuration();
 	unsigned lcore_id;
 	unsigned count = 0;
 
+	/* No need to calculate this function again if we know the result */
+	if (run_once)
+		return ret;
+	run_once = 1;
+
 	/*
 	 * Parse the maximum set of logical cores, detect the subset of running
 	 * ones and enable them by default.
@@ -91,7 +98,7 @@ rte_eal_cpu_init(void)
 				"RTE_MAX_NUMA_NODES (%d)\n",
 				lcore_config[lcore_id].socket_id,
 				RTE_MAX_NUMA_NODES);
-			return -1;
+			return ret = -1;
 #endif
 		}
 		RTE_LOG(DEBUG, EAL, "Detected lcore %u as "
@@ -107,5 +114,5 @@ rte_eal_cpu_init(void)
 		RTE_MAX_LCORE);
 	RTE_LOG(INFO, EAL, "Detected %u lcore(s)\n", config->lcore_count);
 
-	return 0;
+	return ret = 0;
 }
diff --git a/lib/librte_eal/common/eal_common_options.c b/lib/librte_eal/common/eal_common_options.c
index f470195..138a27f 100644
--- a/lib/librte_eal/common/eal_common_options.c
+++ b/lib/librte_eal/common/eal_common_options.c
@@ -131,8 +131,13 @@ static int core_parsed;
 void
 eal_reset_internal_config(struct internal_config *internal_cfg)
 {
+	static int run_once;
 	int i;
 
+	if (run_once)
+		return;
+	run_once = 1;
+
 	internal_cfg->memory = 0;
 	internal_cfg->force_nrank = 0;
 	internal_cfg->force_nchannel = 0;
diff --git a/lib/librte_eal/common/include/rte_eal.h b/lib/librte_eal/common/include/rte_eal.h
index abf020b..e0705de 100644
--- a/lib/librte_eal/common/include/rte_eal.h
+++ b/lib/librte_eal/common/include/rte_eal.h
@@ -46,6 +46,8 @@
 #include <rte_per_lcore.h>
 #include <rte_config.h>
 
+struct rte_cfgfile; /* forward declaration of struct */
+
 #ifdef __cplusplus
 extern "C" {
 #endif
@@ -188,6 +190,25 @@ int rte_eal_iopl_init(void);
  */
 int rte_eal_init(int argc, char **argv);
 
+#ifdef RTE_LIBRTE_CFGFILE
+/**
+ * Initialize the Environment Abstraction Layer (EAL) using
+ * configuration structure
+ *
+ * @param cfg
+ *   pointer to config file structure.
+ *   If 0 - function free allocated for **cfg_argv memory
+ * @param prgname
+ *   pointer to string with execution path
+ *
+ * @return
+ *  - On success, return 0
+ *  - On failure, returns -1.
+ */
+int
+rte_eal_configure(struct rte_cfgfile *cfg, char *prgname);
+#endif
+
 /**
  * Check if a primary process is currently alive
  *
diff --git a/lib/librte_eal/linuxapp/eal/Makefile b/lib/librte_eal/linuxapp/eal/Makefile
index 640afd0..656033e 100644
--- a/lib/librte_eal/linuxapp/eal/Makefile
+++ b/lib/librte_eal/linuxapp/eal/Makefile
@@ -50,6 +50,9 @@ LDLIBS += -ldl
 LDLIBS += -lpthread
 LDLIBS += -lgcc_s
 LDLIBS += -lrt
+ifeq ($(CONFIG_RTE_LIBRTE_CFGFILE),y)
+LDLIBS += -lrte_cfgfile
+endif
 
 # specific to linuxapp exec-env
 SRCS-$(CONFIG_RTE_EXEC_ENV_LINUXAPP) := eal.c
diff --git a/lib/librte_eal/linuxapp/eal/eal.c b/lib/librte_eal/linuxapp/eal/eal.c
index 7c78f2d..f5973f4 100644
--- a/lib/librte_eal/linuxapp/eal/eal.c
+++ b/lib/librte_eal/linuxapp/eal/eal.c
@@ -78,6 +78,9 @@
 #include <rte_version.h>
 #include <rte_atomic.h>
 #include <malloc_heap.h>
+#ifdef RTE_LIBRTE_CFGFILE
+#include <rte_cfgfile.h>
+#endif
 
 #include "eal_private.h"
 #include "eal_thread.h"
@@ -478,6 +481,20 @@ eal_parse_vfio_intr(const char *mode)
 	return -1;
 }
 
+#ifdef RTE_LIBRTE_CFGFILE
+/* Parse the arguments for --log-level only */
+static void
+eal_log_level_cfg(struct rte_cfgfile *cfg)
+{
+	const char *entry;
+
+	entry = rte_cfgfile_get_entry(cfg, "DPDK", OPT_LOG_LEVEL);
+	if (entry)
+		eal_parse_common_option(OPT_LOG_LEVEL_NUM, entry,
+				&internal_config);
+}
+#endif
+
 /* Parse the arguments for --log-level only */
 static void
 eal_log_level_parse(int argc, char **argv)
@@ -515,119 +532,135 @@ eal_log_level_parse(int argc, char **argv)
 	optarg = old_optarg;
 }
 
-/* Parse the argument given in the command line of the application */
+/* Parse single argument */
 static int
-eal_parse_args(int argc, char **argv)
+eal_parse_option(int opt, char *optarg, int option_index, char *prgname)
 {
-	int opt, ret;
-	char **argvopt;
-	int option_index;
-	char *prgname = argv[0];
-	const int old_optind = optind;
-	const int old_optopt = optopt;
-	char * const old_optarg = optarg;
+	int ret;
 
-	argvopt = argv;
-	optind = 1;
+	/* getopt is not happy, stop right now */
+	if (opt == '?') {
+		eal_usage(prgname);
+		ret = -1;
+		goto out;
+	}
 
-	while ((opt = getopt_long(argc, argvopt, eal_short_options,
-				  eal_long_options, &option_index)) != EOF) {
+	ret = eal_parse_common_option(opt, optarg, &internal_config);
+	/* common parser is not happy */
+	if (ret < 0) {
+		eal_usage(prgname);
+		ret = -1;
+		goto out;
+	}
+	/* common parser handled this option */
+	if (ret == 0)
+		return 0;
 
-		/* getopt is not happy, stop right now */
-		if (opt == '?') {
+	switch (opt) {
+	case 'h':
+		eal_usage(prgname);
+		exit(EXIT_SUCCESS);
+		break;
+
+	/* long options */
+	case OPT_XEN_DOM0_NUM:
+#ifdef RTE_LIBRTE_XEN_DOM0
+		internal_config.xen_dom0_support = 1;
+		break;
+#else
+		RTE_LOG(ERR, EAL, "Can't support DPDK app "
+			"running on Dom0, please configure"
+			" RTE_LIBRTE_XEN_DOM0=y\n");
+		ret = -1;
+		goto out;
+#endif
+
+	case OPT_HUGE_DIR_NUM:
+		internal_config.hugepage_dir = optarg;
+		break;
+
+	case OPT_FILE_PREFIX_NUM:
+		internal_config.hugefile_prefix = optarg;
+		break;
+
+	case OPT_SOCKET_MEM_NUM:
+		if (eal_parse_socket_mem(optarg) < 0) {
+			RTE_LOG(ERR, EAL, "invalid parameters for --"
+					OPT_SOCKET_MEM "\n");
 			eal_usage(prgname);
 			ret = -1;
 			goto out;
 		}
+		break;
 
-		ret = eal_parse_common_option(opt, optarg, &internal_config);
-		/* common parser is not happy */
-		if (ret < 0) {
+	case OPT_BASE_VIRTADDR_NUM:
+		if (eal_parse_base_virtaddr(optarg) < 0) {
+			RTE_LOG(ERR, EAL, "invalid parameter for --"
+					OPT_BASE_VIRTADDR "\n");
 			eal_usage(prgname);
 			ret = -1;
 			goto out;
 		}
-		/* common parser handled this option */
-		if (ret == 0)
-			continue;
+		break;
 
-		switch (opt) {
-		case 'h':
+	case OPT_VFIO_INTR_NUM:
+		if (eal_parse_vfio_intr(optarg) < 0) {
+			RTE_LOG(ERR, EAL, "invalid parameters for --"
+					OPT_VFIO_INTR "\n");
 			eal_usage(prgname);
-			exit(EXIT_SUCCESS);
-
-		/* long options */
-		case OPT_XEN_DOM0_NUM:
-#ifdef RTE_LIBRTE_XEN_DOM0
-			internal_config.xen_dom0_support = 1;
-#else
-			RTE_LOG(ERR, EAL, "Can't support DPDK app "
-				"running on Dom0, please configure"
-				" RTE_LIBRTE_XEN_DOM0=y\n");
 			ret = -1;
 			goto out;
-#endif
-			break;
+		}
+		break;
 
-		case OPT_HUGE_DIR_NUM:
-			internal_config.hugepage_dir = optarg;
-			break;
+	case OPT_CREATE_UIO_DEV_NUM:
+		internal_config.create_uio_dev = 1;
+		break;
 
-		case OPT_FILE_PREFIX_NUM:
-			internal_config.hugefile_prefix = optarg;
-			break;
+	default:
+		if (opt < OPT_LONG_MIN_NUM && isprint(opt)) {
+			RTE_LOG(ERR, EAL, "Option %c is not supported "
+				"on Linux\n", opt);
+		} else if (opt >= OPT_LONG_MIN_NUM &&
+			   opt < OPT_LONG_MAX_NUM) {
+			RTE_LOG(ERR, EAL, "Option %s is not supported "
+				"on Linux\n",
+				eal_long_options[option_index].name);
+		} else {
+			RTE_LOG(ERR, EAL, "Option %d is not supported "
+				"on Linux\n", opt);
+		}
+		eal_usage(prgname);
+		ret = -1;
+		goto out;
+	}
 
-		case OPT_SOCKET_MEM_NUM:
-			if (eal_parse_socket_mem(optarg) < 0) {
-				RTE_LOG(ERR, EAL, "invalid parameters for --"
-						OPT_SOCKET_MEM "\n");
-				eal_usage(prgname);
-				ret = -1;
-				goto out;
-			}
-			break;
+	return 0;
+out:
+	return ret;
+}
 
-		case OPT_BASE_VIRTADDR_NUM:
-			if (eal_parse_base_virtaddr(optarg) < 0) {
-				RTE_LOG(ERR, EAL, "invalid parameter for --"
-						OPT_BASE_VIRTADDR "\n");
-				eal_usage(prgname);
-				ret = -1;
-				goto out;
-			}
-			break;
+/* Parse the argument given in the command line of the application */
+static int
+eal_parse_args(int argc, char **argv)
+{
+	int opt, ret;
+	char **argvopt;
+	int option_index;
+	char *prgname = argv[0];
+	const int old_optind = optind;
+	const int old_optopt = optopt;
+	char * const old_optarg = optarg;
 
-		case OPT_VFIO_INTR_NUM:
-			if (eal_parse_vfio_intr(optarg) < 0) {
-				RTE_LOG(ERR, EAL, "invalid parameters for --"
-						OPT_VFIO_INTR "\n");
-				eal_usage(prgname);
-				ret = -1;
-				goto out;
-			}
-			break;
+	argvopt = argv;
+	optind = 1;
 
-		case OPT_CREATE_UIO_DEV_NUM:
-			internal_config.create_uio_dev = 1;
-			break;
+	while ((opt = getopt_long(argc, argvopt, eal_short_options,
+				  eal_long_options, &option_index)) != EOF) {
 
-		default:
-			if (opt < OPT_LONG_MIN_NUM && isprint(opt)) {
-				RTE_LOG(ERR, EAL, "Option %c is not supported "
-					"on Linux\n", opt);
-			} else if (opt >= OPT_LONG_MIN_NUM &&
-				   opt < OPT_LONG_MAX_NUM) {
-				RTE_LOG(ERR, EAL, "Option %s is not supported "
-					"on Linux\n",
-					eal_long_options[option_index].name);
-			} else {
-				RTE_LOG(ERR, EAL, "Option %d is not supported "
-					"on Linux\n", opt);
-			}
-			eal_usage(prgname);
-			ret = -1;
+		ret = eal_parse_option(opt, optarg, option_index, prgname);
+		if (ret < 0)
 			goto out;
-		}
 	}
 
 	if (eal_adjust_config(&internal_config) != 0) {
@@ -995,3 +1028,149 @@ rte_eal_check_module(const char *module_name)
 	/* Module has been found */
 	return 1;
 }
+
+#ifdef RTE_LIBRTE_CFGFILE
+#define vdev_buff_size		200
+#define sectionname_size	20
+static int
+parse_vdev_devices(struct rte_cfgfile *cfg)
+{
+	char sectionname[sectionname_size];
+	char buffer1[vdev_buff_size];
+	int vdev_nb = 0;
+	int n_entries;
+
+	int i;
+
+	/* ----------- parsing VDEVS */
+	snprintf(sectionname, sectionname_size, "DPDK.vdev%d", vdev_nb);
+
+	for (vdev_nb = 1; rte_cfgfile_has_section(cfg, sectionname);
+			vdev_nb++) {
+		n_entries = rte_cfgfile_section_num_entries(cfg, sectionname);
+
+		struct rte_cfgfile_entry entries[n_entries];
+
+
+		if (n_entries != rte_cfgfile_section_entries(cfg, sectionname,
+				entries, n_entries)) {
+			rte_eal_init_alert("Unexpected fault.");
+			rte_errno = EFAULT;
+			return -1;
+		}
+
+		buffer1[0] = 0;
+		for (i = 0; i < n_entries; i++) {
+			if (strlen(entries[i].value)) {
+
+				if ((strlen(buffer1) +
+						strlen(entries[i].name) +
+						strlen(entries[i].value) + 3)
+						>= vdev_buff_size)
+					goto buff_size_err;
+				strcat(buffer1, entries[i].name);
+				strcat(buffer1, "=");
+				strcat(buffer1, entries[i].value);
+			} else {
+				if ((strlen(buffer1) +
+						strlen(entries[i].name) + 2)
+						>= vdev_buff_size)
+					goto buff_size_err;
+				strcat(buffer1, entries[i].name);
+			}
+
+			if (i < (n_entries - 1))
+				strcat(buffer1, ",");
+		}
+
+		/* parsing vdev */
+		if (rte_eal_devargs_add(RTE_DEVTYPE_VIRTUAL,
+				buffer1) < 0) {
+			return -1;
+		}
+		snprintf(sectionname, sectionname_size, "DPDK.vdev%d", vdev_nb);
+	}
+	/* ----------- parsing VDEVS */
+	return 0;
+
+buff_size_err:
+	printf("parse_vdev_devices(): buffer size is to small\n");
+	return -1;
+}
+
+static void
+eal_getopt(const char *str, int *opt, int *option_index)
+{
+	int i;
+
+	*opt = '?';
+	*option_index = 0;
+
+	if (strlen(str) == 1) {
+		*opt = *str;
+		return;
+	}
+
+	for (i = 0; eal_long_options[i].name != NULL; i++) {
+		if (strcmp(str, eal_long_options[i].name) == 0) {
+			*opt = eal_long_options[i].val;
+			*option_index = i;
+			break;
+		}
+	}
+}
+
+int
+rte_eal_configure(struct rte_cfgfile *cfg, char *prgname)
+{
+	int n_entries;
+	int i;
+	int opt;
+	int option_index;
+
+	if (cfg == NULL) {
+		rte_errno = -EINVAL;
+		return -1;
+	}
+
+	n_entries = rte_cfgfile_section_num_entries(cfg, "DPDK");
+
+	if (n_entries < 1) {
+		printf("No DPDK section entries in cfgfile object\n");
+		return 0;
+	}
+
+	struct rte_cfgfile_entry entries[n_entries];
+
+	if (n_entries !=
+			rte_cfgfile_section_entries(cfg, "DPDK", entries,
+					n_entries)) {
+		rte_eal_init_alert("Unexpected fault.");
+		rte_errno = EFAULT;
+		return -1;
+	}
+
+	eal_reset_internal_config(&internal_config);
+
+	/* set log level as early as possible */
+	eal_log_level_cfg(cfg);
+
+	for (i = 0; i < n_entries; i++) {
+		eal_getopt(entries[i].name, &opt, &option_index);
+
+		if (eal_parse_option(opt, entries[i].value,
+				option_index, prgname) != 0) {
+			rte_eal_init_alert("Invalid config file arguments.");
+			rte_errno = EINVAL;
+			return -1;
+		}
+	}
+
+	if (parse_vdev_devices(cfg) < 0) {
+		rte_eal_init_alert("Couldn't parse vdevs");
+		rte_errno = ENOMEM;
+		return -1;
+	}
+	return 0;
+}
+#endif
diff --git a/lib/librte_eal/linuxapp/eal/rte_eal_version.map b/lib/librte_eal/linuxapp/eal/rte_eal_version.map
index 670bab3..c93e6d9 100644
--- a/lib/librte_eal/linuxapp/eal/rte_eal_version.map
+++ b/lib/librte_eal/linuxapp/eal/rte_eal_version.map
@@ -198,3 +198,7 @@ DPDK_17.05 {
 	vfio_get_group_no;
 
 } DPDK_17.02;
+
+DPDK_17.08 {
+	rte_eal_configure;
+} DPDK_17.05;
diff --git a/mk/rte.app.mk b/mk/rte.app.mk
index bcaf1b3..642af92 100644
--- a/mk/rte.app.mk
+++ b/mk/rte.app.mk
@@ -80,7 +80,6 @@ _LDLIBS-$(CONFIG_RTE_LIBRTE_POWER)          += -lrte_power
 
 _LDLIBS-$(CONFIG_RTE_LIBRTE_TIMER)          += -lrte_timer
 _LDLIBS-$(CONFIG_RTE_LIBRTE_EFD)            += -lrte_efd
-_LDLIBS-$(CONFIG_RTE_LIBRTE_CFGFILE)        += -lrte_cfgfile
 
 _LDLIBS-y += --whole-archive
 
@@ -96,6 +95,7 @@ _LDLIBS-$(CONFIG_RTE_LIBRTE_MEMPOOL)        += -lrte_mempool
 _LDLIBS-$(CONFIG_RTE_DRIVER_MEMPOOL_RING)   += -lrte_mempool_ring
 _LDLIBS-$(CONFIG_RTE_LIBRTE_RING)           += -lrte_ring
 _LDLIBS-$(CONFIG_RTE_LIBRTE_EAL)            += -lrte_eal
+_LDLIBS-$(CONFIG_RTE_LIBRTE_CFGFILE)        += -lrte_cfgfile
 _LDLIBS-$(CONFIG_RTE_LIBRTE_CMDLINE)        += -lrte_cmdline
 _LDLIBS-$(CONFIG_RTE_LIBRTE_REORDER)        += -lrte_reorder
 
-- 
2.7.4



More information about the dev mailing list