August 3, 2016
作者:dengshuai_super
出处:http://blog.csdn.net/dengshuai_super/article/details/52069634
声明:转载请注明作者及出处。
注意⚠️:此问题还不算解决,只是暂时用了别人的库,以后解决了,会回来记录。因为我是做笔记,所以建议大家直接看文章最后。
Opencv3.1.0 , Ubuntu16.04 ,开发板Microzed和Zedboard都试过了,出现同样问题。
charVec size:101
file /home/ds/build/opencv-3.1.0/modules/core/src/persistence.cpp, line 2197 terminate called after throwing an instance of 'cv::Exception'
what():/home/ds/build/opencv-3.1.0/modules/core/src/persistence.cpp:2197:error:(-212) /mnt/PRTest/resources/model/ann.xml(1):
There should be space between attributes in function icvXMLParseTag
http://www.th7.cn/Program/cp/201605/851893.shtml
/** @brief Loads algorithm from the file
@param filename Name of the file to read.
@param objname The optional name of the node to read (if empty, the first top-level node will be used)
This is static template method of Algorithm. It's usage is following (in the case of SVM):
@code
Ptr svm = Algorithm::load("my_svm_model.xml");
@endcode
In order to make this method work, the derived class must overwrite Algorithm::read(const
FileNode& fn).
*/
template static Ptr<_Tp> load(const String& filename, const String& objname=String())
{
FileStorage fs(filename, FileStorage::READ);
FileNode fn = objname.empty() ? fs.getFirstTopLevelNode() : fs[objname];
Ptr<_Tp> obj = _Tp::create();
obj->read(fn);
return !obj->empty() ? obj : Ptr<_Tp>();
}
/** @brief Reads algorithm parameters from a file storage
*/
virtual void read(const FileNode& fn) { (void)fn; }
/** @brief Reads algorithm from the file node
This is static template method of Algorithm. It's usage is following (in the case of SVM):
@code
Ptr svm = Algorithm::read(fn);
@endcode
In order to make this method work, the derived class must overwrite Algorithm::read(const
FileNode& fn) and also have static create() method without parameters
(or with all the optional parameters)
*/
template static Ptr<_Tp> read(const FileNode& fn)
{
Ptr<_Tp> obj = _Tp::create();
obj->read(fn);
return !obj->empty() ? obj : Ptr<_Tp>();
}
http://stackoverflow.com/questions/25831111/opencv-traincascade-build-intermediate-result/26301531#26301531
Ubuntu 里面:/home/ds/桌面/EasyPR-master/resources/model/ann.xml
<!opencv_storage>
<opencv_ml_ann_mlp>
<format>3format>
<layer_sizes>120 40 65layer_sizes>
<activation_function>SIGMOID_SYMactivation_function>
<f_param1>1.f_param1>
<f_param2>1.f_param2>
我故意把第二行加了一个”!”,Ubuntu里运行程序:出现:
OpenCV Error: Parsing error (resources/model/ann.xml(2):
file /home/ds/opencv-3.1.0/modules/core/src/persistence.cpp,
line 2249 terminate called after throwing an instance of 'cv::Exception'
what(): /home/ds/opencv-3.1.0/modules/core/src/persistence.cpp:2249:
error: (-212) resources/model/ann.xml(2):
tag is missing in function icvXMLParse
在已经做好opencv移植的arm linux里面运行,出现:
OpenCV Error: Parsing error (resources/model/ann.xml(1):
There should be space between attributes) in icvXMLParseTag,
file /home/ds/build/opencv-3.1.0/modules/core/src/persistence.cpp, line 2197 what():
/home/ds/build/opencv-3.1.0/modules/core/src/persistence.cpp:2197: error: (-212) resources/model/ann.xml(1):
There should be space between attributes in function icvXMLParseTag
然后我只把ann.xml 的第一行改为
在arm linux 报错和Ubuntu 上一样:
OpenCV Error: Parsing error (resources/model/ann.xml(1): Attribute name should be followed by '=') in icvXMLParseTag,
file /home/ds/build/opencv-3.1.0/modules/core/src/persistence.cpp,
line 2149 terminate called after throwing an instance of 'cv::Exception' what():
/home/ds/build/opencv-3.1.0/modules/core/src/persistence.cpp:2149:
error: (-212) resources/model/ann.xml(1): Attribute name should be followed by '=' in function icvXMLParseTag
我把ann.xml 的第一行改为
arm linux显示错误:
OpenCV Error: Parsing error (resources/model/ann.xml(1):
There should be space between attributes) in icvXMLParseTag,
file /home/ds/build/opencv-3.1.0/modules/core/src/persistence.cpp,
line 2197 terminate called after throwing an instance of 'cv::Exception' what(): /home/ds/build/opencv-3.1.0/modules/core/src/persistence.cpp:2197:
error: (-212) resources/model/ann.xml(1):
There should be space between attributes in function icvXMLParseTag
结果arm上没检测出最右边?的问题,Ubuntu检测出来了。
于是我用opencv官方的例子人脸识别的那个(FaceDetection),在Ubuntu上可以顺利跑起来,移植到arm 上之后,出现了同样的问题:
WARNING: Could not load classifier cascade for nested objects OpenCV Error:
There should be space between attributes) in icvXMLParseTag,
file /home/ds/build/opencv3.1.0/modules/core/src/persistence.cpp, line 2197
terminate called after throwing an instance of 'cv::Exception'
what(): /home/ds/build/opencv-3.1.0/modules/core/src/persistence.cpp:2197: error: (-212) haarcascade_frontalface_alt.xml(1):
There should be space between attributes in function icvXMLParseTag
Aborted
说明这是通性的问题,正确的在Ubuntu上可以用的xml,移植到开发板上的arm linux里面时,就会出现
There should be space between attributes in function icvXMLParseTag
的问题。
开始时我怀疑是缺少libxml2库的问题导致了解析失败:(其实后来发现opencv是用自己的解析函数来解析xml)
于是我用ldd命令看Ubuntu程序链接了哪些库:
其中发现了xml2
ldd demo_linux_amd64
打印出:
linux-vdso.so.1 => (0x00007ffdeb3b3000)
`libopencv_world.so.3.1 => /usr/local/lib/libopencv_world.so.3.1 (0x00007f62e0ffe000)
libstdc++.so.6 => /usr/lib/x86_64-linux-gnu/libstdc++.so.6 (0x00007f62e0c61000)
libm.so.6 => /lib/x86_64-linux-gnu/libm.so.6 (0x00007f62e0957000)
libgcc_s.so.1 => /lib/x86_64-linux-gnu/libgcc_s.so.1 (0x00007f62e0741000)
libc.so.6 => /lib/x86_64-linux-gnu/libc.so.6 (0x00007f62e0378000)
libz.so.1 => /lib/x86_64-linux-gnu/libz.so.1 (0x00007f62e015d000)
libdl.so.2 => /lib/x86_64-linux-gnu/libdl.so.2 (0x00007f62dff59000)
libpthread.so.0 => /lib/x86_64-linux-gnu/libpthread.so.0 (0x00007f62dfd3c000)
librt.so.1 => /lib/x86_64-linux-gnu/librt.so.1 (0x00007f62dfb33000)
libpng12.so.0 => /lib/x86_64-linux-gnu/libpng12.so.0 (0x00007f62df90e000)`
libgtk-3.so.0 => /usr/lib/x86_64-linux-gnu/libgtk-3.so.0 (0x00007f62defdf000)
libgdk-3.so.0 => /usr/lib/x86_64-linux-gnu/libgdk-3.so.0 (0x00007f62ded03000)
libcairo.so.2 => /usr/lib/x86_64-linux-gnu/libcairo.so.2 (0x00007f62de9ef000)
libgdk_pixbuf-2.0.so.0 => /usr/lib/x86_64-linux-gnu/libgdk_pixbuf-2.0.so.0 (0x00007f62de7cd000)
libgobject-2.0.so.0 => /usr/lib/x86_64-linux-gnu/libgobject-2.0.so.0 (0x00007f62de579000)
`libglib-2.0.so.0 => /lib/x86_64-linux-gnu/libglib-2.0.so.0 (0x00007f62de268000)`
libavcodec-ffmpeg.so.56 => /usr/lib/x86_64-linux-gnu/libavcodec-ffmpeg.so.56 (0x00007f62dce3e000)
libavformat-ffmpeg.so.56 => /usr/lib/x86_64-linux-gnu/libavformat-ffmpeg.so.56 (0x00007f62dca40000)
libavutil-ffmpeg.so.54 => /usr/lib/x86_64-linux-gnu/libavutil-ffmpeg.so.54 (0x00007f62dc7d1000)
libswscale-ffmpeg.so.3 => /usr/lib/x86_64-linux-gnu/libswscale-ffmpeg.so.3 (0x00007f62dc542000)
`/lib64/ld-linux-x86-64.so.2 (0x0000561e16755000)`
libgmodule-2.0.so.0 => /usr/lib/x86_64-linux-gnu/libgmodule-2.0.so.0 (0x00007f62dc33d000)
libpangocairo-1.0.so.0 => /usr/lib/x86_64-linux-gnu/libpangocairo-1.0.so.0 (0x00007f62dc130000)
libX11.so.6 => /usr/lib/x86_64-linux-gnu/libX11.so.6 (0x00007f62dbdf5000)
libXi.so.6 => /usr/lib/x86_64-linux-gnu/libXi.so.6 (0x00007f62dbbe5000)
libXfixes.so.3 => /usr/lib/x86_64-linux-gnu/libXfixes.so.3 (0x00007f62db9df000)
libcairo-gobject.so.2 => /usr/lib/x86_64-linux-gnu/libcairo-gobject.so.2 (0x00007f62db7d5000)
libatk-1.0.so.0 => /usr/lib/x86_64-linux-gnu/libatk-1.0.so.0 (0x00007f62db5b0000)
libatk-bridge-2.0.so.0 => /usr/lib/x86_64-linux-gnu/libatk-bridge-2.0.so.0 (0x00007f62db381000)
libepoxy.so.0 => /usr/lib/x86_64-linux-gnu/libepoxy.so.0 (0x00007f62db08b000)
libpangoft2-1.0.so.0 => /usr/lib/x86_64-linux-gnu/libpangoft2-1.0.so.0 (0x00007f62dae75000)
libpango-1.0.so.0 => /usr/lib/x86_64-linux-gnu/libpango-1.0.so.0 (0x00007f62dac29000)
libfontconfig.so.1 => /usr/lib/x86_64-linux-gnu/libfontconfig.so.1 (0x00007f62da9e5000)
libgio-2.0.so.0 => /usr/lib/x86_64-linux-gnu/libgio-2.0.so.0 (0x00007f62da65d000)
libXinerama.so.1 => /usr/lib/x86_64-linux-gnu/libXinerama.so.1 (0x00007f62da459000)
libXrandr.so.2 => /usr/lib/x86_64-linux-gnu/libXrandr.so.2 (0x00007f62da24e000)
libXcursor.so.1 => /usr/lib/x86_64-linux-gnu/libXcursor.so.1 (0x00007f62da044000)
libXcomposite.so.1 => /usr/lib/x86_64-linux-gnu/libXcomposite.so.1 (0x00007f62d9e40000)
libXdamage.so.1 => /usr/lib/x86_64-linux-gnu/libXdamage.so.1 (0x00007f62d9c3d000)
libxkbcommon.so.0 => /usr/lib/x86_64-linux-gnu/libxkbcommon.so.0 (0x00007f62d99fe000)
libwayland-cursor.so.0 => /usr/lib/x86_64-linux-gnu/libwayland-cursor.so.0 (0x00007f62d97f5000)
libwayland-egl.so.1 => /usr/lib/x86_64-linux-gnu/libwayland-egl.so.1 (0x00007f62d95f3000)
libwayland-client.so.0 => /usr/lib/x86_64-linux-gnu/libwayland-client.so.0 (0x00007f62d93e5000)
libmirclient.so.9 => /usr/lib/x86_64-linux-gnu/libmirclient.so.9 (0x00007f62d9163000)
libXext.so.6 => /usr/lib/x86_64-linux-gnu/libXext.so.6 (0x00007f62d8f51000)
libpixman-1.so.0 => /usr/lib/x86_64-linux-gnu/libpixman-1.so.0 (0x00007f62d8ca8000)
libfreetype.so.6 => /usr/lib/x86_64-linux-gnu/libfreetype.so.6 (0x00007f62d89fe000)
libxcb-shm.so.0 => /usr/lib/x86_64-linux-gnu/libxcb-shm.so.0 (0x00007f62d87fa000)
libxcb-render.so.0 => /usr/lib/x86_64-linux-gnu/libxcb-render.so.0 (0x00007f62d85ef000)
libxcb.so.1 => /usr/lib/x86_64-linux-gnu/libxcb.so.1 (0x00007f62d83cd000)
libXrender.so.1 => /usr/lib/x86_64-linux-gnu/libXrender.so.1 (0x00007f62d81c3000)
libffi.so.6 => /usr/lib/x86_64-linux-gnu/libffi.so.6 (0x00007f62d7fba000)
libpcre.so.3 => /lib/x86_64-linux-gnu/libpcre.so.3 (0x00007f62d7d4a000)
libswresample-ffmpeg.so.1 => /usr/lib/x86_64-linux-gnu/libswresample-ffmpeg.so.1 (0x00007f62d7b2d000)
libva.so.1 => /usr/lib/x86_64-linux-gnu/libva.so.1 (0x00007f62d7911000)
libzvbi.so.0 => /usr/lib/x86_64-linux-gnu/libzvbi.so.0 (0x00007f62d7686000)
libxvidcore.so.4 => /usr/lib/x86_64-linux-gnu/libxvidcore.so.4 (0x00007f62d7372000)
libx265.so.79 => /usr/lib/x86_64-linux-gnu/libx265.so.79 (0x00007f62d6752000)
libx264.so.148 => /usr/lib/x86_64-linux-gnu/libx264.so.148 (0x00007f62d63ae000)
libwebp.so.5 => /usr/lib/x86_64-linux-gnu/libwebp.so.5 (0x00007f62d6152000)
libwavpack.so.1 => /usr/lib/x86_64-linux-gnu/libwavpack.so.1 (0x00007f62d5f28000)
libvpx.so.3 => /usr/lib/x86_64-linux-gnu/libvpx.so.3 (0x00007f62d5b04000)
libvorbisenc.so.2 => /usr/lib/x86_64-linux-gnu/libvorbisenc.so.2 (0x00007f62d585b000)
libvorbis.so.0 => /usr/lib/x86_64-linux-gnu/libvorbis.so.0 (0x00007f62d562e000)
libtwolame.so.0 => /usr/lib/x86_64-linux-gnu/libtwolame.so.0 (0x00007f62d540b000)
libtheoraenc.so.1 => /usr/lib/x86_64-linux-gnu/libtheoraenc.so.1 (0x00007f62d51cc000)
libtheoradec.so.1 => /usr/lib/x86_64-linux-gnu/libtheoradec.so.1 (0x00007f62d4fb1000)
libspeex.so.1 => /usr/lib/x86_64-linux-gnu/libspeex.so.1 (0x00007f62d4d98000)
libsnappy.so.1 => /usr/lib/x86_64-linux-gnu/libsnappy.so.1 (0x00007f62d4b90000)
libshine.so.3 => /usr/lib/x86_64-linux-gnu/libshine.so.3 (0x00007f62d4982000)
libschroedinger-1.0.so.0 => /usr/lib/x86_64-linux-gnu/libschroedinger-1.0.so.0 (0x00007f62d46ad000)
libopus.so.0 => /usr/lib/x86_64-linux-gnu/libopus.so.0 (0x00007f62d4463000)
`libopenjpeg.so.5 => /usr/lib/x86_64-linux-gnu/libopenjpeg.so.5 (0x00007f62d423f000)`
libmp3lame.so.0 => /usr/lib/x86_64-linux-gnu/libmp3lame.so.0 (0x00007f62d3fca000)
libgsm.so.1 => /usr/lib/x86_64-linux-gnu/libgsm.so.1 (0x00007f62d3dbc000)
libcrystalhd.so.3 => /usr/lib/x86_64-linux-gnu/libcrystalhd.so.3 (0x00007f62d3ba0000)
liblzma.so.5 => /lib/x86_64-linux-gnu/liblzma.so.5 (0x00007f62d397e000)
libssh-gcrypt.so.4 => /usr/lib/x86_64-linux-gnu/libssh-gcrypt.so.4 (0x00007f62d3734000)
librtmp.so.1 => /usr/lib/x86_64-linux-gnu/librtmp.so.1 (0x00007f62d3518000)
libmodplug.so.1 => /usr/lib/x86_64-linux-gnu/libmodplug.so.1 (0x00007f62d318d000)
libgme.so.0 => /usr/lib/x86_64-linux-gnu/libgme.so.0 (0x00007f62d2f3e000)
libbluray.so.1 => /usr/lib/x86_64-linux-gnu/libbluray.so.1 (0x00007f62d2cf5000)
libgnutls.so.30 => /usr/lib/x86_64-linux-gnu/libgnutls.so.30 (0x00007f62d29c5000)
libbz2.so.1.0 => /lib/x86_64-linux-gnu/libbz2.so.1.0 (0x00007f62d27b4000)
libatspi.so.0 => /usr/lib/x86_64-linux-gnu/libatspi.so.0 (0x00007f62d2585000)
libdbus-1.so.3 => /lib/x86_64-linux-gnu/libdbus-1.so.3 (0x00007f62d2338000)
libharfbuzz.so.0 => /usr/lib/x86_64-linux-gnu/libharfbuzz.so.0 (0x00007f62d20da000)
libthai.so.0 => /usr/lib/x86_64-linux-gnu/libthai.so.0 (0x00007f62d1ed0000)
libexpat.so.1 => /lib/x86_64-linux-gnu/libexpat.so.1 (0x00007f62d1ca7000)
libselinux.so.1 => /lib/x86_64-linux-gnu/libselinux.so.1 (0x00007f62d1a85000)
libresolv.so.2 => /lib/x86_64-linux-gnu/libresolv.so.2 (0x00007f62d186a000)
libmircommon.so.5 => /usr/lib/x86_64-linux-gnu/libmircommon.so.5 (0x00007f62d1638000)
libmirprotobuf.so.3 => /usr/lib/x86_64-linux-gnu/libmirprotobuf.so.3 (0x00007f62d13d7000)
libboost_system.so.1.58.0 => /usr/lib/x86_64-linux-gnu/libboost_system.so.1.58.0 (0x00007f62d11d2000)
libprotobuf-lite.so.9 => /usr/lib/x86_64-linux-gnu/libprotobuf-lite.so.9 (0x00007f62d0fa1000)
libXau.so.6 => /usr/lib/x86_64-linux-gnu/libXau.so.6 (0x00007f62d0d9c000)
libXdmcp.so.6 => /usr/lib/x86_64-linux-gnu/libXdmcp.so.6 (0x00007f62d0b96000)
libsoxr.so.0 => /usr/lib/x86_64-linux-gnu/libsoxr.so.0 (0x00007f62d0931000)
libnuma.so.1 => /usr/lib/x86_64-linux-gnu/libnuma.so.1 (0x00007f62d0725000)
libogg.so.0 => /usr/lib/x86_64-linux-gnu/libogg.so.0 (0x00007f62d051c000)
liborc-0.4.so.0 => /usr/lib/x86_64-linux-gnu/liborc-0.4.so.0 (0x00007f62d029b000)
libgcrypt.so.20 => /lib/x86_64-linux-gnu/libgcrypt.so.20 (0x00007f62cffba000)
libgssapi_krb5.so.2 => /usr/lib/x86_64-linux-gnu/libgssapi_krb5.so.2 (0x00007f62cfd6f000)
libhogweed.so.4 => /usr/lib/x86_64-linux-gnu/libhogweed.so.4 (0x00007f62cfb3c000)
libnettle.so.6 => /usr/lib/x86_64-linux-gnu/libnettle.so.6 (0x00007f62cf906000)
libgmp.so.10 => /usr/lib/x86_64-linux-gnu/libgmp.so.10 (0x00007f62cf685000)
`libxml2.so.2 => /usr/local/lib/libxml2.so.2 (0x00007f62cf31e000)`
libp11-kit.so.0 => /usr/lib/x86_64-linux-gnu/libp11-kit.so.0 (0x00007f62cf0b8000)
libidn.so.11 => /usr/lib/x86_64-linux-gnu/libidn.so.11 (0x00007f62cee85000)
libtasn1.so.6 => /usr/lib/x86_64-linux-gnu/libtasn1.so.6 (0x00007f62cec72000)
libsystemd.so.0 => /lib/x86_64-linux-gnu/libsystemd.so.0 (0x00007f62cebec000)
libgraphite2.so.3 => /usr/lib/x86_64-linux-gnu/libgraphite2.so.3 (0x00007f62ce9c7000)
libdatrie.so.1 => /usr/lib/x86_64-linux-gnu/libdatrie.so.1 (0x00007f62ce7bf000)
libboost_filesystem.so.1.58.0 => /usr/lib/x86_64-linux-gnu/libboost_filesystem.so.1.58.0 (0x00007f62ce5a6000)
libgomp.so.1 => /usr/lib/x86_64-linux-gnu/libgomp.so.1 (0x00007f62ce384000)
libgpg-error.so.0 => /lib/x86_64-linux-gnu/libgpg-error.so.0 (0x00007f62ce16f000)
libkrb5.so.3 => /usr/lib/x86_64-linux-gnu/libkrb5.so.3 (0x00007f62cde9d000)
libk5crypto.so.3 => /usr/lib/x86_64-linux-gnu/libk5crypto.so.3 (0x00007f62cdc6e000)
libcom_err.so.2 => /lib/x86_64-linux-gnu/libcom_err.so.2 (0x00007f62cda69000)
libkrb5support.so.0 => /usr/lib/x86_64-linux-gnu/libkrb5support.so.0 (0x00007f62cd85e000)
libkeyutils.so.1 => /lib/x86_64-linux-gnu/libkeyutils.so.1 (0x00007f62cd659000)
可以看出在Ubuntu跑这个程序需要这么多动态链接库的支持,我们在开发板上有好多是用不到的,其中一部分在交叉编译安装opencv时已经禁用掉了。
我把我认为比较重要的库都标注成了绿色。(只是我个人理解,水平有限。)
文章:http://ebaina.com/bbs/forum.php?mod=viewthread&tid=7828&page=1&extra=#pid16931 上面说:
解决方法:
1.对于grfmt_png.cpp的各种undefined reference to,原因是交叉编译环境缺少libpng,解决办法是下载libpng,然后进行交叉编译,编译后生成include和lib文件夹,分别把include和lib下的文件拷贝到交叉编译环境的include和lib文件下,我的也就是上面的/usr/local/hi-arm/arm-hisiv100-linux/arm-hisiv100-linux-uclibcgnueabi/include/和/usr/local/hi-arm/arm-hisiv100-linux/arm-hisiv100-linux-uclibcgnueabi/lib/
然后再进行编译,记得编译命令上加上-lpng,然后发现grfmt_png.cpp的错误都没有了。
2.对于grfmt_jpeg.cpp的各种undefined reference to,是交叉编译环境缺少了libjpeg,解决办法参考上面的1,下载libjpeg,交叉编译,拷贝include和lib文件到交叉编译环境的include和lib下,编译加上-ljpeg
3对于persistence.cpp的各种undefined reference to,是交叉编译环境缺少了libxml2,解决办法同上,编译时加上-xlm2后,这个错误就没了。
受到这个启发,我决定试试。
于是我打算重新交叉编译安装opencv3.1.0和支持xml,jpeg,png的库。
编译libxml2参考:
http://blog.csdn.net/lanyou1900/article/details/47782067
安装libiconv:
http://ftp.gnu.org/pub/gnu/libiconv/libiconv-1.13.1.tar.gz
./configure CC=arm-none-linux-gnueabi-gcc --host=arm-none-linux-gnueabi --prefix=/home/ds/arm-2013.05/x86_64-linux-gnu/usr/libiconv //(这个文件夹自己建立的)
make
make install
安装libz:
./configure --prefix=/home/ds/arm-2013.05/x86_64-linux-gnu/usr/libz
`修改makefile:将30行左右改为:(将LDSHARED 改为交叉编译器)
LDSHARED=arm-none-linux-gnueabi-gcc -shared -Wl,-soname,libz.so.1,--version-script,zlib.map`
`要不然会出现错误:/usr/bin/ld: adler32.lo:普通ELF重定位(M: 40)
/usr/bin/ld: adler32.lo:普通ELF重定位(M: 40)
adler32.lo: 无法添加符号: 文件格式错误
collect2: error: ld returned 1 exit status
Makefile:163: recipe for target 'libz.so.1.2.8' failed`
make CC=arm-none-linux-gnueabi-gcc LD=arm-none-linux-gnueabi-ld AR=arm-none-linux-gnueabi-ar
make install
安装libxml2:
./configure --host=arm-none-linux-gnueabi CC=arm-none-linux-gnueabi-gcc AR=arm-none-linux-gnueabi-ar LD=arm-none-linux-gnueabi-ld ANLIB=arm-none-linux-gnueabi-ranlib --prefix=/home/ds/arm-2013.05/x86_64-linux-gnu/usr/libxml2 --with-zlib=/home/ds/arm-2013.05/x86_64-linux-gnu/usr/libz --with-iconv=/home/ds/arm-2013.05/x86_64-linux-gnu/usr/libiconv
make
`出现错误:parserInternals.c:36:18: fatal error: zlib.h: No such file or directory
compilation terminated.
Makefile:1248: recipe for target 'parserInternals.lo' failed
make[2]: *** [parserInternals.lo] Error 1
make[2]: Leaving directory '/home/ds/build/xml/libxml2-2.9.4'
Makefile:1440: recipe for target 'all-recursive' failed
make[1]: *** [all-recursive] Error 1
make[1]: Leaving directory '/home/ds/build/xml/libxml2-2.9.4'
Makefile:859: recipe for target 'all' failed
make: *** [all] Error 2
于是我去makefile文件,搜索libiconv,在对应的位置把libz的动态链接库和位置和头文件都添加上
XML_INCLUDEDIR = -I${includedir}/libxml2 -I/home/ds/arm-2013.05/x86_64-linux-gnu/usr/libiconv/include -I/home/ds/arm-2013.05/x86_64-linux-gnu/usr/libz/include
XML_LIBS = -lxml2 -lz -L/home/ds/arm-2013.05/x86_64-linux-gnu/usr/libiconv/lib -liconv -lm -L/home/ds/arm-2013.05/x86_64-linux-gnu/usr/libz/lib -lz
CPPFLAGS = -I/home/ds/arm-2013.05/x86_64-linux-gnu/usr/libiconv/include -I/home/ds/arm-2013.05/x86_64-linux-gnu/usr/libz/include
ICONV_LIBS = -L/home/ds/arm-2013.05/x86_64-linux-gnu/usr/libiconv/lib -liconv -L/home/ds/arm-2013.05/x86_64-linux-gnu/usr/libz/lib -lz
这个错误解决。又出现下面python错误,不过网上说没关系,我暂时忽略了。我看了以下makefile文件,应该是编译时python指定的路径不对,或者缺少库。如果不成功再回来解决。
`
make install
出现错误:
cc1: warning: include location "/usr/include/python2.7" is unsafe for cross-compilation [-Wpoison-system-directories]
In file included from /usr/include/python2.7/Python.h:8:0,
from libxml.c:14:
/usr/include/python2.7/pyconfig.h:30:52: fatal error: arm-linux-gnueabi/python2.7/pyconfig.h: No such file or directory
compilation terminated.
Makefile:623: recipe for target 'libxml.lo' failed
make[4]: *** [libxml.lo] Error 1
make[4]: Leaving directory '/home/ds/build/xml/libxml2-2.9.4/python'
Makefile:684: recipe for target 'install-recursive' failed
make[3]: *** [install-recursive] Error 1
make[3]: Leaving directory '/home/ds/build/xml/libxml2-2.9.4/python'
Makefile:841: recipe for target 'install' failed
make[2]: *** [install] Error 2
make[2]: Leaving directory '/home/ds/build/xml/libxml2-2.9.4/python'
Makefile:1440: recipe for target 'install-recursive' failed
make[1]: *** [install-recursive] Error 1
make[1]: Leaving directory '/home/ds/build/xml/libxml2-2.9.4'
Makefile:1743: recipe for target 'install' failed
make: *** [install] Error 2
网上说是python错误无视即可。http://www.aichengxu.com/view/40322
用链接里例子测试了下,成功生成了可执行文件(不过我没移植到板子上测试,等全部的库弄完了再单独测试这个)。
#include
#include
#include
int main(int argc, char **argv)
{
xmlDocPtr doc = NULL;
xmlNodePtr root_node = NULL, node = NULL, node1 = NULL;
doc = xmlNewDoc(BAD_CAST "1.0");
root_node = xmlNewNode(NULL, BAD_CAST "root");
xmlDocSetRootElement(doc, root_node);
xmlNewChild(root_node, NULL, BAD_CAST "node1",BAD_CAST "content of node1");
node=xmlNewChild(root_node, NULL, BAD_CAST "node3",BAD_CAST"node has attributes");
xmlNewProp(node, BAD_CAST "attribute", BAD_CAST "yes");
node = xmlNewNode(NULL, BAD_CAST "node4");
node1 = xmlNewText(BAD_CAST"other way to create content");
xmlAddChild(node, node1);
xmlAddChild(root_node, node);
xmlSaveFormatFileEnc(argc > 1 ? argv[1] : "-", doc, "UTF-8", 1);
xmlFreeDoc(doc);
xmlCleanupParser();
xmlMemoryDump();
return 0;
}
arm-none-linux-gnueabi-gcc -I/home/ds/arm-2013.05/x86_64-linux-gnu/usr/libxml2/include/libxml2 -I/home/ds/arm-2013.05/x86_64-linux-gnu/usr/libz/include -I/home/ds/arm-2013.05/x86_64-linux-gnu/usr/libiconv/include -L/home/ds/arm-2013.05/x86_64-linux-gnu/usr/libxml2/lib -L/home/ds/arm-2013.05/x86_64-linux-gnu/usr/libz/lib -L/home/ds/arm-2013.05/x86_64-linux-gnu/usr/libiconv/lib -lz -liconv -lxml2 xml2test.c -o test //因为libxml2依赖那两个库,因此要加上,否则出错。
接下来安装:libjpeg
http://www.ijg.org/
./configure --host=arm-none-linux-gnueabi CC=arm-none-linux-gnueabi-gcc --prefix=/home/ds/arm-2013.05/x86_64-linux-gnu/usr/libjpeg
make
make install
安装libpng:
https://sourceforge.net/projects/libpng/files/
或者http://download.csdn.net/download/damys/9326857
./configure --host=arm-none-linux-gnueabi CC=arm-none-linux-gnueabi-gcc --prefix=/home/ds/arm-2013.05/x86_64-linux-gnu/usr/libpng --with-zlib=/home/ds/arm-2013.05/x86_64-linux-gnu/usr/libz/
出错:
checking for zlibVersion in -lz... no
checking for /home/ds/arm-2013.05/x86_64-linux-gnu/usr/libz/zlibVersion in -lz... no
configure: error: zlib not installed
于是加上zlib库具体的位置
./configure --host=arm-none-linux-gnueabi CC=arm-none-linux-gnueabi-gcc --prefix=/home/ds/arm-2013.05/x86_64-linux-gnu/usr/libpng LIBS=-L/home/ds/arm-2013.05/x86_64-linux-gnu/usr/libz/lib CPPFLAGS=-I/home/ds/arm-2013.05/x86_64-linux-gnu/usr/libz/include
make
make install
成功。
编译时可以加上以下参数:
如果你要编译一个库的源代码,可以把它编译成静态库,也可以把它编译成动态库。如果你想编译成动态库,就用 --enable-shared参数;如果你想编译成静态库,就用--enable-static参数。
交叉编译 x264,xvid,ffmpeg
为了使OpenCV能处理视频,我们要事先交叉编译ffmpeg,而ffmpeg又是依赖x264和xvid的。
安装yasm(x264需要用到的汇编编译器):
http://yasm.tortall.net/Download.html
./configure --host=arm-none-linux-gnueabi CC=arm-none-linux-gnueabi-gcc --prefix=/home/ds/arm-2013.05/x86_64-linux-gnu/usr/yasm
make
交叉编译x264
CC=arm-none-linux-gnueabi-gcc ./configure --host=arm-none-linux-gnueabi --disable-asm --prefix=/home/ds/arm-2013.05/x86_64-linux-gnu/usr/x264
make
make install
交叉编译libxvid:
用UltraEdit把编码都改为UNIX utf-8 ,发现还是出现相同错误。(后来发现从ubuntu拷贝到板子上本身编码是没问题的。)
查看opencv3.1源码,persistance.cpp —>
static void
icvXMLParse( CvFileStorage* fs )
{
char* ptr = fs->buffer_start;
CvStringHashNode *key = 0, *key2 = 0;
CvAttrList* list = 0;
int tag_type = 0;
// CV_XML_INSIDE_TAG is used to prohibit leading comments
ptr = icvXMLSkipSpaces( fs, ptr, CV_XML_INSIDE_TAG );
if( memcmp( ptr, ", 5 ) != 0 ) //比较前5个字节,因为编码格式是8位。每个字符占8位。
CV_PARSE_ERROR( "Valid XML should start with \'\'" );
ptr = icvXMLParseTag( fs, ptr, &key, &list, &tag_type );
/*{
const char* version = cvAttrValue( list, "version" );
if( version && strncmp( version, "1.", 2 ) != 0 )
CV_Error( CV_StsParseError, "Unsupported version of XML" );
}*/
// we support any 8-bit encoding, so we do not need to check the actual encoding.//支持任何8位的编码
// we do not support utf-16, but in the case of utf-16 we will not get here anyway.
/*{
const char* encoding = cvAttrValue( list, "encoding" );
if( encoding && strcmp( encoding, "ASCII" ) != 0 &&
strcmp( encoding, "UTF-8" ) != 0 &&
strcmp( encoding, "utf-8" ) != 0 )
CV_PARSE_ERROR( "Unsupported encoding" );
}*/
while( *ptr != '\0' )
{
ptr = icvXMLSkipSpaces( fs, ptr, 0 );
if( *ptr != '\0' )
{
CvFileNode* root_node;
ptr = icvXMLParseTag( fs, ptr, &key, &list, &tag_type );
if( tag_type != CV_XML_OPENING_TAG ||
strcmp(key->str.ptr,"opencv_storage") != 0 )
CV_PARSE_ERROR( " tag is missing" );
root_node = (CvFileNode*)cvSeqPush( fs->roots, 0 );
ptr = icvXMLParseValue( fs, ptr, root_node, CV_NODE_NONE );
ptr = icvXMLParseTag( fs, ptr, &key2, &list, &tag_type );
if( tag_type != CV_XML_CLOSING_TAG || key != key2 )
CV_PARSE_ERROR( " tag is missing" );
ptr = icvXMLSkipSpaces( fs, ptr, 0 );
}
}
assert( fs->dummy_eof != 0 );
}
/** @overload
@param source Name of the file to open or the text string to read the data from. Extension of the
file (.xml or .yml/.yaml) determines its format (XML or YAML respectively). Also you can append .gz
to work with compressed files, for example myHugeMatrix.xml.gz. If both FileStorage::WRITE and
FileStorage::MEMORY flags are specified, source is used just to specify the output file format (e.g.
mydata.xml, .yml etc.).
@param flags Mode of operation. See FileStorage::Mode
@param encoding Encoding of the file. Note that UTF-16 XML encoding is not supported currently and
you should use 8-bit encoding instead of it.
*/
CV_WRAP FileStorage(const String& source, int flags, const String& encoding=String());
/** @overload */
FileStorage(CvFileStorage* fs, bool owning=true);
可以看出任何8位的字符编码,opencv都是支持的。因此排除字符编码因素。
在网上找简单的xml读写例子:
//readxml.cpp
#include
#include
#include "opencv2/opencv.hpp"
using namespace std;
using namespace cv;
int main(int argc, char* argv[])
{
//创建XML文件存储
CvFileStorage* fs = cvOpenFileStorage("jarvischu.xml",
0, //用于存储的内存,如果为NULL,则会使用一个临时内存
CV_STORAGE_WRITE,
"utf-8"//编码
);
//写入数据
cvWriteInt(fs,"frame_count",10); //--写Int
cvWriteReal(fs,"pi",3.14); //--写Float
//--写结构体
cvStartWriteStruct(fs,"frame_size",CV_NODE_MAP,"id_size" );// 有名称(会新建一个标签)
cvWriteInt(fs,"width",320);
cvWriteInt(fs,"height",200);
cvEndWriteStruct(fs);
cvStartWriteStruct(fs,"author_info",CV_NODE_SEQ,"id_author");// 无名称
cvWriteString(fs,0,"JarvisChu");
cvWriteString(fs,0,"China");
cvEndWriteStruct(fs);
//--写矩阵
unsigned char vec[]={1,2,3,4,5,6,7,8,9};
CvMat mat = cvMat(3,3,CV_8UC1,vec);
cvWrite(fs,"Matrix",&mat);
//--写注释
cvWriteComment(fs,"This is a example for operatoring the xml file",0);//不为0表示放在当前行,0表示新行
//释放
cvReleaseFileStorage(&fs);
//打开XML文件
fs = cvOpenFileStorage("jarvischu.xml",
0, //用于存储的内存,如果为NULL,则会使用一个临时内存
CV_STORAGE_READ,
"GB2312"//编码 GB2312
);
//读取数据
int f = cvReadIntByName(fs,0,"frame_count",0);//读取有名字的Int
//--读取元素数据
CvFileNode* fn = cvGetFileNodeByName(fs,0,"frame_size"); //先读取父元素(标签,节点)
int width = cvReadIntByName(fs,fn,"width"); //通过父元素读取子元素
int height = cvReadIntByName(fs,fn,"height");
//--读取元素内的顺序数据
fn = cvGetFileNodeByName(fs,0,"author_info");//先读取元素
CvSeq* seq = fn->data.seq; //获取元素的顺序流
const char* name = cvReadString((CvFileNode*)cvGetSeqElem(seq,0));//读取顺序流中数据 0
const char* country = cvReadString((CvFileNode*)cvGetSeqElem(seq,1));//读取顺序流中数据 1
cout<<"frame_count:"<"width:"<"height"<cout <<"name:"<"country:"<return 0;
}
和读写yml的例子:
readyml.cpp
#include
#include "opencv2/opencv.hpp"
#include "opencv2/ml.hpp"
#include
#include
using namespace cv;
using namespace std;
int main(int argc, char **argv)
{
/*
FileStorage fs("test.yml", FileStorage::WRITE);
fs << "frameCount" << 5;
time_t rawtime; time(&rawtime);
fs << "calibrationDate" << asctime(localtime(&rawtime));
Mat cameraMatrix = (Mat_(3,3) << 1000, 0, 320, 0, 1000, 240, 0, 0, 1); //又一种Mat初始化方式
Mat distCoeffs = (Mat_(5,1) << 0.1, 0.01, -0.001, 0, 0);
fs << "cameraMatrix" << cameraMatrix << "distCoeffs" << distCoeffs;
//features为一个大小为3的向量,其中每个元素由随机数x,y和大小为8的uchar数组组成
fs << "features" << "[";
for( int i = 0; i < 3; i++ )
{
int x = rand() % 640;
int y = rand() % 480;
uchar lbp = rand() % 256;
fs << "{:" << "x" << x << "y" << y << "lbp" << "[:";
for( int j = 0; j < 8; j++ )
fs << ((lbp >> j) & 1);
fs << "]" << "}";
}
fs << "]";
fs.release();*/
FileStorage fs("test.yml", FileStorage::READ);
//方式一: []操作符
int frameCount = (int)fs["frameCount"];
//方式二: FileNode::operator >>()
string date;
fs["calibrationDate"] >> date;
Mat cameraMatrix2, distCoeffs2;
fs["cameraMatrix"] >> cameraMatrix2;
fs["distCoeffs"] >> distCoeffs2;
//注意FileNodeIterator的使用,似乎只能用一维数组去读取里面所有的数据
FileNode features = fs["features"];
FileNodeIterator it = features.begin(), it_end = features.end();
int idx = 0;
std::vector lbpval;
for( ; it != it_end; ++it, idx++ )
{
cout << "feature #" << idx << ": ";
cout << "x=" << (int)(*it)["x"] << ", y=" << (int)(*it)["y"] << ", lbp: (";
(*it)["lbp"] >> lbpval; //直接读出一维向量
for( int i = 0; i < (int)lbpval.size(); i++ )
cout << " " << (int)lbpval[i];
cout << ")" << endl;
}
fs.release();
return 0;
}
重点内容结果:在arm上写xml并保存成功,但是读取时出现相同错误。排除这一猜测。
但是在arm 上读写保存yml文件都成功。
FILE* f=fopen(kDefaultAnnPath, "rb+");//http://baike.baidu.com/link?url=1AGB1MzmqkrH0iMjhCb2KTxGIp8u5rb7zebfMGl7gKma5uIcbEUwIsxvqyuo27cA1kzO6yYbKhl-dxNV7ZuBYa
fseek(f, 0, SEEK_END);//函数设置文件指针stream的位置。如果执行成功,stream将指向以fromwhere(偏移起始位置:文件头0(SEEK_SET),当前位置1(SEEK_CUR),文件尾2(SEEK_END))为基准,偏移offset(指针偏移量)个字节的位置。如果执行失败(比如offset超过文件自身大小),则不改变stream指向的位置。(让stream指针指向文件尾)
long l = ftell(f);//函数 ftell 用于得到文件位置指针当前位置相对于文件首的偏移字节数。在随机方式存取文件时,由于文件位置频繁的前后移动,程序不容易确定文件的当前位置。(为了得到文件的字节数)
fseek(f, 0, SEEK_SET);//让stream指针指向文件头,int fseek(FILE *stream, long offset, int fromwhere);
char * str =new char[1024*1024];
fread(str, l, 1, f);//函数原型size_t fread ( void *buffer, size_t size, size_t count, FILE *stream) ;参 数: buffer用于接收数据的内存地址;size : 要读的每个数据项的字节数,单位是字节; count: 要读count个数据项,每个数据项size个字节;stream:输入流
fclose(f);
str[l] = '\0';//把str最后一个字符设置成,字符串结束符
ann_=ml::ANN_MLP::loadFromString(str);
还是报相同错误。排除。
根据以上的结果基本可以断定原因是:在opencv读xml文件的方式在PC(Ubuntu)上和在arm 中的linux上是不同的。
因此我要交叉编译opencv2.4.9,并且用他的库编译一个读写xml文件的程序,移植到板子上是否有问题。
用上面那个readxml.cpp的例子,用opencv-2.4.9的库交叉编译出来放到板子上跑,还是写xml和保存没问题但是读的时候还是相同的错误。排除。
开发板从SD卡启动,我查看内核版本:
ds@ds-Lenovo:~/build/filesys_zedboard/备份$ file uImage
uImage: u-boot legacy uImage, Linux-4.0.0-xilinx, Linux/ARM, OS Kernel Image (Not compressed), 3562248 bytes, Mon Mar 28 05:19:08 2016, Load Address: 0x00008000, Entry Point: 0x00008000, Header CRC: 0x94BFB3BC, Data CRC: 0x72900298
我之前安装交叉编译器之前未安装32位库,不知道这个有没有影响。
重新安装交叉编译器,之前用的是从网上下载的arm-2013.05-24-arm-none-linux-gnueabi-x86_64-linux-gnu.tar.bz2。
现在用xilinx-2011.09-50-arm-xilinx-linux-gnueabi.bin,进行交叉编译readxml.cpp
。移植到zedboard上,还是相同的错误。(也有可能是交叉编译器版本太低,以后用高版本的试一下)
于是打算重新交叉编译opencv3.1.0。
我按照
http://www.eefocus.com/beiyangguangdian/blog/14-03/302119_52e49.html 的方法移植的,可是老是出现交叉编译器include中c++头文件math.h或者cmath的问题。找了网上说什么的都有,有说是交叉编译器版本应该用新版本,有的说是ffmpeg版本的问题。
我分别用opencv3.1版本和opencv2.4.9版本都试了,如果只加上with_jpeg,png,tiff,v4l不出错,一旦加上就出上边math.h或者cmath里面的错误❌。暂时没有解决。
不过xml这个问题,我觉得应该是交叉编译器或者opencv版本或者编译时依赖库的问题(不知道和ubuntu是64位的有没有关系),以后这个问题解决了,我再回过头来记录一下。
现在阶段我用了XAPP1167里面的demo,里面有现成的opencv_install/arm_linux ,有编译好的opencv库,而且支持ffmpeg。它的opencv是2.4.5版本的。
我用它提供的库交叉编译了opencv自带的人脸识别程序和自己的xml读写程序都成功了。(交叉编译器是arm-2014.05-28-arm-none-eabi-i686版本的,其实我觉得和交叉编译器没关系,这里只是记录一下)