diff --git a/cmake/onnxruntime_providers.cmake b/cmake/onnxruntime_providers.cmake index a74633ae7d..6ba1be3d99 100644 --- a/cmake/onnxruntime_providers.cmake +++ b/cmake/onnxruntime_providers.cmake @@ -221,6 +221,40 @@ install(DIRECTORY ${PROJECT_SOURCE_DIR}/../include/onnxruntime/core/providers/cp set_target_properties(onnxruntime_providers PROPERTIES LINKER_LANGUAGE CXX) set_target_properties(onnxruntime_providers PROPERTIES FOLDER "ONNXRuntime") +if (NOT onnxruntime_MINIMAL_BUILD AND NOT onnxruntime_EXTENDED_MINIMAL_BUILD + AND NOT ${CMAKE_SYSTEM_NAME} MATCHES "Darwin|iOS" + AND NOT (CMAKE_SYSTEM_NAME STREQUAL "Android") + AND NOT onnxruntime_BUILD_WEBASSEMBLY) + file(GLOB onnxruntime_providers_shared_cc_srcs CONFIGURE_DEPENDS + "${ONNXRUNTIME_ROOT}/core/providers/shared/*.h" + "${ONNXRUNTIME_ROOT}/core/providers/shared/*.cc" + ) + + source_group(TREE ${ONNXRUNTIME_ROOT}/core FILES ${onnxruntime_providers_shared_cc_srcs}) + onnxruntime_add_shared_library(onnxruntime_providers_shared ${onnxruntime_providers_shared_cc_srcs}) + set_target_properties(onnxruntime_providers_shared PROPERTIES FOLDER "ONNXRuntime") + set_target_properties(onnxruntime_providers_shared PROPERTIES LINKER_LANGUAGE CXX) + + # On Apple/Unix we don't directly link with this library as we load it with RTLD_GLOBAL, so this is only set to the actual library on WIN32 + set(ONNXRUNTIME_PROVIDERS_SHARED) + + if(APPLE) + set_property(TARGET onnxruntime_providers_shared APPEND_STRING PROPERTY LINK_FLAGS "-Xlinker -exported_symbols_list ${ONNXRUNTIME_ROOT}/core/providers/shared/exported_symbols.lst") + elseif(UNIX) + set_property(TARGET onnxruntime_providers_shared APPEND_STRING PROPERTY LINK_FLAGS "-Xlinker --version-script=${ONNXRUNTIME_ROOT}/core/providers/shared/version_script.lds -Xlinker --gc-sections") + elseif(WIN32) + set_property(TARGET onnxruntime_providers_shared APPEND_STRING PROPERTY LINK_FLAGS "-DEF:${ONNXRUNTIME_ROOT}/core/providers/shared/symbols.def") + set(ONNXRUNTIME_PROVIDERS_SHARED onnxruntime_providers_shared) + else() + message(FATAL_ERROR "onnxruntime_providers_shared unknown platform, need to specify shared library exports for it") + endif() + + install(TARGETS onnxruntime_providers_shared + ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR} + LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} + RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR}) +endif() + if (onnxruntime_USE_CUDA) file(GLOB_RECURSE onnxruntime_providers_cuda_cc_srcs CONFIGURE_DEPENDS "${ONNXRUNTIME_ROOT}/core/providers/cuda/*.h" @@ -309,7 +343,7 @@ if (onnxruntime_USE_CUDA) endif() add_dependencies(onnxruntime_providers_cuda onnxruntime_providers_shared ${onnxruntime_EXTERNAL_DEPENDENCIES} ${onnxruntime_tvm_dependencies}) - target_link_libraries(onnxruntime_providers_cuda PRIVATE cudart cublas cudnn curand cufft onnxruntime_providers_shared) + target_link_libraries(onnxruntime_providers_cuda PRIVATE cudart cublas cudnn curand cufft ${ONNXRUNTIME_PROVIDERS_SHARED}) target_include_directories(onnxruntime_providers_cuda PRIVATE ${ONNXRUNTIME_ROOT} ${CMAKE_CURRENT_BINARY_DIR} ${onnxruntime_CUDNN_HOME}/include ${eigen_INCLUDE_DIRS} ${TVM_INCLUDES} PUBLIC ${CMAKE_CUDA_TOOLKIT_INCLUDE_DIRECTORIES}) # ${CMAKE_CURRENT_BINARY_DIR} is so that #include "onnxruntime_config.h" inside tensor_shape.h is found install(DIRECTORY ${PROJECT_SOURCE_DIR}/../include/onnxruntime/core/providers/cuda DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}/onnxruntime/core/providers) @@ -381,36 +415,6 @@ if (onnxruntime_USE_CUDA) endif() -if (NOT onnxruntime_MINIMAL_BUILD AND NOT onnxruntime_EXTENDED_MINIMAL_BUILD - AND NOT ${CMAKE_SYSTEM_NAME} MATCHES "Darwin|iOS" - AND NOT (CMAKE_SYSTEM_NAME STREQUAL "Android") - AND NOT onnxruntime_BUILD_WEBASSEMBLY) - file(GLOB onnxruntime_providers_shared_cc_srcs CONFIGURE_DEPENDS - "${ONNXRUNTIME_ROOT}/core/providers/shared/*.h" - "${ONNXRUNTIME_ROOT}/core/providers/shared/*.cc" - ) - - source_group(TREE ${ONNXRUNTIME_ROOT}/core FILES ${onnxruntime_providers_shared_cc_srcs}) - onnxruntime_add_shared_library(onnxruntime_providers_shared ${onnxruntime_providers_shared_cc_srcs}) - set_target_properties(onnxruntime_providers_shared PROPERTIES FOLDER "ONNXRuntime") - set_target_properties(onnxruntime_providers_shared PROPERTIES LINKER_LANGUAGE CXX) - - if(APPLE) - set_property(TARGET onnxruntime_providers_shared APPEND_STRING PROPERTY LINK_FLAGS "-Xlinker -exported_symbols_list ${ONNXRUNTIME_ROOT}/core/providers/shared/exported_symbols.lst") - elseif(UNIX) - set_property(TARGET onnxruntime_providers_shared APPEND_STRING PROPERTY LINK_FLAGS "-Xlinker --version-script=${ONNXRUNTIME_ROOT}/core/providers/shared/version_script.lds -Xlinker --gc-sections") - elseif(WIN32) - set_property(TARGET onnxruntime_providers_shared APPEND_STRING PROPERTY LINK_FLAGS "-DEF:${ONNXRUNTIME_ROOT}/core/providers/shared/symbols.def") - else() - message(FATAL_ERROR "onnxruntime_providers_shared unknown platform, need to specify shared library exports for it") - endif() - - install(TARGETS onnxruntime_providers_shared - ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR} - LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} - RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR}) -endif() - if (onnxruntime_USE_DNNL) file(GLOB_RECURSE onnxruntime_providers_dnnl_cc_srcs CONFIGURE_DEPENDS "${ONNXRUNTIME_ROOT}/core/providers/dnnl/*.h" @@ -426,7 +430,7 @@ if (onnxruntime_USE_DNNL) add_dependencies(onnxruntime_providers_dnnl onnxruntime_providers_shared project_dnnl ${onnxruntime_EXTERNAL_DEPENDENCIES}) target_include_directories(onnxruntime_providers_dnnl PRIVATE ${ONNXRUNTIME_ROOT} ${CMAKE_CURRENT_BINARY_DIR} ${eigen_INCLUDE_DIRS} ${DNNL_INCLUDE_DIR} ${DNNL_OCL_INCLUDE_DIR}) # ${CMAKE_CURRENT_BINARY_DIR} is so that #include "onnxruntime_config.h" inside tensor_shape.h is found - target_link_libraries(onnxruntime_providers_dnnl PRIVATE dnnl onnxruntime_providers_shared) + target_link_libraries(onnxruntime_providers_dnnl PRIVATE dnnl ${ONNXRUNTIME_PROVIDERS_SHARED}) install(DIRECTORY ${PROJECT_SOURCE_DIR}/../include/onnxruntime/core/providers/dnnl DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}/onnxruntime/core/providers) set_target_properties(onnxruntime_providers_dnnl PROPERTIES FOLDER "ONNXRuntime") set_target_properties(onnxruntime_providers_dnnl PROPERTIES LINKER_LANGUAGE CXX) @@ -510,7 +514,7 @@ if (onnxruntime_USE_TENSORRT) onnxruntime_add_shared_library_module(onnxruntime_providers_tensorrt ${onnxruntime_providers_tensorrt_cc_srcs}) onnxruntime_add_include_to_target(onnxruntime_providers_tensorrt onnxruntime_common onnx flatbuffers) add_dependencies(onnxruntime_providers_tensorrt onnxruntime_providers_shared ${onnxruntime_EXTERNAL_DEPENDENCIES}) - target_link_libraries(onnxruntime_providers_tensorrt PRIVATE ${onnxparser_link_libs} ${trt_link_libs} cudart onnxruntime_providers_shared protobuf::libprotobuf flatbuffers) + target_link_libraries(onnxruntime_providers_tensorrt PRIVATE ${onnxparser_link_libs} ${trt_link_libs} cudart ${ONNXRUNTIME_PROVIDERS_SHARED} protobuf::libprotobuf flatbuffers) target_include_directories(onnxruntime_providers_tensorrt PRIVATE ${ONNXRUNTIME_ROOT} ${CMAKE_CURRENT_BINARY_DIR} ${onnxruntime_CUDNN_HOME}/include ${eigen_INCLUDE_DIRS} PUBLIC ${CMAKE_CUDA_TOOLKIT_INCLUDE_DIRECTORIES}) # ${CMAKE_CURRENT_BINARY_DIR} is so that #include "onnxruntime_config.h" inside tensor_shape.h is found install(DIRECTORY ${PROJECT_SOURCE_DIR}/../include/onnxruntime/core/providers/tensorrt DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}/onnxruntime/core/providers) @@ -637,7 +641,7 @@ if (onnxruntime_USE_OPENVINO) set_target_properties(onnxruntime_providers_openvino PROPERTIES FOLDER "ONNXRuntime") add_dependencies(onnxruntime_providers_openvino onnxruntime_providers_shared ${onnxruntime_EXTERNAL_DEPENDENCIES}) target_include_directories(onnxruntime_providers_openvino SYSTEM PUBLIC ${ONNXRUNTIME_ROOT} ${CMAKE_CURRENT_BINARY_DIR} ${eigen_INCLUDE_DIRS} ${OPENVINO_INCLUDE_DIR_LIST} ${PYTHON_INCLUDE_DIRS}) - target_link_libraries(onnxruntime_providers_openvino onnxruntime_providers_shared ${OPENVINO_LIB_LIST}) + target_link_libraries(onnxruntime_providers_openvino ${ONNXRUNTIME_PROVIDERS_SHARED} ${OPENVINO_LIB_LIST}) if(MSVC) target_compile_options(onnxruntime_providers_openvino PUBLIC /wd4099 /wd4275 /wd4100 /wd4005 /wd4244 /wd4267) diff --git a/onnxruntime/core/framework/ex_lib_loader.cc b/onnxruntime/core/framework/ex_lib_loader.cc index 391106d426..7070cbf9f1 100644 --- a/onnxruntime/core/framework/ex_lib_loader.cc +++ b/onnxruntime/core/framework/ex_lib_loader.cc @@ -38,7 +38,7 @@ common::Status ExLibLoader::LoadExternalLib(const std::string& dso_file_path, } void* lib_handle = nullptr; - ORT_RETURN_IF_ERROR(Env::Default().LoadDynamicLibrary(dso_file_path, &lib_handle)); + ORT_RETURN_IF_ERROR(Env::Default().LoadDynamicLibrary(dso_file_path, false, &lib_handle)); dso_name_data_map_[dso_file_path] = lib_handle; *handle = lib_handle; return Status::OK(); diff --git a/onnxruntime/core/framework/provider_bridge_ort.cc b/onnxruntime/core/framework/provider_bridge_ort.cc index 554b3eea37..155b8c8b6e 100644 --- a/onnxruntime/core/framework/provider_bridge_ort.cc +++ b/onnxruntime/core/framework/provider_bridge_ort.cc @@ -896,7 +896,7 @@ struct ProviderSharedLibrary { return true; std::string full_path = Env::Default().GetRuntimePath() + std::string(LIBRARY_PREFIX "onnxruntime_providers_shared" LIBRARY_EXTENSION); - auto error = Env::Default().LoadDynamicLibrary(full_path, &handle_); + auto error = Env::Default().LoadDynamicLibrary(full_path, true /*shared_globals on unix*/, &handle_); if (!error.IsOK()) { LOGS_DEFAULT(ERROR) << error.ErrorMessage(); return false; @@ -947,7 +947,7 @@ struct ProviderLibrary { return nullptr; std::string full_path = Env::Default().GetRuntimePath() + std::string(filename_); - auto error = Env::Default().LoadDynamicLibrary(full_path, &handle_); + auto error = Env::Default().LoadDynamicLibrary(full_path, false, &handle_); if (!error.IsOK()) { LOGS_DEFAULT(ERROR) << error.ErrorMessage(); return nullptr; diff --git a/onnxruntime/core/platform/env.h b/onnxruntime/core/platform/env.h index 8f412dd84a..3beec3a807 100644 --- a/onnxruntime/core/platform/env.h +++ b/onnxruntime/core/platform/env.h @@ -193,11 +193,13 @@ class Env { // loading a library. The rules for determining the exact location of the // library are platform-specific and are not documented here. // + // global_symbols only has an effect on unix, where a value of true means to load with RTLD_GLOBAL vs RTLD_LOCAL + // // On success, returns a handle to the library in "*handle" and returns // OK from the function. // Otherwise returns nullptr in "*handle" and an error status from the // function. - virtual common::Status LoadDynamicLibrary(const std::string& library_filename, void** handle) const = 0; + virtual common::Status LoadDynamicLibrary(const std::string& library_filename, bool global_symbols, void** handle) const = 0; virtual common::Status UnloadDynamicLibrary(void* handle) const = 0; diff --git a/onnxruntime/core/platform/posix/env.cc b/onnxruntime/core/platform/posix/env.cc index e48a364c35..3a05f424a2 100644 --- a/onnxruntime/core/platform/posix/env.cc +++ b/onnxruntime/core/platform/posix/env.cc @@ -411,9 +411,9 @@ class PosixEnv : public Env { return Status::OK(); } - common::Status LoadDynamicLibrary(const std::string& library_filename, void** handle) const override { + common::Status LoadDynamicLibrary(const std::string& library_filename, bool global_symbols, void** handle) const override { dlerror(); // clear any old error_str - *handle = dlopen(library_filename.c_str(), RTLD_NOW | RTLD_LOCAL); + *handle = dlopen(library_filename.c_str(), RTLD_NOW | (global_symbols ? RTLD_GLOBAL : RTLD_LOCAL)); char* error_str = dlerror(); if (!*handle) { return common::Status(common::ONNXRUNTIME, common::FAIL, diff --git a/onnxruntime/core/platform/windows/env.cc b/onnxruntime/core/platform/windows/env.cc index f33be15444..2fc7e9ae12 100644 --- a/onnxruntime/core/platform/windows/env.cc +++ b/onnxruntime/core/platform/windows/env.cc @@ -494,7 +494,7 @@ class WindowsEnv : public Env { return path.substr(0, slash_index + 1); } - virtual Status LoadDynamicLibrary(const std::string& library_filename, void** handle) const override { + virtual Status LoadDynamicLibrary(const std::string& library_filename, bool /*global_symbols*/, void** handle) const override { #if WINAPI_FAMILY == WINAPI_FAMILY_PC_APP *handle = ::LoadPackagedLibrary(ToWideString(library_filename).c_str(), 0); #else diff --git a/onnxruntime/core/providers/nuphar/common/nuphar_tvm_utils.cc b/onnxruntime/core/providers/nuphar/common/nuphar_tvm_utils.cc index 7e27842f1e..78e6a260fe 100644 --- a/onnxruntime/core/providers/nuphar/common/nuphar_tvm_utils.cc +++ b/onnxruntime/core/providers/nuphar/common/nuphar_tvm_utils.cc @@ -69,7 +69,7 @@ static bool GetCacheSoFilePath(std::string& so_path) { static void* GetFuncFromLibrary(const std::string& so_path, const std::string& func_name, bool throw_if_not_found = true) { void* so_handle; - ORT_ENFORCE(Env::Default().LoadDynamicLibrary(so_path, &so_handle).IsOK()); + ORT_ENFORCE(Env::Default().LoadDynamicLibrary(so_path, false, &so_handle).IsOK()); void* func = nullptr; Status s = Env::Default().GetSymbolFromLibrary(so_handle, func_name, &func); if (throw_if_not_found && !s.IsOK()) diff --git a/onnxruntime/core/session/onnxruntime_c_api.cc b/onnxruntime/core/session/onnxruntime_c_api.cc index 5c2b1fe9ac..e73bdbe18a 100644 --- a/onnxruntime/core/session/onnxruntime_c_api.cc +++ b/onnxruntime/core/session/onnxruntime_c_api.cc @@ -389,7 +389,7 @@ ORT_API_STATUS_IMPL(OrtApis::AddCustomOpDomain, _Inout_ OrtSessionOptions* optio ORT_API_STATUS_IMPL(OrtApis::RegisterCustomOpsLibrary, _Inout_ OrtSessionOptions* options, _In_ const char* library_path, void** library_handle) { API_IMPL_BEGIN - Env::Default().LoadDynamicLibrary(library_path, library_handle); + Env::Default().LoadDynamicLibrary(library_path, false, library_handle); if (!*library_handle) return OrtApis::CreateStatus(ORT_FAIL, "RegisterCustomOpsLibrary: Failed to load library"); diff --git a/onnxruntime/python/onnxruntime_pybind_state.cc b/onnxruntime/python/onnxruntime_pybind_state.cc index 74bf596d48..42d48584ea 100644 --- a/onnxruntime/python/onnxruntime_pybind_state.cc +++ b/onnxruntime/python/onnxruntime_pybind_state.cc @@ -252,7 +252,7 @@ static Env& platform_env = Env::Default(); CustomOpLibrary::CustomOpLibrary(const char* library_path, OrtSessionOptions& ort_so) { { - OrtPybindThrowIfError(platform_env.LoadDynamicLibrary(library_path, &library_handle_)); + OrtPybindThrowIfError(platform_env.LoadDynamicLibrary(library_path, false, &library_handle_)); OrtStatus*(ORT_API_CALL * RegisterCustomOps)(OrtSessionOptions * options, const OrtApiBase* api); @@ -455,7 +455,7 @@ static std::unique_ptr LoadExecutionProvider( const std::string& ep_shared_lib_path, const ProviderOptions& provider_options = {}) { void* handle; - auto error = Env::Default().LoadDynamicLibrary(ep_shared_lib_path, &handle); + auto error = Env::Default().LoadDynamicLibrary(ep_shared_lib_path, false, &handle); if (!error.IsOK()) { throw std::runtime_error(error.ErrorMessage()); }