海思平台OpenCV编译与进一步裁剪

海思平台OpenCV编译与进一步裁剪 outman 2024-02-04 10:09:10 875

OpenCV是计算机视觉算法开发常用的工具。如果我们需要在嵌入式设备上运行opencv,那么就需要交叉编译,将它移植到对应平台上。但是有些嵌入式平台的存储空间有限,能节省1MB也有相当大的作用。OpenCV带了很多用不到的东西,如果对OpenCV做裁剪,可以节省不少空间。现在将opencv移植到海思的3516DV300/CV500平台。

准备工作

1.下载源码
https://opencv.org/releases/下载OpenCV的源码包,我这里用的是3.4.10。
准备交叉编译器
2.需要提前安装好海思的交叉编译器,并配置到环境变量。
3.安装cmake
ubuntu/deepin/debian系统下直接apt install cmake make即可。

如何编译?

参考网上的教程,要用cmake-gui来配置,但是,实际上编译用cmake命令行,指定交叉编译器,然后配置一些目标平台的参数就可以了。
首先解压源码包,然后创建build和output文件夹,用来进行编译以及保存编译好的库。

unzip opencv-3.4.10
cd opencv-3.4.10
mkdir output build
cd build

然后使用cmake进行编译。这里指定交叉编译器,然后配置输出文件夹为上面创建的…/output。由于是嵌入式平台,没有gtk之类的图形库,所以选择WITH_GTK=OFF。OpenCV默认调用系统的zlib,在嵌入式平台上,需要重新编译,所以添加选项BUILD_ZLIB=ON和OPENCV_FORCE_3RDPARTY_BUILD=ON。

cmake ../ \
-DCMAKE_C_COMPILER=arm-himix200-linux-gcc \
-DCMAKE_CXX_COMPILER=arm-himix200-linux-g++ \
-DOPENCV_FORCE_3RDPARTY_BUILD=ON \
-DBUILD_ZLIB=ON \
-DWITH_GTK=OFF \
-DBUILD_SHARED_LIBS=ON \
-DCMAKE_BUILD_TYPE=RELEASE \
-DCMAKE_INSTALL_PREFIX=../output

等待cmake执行完成后,就可以进行编译了。使用make -j && make install命令,完成编译以,并把编译好的库存到指定位置。

进行裁剪

这里为了展示编译效果,替换掉make,使用ninja build来进行编译,因为ninja build可以显示出需要编译的文件的数量,而make只显示编译的百分比。

ninja build

cmake build

实际上效果是相同的。cmake只是一个编译信息生成工具,真正执行编译的是make或者ninja build。使用时,cmake添加-GNinja参数即可生成ninja build所需要的文件,然后就可以用ninja 来进行编译了。下面会使用cmake + ninja build的方式来进行编译,实际使用cmake + make也可以。 从ninja build的截图可以看到,需要处理(编译、链接)1283个对象(包括源码、编译中间产物.o),生成22MB的库文件。

a.裁剪不需要的OpenCV组件

裁剪掉不需要的组件是最简单的方法。先看下opencv包含了什么东西。

opencv

通常,在嵌入式端,比如海思这种芯片,有对视频解码的硬件,而这种平台CPU性能并不强,所以OpenCV关于视频解码的部分,可以完全干掉。在海思上,有深度学习推理硬件NNIE,所以OpenCV的机器学习、深度学习的模块也可以干掉。opencv_highgui是用来显示图像的,在海思平台,没有这种图像显示的设备,关于显示是用海思专门的模块实现的,所以highgui也干掉。 实际上,一般在海思平台开发有关NNIE的应用,用OpenCV最多的就是其中数据表示方式,比如cv::Mat、cv::Rect之类的,还有一些图像处理的功能。此外,在测试时,也可能对图像做读写操作。所以,这里我只留下了opencv_core、opencv_imgproc、opencv_imgcodecs这三个模块。至于opencv_superres、opencv_feature2d等模块,可以按需保留,但是又有多少人会在嵌入式端用CPU来做超分辨、图像特征点这些事呢? 所以,按照上面裁剪的方法,写出cmake命令。

