Minimal ONNX model generated by the reproducer script.
#!/usr/bin/env python3
import sys
import numpy as np
import onnx
import onnxruntime as ort
import openvino as ov
from onnx import TensorProto, helper
a = np.array([200, 100, 50, 10], dtype=np.uint8)
b = np.array([200, 3, 6, 30], dtype=np.uint8)
wrap_ref = ((a.astype(np.int32) * b.astype(np.int32)) % 256).astype(np.uint8)
sat_ref = np.clip(a.astype(np.int32) * b.astype(np.int32), 0, 255).astype(np.uint8)
A = helper.make_tensor_value_info("A", TensorProto.UINT8, [4])
B = helper.make_tensor_value_info("B", TensorProto.UINT8, [4])
Y = helper.make_tensor_value_info("Y", TensorProto.UINT8, [4])
node = helper.make_node("Mul", ["A", "B"], ["Y"])
graph = helper.make_graph([node], "uint8_mul_overflow", [A, B], [Y])
model = helper.make_model(graph, opset_imports=[helper.make_opsetid("", 14)])
model.ir_version = 8
onnx.checker.check_model(model)
mb = model.SerializeToString()
feed = {"A": a, "B": b}
ort_out = ort.InferenceSession(
mb,
providers=["CPUExecutionProvider"],
).run(None, feed)[0]
core = ov.Core()
compiled = core.compile_model(core.read_model(mb, b""), "CPU")
ov_out = compiled(feed)[compiled.output(0)]
print(f"a : {a}")
print(f"b : {b}")
print(f"a*b : {a.astype(np.int32) * b.astype(np.int32)}")
print(f"ORT out : {ort_out}")
print(f"OV out : {ov_out}")
print(f"wrap ref : {wrap_ref}")
print(f"sat ref : {sat_ref}")
ort_wrap = np.array_equal(ort_out, wrap_ref)
ov_wrap = np.array_equal(ov_out, wrap_ref)
ov_sat = np.array_equal(ov_out, sat_ref)
print(f"\nORT matches wrap? {ort_wrap}")
print(f"OV matches wrap? {ov_wrap}")
print(f"OV matches sat? {ov_sat}")
if ort_wrap and ov_sat and not ov_wrap:
print("\nBUG REPRODUCED: OpenVINO uint8 Mul saturates instead of wrapping.")
sys.exit(0)
print("\nNOT REPRODUCED")
sys.exit(1)
OpenVINO Version
2026.1.0
Operating System
Other (Please specify in description)
Device used for inference
CPU
Framework
ONNX
Model used
Minimal ONNX model generated by the reproducer script.
Issue description
OpenVINO CPU produces saturated results for
uint8ONNXMuloverflow cases.For a valid opset-14 ONNX model, ONNX Runtime returns the expected fixed-width
uint8wraparound result, while OpenVINO CPU clamps every overflowed result to255.OS: Ubuntu 24.04.2 LTS / Linux x86_64
Step-by-step reproduction
Relevant log output
Issue submission checklist