Multithreading 使用openCV和std::threads解决SegFault
我尝试使用C++14个线程进入openCV。 操作系统是DebianLinux 我喜欢获得六个RTSP流,调整大小并在结果cv::Mat对象中排列它们,然后查看它。 我认为线程是处理中断流所必需的。 重新开放需要一些时间,我不希望其他流被阻塞 在启动过程中,程序或多或少会遇到SegFault。 调试输出在waitkey()方法之后停止 更常见的情况是,程序启动流并在数小时内运行良好 如何指出非法内存访问? (这是一个Segfault) cv::Mat对象中的某些重新分配是问题所在吗? 还是构造一个与线程相关的问题Multithreading 使用openCV和std::threads解决SegFault,multithreading,opencv,segmentation-fault,stdthread,Multithreading,Opencv,Segmentation Fault,Stdthread,我尝试使用C++14个线程进入openCV。 操作系统是DebianLinux 我喜欢获得六个RTSP流,调整大小并在结果cv::Mat对象中排列它们,然后查看它。 我认为线程是处理中断流所必需的。 重新开放需要一些时间,我不希望其他流被阻塞 在启动过程中,程序或多或少会遇到SegFault。 调试输出在waitkey()方法之后停止 更常见的情况是,程序启动流并在数小时内运行良好 如何指出非法内存访问? (这是一个Segfault) cv::Mat对象中的某些重新分配是问题所在吗? 还是构造一
#include <thread>
#include <mutex>
#include <iostream>
#include <chrono>
#include <opencv2/opencv.hpp>
#include <syslog.h>
#include <atomic>
#include <string>
bool doExit = false;
uint16_t
viewX = 1600,//1920,
viewY = 900,//1080,
imageXCount = 3,
imageYCount = 2,
viewportSizeX = viewX / imageXCount,
viewportSizeY = viewY / imageYCount,
pause = 50;
class Worker
{
public:
std::string name,
url;
cv::VideoCapture RTSPStream;
cv::Mat RTSPImage,
RTSPResized;
int frameCount = -1;
cv::Mat image;
cv::Mat& dest;
cv::Rect roi;
cv::Size size;
std::mutex& mut;
Worker(std::string Name, std::string URL, cv::Mat& Dest, cv::Rect ROI, cv::Size Size, std::mutex& Mut) :
name(Name), url(URL), dest(Dest), roi(ROI), size(Size), mut(Mut)
{
syslog (LOG_INFO, "Thread Init");
std::cout << "Name: \t" << name << std::endl;
std::cout << "URL: \t" << url << std::endl;
}
void operator () ()
{
syslog (LOG_INFO, "Thread Start");
while (!doExit)
{
if (RTSPStream.isOpened())
{
if (!RTSPStream.read(RTSPImage))
{
cv::ellipse (
RTSPImage,
cv::Point( 50, 50 ),
cv::Size(10,10 ),
90,
0,
360,
cv::Scalar( 0, 0, 255 ),
5
);
syslog (LOG_INFO, "Thread StreamRead failed");
}
}
else
{
RTSPStream.open(url);
frameCount = 0;
syslog (LOG_INFO, "Thread Open RTSP");
}
if (RTSPImage.empty())
{
cv::ellipse (
RTSPImage,
cv::Point( 50, 50 ),
cv::Size(10,10 ),
90,
0,
360,
cv::Scalar( 0, 0, 255 ),
5
);
std::cout << url << " Image empty\n";
syslog (LOG_INFO, "Empty Image, reOpen");
RTSPStream.release();
RTSPStream.open(url);
} else
{
frameCount++;
cv::resize(RTSPImage, RTSPResized, size);
mut.lock();
// cv::medianBlur(RTSPResized, dest(roi), 5);
RTSPResized.copyTo(dest(roi));
mut.unlock();
}
}
}
};
int main()
{
openlog ("CamViewer", LOG_PID, LOG_SYSLOG);
syslog (LOG_INFO, "***");
syslog (LOG_INFO, "***");
syslog (LOG_INFO, "Start Main");
std::mutex resultMutex;
cv::Rect roi1 = cv::Rect(0 ,0,viewportSizeX, viewportSizeY); // ROIs setzen
cv::Rect roi2 = cv::Rect(viewportSizeX,0,viewportSizeX, viewportSizeY);
cv::Rect roi3 = cv::Rect(viewportSizeX*2,0,viewportSizeX, viewportSizeY);
cv::Rect roi4 = cv::Rect(0,viewportSizeY,viewportSizeX, viewportSizeY);
cv::Rect roi5 = cv::Rect(viewportSizeX,viewportSizeY,viewportSizeX, viewportSizeY);
cv::Rect roi6 = cv::Rect(viewportSizeX*2,viewportSizeY,viewportSizeX, viewportSizeY);
cv::Size s = cv::Size (viewportSizeX, viewportSizeY);
cv::Mat result (viewY, viewX, CV_8UC3);
cv::namedWindow("Result", cv::WINDOW_NORMAL);
cv::setWindowProperty("Result", cv::WND_PROP_FULLSCREEN, cv::WINDOW_FULLSCREEN);
std::thread worker1 = std::thread (Worker("cam2", "rtsp://192.168.1.62:554/stream1", result, roi1, s, resultMutex));
std::thread worker3 = std::thread (Worker("cam6", "rtsp://192.168.1.60:554/12" , result, roi3, s, resultMutex));
std::thread worker2 = std::thread (Worker("cam1", "rtsp://192.168.1.61:554/stream1", result, roi2, s, resultMutex));
std::thread worker4 = std::thread (Worker("cam4", "rtsp://192.168.1.64:554/stream1", result, roi5, s, resultMutex));
std::thread worker5 = std::thread (Worker("cam5", "rtsp://192.168.1.65:554/stream1", result, roi4, s, resultMutex));
std::thread worker6 = std::thread (Worker("cam3", "rtsp://192.168.1.66:554/stream1", result, roi6, s, resultMutex));
cv::ellipse (
result,
cv::Point( 50, 50 ),
cv::Size(10,10 ),
90,
0,
360,
cv::Scalar( 0, 0, 255 ),
5
);
syslog (LOG_INFO, "Start MainLoop");
while (!doExit)
{
cv::Mat dblBuffer;
resultMutex.lock();
result.copyTo(dblBuffer);
resultMutex.unlock();
cv::imshow("Result", dblBuffer);
cv::waitKey(pause);
std::cout << ".";
}
worker1.join();
worker2.join();
worker3.join();
worker4.join();
worker5.join();
worker6.join();
return 0;
}
#包括
#包括
#包括
#包括
#包括
#包括
#包括
#包括
bool-doExit=false;
uint16\u t
viewX=1600,//1920,
viewY=900,//1080,
imageXCount=3,
imageYCount=2,
viewportSizeX=viewX/imageXCount,
viewportSizeY=viewY/imageYCount,
暂停=50;
班主任
{
公众:
std::字符串名称,
网址;
cv::视频捕获RTSPStream;
cv::Mat RTSPImage,
RTSPResized;
int frameCount=-1;
cv::Mat图像;
cv::Mat和dest;
cv::Rect roi;
cv::大小;
std::mutex&mut;
Worker(std::string Name、std::string URL、cv::Mat&Dest、cv::Rect ROI、cv::Size Size、std::mutex&Mut):
名称(名称)、url(url)、目的地(目的地)、投资回报率(roi)、大小(大小)、mut(mut)
{
系统日志(日志信息,“线程初始化”);
标准::cout