cmake ../ \
-DCMAKE_C_COMPILER=arm-himix200-linux-gcc \
-DCMAKE_CXX_COMPILER=arm-himix200-linux-g++ \
-DOPENCV_FORCE_3RDPARTY_BUILD=ON \
-DBUILD_ZLIB=ON \
-DWITH_GTK=OFF \
-DBUILD_SHARED_LIBS=ON \
-DBUILD_opencv_ts=OFF \
-DBUILD_opencv_shape=OFF \
-DBUILD_opencv_stitching=OFF \
-DBUILD_opencv_apps=OFF \
-DBUILD_opencv_calib3d=OFF \
-DBUILD_opencv_dnn=OFF \
-DBUILD_opencv_features2d=OFF \
-DBUILD_opencv_flann=OFF \
-DBUILD_opencv_highgui=OFF \
-DBUILD_opencv_ml=OFF \
-DBUILD_opencv_objdetect=OFF \
-DBUILD_opencv_photo=OFF \
-DBUILD_opencv_video=OFF \
-DBUILD_opencv_videoio=OFF \
-DBUILD_opencv_videostab=OFF \
-DCMAKE_BUILD_TYPE=RELEASE \
-DCMAKE_INSTALL_PREFIX=../output

可以看到,现在只需处理601个文件,比之前少了一半多,而OpenCV的库也只要9.9MB

第一次裁剪的结果
b.继续裁剪opencv 在编译选项里,可以看到,还有很多WITH_XXX的编译选项,这些也有很多不需要,来删一点点干掉。


以上是需要被干掉的一些东西。部分的解释可能不准确,如有问题请指正。在海思这种平台,图像最常用的格式YUV、BGR(RGB)格式,还有压缩过的jpg/jpeg格式,以及未经过压缩的bmp格式。以上配置,可以按照个人需要来进行设置。以上的cmake命令如下:

cmake ../ \
-DCMAKE_C_COMPILER=arm-himix200-linux-gcc \
-DCMAKE_CXX_COMPILER=arm-himix200-linux-g++ \
-DOPENCV_FORCE_3RDPARTY_BUILD=ON \
-DBUILD_ZLIB=ON \
-DWITH_GTK=OFF \
-DWITH_GTK=OFF \
-DWITH_GTK_2_X=OFF \
-DWITH_CUDA=OFF \
-DWITH_IPP=OFF \
-DWITH_OPENCL=OFF \
-DWITH_OPENCLAMDBLAS=OFF \
-DWITH_QUIRC=OFF \
-DWITH_OPENCLAMDFFT=OFF \
-DWITH_1394=OFF \
-DWITH_FFMPEG=OFF \
-DWITH_WEBP=OFF \
-DWITH_TIFF=OFF \
-DWITH_OPENEXR=OFF \
-DWITH_PNG=OFF \
-DWITH_PROTOBUF=OFF \
-DWITH_GSTREAMER=OFF \
-DWITH_IMGCODEC_SUNRASTER=OFF \
-DBUILD_SHARED_LIBS=ON \
-DBUILD_opencv_ts=OFF \
-DBUILD_opencv_shape=OFF \
-DBUILD_opencv_stitching=OFF \
-DBUILD_opencv_apps=OFF \
-DBUILD_opencv_calib3d=OFF \
-DBUILD_opencv_dnn=OFF \
-DBUILD_opencv_features2d=OFF \
-DBUILD_opencv_flann=OFF \
-DBUILD_opencv_highgui=OFF \
-DBUILD_opencv_ml=OFF \
-DBUILD_opencv_objdetect=OFF \
-DBUILD_opencv_photo=OFF \
-DBUILD_opencv_video=OFF \
-DBUILD_opencv_videoio=OFF \
-DBUILD_opencv_videostab=OFF \
-DCMAKE_BUILD_TYPE=RELEASE \
-DCMAKE_INSTALL_PREFIX=../output

