onnx转TensorRT推理自定义插件(op)的方式,Python&C++

4 篇文章 0 订阅
4 篇文章 0 订阅

首先,无论是python还是C++,我们都要写一个自己的plugin,一般的不支持op网上都有参考的版本,写plugin的参考教程:如何写好一个op
C++实现和使用过程:

  1. 下载TensorRT官网源码, 进入plugin可以看到许多已经定义好的插件可以参考,照着写就行,以ScatterND为例。
  2. 先写好自己的plugin,如名为:myplugin
    注意:此处plugin代码里面不能包含REGISTER_TENSORRT_PLUGIN(MyPluginCreator)代码,不然会导致重复注册的问题。
  3. 在plugin/CMakeLists.txt添加自己大的plugin名称:在这里插入图片描述
  4. 在plugin/InferPlugin.cpp添加注册信息
    在这里插入图片描述
    在这里插入图片描述
  5. 在路径下重新编译源代码
cd TensorRT
mkdir build
cd build
cmake  ..   -DTRT_LIB_DIR=$TRT_RELEASE/lib -DTRT_OUT_DIR=`pwd`/out
make -j${nproc}
  1. 可以看到build路径下有个out文件夹,里面包括libnvinfer_plugin.so的三个文件。将这三个文件复制到自己的目录下,并删掉原来libnvinfer_plugin.so三个文件。
  2. 在自己的TensorRT推理代码的build model之前进行插件注册,这样就可以使用自定义插件了。
#include "NvInferPlugin.h"
bool build() {	
    initLibNvInferPlugins(&gLogger, "");
    ...
}

Python中使用自定义插件(可以不下载源码):

  1. 还是刚刚的myplugin
  2. 在代码中添加REGISTER_TENSORRT_PLUGIN(MyPluginCreator)
  3. 自己写一个CMakeLists.txt,包括所有需要的文件和库,参考如下:
cmake_minimum_required(VERSION 3.8 FATAL_ERROR)
project(TensorRTPlugin LANGUAGES CXX CUDA)
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -Wno-long-long -pedantic -Wno-deprecated-declarations")

set(PLUGIN_SOURCES)
set(PLUGIN_CU_SOURCES)

macro(set_ifndef var val)
    if (NOT ${var})
        set(${var} ${val})
    endif()
    message(STATUS "Configurable variable ${var} set to ${${var}}")
endmacro()

set(PLUGINS_LIST 
    MyPlugin
    )

foreach(PLUGIN_ITER ${PLUGINS_LIST})
    include_directories(${PLUGIN_ITER})
    add_subdirectory(${PLUGIN_ITER})
endforeach(PLUGIN_ITER)

#源码中的plugin/common
add_subdirectory(common/)

set_ifndef(TRT_LIB /usr/lib/x86_64-linux-gnu/)
find_library(_NVINFER_LIB nvinfer HINTS ${TRT_LIB} PATH_SUFFIXES lib lib64)
set_ifndef(NVINFER_LIB ${_NVINFER_LIB})
include_directories(/usr/local/cuda-11.0/targets/x86_64-linux/include/)

list(APPEND PLUGIN_SOURCES "${PLUGIN_CU_SOURCES}")
add_library(tensorrtplugin MODULE ${PLUGIN_SOURCES})

target_link_libraries(tensorrtplugin PRIVATE ${NVINFER_LIB})
set_target_properties(tensorrtplugin PROPERTIES
  CUDA_SEPARABLE_COMPILATION ON
)
  1. 编译生成libtensorrtplugin.so文件
  2. 在Python代码中添加库文件即可:
import ctypes
ctypes.CDLL("plugin/build/libtensorrtplugin.so")
...
  • 3
    点赞
  • 15
    收藏
    觉得还不错? 一键收藏
  • 2
    评论
