onnx-mlir

Logo

ONNX 模型在 MLIR 编译器基础设施中的表示与参考降级

在 GitHub 上查看项目 onnx/onnx-mlir

操作指南

使用 Python 进行推理
使用 C/C++ 进行推理
使用 Java 进行推理

参考资料

ONNX 方言
OMTensor C99 运行时 API
OMTensorList C99 运行时 API
OMTensor Java 运行时 API
OMTensorList Java 运行时 API
生成 ONNX 方言
关于文档

开发

添加一个操作
测试指南
错误处理
命令行选项
性能分析
常量传播
添加一个加速器

工具

工具

RunONNXModel.py
DocCheck

本项目由 onnx 维护

托管于 GitHub Pages — 主题由 orderedlist

调试数值误差

当 onnx-mlir 编译的推理可执行文件产生的数值结果与训练框架产生的结果不一致时,使用 utils/RunONNXModel.py Python 脚本调试数值误差。该 Python 脚本将通过 onnx-mlir 和参考后端运行模型,并逐层比较这两个后端产生的中间结果。

前提条件

参考后端

onnx-mlir 的输出可以通过使用一个参考 ONNX 后端或使用 protobuf 格式的参考输入和输出进行验证。

用法

utils/RunONNXModel.py 支持以下命令行选项

$ python ../utils/RunONNXModel.py  --help
usage: RunONNXModel.py [-h] [--log-to-file [LOG_TO_FILE]] [--model MODEL] [--compile-args COMPILE_ARGS] [--compile-only] [--compile-using-input-shape] [--print-input]
                       [--print-output] [--save-onnx PATH] [--verify {onnxruntime,ref}] [--verify-all-ops] [--verify-with-softmax] [--verify-every-value] [--rtol RTOL]
                       [--atol ATOL] [--save-so PATH | --load-so PATH] [--save-ref PATH] [--load-ref PATH | --shape-info SHAPE_INFO] [--lower-bound LOWER_BOUND]
                       [--upper-bound UPPER_BOUND]

optional arguments:
  -h, --help                  show this help message and exit
  --log-to-file [LOG_TO_FILE] Output compilation messages to file, default compilation.log
  --model MODEL               Path to an ONNX model (.onnx or .mlir)
  --compile-args COMPILE_ARGS Arguments passed directly to onnx-mlir command. See bin/onnx-mlir --help
  --compile-only              Only compile the input model
  --compile-using-input-shape Compile the model by using the shape info getting from the inputs in the reference folder set by --load-ref
  --print-input               Print out inputs
  --print-output              Print out inference outputs produced by onnx-mlir
  --save-onnx PATH            File path to save the onnx model. Only effective if --verify=onnxruntime
  --verify {onnxruntime,ref}  Verify the output by using onnxruntime or reference inputs/outputs. By default, no verification. When being enabled, --verify-with-softmax or --verify-every-value must be used to specify verification mode.
  --verify-all-ops            Verify all operation outputs when using onnxruntime
  --verify-with-softmax       Verify the result obtained by applying softmax to the output
  --verify-every-value        Verify every value of the output using atol and rtol
  --rtol RTOL                 Relative tolerance for verification
  --atol ATOL                 Absolute tolerance for verification
  --save-so PATH              File path to save the generated shared library of the model
  --load-so PATH              File path to load a generated shared library for inference, and the ONNX model will not be re-compiled
  --save-ref PATH             Path to a folder to save the inputs and outputs in protobuf
  --load-ref PATH             Path to a folder containing reference inputs and outputs stored in protobuf. If --verify=ref, inputs and outputs are reference data for verification
  --shape-info SHAPE_INFO     Shape for each dynamic input of the model, e.g. 0:1x10x20,1:7x5x3. Used to generate random inputs for the model if --load-ref is not set
  --lower-bound LOWER_BOUND   Lower bound values for each data type. Used inputs. E.g. --lower-bound=int64:-10,float32:-0.2,uint8:1. Supported types are bool, uint8, int8, uint16, int16, uint32, int32, uint64, int64,float16, float32, float64
  --upper-bound UPPER_BOUND   Upper bound values for each data type. Used to generate random inputs. E.g. --upper-bound=int64:10,float32:0.2,uint8:9. Supported types are bool, uint8, int8, uint16, int16, uint32, int32, uint64, int64, float16, float32, float64

用于在两种不同的编译选项下比较模型的辅助脚本。

基于上述的 utils/runONNXModel.pyutils/checkONNXModel.py 允许用户在两种不同的编译选项下运行给定模型两次,并比较其结果。这让用户可以轻松测试新选项,比较编译器的安全版本(例如 -O0-O3)与更高级的版本(例如 -O3-O3 --march=x86-64)。只需使用 --ref-compile-args--test-compile-args 标志指定编译选项,使用 --model 标志指定模型,以及在存在动态形状输入时可能需要 --shape-info。完整的选项列在 --help 标志下。

调试为操作符生成的代码。

如果您知道或怀疑某个特定的 ONNX MLIR 操作符产生了错误的结果,并且想要缩小问题范围,我们提供了一些有用的 Krnl 操作符,可以在运行时打印张量的值或具有基本数据类型的值。

要在程序的特定位置打印张量的值,请注入以下代码 (其中 X 是要打印的张量)

create.krnl.printTensor("Tensor X: ", X);

注意:当前只在张量秩小于四时打印张量内容。

要打印一条消息后跟一个值,请注入以下代码 (其中 val 是要打印的值,valType 是其类型)

create.krnl.printf("inputElem: ", val, valType);

查找内存错误

如果您知道或怀疑 onnx-mlir 编译的推理可执行文件存在内存分配相关问题,可以使用 valgrind 框架mtrace 内存工具 来辅助调试。这些工具会跟踪内存分配/释放相关的 API,并能检测到内存问题,例如内存泄漏。

然而,如果问题与内存访问有关,特别是缓冲区溢出问题,通常很难调试,因为运行时错误发生在包含问题代码点之外的地方。可以使用 “Electric Fence library” 来调试这些问题。它帮助您检测两个常见的编程问题:超出 malloc() 分配的内存边界的软件,以及访问已被 free() 释放的内存分配的软件。与其他内存调试器不同,Electric Fence 会检测读访问和写访问,并能精确指出导致错误的指令。

由于 Electric Fence library 未得到 RedHat 的官方支持,您需要自己下载、构建和安装其源代码。安装完成后,在生成推理可执行文件时,使用“-lefence”选项链接此库。然后直接执行它,这将导致运行时错误并停止在引起内存访问问题的地方。您可以使用调试器或上一节描述的调试打印函数来确定位置。