2196557_zh-CN

cancel
Showing results for 
Show  only  | Search instead for 
Did you mean: 

2196557_zh-CN

2196557_zh-CN

在 IMX95 的内部 NPU 上运行 Pytorch 模型

我正试图在 IMX95 的内部 NPU 上运行 PyTorch 模型。我按照以下步骤进行了操作:

  1. 将 PyTorch 模型导出为 ONNX 文件(opset 版本 18;dynamo=True;模型权重:Float32)
  2. 使用 onnx2quant 和包含 500 个样本的校准数据集,将模型量化为 int8
  3. 使用 eiq-converter.exe 将 ONNX 文件转换为 TFLite 文件(--plugin eiq-converter-onnx2tflite)
    (eIQ_Toolkit_v1.17.0\bin\eiq-变流器.exe)
  4. 使用 neutron-变流器.exe 转换 IMX95 的 TfLite 文件
    (eIQ_Toolkit_v1.17.0\bin\neutron-变流器\MCU_SDK_25.09.00+Linux_6.12.34_2.1.0\neutron-变流器.exe)

所有步骤运行无误,我还创建了一个 PowerShell 脚本,用于运行第 2-4 步。可在此处下载:
script.ps1

ONNX 文件(输出步骤 1)可在此处下载:
model.onnx

我遇到的问题是:
当我在 IMX95 的 NPU 上运行模型时,尽管提供了不同的输入图像,但输出总是相同的。但是,当我在 IMX95 的 CPU 上运行 TFLite 模型(步骤 3 的输出)时,每幅图像的输出都是正确的。这表明,转换和量化步骤工作正常,但最后一步出现了问题。

我成功进行了转换(使用中子变流器)并运行了恩智浦提供的示例模型(mobilenet_v1_1.0_224_quant.tflite)在 IMX95 的 NPU 上。因此,推理代码并不是问题所在。

我怀疑要么模型中使用的层有问题,要么在导出或转换过程中出现问题。

感谢您就如何解决这个问题提出任何意见或建议。

Re: Run Pytorch Model on the internal NPU of the IMX95

你好@TobiasRothlin


eIQ 1.17 与 LF 6.12.34 兼容。

eIQ 1.16 与 LF 6.12.20 兼容。

您可以尝试使用正确的版本,然后再试一次吗?

Re: Run Pytorch Model on the internal NPU of the IMX95

你好 @danielchen

电路板支持包 版本为 6.12.20
我在 /proc/version 中进行了检查

Linux 版本 6.12.20-lts-next-gdfaf2136deb2 (oe-user @OE-host) (aarch64-参考发行版、系统开发套件。-linux-gcc (GCC) 14.2.0,GNU ld (GNU Binutils) 2.44)#1 SMP PREEMPT Wed Jun 4 10:15:09 UTC 2025


我使用的是 IMX.95 EVK


我使用同样的工具转换了 mobilenet.tflite 锉刀使用 MCU_SDK_25.09.00+Linux_6.12.34_2.1.0 转换模型时 变流器即使输出与 CPU 型号不同,输出看起来也更有用。不过,当我使用 Linux_6.6.3_1.0.0 时,也会出现与自定义模型相同的问题。输出变化

NPU (Linux_6.6.3_1.0.0):

- 推理结果 -
推理时间(平均):0.50 ms
模型输出:(1, 1001)
[[0 0 0 ... 0 0 0]]
非零类得分:
所有类得分均为零!

NPU (MCU_SDK_25.09.00+Linux_6.12.34_2.1.0):

- 推理结果 -
推理时间(平均):2.00 ms
模型输出:(1, 1001)
[[0 6 0 ... 0 0 0]]
非零类得分:
Class ID:1 得分:6
Class ID:114 Score: 6
Class ID:117 Score: 6
Class ID:118 Score: 6
Class ID:123 Score: 6
Class ID:125 Score: 6
Class ID:242 Score: 6
Class ID:245 Score: 6
Class ID:246 Score: 6
Class ID:250 Score: 6
Class ID:251 Score: 6
Class ID:253 Score: 6
Class ID:256 Score: 6
Class ID:257 Score: 6
Class ID:370 Score: 6
Class ID:373 Score: 6
Class ID:374 Score: 6
Class ID:379 Score: 6
Class ID:381 Score: 6
Class ID:457 Score: 6
Class ID:498 Score: 6
Class ID:501 Score: 6
Class ID:502 Score: 6
Class ID:507 Score: 6
Class ID:508 Score: 5
Class ID:509 Score: 6
Class ID:513 Score: 6
Class ID:514 Score: 6
Class ID:626 Score: 6
Class ID:629 Score: 6
Class ID:630 Score: 6
Class ID:635 Score: 6
Class ID:637 Score: 6
Class ID:709 Score: 3
Class ID:754 Score: 6
Class ID:757 Score: 6
Class ID:758 Score: 6
Class ID:763 Score: 6
Class ID:765 Score: 6
Class ID:882 Score: 6
Class ID:885 Score: 6
Class ID:886 Score: 6
Class ID:890 Score: 6
Class ID:891 Score: 6
Class ID:893 分数: 2