TensorRT 是 NVIDIA 的一个高性能深度学习推理引擎,可以在 NVIDIA GPU 上加速深度学习推理。而 ONNX 是一种跨平台、开放的深度学习模型表示格式,可以在不同的深度学习框架之间灵活换模型。 TensorRT 提供了一个 ONNX Parser,可以将 ONNX 模型解析为 TensorRT 的网络表示形式。这样,您就可以在 TensorRT 中加载 ONNX 模型,并在 NVIDIA GPU 上进行加速推理。以下是将 ONNX 模型换为 TensorRT 的一些步骤: 1. 安装 TensorRTONNX Runtime 在使用 ONNX Parser 之前,需要先安装 TensorRTONNX Runtime。可以从 NVIDIA 官网下载 TensorRT,也可以通过 pip 安装 ONNX Runtime。 2. 将 ONNX 模型解析为 TensorRT 的网络表示形式 使用 TensorRTONNX Parser,可以将 ONNX 模型解析为 TensorRT 的网络表示形式。这个过程可以通过以下 Python 代码实现: ```python import tensorrt as trt import onnx # Load the ONNX model onnx_model = onnx.load("model.onnx") # Create a TensorRT builder builder = trt.Builder(TRT_LOGGER) # Create a TensorRT network from the ONNX model network = builder.create_network() parser = trt.OnnxParser(network, TRT_LOGGER) parser.parse(onnx_model.SerializeToString()) # Build an engine from the TensorRT network engine = builder.build_cuda_engine(network) ``` 在这个过程中,首先使用 ONNXPython API 加载 ONNX 模型。然后,使用 TensorRTPython API 创建一个 TensorRT builder 和一个 TensorRT network。接下来,使用 TensorRTONNX Parser 将 ONNX 模型解析为 TensorRT 的网络表示形式,并将其添加到 TensorRT network 中。最后,使用 TensorRT builder 构建一个 TensorRT 引擎。 3. 运行 TensorRT 引擎 构建完 TensorRT 引擎后,可以使用以下代码来运行 TensorRT 推理: ```python import pycuda.driver as cuda import pycuda.autoinit import numpy as np # Load the engine with open("engine.plan", "rb") as f: engine_data = f.read() engine = runtime.deserialize_cuda_engine(engine_data) # Allocate input and output buffers on the GPU input_bindings = [] output_bindings = [] stream = cuda.Stream() for binding in engine: size = trt.volume(engine.get_binding_shape(binding)) * engine.max_batch_size dtype = trt.nptype(engine.get_binding_dtype(binding)) if engine.binding_is_input(binding): input_bindings.append(cuda.mem_alloc(size * dtype.itemsize)) else: output_bindings.append(cuda.mem_alloc(size * dtype.itemsize)) # Load input data to the GPU input buffer input_data = np.random.randn(batch_size, input_size) cuda.memcpy_htod(input_bindings[0], input_data.flatten().astype(np.float32)) # Run inference context = engine.create_execution_context() context.execute_async_v2(bindings=input_bindings + output_bindings, stream_handle=stream.handle) cuda.streams.synchronize() # Get the output data from the GPU output buffer output_data = np.empty((batch_size, output_size), dtype=np.float32) cuda.memcpy_dtoh(output_data.flatten(), output_bindings[0]) ``` 在这个过程中,首先使用 TensorRTPython API 加载 TensorRT 引擎。然后,使用 PyCUDA 分配输入和输出缓冲区,并将输入数据从主机(CPU)传输到设备(GPU)。接下来,使用 TensorRTPython API 创建一个 TensorRT 执行上下文,并在 GPU 上异步执行 TensorRT 推理。最后,使用 PyCUDA 将输出数据从设备(GPU)传输到主机(CPU)。 这就是将 ONNX 模型换为 TensorRT 的一些步骤。由于 ONNX Parser 是 TensorRT 的一部分,因此可以使用 TensorRTPython API 轻松地将 ONNX 模型换为 TensorRT

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值