How to use opencv cuda module log function - opencv

I'm trying to work with Opencv CUDA module, specially refer to cv::cuda::log function.
First, I'll give to details Opencv compilation.
I compiled Opencv with WITH_CUDA flag on, took the libs and dlls from the compilation, however I copied the headers files from the downloaded opencv folder, since the compilation folder does't include headers by default.
I wonder, whether is this the right thing to do ?
Second, I tried to use the cv::cuda:: function.
I include the cuda.hpp header
#include "opencv2/core/cuda.hpp"
cv::cuda::GpuMat source, dest;
GpuMat compiles great for me, However I don't know which file should I include in order to work with the log function. when I write the following line
cv::cuda::log(source, dest);
I kept on getting the error message:
error: C2039: log in not a member of cv::cuda
Windows 7, Visual studio 2013, Opencv 3.0.0, platform: 64 bit, CUDA toolkit 6.5
Third, I'd like to know about Opencv CUDA implementation, does it utilize npp functionality? Opencv vs npp, which one is better to use ?
I could easly write my code using npp, however I'd like to know the opencv CUDA module.
Thanks

After couple days of searching, I'd like to share my knowledge
First thing I was doing wrong, was taking the headers from Opencv compilation, the right thing to do is taking the header from all the Opencv modules (each module individually).
Second, After Opencv compilation with CUDA flag everything worked great.
Third, Several opencv CUDA functions does utilize NPP
Forth, Use github

This code should work for OpenCV 3.1:
#include <opencv2/opencv.hpp>
#include <opencv2/cudaarithm.hpp>
int main()
{
cv::Mat img = cv::imread("img.jpg", cv::IMREAD_GRAYSCALE);
cv::Mat img_32f;
img.convertTo(img_32f, CV_32F);
//To avoid log(0) that is undefined
img_32f += 1.0f;
cv::cuda::GpuMat gpuImg, gpuImgLog;
gpuImg.upload(img_32f);
cv::cuda::log(gpuImg, gpuImgLog);
cv::Mat imgLog, imgLog_32f;
gpuImgLog.download(imgLog_32f);
double min, max;
cv::minMaxLoc(imgLog_32f, &min, &max);
imgLog_32f.convertTo(imgLog, CV_8U, 255.0/(max-min), -255.0*min/(max-min));
cv::imshow("img", img);
cv::imshow("imgLog", imgLog);
cv::waitKey(0);
return 0;
}

Related

Opencv DNN module was not built with CUDA backend, however it was built [duplicate]

I am trying to run YOLOv3 on Visual Studio 2019 using CUDA 10.2 with cuDNN v7.6.5 on Windows 10 using NVidia GeForce 930M. Here is part of the code I used.
#include <fstream>
#include <sstream>
#include <iostream>
#include <opencv2/dnn.hpp>
#include <opencv2/imgproc.hpp>
#include <opencv2/highgui.hpp>
using namespace cv;
using namespace dnn;
using namespace std;
int main()
{
// Load names of classes
string classesFile = "coco.names";
ifstream ifs(classesFile.c_str());
string line;
while (getline(ifs, line)) classes.push_back(line);
// Give the configuration and weight files for the model
String modelConfiguration = "yolovs.cfg";
String modelWeights = "yolov3.weights";
// Load the network
Net net = readNetFromDarknet(modelConfiguration, modelWeights);
net.setPreferableBackend(DNN_BACKEND_CUDA);
net.setPreferableTarget(DNN_TARGET_CUDA);
// Open the video file
inputFile = "vid.mp4";
cap.open(inputFile);
// Get frame from the video
cap >> frame;
// Create a 4D blob from a frame
blobFromImage(frame, blob, 1 / 255.0, Size(inpWidth, inpHeight), Scalar(0, 0, 0), true, false);
// Sets the input to the network
net.setInput(blob);
// Runs the forward pass to get output of the output layers
vector<Mat> outs;
net.forward(outs, getOutputsNames(net));
}
Although I add $(CUDNN)\include;$(cudnn)\include; to Additional Include Directories in both C/C++ and Linker, added CUDNN_HALF;CUDNN; to C/C++>Preprocessor Definitions, and added cudnn.lib; to Linker>Input, I still get this warning:
DNN module was not built with CUDA backend; switching to CPU
and it runs on CPU instead of GPU, can anyone help me with this problem?
I solved it by using CMake, but I had first to add this opencv_contrib then rebuilding it using Visual Studio. Make sure that these WITH_CUDA, WITH_CUBLAS, WITH_CUDNN, OPENCV_DNN_CUDA, BUILD_opencv_world are checked in CMake.
I had a similar issue happen to me about a week ago, but I was using Python and Tensorflow. Although the languages were different compared to C++, I did get the same error. To fix this, I uninstalled CUDA 10.2 and downgraded to CUDA 10.1. From what I have found, there might be a dependency issue with CUDA, or in your case, OpenCV hasn't created support yet for the latest version of CUDA.
EDIT
After some further research it seems to be an issue with Opencv rather than CUDA. Referencing this github thread, if you installed Opencv with cmake, remove the arch bin version below 7 on the config file, then rebuild/reinstall Opencv. However, if that doesn't work, another option would be to remove CUDA arch bin version < 5.3 and rebuild.

OpenCV no longer opens video files VideoCapture

I have a problem seemingly caused by OpenCV 3.xx - the problem does not manifest in OpenCV 2.xx
The issue is reading video files. I've set my code up as follows:
>#include <opencv2\opencv.hpp>
>#include <opencv2\core\core.hpp>
>#include <opencv2\highgui\highgui.hpp>
>#include <opencv2\imgproc\imgproc.hpp>
>#include <opencv2\features2d\features2d.hpp>
>int main()
> cv::VideoCapture cap;
> cv::Mat frame;
> if(!cap.open("Myfile.avi"))
> std::cout << "Open failed" << std::endl;
> else
> cap.read(frame);
>
> cv::imshow("Frame", frame);
> cv::waitKey(5000);
> return 0;
Now the problem is when the code gets to "cap.read(frame)" I get a "vector subscript is out of range" error with OpenCV 3.40 and this does not happen with my build of OpenCV 2.4.9. The format of the file is in avi, its not some weird codec, and clearly it works in previous versions of OpenCV.
I've tried other OpenCV 3.xx builds and I get the same or similar problems with simply reading a file in.
My question is twofold:
How do I get OpenCV 3.xx to work with reading video files (or do I need to regress to 2.xx?)
Why has the major revision change completely screwed up video file reading? That doesn't make any sense for a computer vision API.
As a guess it will be something to do with the FFMPEG implementation because various searches have turned up other people having issues with this.
Any help is much appreciated.
Thanks
I've managed to resolve it myself, it turns out that in OpenCV 3.xx I have to force the VideoCapture::open to use the FFMPEG library by doing this:
>cap.open("Myfile.avi", cv::CAP_FFMPEG)
where the latter parameter is the flags to identify which VideoCapture API backend to use. The list can be found here for any one else interested:
https://docs.opencv.org/3.3.0/d4/d15/group__videoio__flags__base.html

OpenCV won't capture frames from a RTMP source, while FFmpeg does

my goal is to capture a frame from a rtmp stream every second, and process it using OpenCV. I'm using FFmpeg version N-71899-g6ef3426 and OpenCV 2.4.9 with the Java interface (but I'm first experimenting with Python).
For the moment, I can only take the simple and dirty solution, which is to capture images using FFmpeg, store them in disk, and then read those images from my OpenCV program. This is the FFmpeg command I'm using:
ffmpeg -i "rtmp://antena3fms35livefs.fplive.net:1935/antena3fms35live-live/stream-lasexta_1 live=1" -r 1 capImage%03d.jpg
This is currently working for me, at least with this concrete rtmp source. Then I would need to read those images from my OpenCV program in a proper way. I have not actually implemented this part, because I'm trying to find a better solution.
I think the ideal way would be to capture the rtmp frames directly from OpenCV, but I cannot find the way to do it. This is the code in Python I'm using:
cv2.namedWindow("camCapture", cv2.CV_WINDOW_AUTOSIZE)
cap = cv2.VideoCapture()
cap.open('"rtmp://antena3fms35livefs.fplive.net:1935/antena3fms35live-live/stream-lasexta_1 live=1"')
if not cap.open:
print "Not open"
while (True):
err,img = cap.read()
if img and img.shape != (0,0):
cv2.imwrite("img1", img)
cv2.imshow("camCapture", img)
if err:
print err
break
cv2.waitKey(30)
Instead of read() function, I'm also trying with grab() and retrieve() functions without any good result. The read() function is being executed every time, but no "img" or "err" is received.
Is there any other way to do it? or maybe there is no way to get frames directly from OpenCV 2.4.9 from a stream like this?
I've read OpenCV uses FFmpeg to do this kind of tasks, but as you can see, in my case FFmpeg is able to get frames from the stream while OpenCV is not.
In the case I could not find the way to get the frames directly from OpenCV, my next idea is to pipe somehow, FFmpeg output to OpenCV, which seems harder to implement.
Any idea,
thank you!
UPDATE 1:
I'm in Windows 8.1. Since I was running the python script from Eclipse PyDev, this time I run it from cmd instead, and I'm getting the following warning:
warning: Error opening file (../../modules/highgui/src/cap_ffmpeg_impl.hpp:545)
This warning means, as far as I could read, that either the file-path is wrong, or either the codec is not supported. Now, the question is the same. Is OpenCV not capable of getting the frames from this source?
Actually I have spent more that one day to figure out how to solve this issue. Finally I have solved this problem with the help of this link.
Here is client side code.
#include <opencv2/core/core.hpp>
#include <opencv2/imgproc/imgproc.hpp>
#include <opencv2/highgui/highgui.hpp>
#include <opencv2/opencv.hpp>
using namespace cv;
int main(int, char**) {
cv::VideoCapture vcap;
cv::Mat image;
const std::string videoStreamAddress = "rtmp://192.168.173.1:1935/live/test.flv";
if(!vcap.open(videoStreamAddress)) {
std::cout << "Error opening video stream or file" << std::endl;
return -1;
}
cv::namedWindow("Output Window");
cv::Mat edges;
for(;;) {
if(!vcap.read(image)) {
std::cout << "No frame" << std::endl;
cv::waitKey();
}
cv::imshow("Output Window", image);
if(cv::waitKey(1) >= 0) break;
}
}
Note: In this case I have created a android application to get real time video and send it to rtmp server wowza which is deployed in PC.So that is where I created this c++ implementation for real time video processing.
python -c "import cv2; print(cv2.getBuildInformation())"
check build opencv with ffmpeg。If it is correct, your code should be fine。
If not, rebuild opencv with ffmpeg。
Under osx
brew install opencv --with-ffmpeg

VideoCapture OpenCV 2.4.2 error in windows

I have a problem using VideoCapture class with OpenCV 2.4.2 under windows XP 32bits.
It doesn't open any file or camera and fixing it's being a pain.
Im using visual studio 2010 but i have also tried the code in QTcreator with the same result.
The testing code is the following:
#include "opencv/cv.h"
#include "opencv/highgui.h"
#include <iostream>
#include <string>
#include <iomanip>
#include <sstream>
using namespace cv;
using namespace std;
int main()
{
const char* videoPath = "C:/video/";
string videoName = string(videoPath) + "avi.avi";
VideoCapture cap(videoName);
if(!cap.isOpened())
{
std::cout<<"Fail"<<std::endl;
return -3;
}
return 0;
}
The output is always '-3'.
Qt Creator shows a
warning: Error opening file (../../modules/highgui/src/cap_ffmpeg_impl.hpp:361)
I debugged it and the problem appears in the first line of:
CvCapture* cvCreateFileCapture_FFMPEG_proxy(const char * filename)
{
CvCapture_FFMPEG_proxy* result = new CvCapture_FFMPEG_proxy;
if( result->open( filename ))
return result;
delete result;
#if defined WIN32 || defined _WIN32
return cvCreateFileCapture_VFW(filename);
#else
return 0;
#endif
}
in the cap_ffmpeg.cpp internal file.
I have tested the same code in a mac under snow leopard and it works. No surprises here since it must be a library issue.
I have opened the avi file with the same path route using the c-function cvCapture easy and fast.
I got all the dlls of 'C:\opencv\opencv\build\x86\vc10\bin'
included in mi debug file. I got the tbb.dll and all the 'C:\opencv\opencv\3rdparty\ffmpeg' content included too.
This is drving me crazy so any help would be appreciated.
Thanks in advance.
In my case, the same problem was resolved after deleting all opencv_***.dll files in C:\Windows\System32. So, I use the dll files just through the path like "%PATH%;C: \Program Files \OpenCV2.4.2\build\x86\vc10/bin". Please try it.
I also faced with this problem and solved it by correct the path of the function:
VideoCapture cap(videoName);
If the AVI file of videoName does't exist, it will be an error:
(../../modules/highgui/src/cap_ffmpeg_impl.hpp:XXX)
where XXX represents the line number.
I had the same issue with the open method whilst running under Windows 8 (64bit), opencv 2.4.10. IDE is running in x86.
I found that running the application in release configuration solved the problem.
Stumbled across the answer because I had the same issue with imread. Issue is presented in the this thread.
imread not working in Opencv
See the fix I found below, for mp4 files.
I faced the same issue on Windows 7, using OpenCV 2.4.9. I am using the java wrapper for opencv.
Matthias Krings has done a lot of research for this. See this. Apparently this is an issue based on the video file type. With .avi files, it seems to work for a lot of people. Unfortunately his solution of setting OPENCV_DIR did not work for me. But his comments in the bug listing gave me a hint to fix the issue.
You have to do two things:
Set java.library.path to include the directory {opencv\install\dir}opencv-2.4.9\build\x86\vc10\bin. You can set the variable using the -D option on the java command line: java -Djava.library.path=PATH_TO_YOUR_DLL .... Also fetch this variable from your environment, using System.getProperty(...), and print it before calling loadLibrary(), to verify that the path setting is working.
And in your java class, load the ffmpeg dll using System.loadLibrary("opencv_ffmpeg249");. The loadLibrary() function should be invoked from within a static block in java.
There is a file named opencv_ffmpeg249.dll in the java.library.path that we set.
This works on ubuntu also, for .so files.
I too faced the same issue and resolved after pointing to the correct location of the input video.

C++ Eclipse OpenCV : .exe file and binaries generated, but no image displayed

Here's my code (the first DisplayImage.cpp code in the OpenCV documentation)
/*
* DisplayImage.cpp
*
* Created on: Dec 25, 2011
* Author: Arcturus */
#include <iostream>
#include <opencv2\opencv.hpp>
using namespace cv;
using namespace std;
int main(int argc, char** argv){
Mat image;
image = imread(argv[1], 1);
if(argc!=2 || !image.data){
cout<<"no image data";
return -1;
}
namedWindow("Display Image", CV_WINDOW_AUTOSIZE);
imshow("Display Image", image);
waitKey(10000);
return 0;
}
Build complete, executable generated, binaries generated.
I have my image - blackbuck.bmp- in the DisplayImage Debug folder. To run the code, I go to Run> Run Configurations. Select the DisplayImage Debug exe file, key in blackbuck.bmp (also tried it with absolute path) and run it.
On the top of the console, I get the message : DisplayImage Debug. And it displays no image at all. What could be wrong here?
I am running it on Eclipse, using CDT.
Thank you for your time!
EDIT: Problem solved!!! I had to copy all the dll files from the library folder to the folder in which my executable file was being generated. I still do not understand why, though. After all, the linker was already linking the library folder containing all the dlls. If someone could explain this, it would be of great help for future debugging. Thank you karl and mevotron for your time :)
EDIT 2: From the msdn website:
"A potential disadvantage to using DLLs is that the application is not self-contained; it depends on the existence of a separate DLL module. The system terminates processes using load-time dynamic linking if they require a DLL that is not found at process startup and gives an error message to the user. The system does not terminate a process using run-time dynamic linking in this situation, but functions exported by the missing DLL are not available to the program."
I think this answers my question. Perhaps this means eclipse uses load-time dynamic linking.
How did you compile OpenCV with MinGW (i.e., what were your BUILD_TYPE and SSE* options set to during the CMake configuration)? The reason I ask, is that there is a known bug with SSE optimizations that will cause highgui operations to crash when using MinGW built versions. See my other SO answer here.

Resources