Hi there!
I understand that my question not really suit this forum, but I don’t know any suitable one
I am writing my custom OpenCV wrapper (now I am using OpenCV 4.11) for C#
I am using DNN-based face detector for face detection (see cv::FaceDetectorYN), in particular detect method
This method has two input parameters: cv::InputArray and cv::OutputArray
My wrapped method (I expose two detect overloads)
C++ side:
extern "C" {
WRAPPEROPENCV_DLL_API void* Create_FaceDetect_DNN(const char* model, const char* config,
cv::Size input_size, float score_threshold, float nms_threshold, int top_k,
int backend_id, int target_id) {
cv::Ptr<cv::FaceDetectorYN>* faceDetectorYN = new cv::Ptr<cv::FaceDetectorYN>(
cv::FaceDetectorYN::create(model, config, input_size, score_threshold,
nms_threshold, top_k, backend_id, target_id));
if (faceDetectorYN->empty()) {
std::cerr << "Error: Failed to create FaceDetectorYN" << std::endl;
return nullptr;
}
return static_cast<void*>(faceDetectorYN);
}
WRAPPEROPENCV_DLL_API int Detect_FaceDetect_DNN(void* faceDetectorYN, cv::_InputArray* image, cv::_OutputArray* faces) {
if (!faceDetectorYN || !image || !faces) {
std::cerr << "Error: Detect invalid input(s)" << std::endl;
return 0;
}
try {
cv::Ptr<cv::FaceDetectorYN>* detectorPtr = static_cast<cv::Ptr<cv::FaceDetectorYN>*>(faceDetectorYN);
return (*detectorPtr)->detect(*image, *faces);
}
catch (cv::Exception e) {
return 0;
}
}
WRAPPEROPENCV_DLL_API int DetectMat_FaceDetect_DNN(void* faceDetectorYN, cv::Mat* image, cv::Mat* faces) {
if (!faceDetectorYN || !image || !faces) {
std::cerr << "Error: Detect invalid input(s)" << std::endl;
return 0;
}
cv::Ptr<cv::FaceDetectorYN>* detectorPtr = static_cast<cv::Ptr<cv::FaceDetectorYN>*>(faceDetectorYN);
return (*detectorPtr)->detect(*image, *faces);
}
WRAPPEROPENCV_DLL_API void Delete_FaceDetect_DNN(void* faceDetectorYN) {
if (!faceDetectorYN) {
std::cerr << "Error: Delete Invalid input - FaceDetectorYN" << std::endl;
return;
}
delete static_cast<cv::Ptr<cv::FaceDetectorYN>*>(faceDetectorYN);
}
}
C# side:
public class DNNFacedetect : DisposableObject
{
public DNNFacedetect(string model, string config, Size2i input_size, float score_threshold = 0.9f,
float nms_threshold = 0.3f, int top_k = 5000,
Backend backend_id = Backend.DNN_BACKEND_DEFAULT, Target target_id = Target.DNN_TARGET_CPU)
{
NativeObj = ThrowIfNull(Create_FaceDetect_DNN(model, config, input_size, score_threshold, nms_threshold,
top_k, (int)backend_id, (int)target_id));
}
public int Detect(InputArray image, OutputArray faces)
{
return Detect_FaceDetect_DNN(NativeObj, image.NativeObj, faces.NativeObj);
}
public int DetectMat(Mat image, Mat faces)
{
return DetectMat_FaceDetect_DNN(NativeObj, image.NativeObj, faces.NativeObj);
}
protected override void DisposeUnmanaged()
{
if (NativeObj == IntPtr.Zero)
return;
Delete_FaceDetect_DNN(NativeObj);
base.DisposeUnmanaged();
}
[DllImport("WrapperOpenCV.dll", CallingConvention = CallingConvention.Cdecl, CharSet = CharSet.Ansi)]
public static extern IntPtr Create_FaceDetect_DNN(string model, string config, Size2i input_size,
float score_threshold, float nms_threshold, int top_k, int backend_id, int target_id);
[DllImport("WrapperOpenCV.dll", CallingConvention = CallingConvention.Cdecl)]
public static extern int Detect_FaceDetect_DNN(IntPtr faceDetectorYN, IntPtr image, IntPtr faces);
[DllImport("WrapperOpenCV.dll", CallingConvention = CallingConvention.Cdecl)]
public static extern int DetectMat_FaceDetect_DNN(IntPtr faceDetectorYN, IntPtr image, IntPtr faces);
[DllImport("WrapperOpenCV.dll", CallingConvention = CallingConvention.Cdecl)]
public static extern void Delete_FaceDetect_DNN(IntPtr faceDetectorYN);
}
Example of usage:
inMat = new Mat(new Size2i(width, height), MatType.CV_8UC3); //copy image to this Mat
inResizedMat = new Mat();
detectedFaceMat = new Mat();
dnnFacedetect = new DNNFacedetect(modelPath, "", size320,
scoreThreshold, nmsThreshold, topK, Backend.DNN_BACKEND_CUDA, Target.DNN_TARGET_CUDA);
Imgproc.Resize(inMat, inResizedMat, size320);
dnnFacedetect?.DetectMat(inResizedMat, detectedFaceMat);
If I use public int DetectMat(Mat image, Mat faces)
programm works fine (without crashes)
But if I use public int Detect(InputArray image, OutputArray faces)
programm crashes after few seconds
What could be reason for such behavior?
Best regards,