以上配置,需要处理的文件数量以及生成的库的大小如下图:

现在可以看到,opencv已经被压缩到很小了。

c.还能不能再小?

已经完成了opencv的裁剪,现在已经是裁剪到不能再裁剪了,那么能不能再让它变小点呢?能,当然能!这时候就要从编译器的角度来看了。

我们使用file命令来看下编译产物。这里,我们可以看到,这个是arm平台下的动态库,是not stripped的。这也就是说,这里包含符号表、重定位信息等多余的东西。
我们再看编译选项-s和-Os

-s是链接器的选项,是在链接时删除所有的符号表等信息,实际使用的时候,传给链接器ld,当然传给gcc/g++也可以实现相同功能,-Os是针对体积进行优化。所以,在编译的时候,设置编译选项为-s -Os,就可以达到目的。现在,cmake命令如下:

cmake ../ \
-DCMAKE_C_COMPILER=arm-himix200-linux-gcc \
-DCMAKE_CXX_COMPILER=arm-himix200-linux-g++ \
-DOPENCV_FORCE_3RDPARTY_BUILD=ON \
-DBUILD_ZLIB=ON -DWITH_GTK=OFF -DWITH_GTK=OFF \
-DWITH_GTK_2_X=OFF -DWITH_CUDA=OFF -DWITH_IPP=OFF \
-DWITH_OPENCL=OFF -DWITH_OPENCLAMDBLAS=OFF \
-DWITH_QUIRC=OFF -DWITH_OPENCLAMDFFT=OFF \
-DWITH_1394=OFF -DWITH_FFMPEG=OFF -DWITH_WEBP=OFF \
-DWITH_TIFF=OFF -DWITH_OPENEXR=OFF -DWITH_PNG=OFF \
-DWITH_PROTOBUF=OFF -DWITH_GSTREAMER=OFF -DWITH_IMGCODEC_SUNRASTER=OFF \
-DBUILD_SHARED_LIBS=ON -DBUILD_opencv_ts=OFF \
-DBUILD_opencv_shape=OFF -DBUILD_opencv_stitching=OFF \
-DBUILD_opencv_apps=OFF -DBUILD_opencv_calib3d=OFF \
-DBUILD_opencv_dnn=OFF -DBUILD_opencv_features2d=OFF \
-DBUILD_opencv_flann=OFF -DBUILD_opencv_highgui=OFF \
-DBUILD_opencv_ml=OFF -DBUILD_opencv_objdetect=OFF \
-DBUILD_opencv_photo=OFF -DBUILD_opencv_video=OFF \
-DBUILD_opencv_videoio=OFF -DBUILD_opencv_videostab=OFF \
-DCMAKE_BUILD_TYPE=RELEASE \
-DCMAKE_INSTALL_PREFIX=../output \
-DCMAKE_CXX_FLAGS="-s -Os" -DCMAKE_C_FLAGS="-s -Os"

在命令行中指定编译选项,cmake会自动把这些选项与cmake生成的选项合并。

执行编译,和上面相同,需要处理283个文件。看下生成的文件:

现在已经是stripped的了。然后现在生成的库的只剩了5.2MB的大小,相比之前,小了非常多。

结束

在某些嵌入式设备上,存储空间非常紧张,通过这样的方法以及思路可以节省不少的存储空间。以上编译opencv的命令如下,直接复制粘贴了执行就可以,当然也可以替换了交叉编译器,来编译不同平台的库。

 cmake ../ \
