java-topology/defects/opencv/patch/opencv-0003-onnx-ifint8output-static-vector-find.patch

98 lines
3 KiB
Diff

# UNDF: UNDF-2026-000001132
--- a/modules/dnn/src/onnx/onnx_importer.cpp
+++ b/modules/dnn/src/onnx/onnx_importer.cpp
@@ -724,38 +724,44 @@ std::string ONNXImporter::getLayerTypeDomain(const opencv_onnx::NodeProto& node_
static bool ifInt8Output(const String& layerType)
{
- // Contains all node types whose output should be int8 when it get int8 input.
- // ai.onnx opset 15
- // FIXME: This search might be better in time once we start using string
- static std::vector<String> input8output8List = {
- "QuantizeLinear",
- "QLinearAdd",
- "QLinearMul",
- "QLinearAveragePool",
- "QLinearGlobalAveragePool",
- "QLinearLeakyRelu",
- "QLinearSigmoid",
- "QLinearConcat",
- "QGemm",
- "QLinearSoftmax",
- "QLinearConv",
- "QLinearMatMul",
- "MaxPool",
- "ReduceMax",
- "ReduceMin",
- "Split",
- "Clip",
- "Abs",
- "Transpose",
- "Squeeze",
- "Flatten",
- "Unsqueeze",
- "Expand",
- "Reshape",
- "Pad",
- "Gather",
- "Concat",
- "Resize",
- "SpaceToDepth",
- "DepthToSpace",
- "Pow",
- "Add",
- "Sub",
- "Mul",
- "Div"
- };
- auto layerIt = std::find(input8output8List.begin(), input8output8List.end(), layerType);
- return layerIt != input8output8List.end();
+ // Contains all node types whose output should be int8 when it get int8 input.
+ // ai.onnx opset 15
+ //
+ // CWE-407 fix: replaced static vector<String> + std::find (O(L) per call)
+ // with static unordered_set<String> (O(1) per call).
+ //
+ // ifInt8Output() is called once per ONNX node input inside setParamsDtype(),
+ // which is called for every node in populateNet(). A model with N nodes
+ // and I inputs per node incurs O(N*I*L) work with a vector (L=35 entries).
+ // With an unordered_set the same work is O(N*I). For large transformer
+ // models (N=1000 nodes, I=3 inputs) the saving is ~35x.
+ static const std::unordered_set<String> input8output8Set = {
+ "QuantizeLinear",
+ "QLinearAdd",
+ "QLinearMul",
+ "QLinearAveragePool",
+ "QLinearGlobalAveragePool",
+ "QLinearLeakyRelu",
+ "QLinearSigmoid",
+ "QLinearConcat",
+ "QGemm",
+ "QLinearSoftmax",
+ "QLinearConv",
+ "QLinearMatMul",
+ "MaxPool",
+ "ReduceMax",
+ "ReduceMin",
+ "Split",
+ "Clip",
+ "Abs",
+ "Transpose",
+ "Squeeze",
+ "Flatten",
+ "Unsqueeze",
+ "Expand",
+ "Reshape",
+ "Pad",
+ "Gather",
+ "Concat",
+ "Resize",
+ "SpaceToDepth",
+ "DepthToSpace",
+ "Pow",
+ "Add",
+ "Sub",
+ "Mul",
+ "Div"
+ };
+ return input8output8Set.count(layerType) > 0;
}