开发插件执行提供程序库
本页提供了如何使用 ONNX Runtime 开发插件 EP 库的参考。
内容
创建插件 EP 库
插件 EP 构建为动态/共享库,它导出 C 函数 CreateEpFactories() 和 ReleaseEpFactory()。ONNX Runtime 调用 CreateEpFactories() 以获取一个或多个 OrtEpFactory 实例。OrtEpFactory 用于创建 OrtEp 实例并指定其创建的 EP 所支持的硬件设备。
ONNX Runtime 仓库包含一些示例插件 EP 库,后续章节将引用这些库。
定义 OrtEp
OrtEp 表示 EP 的一个实例,ONNX Runtime 会话使用该实例来识别和执行该 EP 支持的模型操作。
OrtEp API 结构体定义在 onnxruntime_ep_c_api.h 中。
下表列出了实现者必须为 OrtEp 定义的必需变量和函数。
| 字段 | 概述 | 示例实现 |
|---|---|---|
| ort_version_supported | 编译该 EP 所使用的 ONNX Runtime 版本。实现应将其设置为 ORT_API_VERSION。 | ExampleEp() |
| GetName | 获取执行提供程序名称。 执行提供程序名称的推荐约定是以“ExecutionProvider”后缀结尾。例如:“ContosoAiExecutionProvider”。 | ExampleEp::GetNameImpl() |
| GetCapability | 获取有关 OrtEp 实例支持的节点/子图的信息。 | ExampleEp::GetCapabilityImpl() |
下表列出了实现者必须为编译节点的 OrtEp 定义的必需函数。在 ORT 1.23 中,这些是必需函数,因为当时仅支持编译型 EP。
| 字段 | 概述 | 示例实现 |
|---|---|---|
| Compile | 编译分配给 OrtEp 的 OrtGraph 实例。实现必须为每个 OrtGraph 设置一个 OrtNodeComputeInfo 实例,以便定义其计算函数。如果会话配置为生成预编译模型,则执行提供程序必须返回 count 数量的 EPContext 节点。 | ExampleEp::CompileImpl() |
| ReleaseNodeComputeInfos | 释放 OrtNodeComputeInfo 实例。 | ExampleEp::ReleaseNodeComputeInfosImpl() |
下表列出了实现者必须为通过内核注册表提供算子内核的 OrtEp 定义的必需函数。
| 字段 | 概述 | 示例实现 |
|---|---|---|
| GetKernelRegistry | 获取执行提供程序的内核注册表(如果有)。 内核注册表包含 EP 支持的算子内核的内核创建信息。 | ExampleKernelEp::GetKernelRegistryImpl() |
下表列出了实现者可以为 OrtEp 定义的可选函数。如果未定义可选的 OrtEp 函数,ONNX Runtime 将使用默认实现。
| 字段 | 概述 | 示例实现 |
|---|---|---|
| GetPreferredDataLayout | 获取 EP 首选的数据布局。 如果未实现此函数,ORT 将假定 EP 首选 OrtEpDataLayout::NCHW 数据布局。 | |
| ShouldConvertDataLayoutForOp | 给定一个域为 domain 且类型为 op_type 的算子,确定是否应将相关节点的数据布局转换为 target_data_layout。如果 EP 首选非默认数据布局,则将在布局转换期间调用此函数,并将 target_data_layout 设置为 EP 首选的数据布局。此函数的实现是可选的。如果 EP 首选非默认数据布局,它可以实现此函数以更细粒度地自定义特定算子的数据布局偏好。 | |
| SetDynamicOptions | 在此 EP 上设置动态选项。应用程序可以在会话创建后的任何时间通过 OrtApi::SetEpDynamicOptions() 设置动态选项。此函数的实现是可选的。EP 仅在需要处理任何动态选项时才应实现此函数。 | |
| OnRunStart | 由 ORT 调用,以通知 EP 运行开始。 此函数的实现是可选的。EP 仅在需要在运行开始时处理应用程序提供的选项时才应实现此函数。 | |
| OnRunEnd | 由 ORT 调用,以通知 EP 运行结束。 此函数的实现是可选的。EP 仅在需要在运行结束时处理应用程序提供的选项时才应实现此函数。 | |
| CreateAllocator | 为 OrtSession 的给定 OrtMemoryInfo 创建一个 OrtAllocator。OrtMemoryInfo 实例将与使用 EpDevice_AddAllocatorInfo 在 OrtEpDevice 中设置的值之一相匹配。任何分配器特定的选项都应从会话选项中读取。此函数的实现是可选的。如果未提供,ORT 将使用 `OrtEpFactory::CreateAllocator()`。 | |
| CreateSyncStreamForDevice | 为 OrtSession 的给定内存设备创建一个同步流。这用于为执行提供程序创建一个同步流,并在模型执行期间用于同步设备上的操作。任何流特定的选项都应从会话选项中读取。 此函数的实现是可选的。如果未提供,ORT 将使用 `OrtEpFactory::CreateSyncStreamForDevice()`。 | |
| GetCompiledModelCompatibilityInfo | 获取包含用于生成编译模型的 EP 堆栈详细信息的字符串。 该兼容性信息字符串可与 OrtEpFactory::ValidateCompiledModelCompatibilityInfo 配合使用,以确定编译模型是否与 EP 兼容。 | |
| IsConcurrentRunSupported | 获取执行提供程序是否支持对会话进行并发运行调用。 如果未实现,ORT 将假定支持并发运行。 |
定义 OrtEpFactory
OrtEpFactory 表示一个 EP 工厂实例,ONNX Runtime 会话使用该实例来查询设备支持、创建分配器、创建数据传输对象以及创建 EP 实例(即 OrtEp)。
OrtEpFactory API 结构体定义在 onnxruntime_ep_c_api.h 中。
下表列出了实现者必须为 OrtEpFactory 定义的必需变量和函数。
| 字段 | 概述 | 示例实现 |
|---|---|---|
| ort_version_supported | 编译该 EP 时所使用的 ONNX Runtime 版本。实现应将其设置为 ORT_API_VERSION。 | ExampleEpFactory() |
| GetName | 获取该工厂创建的 EP 的名称。必须与 OrtEp::GetName() 匹配。 | ExampleEpFactory::GetNameImpl() |
| GetVendor | 获取该工厂创建的 EP 所属厂商的名称。 | ExampleEpFactory::GetVendor() |
| GetVendorId | 获取该工厂创建的 EP 所属厂商的厂商 ID。这通常是 PCI 厂商 ID。 | ExampleEpFactory::GetVendorId() |
| GetVersion | 获取该工厂创建的 EP 的版本。版本字符串应遵循 语义化版本 2.0 规范。 | ExampleEpFactory::GetVersionImpl() |
| GetSupportedDevices | 获取有关该工厂创建的 EP 所支持的 OrtHardwareDevice 实例的信息。 | ExampleEpFactory::GetSupportedDevicesImpl() |
| CreateEp | 创建一个用于 ONNX Runtime 会话中的 OrtEp 实例。ORT 调用 OrtEpFactory::ReleaseEp() 来释放该实例。 | ExampleEpFactory::CreateEpImpl() |
下表列出了实现者可以为 OrtEpFactory 定义的可选函数。
| 字段 | 概述 | 示例实现 |
|---|---|---|
| ValidateCompiledModelCompatibilityInfo | 验证编译模型与 EP 的兼容性。 此函数用于验证底层 EP 是否支持使用提供的兼容性信息字符串生成的模型。实现应检查编译模型是否与 EP 兼容,并返回相应的 OrtCompiledModelCompatibility 值。 | |
| CreateAllocator | 为给定的 OrtMemoryInfo 创建一个可在会话之间共享的 OrtAllocator。创建 EP 的工厂负责提供 EP 所需的分配器。 OrtMemoryInfo 实例将与使用 EpDevice_AddAllocatorInfo 在 OrtEpDevice 中设置的值之一相匹配。 | ExampleEpFactory::CreateAllocatorImpl() |
| ReleaseAllocator | 释放由工厂创建的 OrtAllocator 实例。 | ExampleEpFactory::ReleaseAllocatorImpl() |
| CreateDataTransfer | 为工厂创建一个 OrtDataTransferImpl 实例。OrtDataTransferImpl 可用于在 EP 支持的设备之间复制数据。 | ExampleEpFactory::CreateDataTransferImpl() |
| IsStreamAware | 如果该工厂创建的 EP 是流感知的(stream-aware),则返回 true。 | ExampleEpFactory::IsStreamAwareImpl() |
| CreateSyncStreamForDevice | 为给定的 OrtMemoryDevice 创建一个同步流。这用于为 OrtMemoryDevice 创建一个同步流,可用于会话之外的操作。 | ExampleEpFactory::CreateSyncStreamForDeviceImpl() |
| GetHardwareDeviceIncompatibilityDetails | 检查硬件设备与此执行提供程序之间已知的互不兼容原因。 此函数允许执行提供程序检查特定硬件设备是否与执行提供程序兼容。EP 可以通过 OrtDeviceEpIncompatibilityDetails 参数使用 OrtEpApi::DeviceEpIncompatibilityDetails_SetDetails 设置特定的不兼容原因。 | ExampleEpFactory::GetHardwareDeviceIncompatibilityDetailsImpl() |
| CreateExternalResourceImporterForDevice | 创建一个用于外部资源导入的 OrtExternalResourceImporterImpl。这用于创建一个外部资源导入器,以实现外部 GPU 内存(例如 D3D12 共享资源)和同步原语(例如 D3D12 时间线围栏)的零拷贝导入。 支持外部资源导入(通过 CUDA、HIP、Vulkan 或 D3D12 API)的 EP 可以实现此功能,以允许应用程序在无拷贝的情况下共享 GPU 资源。 | ExampleEpFactory::CreateExternalResourceImporterForDeviceImpl() |
| GetNumCustomOpDomains | 获取工厂提供的 EP 专用 OrtCustomOpDomain 的数量。 | ExampleEpFactory::GetNumCustomOpDomainsImpl() |
| GetCustomOpDomains | 获取工厂提供的 EP 专用 OrtCustomOpDomain。 | ExampleEpFactory::GetCustomOpDomainsImpl() |
导出用于创建和释放工厂的函数
ONNX Runtime 要求插件 EP 库导出某些函数/符号。下表列出了必须从插件 EP 库中导出的函数。
| 函数 | 描述 | 示例实现 |
|---|---|---|
| CreateEpFactories | ONNX Runtime 调用此函数来创建 OrtEpFactory 实例。 | ExampleEp: CreateEpFactories |
| ReleaseEpFactory | ONNX Runtime 调用此函数来释放 OrtEpFactory 实例。 | ExampleEp: ReleaseEpFactory |
API 参考
API 头文件
- onnxruntime_ep_c_api.h
- 定义由插件 EP 和 EP 工厂实例实现的接口。
- 提供由插件 EP 和 EP 工厂实例使用的 API。
- onnxruntime_c_api.h
- 提供用于遍历输入模型图的 API。
数据类型
| 类型 | 描述 |
|---|---|
| OrtHardwareDeviceType | 枚举硬件设备类别
|
| OrtHardwareDevice | 表示物理硬件设备的不透明类型。 |
| OrtExecutionProviderDevicePolicy | 枚举可供 ORT 自动 EP 选择功能的用户使用的默认 EP 选择策略。 |
| OrtEpDevice | 表示可以运行模型或模型子图的 EP 与硬件设备组合的不透明类型。 |
| OrtNodeFusionOptions | 包含用于融合 EP 支持的节点的选项的结构体。 |
| OrtNodeComputeContext | 包含已编译/融合节点的名称和主机内存分配函数的不透明类型。ONNX Runtime 提供 OrtNodeComputeContext 的一个实例作为 OrtNodeComputeInfo::CreateState() 的参数。 |
| OrtNodeComputeInfo | 包含已编译 OrtGraph 实例的计算函数的结构体。由 OrtEp 实例初始化。 |
| OrtEpGraphSupportInfo | 包含有关 EP 支持的节点的信息的不透明类型。OrtEpGraphSupportInfo 的一个实例被传递给 OrtEp::GetCapability(),并且 EP 会将它支持的节点信息填充到该 OrtEpGraphSupportInfo 实例中。 |
| OrtEpDataLayout | 枚举 EP 可能首选的算子数据布局。默认情况下,ONNX 模型使用“通道优先”布局(例如 NCHW),但某些 EP 可能首选“通道最后”布局(例如 NHWC)。 |
| OrtMemoryDevice | 表示物理设备和内存类型组合的不透明类型。内存分配和分配器与特定的 OrtMemoryDevice 相关联,此信息用于确定何时需要进行数据传输。 |
| OrtDataTransferImpl | EP 为在 EP 使用的设备与 CPU 之间复制数据而实现的函数结构体。 |
| OrtSyncNotificationImpl | EP 为流通知(Stream notifications)实现的函数结构体。 |
| OrtSyncStreamImpl | 如果 EP 需要支持流,则实现的函数结构体。 |
| OrtEpFactory | 插件 EP 库向 ORT 提供一个或多个 OrtEpFactory 实例。OrtEpFactory 实现了一些函数,ORT 使用这些函数来查询设备支持、创建分配器、创建数据传输对象以及创建 EP 实例(即 OrtEp 实例)。一个 OrtEpFactory 可以支持多个硬件设备(OrtHardwareDevice)。如果工厂支持多个硬件设备,则该工厂创建的 EP 实例预期在其支持的硬件设备之间内部分割分配给该 EP 的任何图节点。或者,如果 EP 库作者需要 ONNX Runtime 在 EP 库支持的不同硬件设备之间分割图节点,则 EP 库必须提供多个 OrtEpFactory 实例。每个 OrtEpFactory 实例必须支持一个硬件设备,并且必须创建一个具有唯一名称的 EP 实例(例如 MyEP_CPU、MyEP_GPU、MyEP_NPU)。 |
| OrtEp | 可以在一个或多个硬件设备(OrtHardwareDevice)上执行模型节点的 EP 实例。OrtEp 实现了一些函数,ORT 使用这些函数来查询图节点支持、编译支持的节点、查询首选数据布局、设置运行选项等。OrtEpFactory 通过 OrtEpFactory::CreateEp() 函数创建一个 OrtEp 实例。 |
| OrtRunOptions | 包含传递给运行模型的 OrtApi::Run() 函数的选项的不透明对象。 |
| OrtGraph | 表示图的不透明类型。在对 OrtEp::GetCapability() 和 OrtEp::Compile() 的调用中提供给 OrtEp 实例。 |
| OrtValueInfo | 包含图中某个值的信息的不透明类型。图中的值可以是图输入、图输出、图初始化器、节点输入或节点输出。OrtValueInfo 实例包含以下信息。
|
| OrtExternalInitializerInfo | 包含存储在外部文件中的初始化器信息的不透明类型。OrtExternalInitializerInfo 实例包含该初始化器的文件路径、文件偏移量和字节大小。可以通过 ValueInfo_GetExternalInitializerInfo() 函数从 OrtValueInfo 中获取。 |
| OrtTypeInfo | 包含 ONNX 张量、序列、映射、稀疏张量等的元素类型和形状信息的不透明类型。 |
| OrtTensorTypeAndShapeInfo | 包含 ONNX 张量元素类型和形状信息的不透明类型。 |
| OrtNode | 表示图中节点的不透明类型。 |
| OrtOpAttrType | 枚举属性类型。 |
| OrtOpAttr | 表示 ONNX 算子属性的不透明类型。 |