预测等级 ID:1
预测等级得分:6
最低得分:0 最高得分:6

CPU:

- 推理结果 -
推理时间(平均):116.31 ms
模型输出:(1, 1001)
[[0 0 0 ... 0 0 0]]
非零类得分:
Class ID:439 分数:18
Class ID:441 Score: 1
Class ID:454 Score: 1
Class ID:496 Score: 1
Class ID:505 Score: 3
Class ID:506 Score: 7
Class ID:527 Score: 2
Class ID:528 Score: 1
Class ID:544 Score: 1
Class ID:549 Score: 1
Class ID:551 Score: 1
Class ID:554 Score: 1
Class ID:573 Score: 15
Class ID:599 Score: 2
Class ID:605 Score: 112
Class ID:620 Score: 11
Class ID:627 Score: 1
Class ID:630 Score: 1
Class ID:645 Score: 1
Class ID:665 Score: 2
Class ID:697 Score: 6
Class ID:712 Score: 13
Class ID:726 Score: 1
Class ID:738 Score: 2
Class ID:744 Score: 1
Class ID:774 Score: 3
Class ID:783 Score: 8
Class ID:800 Score: 1
Class ID:805 Score: 2
Class ID:847 Score: 5
Class ID:852 Score: 3
Class ID:895 Score: 1
Class ID:899 Score: 3
Class ID:900 Score: 5
Class ID:906 Score: 3
Class ID:908 Score: 1
Class ID:967 分数: 3

预测等级 ID:605
预测等级得分:112
最低得分:0 最高得分:112

Python 代码推理


 
import time

import numpy as np
from PIL import Image
import matplotlib.pyplot as plt

from tensorflow.lite.python.interpreter import Interpreter
from tensorflow.lite.python.interpreter import load_delegate

from tqdm import tqdm

MODEL_PATH_NPU = ‘./mobilenet_v1_1.0_224_quant_IMX_95.tflite’
MODEL_PATH_CPU = ‘./mobilenet_v1_1.0_224_quant.tflite’
IMAGE_PATH = ‘./train.jpg’

USE_NPU_DELEGATE = True
NPU_DELEGATE_PATH = ‘/usr/lib/liblitert_neutron_delegate.so’

INFERENCE_WARMUP_STEPS = 10
INFERENCE_STEPS = 10

class TFLiteModel:

def __init__(self, model_path, use_npu_delegate, npu_delegate_path):
    if use_npu_delegate:
        ext_delegate = [load_delegate(npu_delegate_path)]
        self.interpreter = Interpreter(model_path=model_path, experimental_delegates=ext_delegate)
    else:
        self.interpreter = Interpreter(model_path=model_path)

    self.interpreter.allocate_tensors()

    self.input_details = self.interpreter.get_input_details()
    self.output_details = self.interpreter.get_output_details()

def load_image(self, image_path, input_mean, input_std):
    image_height = self.input_details[0]['shape'][1]
    image_width = self.input_details[0]['shape'][2]

    img = Image.open(image_path).resize((image_width, image_height))

    img_array = np.array(img)
    input_data = np.expand_dims(img_array, axis=0)

    return input_data

def infer(self, input_tensor):
    self.interpreter.set_tensor(self.input_details[0]['index'], input_tensor)
    self.interpreter.invoke()
    output_data = self.interpreter.get_tensor(self.output_details[0]['index'])
    return output_data

if __name__ == ‘__main__':
 if not USE_NPU_DELEGATE:
  MODEL_PATH = MODEL_PATH_CPU
else:
 MODEL_PATH = MODEL_PATH_NPU

