From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: from mails.dpdk.org (mails.dpdk.org [217.70.189.124]) by inbox.dpdk.org (Postfix) with ESMTP id 515A24369B; Thu, 7 Dec 2023 21:27:09 +0100 (CET) Received: from mails.dpdk.org (localhost [127.0.0.1]) by mails.dpdk.org (Postfix) with ESMTP id CE5ED42F8F; Thu, 7 Dec 2023 21:27:04 +0100 (CET) Received: from linux.microsoft.com (linux.microsoft.com [13.77.154.182]) by mails.dpdk.org (Postfix) with ESMTP id 2B81942EF8 for ; Thu, 7 Dec 2023 21:27:02 +0100 (CET) Received: by linux.microsoft.com (Postfix, from userid 1086) id 29ED120B74C1; Thu, 7 Dec 2023 12:27:01 -0800 (PST) DKIM-Filter: OpenDKIM Filter v2.11.0 linux.microsoft.com 29ED120B74C1 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linux.microsoft.com; s=default; t=1701980821; bh=30IqhkyTf5N/XN7hfhj9TItTsYA0x+A0f08urobPyhs=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=VWxbzS2gYoaJMf60psiZj6Zy6OwV4WvDc9tBm6qkSgVRj4VGDwsOJ6gNoU47xjQpt mX3OKyaJATMQ/sV4Nv9uP6nglfnDy+lQGVMhylUkRIAI45R5TH+Cf6CAZQQAhLwwLK vy2saTnNYRyK0RXrVIPFmElDVevszNpr25cjL0X4= From: Tyler Retzlaff To: dev@dpdk.org Cc: Dmitry Kozlyuk , Pallavi Kadam , Tyler Retzlaff Subject: [PATCH v2] eal: initialize shared plugins on Windows Date: Thu, 7 Dec 2023 12:26:59 -0800 Message-Id: <1701980819-26640-2-git-send-email-roretzla@linux.microsoft.com> X-Mailer: git-send-email 1.8.3.1 In-Reply-To: <1701980819-26640-1-git-send-email-roretzla@linux.microsoft.com> References: <1701976851-17275-1-git-send-email-roretzla@linux.microsoft.com> <1701980819-26640-1-git-send-email-roretzla@linux.microsoft.com> X-BeenThere: dev@dpdk.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: DPDK patches and discussions List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: dev-bounces@dpdk.org When EAL is built with MSVC it is possible to dynamically load plugins on Windows. Hook eal_plugins_init into rte_eal_init if built with MSVC and provide code to load plugins on Windows. Signed-off-by: Tyler Retzlaff --- lib/eal/common/eal_common_options.c | 91 +++++++++++++++++++++++++++++++------ lib/eal/windows/eal.c | 8 ++++ 2 files changed, 84 insertions(+), 15 deletions(-) diff --git a/lib/eal/common/eal_common_options.c b/lib/eal/common/eal_common_options.c index a6d21f1..55be61d 100644 --- a/lib/eal/common/eal_common_options.c +++ b/lib/eal/common/eal_common_options.c @@ -5,6 +5,7 @@ #include #include +#include #include #ifndef RTE_EXEC_ENV_WINDOWS #include @@ -18,9 +19,7 @@ #include #endif #include -#ifndef RTE_EXEC_ENV_WINDOWS #include -#endif #include #include @@ -123,10 +122,8 @@ struct shared_driver { static struct shared_driver_list solib_list = TAILQ_HEAD_INITIALIZER(solib_list); -#ifndef RTE_EXEC_ENV_WINDOWS /* Default path of external loadable drivers */ static const char *default_solib_dir = RTE_EAL_PMD_PATH; -#endif /* * Stringified version of solib path used by dpdk-pmdinfo.py @@ -371,12 +368,12 @@ struct device_option { } #ifdef RTE_EXEC_ENV_WINDOWS -int -eal_plugins_init(void) -{ - return 0; -} +#define SOEXT ".dll" #else +#define SOEXT ".so" +#endif + +#define SOABIEXT SOEXT"."ABI_VERSION static int eal_plugindir_init(const char *path) @@ -397,12 +394,14 @@ struct device_option { while ((dent = readdir(d)) != NULL) { struct stat sb; - int nlen = strnlen(dent->d_name, sizeof(dent->d_name)); + size_t nlen = strnlen(dent->d_name, sizeof(dent->d_name)); - /* check if name ends in .so or .so.ABI_VERSION */ - if (strcmp(&dent->d_name[nlen - 3], ".so") != 0 && - strcmp(&dent->d_name[nlen - 4 - strlen(ABI_VERSION)], - ".so."ABI_VERSION) != 0) + if (nlen < strlen(SOABIEXT)) + continue; + + /* check if name ends in SOEXT or SOABIEXT */ + if (strcmp(&dent->d_name[nlen - strlen(SOEXT)], SOEXT) != 0 && + strcmp(&dent->d_name[nlen - strlen(SOABIEXT)], SOABIEXT) != 0) continue; snprintf(sopath, sizeof(sopath), "%s/%s", path, dent->d_name); @@ -420,6 +419,68 @@ struct device_option { return (dent == NULL) ? 0 : -1; } +#ifdef RTE_EXEC_ENV_WINDOWS +static void* +eal_dlopen(const char *pathname) +{ + void *retval = NULL; + struct stat pathstat; + char *fullpath = _fullpath(NULL, pathname, 0); + + const char *loadpath = fullpath; + DWORD loadflags = 0; + + if (fullpath == NULL) { + RTE_LOG(ERR, EAL, "Error expanding full path for %s, %s\n", + pathname, strerror(errno)); + } else { + /* Verify that the path exists */ + if ((stat(fullpath, &pathstat) != 0) && (errno == ENOENT)) { + /* not a full or relative path, try a load from default dirs */ + loadpath = pathname; + loadflags = LOAD_LIBRARY_SEARCH_DEFAULT_DIRS; + } + + retval = LoadLibraryExA(loadpath, NULL, loadflags); + if (retval == NULL) + RTE_LOG(ERR, EAL, "Error loading %s, error code: %" PRIu32 "\n", + loadpath, GetLastError()); + } + + free(fullpath); + return retval; +} + +static int +is_shared_build(void) +{ + int shared = 0; + HMODULE apphandle = NULL; + HMODULE libhandle = NULL; + + /* if fail to get handle, assume statically linked */ + apphandle = GetModuleHandleA(NULL); + if (apphandle == NULL) { + RTE_LOG(ERR, EAL, "Cannot get handle to the app\n"); + goto out; + } + + /* if fail to get handle, assume statically linked */ + if (GetModuleHandleExA(GET_MODULE_HANDLE_EX_FLAG_FROM_ADDRESS | + GET_MODULE_HANDLE_EX_FLAG_UNCHANGED_REFCOUNT, + (LPCSTR)&eal_plugins_init, + &libhandle)) { + if (apphandle != libhandle) { + /* lib and app handles are different. */ + /* Therefore lib is dynamically linked */ + shared = 1; + } + } + +out: + return shared; +} +#else static int verify_perms(const char *dirpath) { @@ -527,6 +588,7 @@ struct device_option { RTE_LOG(INFO, EAL, "Detected static linkage of DPDK\n"); return 0; } +#endif int eal_plugins_init(void) @@ -565,7 +627,6 @@ struct device_option { } return 0; } -#endif /* * Parse the coremask given as argument (hexadecimal string) and fill diff --git a/lib/eal/windows/eal.c b/lib/eal/windows/eal.c index 7ec2152..af51bf3 100644 --- a/lib/eal/windows/eal.c +++ b/lib/eal/windows/eal.c @@ -305,6 +305,14 @@ enum rte_proc_type_t if (fctret < 0) exit(1); +#ifdef RTE_TOOLCHAIN_MSVC + if (eal_plugins_init() < 0) { + rte_eal_init_alert("Cannot init plugins"); + rte_errno = EINVAL; + return -1; + } +#endif + if (eal_option_device_parse()) { rte_errno = ENODEV; return -1; -- 1.8.3.1