征程6|YOLOv5x 在 Horizon 征程6 平台的完整部署实战(上) YOLOv5x 在 Horizon 征程6 上的端到端部署实践上工具链部署本文记录 YOLOv5x 从 PyTorch 权重到 J6 可执行 HBM 模型的部署流程。上篇聚焦工具链侧环境准备、ONNX 导出、校准数据生成和 HBM 编译下篇再展开板端 C 推理部署与精度评估。平台Horizon J6 (nash-e)SDKhorizon_j6_open_explorer_v3.8.1-py310模型YOLOv5x输入分辨率 640x640板端输入NV12PC 端校准输入RGB float321. 环境准备首先安装 SDK 中的 host 端工具链和 board 端运行时cdhorizon_j6_open_explorer_v3.8.1-py310_20260326/package/hostbashinstall.shcd../boardbashinstall.shPython 侧需要准备模型导出、ONNX 处理、校准与评估相关依赖pipinstalltorch onnx onnxsim onnxruntime opencv-python-headless pycocotoolsHorizon 工具链建议使用 SDK 自带 whl 安装重点包括horizon_tc_uihmcthbdk4_compiler后续操作均在示例工程目录中进行cdhorizon_j6_open_explorer_v3.8.1-py310_20260326/nano_toolchain/yolov5x_End-to-End_Pipeline/2. Stage 1PyTorch 导出 ONNXYOLOv5 的.pt权重是包含 Python 对象引用的序列化文件因此导出前需要确保 YOLOv5 源码在 Python 路径中。SDK 中已经包含对应源码可直接复用nano_toolchain/model_convert/detection/yolov5x_scratch/yolov5_repo/导出流程可以概括为加载yolov5x.pt设置模型为eval和export状态构造(1, 3, 640, 640)的 dummy input使用torch.onnx.export导出 ONNX使用onnxsim简化模型执行命令python3 stage1_model_export.py\--weights./model/yolov5x.pt\--img-size640\--batch-size1\--includeonnx\--opset12\--simplify导出后得到文件说明model/yolov5x.pt原始 PyTorch 权重model/yolov5x.onnx简化后的 ONNX 模型模型输出包含三个检测头P3/8 (1, 3, 80, 80, 85) P4/16 (1, 3, 40, 40, 85) P5/32 (1, 3, 20, 20, 85)其中85 4(bbox) 1(obj) 80(classes)。3. Stage 2生成校准数据PTQ 量化需要少量代表性样本来统计激活分布。一般选择 50 到 500 张图片即可关键是预处理必须和后续推理保持一致。本流程中的校准预处理为原始图片 - Letterbox Resize 到 640x640padding114 - BGR 转 RGB - HWC 转 CHW - /255 归一化 - 保存为 .npy执行mkdir-pcalib_images# 从 COCO 验证集拷贝若干图片到 calib_images/python3 stage2_calibration_set.py输出目录calibration_data_yolov5/ ├── xxx.npy ├── yyy.npy └── ...每个.npy文件的格式为shape: (1, 3, 640, 640) dtype: float32 range: [0, 1]4. Stage 3ONNX 编译为 HBMHorizon 工具链的大致链路为ONNX - hmct 量化校准 - .bc 量化模型 - hbdk4 编译 - .hbm核心编译配置如下model_parameters:onnx_model:model/yolov5x.onnxmarch:nash-eworking_dir:./model_outputoutput_model_file_prefix:yolov5x_640x640_nv12remove_node_type:Dequantizeinput_parameters:input_name:imagesinput_type_rt:nv12input_type_train:rgbinput_layout_train:NCHWinput_shape:1x3x640x640norm_type:data_scalescale_value:0.003921568627451calibration_parameters:cal_data_dir:./calibration_data_yolov5calibration_type:defaultcompiler_parameters:compile_mode:latencycore_num:1optimize_level:O2jobs:16这里最需要注意的是march: nash-e对应 J6 BPU 架构。input_type_rt: nv12表示板端运行时输入为 NV12。input_type_train: rgb与校准数据保持一致。scale_value: 1/255表示板端运行时由模型完成归一化。编译命令hb_compile-cfull_compile_config.yaml主要产物model_output/ ├── yolov5x_640x640_nv12.hbm ├── yolov5x_640x640_nv12_quantized_model.bc ├── yolov5x_640x640_nv12_original_float_model.onnx ├── yolov5x_640x640_nv12_quant_info.json └── yolov5x_640x640_nv12.html其中.hbm是后续板端部署使用的模型文件。5. 查看模型输入输出将 HBM 放到板端后可以用hrt_model_exec查看模型信息hrt_model_exec model_info--model_fileyolov5x_640x640_nv12.hbm输入一般会被拆成两个 NV12 tensorTensorShape说明images_y(1, 640, 640, 1)Y 平面images_uv(1, 320, 320, 2)UV 交错平面输出仍然是 YOLOv5 的三个检测头但要特别关注 strideoutput: shape(1,3,80,80,85), stride(7372800,2457600,30720,384,4) 729: shape(1,3,40,40,85), stride(1843200,614400,15360,384,4) 741: shape(1,3,20,20,85), stride(460800,153600,7680,384,4)最后一维虽然只有85个 float理论大小是 340 bytes但实际 col stride 是 384 bytes说明中间存在 padding。这个细节会直接影响下篇的 C 后处理实现。小结上篇完成了从yolov5x.pt到yolov5x_640x640_nv12.hbm的工具链流程。关键点主要有三个导出 ONNX 时要正确加载 YOLOv5 源码和模型结构。校准数据预处理要与部署推理保持一致。编译配置中要明确 J6 架构、NV12 输入和运行时归一化方式。下篇将继续介绍如何在 J6 板端用 C 加载 HBM、构造 NV12 输入、调用 UCP/DNN API、解析带 padding 的输出并完成 YOLOv5 后处理和 mAP 评估。