From 7b4aefedead8bc6f990b825072d886ea9c2e1e6f Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Mon, 6 May 2019 16:04:19 -0400 Subject: [PATCH] Add support for loading ONNX model from in-memory buffer. --- modules/dnn/include/opencv2/dnn/dnn.hpp | 17 ++++++++++++++ modules/dnn/src/onnx/onnx_importer.cpp | 31 +++++++++++++++++++++++++ 2 files changed, 48 insertions(+) diff --git a/modules/dnn/include/opencv2/dnn/dnn.hpp b/modules/dnn/include/opencv2/dnn/dnn.hpp index 07099dcb73..a8ee534034 100644 --- a/modules/dnn/include/opencv2/dnn/dnn.hpp +++ b/modules/dnn/include/opencv2/dnn/dnn.hpp @@ -868,6 +868,23 @@ CV__DNN_EXPERIMENTAL_NS_BEGIN */ CV_EXPORTS_W Net readNetFromONNX(const String &onnxFile); + /** @brief Reads a network model from ONNX + * in-memory buffer. + * @param buffer memory address of the first byte of the buffer. + * @param sizeBuffer size of the buffer. + * @returns Network object that ready to do forward, throw an exception + * in failure cases. + */ + CV_EXPORTS Net readNetFromONNX(const char* buffer, size_t sizeBuffer); + + /** @brief Reads a network model from ONNX + * in-memory buffer. + * @param buffer in-memory buffer that stores the ONNX model bytes. + * @returns Network object that ready to do forward, throw an exception + * in failure cases. + */ + CV_EXPORTS_W Net readNetFromONNX(const std::vector& buffer); + /** @brief Creates blob from .pb file. * @param path to the .pb file with input tensor. * @returns Mat. diff --git a/modules/dnn/src/onnx/onnx_importer.cpp b/modules/dnn/src/onnx/onnx_importer.cpp index e722b4a735..91110cb15e 100644 --- a/modules/dnn/src/onnx/onnx_importer.cpp +++ b/modules/dnn/src/onnx/onnx_importer.cpp @@ -57,6 +57,24 @@ public: CV_Error(Error::StsUnsupportedFormat, "Failed to parse onnx model"); } + ONNXImporter(const char* buffer, size_t sizeBuffer) + { + struct _Buf : public std::streambuf + { + _Buf(const char* buffer, size_t sizeBuffer) + { + char* p = const_cast(buffer); + setg(p, p, p + sizeBuffer); + } + }; + + _Buf buf(buffer, sizeBuffer); + std::istream input(&buf); + + if (!model_proto.ParseFromIstream(&input)) + CV_Error(Error::StsUnsupportedFormat, "Failed to parse onnx model from in-memory byte array."); + } + void populateNet(Net dstNet); }; @@ -808,6 +826,19 @@ Net readNetFromONNX(const String& onnxFile) return net; } +Net readNetFromONNX(const char* buffer, size_t sizeBuffer) +{ + ONNXImporter onnxImporter(buffer, sizeBuffer); + Net net; + onnxImporter.populateNet(net); + return net; +} + +Net readNetFromONNX(const std::vector& buffer) +{ + return readNetFromONNX(reinterpret_cast(buffer.data()), buffer.size()); +} + Mat readTensorFromONNX(const String& path) { opencv_onnx::TensorProto tensor_proto = opencv_onnx::TensorProto();