-
Notifications
You must be signed in to change notification settings - Fork 704
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
onnxruntime的gpu怎么支持? #10
Comments
你需要额外编译GPU版本的onnxruntime的GPU版本的库哦,我这没专门测试,代码是不用改的,但链接的库需要改。
另外,有个小伙伴尝试了GPU下的测试 #9 ,应该是ok的 |
这个是1.8.1的库,我们的支持吗? |
我这默认的线程数是1,你可以尝试别的线程数。
1.8.1的库,我还没有测过高版本的库,一般情况下这些库都是向后兼容的。你可以直接替换1.8.1的库和头文件试一下。另外需要注意的是,可能你得看一下官方说明里边对于CUDA版本的要求。希望小伙伴能尝试成功啊~ |
嗯嗯。刚刚下载了1.8.1的gpu的库,然后重新编译试了试,结果没啥效果,更1.7.0 cpu版本一样,甚至还不如,一张图改成了8线程后,107ms。应该是要使用gpu,是需要一个设置和变量的。 |
可以尝试下设置CUDAProvider, 在ort_handler.cpp中修改session_options. // GPU compatiable. 尝试增加以下2句,emmm..... 我没有windows环境,其实没试过
OrtCUDAProviderOptions provider_options; // C接口
session_options.AppendExecutionProvider_CUDA(provider_options);
// 1. session
ort_session = new Ort::Session(ort_env, onnx_path, session_options); 以及可以参考下这个官方案例fns_candy_style_transfer.c 里面有不同Provider的设置方法。比如. #ifdef USE_CUDA
void enable_cuda(OrtSessionOptions* session_options) {
ORT_ABORT_ON_ERROR(OrtSessionOptionsAppendExecutionProvider_CUDA(session_options, 0));
}
#endif 使用了OrtSessionOptionsAppendExecutionProvider_CUDA,对应到c++的API, 在onnxruntime_cxx_inline.h中: // C++ API调用转接到C API
inline SessionOptions& SessionOptions::AppendExecutionProvider_CUDA(const OrtCUDAProviderOptions& provider_options) {
ThrowOnError(GetApi().SessionOptionsAppendExecutionProvider_CUDA(p_, &provider_options));
return *this;
}
// OrtCUDAProviderOptions是默认的设置
typedef struct OrtCUDAProviderOptions {
int device_id; // cuda device with id=0 as default device.
OrtCudnnConvAlgoSearch cudnn_conv_algo_search; // cudnn conv algo search option
size_t cuda_mem_limit; // default cuda memory limitation to maximum finite value of size_t.
int arena_extend_strategy; // default area extend strategy to KNextPowerOfTwo.
int do_copy_in_default_stream;
int has_user_compute_stream;
void* user_compute_stream;
} OrtCUDAProviderOptions;
// cuda_provider_factory.cc 中的内部实现 只有GPU版本会启用 CPU的则是直接返回ERROR
ORT_API_STATUS_IMPL(OrtApis::SessionOptionsAppendExecutionProvider_CUDA,
_In_ OrtSessionOptions* options, _In_ const OrtCUDAProviderOptions* cuda_options) {
CUDAExecutionProviderInfo info{};
info.device_id = gsl::narrow<OrtDevice::DeviceId>(cuda_options->device_id); // device_id默认是0
info.cuda_mem_limit = cuda_options->cuda_mem_limit;
info.arena_extend_strategy = static_cast<onnxruntime::ArenaExtendStrategy>(cuda_options->arena_extend_strategy);
info.cudnn_conv_algo_search = cuda_options->cudnn_conv_algo_search;
info.do_copy_in_default_stream = cuda_options->do_copy_in_default_stream;
info.has_user_compute_stream = cuda_options->has_user_compute_stream;
info.user_compute_stream = cuda_options->user_compute_stream;
options->provider_factories.push_back(onnxruntime::CreateExecutionProviderFactory_CUDA(info));
return nullptr;
} |
GPU推理需要在ort_handler的initialize_handler()里加上OrtSessionOptionsAppendExecutionProvider_CUDA(session_options, 0); |
gpu除了nuget安装外,不需要额外配置环境,因为cuda在安装时已经在电脑的环境变量中添加了路径 |
应该也不能完全说不对的,应该还是用法有些问题。我这版代码是暂时没有做GPU兼容的,应该有些地方需要你去修改。首先你需要确保你用的GPU版本的库以及对应CUDA版本是对的。 我们可以从源码来分析一下用法。在onnxruntime_c_api.cc中有一段: # include "core/session/onnxruntime_c_api.h"
// ...省略一部分头文件
#ifdef USE_CUDA
#include "core/providers/cuda/cuda_provider_factory.h"
#endif 可以看到 如果是GPU版本 定义了USE_CUDA 则会引入cuda_provider_factory.h. 这个头文件放的就是OrtSessionOptionsAppendExecutionProvider_CUDA的函数签名: /**
* \param device_id cuda device id, starts from zero.
*/
ORT_API_STATUS(OrtSessionOptionsAppendExecutionProvider_CUDA, _In_ OrtSessionOptions* options, int device_id); 我们看到这里需要输入的是一个OrtSessionOptions指针,而并非Ort::SessionOptions. 但事实上: struct SessionOptions : Base<OrtSessionOptions> {};
struct Base<const T> {
using contained_type = const T;
Base() = default;
Base(const T* p) : p_{p} {
if (!p)
ORT_CXX_API_THROW("Invalid instance ptr", ORT_INVALID_ARGUMENT);
}
~Base() = default;
operator const T*() const { return p_; } // 注意这里重载了T*()的类型转换函数。
// ...
} 由于Ort::SessionOptions重载了类型转换函数,所以可以直接使用OrtSessionOptionsAppendExecutionProvider_CUDA接口,在传参时会通过 (OrtSessionOptions*)session_options 对 session_options进行隐式转换。另一种方式就是使用C++封装了一层的接口。他们的本质上是一样的。 在onnxruntime_cxx_inline.h中: inline SessionOptions& SessionOptions::AppendExecutionProvider_CUDA(const OrtCUDAProviderOptions& provider_options) {
// 这个指针p_就是 OrtSessionOptions*, OrtCUDAProviderOptions在前面的分析已经讲过了,就不重复了
ThrowOnError(GetApi().SessionOptionsAppendExecutionProvider_CUDA(p_, &provider_options));
return *this;
} 关于Ort::Session、Ort::SessionOptions、Ort::Env的更多分析,你可以参考 #8 , 这位小伙伴贴出了一份 GPU版本的代码,你可以看下。 或者你可以把error具体的log发上来,这样我们能清楚具体发生了什么问题。至于一些环境问题,可能需要小伙伴你自己解决一下了~ good luck ~ 🙃🙃🙃 |
我想问一下,模型导出的时候,有没有cpu和gpu之分,导出的cpu模型,gpu不能加载? |
这个没有cpu和gpu区别的,都是可以用的。你现在用的是GPU版本的库和头文件吗?你直接导入这些头文件试试?onnxruntime_c_api.h已经是被包含在onnxruntime_cxx_api.h里面的, OrtSessionOptionsAppendExecutionProvider_CUDA这个C API应该能找到才对啊。你这有点奇怪 #include <onnxruntime/core/providers/cuda/cuda_provider_factory.h>
#include <onnxruntime/core/session/onnxruntime_cxx_api.h> |
https://github.com/microsoft/onnxruntime/releases 我是从这里下载的,这里下载的,貌似就没有cuda那个文件夹 |
你电脑确定是NVIDIA的显卡吗?只能是N卡哦 |
非常感谢,可以了。哎。 #include "onnxruntime_c_api.h" #ifdef USE_CUDA 然后: OrtSessionOptionsAppendExecutionProvider_CUDA(session_options, 0); |
我看到是有cuda_provider_factory.h的,应该是一样。官方包里面的头文件目录结构和自己编的是不一样的。官方包里面的include是这样的。 |
感谢。感谢。就是,其他两种方式不行,还必须就得OrtSessionOptionsAppendExecutionProvider_CUDA(session_options, 0); |
你太艰难了~ 哈哈 ~ |
没事,只要弄成了,再难都值得。哈哈。你可以把这一句加上了,兼容gpu。 |
get ~ |
只是,接下来,希望把yolor模型进行兼容吧 |
之后看时间允不允许,平时工作也比较忙。不过这个项目应该会长期维护~ |
嗯。加油。希望可以整个qq群吧,这样交流起来比较方便点。 |
精力有限,暂时没有这个计划哈哈~ |
另外,如果模型输入,不是640*640,怎么修改? |
|
你好,请问下如果用onnxruntime-gpu的话,链接库的代码在哪里修改 |
This issue is stale because it has been open for 30 days with no activity. |
This issue was closed because it has been inactive for 7 days since being marked as stale. |
No description provided.
The text was updated successfully, but these errors were encountered: