Merge remote-tracking branch 'upstream/master' into HEAD

This commit is contained in:
Ryan Lai 2021-06-04 15:58:15 -07:00
commit 64f1a4ed22
194 changed files with 3762 additions and 1583 deletions

2
.gitmodules vendored
View file

@ -77,4 +77,4 @@
[submodule "cmake/external/emsdk"]
path = cmake/external/emsdk
url = https://github.com/emscripten-core/emsdk.git
branch = 2.0.13
branch = 2.0.23

View file

@ -5,9 +5,9 @@
"Component": {
"Type": "other",
"other": {
"Name": "patchelf",
"Version": "0.12",
"DownloadUrl": "https://github.com/NixOS/patchelf/archive/0.12.tar.gz"
"Name": "autoconf",
"Version": "2.71",
"DownloadUrl": "http://ftp.gnu.org/gnu/autoconf/autoconf-2.71.tar.gz"
},
"comments": "manylinux dependency"
}
@ -17,8 +17,8 @@
"Type": "other",
"other": {
"Name": "automake",
"Version": "1.16.2",
"DownloadUrl": "http://ftp.gnu.org/gnu/automake/automake-1.16.2.tar.gz"
"Version": "1.16.3",
"DownloadUrl": "http://ftp.gnu.org/gnu/automake/automake-1.16.3.tar.gz"
},
"comments": "manylinux dependency"
}
@ -38,20 +38,9 @@
"Component": {
"Type": "other",
"other": {
"Name": "sqlite_autoconf",
"Version": "3340000",
"DownloadUrl": "https://www.sqlite.org/2020/sqlite-autoconf-3340000.tar.gz"
},
"comments": "manylinux dependency"
}
},
{
"Component": {
"Type": "other",
"other": {
"Name": "cmake",
"Version": "3.18.3",
"DownloadUrl": "https://github.com/Kitware/CMake/releases/download/v3.18.3/cmake-3.18.3.tar.gz"
"Name": "patchelf",
"Version": "0.12",
"DownloadUrl": "https://github.com/NixOS/patchelf/archive/0.12.tar.gz"
},
"comments": "manylinux dependency"
}
@ -72,8 +61,52 @@
"Type": "other",
"other": {
"Name": "git",
"Version": "2.30.0",
"DownloadUrl": "https://www.kernel.org/pub/software/scm/git/git-2.30.0.tar.gz"
"Version": "2.31.1",
"DownloadUrl": "https://www.kernel.org/pub/software/scm/git/git-2.31.1.tar.gz"
},
"comments": "manylinux dependency"
}
},
{
"Component": {
"Type": "other",
"other": {
"Name": "cmake",
"Version": "3.20.2",
"DownloadUrl": "https://github.com/Kitware/CMake/releases/download/v3.20.2/cmake-3.20.2.tar.gz"
},
"comments": "manylinux dependency"
}
},
{
"Component": {
"Type": "other",
"other": {
"Name": "swig",
"Version": "4.0.2",
"DownloadUrl": "https://sourceforge.net/projects/swig/files/swig/${SWIG_ROOT}/swig-4.0.2.tar.gz"
},
"comments": "manylinux dependency"
}
},
{
"Component": {
"Type": "other",
"other": {
"Name": "sqlite_autoconf",
"Version": "3350500",
"DownloadUrl": "https://www.sqlite.org/2021/sqlite-autoconf-3350500.tar.gz"
},
"comments": "manylinux dependency"
}
},
{
"Component": {
"Type": "other",
"other": {
"Name": "openssl",
"Version": "1.1.1k",
"DownloadUrl": "https://www.openssl.org/source/openssl-1.1.1k.tar.gz"
},
"comments": "manylinux dependency"
}
@ -182,7 +215,7 @@
"component": {
"type": "git",
"git": {
"commitHash": "8b32b7def837a15e766039501630549149d3db41",
"commitHash": "f44b84154703d29a946d51ddee08f4e5725a61db",
"repositoryUrl": "https://github.com/emscripten-core/emsdk.git"
},
"comments": "git submodule at cmake/external/emsdk"

View file

@ -15,25 +15,24 @@ package_url = None
registrations = []
with open(os.path.join(REPO_DIR, 'tools', 'ci_build', 'github', 'linux', 'docker', 'manylinux2014_build_scripts',
'build_env.sh'), "r") as f:
with open(os.path.join(REPO_DIR, 'tools', 'ci_build', 'github', 'linux', 'docker', 'Dockerfile.manylinux2014_cuda11'), "r") as f:
for line in f:
if not line.strip():
package_name = None
package_filename = None
package_url = None
if package_filename is None:
m = re.match("(.+?)_ROOT=(.*)$", line)
m = re.match("RUN\s+export\s+(.+?)_ROOT=(\S+).*", line)
if m is not None:
package_name = m.group(1)
package_filename = m.group(2)
else:
m = re.match("(.+?)_VERSION=(.*)$", line)
m = re.match("RUN\s+export\s+(.+?)_VERSION=(\S+).*", line)
if m is not None:
package_name = m.group(1)
package_filename = m.group(2)
elif package_url is None:
m = re.match("(.+?)_DOWNLOAD_URL=(.+)$", line)
m = re.match("(.+?)_DOWNLOAD_URL=(\S+)", line)
if m is not None:
package_url = m.group(2)
if package_name == 'LIBXCRYPT':

View file

@ -3,12 +3,14 @@
# Licensed under the MIT License.
# Minimum CMake required
cmake_minimum_required(VERSION 3.13)
cmake_minimum_required(VERSION 3.18)
cmake_policy(SET CMP0069 NEW)
set(CMAKE_POLICY_DEFAULT_CMP0069 NEW)
if (${CMAKE_VERSION} VERSION_GREATER_EQUAL "3.15")
cmake_policy(SET CMP0092 NEW)
cmake_policy(SET CMP0092 NEW)
cmake_policy(SET CMP0091 NEW)
if (${CMAKE_VERSION} VERSION_GREATER_EQUAL "3.20")
cmake_policy(SET CMP0117 NEW)
endif()
# Support OS X versions 10.12+
@ -29,6 +31,7 @@ set (CMAKE_C_STANDARD 99)
include(CheckCXXCompilerFlag)
include(CheckLanguage)
include(CMakeDependentOption)
set(CMAKE_CXX_STANDARD 14)
@ -61,8 +64,6 @@ option(onnxruntime_USE_RKNPU "Build with RKNPU support" OFF)
option(onnxruntime_USE_DNNL "Build with DNNL support" OFF)
option(onnxruntime_USE_FEATURIZERS "Build ML Featurizers support" OFF)
option(onnxruntime_DEV_MODE "Enable developer warnings and treat most of them as error." OFF)
option(onnxruntime_MSVC_STATIC_RUNTIME "Compile for the static CRT" OFF)
option(onnxruntime_GCC_STATIC_CPP_RUNTIME "Compile for the static libstdc++" OFF)
option(onnxruntime_BUILD_UNIT_TESTS "Build ONNXRuntime unit tests" ON)
option(onnxruntime_BUILD_CSHARP "Build C# library" OFF)
option(onnxruntime_BUILD_OBJC "Build Objective-C library" OFF)
@ -116,7 +117,7 @@ option(onnxruntime_USE_ROCM "Build with AMD GPU support" OFF)
# Options related to reducing the binary size produced by the build
option(onnxruntime_DISABLE_CONTRIB_OPS "Disable contrib ops" OFF)
option(onnxruntime_DISABLE_ML_OPS "Disable traditional ML ops" OFF)
option(onnxruntime_DISABLE_RTTI "Disable RTTI" OFF)
cmake_dependent_option(onnxruntime_DISABLE_RTTI "Disable RTTI" ON "NOT onnxruntime_ENABLE_PYTHON" OFF)
# For now onnxruntime_DISABLE_EXCEPTIONS will only work with onnxruntime_MINIMAL_BUILD, more changes (ONNX, non-CPU EP, ...) are required to run this standalone
option(onnxruntime_DISABLE_EXCEPTIONS "Disable exception handling. Requires onnxruntime_MINIMAL_BUILD currently." OFF)
option(onnxruntime_MINIMAL_BUILD "Exclude as much as possible from the build. Support ORT format models. No support for ONNX format models." OFF)
@ -379,6 +380,12 @@ if(onnxruntime_DISABLE_RTTI)
else()
add_compile_options("$<$<COMPILE_LANGUAGE:CXX>:-fno-rtti>")
endif()
else()
#MSVC RTTI flag /GR is not added to CMAKE_CXX_FLAGS by default. But, anyway VC++2019 treats "/GR" default on.
#So we don't need the following three lines. But it's better to make it more explicit.
if(MSVC)
add_compile_options("$<$<COMPILE_LANGUAGE:CXX>:/GR>")
endif()
endif()
# If this is only enabled in an onnxruntime_ORT_MODEL_FORMAT_ONLY build we don't need ONNX changes
@ -474,33 +481,6 @@ endmacro()
#Set global compile flags for all the source code(including third_party code like protobuf)
#This section must be before any add_subdirectory, otherwise build may fail because /MD,/MT mismatch
if (MSVC)
if (onnxruntime_MSVC_STATIC_RUNTIME)
# set all of our submodules to static runtime
set(ONNX_USE_MSVC_STATIC_RUNTIME ON)
set(protobuf_MSVC_STATIC_RUNTIME ON CACHE BOOL "" FORCE)
set(gtest_force_shared_crt OFF CACHE BOOL "" FORCE)
# In case we are building static libraries, link also the runtime library statically
# so that MSVCR*.DLL is not required at runtime.
# https://msdn.microsoft.com/en-us/library/2kzt1wy3.aspx
# This is achieved by replacing msvc option /MD with /MT and /MDd with /MTd
# https://gitlab.kitware.com/cmake/community/wikis/FAQ#how-can-i-build-my-msvc-application-with-a-static-runtime
foreach(flag_var
CMAKE_CXX_FLAGS CMAKE_CXX_FLAGS_DEBUG CMAKE_CXX_FLAGS_RELEASE
CMAKE_CXX_FLAGS_MINSIZEREL CMAKE_CXX_FLAGS_RELWITHDEBINFO
CMAKE_C_FLAGS CMAKE_C_FLAGS_DEBUG CMAKE_C_FLAGS_RELEASE
CMAKE_C_FLAGS_MINSIZEREL CMAKE_C_FLAGS_RELWITHDEBINFO)
if(${flag_var} MATCHES "/MD")
string(REGEX REPLACE "/MD" "/MT" ${flag_var} "${${flag_var}}")
endif(${flag_var} MATCHES "/MD")
endforeach(flag_var)
else()
set(ONNX_USE_MSVC_STATIC_RUNTIME OFF)
set(protobuf_WITH_ZLIB OFF CACHE BOOL "" FORCE)
set(protobuf_MSVC_STATIC_RUNTIME OFF CACHE BOOL "Link protobuf to static runtime libraries" FORCE)
set(gtest_force_shared_crt ON CACHE BOOL "Use shared (DLL) run-time lib for gtest" FORCE)
endif()
#Always enable exception handling, even for Windows ARM
if(NOT onnxruntime_DISABLE_EXCEPTIONS)
string(APPEND CMAKE_CXX_FLAGS " /EHsc /wd26812")
@ -558,9 +538,6 @@ else()
string(APPEND CMAKE_CXX_FLAGS " -mavx512f -mavx512cd -mavx512bw -mavx512dq -mavx512vl")
string(APPEND CMAKE_C_FLAGS " -mavx512f -mavx512cd -mavx512bw -mavx512dq -mavx512vl")
endif()
if(onnxruntime_GCC_STATIC_CPP_RUNTIME)
string(APPEND CMAKE_CXX_FLAGS " -static-libstdc++")
endif()
# Check support for AVX and f16c.
include(CheckCXXCompilerFlag)
@ -629,6 +606,8 @@ if (onnxruntime_BUILD_UNIT_TESTS)
add_subdirectory(${PROJECT_SOURCE_DIR}/external/googletest EXCLUDE_FROM_ALL)
set_msvc_c_cpp_compiler_warning_level(3)
set_target_properties(gmock PROPERTIES FOLDER "External/GTest")
# disable treating all warnings as errors for gmock
target_compile_options(gmock PRIVATE "-w")
set_target_properties(gmock_main PROPERTIES FOLDER "External/GTest")
set_target_properties(gtest PROPERTIES FOLDER "External/GTest")
set_target_properties(gtest_main PROPERTIES FOLDER "External/GTest")
@ -650,10 +629,13 @@ endif()
#Need python to generate def file
if(onnxruntime_BUILD_SHARED_LIB OR onnxruntime_ENABLE_PYTHON)
if(onnxruntime_ENABLE_PYTHON)
find_package(PythonInterp 3.5 REQUIRED)
find_package(PythonLibs 3.5 REQUIRED)
if(onnxruntime_ENABLE_LANGUAGE_INTEROP_OPS)
find_package(Python 3.6 COMPONENTS Interpreter Development NumPy)
else()
find_package(Python 3.6 COMPONENTS Interpreter Development.Module NumPy)
endif()
else()
find_package(PythonInterp 3.4 REQUIRED)
find_package(Python 3.6 COMPONENTS Interpreter)
endif()
endif()
@ -713,8 +695,11 @@ else()
if (CMAKE_SYSTEM_NAME STREQUAL "Android")
set(protobuf_BUILD_PROTOC_BINARIES OFF CACHE BOOL "Build protobuf tests" FORCE)
endif()
if(onnxruntime_DISABLE_RTTI)
set(protobuf_DISABLE_RTTI OFF CACHE BOOL "Remove runtime type information in the binaries" FORCE)
endif()
add_subdirectory(${PROJECT_SOURCE_DIR}/external/protobuf/cmake EXCLUDE_FROM_ALL)
if(TARGET libprotoc)
set_target_properties(libprotoc PROPERTIES FOLDER "External/Protobuf")
add_executable(protobuf::protoc ALIAS protoc)
@ -723,10 +708,8 @@ else()
set_target_properties(protoc PROPERTIES FOLDER "External/Protobuf")
endif()
if (onnxruntime_USE_FULL_PROTOBUF)
add_library(protobuf::libprotobuf ALIAS libprotobuf)
set(PROTOBUF_LIB libprotobuf)
else()
add_library(protobuf::libprotobuf ALIAS libprotobuf-lite)
set(PROTOBUF_LIB libprotobuf-lite)
endif()
endif()

@ -1 +1 @@
Subproject commit 8b32b7def837a15e766039501630549149d3db41
Subproject commit f44b84154703d29a946d51ddee08f4e5725a61db

View file

@ -11,14 +11,14 @@ if(flake8_BIN)
else()
# see if we can run the python module instead if there's no executable
set(FLAKE8_NOT_FOUND false)
exec_program("${PYTHON_EXECUTABLE}"
exec_program("${Python_EXECUTABLE}"
ARGS "-m flake8 --version"
OUTPUT_VARIABLE FLAKE8_VERSION
RETURN_VALUE FLAKE8_NOT_FOUND)
if(${FLAKE8_NOT_FOUND})
message(WARNING "Could not find 'flake8' to check python scripts. Please install flake8 using pip.")
else()
set(flake8_BIN ${PYTHON_EXECUTABLE} "-m" "flake8")
set(flake8_BIN ${Python_EXECUTABLE} "-m" "flake8")
endif(${FLAKE8_NOT_FOUND})
endif()

View file

@ -43,7 +43,7 @@ foreach(f ${ONNXRUNTIME_PROVIDER_NAMES})
endforeach()
add_custom_command(OUTPUT ${SYMBOL_FILE} ${CMAKE_CURRENT_BINARY_DIR}/generated_source.c
COMMAND ${PYTHON_EXECUTABLE} "${REPO_ROOT}/tools/ci_build/gen_def.py"
COMMAND ${Python_EXECUTABLE} "${REPO_ROOT}/tools/ci_build/gen_def.py"
--version_file "${ONNXRUNTIME_ROOT}/../VERSION_NUMBER" --src_root "${ONNXRUNTIME_ROOT}"
--config ${ONNXRUNTIME_PROVIDER_NAMES} --style=${OUTPUT_STYLE} --output ${SYMBOL_FILE}
--output_source ${CMAKE_CURRENT_BINARY_DIR}/generated_source.c
@ -66,10 +66,14 @@ elseif(onnxruntime_BUILD_APPLE_FRAMEWORK)
"${CMAKE_CURRENT_BINARY_DIR}/generated_source.c"
)
# create Info.plist for the framework and podspec for CocoaPods (optional)
set(MACOSX_FRAMEWORK_NAME "onnxruntime")
set(MACOSX_FRAMEWORK_IDENTIFIER "com.microsoft.onnxruntime")
configure_file(${REPO_ROOT}/cmake/Info.plist.in ${CMAKE_CURRENT_BINARY_DIR}/Info.plist)
configure_file(
${REPO_ROOT}/tools/ci_build/github/apple/onnxruntime-mobile-c.podspec.template
${CMAKE_CURRENT_BINARY_DIR}/onnxruntime-mobile-c.podspec
)
set_target_properties(onnxruntime PROPERTIES
FRAMEWORK TRUE
FRAMEWORK_VERSION A

View file

@ -19,7 +19,7 @@ source_group(TREE ${ONNXRUNTIME_ROOT}/core FILES ${onnxruntime_codegen_common_sr
onnxruntime_add_static_library(onnxruntime_codegen_tvm ${onnxruntime_codegen_common_srcs} ${onnxruntime_codegen_tvm_srcs})
set_target_properties(onnxruntime_codegen_tvm PROPERTIES FOLDER "ONNXRuntime")
target_include_directories(onnxruntime_codegen_tvm PRIVATE ${ONNXRUNTIME_ROOT} ${TVM_INCLUDES} ${MKLML_INCLUDE_DIR} ${eigen_INCLUDE_DIRS})
onnxruntime_add_include_to_target(onnxruntime_codegen_tvm onnxruntime_common onnxruntime_framework onnx onnx_proto protobuf::libprotobuf flatbuffers)
onnxruntime_add_include_to_target(onnxruntime_codegen_tvm onnxruntime_common onnxruntime_framework onnx onnx_proto ${PROTOBUF_LIB} flatbuffers)
target_compile_options(onnxruntime_codegen_tvm PRIVATE ${DISABLED_WARNINGS_FOR_TVM})
# need onnx to build to create headers that this project includes
add_dependencies(onnxruntime_codegen_tvm ${onnxruntime_EXTERNAL_DEPENDENCIES})

View file

@ -10,7 +10,7 @@ source_group(TREE ${REPO_ROOT} FILES ${onnxruntime_eager_srcs})
add_library(onnxruntime_eager ${onnxruntime_eager_srcs})
install(DIRECTORY ${PROJECT_SOURCE_DIR}/../include/onnxruntime/core/eager DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}/onnxruntime/core)
onnxruntime_add_include_to_target(onnxruntime_eager onnxruntime_common onnxruntime_framework onnxruntime_optimizer onnxruntime_graph onnx onnx_proto protobuf::libprotobuf flatbuffers)
onnxruntime_add_include_to_target(onnxruntime_eager onnxruntime_common onnxruntime_framework onnxruntime_optimizer onnxruntime_graph onnx onnx_proto ${PROTOBUF_LIB} flatbuffers)
if(onnxruntime_ENABLE_INSTRUMENT)
target_compile_definitions(onnxruntime_eager PUBLIC ONNXRUNTIME_ENABLE_INSTRUMENT)
endif()

View file

@ -44,7 +44,7 @@ if (onnxruntime_ENABLE_TRAINING OR onnxruntime_ENABLE_TRAINING_OPS)
target_include_directories(onnxruntime_framework PUBLIC ${MPI_CXX_INCLUDE_DIRS})
endif()
endif()
onnxruntime_add_include_to_target(onnxruntime_framework onnxruntime_common onnx onnx_proto protobuf::libprotobuf flatbuffers)
onnxruntime_add_include_to_target(onnxruntime_framework onnxruntime_common onnx onnx_proto ${PROTOBUF_LIB} flatbuffers)
set_target_properties(onnxruntime_framework PROPERTIES FOLDER "ONNXRuntime")
# need onnx to build to create headers that this project includes
add_dependencies(onnxruntime_framework ${onnxruntime_EXTERNAL_DEPENDENCIES})

View file

@ -80,7 +80,7 @@ endif()
onnxruntime_add_static_library(onnxruntime_graph ${onnxruntime_graph_lib_src})
add_dependencies(onnxruntime_graph onnx_proto flatbuffers)
onnxruntime_add_include_to_target(onnxruntime_graph onnxruntime_common onnx onnx_proto protobuf::libprotobuf flatbuffers)
onnxruntime_add_include_to_target(onnxruntime_graph onnxruntime_common onnx onnx_proto ${PROTOBUF_LIB} flatbuffers)
if (onnxruntime_ENABLE_TRAINING)
#TODO: the graph library should focus on ONNX IR, it shouldn't depend on math libraries like MKLML/OpenBlas

View file

@ -132,19 +132,19 @@ file(MAKE_DIRECTORY ${JAVA_PACKAGE_JNI_DIR})
if (WIN32)
#Our static analysis plugin set /p:LinkCompiled=false
if(NOT onnxruntime_ENABLE_STATIC_ANALYSIS)
add_custom_command(TARGET onnxruntime4j_jni POST_BUILD COMMAND ${CMAKE_COMMAND} -E create_symlink $<TARGET_FILE:onnxruntime> ${JAVA_PACKAGE_LIB_DIR}/$<TARGET_FILE_NAME:onnxruntime>)
add_custom_command(TARGET onnxruntime4j_jni POST_BUILD COMMAND ${CMAKE_COMMAND} -E create_symlink $<TARGET_FILE:onnxruntime4j_jni> ${JAVA_PACKAGE_JNI_DIR}/$<TARGET_FILE_NAME:onnxruntime4j_jni>)
add_custom_command(TARGET onnxruntime4j_jni POST_BUILD COMMAND ${CMAKE_COMMAND} -E copy_if_different $<TARGET_FILE:onnxruntime> ${JAVA_PACKAGE_LIB_DIR}/$<TARGET_FILE_NAME:onnxruntime>)
add_custom_command(TARGET onnxruntime4j_jni POST_BUILD COMMAND ${CMAKE_COMMAND} -E copy_if_different $<TARGET_FILE:onnxruntime4j_jni> ${JAVA_PACKAGE_JNI_DIR}/$<TARGET_FILE_NAME:onnxruntime4j_jni>)
if (onnxruntime_USE_CUDA)
add_custom_command(TARGET onnxruntime4j_jni POST_BUILD COMMAND ${CMAKE_COMMAND} -E create_symlink $<TARGET_FILE:onnxruntime_providers_shared> ${JAVA_PACKAGE_LIB_DIR}/$<TARGET_FILE_NAME:onnxruntime_providers_shared>)
add_custom_command(TARGET onnxruntime4j_jni POST_BUILD COMMAND ${CMAKE_COMMAND} -E create_symlink $<TARGET_FILE:onnxruntime_providers_cuda> ${JAVA_PACKAGE_LIB_DIR}/$<TARGET_FILE_NAME:onnxruntime_providers_cuda>)
add_custom_command(TARGET onnxruntime4j_jni POST_BUILD COMMAND ${CMAKE_COMMAND} -E copy_if_different $<TARGET_FILE:onnxruntime_providers_shared> ${JAVA_PACKAGE_LIB_DIR}/$<TARGET_FILE_NAME:onnxruntime_providers_shared>)
add_custom_command(TARGET onnxruntime4j_jni POST_BUILD COMMAND ${CMAKE_COMMAND} -E copy_if_different $<TARGET_FILE:onnxruntime_providers_cuda> ${JAVA_PACKAGE_LIB_DIR}/$<TARGET_FILE_NAME:onnxruntime_providers_cuda>)
endif()
endif()
else()
add_custom_command(TARGET onnxruntime4j_jni POST_BUILD COMMAND ${CMAKE_COMMAND} -E create_symlink $<TARGET_FILE:onnxruntime> ${JAVA_PACKAGE_LIB_DIR}/$<TARGET_LINKER_FILE_NAME:onnxruntime>)
add_custom_command(TARGET onnxruntime4j_jni POST_BUILD COMMAND ${CMAKE_COMMAND} -E create_symlink $<TARGET_FILE:onnxruntime4j_jni> ${JAVA_PACKAGE_JNI_DIR}/$<TARGET_LINKER_FILE_NAME:onnxruntime4j_jni>)
add_custom_command(TARGET onnxruntime4j_jni POST_BUILD COMMAND ${CMAKE_COMMAND} -E copy_if_different $<TARGET_FILE:onnxruntime> ${JAVA_PACKAGE_LIB_DIR}/$<TARGET_LINKER_FILE_NAME:onnxruntime>)
add_custom_command(TARGET onnxruntime4j_jni POST_BUILD COMMAND ${CMAKE_COMMAND} -E copy_if_different $<TARGET_FILE:onnxruntime4j_jni> ${JAVA_PACKAGE_JNI_DIR}/$<TARGET_LINKER_FILE_NAME:onnxruntime4j_jni>)
if (onnxruntime_USE_CUDA)
add_custom_command(TARGET onnxruntime4j_jni POST_BUILD COMMAND ${CMAKE_COMMAND} -E create_symlink $<TARGET_FILE:onnxruntime_providers_shared> ${JAVA_PACKAGE_LIB_DIR}/$<TARGET_LINKER_FILE_NAME:onnxruntime_providers_shared>)
add_custom_command(TARGET onnxruntime4j_jni POST_BUILD COMMAND ${CMAKE_COMMAND} -E create_symlink $<TARGET_FILE:onnxruntime_providers_cuda> ${JAVA_PACKAGE_LIB_DIR}/$<TARGET_LINKER_FILE_NAME:onnxruntime_providers_cuda>)
add_custom_command(TARGET onnxruntime4j_jni POST_BUILD COMMAND ${CMAKE_COMMAND} -E copy_if_different $<TARGET_FILE:onnxruntime_providers_shared> ${JAVA_PACKAGE_LIB_DIR}/$<TARGET_LINKER_FILE_NAME:onnxruntime_providers_shared>)
add_custom_command(TARGET onnxruntime4j_jni POST_BUILD COMMAND ${CMAKE_COMMAND} -E copy_if_different $<TARGET_FILE:onnxruntime_providers_cuda> ${JAVA_PACKAGE_LIB_DIR}/$<TARGET_LINKER_FILE_NAME:onnxruntime_providers_cuda>)
endif()
endif()
@ -170,9 +170,9 @@ if (CMAKE_SYSTEM_NAME STREQUAL "Android")
file(MAKE_DIRECTORY ${ANDROID_PACKAGE_JNILIBS_DIR})
file(MAKE_DIRECTORY ${ANDROID_PACKAGE_ABI_DIR})
# Create symbolic links for onnxruntime.so and onnxruntime4j_jni.so for building Android AAR package
add_custom_command(TARGET onnxruntime4j_jni POST_BUILD COMMAND ${CMAKE_COMMAND} -E create_symlink $<TARGET_FILE:onnxruntime> ${ANDROID_PACKAGE_ABI_DIR}/$<TARGET_LINKER_FILE_NAME:onnxruntime>)
add_custom_command(TARGET onnxruntime4j_jni POST_BUILD COMMAND ${CMAKE_COMMAND} -E create_symlink $<TARGET_FILE:onnxruntime4j_jni> ${ANDROID_PACKAGE_ABI_DIR}/$<TARGET_LINKER_FILE_NAME:onnxruntime4j_jni>)
# Copy onnxruntime.so and onnxruntime4j_jni.so for building Android AAR package
add_custom_command(TARGET onnxruntime4j_jni POST_BUILD COMMAND ${CMAKE_COMMAND} -E copy_if_different $<TARGET_FILE:onnxruntime> ${ANDROID_PACKAGE_ABI_DIR}/$<TARGET_LINKER_FILE_NAME:onnxruntime>)
add_custom_command(TARGET onnxruntime4j_jni POST_BUILD COMMAND ${CMAKE_COMMAND} -E copy_if_different $<TARGET_FILE:onnxruntime4j_jni> ${ANDROID_PACKAGE_ABI_DIR}/$<TARGET_LINKER_FILE_NAME:onnxruntime4j_jni>)
# Generate the Android AAR package
add_custom_command(TARGET onnxruntime4j_jni POST_BUILD COMMAND ${GRADLE_EXECUTABLE} -b build-android.gradle -c settings-android.gradle build -DjniLibsDir=${ANDROID_PACKAGE_JNILIBS_DIR} -DbuildDir=${ANDROID_PACKAGE_OUTPUT_DIR} -DminSdkVer=${ANDROID_MIN_SDK} WORKING_DIRECTORY ${JAVA_ROOT})
@ -185,7 +185,7 @@ if (CMAKE_SYSTEM_NAME STREQUAL "Android")
set(ANDROID_TEST_PACKAGE_LIB_DIR ${ANDROID_TEST_PACKAGE_DIR}/app/libs)
file(MAKE_DIRECTORY ${ANDROID_TEST_PACKAGE_LIB_DIR})
# Copy the built Android AAR package to libs folder of our test app
add_custom_command(TARGET onnxruntime4j_jni POST_BUILD COMMAND ${CMAKE_COMMAND} -E create_symlink ${ANDROID_PACKAGE_OUTPUT_DIR}/outputs/aar/onnxruntime-debug.aar ${ANDROID_TEST_PACKAGE_LIB_DIR}/onnxruntime-debug.aar)
add_custom_command(TARGET onnxruntime4j_jni POST_BUILD COMMAND ${CMAKE_COMMAND} -E copy_if_different ${ANDROID_PACKAGE_OUTPUT_DIR}/outputs/aar/onnxruntime-debug.aar ${ANDROID_TEST_PACKAGE_LIB_DIR}/onnxruntime-debug.aar)
# Build Android test apk for java package
add_custom_command(TARGET onnxruntime4j_jni POST_BUILD COMMAND ${GRADLE_EXECUTABLE} clean WORKING_DIRECTORY ${ANDROID_TEST_PACKAGE_DIR})
add_custom_command(TARGET onnxruntime4j_jni POST_BUILD COMMAND ${GRADLE_EXECUTABLE} assembleDebug assembleDebugAndroidTest -DminSdkVer=${ANDROID_MIN_SDK} WORKING_DIRECTORY ${ANDROID_TEST_PACKAGE_DIR})

View file

@ -4,5 +4,5 @@ include(onnxruntime_pyop.cmake)
file (GLOB onnxruntime_language_interop_ops_src "${ONNXRUNTIME_ROOT}/core/language_interop_ops/language_interop_ops.cc")
onnxruntime_add_static_library(onnxruntime_language_interop ${onnxruntime_language_interop_ops_src})
add_dependencies(onnxruntime_language_interop onnxruntime_pyop)
onnxruntime_add_include_to_target(onnxruntime_language_interop onnxruntime_common onnxruntime_graph onnxruntime_framework onnxruntime_pyop onnx onnx_proto protobuf::libprotobuf flatbuffers)
onnxruntime_add_include_to_target(onnxruntime_language_interop onnxruntime_common onnxruntime_graph onnxruntime_framework onnxruntime_pyop onnx onnx_proto ${PROTOBUF_LIB} flatbuffers)
target_include_directories(onnxruntime_language_interop PRIVATE ${ONNXRUNTIME_ROOT} ${eigen_INCLUDE_DIRS})

View file

@ -45,6 +45,7 @@ set(OBJC_ROOT "${REPO_ROOT}/objectivec")
# explicitly list them here so it is easy to see what is included
set(onnxruntime_objc_headers
"${OBJC_ROOT}/include/onnxruntime.h"
"${OBJC_ROOT}/include/ort_coreml_execution_provider.h"
"${OBJC_ROOT}/include/ort_enums.h"
"${OBJC_ROOT}/include/ort_env.h"
"${OBJC_ROOT}/include/ort_session.h"
@ -68,9 +69,15 @@ target_include_directories(onnxruntime_objc
PUBLIC
"${OBJC_ROOT}/include"
PRIVATE
"${ONNXRUNTIME_ROOT}/include/onnxruntime/core/session"
"${ONNXRUNTIME_INCLUDE_DIR}/core/session"
"${OBJC_ROOT}")
if(onnxruntime_USE_COREML)
target_include_directories(onnxruntime_objc
PRIVATE
"${ONNXRUNTIME_INCLUDE_DIR}/core/providers/coreml")
endif()
find_library(FOUNDATION_LIB Foundation REQUIRED)
target_link_libraries(onnxruntime_objc

View file

@ -31,7 +31,7 @@ source_group(TREE ${REPO_ROOT} FILES ${onnxruntime_optimizer_srcs})
onnxruntime_add_static_library(onnxruntime_optimizer ${onnxruntime_optimizer_srcs})
install(DIRECTORY ${PROJECT_SOURCE_DIR}/../include/onnxruntime/core/optimizer DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}/onnxruntime/core)
onnxruntime_add_include_to_target(onnxruntime_optimizer onnxruntime_common onnxruntime_framework onnx onnx_proto protobuf::libprotobuf flatbuffers)
onnxruntime_add_include_to_target(onnxruntime_optimizer onnxruntime_common onnxruntime_framework onnx onnx_proto ${PROTOBUF_LIB} flatbuffers)
target_include_directories(onnxruntime_optimizer PRIVATE ${ONNXRUNTIME_ROOT})
if (onnxruntime_ENABLE_TRAINING)
target_include_directories(onnxruntime_optimizer PRIVATE ${ORTTRAINING_ROOT})

View file

@ -170,7 +170,7 @@ if (MSVC)
target_compile_options(onnxruntime_providers PRIVATE "/wd4244")
endif()
endif()
onnxruntime_add_include_to_target(onnxruntime_providers onnxruntime_common onnxruntime_framework onnx onnx_proto protobuf::libprotobuf flatbuffers)
onnxruntime_add_include_to_target(onnxruntime_providers onnxruntime_common onnxruntime_framework onnx onnx_proto ${PROTOBUF_LIB} flatbuffers)
if (onnxruntime_BUILD_MS_EXPERIMENTAL_OPS)
target_compile_definitions(onnxruntime_providers PRIVATE BUILD_MS_EXPERIMENTAL_OPS=1)
@ -336,7 +336,7 @@ if (onnxruntime_USE_CUDA)
target_compile_options(onnxruntime_providers_cuda PRIVATE "$<$<COMPILE_LANGUAGE:CUDA>:SHELL:-Xcompiler /wd4834>")
target_compile_options(onnxruntime_providers_cuda PRIVATE "$<$<COMPILE_LANGUAGE:CUDA>:SHELL:-Xcompiler /wd4127>")
endif()
onnxruntime_add_include_to_target(onnxruntime_providers_cuda onnxruntime_common onnxruntime_framework onnx onnx_proto protobuf::libprotobuf flatbuffers)
onnxruntime_add_include_to_target(onnxruntime_providers_cuda onnxruntime_common onnxruntime_framework onnx onnx_proto ${PROTOBUF_LIB} flatbuffers)
if (onnxruntime_ENABLE_TRAINING OR onnxruntime_ENABLE_TRAINING_OPS)
onnxruntime_add_include_to_target(onnxruntime_providers_cuda onnxruntime_training)
target_link_libraries(onnxruntime_providers_cuda PRIVATE onnxruntime_training)
@ -514,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_LIB} 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)
@ -578,7 +578,7 @@ if (onnxruntime_USE_NUPHAR)
source_group(TREE ${ONNXRUNTIME_ROOT}/core FILES ${onnxruntime_providers_nuphar_cc_srcs})
onnxruntime_add_static_library(onnxruntime_providers_nuphar ${onnxruntime_providers_nuphar_cc_srcs})
onnxruntime_add_include_to_target(onnxruntime_providers_nuphar onnxruntime_common onnxruntime_framework onnx onnx_proto protobuf::libprotobuf flatbuffers)
onnxruntime_add_include_to_target(onnxruntime_providers_nuphar onnxruntime_common onnxruntime_framework onnx onnx_proto ${PROTOBUF_LIB} flatbuffers)
set_target_properties(onnxruntime_providers_nuphar PROPERTIES FOLDER "ONNXRuntime")
target_include_directories(onnxruntime_providers_nuphar PRIVATE ${ONNXRUNTIME_ROOT} ${TVM_INCLUDES} ${eigen_INCLUDE_DIRS})
set_target_properties(onnxruntime_providers_nuphar PROPERTIES LINKER_LANGUAGE CXX)
@ -595,7 +595,7 @@ if (onnxruntime_USE_VITISAI)
source_group(TREE ${ONNXRUNTIME_ROOT}/core FILES ${onnxruntime_providers_vitisai_cc_srcs})
onnxruntime_add_static_library(onnxruntime_providers_vitisai ${onnxruntime_providers_vitisai_cc_srcs})
onnxruntime_add_include_to_target(onnxruntime_providers_vitisai onnxruntime_common onnxruntime_framework onnx onnx_proto protobuf::libprotobuf flatbuffers)
onnxruntime_add_include_to_target(onnxruntime_providers_vitisai onnxruntime_common onnxruntime_framework onnx onnx_proto ${PROTOBUF_LIB} flatbuffers)
add_dependencies(onnxruntime_providers_vitisai ${onnxruntime_EXTERNAL_DEPENDENCIES})
set_target_properties(onnxruntime_providers_vitisai PROPERTIES FOLDER "ONNXRuntime")
target_include_directories(onnxruntime_providers_vitisai PRIVATE ${ONNXRUNTIME_ROOT} ${eigen_INCLUDE_DIRS} ${VITISAI_INCLUDE_DIR})
@ -681,8 +681,8 @@ if (onnxruntime_USE_COREML)
"${COREML_PROTO_ROOT}/*.proto"
)
onnxruntime_add_static_library(onnxruntime_coreml_proto ${coreml_proto_srcs})
target_include_directories(onnxruntime_coreml_proto PUBLIC $<TARGET_PROPERTY:protobuf::libprotobuf,INTERFACE_INCLUDE_DIRECTORIES> "${CMAKE_CURRENT_BINARY_DIR}")
target_compile_definitions(onnxruntime_coreml_proto PUBLIC $<TARGET_PROPERTY:protobuf::libprotobuf,INTERFACE_COMPILE_DEFINITIONS>)
target_include_directories(onnxruntime_coreml_proto PUBLIC $<TARGET_PROPERTY:${PROTOBUF_LIB},INTERFACE_INCLUDE_DIRECTORIES> "${CMAKE_CURRENT_BINARY_DIR}")
target_compile_definitions(onnxruntime_coreml_proto PUBLIC $<TARGET_PROPERTY:${PROTOBUF_LIB},INTERFACE_COMPILE_DEFINITIONS>)
set_target_properties(onnxruntime_coreml_proto PROPERTIES COMPILE_FLAGS "-fvisibility=hidden")
set_target_properties(onnxruntime_coreml_proto PROPERTIES COMPILE_FLAGS "-fvisibility-inlines-hidden")
set(_src_sub_dir "coreml/")
@ -729,7 +729,7 @@ if (onnxruntime_USE_COREML)
source_group(TREE ${ONNXRUNTIME_ROOT}/core FILES ${onnxruntime_providers_coreml_cc_srcs})
onnxruntime_add_static_library(onnxruntime_providers_coreml ${onnxruntime_providers_coreml_cc_srcs} ${onnxruntime_providers_coreml_objcc_srcs})
onnxruntime_add_include_to_target(onnxruntime_providers_coreml onnxruntime_common onnxruntime_framework onnx onnx_proto protobuf::libprotobuf-lite flatbuffers)
onnxruntime_add_include_to_target(onnxruntime_providers_coreml onnxruntime_common onnxruntime_framework onnx onnx_proto ${PROTOBUF_LIB} flatbuffers)
onnxruntime_add_include_to_target(onnxruntime_providers_coreml onnxruntime_coreml_proto)
target_link_libraries(onnxruntime_providers_coreml PRIVATE onnxruntime_coreml_proto "-framework Foundation" "-framework CoreML")
add_dependencies(onnxruntime_providers_coreml onnx onnxruntime_coreml_proto ${onnxruntime_EXTERNAL_DEPENDENCIES})
@ -860,7 +860,7 @@ if (onnxruntime_USE_DML)
onnxruntime_add_static_library(onnxruntime_providers_dml ${onnxruntime_providers_dml_cc_srcs})
set_msvc_c_cpp_compiler_warning_level(4)
onnxruntime_add_include_to_target(onnxruntime_providers_dml onnxruntime_common onnxruntime_framework onnx onnx_proto protobuf::libprotobuf flatbuffers)
onnxruntime_add_include_to_target(onnxruntime_providers_dml onnxruntime_common onnxruntime_framework onnx onnx_proto ${PROTOBUF_LIB} flatbuffers)
add_dependencies(onnxruntime_providers_dml ${onnxruntime_EXTERNAL_DEPENDENCIES})
target_include_directories(onnxruntime_providers_dml PRIVATE ${ONNXRUNTIME_ROOT} ${ONNXRUNTIME_ROOT}/../cmake/external/wil/include)
@ -947,7 +947,7 @@ if (onnxruntime_USE_ACL)
source_group(TREE ${ONNXRUNTIME_ROOT}/core FILES ${onnxruntime_providers_acl_cc_srcs})
onnxruntime_add_static_library(onnxruntime_providers_acl ${onnxruntime_providers_acl_cc_srcs})
onnxruntime_add_include_to_target(onnxruntime_providers_acl onnxruntime_common onnxruntime_framework onnx onnx_proto protobuf::libprotobuf flatbuffers)
onnxruntime_add_include_to_target(onnxruntime_providers_acl onnxruntime_common onnxruntime_framework onnx onnx_proto ${PROTOBUF_LIB} flatbuffers)
target_link_libraries(onnxruntime_providers_acl -L$ENV{LD_LIBRARY_PATH})
add_dependencies(onnxruntime_providers_acl ${onnxruntime_EXTERNAL_DEPENDENCIES})
set_target_properties(onnxruntime_providers_acl PROPERTIES FOLDER "ONNXRuntime")
@ -965,7 +965,7 @@ if (onnxruntime_USE_ARMNN)
source_group(TREE ${ONNXRUNTIME_ROOT}/core FILES ${onnxruntime_providers_armnn_cc_srcs})
onnxruntime_add_static_library(onnxruntime_providers_armnn ${onnxruntime_providers_armnn_cc_srcs})
onnxruntime_add_include_to_target(onnxruntime_providers_armnn onnxruntime_common onnxruntime_framework onnx onnx_proto protobuf::libprotobuf flatbuffers)
onnxruntime_add_include_to_target(onnxruntime_providers_armnn onnxruntime_common onnxruntime_framework onnx onnx_proto ${PROTOBUF_LIB} flatbuffers)
add_dependencies(onnxruntime_providers_armnn ${onnxruntime_EXTERNAL_DEPENDENCIES})
set_target_properties(onnxruntime_providers_armnn PROPERTIES FOLDER "ONNXRuntime")
target_include_directories(onnxruntime_providers_armnn PRIVATE ${ONNXRUNTIME_ROOT} ${eigen_INCLUDE_DIRS} ${onnxruntime_ARMNN_HOME} ${onnxruntime_ARMNN_HOME}/include ${onnxruntime_ACL_HOME} ${onnxruntime_ACL_HOME}/include)
@ -1094,7 +1094,7 @@ if (onnxruntime_USE_ROCM)
target_include_directories(onnxruntime_providers_rocm PRIVATE ${ORTTRAINING_ROOT} ${CMAKE_CURRENT_BINARY_DIR}/amdgpu/orttraining)
endif()
onnxruntime_add_include_to_target(onnxruntime_providers_rocm onnxruntime_common onnxruntime_framework onnx onnx_proto protobuf::libprotobuf flatbuffers)
onnxruntime_add_include_to_target(onnxruntime_providers_rocm onnxruntime_common onnxruntime_framework onnx onnx_proto ${PROTOBUF_LIB} flatbuffers)
add_dependencies(onnxruntime_providers_rocm ${onnxruntime_EXTERNAL_DEPENDENCIES})
install(DIRECTORY ${PROJECT_SOURCE_DIR}/../include/onnxruntime/core/providers/hip DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}/onnxruntime/core/providers)
set_target_properties(onnxruntime_providers_rocm PROPERTIES LINKER_LANGUAGE CXX)

View file

@ -3,9 +3,9 @@
file(GLOB onnxruntime_pyop_srcs "${ONNXRUNTIME_ROOT}/core/language_interop_ops/pyop/pyop.cc")
onnxruntime_add_static_library(onnxruntime_pyop ${onnxruntime_pyop_srcs})
add_dependencies(onnxruntime_pyop onnxruntime_graph)
onnxruntime_add_include_to_target(onnxruntime_pyop onnxruntime_common onnxruntime_graph onnxruntime_framework onnx onnx_proto protobuf::libprotobuf flatbuffers)
onnxruntime_add_include_to_target(onnxruntime_pyop onnxruntime_common onnxruntime_graph onnxruntime_framework onnx onnx_proto ${PROTOBUF_LIB} flatbuffers)
target_include_directories(onnxruntime_pyop PRIVATE ${ONNXRUNTIME_ROOT} ${eigen_INCLUDE_DIRS})
target_include_directories(onnxruntime_pyop PRIVATE ${PYTHON_INCLUDE_DIR} ${NUMPY_INCLUDE_DIR})
target_link_libraries(onnxruntime_pyop PRIVATE ${PYTHON_LIBRARIES})
onnxruntime_add_include_to_target(onnxruntime_pyop Python::Module Python::NumPy)
target_link_libraries(onnxruntime_pyop PRIVATE Python::Python)

View file

@ -2,33 +2,6 @@
# Licensed under the MIT License.
include(pybind11)
FIND_PACKAGE(NumPy)
if(NOT PYTHON_INCLUDE_DIR)
set(PYTHON_NOT_FOUND false)
exec_program("${PYTHON_EXECUTABLE}"
ARGS "-c \"import distutils.sysconfig; print(distutils.sysconfig.get_python_inc())\""
OUTPUT_VARIABLE PYTHON_INCLUDE_DIR
RETURN_VALUE PYTHON_NOT_FOUND)
if(${PYTHON_NOT_FOUND})
message(FATAL_ERROR
"Cannot get Python include directory. Is distutils installed?")
endif(${PYTHON_NOT_FOUND})
endif(NOT PYTHON_INCLUDE_DIR)
# 2. Resolve the installed version of NumPy (for numpy/arrayobject.h).
if(NOT NUMPY_INCLUDE_DIR)
set(NUMPY_NOT_FOUND false)
exec_program("${PYTHON_EXECUTABLE}"
ARGS "-c \"import numpy; print(numpy.get_include())\""
OUTPUT_VARIABLE NUMPY_INCLUDE_DIR
RETURN_VALUE NUMPY_NOT_FOUND)
if(${NUMPY_NOT_FOUND})
message(FATAL_ERROR
"Cannot get NumPy include directory: Is NumPy installed?")
endif(${NUMPY_NOT_FOUND})
endif(NOT NUMPY_INCLUDE_DIR)
# ---[ Python + Numpy
set(onnxruntime_pybind_srcs_pattern
@ -64,7 +37,8 @@ if (MSVC AND NOT CMAKE_SIZEOF_VOID_P EQUAL 8)
target_compile_options(onnxruntime_pybind11_state PRIVATE "/wd4244")
endif()
target_include_directories(onnxruntime_pybind11_state PRIVATE ${ONNXRUNTIME_ROOT} ${PYTHON_INCLUDE_DIR} ${NUMPY_INCLUDE_DIR} ${pybind11_INCLUDE_DIRS})
onnxruntime_add_include_to_target(onnxruntime_pybind11_state Python::Module Python::NumPy)
target_include_directories(onnxruntime_pybind11_state PRIVATE ${ONNXRUNTIME_ROOT} ${pybind11_INCLUDE_DIRS})
if(onnxruntime_USE_CUDA)
target_include_directories(onnxruntime_pybind11_state PRIVATE ${onnxruntime_CUDNN_HOME}/include)
endif()
@ -89,7 +63,11 @@ else()
set(ONNXRUNTIME_SO_LINK_FLAG "-DEF:${ONNXRUNTIME_ROOT}/python/pybind.def")
endif()
set(onnxruntime_pybind11_state_libs
if (onnxruntime_ENABLE_TRAINING)
target_link_libraries(onnxruntime_pybind11_state PRIVATE onnxruntime_training)
endif()
target_link_libraries(onnxruntime_pybind11_state PRIVATE
onnxruntime_session
${onnxruntime_libs}
${PROVIDERS_MIGRAPHX}
@ -115,12 +93,10 @@ set(onnxruntime_pybind11_state_libs
)
if (onnxruntime_ENABLE_LANGUAGE_INTEROP_OPS)
list(APPEND onnxruntime_pybind11_state_libs onnxruntime_language_interop onnxruntime_pyop)
target_link_libraries(onnxruntime_pybind11_state PRIVATE onnxruntime_language_interop onnxruntime_pyop)
endif()
if (onnxruntime_ENABLE_TRAINING)
list(INSERT onnxruntime_pybind11_state_libs 1 onnxruntime_training)
endif()
set(onnxruntime_pybind11_state_dependencies
${onnxruntime_EXTERNAL_DEPENDENCIES}
@ -132,20 +108,19 @@ add_dependencies(onnxruntime_pybind11_state ${onnxruntime_pybind11_state_depende
if (MSVC)
set_target_properties(onnxruntime_pybind11_state PROPERTIES LINK_FLAGS "${ONNXRUNTIME_SO_LINK_FLAG}")
# if MSVC, pybind11 looks for release version of python lib (pybind11/detail/common.h undefs _DEBUG)
target_link_libraries(onnxruntime_pybind11_state ${onnxruntime_pybind11_state_libs}
${PYTHON_LIBRARY_RELEASE} ${onnxruntime_EXTERNAL_LIBRARIES})
target_link_libraries(onnxruntime_pybind11_state PRIVATE Python::Module)
elseif (APPLE)
set_target_properties(onnxruntime_pybind11_state PROPERTIES LINK_FLAGS "${ONNXRUNTIME_SO_LINK_FLAG} -undefined dynamic_lookup")
target_link_libraries(onnxruntime_pybind11_state ${onnxruntime_pybind11_state_libs} ${onnxruntime_EXTERNAL_LIBRARIES})
set_target_properties(onnxruntime_pybind11_state PROPERTIES
INSTALL_RPATH "@loader_path"
BUILD_WITH_INSTALL_RPATH TRUE
INSTALL_RPATH_USE_LINK_PATH FALSE)
else()
target_link_libraries(onnxruntime_pybind11_state PRIVATE ${onnxruntime_pybind11_state_libs} ${onnxruntime_EXTERNAL_LIBRARIES})
set_property(TARGET onnxruntime_pybind11_state APPEND_STRING PROPERTY LINK_FLAGS " -Xlinker -rpath=\\$ORIGIN")
endif()
target_link_libraries(onnxruntime_pybind11_state PRIVATE ${onnxruntime_EXTERNAL_LIBRARIES})
set_target_properties(onnxruntime_pybind11_state PROPERTIES PREFIX "")
set_target_properties(onnxruntime_pybind11_state PROPERTIES FOLDER "ONNXRuntime")
if(onnxruntime_ENABLE_LTO)

View file

@ -11,7 +11,7 @@ source_group(TREE ${REPO_ROOT} FILES ${onnxruntime_session_srcs})
onnxruntime_add_static_library(onnxruntime_session ${onnxruntime_session_srcs})
install(DIRECTORY ${PROJECT_SOURCE_DIR}/../include/onnxruntime/core/session DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}/onnxruntime/core)
onnxruntime_add_include_to_target(onnxruntime_session onnxruntime_common onnxruntime_framework onnx onnx_proto protobuf::libprotobuf flatbuffers)
onnxruntime_add_include_to_target(onnxruntime_session onnxruntime_common onnxruntime_framework onnx onnx_proto ${PROTOBUF_LIB} flatbuffers)
if(onnxruntime_ENABLE_INSTRUMENT)
target_compile_definitions(onnxruntime_session PUBLIC ONNXRUNTIME_ENABLE_INSTRUMENT)
endif()

View file

@ -19,7 +19,7 @@ file(GLOB_RECURSE onnxruntime_training_srcs
onnxruntime_add_static_library(onnxruntime_training ${onnxruntime_training_srcs})
add_dependencies(onnxruntime_training onnx tensorboard ${onnxruntime_EXTERNAL_DEPENDENCIES})
onnxruntime_add_include_to_target(onnxruntime_training onnxruntime_common onnx onnx_proto tensorboard protobuf::libprotobuf flatbuffers)
onnxruntime_add_include_to_target(onnxruntime_training onnxruntime_common onnx onnx_proto tensorboard ${PROTOBUF_LIB} flatbuffers)
# fix event_writer.cc 4100 warning
if(WIN32)
@ -62,7 +62,7 @@ if (onnxruntime_BUILD_UNIT_TESTS)
onnxruntime_add_static_library(onnxruntime_training_runner ${onnxruntime_training_runner_srcs} ${onnxruntime_perf_test_src})
add_dependencies(onnxruntime_training_runner ${onnxruntime_EXTERNAL_DEPENDENCIES} onnx onnxruntime_providers)
onnxruntime_add_include_to_target(onnxruntime_training_runner onnxruntime_training onnxruntime_framework onnxruntime_common onnx onnx_proto protobuf::libprotobuf onnxruntime_training flatbuffers)
onnxruntime_add_include_to_target(onnxruntime_training_runner onnxruntime_training onnxruntime_framework onnxruntime_common onnx onnx_proto ${PROTOBUF_LIB} onnxruntime_training flatbuffers)
target_include_directories(onnxruntime_training_runner PRIVATE ${CMAKE_CURRENT_BINARY_DIR} ${ONNXRUNTIME_ROOT} ${ORTTRAINING_ROOT} ${eigen_INCLUDE_DIRS} PUBLIC ${onnxruntime_graph_header})
target_link_libraries(onnxruntime_training_runner PRIVATE nlohmann_json::nlohmann_json)
@ -100,7 +100,7 @@ if (onnxruntime_BUILD_UNIT_TESTS)
"${ORTTRAINING_SOURCE_DIR}/models/mnist/main.cc"
)
onnxruntime_add_executable(onnxruntime_training_mnist ${training_mnist_src})
onnxruntime_add_include_to_target(onnxruntime_training_mnist onnxruntime_common onnx onnx_proto protobuf::libprotobuf onnxruntime_training flatbuffers)
onnxruntime_add_include_to_target(onnxruntime_training_mnist onnxruntime_common onnx onnx_proto ${PROTOBUF_LIB} onnxruntime_training flatbuffers)
target_include_directories(onnxruntime_training_mnist PUBLIC ${CMAKE_CURRENT_BINARY_DIR} ${ONNXRUNTIME_ROOT} ${ORTTRAINING_ROOT} ${eigen_INCLUDE_DIRS} ${CXXOPTS} ${extra_includes} ${onnxruntime_graph_header} ${onnxruntime_exec_src_dir} ${CMAKE_CURRENT_BINARY_DIR} ${CMAKE_CURRENT_BINARY_DIR}/onnx onnxruntime_training_runner)
set(ONNXRUNTIME_LIBS
@ -138,7 +138,7 @@ if (onnxruntime_BUILD_UNIT_TESTS)
"${ORTTRAINING_SOURCE_DIR}/models/squeezenet/*.cc"
)
onnxruntime_add_executable(onnxruntime_training_squeezenet ${training_squeezene_src})
onnxruntime_add_include_to_target(onnxruntime_training_squeezenet onnxruntime_common onnx onnx_proto protobuf::libprotobuf onnxruntime_training flatbuffers)
onnxruntime_add_include_to_target(onnxruntime_training_squeezenet onnxruntime_common onnx onnx_proto ${PROTOBUF_LIB} onnxruntime_training flatbuffers)
target_include_directories(onnxruntime_training_squeezenet PUBLIC ${ONNXRUNTIME_ROOT} ${ORTTRAINING_ROOT} ${eigen_INCLUDE_DIRS} ${extra_includes} ${onnxruntime_graph_header} ${onnxruntime_exec_src_dir} ${CMAKE_CURRENT_BINARY_DIR} ${CMAKE_CURRENT_BINARY_DIR}/onnx onnxruntime_training_runner)
if(UNIX AND NOT APPLE)
target_compile_options(onnxruntime_training_squeezenet PUBLIC "-Wno-maybe-uninitialized")
@ -160,7 +160,7 @@ if (onnxruntime_BUILD_UNIT_TESTS)
endif()
endif()
onnxruntime_add_include_to_target(onnxruntime_training_bert onnxruntime_common onnx onnx_proto protobuf::libprotobuf onnxruntime_training flatbuffers)
onnxruntime_add_include_to_target(onnxruntime_training_bert onnxruntime_common onnx onnx_proto ${PROTOBUF_LIB} onnxruntime_training flatbuffers)
target_include_directories(onnxruntime_training_bert PUBLIC ${CMAKE_CURRENT_BINARY_DIR} ${ONNXRUNTIME_ROOT} ${ORTTRAINING_ROOT} ${MPI_CXX_INCLUDE_DIRS} ${eigen_INCLUDE_DIRS} ${CXXOPTS} ${extra_includes} ${onnxruntime_graph_header} ${onnxruntime_exec_src_dir} ${CMAKE_CURRENT_BINARY_DIR} ${CMAKE_CURRENT_BINARY_DIR}/onnx onnxruntime_training_runner)
target_link_libraries(onnxruntime_training_bert PRIVATE onnxruntime_training_runner onnxruntime_training ${ONNXRUNTIME_LIBS} ${onnxruntime_EXTERNAL_LIBRARIES})
@ -179,7 +179,7 @@ if (onnxruntime_BUILD_UNIT_TESTS)
endif()
endif()
onnxruntime_add_include_to_target(onnxruntime_training_pipeline_poc onnxruntime_common onnx onnx_proto protobuf::libprotobuf onnxruntime_training flatbuffers)
onnxruntime_add_include_to_target(onnxruntime_training_pipeline_poc onnxruntime_common onnx onnx_proto ${PROTOBUF_LIB} onnxruntime_training flatbuffers)
target_include_directories(onnxruntime_training_pipeline_poc PUBLIC ${CMAKE_CURRENT_BINARY_DIR} ${ONNXRUNTIME_ROOT} ${ORTTRAINING_ROOT} ${MPI_CXX_INCLUDE_DIRS} ${eigen_INCLUDE_DIRS} ${CXXOPTS} ${extra_includes} ${onnxruntime_graph_header} ${onnxruntime_exec_src_dir} ${CMAKE_CURRENT_BINARY_DIR} ${CMAKE_CURRENT_BINARY_DIR}/onnx onnxruntime_training_runner)
if (onnxruntime_USE_NCCL)
target_include_directories(onnxruntime_training_pipeline_poc PRIVATE ${NCCL_INCLUDE_DIRS})
@ -199,7 +199,7 @@ if (onnxruntime_BUILD_UNIT_TESTS)
target_compile_options(onnxruntime_training_gpt2 PUBLIC "-Wno-maybe-uninitialized")
endif()
endif()
onnxruntime_add_include_to_target(onnxruntime_training_gpt2 onnxruntime_common onnx onnx_proto protobuf::libprotobuf onnxruntime_training flatbuffers)
onnxruntime_add_include_to_target(onnxruntime_training_gpt2 onnxruntime_common onnx onnx_proto ${PROTOBUF_LIB} onnxruntime_training flatbuffers)
target_include_directories(onnxruntime_training_gpt2 PUBLIC ${CMAKE_CURRENT_BINARY_DIR} ${ONNXRUNTIME_ROOT} ${ORTTRAINING_ROOT} ${MPI_CXX_INCLUDE_DIRS} ${eigen_INCLUDE_DIRS} ${CXXOPTS} ${extra_includes} ${onnxruntime_graph_header} ${onnxruntime_exec_src_dir} ${CMAKE_CURRENT_BINARY_DIR} ${CMAKE_CURRENT_BINARY_DIR}/onnx onnxruntime_training_runner)
target_link_libraries(onnxruntime_training_gpt2 PRIVATE onnxruntime_training_runner onnxruntime_training ${ONNXRUNTIME_LIBS} ${onnxruntime_EXTERNAL_LIBRARIES})

View file

@ -857,7 +857,7 @@ if(onnxruntime_ENABLE_EAGER_MODE)
onnxruntime_mlas
onnx
onnx_proto
protobuf::libprotobuf
${PROTOBUF_LIB}
GTest::gtest
re2::re2
onnxruntime_flatbuffers
@ -1088,7 +1088,7 @@ else()
endif()
set_property(TARGET custom_op_library APPEND_STRING PROPERTY LINK_FLAGS ${ONNXRUNTIME_CUSTOM_OP_LIB_LINK_FLAG})
if (onnxruntime_BUILD_JAVA)
if (onnxruntime_BUILD_JAVA AND NOT onnxruntime_ENABLE_STATIC_ANALYSIS)
message(STATUS "Running Java tests")
# native-test is added to resources so custom_op_lib can be loaded
# and we want to symlink it there
@ -1097,7 +1097,7 @@ if (onnxruntime_BUILD_JAVA)
# delegate to gradle's test runner
if(WIN32)
add_custom_command(TARGET custom_op_library POST_BUILD COMMAND ${CMAKE_COMMAND} -E create_symlink $<TARGET_FILE:custom_op_library>
add_custom_command(TARGET custom_op_library POST_BUILD COMMAND ${CMAKE_COMMAND} -E copy_if_different $<TARGET_FILE:custom_op_library>
${JAVA_NATIVE_TEST_DIR}/$<TARGET_FILE_NAME:custom_op_library>)
# On windows ctest requires a test to be an .exe(.com) file
# So there are two options 1) Install Chocolatey and its gradle package
@ -1111,7 +1111,7 @@ if (onnxruntime_BUILD_JAVA)
${ORT_PROVIDER_CMAKE_FLAGS}
-P ${CMAKE_CURRENT_SOURCE_DIR}/onnxruntime_java_unittests.cmake)
else()
add_custom_command(TARGET custom_op_library POST_BUILD COMMAND ${CMAKE_COMMAND} -E create_symlink $<TARGET_FILE:custom_op_library>
add_custom_command(TARGET custom_op_library POST_BUILD COMMAND ${CMAKE_COMMAND} -E copy_if_different $<TARGET_FILE:custom_op_library>
${JAVA_NATIVE_TEST_DIR}/$<TARGET_LINKER_FILE_NAME:custom_op_library>)
if (onnxruntime_USE_CUDA)
add_test(NAME onnxruntime4j_test COMMAND ${GRADLE_EXECUTABLE} cmakeCheck -DcmakeBuildDir=${CMAKE_CURRENT_BINARY_DIR} -DUSE_CUDA=1

View file

@ -15,7 +15,7 @@ target_include_directories(onnxruntime_util PRIVATE ${ONNXRUNTIME_ROOT} PUBLIC $
if (onnxruntime_USE_CUDA)
target_include_directories(onnxruntime_util PRIVATE ${CMAKE_CUDA_TOOLKIT_INCLUDE_DIRECTORIES})
endif()
onnxruntime_add_include_to_target(onnxruntime_util onnxruntime_common onnxruntime_framework onnx onnx_proto protobuf::libprotobuf)
onnxruntime_add_include_to_target(onnxruntime_util onnxruntime_common onnxruntime_framework onnx onnx_proto ${PROTOBUF_LIB})
if(UNIX)
target_compile_options(onnxruntime_util PUBLIC "-Wno-error=comment")
endif()

View file

@ -24,7 +24,7 @@ target_compile_options(onnx PRIVATE -Wno-unused-parameter -Wno-unused-variable)
target_link_libraries(onnxruntime_webassembly PRIVATE
nsync_cpp
protobuf::libprotobuf-lite
${PROTOBUF_LIB}
onnx
onnx_proto
onnxruntime_common
@ -51,6 +51,7 @@ set_target_properties(onnxruntime_webassembly PROPERTIES LINK_FLAGS "
-s LLD_REPORT_UNDEFINED \
-s VERBOSE=0 \
-s NO_FILESYSTEM=1 \
-s MALLOC=${onnxruntime_WEBASSEMBLY_MALLOC} \
--no-entry")
if (CMAKE_BUILD_TYPE STREQUAL "Debug")

View file

@ -318,7 +318,7 @@ set_target_properties(winml_adapter PROPERTIES CXX_STANDARD 17)
set_target_properties(winml_adapter PROPERTIES CXX_STANDARD_REQUIRED ON)
# Compiler definitions
onnxruntime_add_include_to_target(winml_adapter onnxruntime_common onnxruntime_framework onnx onnx_proto protobuf::libprotobuf flatbuffers)
onnxruntime_add_include_to_target(winml_adapter onnxruntime_common onnxruntime_framework onnx onnx_proto ${PROTOBUF_LIB} flatbuffers)
target_include_directories(winml_adapter PRIVATE ${ONNXRUNTIME_ROOT} ${eigen_INCLUDE_DIRS})
add_dependencies(winml_adapter ${onnxruntime_EXTERNAL_DEPENDENCIES})

View file

@ -269,7 +269,7 @@ target_include_directories(winml_test_adapter PRIVATE ${winml_lib_common_dir}/in
target_include_directories(winml_test_adapter PRIVATE ${ONNXRUNTIME_INCLUDE_DIR})
target_include_directories(winml_test_adapter PRIVATE ${ONNXRUNTIME_ROOT})
onnxruntime_add_include_to_target(winml_test_adapter onnxruntime_common onnxruntime_framework onnx onnx_proto protobuf::libprotobuf flatbuffers)
onnxruntime_add_include_to_target(winml_test_adapter onnxruntime_common onnxruntime_framework onnx onnx_proto ${PROTOBUF_LIB} flatbuffers)
target_include_directories(winml_test_adapter PRIVATE ${ONNXRUNTIME_ROOT} ${eigen_INCLUDE_DIRS})
add_dependencies(winml_test_adapter ${onnxruntime_EXTERNAL_DEPENDENCIES})
target_include_directories(winml_test_adapter PRIVATE ${winml_adapter_dir})

View file

@ -31,10 +31,10 @@ RUN pip3 install numpy
# Build the latest cmake
WORKDIR /code
RUN wget https://github.com/Kitware/CMake/releases/download/v3.18.3/cmake-3.18.3.tar.gz
RUN tar zxf cmake-3.18.3.tar.gz
RUN wget https://github.com/Kitware/CMake/releases/download/v3.20.3/cmake-3.20.3.tar.gz
RUN tar zxf cmake-3.20.3.tar.gz
WORKDIR /code/cmake-3.18.3
WORKDIR /code/cmake-3.20.3
RUN ./configure --system-curl
RUN make
RUN sudo make install
@ -50,7 +50,7 @@ RUN git clone --single-branch --branch ${ONNXRUNTIME_SERVER_BRANCH} --recursive
# Build ORT including the shared lib and python bindings
WORKDIR /code/onnxruntime
RUN ./build.sh --use_openmp ${BUILDARGS} --update --build --build_shared_lib --build_wheel
RUN ./build.sh ${BUILDARGS} --update --build --build_shared_lib --build_wheel
# Build Output
RUN ls -l /code/onnxruntime/build/Linux/${BUILDTYPE}/*.so

View file

@ -4,18 +4,18 @@
# --------------------------------------------------------------
# Dockerfile to run ONNXRuntime with CUDA, CUDNN integration
# nVidia cuda 10.2 Base Image
FROM nvidia/cuda:10.2-cudnn8-devel
# nVidia cuda 11.1 Base Image
FROM nvcr.io/nvidia/cuda:11.1.1-cudnn8-devel-ubuntu18.04
MAINTAINER Changming Sun "chasun@microsoft.com"
ADD . /code
ENV PATH /usr/local/nvidia/bin:/usr/local/cuda/bin:${PATH}
RUN apt-get update && apt-get install -y --no-install-recommends python3-dev ca-certificates g++ python3-numpy gcc make git python3-setuptools python3-wheel python3-pip aria2 && aria2c -q -d /tmp -o cmake-3.18.2-Linux-x86_64.tar.gz https://github.com/Kitware/CMake/releases/download/v3.18.2/cmake-3.18.2-Linux-x86_64.tar.gz && tar -zxf /tmp/cmake-3.18.2-Linux-x86_64.tar.gz --strip=1 -C /usr
RUN apt-get update && apt-get install -y --no-install-recommends python3-dev ca-certificates g++ python3-numpy gcc make git python3-setuptools python3-wheel python3-pip aria2 && aria2c -q -d /tmp -o cmake-3.20.3-Linux-x86_64.tar.gz https://github.com/Kitware/CMake/releases/download/v3.20.3/cmake-3.20.3-Linux-x86_64.tar.gz && tar -zxf /tmp/cmake-3.20.3-Linux-x86_64.tar.gz --strip=1 -C /usr
RUN cd /code && /bin/bash ./build.sh --skip_submodule_sync --cuda_home /usr/local/cuda --cudnn_home /usr/lib/x86_64-linux-gnu/ --use_cuda --config Release --build_wheel --update --build --parallel --cmake_extra_defines ONNXRUNTIME_VERSION=$(cat ./VERSION_NUMBER) 'CMAKE_CUDA_ARCHITECTURES=30;37;50;52;60;70'
FROM nvidia/cuda:10.2-cudnn8-runtime
FROM nvcr.io/nvidia/cuda:11.1.1-cudnn8-runtime-ubuntu18.04
COPY --from=0 /code/build/Linux/Release/dist /root
COPY --from=0 /code/dockerfiles/LICENSE-IMAGE.txt /code/LICENSE-IMAGE.txt
ENV DEBIAN_FRONTEND=noninteractive
RUN apt-get update && apt-get install -y --no-install-recommends libstdc++6 ca-certificates python3-setuptools python3-wheel python3-pip unattended-upgrades && unattended-upgrade && python3 -m pip install /root/*.whl && rm -rf /root/*.whl
RUN apt-get update && apt-get install -y --no-install-recommends libstdc++6 ca-certificates python3-setuptools python3-wheel python3-pip unattended-upgrades && unattended-upgrade && python3 -m pip install /root/*.whl && rm -rf /root/*.whl

View file

@ -29,7 +29,7 @@ RUN apt-get update &&\
# Install rbuild
RUN pip3 install https://github.com/RadeonOpenCompute/rbuild/archive/master.tar.gz
ENV PATH /opt/miniconda/bin:/code/cmake-3.14.3-Linux-x86_64/bin:${PATH}
ENV PATH /opt/miniconda/bin:/code/cmake-3.20.3-Linux-x86_64/bin:${PATH}
# Install MIGraphX from source
RUN mkdir -p /migraphx
@ -47,4 +47,4 @@ RUN git clone --single-branch --branch ${ONNXRUNTIME_BRANCH} --recursive ${ONNXR
/bin/sh ./build.sh --config Release --build_wheel --update --build --parallel --cmake_extra_defines ONNXRUNTIME_VERSION=$(cat ./VERSION_NUMBER) --use_migraphx &&\
pip install /code/onnxruntime/build/Linux/Release/dist/*.whl &&\
cd .. &&\
rm -rf onnxruntime cmake-3.14.3-Linux-x86_64
rm -rf onnxruntime cmake-3.20.3-Linux-x86_64

View file

@ -12,7 +12,7 @@ ARG ONNXRUNTIME_BRANCH=master
WORKDIR /code
ARG MY_ROOT=/code
ENV PATH /opt/miniconda/bin:/code/cmake-3.14.3-Linux-x86_64/bin:$PATH
ENV PATH /opt/miniconda/bin:/code/cmake-3.20.3-Linux-x86_64/bin:$PATH
ENV LD_LIBRARY_PATH=/opt/miniconda/lib:/usr/lib:/usr/lib/x86_64-linux-gnu:$LD_LIBRARY_PATH
ENV INTEL_OPENVINO_DIR=/opt/intel/openvino_2021.3.394

View file

@ -12,7 +12,7 @@ ARG ONNXRUNTIME_BRANCH=master
WORKDIR /code
ARG MY_ROOT=/code
ENV PATH /opt/miniconda/bin:/code/cmake-3.14.3-Linux-x86_64/bin:$PATH
ENV PATH /opt/miniconda/bin:/code/cmake-3.20.3-Linux-x86_64/bin:$PATH
ENV LD_LIBRARY_PATH=/opt/miniconda/lib:/usr/lib:/usr/lib/x86_64-linux-gnu:$LD_LIBRARY_PATH
ENV INTEL_OPENVINO_DIR=/opt/intel/openvino_2021.3.394

View file

@ -29,7 +29,7 @@ RUN apt-get update &&\
# Install yapf
RUN pip3 install yapf==0.28.0
ENV PATH /opt/miniconda/bin:/code/cmake-3.14.3-Linux-x86_64/bin:${PATH}
ENV PATH /opt/miniconda/bin:/code/cmake-3.20.3-Linux-x86_64/bin:${PATH}
# Install dependencies
COPY ./scripts/install_rocm_deps.sh /
@ -45,5 +45,5 @@ RUN git clone --single-branch --branch ${ONNXRUNTIME_BRANCH} --recursive ${ONNXR
ONNXRUNTIME_VERSION=$(cat ./VERSION_NUMBER) --use_rocm --rocm_home=/opt/rocm &&\
pip install /code/onnxruntime/build/Linux/Release/dist/*.whl &&\
cd .. &&\
rm -rf onnxruntime cmake-3.14.3-Linux-x86_64
rm -rf onnxruntime cmake-3.20.3-Linux-x86_64

View file

@ -9,12 +9,12 @@ MAINTAINER Changming Sun "chasun@microsoft.com"
ADD . /code
ENV DEBIAN_FRONTEND=noninteractive
RUN apt-get update && apt-get install -y --no-install-recommends python3-dev ca-certificates g++ python3-numpy gcc make git python3-setuptools python3-wheel python3-pip aria2 && aria2c -q -d /tmp -o cmake-3.18.2-Linux-x86_64.tar.gz https://github.com/Kitware/CMake/releases/download/v3.18.2/cmake-3.18.2-Linux-x86_64.tar.gz && tar -zxf /tmp/cmake-3.18.2-Linux-x86_64.tar.gz --strip=1 -C /usr
RUN apt-get update && apt-get install -y --no-install-recommends python3-dev ca-certificates g++ python3-numpy gcc make git python3-setuptools python3-wheel python3-pip aria2 && aria2c -q -d /tmp -o cmake-3.20.3-Linux-x86_64.tar.gz https://github.com/Kitware/CMake/releases/download/v3.20.3/cmake-3.20.3-Linux-x86_64.tar.gz && tar -zxf /tmp/cmake-3.20.3-Linux-x86_64.tar.gz --strip=1 -C /usr
# Prepare onnxruntime repository & build onnxruntime
RUN cd /code && /bin/bash ./build.sh --skip_submodule_sync --use_openmp --config Release --build_wheel --update --build --parallel --cmake_extra_defines ONNXRUNTIME_VERSION=$(cat ./VERSION_NUMBER)
RUN cd /code && /bin/bash ./build.sh --skip_submodule_sync --config Release --build_wheel --update --build --parallel --cmake_extra_defines ONNXRUNTIME_VERSION=$(cat ./VERSION_NUMBER)
FROM ubuntu:18.04
COPY --from=0 /code/build/Linux/Release/dist /root
COPY --from=0 /code/dockerfiles/LICENSE-IMAGE.txt /code/LICENSE-IMAGE.txt
RUN apt-get update && apt-get install -y --no-install-recommends libstdc++6 libgomp1 ca-certificates python3-setuptools python3-wheel python3-pip unattended-upgrades && unattended-upgrade && python3 -m pip install /root/*.whl && rm -rf /root/*.whl
RUN apt-get update && apt-get install -y --no-install-recommends libstdc++6 ca-certificates python3-setuptools python3-wheel python3-pip unattended-upgrades && unattended-upgrade && python3 -m pip install /root/*.whl && rm -rf /root/*.whl

View file

@ -15,7 +15,7 @@ RUN apt-get update &&\
RUN unattended-upgrade
WORKDIR /code
ENV PATH /usr/local/nvidia/bin:/usr/local/cuda/bin:/code/cmake-3.14.3-Linux-x86_64/bin:/opt/miniconda/bin:${PATH}
ENV PATH /usr/local/nvidia/bin:/usr/local/cuda/bin:/code/cmake-3.20.3-Linux-x86_64/bin:/opt/miniconda/bin:${PATH}
# Prepare onnxruntime repository & build onnxruntime with TensorRT
RUN git clone --single-branch --branch ${ONNXRUNTIME_BRANCH} --recursive ${ONNXRUNTIME_REPO} onnxruntime &&\
@ -27,4 +27,4 @@ RUN git clone --single-branch --branch ${ONNXRUNTIME_BRANCH} --recursive ${ONNXR
/bin/sh ./build.sh --parallel --cuda_home /usr/local/cuda --cudnn_home /usr/lib/x86_64-linux-gnu/ --use_tensorrt --tensorrt_home /workspace/tensorrt --config Release --build_wheel --update --build --cmake_extra_defines ONNXRUNTIME_VERSION=$(cat ./VERSION_NUMBER) &&\
pip install /code/onnxruntime/build/Linux/Release/dist/*.whl &&\
cd .. &&\
rm -rf onnxruntime cmake-3.14.3-Linux-x86_64
rm -rf onnxruntime cmake-3.20.3-Linux-x86_64

View file

@ -14,7 +14,7 @@ ARG OPENMPI_PATH=/opt/openmpi-${OPENMPI_VERSION}
ARG COMMIT=master
# cuda development image for building sources
FROM nvidia/cuda:10.2-cudnn8-devel-ubuntu18.04 as builder
FROM nvcr.io/nvidia/cuda:11.1.1-cudnn8-devel-ubuntu18.04 as builder
# set location for builds
WORKDIR /stage
@ -32,7 +32,10 @@ RUN apt-get -y update &&\
RUN unattended-upgrade
RUN locale-gen en_US.UTF-8 && \
update-locale LANG=en_US.UTF-8
update-locale LANG=en_US.UTF-8 && \
curl -O -L https://github.com/Kitware/CMake/releases/download/v3.20.3/cmake-3.20.3-Linux-x86_64.tar.gz && \
tar -zxf cmake-3.20.3-Linux-x86_64.tar.gz --strip=1 -C /usr && \
rm -rf cmake-3.20.3-Linux-x86_64.tar.gz
# install miniconda (comes with python 3.7 default)
ARG CONDA_VERSION
@ -42,12 +45,11 @@ RUN cd /stage && curl -fSsL --insecure ${CONDA_URL} -o install-conda.sh &&\
/opt/conda/bin/conda clean -ya
ENV PATH=/opt/conda/bin:${PATH}
# install cmake, setuptools, numpy, and onnx
# install setuptools, numpy, and onnx
ARG NUMPY_VERSION
ARG ONNX_VERSION
RUN conda install -y \
setuptools \
cmake \
numpy=${NUMPY_VERSION} &&\
pip install \
onnx=="${ONNX_VERSION}"
@ -147,7 +149,7 @@ RUN cd /stage && git clone https://github.com/microsoft/onnxruntime.git &&\
--build_dir build \
--build \
--build_wheel \
--skip_tests &&\
--skip_tests --cmake_extra_defines 'CMAKE_CUDA_ARCHITECTURES=35;37;50;52;60;61;70;75;80;86' &&\
pip install build/${BUILD_CONFIG}/dist/*.whl
# Install AzureML support and commonly used packages.
@ -155,7 +157,7 @@ RUN pip install azureml-defaults sentencepiece==0.1.92 transformers==2.11.0 msgp
# switch to cuda runtime environment
# note: launch with --gpus all or nvidia-docker
FROM nvidia/cuda:10.2-cudnn8-runtime-ubuntu18.04
FROM nvcr.io/nvidia/cuda:11.1.1-cudnn8-runtime-ubuntu18.04
WORKDIR /stage
# install ucx
@ -215,8 +217,7 @@ LABEL PYTORCH_VERSION=${PYTORCH_VERSION}
# clean\finalize environment
# note: adds onnxruntime license and third party notices
RUN conda remove -y cmake &&\
apt-get purge -y build-essential &&\
RUN apt-get purge -y build-essential &&\
apt-get autoremove -y &&\
rm -fr /stage
WORKDIR /workspace

View file

@ -4,25 +4,32 @@
# --------------------------------------------------------------
# Dockerfile to run ONNXRuntime with Vitis-AI integration
FROM xilinx/vitis-ai:latest
FROM xilinx/vitis-ai-cpu:1.3.598
ARG ONNXRUNTIME_REPO=https://github.com/Microsoft/onnxruntime
ARG ONNXRUNTIME_BRANCH=master
ARG PYXIR_REPO=https://github.com/Xilinx/pyxir
ARG PYXIR_BRANCH=master
ARG PYXIR_BRANCH=v0.2.0
ARG PYXIR_FLAG="--use_vai_rt"
RUN apt-get update &&\
apt-get install -y sudo git bash
RUN apt-get update && \
apt-get install -y \
sudo \
git \
bash \
gcc-aarch64-linux-gnu && \
apt-get clean && \
rm -rf /var/lib/apt/lists/*
ENV PATH /code/cmake-3.14.3-Linux-x86_64/bin:$PATH
ENV PATH /code/cmake-3.20.3-Linux-x86_64/bin:$PATH
ENV LD_LIBRARY_PATH /opt/xilinx/xrt/lib:$LD_LIBRARY_PATH
WORKDIR /code
RUN . $VAI_ROOT/conda/etc/profile.d/conda.sh &&\
conda activate vitis-ai-tensorflow &&\
git clone --single-branch --branch ${PYXIR_BRANCH} --recursive ${PYXIR_REPO} pyxir &&\
cd pyxir && python3 setup.py install --use_vai_rt
cd pyxir && python3 setup.py install ${PYXIR_FLAG}
RUN . $VAI_ROOT/conda/etc/profile.d/conda.sh &&\
conda activate vitis-ai-tensorflow &&\
git clone --single-branch --branch ${ONNXRUNTIME_BRANCH} --recursive ${ONNXRUNTIME_REPO} onnxruntime &&\
@ -34,4 +41,4 @@ RUN . $VAI_ROOT/conda/etc/profile.d/conda.sh &&\
/bin/sh ./build.sh --use_openmp --config RelWithDebInfo --enable_pybind --build_wheel --use_vitisai --parallel --update --build --build_shared_lib &&\
pip install /code/onnxruntime/build/Linux/RelWithDebInfo/dist/*-linux_x86_64.whl &&\
cd .. &&\
rm -rf onnxruntime cmake-3.14.3-Linux-x86_64
rm -rf onnxruntime cmake-3.20.3-Linux-x86_64

View file

@ -19,6 +19,6 @@ pip install numpy
rm -rf /opt/miniconda/pkgs
# Dependencies: cmake
wget --quiet https://github.com/Kitware/CMake/releases/download/v3.14.3/cmake-3.14.3-Linux-x86_64.tar.gz
tar zxf cmake-3.14.3-Linux-x86_64.tar.gz
rm -rf cmake-3.14.3-Linux-x86_64.tar.gz
wget --quiet https://github.com/Kitware/CMake/releases/download/v3.20.3/cmake-3.20.3-Linux-x86_64.tar.gz
tar zxf cmake-3.20.3-Linux-x86_64.tar.gz
rm -rf cmake-3.20.3-Linux-x86_64.tar.gz

View file

@ -7,7 +7,7 @@ sphinx-gallery
sphinxcontrib.imagesvg
sphinx_rtd_theme
pyquickhelper
tensorflow
tensorflow>=2.2.0,<2.5.0
tf2onnx
pandas
pydot

View file

@ -5,7 +5,7 @@
#include "onnxruntime_c_api.h"
// COREMLFlags are bool options we want to set for CoreML EP
// This enum is defined as bit flats, and cannot have negative value
// This enum is defined as bit flags, and cannot have negative value
// To generate an uint32_t coreml_flags for using with OrtSessionOptionsAppendExecutionProvider_CoreML below,
// uint32_t coreml_flags = 0;
// coreml_flags |= COREML_FLAG_USE_CPU_ONLY;

View file

@ -5,7 +5,7 @@
#include "onnxruntime_c_api.h"
// NNAPIFlags are bool options we want to set for NNAPI EP
// This enum is defined as bit flats, and cannot have negative value
// This enum is defined as bit flags, and cannot have negative value
// To generate an uint32_t nnapi_flags for using with OrtSessionOptionsAppendExecutionProvider_Nnapi below,
// uint32_t nnapi_flags = 0;
// nnapi_flags |= NNAPI_FLAG_USE_FP16;

View file

@ -10,7 +10,9 @@ extern "C" {
/**
* \param use_arena zero: false. non-zero: true.
*/
ORT_API_STATUS(OrtSessionOptionsAppendExecutionProvider_VITISAI, _In_ OrtSessionOptions* options, const char *backend_type, int device_id);
ORT_API_STATUS(OrtSessionOptionsAppendExecutionProvider_VITISAI, _In_ OrtSessionOptions* options,
const char* backend_type, int device_id, const char* export_runtime_module,
const char* load_runtime_module);
#ifdef __cplusplus
}

View file

@ -145,39 +145,53 @@ This project is a library for running ONNX models on browsers. It is the success
2. in `<ORT_ROOT>/js/common/`, run `npm ci`.
3. in `<ORT_ROOT>/js/web/`, run `npm ci`.
2. ~~Follow [instructions](https://www.onnxruntime.ai/docs/how-to/build.html#apis-and-language-bindings) for building ONNX Runtime WebAssembly. (TODO: document is not ready. we are working on it. Please see steps described as below.)~~
2. Prepare ONNX Runtime WebAssembly artifacts.
in `<ORT_ROOT>/`, run one of the following commands to build WebAssembly:
You can either use the prebuilt artifacts or build it by yourself.
```sh
# In windows, use 'build' to replace './build.sh'
- Setup by script.
# The following command build debug.
./build.sh --build_wasm
In `<ORT_ROOT>/js/web/`, run `npm run pull:wasm` to pull WebAssembly artifacts for latest master branch from CI pipeline.
# The following command build debug with debug info.
./build.sh --build_wasm --skip_tests --enable_wasm_debug_info
- Download artifacts from pipeline manually.
# The following command build release.
./build.sh --config Release --build_wasm --skip_tests --disable_wasm_exception_catching --disable_rtti
```
you can download prebuilt WebAssembly artifacts from [Windows WebAssembly CI Pipeline](https://dev.azure.com/onnxruntime/onnxruntime/_build?definitionId=161&_a=summary). Select a build, download artifacts "Release_ort-wasm" and "Release_ort-wasm-threaded" and unzip. See instructions below to put files into destination folders.
To build with multi-thread support, append flag `--enable_wasm_threads` to the command. Make sure to build both single-thread and multi-thread before next step.
- Build WebAssembly artifacts.
NOTE: You can also find latest build artifacts on [Windows WebAssembly CI Pipeline](https://dev.azure.com/onnxruntime/onnxruntime/_build?definitionId=161&_a=summary&repositoryFilter=1&branchFilter=4%2C4%2C4%2C4%2C4%2C4). Choose any build for master branch, download artifacts "Release_ort-wasm" and "Release_ort-wasm-threaded" and unzip.
1. Build ONNX Runtime WebAssembly
3. Copy following files from build output folder to `<ORT_ROOT>/js/web/dist/`:
~~Follow [instructions](https://www.onnxruntime.ai/docs/how-to/build.html#apis-and-language-bindings) for building ONNX Runtime WebAssembly. (TODO: document is not ready. we are working on it. Please see steps described as below.)~~
- ort-wasm.wasm
- ort-wasm-threaded.wasm (build with flag '--enable_wasm_threads')
in `<ORT_ROOT>/`, run one of the following commands to build WebAssembly:
4. Copy following files from build output folder to `<ORT_ROOT>/js/web/lib/wasm/binding/`:
```sh
# In windows, use 'build' to replace './build.sh'
- ort-wasm.js
- ort-wasm-threaded.js (build with flag '--enable_wasm_threads')
- ort-wasm-threaded.worker.js (build with flag '--enable_wasm_threads')
# The following command build debug.
./build.sh --build_wasm
5. Use following command in folder `<ORT_ROOT>/js/web` to build:
# The following command build debug with debug info.
./build.sh --build_wasm --skip_tests --enable_wasm_debug_info
# The following command build release.
./build.sh --config Release --build_wasm --skip_tests --disable_wasm_exception_catching --disable_rtti
```
To build with multi-thread support, append flag `--enable_wasm_threads` to the command. Make sure to build both single-thread and multi-thread before next step.
2. Copy following files from build output folder to `<ORT_ROOT>/js/web/dist/`:
- ort-wasm.wasm
- ort-wasm-threaded.wasm (build with flag '--enable_wasm_threads')
3. Copy following files from build output folder to `<ORT_ROOT>/js/web/lib/wasm/binding/`:
- ort-wasm.js
- ort-wasm-threaded.js (build with flag '--enable_wasm_threads')
- ort-wasm-threaded.worker.js (build with flag '--enable_wasm_threads')
3. Use following command in folder `<ORT_ROOT>/js/web` to build:
```
npm run build
```

View file

@ -34,13 +34,13 @@ Refer to the following links for development information:
### Compatibility
| OS/Browser | Chrome | Edge | Safari | Electron | Node.js |
| :--------------: | :---------: | :---------: | :----: | :---------: | :-----: |
| Windows 10 | wasm, webgl | wasm, webgl | - | wasm, webgl | wasm |
| macOS | wasm | - | wasm | wasm | wasm |
| Ubuntu LTS 18.04 | wasm | - | - | wasm | wasm |
| iOS | wasm | wasm | wasm | - | - |
| Android | wasm | - | - | - | - |
| OS/Browser | Chrome | Edge | Safari | Electron | Node.js |
| :--------------: | :---------: | :---------: | :---------: | :---------: | :-----: |
| Windows 10 | wasm, webgl | wasm, webgl | - | wasm, webgl | wasm |
| macOS | wasm, webgl | - | wasm, webgl | wasm, webgl | wasm |
| Ubuntu LTS 18.04 | wasm | - | - | wasm | wasm |
| iOS | wasm | wasm | wasm | - | - |
| Android | wasm | - | - | - | - |
### Operators

View file

@ -2,6 +2,7 @@
// Licensed under the MIT License.
import {Tensor} from '../../../tensor';
import {getGlsl} from '../glsl-source';
import {WebGLInferenceHandler} from '../inference-handler';
import {ProgramInfo, RunData, WebGLOperator} from '../types';
import {unpackFromChannel} from './packing-utils';
@ -38,6 +39,7 @@ export class WebGLIm2ColPacked implements WebGLOperator {
const im2colShape = [wshape[1] * wshape[2] * wshape[3], this.convOutputShape[2] * this.convOutputShape[3]];
const kernelSize = wshape[2] * wshape[3];
const unpackChannel = unpackFromChannel();
const glsl = getGlsl(inferenceHandler.session.backend.glContext.version);
let unrolled = '';
for (let row = 0; row <= 1; row++) {
@ -78,7 +80,7 @@ export class WebGLIm2ColPacked implements WebGLOperator {
int blockIndex, pos, offsetY, d0, offsetX, d1, ch;
vec2 innerDims;
${unrolled}
outputColor = result;
${glsl.output} = result;
}
`;
return {

View file

@ -84,7 +84,7 @@ function getA(allGlChannels: string[], rank: number): string {
res += `rc.${allGlChannels[i]}, `;
}
res += `rc.${allGlChannels[rank - 2]}, ` +
'i<<1';
'i*2';
return res;
}
@ -93,7 +93,7 @@ function getB(allGlChannels: string[], rank: number): string {
for (let i = 0; i < rank - 2; i++) {
res += `rc.${allGlChannels[i]}, `;
}
res += 'i<<1, ' +
res += 'i*2, ' +
`rc.${allGlChannels[rank - 1]}`;
return res;
}

View file

@ -186,7 +186,7 @@ export class Tensor {
}
if (empty) {
cache = new Array<string>(size);
this.cache = new Array<string>(size);
}
} else {
if (cache !== undefined) {

View file

@ -7,7 +7,7 @@ export interface OrtWasmModule extends EmscriptenModule {
stackRestore(stack: number): void;
stackAlloc(size: number): number;
UTF8ToString(offset: number): string;
UTF8ToString(offset: number, maxBytesToRead?: number): string;
lengthBytesUTF8(str: string): number;
stringToUTF8(str: string, offset: number, maxBytes: number): void;
//#endregion

View file

@ -1,8 +1,6 @@
// Copyright (c) Microsoft Corporation. All rights reserved.
// Licensed under the MIT License.
import {getInstance} from './wasm-factory';
interface ExtraOptionsHandler {
(name: string, value: string): void;
}
@ -31,14 +29,3 @@ export const iterateExtraOptions =
}
});
};
export const allocWasmString = (data: string, allocs: number[]): number => {
const wasm = getInstance();
const dataLength = wasm.lengthBytesUTF8(data) + 1;
const dataOffset = wasm._malloc(dataLength);
wasm.stringToUTF8(data, dataOffset, dataLength);
allocs.push(dataOffset);
return dataOffset;
};

View file

@ -3,7 +3,8 @@
import {InferenceSession} from 'onnxruntime-common';
import {allocWasmString, iterateExtraOptions} from './options-utils';
import {iterateExtraOptions} from './options-utils';
import {allocWasmString} from './string-utils';
import {getInstance} from './wasm-factory';
export const setRunOptions = (options: InferenceSession.RunOptions): [number, number[]] => {

View file

@ -6,6 +6,7 @@ import {env, InferenceSession, SessionHandler, Tensor, TypedTensor} from 'onnxru
import {setRunOptions} from './run-options';
import {setSessionOptions} from './session-options';
import {allocWasmString} from './string-utils';
import {getInstance} from './wasm-factory';
let ortInit: boolean;
@ -212,10 +213,6 @@ export class OnnxruntimeWebAssemblySessionHandler implements SessionHandler {
if (index === -1) {
throw new Error(`invalid input '${name}'`);
}
if (tensor.type === 'string') {
// TODO: support string tensor
throw new TypeError('string tensor is not supported');
}
inputArray.push(tensor);
inputIndices.push(index);
});
@ -235,41 +232,55 @@ export class OnnxruntimeWebAssemblySessionHandler implements SessionHandler {
const outputCount = outputIndices.length;
let runOptionsHandle = 0;
let allocs: number[] = [];
let runOptionsAllocs: number[] = [];
const inputValues: number[] = [];
const inputDataOffsets: number[] = [];
const inputAllocs: number[] = [];
try {
[runOptionsHandle, allocs] = setRunOptions(options);
[runOptionsHandle, runOptionsAllocs] = setRunOptions(options);
// create input tensors
for (let i = 0; i < inputCount; i++) {
const data = inputArray[i].data;
let dataOffset: number;
let dataByteLength: number;
if (Array.isArray(data)) {
// string tensor
throw new TypeError('string tensor is not supported');
} else {
const dataOffset = wasm._malloc(data.byteLength);
inputDataOffsets.push(dataOffset);
wasm.HEAPU8.set(new Uint8Array(data.buffer, data.byteOffset, data.byteLength), dataOffset);
const dims = inputArray[i].dims;
const stack = wasm.stackSave();
const dimsOffset = wasm.stackAlloc(4 * dims.length);
try {
let dimIndex = dimsOffset / 4;
dims.forEach(d => wasm.HEAP32[dimIndex++] = d);
const tensor = wasm._OrtCreateTensor(
tensorDataTypeStringToEnum(inputArray[i].type), dataOffset, data.byteLength, dimsOffset, dims.length);
if (tensor === 0) {
throw new Error('Can\'t create a tensor');
dataByteLength = 4 * data.length;
dataOffset = wasm._malloc(dataByteLength);
inputAllocs.push(dataOffset);
let dataIndex = dataOffset / 4;
for (let i = 0; i < data.length; i++) {
if (typeof data[i] !== 'string') {
throw new TypeError(`tensor data at index ${i} is not a string`);
}
inputValues.push(tensor);
} finally {
wasm.stackRestore(stack);
wasm.HEAPU32[dataIndex++] = allocWasmString(data[i], inputAllocs);
}
} else {
dataByteLength = data.byteLength;
dataOffset = wasm._malloc(dataByteLength);
inputAllocs.push(dataOffset);
wasm.HEAPU8.set(new Uint8Array(data.buffer, data.byteOffset, dataByteLength), dataOffset);
}
const dims = inputArray[i].dims;
const stack = wasm.stackSave();
const dimsOffset = wasm.stackAlloc(4 * dims.length);
try {
let dimIndex = dimsOffset / 4;
dims.forEach(d => wasm.HEAP32[dimIndex++] = d);
const tensor = wasm._OrtCreateTensor(
tensorDataTypeStringToEnum(inputArray[i].type), dataOffset, dataByteLength, dimsOffset, dims.length);
if (tensor === 0) {
throw new Error('Can\'t create a tensor');
}
inputValues.push(tensor);
} finally {
wasm.stackRestore(stack);
}
}
@ -307,6 +318,8 @@ export class OnnxruntimeWebAssemblySessionHandler implements SessionHandler {
const beforeGetTensorDataStack = wasm.stackSave();
// stack allocate 4 pointer value
const tensorDataOffset = wasm.stackAlloc(4 * 4);
let type: Tensor.Type|undefined, dataOffset = 0;
try {
errorCode = wasm._OrtGetTensorData(
tensor, tensorDataOffset, tensorDataOffset + 4, tensorDataOffset + 8, tensorDataOffset + 12);
@ -315,7 +328,7 @@ export class OnnxruntimeWebAssemblySessionHandler implements SessionHandler {
}
let tensorDataIndex = tensorDataOffset / 4;
const dataType = wasm.HEAPU32[tensorDataIndex++];
const dataOffset: number = wasm.HEAPU32[tensorDataIndex++];
dataOffset = wasm.HEAPU32[tensorDataIndex++];
const dimsOffset = wasm.HEAPU32[tensorDataIndex++];
const dimsLength = wasm.HEAPU32[tensorDataIndex++];
const dims = [];
@ -324,13 +337,19 @@ export class OnnxruntimeWebAssemblySessionHandler implements SessionHandler {
}
wasm._OrtFree(dimsOffset);
const type = tensorDataTypeEnumToString(dataType);
const size = dims.length === 0 ? 1 : dims.reduce((a, b) => a * b);
type = tensorDataTypeEnumToString(dataType);
if (type === 'string') {
// string tensor
throw new TypeError('string tensor is not supported');
const stringData: string[] = [];
let dataIndex = dataOffset / 4;
for (let i = 0; i < size; i++) {
const offset = wasm.HEAPU32[dataIndex++];
const maxBytesToRead = i === size - 1 ? undefined : wasm.HEAPU32[dataIndex] - offset;
stringData.push(wasm.UTF8ToString(offset, maxBytesToRead));
}
output[this.outputNames[outputIndices[i]]] = new Tensor('string', stringData, dims);
} else {
const typedArray = numericTensorTypeToTypedArray(type);
const size = dims.length === 0 ? 1 : dims.reduce((a, b) => a * b);
const t = new Tensor(type, new typedArray(size), dims) as TypedTensor<Exclude<Tensor.Type, 'string'>>;
new Uint8Array(t.data.buffer, t.data.byteOffset, t.data.byteLength)
.set(wasm.HEAPU8.subarray(dataOffset, dataOffset + t.data.byteLength));
@ -338,6 +357,9 @@ export class OnnxruntimeWebAssemblySessionHandler implements SessionHandler {
}
} finally {
wasm.stackRestore(beforeGetTensorDataStack);
if (type === 'string' && dataOffset) {
wasm._free(dataOffset);
}
wasm._OrtReleaseTensor(tensor);
}
}
@ -353,10 +375,10 @@ export class OnnxruntimeWebAssemblySessionHandler implements SessionHandler {
}
} finally {
inputValues.forEach(wasm._OrtReleaseTensor);
inputDataOffsets.forEach(wasm._free);
inputAllocs.forEach(wasm._free);
wasm._OrtReleaseRunOptions(runOptionsHandle);
allocs.forEach(wasm._free);
runOptionsAllocs.forEach(wasm._free);
}
}

View file

@ -3,7 +3,8 @@
import {InferenceSession} from 'onnxruntime-common';
import {allocWasmString, iterateExtraOptions} from './options-utils';
import {iterateExtraOptions} from './options-utils';
import {allocWasmString} from './string-utils';
import {getInstance} from './wasm-factory';
const getGraphOptimzationLevel = (graphOptimizationLevel: string|unknown): number => {

View file

@ -0,0 +1,15 @@
// Copyright (c) Microsoft Corporation. All rights reserved.
// Licensed under the MIT License.
import {getInstance} from './wasm-factory';
export const allocWasmString = (data: string, allocs: number[]): number => {
const wasm = getInstance();
const dataLength = wasm.lengthBytesUTF8(data) + 1;
const dataOffset = wasm._malloc(dataLength);
wasm.stringToUTF8(data, dataOffset, dataLength);
allocs.push(dataOffset);
return dataOffset;
};

View file

@ -2442,6 +2442,12 @@
"integrity": "sha512-BMpfD7PpiETpBl/A6S498BaIJ6Y/ABT93ETbby2fP00v4EbvPBXWEoaR1UBPKs3iR53pJY7EtZk5KACI57i1Uw==",
"dev": true
},
"immediate": {
"version": "3.0.6",
"resolved": "https://registry.npmjs.org/immediate/-/immediate-3.0.6.tgz",
"integrity": "sha1-nbHb0Pr43m++D13V5Wu2BigN5ps=",
"dev": true
},
"import-local": {
"version": "3.0.2",
"resolved": "https://registry.npmjs.org/import-local/-/import-local-3.0.2.tgz",
@ -2792,6 +2798,18 @@
"universalify": "^2.0.0"
}
},
"jszip": {
"version": "3.6.0",
"resolved": "https://registry.npmjs.org/jszip/-/jszip-3.6.0.tgz",
"integrity": "sha512-jgnQoG9LKnWO3mnVNBnfhkh0QknICd1FGSrXcgrl67zioyJ4wgx25o9ZqwNtrROSflGBCGYnJfjrIyRIby1OoQ==",
"dev": true,
"requires": {
"lie": "~3.3.0",
"pako": "~1.0.2",
"readable-stream": "~2.3.6",
"set-immediate-shim": "~1.0.1"
}
},
"karma": {
"version": "6.3.2",
"resolved": "https://registry.npmjs.org/karma/-/karma-6.3.2.tgz",
@ -2953,6 +2971,15 @@
"integrity": "sha512-dcS1ul+9tmeD95T+x28/ehLgd9mENa3LsvDTtzm3vyBEO7RPptvAD+t44WVXaUjTBRcrpFeFlC8WCruUR456hw==",
"dev": true
},
"lie": {
"version": "3.3.0",
"resolved": "https://registry.npmjs.org/lie/-/lie-3.3.0.tgz",
"integrity": "sha512-UaiMJzeWRlEujzAuw5LokY1L5ecNQYZKfmyZ9L7wDHb/p5etKaxXhohBcrw0EYby+G/NA52vRSN4N39dxHAIwQ==",
"dev": true,
"requires": {
"immediate": "~3.0.5"
}
},
"loader-runner": {
"version": "4.2.0",
"resolved": "https://registry.npmjs.org/loader-runner/-/loader-runner-4.2.0.tgz",
@ -4133,6 +4160,12 @@
"integrity": "sha1-BF+XgtARrppoA93TgrJDkrPYkPc=",
"dev": true
},
"set-immediate-shim": {
"version": "1.0.1",
"resolved": "https://registry.npmjs.org/set-immediate-shim/-/set-immediate-shim-1.0.1.tgz",
"integrity": "sha1-SysbJ+uAip+NzEgaWOXlb1mfP2E=",
"dev": true
},
"setimmediate": {
"version": "1.0.5",
"resolved": "https://registry.npmjs.org/setimmediate/-/setimmediate-1.0.5.tgz",

View file

@ -17,6 +17,7 @@
"prepare": "tsc",
"build": "node ./script/build",
"build:doc": "node ./script/generate-operator-md",
"pull:wasm": "node ./script/pull-prebuilt-wasm-artifacts",
"test": "node ./script/prepare-test-data && node ./script/test-runner-cli",
"test:e2e": "node ./test/e2e/run",
"prepack": "node ./script/prepack"
@ -46,6 +47,7 @@
"electron": "^12.0.2",
"fs-extra": "^9.1.0",
"globby": "^11.0.3",
"jszip": "^3.6.0",
"karma": "^6.3.2",
"karma-browserstack-launcher": "^1.6.0",
"karma-chai": "^0.1.0",

View file

@ -0,0 +1,127 @@
// Copyright (c) Microsoft Corporation. All rights reserved.
// Licensed under the MIT License.
//
// This script is used to download WebAssembly build artifacts from CI pipeline.
//
// The goal of this script is to save time for ORT Web developers. For most TypeScript tasks, there is no change in the
// WebAssembly side, so there is no need to rebuild WebAssembly.
//
// It performs the following operations:
// 1. query build ID for latest successful build on master branch
// 2. query download URL of build artifacts
// 3. download and unzip the files to folders
//
import fs from 'fs';
import https from 'https';
import jszip from 'jszip';
import path from 'path';
function downloadJson(url: string, onSuccess: (data: any) => void) {
https.get(url, res => {
const {statusCode} = res;
const contentType = res.headers['content-type'];
if (statusCode !== 200) {
throw new Error(`Failed to download build list. HTTP status code = ${statusCode}`);
}
if (!contentType || !/^application\/json/.test(contentType)) {
throw new Error(`unexpected content type: ${contentType}`);
}
res.setEncoding('utf8');
let rawData = '';
res.on('data', (chunk) => {
rawData += chunk;
});
res.on('end', () => {
onSuccess(JSON.parse(rawData));
});
});
}
function downloadZip(url: string, onSuccess: (data: Buffer) => void) {
https.get(url, res => {
const {statusCode} = res;
const contentType = res.headers['content-type'];
if (statusCode !== 200) {
throw new Error(`Failed to download build list. HTTP status code = ${statusCode}`);
}
if (!contentType || !/^application\/zip/.test(contentType)) {
throw new Error(`unexpected content type: ${contentType}`);
}
const chunks: Buffer[] = [];
res.on('data', (chunk) => {
chunks.push(chunk);
});
res.on('end', () => {
onSuccess(Buffer.concat(chunks));
});
});
}
function extractFile(zip: jszip, folder: string, file: string, artifactName: string) {
zip.file(`${artifactName}/${file}`)!.nodeStream()
.pipe(fs.createWriteStream(path.join(folder, file)))
.on('finish', () => {
console.log('# file downloaded and extracted: ' + file);
});
}
console.log('=== Start to pull WebAssembly artifacts from CI ===');
// API reference: https://docs.microsoft.com/en-us/rest/api/azure/devops/build/builds/list
downloadJson(
'https://dev.azure.com/onnxruntime/onnxruntime/_apis/build/builds?api-version=6.1-preview.6' +
'&definitions=161' +
'&resultFilter=succeeded' +
'&$top=1' +
'&repositoryId=Microsoft/onnxruntime' +
'&repositoryType=GitHub' +
'&branchName=refs/heads/master',
data => {
const buildId = data.value[0].id;
console.log(`=== Found latest master build : ${buildId} ===`);
// API reference: https://docs.microsoft.com/en-us/rest/api/azure/devops/build/artifacts/get%20artifact
downloadJson(
`https://dev.azure.com/onnxruntime/onnxruntime/_apis/build/builds/${
buildId}/artifacts?api-version=6.1-preview.5`,
data => {
let ortWasmZipLink, ortWasmThreadedZipLink;
for (const v of data.value) {
if (v.name === 'Release_ort-wasm') {
ortWasmZipLink = v.resource.downloadUrl;
}
if (v.name === 'Release_ort-wasm-threaded') {
ortWasmThreadedZipLink = v.resource.downloadUrl;
}
}
console.log('=== Ready to download zip files ===');
const WASM_FOLDER = path.join(__dirname, '../dist');
if (!fs.existsSync(WASM_FOLDER)) {
fs.mkdirSync(WASM_FOLDER);
}
const JS_FOLDER = path.join(__dirname, '../lib/wasm/binding');
downloadZip(ortWasmZipLink, buffer => {
void jszip.loadAsync(buffer).then(zip => {
extractFile(zip, JS_FOLDER, 'ort-wasm.js', 'Release_ort-wasm');
extractFile(zip, WASM_FOLDER, 'ort-wasm.wasm', 'Release_ort-wasm');
});
});
downloadZip(ortWasmThreadedZipLink, buffer => {
void jszip.loadAsync(buffer).then(zip => {
extractFile(zip, JS_FOLDER, 'ort-wasm-threaded.js', 'Release_ort-wasm-threaded');
extractFile(zip, JS_FOLDER, 'ort-wasm-threaded.worker.js', 'Release_ort-wasm-threaded');
extractFile(zip, WASM_FOLDER, 'ort-wasm-threaded.wasm', 'Release_ort-wasm-threaded');
});
});
});
});

View file

@ -382,7 +382,12 @@ export class TensorResultValidator {
}
for (let i = actual.length - 1; i >= 0; i--) {
const a = actual[i], b = Math.max(Math.min(expected[i], this.maxFloatValue), -this.maxFloatValue);
const a = actual[i];
let b = expected[i];
if (a === b) {
continue; // exact the same value, treat as equal
}
// check for NaN
//
@ -394,6 +399,16 @@ export class TensorResultValidator {
return false; // one is NaN and the other is not
}
// check for Infinity
//
if (!Number.isFinite(a) || !Number.isFinite(b)) {
Logger.error('Validator', `a or b is Infinity -- index:${i}: actual=${actual[i]},expected=${expected[i]}`);
return false; // at least one is Infinity and the other is not or their sign is different
}
// normalize value of b
b = Math.max(Math.min(expected[i], this.maxFloatValue), -this.maxFloatValue);
// Comparing 2 float numbers: (Suppose a >= b)
//
// if ( a - b < ABSOLUTE_ERROR || 1.0 < a / b < RELATIVE_ERROR)
@ -433,28 +448,6 @@ export class TensorResultValidator {
}
}
// TODO fix the reshape and flatten ops to be compatible with webgl1
const UNSUPPORTED_WEBGL_1_TESTS = [
'test_flatten_axis0', 'test_flatten_axis1', 'test_flatten_axis2',
'test_flatten_default_axis', 'test_reshape_extended_dims', 'test_reshape_negative_dim',
'test_reshape_one_dim', 'test_reshape_reduced_dims', 'test_flatten_axis0',
'test_flatten_axis1', 'test_flatten_axis2', 'test_flatten_default_axis',
'test_reshape_extended_dims', 'test_reshape_negative_dim', 'test_reshape_one_dim',
'test_reshape_reduced_dims', 'test_flatten_axis0', 'test_flatten_axis1',
'test_flatten_axis2', 'test_flatten_default_axis', 'test_reshape_extended_dims',
'test_reshape_negative_dim', 'test_reshape_one_dim', 'test_reshape_reduced_dims',
'test_reshape_reordered_dims', 'test_flatten_axis0', 'test_flatten_axis1',
'test_flatten_axis2', 'test_flatten_default_axis', 'test_reshape_extended_dims',
'test_reshape_negative_dim', 'test_reshape_one_dim', 'test_reshape_reduced_dims',
'test_reshape_reordered_dims', 'test_flatten_axis0', 'test_flatten_axis1',
'test_flatten_axis2', 'test_flatten_default_axis', 'test_reshape_extended_dims',
'test_reshape_negative_dim', 'test_reshape_one_dim', 'test_reshape_reduced_dims',
'test_reshape_reordered_dims', 'test_flatten_axis0', 'test_flatten_axis1',
'test_flatten_axis2', 'test_flatten_default_axis', 'test_reshape_extended_dims',
'test_reshape_negative_dim', 'test_reshape_one_dim', 'test_reshape_reduced_dims',
'test_reshape_reordered_dims',
];
/**
* run a single model test case. the inputs/outputs tensors should already been prepared.
*/
@ -464,15 +457,6 @@ export async function runModelTestSet(
Logger.verbose('TestRunner', `Start to run test data from folder: ${testCase.name}`);
const validator = new TensorResultValidator(context.backend);
try {
if (context.backend === 'webgl') {
// TODO skipping incompatible tests for now
if (createWebGLContext(ort.env.webgl.contextId).version === 1 &&
UNSUPPORTED_WEBGL_1_TESTS.indexOf(testName) !== -1) {
Logger.info('TestRunner', `Found incompatible test on webgl 1: ${testName} - ${testCase.name}. Skipping.`);
return;
}
}
const feeds: Record<string, ort.Tensor> = {};
testCase.inputs!.forEach((tensor, i) => feeds[context.session.inputNames[i]] = tensor);
const start = now();

View file

@ -315,6 +315,7 @@
"test_basic_conv_without_padding",
"test_batchnorm_epsilon",
"test_batchnorm_example",
"v{10,11,12}/test_cast_STRING_to_FLOAT",
"v{7,8,9,10}/test_clip_splitbounds",
"v{7,8,9,10}/test_clip_outbounds",
"v{7,8,9,10}/test_clip_inbounds",

View file

@ -217,12 +217,6 @@ describe('#UnitTest# - packed concat - Tensor concat', () => {
it('Test packed concat kernel ', () => {
const webglInferenceHandler = inferenceHandler as WebGLInferenceHandler;
// TODO support WebGl 1.0
if (webglInferenceHandler.session.textureManager.glContext.version === 1) {
console.log('Running packed concat with webgl1 is not supported. Skipping.');
return;
}
if (!env.webgl.pack) {
console.log('Skipping in unpacked texture mode.');
return;

View file

@ -131,12 +131,6 @@ describe('#UnitTest# - unpacked WebGLDepthToSpace - Tensor WebGLDepthToSpace', (
it('Test depth to space ', () => {
const webglInferenceHandler = inferenceHandler as WebGLInferenceHandler;
// TODO support WebGl 1.0
if (webglInferenceHandler.session.textureManager.glContext.version === 1) {
console.log('Running depth to space with webgl1 is not supported. Skipping.');
return;
}
const op = new WebGLDepthToSpace();
const attributes = new Attribute(undefined);
const blocksize = testData.blocksize;

View file

@ -151,12 +151,6 @@ describe('#UnitTest# - packed matmul - Tensor matmul', () => {
it('Test packed matmul kernel ', () => {
const webglInferenceHandler = inferenceHandler as WebGLInferenceHandler;
// TODO support WebGl 1.0
if (webglInferenceHandler.session.textureManager.glContext.version === 1) {
console.log('Running packed matmul with webgl1 is not supported. Skipping.');
return;
}
if (!env.webgl.pack) {
console.log('Skipping in unpacked texture mode.');
return;

View file

@ -219,12 +219,6 @@ describe('#UnitTest# - pack - Tensor pack', () => {
it(`Test pack kernal ${textureLayout[w]} ${JSON.stringify(testData)}`, () => {
const webglInferenceHandler = inferenceHandler as WebGLInferenceHandler;
// TODO support WebGl 1.0
if (webglInferenceHandler.session.textureManager.glContext.version === 1) {
console.log('Running pack with webgl1 is not supported. Skipping.');
return;
}
const op = new WebGLPack();
const elementCount = testData.elementCount;
@ -287,12 +281,6 @@ describe('#UnitTest# - unpack - Tensor unpack', () => {
it(`Test unpack kernal ${testData.inputShape}`, () => {
const webglInferenceHandler = inferenceHandler as WebGLInferenceHandler;
// TODO support WebGl 1.0
if (webglInferenceHandler.session.textureManager.glContext.version === 1) {
console.log('Running unpack with webgl1 is not supported. Skipping.');
return;
}
const op = new WebGLUnpack();
const elementCount = testData.elementCount;
@ -370,12 +358,6 @@ describe('#UnitTest# - pack-unpack round trip', () => {
it(`Test pack-unpack round trip ${JSON.stringify(testData)}`, () => {
const webglInferenceHandler = inferenceHandler as WebGLInferenceHandler;
// TODO support WebGl 1.0
if (webglInferenceHandler.session.textureManager.glContext.version === 1) {
console.log('Running pack with webgl1 is not supported. Skipping.');
return;
}
const packOp = new WebGLPack();
const elementCount = testData.elementCount;

View file

@ -121,12 +121,6 @@ describe('#UnitTest# - reshape - packed', () => {
it(`Test packed reshape kernel ${JSON.stringify(testData.outputShape)}`, () => {
const webglInferenceHandler = inferenceHandler as WebGLInferenceHandler;
// TODO support WebGl 1.0
if (webglInferenceHandler.session.textureManager.glContext.version === 1) {
console.log('Running packed concat with webgl1 is not supported. Skipping.');
return;
}
if (!env.webgl.pack) {
console.log('Skipping in unpacked texture mode.');
return;

View file

@ -4,6 +4,7 @@
// this header contains the entire ONNX Runtime Objective-C API
// the headers below can also be imported individually
#import "ort_coreml_execution_provider.h"
#import "ort_enums.h"
#import "ort_env.h"
#import "ort_session.h"

View file

@ -0,0 +1,54 @@
// Copyright (c) Microsoft Corporation. All rights reserved.
// Licensed under the MIT License.
#import <Foundation/Foundation.h>
#import "ort_session.h"
NS_ASSUME_NONNULL_BEGIN
/**
* Gets whether the CoreML execution provider is available.
*/
BOOL ORTIsCoreMLExecutionProviderAvailable();
/**
* Options for configuring the CoreML execution provider.
*/
@interface ORTCoreMLExecutionProviderOptions : NSObject
/**
* Whether the CoreML execution provider should run on CPU only.
*/
@property BOOL useCPUOnly;
/**
* Whether the CoreML execution provider is enabled on subgraphs.
*/
@property BOOL enableOnSubgraphs;
/**
* Whether the CoreML execution provider is only enabled for devices with Apple
* Neural Engine (ANE).
*/
@property BOOL onlyEnableForDevicesWithANE;
@end
@interface ORTSessionOptions (ORTSessionOptionsCoreMLEP)
/**
* Enables the CoreML execution provider in the session configuration options.
* It is appended to the execution provider list which is ordered by
* decreasing priority.
*
* @param options The CoreML execution provider configuration options.
* @param[out] error Optional error information set if an error occurs.
* @return Whether the provider was enabled successfully.
*/
- (BOOL)appendCoreMLExecutionProviderWithOptions:(ORTCoreMLExecutionProviderOptions*)options
error:(NSError**)error;
@end
NS_ASSUME_NONNULL_END

View file

@ -0,0 +1,53 @@
// Copyright (c) Microsoft Corporation. All rights reserved.
// Licensed under the MIT License.
#import "ort_coreml_execution_provider.h"
#if __has_include("coreml_provider_factory.h")
#define ORT_OBJC_API_COREML_EP_AVAILABLE 1
#else
#define ORT_OBJC_API_COREML_EP_AVAILABLE 0
#endif
#if ORT_OBJC_API_COREML_EP_AVAILABLE
#include "coreml_provider_factory.h"
#endif
#import "src/error_utils.h"
#import "src/ort_session_internal.h"
NS_ASSUME_NONNULL_BEGIN
BOOL ORTIsCoreMLExecutionProviderAvailable() {
return ORT_OBJC_API_COREML_EP_AVAILABLE ? YES : NO;
}
@implementation ORTCoreMLExecutionProviderOptions
@end
@implementation ORTSessionOptions (ORTSessionOptionsCoreMLEP)
- (BOOL)appendCoreMLExecutionProviderWithOptions:(ORTCoreMLExecutionProviderOptions*)options
error:(NSError**)error {
#if ORT_OBJC_API_COREML_EP_AVAILABLE
try {
const uint32_t flags =
(options.useCPUOnly ? COREML_FLAG_USE_CPU_ONLY : 0) |
(options.enableOnSubgraphs ? COREML_FLAG_ENABLE_ON_SUBGRAPH : 0) |
(options.onlyEnableForDevicesWithANE ? COREML_FLAG_ONLY_ENABLE_DEVICE_WITH_ANE : 0);
Ort::ThrowOnError(OrtSessionOptionsAppendExecutionProvider_CoreML(
[self CXXAPIOrtSessionOptions], flags));
return YES;
}
ORT_OBJC_API_IMPL_CATCH_RETURNING_BOOL(error);
#else // !ORT_OBJC_API_COREML_EP_AVAILABLE
static_cast<void>(options);
ORTSaveCodeAndDescriptionToError(ORT_FAIL, "CoreML execution provider is not enabled.", error);
return NO;
#endif
}
@end
NS_ASSUME_NONNULL_END

View file

@ -1,7 +1,7 @@
// Copyright (c) Microsoft Corporation. All rights reserved.
// Licensed under the MIT License.
#import "ort_session_internal.h"
#import "src/ort_session_internal.h"
#include <optional>
#include <vector>

View file

@ -3,6 +3,7 @@
#import <XCTest/XCTest.h>
#import "ort_coreml_execution_provider.h"
#import "ort_env.h"
#import "ort_session.h"
#import "ort_value.h"
@ -191,6 +192,29 @@ NS_ASSUME_NONNULL_BEGIN
ORTAssertBoolResultUnsuccessful(runResult, err);
}
- (void)testAppendCoreMLEP {
NSError* err = nil;
ORTSessionOptions* sessionOptions = [ORTSessionTest makeSessionOptions];
ORTCoreMLExecutionProviderOptions* coreMLOptions = [[ORTCoreMLExecutionProviderOptions alloc] init];
coreMLOptions.enableOnSubgraphs = YES; // set an arbitrary option
BOOL appendResult = [sessionOptions appendCoreMLExecutionProviderWithOptions:coreMLOptions
error:&err];
if (!ORTIsCoreMLExecutionProviderAvailable()) {
ORTAssertBoolResultUnsuccessful(appendResult, err);
return;
}
ORTAssertBoolResultSuccessful(appendResult, err);
ORTSession* session = [[ORTSession alloc] initWithEnv:self.ortEnv
modelPath:[ORTSessionTest getAddModelPath]
sessionOptions:sessionOptions
error:&err];
ORTAssertNullableResultSuccessful(session, err);
}
@end
NS_ASSUME_NONNULL_END

Binary file not shown.

Binary file not shown.

View file

@ -15,5 +15,5 @@ graph = helper.make_graph(
helper.make_tensor_value_info('C', TensorProto.FLOAT, [1]),
])
model = helper.make_model(graph)
model = helper.make_model(graph, opset_imports=[helper.make_opsetid("", 12)])
onnx.save(model, r'single_add.onnx')

View file

@ -54,9 +54,12 @@ static ONNX_NAMESPACE::ModelProto GetModelProtoFromFusedNode(const onnxruntime::
VitisAICustomOp::VitisAICustomOp(const ComputeContext* context,
const onnxruntime::Node* fused_node,
const std::string &backend_type,
const std::string& backend_type,
const std::string& export_runtime_module,
const std::string& load_runtime_module,
const logging::Logger* logger)
: backend_type_(backend_type)
: backend_type_(backend_type), export_runtime_module_(export_runtime_module),
load_runtime_module_(load_runtime_module)
{
SetLogger(logger);
@ -66,26 +69,43 @@ VitisAICustomOp::VitisAICustomOp(const ComputeContext* context,
name_ = context->node_name;
model_proto_ = GetModelProtoFromFusedNode(fused_node, *GetLogger());
std::istringstream model_stream{model_proto_.SerializeAsString()};
xg_ = pyxir::onnx::import_onnx_model(model_stream);
pyxir::partition(xg_, std::vector<std::string>{backend_type_}, "");
auto input_defs = fused_node->InputDefs();
for (auto idef : input_defs) {
in_tensor_names_.push_back(idef->Name());
}
auto output_defs = fused_node->OutputDefs();
for (auto odef : output_defs) {
out_tensor_names_.push_back(odef->Name());
}
pyxir::RunOptionsHolder run_options(new pyxir::runtime::RunOptions());
run_options->on_the_fly_quantization = true;
rt_mod_ = pyxir::build_rt(xg_, backend_type_, in_tensor_names_, out_tensor_names_,
"vai", run_options);
// If the `load_runtime_module` provider option is empty we build a PyXIR
// runtime module from scratch. Otherwise, we load the runtime module from
// the provided file.
if (load_runtime_module_.empty()) {
pyxir::partition(xg_, std::vector<std::string>{backend_type_}, "");
auto input_defs = fused_node->InputDefs();
for (auto idef : input_defs) {
in_tensor_names_.push_back(idef->Name());
}
auto output_defs = fused_node->OutputDefs();
for (auto odef : output_defs) {
out_tensor_names_.push_back(odef->Name());
}
pyxir::RunOptionsHolder run_options(new pyxir::runtime::RunOptions());
run_options->on_the_fly_quantization = true;
run_options->export_runtime_module_path = export_runtime_module_;
rt_mod_ = pyxir::build_rt(xg_, backend_type_, in_tensor_names_,
out_tensor_names_, "vai", run_options);
} else {
std::ifstream in_file(load_runtime_module_);
std::stringstream buffer;
buffer << in_file.rdbuf();
std::string serialized_rt_mod = buffer.str();
in_file.close();
std::istringstream sstream(serialized_rt_mod);
rt_mod_.reset(new pyxir::runtime::RuntimeModule());
rt_mod_->deserialize(sstream);
in_tensor_names_ = rt_mod_->get_in_tensor_names();
out_tensor_names_ = rt_mod_->get_out_tensor_names();
}
}
VitisAICustomOp::~VitisAICustomOp() {}

View file

@ -30,7 +30,9 @@ class VitisAICustomOp {
public:
VitisAICustomOp(const ComputeContext* context,
const onnxruntime::Node* fused_node,
const std::string &backend_type,
const std::string& backend_type,
const std::string& export_runtime_module,
const std::string& load_runtime_module,
const logging::Logger* logger);
Status Compute(const OrtApi* api, OrtKernelContext* context) const;
@ -46,27 +48,35 @@ class VitisAICustomOp {
}
private:
// The partition input tensor names
std::vector<std::string> in_tensor_names_;
// The partition output tensor names
std::vector<std::string> out_tensor_names_;
// The PyXIR graph data structure
pyxir::XGraphHolder xg_;
// The Vitis AI DPU target
std::string backend_type_;
// If not empty, the path to the file where the PyXIR runtime module
// should be exported to (used for cross compilation)
std::string export_runtime_module_;
// If not empty, the path to the file where the PyXIR runtime module should
// be loaded from
std::string load_runtime_module_;
// The PyXIR runtime module
pyxir::RtModHolder rt_mod_ = nullptr;
// The EP ComputeContext allocation function
AllocateFunc allocate_func_ = nullptr;
// The EP ComputeContext release function
DestroyFunc release_func_ = nullptr;
// The EP ComputeContext allocator
AllocatorHandle allocator_ = nullptr;
// The EP ComputeContext node name
std::string name_;
// The compute lock
mutable std::mutex compute_lock_;
// The logger
const logging::Logger* logger_ = nullptr;
// The ONNX ModelProto to go from fused node -> ModelProto -> PyXIR
ONNX_NAMESPACE::ModelProto model_proto_;
};
} // namespace vitisai_ep

View file

@ -30,7 +30,9 @@ typedef std::shared_ptr<pyxir::graph::XGraph> XGraphHolder;
typedef std::shared_ptr<pyxir::graph::XLayer> XLayerHolder;
VitisAIExecutionProvider::VitisAIExecutionProvider(const VitisAIExecutionProviderInfo& info)
: IExecutionProvider{onnxruntime::kVitisAIExecutionProvider}, backend_type_(info.backend_type), device_id_(info.device_id) {
: IExecutionProvider{onnxruntime::kVitisAIExecutionProvider}, backend_type_(info.backend_type),
device_id_(info.device_id), export_runtime_module_(info.export_runtime_module),
load_runtime_module_(info.load_runtime_module) {
AllocatorCreationInfo default_memory_info{
[](int) {
return std::make_unique<CPUAllocator>(OrtMemoryInfo(VITISAI, OrtAllocatorType::OrtDeviceAllocator));
@ -276,7 +278,8 @@ common::Status VitisAIExecutionProvider::Compile(const std::vector<onnxruntime::
for (const auto& fused_node : fused_nodes) {
NodeComputeInfo compute_info;
compute_info.create_state_func = [this, fused_node, logger = GetLogger()](ComputeContext* context, FunctionState* state) {
auto* p = new vitisai_ep::VitisAICustomOp(context, fused_node, backend_type_, logger);
auto* p = new vitisai_ep::VitisAICustomOp(context, fused_node, backend_type_, export_runtime_module_,
load_runtime_module_, logger);
*state = p;
return 0;
};

View file

@ -13,6 +13,8 @@ namespace onnxruntime {
struct VitisAIExecutionProviderInfo {
int device_id{0};
std::string backend_type;
std::string export_runtime_module;
std::string load_runtime_module;
};
// Logical device representation.
@ -31,8 +33,16 @@ class VitisAIExecutionProvider : public IExecutionProvider {
std::vector<NodeComputeInfo>& node_compute_funcs) override;
private:
std::string backend_type_;
// The Vitis AI DPU target
std::string backend_type_;
// Device ID (Unused for now)
int device_id_;
// If not empty, the path to the file where the PyXIR runtime module
// should be exported to (used for cross compilation)
std::string export_runtime_module_;
// If not empty, the path to the file where the PyXIR runtime module
// should be loaded from
std::string load_runtime_module_;
};
} // namespace onnxruntime

View file

@ -11,31 +11,50 @@ using namespace onnxruntime;
namespace onnxruntime {
struct VitisAIProviderFactory : IExecutionProviderFactory {
VitisAIProviderFactory(std::string&& backend_type, int device_id)
: backend_type_(std::move(backend_type)), device_id_(device_id) {}
VitisAIProviderFactory(std::string&& backend_type, int device_id, std::string&& export_runtime_module,
std::string&& load_runtime_module)
: backend_type_(std::move(backend_type)), device_id_(device_id),
export_runtime_module_(std::move(export_runtime_module)),
load_runtime_module_(std::move(load_runtime_module)) {}
~VitisAIProviderFactory() = default;
std::unique_ptr<IExecutionProvider> CreateProvider() override;
private:
// The Vitis AI DPU target
const std::string backend_type_;
// Device ID (Unused for now)
int device_id_;
// If not empty, the path to the file where the PyXIR runtime module
// should be exported to (used for cross compilation)
const std::string export_runtime_module_;
// If not empty, the path to the file where the PyXIR runtime module
// should be loaded from
const std::string load_runtime_module_;
};
std::unique_ptr<IExecutionProvider> VitisAIProviderFactory::CreateProvider() {
VitisAIExecutionProviderInfo info;
info.backend_type = backend_type_;
info.device_id = device_id_;
info.export_runtime_module = export_runtime_module_;
info.load_runtime_module = load_runtime_module_;
return std::make_unique<VitisAIExecutionProvider>(info);
}
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_VITISAI(const char *backend_type, int device_id) {
return std::make_shared<onnxruntime::VitisAIProviderFactory>(backend_type, device_id);
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_VITISAI(
const char* backend_type, int device_id, const char* export_runtime_module,
const char* load_runtime_module) {
return std::make_shared<onnxruntime::VitisAIProviderFactory>(
backend_type, device_id, export_runtime_module, load_runtime_module);
}
} // namespace onnxruntime
ORT_API_STATUS_IMPL(OrtSessionOptionsAppendExecutionProvider_VITISAI, _In_ OrtSessionOptions* options, _In_ const char* backend_type, int device_id) {
options->provider_factories.push_back(onnxruntime::CreateExecutionProviderFactory_VITISAI(backend_type, device_id));
ORT_API_STATUS_IMPL(OrtSessionOptionsAppendExecutionProvider_VITISAI,
_In_ OrtSessionOptions* options, _In_ const char* backend_type, int device_id,
const char* export_runtime_module, const char* load_runtime_module) {
options->provider_factories.push_back(onnxruntime::CreateExecutionProviderFactory_VITISAI(
backend_type, device_id, export_runtime_module, load_runtime_module));
return nullptr;
}

View file

@ -47,7 +47,9 @@ std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_Cuda(c
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_Dnnl(int use_arena);
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_OpenVINO(const OrtOpenVINOProviderOptions* params);
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_Nuphar(bool, const char*);
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_VITISAI(const char* backend_type, int device_id);
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_VITISAI(const char* backend_type, int device_id,
const char* export_runtime_module,
const char* load_runtime_module);
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_ACL(int use_arena);
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_ArmNN(int use_arena);
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_DML(int device_id);
@ -574,7 +576,34 @@ static void RegisterExecutionProviders(InferenceSession* sess, const std::vector
#endif
} else if (type == kVitisAIExecutionProvider) {
#if USE_VITISAI
RegisterExecutionProvider(sess, *onnxruntime::CreateExecutionProviderFactory_VITISAI("dpuv1", 0));
// Retrieve Vitis AI provider options
// `target`: The name of the DPU target (default is DPUCADX8G for backward compatibility).
// `export_runtime_module`: export a Vitis AI PyXIR runtime module to the specified file.
// This can be used for cross compilation or saving state.
// `load_runtime_module`: Load an exported runtime module from disk.
std::string target = "DPUCADX8G";
std::string export_runtime_module = "";
std::string load_runtime_module = "";
auto it = provider_options_map.find(type);
if (it != provider_options_map.end()) {
auto vitis_ai_provider_options = it->second;
auto vai_options_it = vitis_ai_provider_options.find("target");
if (vai_options_it != vitis_ai_provider_options.end()) {
target = vai_options_it->second;
}
vai_options_it = vitis_ai_provider_options.find("export_runtime_module");
if (vai_options_it != vitis_ai_provider_options.end()) {
export_runtime_module = vai_options_it->second;
}
vai_options_it = vitis_ai_provider_options.find("load_runtime_module");
if (vai_options_it != vitis_ai_provider_options.end()) {
load_runtime_module = vai_options_it->second;
}
}
RegisterExecutionProvider(
sess, *onnxruntime::CreateExecutionProviderFactory_VITISAI(target.c_str(), 0,
export_runtime_module.c_str(),
load_runtime_module.c_str()));
#endif
} else if (type == kAclExecutionProvider) {
#ifdef USE_ACL
@ -861,7 +890,7 @@ void addGlobalMethods(py::module& m, Environment& env) {
onnxruntime::CreateExecutionProviderFactory_MIGraphX(0),
#endif
#ifdef USE_VITISAI
onnxruntime::CreateExecutionProviderFactory_VitisAI("DPU", 0),
onnxruntime::CreateExecutionProviderFactory_VITISAI("DPUCADX8G", 0, "", ""),
#endif
#ifdef USE_ACL
onnxruntime::CreateExecutionProviderFactory_ACL(0),

View file

@ -112,7 +112,7 @@ class ONNXModel:
def find_node_by_name(self, node_name, new_nodes_list, graph):
'''
Find out if a node exists in a graph or a node is in the
Find out if a node exists in a graph or a node is in the
new set of nodes created during quantization. Return the node found.
'''
graph_nodes_list = list(graph.node) #deep copy
@ -256,6 +256,8 @@ class ONNXModel:
return True
return False
# TODO:use OnnxModel.graph_topological_sort(self.model.graph) from transformers.onnx_model
# Currently it breaks Openvino/Linux training gpu pipeline so hold off for 1.8 release
def topological_sort(self):
deps_count = [0]*len(self.nodes()) # dependency count of each node
deps_to_nodes = {} # input to node indice

View file

@ -781,7 +781,67 @@ class OnnxModel:
return False
return True
@staticmethod
def graph_topological_sort(graph):
deps_count = [0]*len(graph.node) # dependency count of each node
deps_to_nodes = {} # input to node indice
sorted_nodes = [] # initialize sorted_nodes
for node_idx, node in enumerate(graph.node):
# CANNOT use len(node.input) directly because input can be optional
deps_count[node_idx] = sum(1 for _ in node.input if _ )
if deps_count[node_idx] == 0: # Constant doesn't depend on any inputs
sorted_nodes.append(graph.node[node_idx])
continue
for input_name in node.input:
if input_name not in deps_to_nodes:
deps_to_nodes[input_name] = [node_idx]
else:
deps_to_nodes[input_name].append(node_idx)
initializer_names = [init.name for init in graph.initializer]
graph_input_names = [input.name for input in graph.input]
input_names = initializer_names + graph_input_names
input_names.sort()
prev_input_name = None
for input_name in input_names:
if prev_input_name == input_name:
continue
prev_input_name = input_name
if input_name in deps_to_nodes:
for node_idx in deps_to_nodes[input_name]:
deps_count[node_idx] = deps_count[node_idx] - 1
if deps_count[node_idx] == 0:
sorted_nodes.append(graph.node[node_idx])
start = 0
end = len(sorted_nodes)
while start < end:
for output in sorted_nodes[start].output:
if output in deps_to_nodes:
for node_idx in deps_to_nodes[output]:
deps_count[node_idx] = deps_count[node_idx] - 1
if deps_count[node_idx] == 0:
sorted_nodes.append(graph.node[node_idx])
end = end + 1
start = start + 1
assert(end == len(graph.node)), "Graph is not a DAG"
graph.ClearField('node')
graph.node.extend(sorted_nodes)
def topological_sort(self):
#TODO: support graph_topological_sort() in subgraphs
#for graph in self.graphs():
# self.graph_topological_sort(graph)
OnnxModel.graph_topological_sort(self.model.graph)
def save_model_to_file(self, output_path, use_external_data_format=False):
logger.info(f"Sort graphs in topological order")
self.topological_sort()
logger.info(f"Output model to {output_path}")
Path(output_path).parent.mkdir(parents=True, exist_ok=True)

View file

@ -206,8 +206,8 @@ static std::vector<uint8_t> transpose_to_nhwc(const std::vector<uint8_t>& nchw_d
auto channels = nchw_dims[1];
int64_t image_size = std::accumulate(nchw_dims.begin() + 2, nchw_dims.end(), 1LL, std::multiplies<int64_t>());
for (int64_t b = 0; b < batch_count; b++) {
const uint8_t* nchw_image = nchw_data.data() + (b * image_size);
uint8_t* nhwc_image = nhwc_data.data() + (b * image_size);
const uint8_t* nchw_image = nchw_data.data() + (b * channels * image_size);
uint8_t* nhwc_image = nhwc_data.data() + (b * channels * image_size);
for (int64_t img_index = 0; img_index < image_size; ++img_index) {
for (int64_t c = 0; c < channels; c++) {
*nhwc_image++ = nchw_image[c * image_size + img_index];
@ -331,6 +331,16 @@ TEST(QLinearPoolTest, AveragePool2D_IncludePadPixel) {
1); // count_include_pad
}
TEST(QLinearPoolTest, AveragePool2D_MultiChannel) {
RunQLinearAveragePoolNchwU8(
{1, 3, 5, 7}, // x shape
{1, 3, 6, 4}, // expected y shape
{3, 4}, // kernel shape
{1, 2}, // strides
{1, 3, 2, 1}, // pads
1); // count_include_pad
}
TEST(QLinearPoolTest, AveragePool3D_ExcludePadPixel) {
RunQLinearAveragePoolNchwU8(
{1, 1, 5, 7, 9}, // x shape
@ -394,6 +404,16 @@ TEST(QLinearPoolTest, AveragePool2D_IncludePadPixel_nhwc) {
1); // count_include_pad
}
TEST(QLinearPoolTest, AveragePool2D_MultiChannel_nhwc) {
RunQLinearAveragePoolNhwcU8(
{1, 3, 5, 7}, // x shape
{1, 3, 6, 4}, // expected y shape
{3, 4}, // kernel shape
{1, 2}, // strides
{1, 3, 2, 1}, // pads
1); // count_include_pad
}
TEST(QLinearPoolTest, AveragePool3D_ExcludePadPixel_nhwc) {
RunQLinearAveragePoolNhwcU8(
{1, 1, 5, 7, 9}, // x shape

View file

@ -11,9 +11,9 @@ namespace onnxruntime {
namespace test {
TEST(InvokerTest, Basic) {
std::unique_ptr<IExecutionProvider> cpu_execution_provider = onnxruntime::make_unique<CPUExecutionProvider>(CPUExecutionProviderInfo(false));
std::unique_ptr<IExecutionProvider> cpu_execution_provider = std::make_unique<CPUExecutionProvider>(CPUExecutionProviderInfo(false));
const std::string logger_id{"InvokerTest"};
auto logging_manager = onnxruntime::make_unique<logging::LoggingManager>(
auto logging_manager = std::make_unique<logging::LoggingManager>(
std::unique_ptr<logging::ISink>{new logging::CLogSink{}},
logging::Severity::kVERBOSE, false,
logging::LoggingManager::InstanceType::Default,
@ -44,9 +44,9 @@ TEST(InvokerTest, Basic) {
}
TEST(InvokerTest, Inplace) {
std::unique_ptr<IExecutionProvider> cpu_execution_provider = onnxruntime::make_unique<CPUExecutionProvider>(CPUExecutionProviderInfo(false));
std::unique_ptr<IExecutionProvider> cpu_execution_provider = std::make_unique<CPUExecutionProvider>(CPUExecutionProviderInfo(false));
const std::string logger_id{"InvokerTest"};
auto logging_manager = onnxruntime::make_unique<logging::LoggingManager>(
auto logging_manager = std::make_unique<logging::LoggingManager>(
std::unique_ptr<logging::ISink>{new logging::CLogSink{}},
logging::Severity::kVERBOSE, false,
logging::LoggingManager::InstanceType::Default,

View file

@ -1,13 +1,8 @@
// Copyright (c) Microsoft Corporation. All rights reserved.
// Licensed under the MIT License.
#undef USE_CUDA // TODO: Cuda is a shared library, so can't call any Cuda provider methods directly from here
#include "test/framework/TestAllocatorManager.h"
#include "core/framework/allocatormgr.h"
#ifdef USE_CUDA
#include "core/providers/cuda/cuda_allocator.h"
#endif // USE_CUDA
namespace onnxruntime {
namespace test {
@ -99,14 +94,6 @@ AllocatorManager::AllocatorManager() {
Status AllocatorManager::InitializeAllocators() {
auto cpu_alocator = std::make_unique<CPUAllocator>();
ORT_RETURN_IF_ERROR(RegisterAllocator(map_, std::move(cpu_alocator), std::numeric_limits<size_t>::max(), true));
#ifdef USE_CUDA
auto cuda_alocator = std::make_unique<CUDAAllocator>(static_cast<OrtDevice::DeviceId>(0), CUDA);
ORT_RETURN_IF_ERROR(RegisterAllocator(map_, std::move(cuda_alocator), std::numeric_limits<size_t>::max(), true));
auto cuda_pinned_alocator = std::make_unique<CUDAPinnedAllocator>(static_cast<OrtDevice::DeviceId>(0), CUDA_PINNED);
ORT_RETURN_IF_ERROR(RegisterAllocator(map_, std::move(cuda_pinned_alocator), std::numeric_limits<size_t>::max(), true));
#endif // USE_CUDA
return Status::OK();
}

View file

@ -1,6 +1,5 @@
// Copyright (c) Microsoft Corporation. All rights reserved.
// Licensed under the MIT License.
#if 0 // TODO: Can't call these directly from external code as Cuda is now a shared library
#include "core/graph/onnx_protobuf.h"
#include "core/session/inference_session.h"
@ -15,24 +14,25 @@
#include "core/framework/execution_provider.h"
#include "core/framework/op_kernel.h"
#include "core/framework/session_state.h"
#include "core/framework/tensorprotoutils.h"
#include "core/graph/graph_viewer.h"
#include "core/graph/model.h"
#include "core/graph/op.h"
#include "core/providers/cuda/cuda_execution_provider.h"
#include "core/providers/cpu/math/element_wise_ops.h"
#include "core/framework/tensorprotoutils.h"
#include "test/capturing_sink.h"
#include "test/test_environment.h"
#include "test/framework/test_utils.h"
#include "gtest/gtest.h"
#include "core/util/protobuf_parsing_utils.h"
#include "test/providers/provider_test_utils.h"
#include "default_providers.h"
#include "asserts.h"
using namespace std;
using namespace ONNX_NAMESPACE;
using namespace onnxruntime::logging;
namespace onnxruntime {
namespace test {
typedef std::vector<onnxruntime::NodeArg*> ArgMap;
@ -121,8 +121,7 @@ TEST(CUDAFenceTests, DISABLED_PartOnCPU) {
SessionOptions so;
FenceCudaTestInferenceSession session(so, GetEnvironment());
LoadInferenceSessionFromModel(session, *model);
CUDAExecutionProviderInfo xp_info;
ASSERT_STATUS_OK(session.RegisterExecutionProvider(std::make_unique<CUDAExecutionProvider>(xp_info)));
ASSERT_STATUS_OK(session.RegisterExecutionProvider(DefaultCudaExecutionProvider()));
ASSERT_TRUE(session.Initialize().IsOK());
ASSERT_TRUE(1 == CountCopyNodes(graph));
@ -176,8 +175,7 @@ TEST(CUDAFenceTests, TileWithInitializer) {
SessionOptions so;
FenceCudaTestInferenceSession session(so, GetEnvironment());
LoadInferenceSessionFromModel(session, *model);
CUDAExecutionProviderInfo xp_info;
ASSERT_STATUS_OK(session.RegisterExecutionProvider(std::make_unique<CUDAExecutionProvider>(xp_info)));
ASSERT_STATUS_OK(session.RegisterExecutionProvider(DefaultCudaExecutionProvider()));
ASSERT_STATUS_OK(session.Initialize());
vector<OrtValue> outputs;
@ -242,8 +240,7 @@ TEST(CUDAFenceTests, TileWithComputedInput) {
SessionOptions so;
FenceCudaTestInferenceSession session(so, GetEnvironment());
LoadInferenceSessionFromModel(session, *model);
CUDAExecutionProviderInfo xp_info;
ASSERT_STATUS_OK(session.RegisterExecutionProvider(std::make_unique<CUDAExecutionProvider>(xp_info)));
ASSERT_STATUS_OK(session.RegisterExecutionProvider(DefaultCudaExecutionProvider()));
ASSERT_TRUE(session.Initialize().IsOK());
vector<OrtValue> outputs;
@ -263,4 +260,3 @@ TEST(CUDAFenceTests, TileWithComputedInput) {
} // namespace test
} // namespace onnxruntime
#endif

View file

@ -1,6 +1,5 @@
// Copyright (c) Microsoft Corporation. All rights reserved.
// Licensed under the MIT License.
#undef USE_CUDA // TODO: Cuda is a shared library, so can't call any Cuda provider methods directly from here
#include "core/graph/onnx_protobuf.h"
#include "core/session/inference_session.h"
@ -32,6 +31,7 @@
#include "core/platform/env.h"
#include "core/providers/cpu/cpu_execution_provider.h"
#include "core/providers/cpu/math/element_wise_ops.h"
#include "core/providers/cuda/cuda_provider_factory.h"
#ifdef USE_CUDA
#include "core/providers/cuda/gpu_data_transfer.h"
#elif USE_ROCM
@ -66,6 +66,11 @@ struct KernelRegistryAndStatus {
};
} // namespace
namespace onnxruntime {
#ifdef USE_CUDA
ProviderInfo_CUDA* GetProviderInfo_CUDA();
#endif
class FuseAdd : public OpKernel {
public:
explicit FuseAdd(const OpKernelInfo& info) : OpKernel(info) {
@ -260,6 +265,7 @@ void RunModelWithBindingMatMul(InferenceSession& session_object,
ProviderType bind_provider_type,
bool is_preallocate_output_vec,
ProviderType allocation_provider,
IExecutionProvider *gpu_provider,
OrtDevice* output_device) {
unique_ptr<IOBinding> io_binding;
Status st = session_object.NewIOBinding(&io_binding);
@ -307,16 +313,8 @@ void RunModelWithBindingMatMul(InferenceSession& session_object,
if (allocation_provider == kCpuExecutionProvider) {
AllocateMLValue<float>(TestCPUExecutionProvider()->GetAllocator(0, OrtMemTypeDefault), expected_output_dims,
&output_ml_value);
} else if (allocation_provider == kCudaExecutionProvider) {
#ifdef USE_CUDA
AllocateMLValue<float>(TestCudaExecutionProvider()->GetAllocator(0, OrtMemTypeDefault), expected_output_dims,
&output_ml_value);
#endif
} else if (allocation_provider == kRocmExecutionProvider) {
#ifdef USE_ROCM
AllocateMLValue<float>(TestRocmExecutionProvider()->GetAllocator(0, OrtMemTypeDefault), expected_output_dims,
&output_ml_value);
#endif
} else if (allocation_provider == kCudaExecutionProvider || allocation_provider == kRocmExecutionProvider) {
AllocateMLValue<float>(gpu_provider->GetAllocator(0, OrtMemTypeDefault), expected_output_dims, &output_ml_value);
} else {
ORT_THROW("Unsupported provider");
}
@ -354,11 +352,12 @@ void RunModelWithBindingMatMul(InferenceSession& session_object,
shape,
cpu_allocator);
#ifdef USE_CUDA
cudaStream_t stream = static_cast<cudaStream_t>(static_cast<const onnxruntime::CUDAExecutionProvider*>(TestCudaExecutionProvider())->GetComputeStream());
cudaStream_t stream = static_cast<cudaStream_t>(gpu_provider->GetComputeStream());
st = GetProviderInfo_CUDA()->CreateGPUDataTransfer(stream)->CopyTensor(rtensor, *cpu_tensor.get(), 0);
#elif USE_ROCM
hipStream_t stream = static_cast<hipStream_t>(static_cast<const onnxruntime::ROCMExecutionProvider*>(TestRocmExecutionProvider())->GetComputeStream());
#endif
hipStream_t stream = static_cast<hipStream_t>(gpu_provider->GetComputeStream());
st = GPUDataTransfer(stream).CopyTensor(rtensor, *cpu_tensor.get(), 0);
#endif
ASSERT_TRUE(st.IsOK());
OrtValue ml_value;
ml_value.Init(cpu_tensor.release(),
@ -367,14 +366,8 @@ void RunModelWithBindingMatMul(InferenceSession& session_object,
VerifyOutputs({ml_value}, expected_output_dims, expected_values_mul_y);
#endif
} else {
if (allocation_provider == kCudaExecutionProvider) {
#ifdef USE_CUDA
TestCudaExecutionProvider()->Sync();
#endif
} else if (allocation_provider == kRocmExecutionProvider) {
#ifdef USE_ROCM
TestRocmExecutionProvider()->Sync();
#endif
if (allocation_provider == kCudaExecutionProvider || allocation_provider == kRocmExecutionProvider) {
gpu_provider->Sync();
}
VerifyOutputs(io_binding->GetOutputs(), expected_output_dims, expected_values_mul_y);
}
@ -622,9 +615,7 @@ TEST(InferenceSessionTests, CheckRunProfilerWithSessionOptions) {
InferenceSession session_object(so, GetEnvironment());
#ifdef USE_CUDA
CUDAExecutionProviderInfo epi;
epi.device_id = 0;
EXPECT_TRUE(session_object.RegisterExecutionProvider(std::make_unique<CUDAExecutionProvider>(epi)).IsOK());
ASSERT_STATUS_OK(session_object.RegisterExecutionProvider(DefaultCudaExecutionProvider()));
#endif
ASSERT_STATUS_OK(session_object.Load(MODEL_URI));
ASSERT_STATUS_OK(session_object.Initialize());
@ -858,16 +849,21 @@ static void TestBindHelper(const std::string& log_str,
so.session_log_verbosity_level = 1; // change to 1 for detailed logging
InferenceSession session_object{so, GetEnvironment()};
IExecutionProvider *gpu_provider{};
if (bind_provider_type == kCudaExecutionProvider || bind_provider_type == kRocmExecutionProvider) {
#ifdef USE_CUDA
CUDAExecutionProviderInfo epi;
epi.device_id = 0;
EXPECT_TRUE(session_object.RegisterExecutionProvider(std::make_unique<CUDAExecutionProvider>(epi)).IsOK());
auto provider = DefaultCudaExecutionProvider();
gpu_provider = provider.get();
ASSERT_STATUS_OK(session_object.RegisterExecutionProvider(std::move(provider)));
#elif USE_ROCM
ROCMExecutionProviderInfo epi;
epi.device_id = 0;
EXPECT_TRUE(session_object.RegisterExecutionProvider(std::make_unique<ROCMExecutionProvider>(epi)).IsOK());
auto provider = std::make_unique<ROCMExecutionProvider>(epi);
gpu_provider = provider.get();
ASSERT_STATUS_OK(session_object.RegisterExecutionProvider(std::move(provider)));
#endif
}
@ -889,6 +885,7 @@ static void TestBindHelper(const std::string& log_str,
bind_provider_type,
preallocate_output,
allocation_provider,
gpu_provider,
output_device);
}
@ -1481,13 +1478,11 @@ TEST(InferenceSessionTests, Test3LayerNestedSubgraph) {
InferenceSession session_object{so, GetEnvironment()};
#ifdef USE_CUDA
CUDAExecutionProviderInfo epi;
epi.device_id = 0;
EXPECT_TRUE(session_object.RegisterExecutionProvider(std::make_unique<CUDAExecutionProvider>(epi)).IsOK());
ASSERT_STATUS_OK(session_object.RegisterExecutionProvider(DefaultCudaExecutionProvider()));
#elif USE_ROCM
ROCMExecutionProviderInfo epi;
epi.device_id = 0;
EXPECT_TRUE(session_object.RegisterExecutionProvider(std::make_unique<ROCMExecutionProvider>(epi)).IsOK());
ASSERT_STATUS_OK(session_object.RegisterExecutionProvider(std::make_unique<ROCMExecutionProvider>(epi)));
#endif
status = session_object.Load(model_file_name);
@ -1621,13 +1616,11 @@ TEST(InferenceSessionTests, Test2LayerNestedSubgraph) {
InferenceSession session_object{so, GetEnvironment()};
#ifdef USE_CUDA
CUDAExecutionProviderInfo epi;
epi.device_id = 0;
EXPECT_TRUE(session_object.RegisterExecutionProvider(std::make_unique<CUDAExecutionProvider>(epi)).IsOK());
ASSERT_STATUS_OK(session_object.RegisterExecutionProvider(DefaultCudaExecutionProvider()));
#elif USE_ROCM
ROCMExecutionProviderInfo epi;
epi.device_id = 0;
EXPECT_TRUE(session_object.RegisterExecutionProvider(std::make_unique<ROCMExecutionProvider>(epi)).IsOK());
ASSERT_STATUS_OK(session_object.RegisterExecutionProvider(std::make_unique<ROCMExecutionProvider>(epi)));
#endif
status = session_object.Load(model_file_name);
@ -1989,9 +1982,7 @@ TEST(InferenceSessionTests, TestParallelExecutionWithCudaProvider) {
so.session_logid = "InferenceSessionTests.TestParallelExecutionWithCudaProvider";
InferenceSession session_object{so, GetEnvironment()};
CUDAExecutionProviderInfo epi;
epi.device_id = 0;
EXPECT_TRUE(session_object.RegisterExecutionProvider(std::make_unique<CUDAExecutionProvider>(epi)).IsOK());
ASSERT_STATUS_OK(session_object.RegisterExecutionProvider(DefaultCudaExecutionProvider()));
ASSERT_STATUS_OK(session_object.Load(model_uri));
@ -2012,12 +2003,13 @@ TEST(InferenceSessionTests, TestArenaShrinkageAfterRun) {
SessionOptions so;
InferenceSession session_object{so, GetEnvironment()};
CUDAExecutionProviderInfo epi;
epi.default_memory_arena_cfg = &arena_cfg;
OrtCUDAProviderOptions provider_options{};
provider_options.default_memory_arena_cfg = &arena_cfg;
provider_options.device_id = 0;
auto factory = CreateExecutionProviderFactory_Cuda(&provider_options);
epi.device_id = 0;
ASSERT_STATUS_OK(session_object.Load(MODEL_URI));
EXPECT_TRUE(session_object.RegisterExecutionProvider(std::make_unique<CUDAExecutionProvider>(epi)).IsOK());
ASSERT_STATUS_OK(session_object.RegisterExecutionProvider(factory->CreateProvider()));
ASSERT_STATUS_OK(session_object.Initialize());
// Fetch the CUDA allocator to analyze its stats

View file

@ -1,12 +1,12 @@
// Copyright (c) Microsoft Corporation. All rights reserved.
// Licensed under the MIT License.
#undef USE_CUDA // TODO: Cuda is a shared library, so can't call any Cuda provider methods directly from here
#include <iterator>
#include "core/framework/execution_providers.h"
#include "core/optimizer/transformer_memcpy.h"
#include "core/graph/model.h"
#include "default_providers.h"
#include "gtest/gtest.h"
#include "test_utils.h"
#include "test/test_environment.h"
@ -106,8 +106,7 @@ TEST(TransformerTest, MemcpyTransformerTest) {
KernelRegistryManager kernel_registry_manager;
ExecutionProviders execution_providers;
execution_providers.Add(onnxruntime::kCudaExecutionProvider,
std::make_unique<CUDAExecutionProvider>(CUDAExecutionProviderInfo()));
execution_providers.Add(onnxruntime::kCudaExecutionProvider, DefaultCudaExecutionProvider());
execution_providers.Add(onnxruntime::kCpuExecutionProvider,
std::make_unique<CPUExecutionProvider>(CPUExecutionProviderInfo()));
KernelRegistryManager test_registry_manager;
@ -162,8 +161,7 @@ TEST(TransformerTest, MemcpyTransformerTestCudaFirst) {
KernelRegistryManager kernel_registry_manager;
ExecutionProviders execution_providers;
execution_providers.Add(onnxruntime::kCudaExecutionProvider,
std::make_unique<CUDAExecutionProvider>(CUDAExecutionProviderInfo()));
execution_providers.Add(onnxruntime::kCudaExecutionProvider, DefaultCudaExecutionProvider());
execution_providers.Add(onnxruntime::kCpuExecutionProvider,
std::make_unique<CPUExecutionProvider>(CPUExecutionProviderInfo()));
KernelRegistryManager test_registry_manager;
@ -277,8 +275,7 @@ TEST(TransformerTest, TestCopyNodeInsertionInitializerInSubgraph) {
KernelRegistryManager kernel_registry_manager;
ExecutionProviders execution_providers;
execution_providers.Add(onnxruntime::kCudaExecutionProvider,
std::make_unique<CUDAExecutionProvider>(CUDAExecutionProviderInfo()));
execution_providers.Add(onnxruntime::kCudaExecutionProvider, DefaultCudaExecutionProvider());
execution_providers.Add(onnxruntime::kCpuExecutionProvider,
std::make_unique<CPUExecutionProvider>(CPUExecutionProviderInfo()));
KernelRegistryManager test_registry_manager;

View file

@ -1,18 +1,19 @@
# This pod spec template is used to generate podspec file for running ios_package_test project,
# this is not a podspec template used by onnxruntime-mobile official CocoaPods package
Pod::Spec.new do |spec|
spec.name = "onnxruntime-mobile"
spec.version = "${ORT_VERSION}"
spec.summary = "Onnx Runtime C/C++ Package"
spec.description = <<-DESC
Onnx Runtime C/C++ framework pod.
spec.name = "onnxruntime-mobile"
spec.version = "${ORT_VERSION}"
spec.summary = "ONNX Runtime C/C++ Package"
spec.description = <<-DESC
ONNX Runtime C/C++ framework pod.
DESC
spec.homepage = "https://github.com/microsoft/onnxruntime"
spec.license = { :type => 'MIT' }
spec.authors = { "ONNX Runtime" => "onnxruntime@microsoft.com" }
spec.platform = :ios, '13.0'
spec.homepage = "https://github.com/microsoft/onnxruntime"
spec.license = { :type => 'MIT' }
spec.authors = { "ONNX Runtime" => "onnxruntime@microsoft.com" }
spec.platform = :ios, '13.0'
# if you are going to use a file as the spec.source, add 'file:' before your file path
spec.source = { :http => '${ORT_BASE_FRAMEWORK_ARCHIVE}' }
spec.vendored_frameworks = 'onnxruntime.framework'
spec.source = { :http => '${ORT_BASE_FRAMEWORK_ARCHIVE}' }
spec.vendored_frameworks = 'onnxruntime.framework'
spec.source_files = 'onnxruntime.framework/Headers/*.h'
end

View file

@ -1,12 +1,10 @@
// Copyright (c) Microsoft Corporation. All rights reserved.
// Licensed under the MIT License.
#include <memory>
#include "default_providers.h"
#include "providers.h"
#include "core/providers/cpu/cpu_provider_factory_creator.h"
#ifdef USE_CUDA
#include "core/providers/cuda/cuda_provider_factory_creator.h"
#endif
#ifdef USE_ROCM
#include "core/providers/rocm/rocm_provider_factory_creator.h"
#endif
@ -16,26 +14,6 @@
#include "core/session/onnxruntime_cxx_api.h"
namespace onnxruntime {
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_OpenVINO(
const char* device_type, bool enable_vpu_fast_compile, const char* device_id, size_t num_of_threads, bool use_compiled_network, const char* blob_dump_path);
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_Cuda(const OrtCUDAProviderOptions* provider_options);
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_Dnnl(int use_arena);
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_OpenVINO(const OrtOpenVINOProviderOptions* params);
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_Nuphar(bool, const char*);
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_Nnapi(uint32_t);
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_Rknpu();
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_Tensorrt(const OrtTensorRTProviderOptions* params);
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_MIGraphX(int device_id);
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_ACL(int use_arena);
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_ArmNN(int use_arena);
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_CoreML(uint32_t);
// EP for internal testing
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_InternalTesting(
const std::unordered_set<std::string>& supported_ops);
namespace test {
std::unique_ptr<IExecutionProvider> DefaultCpuExecutionProvider(bool enable_arena) {

View file

@ -1,9 +1,28 @@
// Copyright (c) Microsoft Corporation. All rights reserved.
// Licensed under the MIT License.
#pragma once
#include "core/providers/providers.h"
#include "core/framework/execution_provider.h"
namespace onnxruntime {
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_ACL(int use_arena);
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_ArmNN(int use_arena);
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_CoreML(uint32_t);
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_Cuda(const OrtCUDAProviderOptions* provider_options);
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_Dnnl(int use_arena);
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_MIGraphX(int device_id);
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_Nnapi(uint32_t);
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_Nuphar(bool, const char*);
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_OpenVINO(
const char* device_type, bool enable_vpu_fast_compile, const char* device_id, size_t num_of_threads, bool use_compiled_network, const char* blob_dump_path);
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_OpenVINO(const OrtOpenVINOProviderOptions* params);
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_Rknpu();
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_Tensorrt(const OrtTensorRTProviderOptions* params);
// EP for internal testing
std::shared_ptr<IExecutionProviderFactory> CreateExecutionProviderFactory_InternalTesting(const std::unordered_set<std::string>& supported_ops);
namespace test {
// unique_ptr providers with default values for session registration

View file

@ -26,20 +26,20 @@ OrtErrorCode CheckStatus(OrtStatusPtr status) {
#define CHECK_STATUS(ORT_API_NAME, ...) \
CheckStatus(Ort::GetApi().ORT_API_NAME(__VA_ARGS__))
#define RETURN_ERROR_CODE_IF_ERROR(ORT_API_NAME, ...) \
do { \
int error_code = CHECK_STATUS(ORT_API_NAME, __VA_ARGS__); \
if (error_code != ORT_OK) { \
return error_code; \
} \
#define RETURN_ERROR_CODE_IF_ERROR(ORT_API_NAME, ...) \
do { \
int error_code = CHECK_STATUS(ORT_API_NAME, __VA_ARGS__); \
if (error_code != ORT_OK) { \
return error_code; \
} \
} while (false)
// TODO: This macro can be removed when we changed all APIs to return a status code.
#define RETURN_NULLPTR_IF_ERROR(ORT_API_NAME, ...) \
do { \
if (CHECK_STATUS(ORT_API_NAME, __VA_ARGS__) != ORT_OK) { \
return nullptr; \
} \
#define RETURN_NULLPTR_IF_ERROR(ORT_API_NAME, ...) \
do { \
if (CHECK_STATUS(ORT_API_NAME, __VA_ARGS__) != ORT_OK) { \
return nullptr; \
} \
} while (false)
int OrtInit(int num_threads, int logging_level) {
@ -107,8 +107,8 @@ OrtSessionOptions* OrtCreateSessionOptions(size_t graph_optimization_level,
}
int OrtAddSessionConfigEntry(OrtSessionOptions* session_options,
const char* config_key,
const char* config_value) {
const char* config_key,
const char* config_value) {
return CHECK_STATUS(AddSessionConfigEntry, session_options, config_key, config_value);
}
@ -132,7 +132,8 @@ OrtSession* OrtCreateSession(void* data, size_t data_length, OrtSessionOptions*
OrtSession* session = nullptr;
return (CHECK_STATUS(CreateSessionFromArray, g_env, data, data_length, session_options, &session) == ORT_OK)
? session : nullptr;
? session
: nullptr;
}
void OrtReleaseSession(OrtSession* session) {
@ -155,7 +156,8 @@ char* OrtGetInputName(OrtSession* session, size_t index) {
char* input_name = nullptr;
return (CHECK_STATUS(SessionGetInputName, session, index, allocator, &input_name) == ORT_OK)
? input_name : nullptr;
? input_name
: nullptr;
}
char* OrtGetOutputName(OrtSession* session, size_t index) {
@ -164,7 +166,8 @@ char* OrtGetOutputName(OrtSession* session, size_t index) {
char* output_name = nullptr;
return (CHECK_STATUS(SessionGetOutputName, session, index, allocator, &output_name) == ORT_OK)
? output_name : nullptr;
? output_name
: nullptr;
}
void OrtFree(void* ptr) {
@ -180,36 +183,55 @@ OrtValue* OrtCreateTensor(int data_type, void* data, size_t data_length, size_t*
shapes[i] = dims[i];
}
OrtMemoryInfo* memoryInfo = nullptr;
RETURN_NULLPTR_IF_ERROR(CreateCpuMemoryInfo, OrtDeviceAllocator, OrtMemTypeDefault, &memoryInfo);
if (data_type == ONNX_TENSOR_ELEMENT_DATA_TYPE_STRING) {
OrtAllocator* allocator = nullptr;
RETURN_NULLPTR_IF_ERROR(GetAllocatorWithDefaultOptions, &allocator);
OrtValue* value = nullptr;
int error_code = CHECK_STATUS(CreateTensorWithDataAsOrtValue, memoryInfo, data, data_length,
dims_length > 0 ? shapes.data() : nullptr, dims_length,
static_cast<ONNXTensorElementDataType>(data_type), &value);
OrtValue* value = nullptr;
RETURN_NULLPTR_IF_ERROR(CreateTensorAsOrtValue, allocator,
dims_length > 0 ? shapes.data() : nullptr, dims_length,
ONNX_TENSOR_ELEMENT_DATA_TYPE_STRING, &value);
Ort::GetApi().ReleaseMemoryInfo(memoryInfo);
return (error_code == ORT_OK) ? value : nullptr;
const char* const* strings = reinterpret_cast<const char* const*>(data);
RETURN_NULLPTR_IF_ERROR(FillStringTensor, value, strings, data_length / sizeof(const char*));
return value;
} else {
OrtMemoryInfo* memoryInfo = nullptr;
RETURN_NULLPTR_IF_ERROR(CreateCpuMemoryInfo, OrtDeviceAllocator, OrtMemTypeDefault, &memoryInfo);
OrtValue* value = nullptr;
int error_code = CHECK_STATUS(CreateTensorWithDataAsOrtValue, memoryInfo, data, data_length,
dims_length > 0 ? shapes.data() : nullptr, dims_length,
static_cast<ONNXTensorElementDataType>(data_type), &value);
Ort::GetApi().ReleaseMemoryInfo(memoryInfo);
return (error_code == ORT_OK) ? value : nullptr;
}
}
int OrtGetTensorData(OrtValue* tensor, int* data_type, void** data, size_t** dims, size_t* dims_length) {
#define RELEASE_AND_RETURN_ERROR_CODE_IF_ERROR(ORT_API_NAME, ...) \
do { \
int error_code = CHECK_STATUS(ORT_API_NAME, __VA_ARGS__); \
if (error_code != ORT_OK) { \
if (info != nullptr) { \
Ort::GetApi().ReleaseTensorTypeAndShapeInfo(info); \
} \
if (allocator != nullptr && p_dims != nullptr) { \
allocator->Free(allocator, p_dims); \
} \
return error_code; \
} \
#define RELEASE_AND_RETURN_ERROR_CODE_IF_ERROR(ORT_API_NAME, ...) \
do { \
int error_code = CHECK_STATUS(ORT_API_NAME, __VA_ARGS__); \
if (error_code != ORT_OK) { \
if (info != nullptr) { \
Ort::GetApi().ReleaseTensorTypeAndShapeInfo(info); \
} \
if (allocator != nullptr && p_dims != nullptr) { \
allocator->Free(allocator, p_dims); \
} \
if (allocator != nullptr && p_string_data != nullptr) { \
allocator->Free(allocator, p_string_data); \
} \
return error_code; \
} \
} while (false)
OrtTensorTypeAndShapeInfo* info = nullptr;
OrtAllocator* allocator = nullptr;
size_t* p_dims = nullptr;
void* p_string_data = nullptr;
RETURN_ERROR_CODE_IF_ERROR(GetTensorTypeAndShape, tensor, &info);
@ -233,6 +255,42 @@ int OrtGetTensorData(OrtValue* tensor, int* data_type, void** data, size_t** dim
}
*dims = p_dims;
if (type == ONNX_TENSOR_ELEMENT_DATA_TYPE_STRING) {
size_t num_elements;
RELEASE_AND_RETURN_ERROR_CODE_IF_ERROR(GetTensorShapeElementCount, info, &num_elements);
// NOTE: ORT C-API does not expose an interface for users to get string raw data directly. There is always a copy.
// we can use the tensor raw data because it is type of "std::string *", which is very starightforward to
// implement and can also save memory usage. However, this approach depends on the Tensor's implementation
// details. So we have to copy the string content here.
size_t string_data_length;
RELEASE_AND_RETURN_ERROR_CODE_IF_ERROR(GetStringTensorDataLength, tensor, &string_data_length);
// The buffer contains following data:
// - a sequence of pointers to (const char*), size = num_elements * sizeof(const char*).
// - followed by a raw buffer to store string content, size = string_data_length + 1.
static_assert(sizeof(const char*) == sizeof(size_t), "size of a pointer and a size_t value should be the same.");
size_t string_data_offset = num_elements * sizeof(const char*);
size_t buf_size = string_data_offset + string_data_length;
p_string_data = allocator->Alloc(allocator, buf_size + 1);
void* p_string_content = reinterpret_cast<char*>(p_string_data) + string_data_offset;
size_t* p_offsets = reinterpret_cast<size_t*>(p_string_data);
RELEASE_AND_RETURN_ERROR_CODE_IF_ERROR(GetStringTensorContent, tensor, p_string_content, string_data_length, p_offsets, num_elements);
// replace offsets by pointers
const char** p_c_strs = reinterpret_cast<const char**>(p_offsets);
for (size_t i = 0; i < num_elements; i++) {
p_c_strs[i] = reinterpret_cast<const char*>(p_string_content) + p_offsets[i];
}
// put null at the last char
reinterpret_cast<char*>(p_string_data)[buf_size] = '\0';
*data = p_string_data;
}
Ort::GetApi().ReleaseTensorTypeAndShapeInfo(info);
return ORT_OK;
}
@ -267,8 +325,8 @@ OrtRunOptions* OrtCreateRunOptions(size_t log_severity_level,
}
int OrtAddRunConfigEntry(OrtRunOptions* run_options,
const char* config_key,
const char* config_value) {
const char* config_key,
const char* config_value) {
return CHECK_STATUS(AddRunConfigEntry, run_options, config_key, config_value);
}

View file

@ -118,8 +118,8 @@ void EMSCRIPTEN_KEEPALIVE OrtFree(void* ptr);
/**
* create an instance of ORT tensor.
* @param data_type data type defined in enum ONNXTensorElementDataType.
* @param data a pointer to the tensor data.
* @param data_length size of the tensor data in bytes.
* @param data for numeric tensor: a pointer to the tensor data buffer. for string tensor: a pointer to a C-Style null terminated string array.
* @param data_length size of the buffer 'data' in bytes.
* @param dims a pointer to an array of dims. the array should contain (dims_length) element(s).
* @param dims_length the length of the tensor's dimension
* @returns a handle of the tensor.
@ -130,10 +130,11 @@ ort_tensor_handle_t EMSCRIPTEN_KEEPALIVE OrtCreateTensor(int data_type, void* da
* get type, shape info and data of the specified tensor.
* @param tensor handle of the tensor.
* @param data_type [out] specify the memory to write data type
* @param data [out] specify the memory to write the tensor data
* @param data [out] specify the memory to write the tensor data. for string tensor: an array of C-Style null terminated string.
* @param dims [out] specify the memory to write address of the buffer containing value of each dimension.
* @param dims_length [out] specify the memory to write dims length
* @remarks a temporary buffer 'dims' is allocated during the call. Caller must release the buffer after use by calling OrtFree().
* @remarks following temporary buffers are allocated during the call. Caller must release the buffers after use by calling OrtFree():
* 'dims' (for all types of tensor), 'data' (only for string tensor)
*/
int EMSCRIPTEN_KEEPALIVE OrtGetTensorData(ort_tensor_handle_t tensor, int* data_type, void** data, size_t** dims, size_t* dims_length);

View file

@ -67,7 +67,8 @@ static std::unordered_map<std::string, std::unordered_set<size_t>>
{"Unsqueeze", {1}},
{"ReduceSum", {1}},
{"Split", {1}},
{"Clip", {1, 2}}};
{"Clip", {1, 2}},
{"Pad", {1, 2}}};
class GradientGraphBuilder {
public:

View file

@ -1666,5 +1666,20 @@ IMPLEMENT_GRADIENT_BUILDER(GetATenOpGradient) {
return std::vector<NodeDef>{NodeDef(OpDef{"ATenOpGrad", kMSDomain, 1}, input_args, output_args, attrs)};
}
IMPLEMENT_GRADIENT_BUILDER(GetPadGradient) {
const auto& attributes = SrcNodeAttributes();
std::string mode = "constant";
if (attributes.find("mode") != attributes.end() && utils::HasString(attributes.at("mode"))) {
mode = attributes.at("mode").s();
}
if (mode != "constant") {
ORT_THROW("Pad gradient currently supports constant mode only.");
}
return std::vector<NodeDef>{NodeDef("Neg", {I(1)}, {IA("Neg_pads")}),
NodeDef("Pad", {GO(0), IA("Neg_pads")}, {GI(0)})};
}
} // namespace training
} // namespace onnxruntime

View file

@ -73,6 +73,7 @@ DECLARE_GRADIENT_BUILDER(GetAbsGradient)
DECLARE_GRADIENT_BUILDER(GetMinMaxGradient)
DECLARE_GRADIENT_BUILDER(GetTileGradient)
DECLARE_GRADIENT_BUILDER(GetATenOpGradient)
DECLARE_GRADIENT_BUILDER(GetPadGradient)
DECLARE_GRADIENT_BUILDER(GetIdentityGradient)
} // namespace training

View file

@ -105,6 +105,7 @@ void GradientBuilderRegistry::RegisterGradientBuilders() {
REGISTER_GRADIENT_BUILDER("Max", GetMinMaxGradient);
REGISTER_GRADIENT_BUILDER("Tile", GetTileGradient);
REGISTER_GRADIENT_BUILDER("ATenOp", GetATenOpGradient);
REGISTER_GRADIENT_BUILDER("Pad", GetPadGradient);
REGISTER_GRADIENT_BUILDER("Identity", GetIdentityGradient);
};

View file

@ -39,8 +39,8 @@ elif not os.access(python_package_dir, os.X_OK | os.W_OK):
if not os.path.exists(TORCH_CPP_BUILD_DIR):
os.makedirs(TORCH_CPP_BUILD_DIR, exist_ok = True)
elif os.path.exists(os.path.join(TORCH_CPP_BUILD_DIR,'lock')):
print("WARNING: ORTModule detected PyTorch CPP extension's lock file during initialization, "
"which can cause unexpected hangs. "
print("WARNING: ORTModule detected PyTorch's CPP extension lock file during initialization, "
"which can cause the script to stop responding. "
f"Delete {os.path.join(TORCH_CPP_BUILD_DIR,'lock')} if a hang occurs.")
# Verify proper PyTorch is installed before proceding to ONNX Runtime initialization

View file

@ -54,6 +54,7 @@ class GraphExecutionManager(ABC):
self._graph_info = None
self._graph_initializer_names = None
self._graph_initializer_names_to_train = None
self._graph_initializers = None
# TrainingAgent or InferenceAgent
self._execution_agent = None
@ -320,3 +321,8 @@ class GraphExecutionManager(ABC):
# a set (unordered_set in the backend) that does not require a copy on each reference.
self._graph_initializer_names = set(initializer_names)
self._graph_initializer_names_to_train = set(initializer_names_to_train)
# Initializers can be cached and used since they are expected not to be re-instantiated
# between forward calls.
self._graph_initializers = [param for name, param in self._flattened_module.named_parameters()
if name in self._graph_initializer_names]

View file

@ -89,8 +89,7 @@ class InferenceManager(GraphExecutionManager):
self._optimized_onnx_model,
self._device,
*_io._combine_input_buffers_initializers(
[param for name, param in self._flattened_module.named_parameters()
if name in self._graph_initializer_names],
self._graph_initializers,
self._graph_info.user_input_names,
self._input_info,
self._flattened_module.named_buffers(),

View file

@ -47,9 +47,6 @@ class TrainingManager(GraphExecutionManager):
execution_session.run_forward(forward_inputs, forward_outputs, state)
user_outputs = tuple(_utils._ortvalue_to_torch_tensor(forward_output) for forward_output in forward_outputs)
# Assert that the outputs and model device match
_utils._check_same_device(device, "Output argument from forward", *user_outputs)
output_info = [(output.shape, output.device, output.dtype) for output in user_outputs]
run_info = RunStateInfo(state, output_info)
# Return user outputs and forward run information
@ -192,8 +189,7 @@ class TrainingManager(GraphExecutionManager):
return _io.unflatten_user_output(self._module_output_schema,
_ORTModuleFunction.apply(
*_io._combine_input_buffers_initializers(
[param for name, param in self._flattened_module.named_parameters()
if name in self._graph_initializer_names],
self._graph_initializers,
self._graph_info.user_input_names,
self._input_info,
self._flattened_module.named_buffers(),

View file

@ -2580,6 +2580,77 @@ TEST(GradientCheckerTest, TileGrad) {
}
}
#ifdef USE_CUDA
TEST(GradientCheckerTest, PadGrad) {
float max_error;
GradientChecker<float, float, float> gradient_checker;
OpDef op_def{"Pad", kOnnxDomain, 11};
{
TensorInfo x_info({2, 4}, true);
TensorInfo pads_info({4}, false, nullptr, DataTypeImpl::GetTensorType<int64_t>());
std::vector<std::vector<float>> x_datas = {{1, 2, 3, 4, 5, 6, 7, 8}, {0, 2, 2, 0}};
TensorInfo y_info({4, 6}, true);
gradient_checker.ComputeGradientError(op_def, {x_info, pads_info}, {y_info}, &max_error, x_datas);
EXPECT_IS_TINY(max_error);
}
{
TensorInfo x_info({2, 4}, true);
TensorInfo pads_info({4}, false, nullptr, DataTypeImpl::GetTensorType<int64_t>());
std::vector<std::vector<float>> x_datas = {{1, 2, 3, 4, 5, 6, 7, 8}, {0, -2, 2, 0}};
TensorInfo y_info({4, 2}, true);
gradient_checker.ComputeGradientError(op_def, {x_info, pads_info}, {y_info}, &max_error, x_datas,
{MakeAttribute("mode", "constant")});
EXPECT_IS_TINY(max_error);
}
{
TensorInfo x_info({2, 4}, true);
TensorInfo pads_info({4}, false, nullptr, DataTypeImpl::GetTensorType<int64_t>());
std::vector<std::vector<float>> x_datas = {{1, 2, 3, 4, 5, 6, 7, 8}, {0, 2, 2, 0}};
TensorInfo y_info({4, 6}, true);
bool has_error = false;
try {
gradient_checker.ComputeGradientError(op_def, {x_info, pads_info}, {y_info}, &max_error, x_datas,
{MakeAttribute("mode", "reflect")});
} catch (const std::exception& ex) {
auto ret = std::string(ex.what()).find("Pad gradient currently supports constant mode only.");
ASSERT_TRUE(ret != std::string::npos);
has_error = true;
}
ASSERT_TRUE(has_error);
}
{
TensorInfo x_info({2, 4}, true);
TensorInfo pads_info({4}, false, nullptr, DataTypeImpl::GetTensorType<int64_t>());
std::vector<std::vector<float>> x_datas = {{1, 2, 3, 4, 5, 6, 7, 8}, {0, 2, 2, 0}};
TensorInfo y_info({4, 6}, true);
bool has_error = false;
try {
gradient_checker.ComputeGradientError(op_def, {x_info, pads_info}, {y_info}, &max_error, x_datas,
{MakeAttribute("mode", "edge")});
} catch (const std::exception& ex) {
auto ret = std::string(ex.what()).find("Pad gradient currently supports constant mode only.");
ASSERT_TRUE(ret != std::string::npos);
has_error = true;
}
ASSERT_TRUE(has_error);
}
}
#endif // USE_CUDA
} // namespace test
} // namespace onnxruntime

View file

@ -20,7 +20,7 @@ limitations under the License.
struct CachedInterpolation {
int64_t lower; // Lower source index used in the interpolation
int64_t upper; // Upper source index used in the interpolation
// 1-D linear iterpolation scale (see:
// 1-D linear interpolation scale (see:
// https://en.wikipedia.org/wiki/Bilinear_interpolation)
float lerp;
};

View file

@ -1,13 +1,13 @@
#-------------------------------------------------------------------------
# -------------------------------------------------------------------------
# Copyright (c) Microsoft Corporation. All rights reserved.
# Licensed under the MIT License.
#--------------------------------------------------------------------------
# --------------------------------------------------------------------------
from setuptools import setup, find_packages, Extension
from setuptools import setup, Extension
from distutils import log as logger
from distutils.command.build_ext import build_ext as _build_ext
from glob import glob
from os import path, getcwd, environ, remove, walk, makedirs, listdir
from os import path, getcwd, environ, remove, listdir
from shutil import copyfile, copytree, rmtree
import platform
import subprocess
@ -19,6 +19,7 @@ featurizers_build = False
package_name = 'onnxruntime'
wheel_name_suffix = None
def parse_arg_remove_boolean(argv, arg_name):
arg_value = False
if arg_name in sys.argv:
@ -27,6 +28,7 @@ def parse_arg_remove_boolean(argv, arg_name):
return arg_value
def parse_arg_remove_string(argv, arg_name_equal):
arg_value = None
for arg in sys.argv[1:]:
@ -37,6 +39,7 @@ def parse_arg_remove_string(argv, arg_name_equal):
return arg_value
# Any combination of the following arguments can be applied
featurizers_build = parse_arg_remove_boolean(sys.argv, '--use_featurizers')
@ -107,6 +110,7 @@ class build_ext(_build_ext):
try:
from wheel.bdist_wheel import bdist_wheel as _bdist_wheel
class bdist_wheel(_bdist_wheel):
def finalize_options(self):
_bdist_wheel.finalize_options(self)
@ -392,6 +396,15 @@ if not path.exists(requirements_path):
with open(requirements_path) as f:
install_requires = f.read().splitlines()
if is_manylinux:
AUDITWHEEL_PLAT = environ.get('AUDITWHEEL_PLAT', None)
if AUDITWHEEL_PLAT == 'manylinux2014_aarch64':
for i in range(len(install_requires)):
req = install_requires[i]
if req.startswith("numpy"):
install_requires[i] = "numpy >= 1.19.5"
if enable_training:
def save_build_and_package_info(package_name, version_number, cuda_version):

View file

@ -346,12 +346,15 @@ def parse_arguments():
parser.add_argument(
"--enable_wasm_debug_info", action='store_true',
help="Build WebAssembly with DWARF format debug info")
parser.add_argument(
"--wasm_malloc", default="dlmalloc", help="Specify memory allocator for WebAssembly")
# Arguments needed by CI
parser.add_argument(
"--cmake_path", default="cmake", help="Path to the CMake program.")
parser.add_argument(
"--ctest_path", default="ctest", help="Path to the CTest program.")
"--ctest_path", default="ctest", help="Path to the CTest program. It can be an empty string. If it is empty, "
"we will use this script driving the test programs directly.")
parser.add_argument(
"--skip_submodule_sync", action='store_true', help="Don't do a "
"'git submodule update'. Makes the Update phase faster.")
@ -530,11 +533,14 @@ def is_reduced_ops_build(args):
def resolve_executable_path(command_or_path):
"""Returns the absolute path of an executable."""
executable_path = shutil.which(command_or_path)
if executable_path is None:
raise BuildError("Failed to resolve executable path for "
"'{}'.".format(command_or_path))
return os.path.abspath(executable_path)
if command_or_path and command_or_path.strip():
executable_path = shutil.which(command_or_path)
if executable_path is None:
raise BuildError("Failed to resolve executable path for "
"'{}'.".format(command_or_path))
return os.path.abspath(executable_path)
else:
return None
def get_linux_distro():
@ -652,6 +658,11 @@ def generate_build_tree(cmake_path, source_dir, build_dir, cuda_home, cudnn_home
"-Donnxruntime_BUILD_WINML_TESTS=" + ("OFF" if args.skip_winml_tests else "ON"),
"-Donnxruntime_GENERATE_TEST_REPORTS=ON",
"-Donnxruntime_DEV_MODE=" + use_dev_mode(args),
# There are two ways of locating python C API header file. "find_package(PythonLibs 3.5 REQUIRED)"
# and "find_package(Python 3.5 COMPONENTS Development.Module)". The first one is deprecated and it
# depends on the "PYTHON_EXECUTABLE" variable. The second needs "Python_EXECUTABLE". Here we set both
# of them to get the best compatibility.
"-DPython_EXECUTABLE=" + sys.executable,
"-DPYTHON_EXECUTABLE=" + sys.executable,
"-Donnxruntime_USE_CUDA=" + ("ON" if args.use_cuda else "OFF"),
"-Donnxruntime_CUDA_VERSION=" + (args.cuda_version if args.use_cuda else ""),
@ -706,7 +717,6 @@ def generate_build_tree(cmake_path, source_dir, build_dir, cuda_home, cudnn_home
"-Donnxruntime_MINIMAL_BUILD_CUSTOM_OPS=" + ("ON" if args.minimal_build and 'custom_ops' in args.minimal_build
else "OFF"),
"-Donnxruntime_REDUCED_OPS_BUILD=" + ("ON" if is_reduced_ops_build(args) else "OFF"),
"-Donnxruntime_MSVC_STATIC_RUNTIME=" + ("ON" if args.enable_msvc_static_runtime else "OFF"),
# enable pyop if it is nightly build
"-Donnxruntime_ENABLE_LANGUAGE_INTEROP_OPS=" + ("ON" if args.enable_language_interop_ops else "OFF"),
"-Donnxruntime_USE_DML=" + ("ON" if args.use_dml else "OFF"),
@ -742,9 +752,21 @@ def generate_build_tree(cmake_path, source_dir, build_dir, cuda_home, cudnn_home
else "ON"),
"-Donnxruntime_ENABLE_WEBASSEMBLY_THREADS=" + ("ON" if args.enable_wasm_threads else "OFF"),
"-Donnxruntime_ENABLE_WEBASSEMBLY_DEBUG_INFO=" + ("ON" if args.enable_wasm_debug_info else "OFF"),
"-Donnxruntime_WEBASSEMBLY_MALLOC=" + args.wasm_malloc,
"-Donnxruntime_ENABLE_EAGER_MODE=" + ("ON" if args.build_eager_mode else "OFF"),
]
if args.enable_msvc_static_runtime:
cmake_args += ["-DCMAKE_MSVC_RUNTIME_LIBRARY=MultiThreaded$<$<CONFIG:Debug>:Debug>",
"-DONNX_USE_MSVC_STATIC_RUNTIME=ON",
"-Dprotobuf_MSVC_STATIC_RUNTIME=ON",
"-Dgtest_force_shared_crt=OFF"]
else:
cmake_args += ["-DCMAKE_MSVC_RUNTIME_LIBRARY=MultiThreaded$<$<CONFIG:Debug>:Debug>DLL",
"-DONNX_USE_MSVC_STATIC_RUNTIME=OFF",
"-Dprotobuf_MSVC_STATIC_RUNTIME=OFF",
"-Dgtest_force_shared_crt=ON"]
if acl_home and os.path.exists(acl_home):
cmake_args += ["-Donnxruntime_ACL_HOME=" + acl_home]
@ -1405,27 +1427,38 @@ def run_onnxruntime_tests(args, source_dir, ctest_path, build_dir, configs):
if len(dll_path_list) > 0:
dll_path = os.pathsep.join(dll_path_list)
if ctest_path is None:
# Get the "Google Test Adapter" for vstest.
if not os.path.exists(os.path.join(cwd,
'googletestadapter.0.17.1')):
if not ctest_path:
if is_windows():
# Get the "Google Test Adapter" for vstest.
if not os.path.exists(os.path.join(cwd,
'googletestadapter.0.17.1')):
run_subprocess(
['nuget.exe', 'restore',
os.path.join(source_dir, 'packages.config'),
'-ConfigFile', os.path.join(source_dir, 'NuGet.config'),
'-PackagesDirectory', cwd])
cwd2 = os.path.join(cwd, config)
executables = ['onnxruntime_test_all.exe']
if args.build_shared_lib:
executables.append('onnxruntime_shared_lib_test.exe')
executables.append('onnxruntime_global_thread_pools_test.exe')
executables.append('onnxruntime_api_tests_without_env.exe')
run_subprocess(
['nuget.exe', 'restore',
os.path.join(source_dir, 'packages.config'),
'-ConfigFile', os.path.join(source_dir, 'NuGet.config'),
'-PackagesDirectory', cwd])
cwd2 = os.path.join(cwd, config)
executables = ['onnxruntime_test_all.exe']
if args.build_shared_lib:
executables.append('onnxruntime_shared_lib_test.exe')
executables.append('onnxruntime_global_thread_pools_test.exe')
run_subprocess(
['vstest.console.exe', '--parallel',
'--TestAdapterPath:..\\googletestadapter.0.17.1\\build\\_common', # noqa
'/Logger:trx', '/Enablecodecoverage', '/Platform:x64',
"/Settings:%s" % os.path.join(
source_dir, 'cmake\\codeconv.runsettings')] + executables,
cwd=cwd2, dll_path=dll_path)
['vstest.console.exe', '--parallel',
'--TestAdapterPath:..\\googletestadapter.0.17.1\\build\\_common', # noqa
'/Logger:trx', '/Enablecodecoverage', '/Platform:x64',
"/Settings:%s" % os.path.join(
source_dir, 'cmake\\codeconv.runsettings')] + executables,
cwd=cwd2, dll_path=dll_path)
else:
executables = ['onnxruntime_test_all']
if args.build_shared_lib:
executables.append('onnxruntime_shared_lib_test')
executables.append('onnxruntime_global_thread_pools_test')
executables.append('onnxruntime_api_tests_without_env')
for exe in executables:
run_subprocess([os.path.join(cwd, exe)], cwd=cwd, dll_path=dll_path)
else:
ctest_cmd = [ctest_path, "--build-config", config, "--verbose", "--timeout", "7200"]
run_subprocess(ctest_cmd, cwd=cwd, dll_path=dll_path)
@ -1518,11 +1551,6 @@ def nuphar_run_python_tests(build_dir, configs):
if is_windows():
cwd = os.path.join(cwd, config)
dll_path = os.path.join(build_dir, config, "external", "tvm", config)
# install onnx for shape inference in testing Nuphar scripts
# this needs to happen after onnx_test_data preparation which
# uses onnx 1.3.0
run_subprocess(
[sys.executable, '-m', 'pip', 'install', '--user', 'onnx==1.5.0'])
run_subprocess(
[sys.executable, 'onnxruntime_test_python_nuphar.py'],
cwd=cwd, dll_path=dll_path)
@ -1850,6 +1878,9 @@ def main():
if args.build_nuget and cross_compiling:
raise BuildError('Currently nuget package creation is not supported while cross-compiling')
if args.enable_pybind and args.disable_rtti:
raise BuildError("Python bindings use typeid so you can't disable RTTI")
if args.enable_pybind and args.disable_exceptions:
raise BuildError('Python bindings require exceptions to be enabled.')
@ -1888,6 +1919,8 @@ def main():
configs = set(args.config)
# setup paths and directories
# cmake_path and ctest_path can be None. For example, if a person only wants to run the tests, he/she doesn't need
# to have cmake/ctest.
cmake_path = resolve_executable_path(args.cmake_path)
ctest_path = None if args.use_vstest else resolve_executable_path(
args.ctest_path)
@ -2003,7 +2036,7 @@ def main():
# since emscripten doesn't support file packaging required for unit tests,
# need to apply patch with the specific version of emscripten.
# once patch is committed to emsdk repository, this must be replaced with 'latest'.
emsdk_version = "2.0.13"
emsdk_version = "2.0.23"
emsdk_dir = os.path.join(source_dir, "cmake", "external", "emsdk")
emsdk_file = os.path.join(emsdk_dir, "emsdk.bat") if is_windows() else os.path.join(emsdk_dir, "emsdk")

Some files were not shown because too many files have changed in this diff Show more