tf_lite_model = TFLiteModel(MODEL_PATH, USE_NPU_DELEGATE, NPU_DELEGATE_PATH)
input_tensor = tf_lite_model.load_image(IMAGE_PATH, input_mean=[0.485, 0.456, 0.406], input_std=[0.229, 0.224, 0.225])

#Warm up
for _ in tqdm(range(INFERENCE_WARMUP_STEPS), desc="Warming up",total=INFERENCE_WARMUP_STEPS):
    tf_lite_model.infer(input_tensor)


# Actual inference
average_inference_time = 0

for _ in tqdm(range(INFERENCE_STEPS), desc="Inference", total=INFERENCE_STEPS):
    start_time = time.time()
    output_data = tf_lite_model.infer(input_tensor)
    stop_time = time.time()
    average_inference_time += (stop_time - start_time) * 1000
average_inference_time /= INFERENCE_STEPS

print('\n--- Inference Results ---')

print(f'Inference Time (average): {average_inference_time:.2f} ms')
print(f'Model Output: {output_data.shape} \n {output_data}')

# List all None-zero class scores
print('Non-zero class scores:')
number_of_zero_scores = 0
for class_id, score in enumerate(output_data[0]):
    if np.abs(score) > 1e-6:
        print(f'    Class ID: {class_id}   Score: {score}')
    else:
        number_of_zero_scores += 1

if number_of_zero_scores == len(output_data[0]):
    print('    All class scores are zero!')
else:
    id = np.argmax(output_data)
    print(f'\nPredicted class ID: {id}')
    print(f'Predicted class score: {output_data[0][id]}')
    print(f'Min score: {np.min(output_data)}    Max score: {np.max(output_data)}')

print('-------------------------\n')

# Plot a heat map with the logits for each class
class_width_pixels = 100
plt.figure(figsize=(20, 4))
plt.imshow(output_data, aspect='auto', cmap='viridis', extent=[0, output_data.shape[1]*class_width_pixels, 0, 1])
plt.colorbar()
plt.xlabel('Class ID')
plt.title('Model Output Scores per Class')
plt.savefig(f'model_output_scores_{"NPU" if USE_NPU_DELEGATE else "CPU"}.png')
plt.close()```

Re: Run Pytorch Model on the internal NPU of the IMX95

你使用的是哪个电路板支持包 版本?

Re: Run Pytorch Model on the internal NPU of the IMX95

@danielchen感谢您的建议。

我用 eIQ 1.17 和 LF 6.12.34(Linux 版本 6.12.34-lts-next-gbe78e49cb433)进行了重试。

我也没有使用自定义代码,而是使用了 /usr/bin/tensorflow-lite-2.19.0/examples 中的label_image.py文件。

1.使用所提供的模型进行测试

python3 label_image.py --ext_delegate /usr/lib/libneutron_delegate.so

INFO:NeutronDelegate 委托:31 个节点中有 0 个节点被委托,0 个分区。

INFO:
预热时间:57.4 ms

推理时间: 54.8 毫秒

0.878431: 军装
0.027451:温莎领带
0.011765: 按揭板
0.011765: 防弹背心
0.007843: 萨克斯

查看结果 NPU 上执行了 0 个节点

2.使用 MCU_SDK_25.09.00+Linux_6.12.34_2.1.0

python3 label_image.py --ext_delegate /usr/lib/libneutron_delegate.so --model_file /root/mobilenet_v1_1.0_224_quant_imx95_MCU-SDK-25-09-00-Linux-6-12-34-2-1-0.tflite

INFO:NeutronDelegate 委托:4 个节点中委托了 1 个节点,有 1 个分区。

INFO:Neutron 委托版本:v1.0.0-be8bf399,已启用 zerocp。
INFO:
预热时间:0.6 毫秒

推理时间:0.4 毫秒

0.000000: 卫生纸
0.000000: 海星
0.000000: 斑马
0.000000: 苏木
0.000000: 天竺鼠

结果显示,在 NPU 上执行了一个节点,但输出全为零,是错误的。

使用的 .tflite 文件附在帖子后面。


我还用自定义模型进行了实验,结果也显示了同样的问题,即所有零或所有对数的值都完全相同,与输入图像无关。



Tags (1)
No ratings
Version history
Last update:
‎01-08-2026 03:24 AM
Updated by: