Ubuntu 16.04下手动编译OpenCV 2.4.13,并提供对FFmpeg以及CUDA 8的支持来使用GPU加速视频图像处理。 考虑到大数据处理系统spark的需要,这里也同时加入opencv对java的支持。
系统为ubuntu 16.04.1 x64服务器版的最小化系统,具体参数如下:
1 2 3 4 DISTRIB_ID=Ubuntu DISTRIB_RELEASE=16.04 DISTRIB_CODENAME=xenial DISTRIB_DESCRIPTION="Ubuntu 16.04.1 LTS"
假定已经安装好了CUDA 8,如果还没有安装CUDA 8环境可以参考这里安装http://notes.maxwi.com/2017/02/26/ubuntu-cuda8-env-set/ 也需要提前安装好FFmpeg并将其二进制放到环境变量中,如果还没有编译安装好FFmpeg对GPU解码的支持,可以参考这里http://notes.maxwi.com/2017/03/01/ubuntu-compile-ffmpeg-with-cuvid-nvenc-npp/
安装OpenCV依赖包 官方要求的必装包:
1 sudo apt-get install build-essential cmake git libgtk2.0-dev pkg-config libavcodec-dev libavformat-dev libswscale-dev
上面的git如果采用zip方式安装可以不需要,但如果是通过zip方式安装则需要安装上unzip用于解压
官方推荐的可选包:
1 sudo apt-get install python-dev python-numpy libtbb2 libtbb-dev libjpeg-dev libpng-dev libtiff-dev libjasper-dev libdc1394-22-dev
添加对OpenGL的支持所需要的包:
1 sudo apt-get install freeglut3-dev mesa-common-dev libgtkglext1 libgtkglext1-dev
其他一些推荐包,包括视频编解码所需要的开发包等:
1 sudo apt-get install checkinstall yasm libgstreamer0.10-dev libgstreamer-plugins-base0.10-dev libv4l-dev libtbb-dev libqt4-dev libgtk2.0-dev libmp3lame-dev libtheora-dev libvorbis-dev libxvidcore-dev x264 v4l-utils
我这里把这些包全部安装上
验证OpenGL的配置 如果不需要OpenGL可以跳过此步 保存如下代码,并命名为testgl.c:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 #include <GL/glut.h> void draw (void ) { glClearColor (0 ,1 ,0 ,1 ); glClear (GL_COLOR_BUFFER_BIT ); glFlush (); } int main (int argc, char **argv) { glutInit (&argc, argv); glutInitDisplayMode (GLUT_SINGLE | GLUT_RGB ); glutInitWindowPosition (50 ,25 ); glutInitWindowSize (500 ,250 ); glutCreateWindow ("Green window" ); glutDisplayFunc (draw); glutMainLoop (); return 0 ; }
编译:
1 gcc testgl.c -o testgl -lGL -lGLU -lglut
如果编译通过,则表示OpenGl安装成功,运行的话需要有桌面环境,可以通过如下代码为服务器系统安装桌面环境用于测试:
1 sudo apt install ubuntu-desktop
如果需要远程通过VNC在windows上连接ubuntu,可以打开ubuntu上的vino,也就是那个desktop sharing,设置允许远程连接,再在命令行中执行以下语句即可(这些操作要求ubuntu有桌面环境):
1 gsettings set org.gnome.Vino require-encryption false
实际测试代码性能时,为了避免由于桌面占用GPU/CPU影响系统性能,可能使用以下命令禁用桌面
1 sudo systemctl disable lightdm.service
需要启用桌面时使用以下命令:
1 sudo systemctl disable lightdm.service
编译OpenCV 下载OpenCV,可以通过git获取官方最新的版本,然后切换到自己所需要的2.4.13进行编译:
1 2 3 git clone https://github.com/opencv/opencv.git cd opencv git checkout 2.4.13.2
或者直接通过wget下载官方最新2.4版的包并解压(记得提前安装unzip):
1 2 wget https://github.com/Itseez/opencv/archive/2.4.13.zip unzip 2.4.13
为了避免由于OpenCV版对最新CUDA的不兼容,这里选技通过git仓库安装 进入到解压后的OpenCV根目录,创建一个build文件夹,然后进入build文件后执行以下编译代码,注意编译选项上包含了CUDA的支持,NVCUVID的支持,OpenGL的支持,以及对ffmpeg的支持。 cmake选项:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 cmake \ -D CMAKE_BUILD_TYPE=RELEASE \ -D CMAKE_INSTALL_PREFIX=/usr/local \ -D WITH_CUDA=ON \ -D WITH_CUBLAS=ON \ -D CUDA_FAST_MATH=ON \ -D WITH_CUFFT=ON \ -D WITH_NVCUVID=ON \ -D WITH_V4L=ON \ -D WITH_LIBV4L=ON \ -D WITH_OPENGL=ON \ -D WITH_FFMPEG=ON \ -D INSTALL_C_EXAMPLES=ON \ -D BUILD_EXAMPLES=ON \ ..
更多cmake选项可以查看OpenCV源码目录下的CMakeLists.txt文件内容。如果需要添加对java的支持,需要添加选项-D BUILD_SHARED_LIBS=OFF \
如果你之前的CUDA、支持CUDA、NVCUVID、NVENC的FFmpeg以及opengl编译安装的都没有问题的话,输出应该如下:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 -- Linker flags (Release): -- Linker flags (Debug): -- ccache: NO -- Precompiled headers: YES -- -- OpenCV modules: -- To be built: core flann imgproc highgui features2d calib3d ml video legacy objdetect photo gpu ocl nonfree contrib python stitching superres ts videostab -- Disabled: world -- Disabled by dependency: - -- Unavailable: androidcamera dynamicuda java viz -- -- GUI: -- QT: NO -- GTK+ 2.x: YES (ver 2.24.30) -- GThread : YES (ver 2.48.2) -- GtkGlExt: YES (ver 1.2.0) -- OpenGL support: YES (/usr/lib/x86_64-linux-gnu/libGLU.so /usr/lib/x86_64-linux-gnu/libGL.so) -- VTK support: NO -- -- Media I/O: -- ZLib: /usr/lib/x86_64-linux-gnu/libz.so (ver 1.2.8) -- JPEG: /usr/lib/x86_64-linux-gnu/libjpeg.so (ver ) -- PNG: /usr/lib/x86_64-linux-gnu/libpng.so (ver 1.2.54) -- TIFF: /usr/lib/x86_64-linux-gnu/libtiff.so (ver 42 - 4.0.6) -- JPEG 2000: /usr/lib/x86_64-linux-gnu/libjasper.so (ver 1.900.1) -- OpenEXR: /usr/lib/x86_64-linux-gnu/libImath.so /usr/lib/x86_64-linux-gnu/libIlmImf.so /usr/lib/x86_64-linux-gnu/libIex.so /usr/lib/x86_64-linux-gnu/libHalf.so /usr/lib/x86_64-linux-gnu/libIlmThread.so (ver 2.2.0) -- -- Video I/O: -- DC1394 1.x: NO -- DC1394 2.x: YES (ver 2.2.4) -- FFMPEG: YES -- avcodec: YES (ver 56.60.100) -- avformat: YES (ver 56.40.101) -- avutil: YES (ver 54.31.100) -- swscale: YES (ver 3.1.101) -- avresample: NO -- GStreamer: -- base: YES (ver 0.10.36) -- video: YES (ver 0.10.36) -- app: YES (ver 0.10.36) -- riff: YES (ver 0.10.36) -- pbutils: YES (ver 0.10.36) -- OpenNI: NO -- OpenNI PrimeSensor Modules: NO -- PvAPI: NO -- GigEVisionSDK: NO -- UniCap: NO -- UniCap ucil: NO -- V4L/V4L2: Using libv4l1 (ver 1.10.0) / libv4l2 (ver 1.10.0) -- XIMEA: NO -- Xine: NO -- -- Other third-party libraries: -- Use IPP: NO -- Use Eigen: NO -- Use TBB: NO -- Use OpenMP: NO -- Use GCD NO -- Use Concurrency NO -- Use C=: NO -- Use Cuda: YES (ver 8.0) -- Use OpenCL: YES -- -- NVIDIA CUDA -- Use CUFFT: YES -- Use CUBLAS: YES -- USE NVCUVID: YES -- NVIDIA GPU arch: 20 21 30 35 -- NVIDIA PTX archs: 30 -- Use fast math: YES -- Tiny gpu module: NO -- -- OpenCL: -- Version: dynamic -- Include path: /home/dutoeserver/OpenCV/opencv_git/3rdparty/include/opencl/1.2 -- Use AMD FFT: NO -- Use AMD BLAS: NO -- -- Python: -- Interpreter: /usr/bin/python2 (ver 2.7.12) -- Libraries: /usr/lib/x86_64-linux-gnu/libpython2.7.so (ver 2.7.12) -- numpy: /usr/lib/python2.7/dist-packages/numpy/core/include (ver 1.11.0) -- packages path: lib/python2.7/dist-packages -- -- Java: -- ant: NO -- JNI: NO -- Java tests: NO -- -- Documentation: -- Build Documentation: NO -- Sphinx: NO -- PdfLaTeX compiler: NO -- Doxygen: NO -- -- Tests and samples: -- Tests: YES -- Performance tests: YES -- C/C++ Examples: YES -- -- Install path: /usr/local -- -- cvconfig.h is in: /home/dutoeserver/OpenCV/opencv_git/build -- ----------------------------------------------------------------- -- -- Configuring done -- Generating done -- Build files have been written to: /home/dutoeserver/OpenCV/opencv_git/build
从中可以看到我们所添加的编译选项后面都有YES 下面使用make进行编译:
1 make -j $(($(nproc) + 1))
然后遍是漫长的编译过程,如果没有问题的话,编译会顺利进行。 然后使用make进行安装并配置环境:
1 2 3 sudo make install sudo /bin/bash -c 'echo "/usr/local/lib" > /etc/ld.so.conf.d/opencv.conf' sudo ldconfig
建议上述安装完成之后重启一次系统
可以将上面sudo make install
部分换成sudo checkinstall
,这样安装完成之后checkinstall会在当前目录生成一个相应的deb,可以二次安装,也可以用sudo dpkg -r xx.deb来卸载 更多checkinstall的用法可以参见IBM的一篇文章:http://www.ibm.com/developerworks/cn/linux/l-cn-checkinstall/
验证 找到OpenCV源代码文件夹下的samples/gpu
里面有很多gpu的示例代码,这里以其中的hog.cpp为例,它的功能就是利用方向梯度直方图(Histogram of oriented gradient)进行目标检测 将该代码单独拷贝到一个文件中,并在该文件夹下创建CMakeLists.txt
,内容如下:
1 2 3 4 5 cmake_minimum_required (VERSION 2.8 )project (HOG)find_package (OpenCV REQUIRED)add_executable (hog hog.cpp)target_link_libraries (hog ${OpenCV_LIBS} )
然后执行编译:
1 2 3 4 mkdir build cd build cmake -D CUDA_USE_STATIC_CUDA_RUNTIME=OFF .. make
如果环境配置没有问题的话,build文件下就会生成可执行的程序hog,可以通过hog --help
查看帮助,下面使用hog来播放视频,或者也可以直接接摄像头:
1 ./hog --video ~/input.mp4
输出结果如下:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 Device 0: "GeForce GTX 1080" 8112Mb, sm_61, Driver/Runtime ver.8.0/8.0 Controls: ESC - exit m - change mode GPU <-> CPU g - convert image to gray or not 1/q - increase/decrease HOG scale 2/w - increase/decrease levels count 3/e - increase/decrease HOG group threshold 4/r - increase/decrease hit threshold Scale: 1.05 Group threshold: 8 Levels number: 13 Win width: 48 Win stride: (8, 8) Hit threshold: 1.4 Gamma correction: 1
可以通过m键来切换使用CPU mode或者CUDA mode。 可以打开nvidia-setting来查看CUDA mode下GPU的占用情况
可能出现的错误 如果出现NVCUVID后面是NO,而CUDA后面是YES 如果出现NVCUVID后面是NO,而CUDA后面是YES 这种情况下将无法使用CUDA编解码功能,这是由于cmake在查找库的时候采用的路径是/usr/lib
以及/usr/lib/nvidia-current
路径,而实际上我的nvidia显卡驱动安装路径为/usr/lib/nvidia-378
,所以导致无法找到这个路径。 PS:为了解决这个问题,查看了opencv的cmake中的相关代码后才发现,但在些之前搜索了很久,也乱试了很久都无果,所以一定要有根据的解决问题,还不是盲目地去试。 解决:
1 2 sudo ln -s /usr/lib/nvidia-378/libnvcuvid.so /usr/lib/libnvcuvid.so sudo ln -s /usr/lib/nvidia-378/libnvcuvid.so.1 /usr/lib/libnvcuvid.so.1
记得修改成你自己的nvidia驱动安装路径
如果FFmpeg没有YES 可能是你的FFmpeg编译后没有将其添加到环境变量中。
cannot find -lopencv_dep_cudart 错误详情:
1 2 3 4 5 6 7 8 /usr/bin/ld: cannot find -lopencv_dep_cudart collect2: error: ld returned 1 exit status CMakeFiles/hog.dir/build.make:120: recipe for target 'hog' failed make[2]: *** [hog] Error 1 CMakeFiles/Makefile2:67: recipe for target 'CMakeFiles/hog.dir/all' failed make[1]: *** [CMakeFiles/hog.dir/all] Error 2 Makefile:83: recipe for target 'all' failed make: *** [all] Error 2
添加cmake编译选项来解决:
1 cmake -D CUDA_USE_STATIC_CUDA_RUNTIME=OFF ..
Exception in thread “main” java.lang.NoClassDefFoundError: org/opencv/core/Core 如果需要配置java调用opencv,需要修改如下配置文件:
1 2 export CLASSPATH=.:$JAVA_HOME/lib:$JRE_HOME/lib:/usr/local/share/OpenCV/java/opencv-2413.jar export LD_LIBRARY_PATH=/usr/local/lib/:/usr/lib/:/usr/local/share/OpenCV/java:$LD_LIBRARY_PATH