-DCMAKE_C_COMPILER=arm-himix200-linux-gcc \
-DCMAKE_CXX_COMPILER=arm-himix200-linux-g++ \
-DOPENCV_FORCE_3RDPARTY_BUILD=ON \
-DBUILD_ZLIB=ON \
-DWITH_GTK=OFF \
-DENABLE_NEON=OFF \
-DWITH_GTK_2_X=OFF \
-DWITH_CUDA=OFF \
-DWITH_IPP=OFF \
-DWITH_OPENCL=OFF \
-DWITH_OPENCLAMDBLAS=OFF \
-DWITH_QUIRC=OFF \
-DWITH_OPENCLAMDFFT=OFF \
-DWITH_1394=OFF \
-DWITH_FFMPEG=OFF \
-DWITH_WEBP=OFF \
-DWITH_TIFF=OFF \
-DWITH_OPENEXR=OFF \
-DWITH_PNG=OFF \
-DWITH_PROTOBUF=OFF \
-DWITH_GSTREAMER=OFF \
-DWITH_IMGCODEC_SUNRASTER=OFF \
-DBUILD_SHARED_LIBS=ON \
-DBUILD_opencv_ts=OFF \
-DBUILD_opencv_shape=OFF \
-DBUILD_opencv_stitching=OFF \
-DBUILD_opencv_apps=OFF \
-DBUILD_opencv_calib3d=OFF \
-DBUILD_opencv_dnn=OFF \
-DBUILD_opencv_features2d=OFF \
-DBUILD_opencv_flann=OFF \
-DBUILD_opencv_highgui=OFF \
-DBUILD_opencv_ml=OFF \
-DBUILD_opencv_objdetect=OFF \
-DBUILD_opencv_photo=OFF \
-DBUILD_opencv_video=OFF \
-DBUILD_opencv_videoio=OFF \
-DBUILD_opencv_videostab=OFF \
-DBUILD_opencv_world=ON \
-DBUILD_opencv_python2=OFF \
-DBUILD_opencv_python3=OFF \
-DBUILD_opencv_python_bindings_generator=OFF \
-DBUILD_DOCS=OFF\
-DCMAKE_BUILD_TYPE=RELEASE \
-DCMAKE_INSTALL_PREFIX=../output \
-DCMAKE_CXX_FLAGS="-s -Os" \
-DCMAKE_C_FLAGS="-s -Os"
声明:本文内容由易百纳平台入驻作者撰写,文章观点仅代表作者本人,不代表易百纳立场。如有内容侵权或者其他问题,请联系本站进行删除。
outman
红包 点赞 收藏 评论 打赏
评论
0个
内容存在敏感词
手气红包
    易百纳技术社区暂无数据
相关专栏
置顶时间设置
结束时间
删除原因
  • 广告/SPAM
  • 恶意灌水
  • 违规内容
  • 文不对题
  • 重复发帖
打赏作者
易百纳技术社区
outman
您的支持将鼓励我继续创作!
打赏金额:
¥1易百纳技术社区
¥5易百纳技术社区
¥10易百纳技术社区
¥50易百纳技术社区
¥100易百纳技术社区
支付方式:
微信支付
支付宝支付
易百纳技术社区微信支付
易百纳技术社区
打赏成功!

感谢您的打赏,如若您也想被打赏,可前往 发表专栏 哦~

举报反馈

举报类型

  • 内容涉黄/赌/毒
  • 内容侵权/抄袭
  • 政治相关
  • 涉嫌广告
  • 侮辱谩骂
  • 其他

详细说明

审核成功

发布时间设置
发布时间:
是否关联周任务-专栏模块

审核失败

失败原因
备注
拼手气红包 红包规则
祝福语
恭喜发财,大吉大利!
红包金额
红包最小金额不能低于5元
红包数量
红包数量范围10~50个
余额支付
当前余额:
可前往问答、专栏板块获取收益 去获取
取 消 确 定

小包子的红包

恭喜发财,大吉大利

已领取20/40,共1.6元 红包规则

    易百纳技术社区