OpenCV 3 runtime error "Invalid pointer to file storage" cv_bridge + third party library
I'm trying to publish the image of a picozense camera in a ROS node in ROS kinetic, Ubuntu 16.04. I build a catkin package and included the camera's API (.h and .so files) which is OpenCV3 compatible. This works fine, i can call the API functions in the c++ source code. However, OpenCV crashes at runtime with an error that after some research most posts argue is a conflict between OpenCV2 and OpenCV3. But my installed OpenCV version is 3.3.1 and i don't have any OpenCV 2.x installed. (Also i'm using cv_bridge which depends on OpenCV3 components)
The only OpenCV package i added to my dependencies and in my code is the highgui package. If i leave it out, the node does not crash at all. But even with the highgui package the node runs successfully sometimes.
How can i fix the error?
OpenCV Runtime Error
rosusr@ubuntu:~/catkin_ws$ rosrun picozense publisher
1
OpenCV Error: Bad argument (Invalid pointer to file storage) in cvGetFileNodeByName, file /tmp/binarydeb/ros-kinetic-opencv3-3.3.1/modules/core/src/persistence.cpp, line 861
terminate called after throwing an instance of 'cv::Exception'
what(): /tmp/binarydeb/ros-kinetic-opencv3-3.3.1/modules/core/src/persistence.cpp:861: error: (-5) Invalid pointer to file storage in function cvGetFileNodeByName
Aborted (core dumped)
Running the node works sometimes (the initialization just fails because the camera is not connected)
rosusr@ubuntu:~/catkin_ws$ rosrun picozense publisher
1
2
PsInitialize status: -1
Initialize failed!
Shutdown status: 0
publisher.cpp
#include <ros/ros.h>
#include <cv_bridge/cv_bridge.h>
#include <opencv2/highgui.hpp>
#include "PicoZense_api.h"
int main(int argc, char** argv){
ros::init(argc, argv, "publisher");
ros::NodeHandle nh;
PsReturnStatus status;
std::cout << "1" << std::endl;
status = PsInitialize();
std::cout << "2" << std::endl;
std::cout << "PsInitialize status: " << status << std::endl;
if (status != PsReturnStatus::PsRetOK){
std::cout << "Initialize failed!" << std::endl;
status = PsShutdown();
std::cout << "Shutdown status: " << status << std::endl;
return -1;
}
// ...
// using opencv highgui etc. here
//
return 0;
}
CMakeLists.txt
cmake_minimum_required(VERSION 2.8.3)
project(picozense)
add_compile_options(-std=c++11)
find_package(catkin REQUIRED COMPONENTS
cv_bridge
image_transport
sensor_msgs
message_generation
)
find_package(OpenCV 3 REQUIRED COMPONENTS highgui)
generate_messages( DEPENDENCIES
sensor_msgs
)
catkin_package( CATKIN_DEPENDS
cv_bridge
image_transport
sensor_msgs
message_runtime
)
include_directories( include
${catkin_INCLUDE_DIRS} #picoZense API header file is here (/picozense/include/)
${OpenCV_INCLUDE_DIRS}
)
message(STATUS "catkin_include_dirs: " ${catkin_INCLUDE_DIRS})
message(STATUS "opencv_include_dirs: " ${OpenCV_INCLUDE_DIRS})
add_executable(publisher src/publisher.cpp)
add_dependencies(publisher ${catkin_EXPORTED_TARGETS} ${${PROJECT_NAME}_EXPORTED_TARGETS})
target_link_libraries(publisher ${catkin_LIBRARIES} ${OpenCV_LIBRARIES} ${PROJECT_SOURCE_DIR}/lib/x64/libpicozense_api.so)
message(STATUS "opencv_libraries: " ${OpenCV_LIBRARIES})
package.xml
<?xml version="1.0"?>
<package format="2">
<name>picozense</name>
<version>0.0.0</version>
<description>The picozense package</description>
<maintainer email="rosusr@todo.todo">rosusr</maintainer>
<license>TODO</license>
<buildtool_depend>catkin</buildtool_depend>
<build_depend>cv_bridge</build_depend>
<build_depend>image_transport</build_depend>
<build_depend>sensor_msgs</build_depend>
<build_depend>message_generation</build_depend>
<build_export_depend>cv_bridge</build_export_depend>
<build_export_depend>image_transport</build_export_depend>
<build_export_depend>sensor_msgs</build_export_depend>
<build_export_depend>message_generation</build_export_depend>
<exec_depend>cv_bridge</exec_depend>
<exec_depend>image_transport</exec_depend>
<exec_depend>sensor_msgs</exec_depend>
<exec_depend>message_runtime</exec_depend>
<export>
</export>
</package>
ldd libpicozense_api.so
linux-vdso.so.1 => (0x00007ffc19ea8000)
libpthread.so.0 => /lib/x86_64-linux-gnu/libpthread.so.0 (0x00007ff34274c000)
libstdc ...
Does
libpicozense_api.so
link to anything suspicuous? What is the output ofldd libpicozense_api.so
?That is interesting. What is the contents of the various
OpenCV
CMake variables? ParticularlyOpenCV_LIBRARIES
?Random
SEGFAULT
s (ie: sometimes they occur, sometimes they don't) are a strong pointer to ABI incompatibility...
..
if the camera sdk is linking against a different version of OpenCV (or expecting to link against a different version), that could be the problem.
Edit: I tried looking for the lib, but it appears the ..
.. camera is only in pre-order now. I'm guessing you have a preproduction unit for evaluation purposes?
"if the camera sdk is linking against a different version of OpenCV (or expecting to link against a different version), that could be the problem."
Exactly my thought. Problem is i only have a .h and a .so file and in the header it does not state any opencv version whatsoever
which is rather unfortunate, as find scripts should populate those variables with absolute paths. Not with library names.
I'm not sure how ..
.. your last sentence supports your conclusion.
That's why you need to look at the output of
ldd
.