ros / roscpp_core Goto Github PK
View Code? Open in Web Editor NEWros distribution sandbox
ros distribution sandbox
Here is a patch fixing an issue with bool serialization on ARM.
We are currently adapting much of our software stack to work in simulation. There, /clock
is published with a rate of 125Hz. In some parts of our software, we are using ros rates at higher rates (for example 500Hz). In these cases, rate.sleep()
does not work as expected (blocking until the time progresses) and instead returns immediately. This leads to those parts of our software running at unlimited rates, using too much resources.
In my opinion, in this case, rate.sleep()
should block like it does in python.
There is supposed to be constructor for ros::Duration taking a ros::Rate as param:
explicit Duration(const Rate&);
I can't see any implementation though and using it gives a linker error.
undefined reference to `ros::Duration::Duration(ros::Rate const&)
message_event.h
contains the following equals operator:
roscpp_core/roscpp_traits/include/ros/message_event.h
Lines 201 to 205 in 3b362ac
Which assigns the rhs.message_
to the message_
member, instead of comparing them.
roscpp_core/rostime/src/time.cpp defines TIME_MIN
, TIME_MAX
, DURATION_MIN
and DURATION_MAX
with std::numeric_limits
. Performing arithmetic operations on them throws an exception due to causing an overflow.
From a user's standpoint however, I would expect
ros::Time::now() + ros::DURATION_MAX == ros::TIME_MAX
Is there a design reason why this is not implemented?
My most recent Fedora builds of cpp_common
[1] are not installing the boost development libraries as they did about 2 weeks ago. I don't see any changes to cpp_common
that would have triggered this, so it must have been an upstream package that changed its deps or something like that.
I can't see any reason not to have cpp_common
depend on boost, as it references boost headers [2].
I can confirm this on an f20 system without boost-devel
by running:
mkdir -p ~/boost_test_ws/src
cd ~/boost_test_ws
rosinstall_generator --deps --tar --rosdistro indigo cpp_common > src/.rosinstall
wstool update -t src
rosdep install --from-path src --ignore-src
...and finding that boost-devel is not installed as it should be.
I have confirmed that adding boost
as a run and build dependency fixes things [3] [4], but I'm not sure what caused this to begin with, so I can only suggest that as a possible fix.
Thanks,
--scott
[1] http://csc.mcs.sdsmt.edu/jenkins/view/IbinF20x32/job/ros-indigo-cpp-common_binaryrpm_heisenbug_i386/10/console
[2] http://github.com/ros/roscpp_core/blob/indigo-devel/cpp_common/include/ros/header.h#L41
[3] http://github.com/smd-ros-rpm-release/roscpp_core-release/commit/e92922ec6b7c55aefa55e8f7c2c8a5cdae1535ca
[4] http://csc.mcs.sdsmt.edu/jenkins/view/IbinF20x32/job/ros-indigo-cpp-common_binaryrpm_heisenbug_i386/11/console
Hi,
We face long build times.
In many compilation units ros/console.h
is all that is is needed from ros. But that includes a lot of unecessary boost:
ros/console.h includes ros/time
ros/time.h includes boost/special_functions/round
boost/special_functions/round in turn includes more of boost than needed for rounding.
But 'fixing' this in ros/time, by using other means of rounding, breaks ros/console, because ros/console also needs boost shared ptr, that implicitely came with the special functions.
Fixing this in ros/console, eg by using std::shared ptr, would probably lead to similar problems in depending projects.
Are there plans for gradually removing boost from the core of ros? What can we do to help?
BR!
Since the last bionic package import yesterday, the cpp_common
package cannot be installed because its' dependencies are not available anymore (libconsole-bridge is now 0.4 and not 0.2).
apt console output below:
root@532af06e867b:/# apt install ros-melodic-cpp-common
Reading package lists... Done
Building dependency tree
Reading state information... Done
Some packages could not be installed. This may mean that you have
requested an impossible situation or if you are using the unstable
distribution that some required packages have not yet been created
or been moved out of Incoming.
The following information may help to resolve the situation:
The following packages have unmet dependencies:
ros-melodic-cpp-common : Depends: libconsole-bridge0.2v5 but it is not installable
E: Unable to correct problems, you have held broken packages.
Dear developers,
we suspect that ros::serialization::serializeServiceResponse had a bug to assign unused memory unsafely.
when service response returned false (argument "ok" == false), else statement assigned (sizeof(message) + 1) bytes.
the following codes in the else-statement, serializatio of "ok" flag will be safe, but unfortunately, the next serialization of message should be unsafe because lack of message size information before that data.
if roscpp sent a message data in the else-statement, we thought that it's neccesary to serialize size of message like in "if-true-statement".
if not, we thought it's better to set m.num_bytes to "1" and remove this sentence.
we hope it could be a help.
roscpp_core/rostime/src/time.cpp
Line 285 in 1110bb0
void Time::useSystemTime()
{
g_use_sim_time = false;
}
In some corner cases, floating point inaccuracy can lead to invalid data where nsec is calculated to be outside [0;1e9-1].
To illustrate the problem think of the following
#include <cmath>
#include <boost/math/special_functions/round.hpp>
int main()
{
double someint = 1031.0; // some integer
double t = std::nextafter(someint, 0); // someint - epsilon
std::cout << next << std::endl; // prints 1031.000000
// ros implementation of fromSec
uint32_t sec = (uint32_t)floor(t);
uint32_t nsec = (uint32_t)boost::math::round((t-sec) * 1e9);
std::cout << "sec" << sec << std::endl; // prints 1030 (!)
std::cout << "nsec"<< nsec << std::endl; // prints 1000000000 (!)
}
(compile with c++11)
Correct behavior would be sec: 1031 nsec: 0, of course.
I guess the rounding behavior is desired in general, so a remaining fix would be to catch this specific case. Alternatively, the order could be changed to multiply with 1e9 -> round -> split into secs/nsec.
The latter solution requires an appropriately long integer data type for the temporary.
I'm not sure if this is the correct project, but it seems like the correctly named one and I could not find which repo actually has node_handle.h.
In my version of ros (indigo), NodeHandle does not have a ::getParam() overload for float, the rationale for which is not clear. This seems like a bug/oversight.
Thank you!
message_traits.h has several unused parameter violations, for example here on line 171.
All the offending lines are (171, 172, 190, 191, 210, 211).
For a project that wants to build with warnings-as-errors, this requires us to disable these warnings for any file that includes ROS messages, which is unfortunate.
I previously pushed to have the same issue fixed in dynamic reconfigure here. As you can see, the solution is just to comment out the parameter name when it's not used in a particular implementation.
e.g.
static std_msgs::Header* pointer(M& /*m*/) { return 0; }
PR #52 which dealt with this issue on clang breaks on gcc 6 (gcc doesn't recognize the void cast as a valid use of the variable and still emits the warning).
Is there a reason the indent is unused in the first place? That is, why aren't these
s << indent << thing_to_output << "\n";
Hi,
By reading through the code of the rostime
package I found that ros::Duration::sleep()
has an internal sleep in wall time with a length of 1,000,000 nanoseconds = 1 millisecond
. Code -> https://github.com/ros/roscpp_core/blob/noetic-devel/rostime/src/time.cpp#L402
As far as I understand, the internal call to ros_wallsleep(0, 1000000);
is limiting the maximum resolution of ros::Duration::sleep()
to 1 millisecond
in wall time.
I intend to use ros::Time
inside a node that spins at a rate of 400Hz
(every 2.5ms
), and this aspect of the current implementation would not allow me to sleep()
with a fine-enough resolution. Due to the 1ms
resolution, sleep would wake up at t=2ms
, or t=3ms
, but never t=2.5ms
.
Therefore, I have two related questions:
bool Duration::sleep(const uint32_t min_wall_sleep_time_ns = 1000000) const;
Thank you very much in advance.
Best regards,
Yoshua Nava
Hi,
could you please add an SONAME to the libs?
Thanks!
Jochen
The MessageEvent constructors not receiving connections header are "evil". I tried to remove them in #21 before but could not get rid of all code which uses it (therefore they have been reintroduced).
But in two cases that already backfired. Two code parts which worked before behaved wrong (silently having empty connection header) which was difficult to spot:
In both cases with the "evil" MessageEvent constructors present the code compiles but does not work correctly due to the missing connection info. When the two constructors are commented out the code fails to build. I worked around that with the two commits referenced above.
But this should not be necessary. I think the templated functions for subscribing to topics should deal with this problem and avoid the usage of the "evil" constructors without requiring the commited hacks.
Greetings roscpp_core developers and contributors,
We’re reaching out because your project is an important part of the open source ecosystem, and we’d like to invite you to integrate with our fuzzing service, OSS-Fuzz. OSS-Fuzz is a free fuzzing infrastructure you can use to identify security vulnerabilities and stability bugs in your project. OSS-Fuzz will:
Many widely used open source projects like OpenSSL, FFmpeg, LibreOffice, and ImageMagick are fuzzing via OSS-Fuzz, which helps them find and remediate critical issues.
Even though typical integrations can be done in < 100 LoC, we have a reward program in place which aims to recognize folks who are not just contributing to open source, but are also working hard to make it more secure.
We want to stress that anyone who meets the eligibility criteria and integrates a project with OSS-Fuzz is eligible for a reward.
If you're not interested in integrating with OSS-Fuzz, it would be helpful for us to understand why—lack of interest, lack of time, or something else—so we can better support projects like yours in the future.
If we’ve missed your question in our FAQ, feel free to reply or reach out to us at [email protected].
Thanks!
Tommy
OSS-Fuzz Team
Is there a reason why ROS uses reinterpret_cast
instead of memcpy
for serializing on x86? When I compile any node with GCC's undefined behaviour sanitizer, I get a bunch of errors like the following:
/opt/ros/kinetic/include/ros/serialization.h:234:129: runtime error: store to misaligned address 0x619000006e9f for type 'double', which requires 8 byte alignment
0x619000006e9f: note: pointer points here
69 63 6c 65 be be be be be be be be be be be be be be be be be be be be be be be be be be be be
^
/opt/ros/kinetic/include/ros/serialization.h:234:269: runtime error: load of misaligned address 0x7f462000461b for type 'double', which requires 8 byte alignment
0x7f462000461b: note: pointer points here
69 63 6c 65 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
Hi, I'm experiencing a problem which I sense may be a bug. I have opened a question on ROS answers, but as I describe there it would appear to be a bug.
If you need further description to understand the problem let me know. I opened the issue here since from a backtrace I found out the copy is being done on the copyMessageIfNecessary() function of message_event.h (https://github.com/ros/roscpp_core/blob/indigo-devel/roscpp_traits/include/ros/message_event.h#L215).
To sum it up, the copy is being performed after this sequence (nodeletA is publisher, nodeletB and nodeletC subscribe expecting non-const ptrs in the callback)
nodeletA publishes non-constr ptr message
nodeletB receives the same object (.get() matches)
nodeletC is loaded
nodeletA publishes non-constr ptr message (same one as first case, matches .get())
nodeletB receives a copy of the object (.get() is different)
nodeletC receives a copy of the object (.get() is different)
If nodeletC expects const-ptr in the callback, the sequence is only modified in the last step, since it receives the same ptr as was sent originally.
Release should include fixes from #8
(I'm going to try creating a meta-issue for the release, as described on the mailing list, and see how it goes)
Example Project: https://github.com/AutoxingTech/simple_publisher_crash
output message size
Publication::enqueueMessage 1 2427156042
Publication::enqueueMessage 2 2427156042
Publication::enqueueMessage 3
https://github.com/ros/roscpp_core/blob/indigo-devel/rostime/src/time.cpp#L104
clock_gettime(CLOCK_REALTIME, &start);
CLOCK_REALTIME is subject to discontinuity administratively or from NTP leap second. Last time a leap second elapsed, millions of servers exploded http://lwn.net/Articles/509207/ . Considering the real-time sensitivity of robot control and the schedule of the next leap second, CLOCK_REALTIME should be changed to CLOCK_MONOTONIC. Other usage of CLOCK_REALTIME in ROS code base should also be eliminated.
Hello,
Can you please specify which BDS(full text), mentioned in https://github.com/ros/roscpp_core/blob/0.6.11/roscpp_core/package.xml applies on roscpp_core 0.6.11?
There is no License file regarding the BSD that applies on roscpp_core 0.6.11.
Thank you
Negative int8_t values are printed as very large integers near 2^32 as they are casted to a uint32_t in the specialization of the ros::message_operations::Printer<int8_t> class. I assume this is copy&paste bug from the uint8_t case and
s << (uint32_t)value << "\n";
in line 56 of message_operations.h should be replaced by
s << (int32_t)value << "\n";
or even better by a static_cast.
TimeBase::fromSec(double)
casts a double
value to an int64_t
value. If the double value is exceeds the int64_t
range this is undefined behaviour (for reference).
I have the -Wconversion tag in my CMake (version 3.5), and it caught some warnings in ros/time.h. Nothing urgent, just wanted to pass it along in case you guys didn't compile with that flag. (Running ROS Melodic with gcc 7.4.0)
In file included from /opt/ros/melodic/include/ros/ros.h:38:0,
from /root/src/path_to_my_header.h:5,
from /root/src/path_to_my_test.cpp:2:
/opt/ros/melodic/include/ros/time.h: In instantiation of ‘T& ros::TimeBase<T, D>::fromSec(double) [with T = ros::Time; D = ros::Duration]’:
/opt/ros/melodic/include/ros/time.h:191:40: required from here
/opt/ros/melodic/include/ros/time.h:161:11: warning: conversion to ‘uint32_t {aka unsigned int}’ from ‘long unsigned int’ may alter its value [-Wconversion]
sec += (nsec / 1000000000ul);
~~~~^~~~~~~~~~~~~~~~~~~~~~~~
/opt/ros/melodic/include/ros/time.h: In instantiation of ‘T& ros::TimeBase<T, D>::fromSec(double) [with T = ros::WallTime; D = ros::WallDuration]’:
/opt/ros/melodic/include/ros/time.h:247:44: required from here
/opt/ros/melodic/include/ros/time.h:161:11: warning: conversion to ‘uint32_t {aka unsigned int}’ from ‘long unsigned int’ may alter its value [-Wconversion]
/opt/ros/melodic/include/ros/time.h: In instantiation of ‘T& ros::TimeBase<T, D>::fromSec(double) [with T = ros::SteadyTime; D = ros::WallDuration]’:
/opt/ros/melodic/include/ros/time.h:281:48: required from here
/opt/ros/melodic/include/ros/time.h:161:11: warning: conversion to ‘uint32_t {aka unsigned int}’ from ‘long unsigned int’ may alter its value [-Wconversion]
I get this when building from source:
-- The C compiler identification is Clang 5.1.0
-- The CXX compiler identification is Clang 5.1.0
-- Check for working C compiler: /usr/bin/cc
-- Check for working C compiler: /usr/bin/cc -- works
-- Detecting C compiler ABI info
-- Detecting C compiler ABI info - done
-- Check for working CXX compiler: /usr/bin/c++
-- Check for working CXX compiler: /usr/bin/c++ -- works
-- Detecting CXX compiler ABI info
-- Detecting CXX compiler ABI info - done
CMake Warning at CMakeLists.txt:3 (find_package):
By not providing "Findconsole_bridge.cmake" in CMAKE_MODULE_PATH this
project has asked CMake to find a package configuration file provided by
"console_bridge", but CMake did not find one.
Could not find a package configuration file provided by "console_bridge"
with any of the following names:
console_bridgeConfig.cmake
console_bridge-config.cmake
Add the installation prefix of "console_bridge" to CMAKE_PREFIX_PATH or set
"console_bridge_DIR" to a directory containing one of the above files. If
"console_bridge" provides a separate development package or SDK, be sure it
has been installed.
-- Using CATKIN_DEVEL_PREFIX: /tmp/rviz_urdfdom_ws/devel
-- Using CMAKE_PREFIX_PATH: /tmp/rviz_urdfdom_ws/devel
-- This workspace overlays: /tmp/rviz_urdfdom_ws/devel
-- Found PythonInterp: /usr/bin/python (found version "2.7.5")
-- Using PYTHON_EXECUTABLE: /usr/bin/python
-- Using default Python package layout
-- Found PY_em: /Library/Python/2.7/site-packages/em.pyc
-- Using empy: /Library/Python/2.7/site-packages/em.pyc
-- Using CATKIN_ENABLE_TESTING: ON
-- Call enable_testing()
-- Using CATKIN_TEST_RESULTS_DIR: /tmp/rviz_urdfdom_ws/build/cpp_common/test_results
-- Found gtest: gtests will be built
-- Using Python nosetests: /usr/local/bin/nosetests-2.7
-- catkin 0.6.7
CMake Error at /tmp/rviz_urdfdom_ws/src/catkin/cmake/catkin_package.cmake:159 (message):
catkin_package() DEPENDS on 'console_bridge' which must be
find_package()-ed before. If it is a catkin package it can be declared as
CATKIN_DEPENDS instead without find_package()-ing it.
Call Stack (most recent call first):
/tmp/rviz_urdfdom_ws/src/catkin/cmake/catkin_package.cmake:98 (_catkin_package)
CMakeLists.txt:5 (catkin_package)
-- Configuring incomplete, errors occurred!
Now I think this is because I don't have console_bridge installed from my package manager (not yet in Homebrew), but I think that there should be a REQUIRED
for find_package
ing console_bridge
:
https://github.com/ros/roscpp_core/blob/indigo-devel/cpp_common/CMakeLists.txt#L3
See the code
roscpp_core/cpp_common/CMakeLists.txt
Line 25 in d2bb8cb
See the code
roscpp_core/rostime/include/ros/duration.h
Line 108 in d2bb8cb
Even though WallRate and Rate have the same function and should have the same interface, their constructors work differently:
Rate::Rate(const Duration& d)
: start_(Time::now())
, expected_cycle_time_(d.sec, d.nsec)
, actual_cycle_time_(0.0)
{ }
WallRate::WallRate(const Duration& d)
: start_(WallTime::now())
, expected_cycle_time_(1.0 / d.toSec())
, actual_cycle_time_(0.0)
{}
So if you exchange both classes, you have a different cycle time which is really suprising. The wiki also says that they should have the same interface:
In roscpp_serialization/include/ros/serialization.h:417 v.size() returns with size_t
and the serializedLength returns with uint32_t
. size_t
on 64-bit systems usually 64 bit wide, so this line cause a warning. (I noticed this on windows, where some warnings are enabled by default.)
The proper return type should be size_t
, but since size_of(T)
is already converted to uint32_t
, this can be fixed with another static cast.
I can create a pull request if needed.
I'm using ROS Melodic on Ubuntu 18.04.5 with gcc-10.1. This test program compiles and runs fine with -std=gnu++17
option, but fails to compile with -std=gnu++2a
:
#include <iostream>
#include <ros/ros.h>
#include <ros/callback_queue.h>
#include <sensor_msgs/Image.h>
using namespace std;
ros::NodeHandle* nodeHandle;
ros::Subscriber* imageSubsc;
int imageId{-1}, prevImageId{-1};
float imageStamp{-1};
void imageCallback(const sensor_msgs::Image::ConstPtr& message) {
imageId = message->header.seq;
imageStamp = message->header.stamp.sec + 1e-9 * message->header.stamp.nsec;
cout << fixed << setprecision(3) << ros::Time::now().toSec() << " " << imageStamp << " " << imageId << " * callback" << endl;
}
int main(int argc, char* argv[]) {
ros::init(argc, argv, "igntest");
cout << "Testing: /X1/front_rgbd/image_raw" << endl;
ros::Time::init();
ros::Duration(10.0).sleep();
nodeHandle = new ros::NodeHandle; // this will create the node and make it visible to ROS
imageSubsc = new ros::Subscriber(nodeHandle->subscribe<sensor_msgs::Image>("/X1/front_rgbd/image_raw", 1, imageCallback, ros::TransportHints().tcpNoDelay()));
ros::Duration(10.0).sleep();
for (int i = 0; i < 50; i++) {
ros::getGlobalCallbackQueue()->callAvailable(ros::WallDuration(0.1));
cout << fixed << setprecision(3) << ros::Time::now().toSec() << " " << imageStamp << " " << imageId;
cout << (prevImageId == imageId ? " * sequence number repeated!" : "") << endl;
prevImageId = imageId;
}
}
Here is the error message:
[build] [1/2 50% :: 2.581] Building CXX object CMakeFiles/ign-test.dir/main.cpp.o
[build] FAILED: CMakeFiles/ign-test.dir/main.cpp.o
[build] /usr/local/bin/cmake -E time /usr/bin/g++-10 -DROSCONSOLE_BACKEND_LOG4CXX -DROS_BUILD_SHARED_LIBS=1 -DROS_PACKAGE_NAME=\"ign-test\" -I/home/paul/subt_ws/install/include -I/opt/ros/melodic/include -I/opt/ros/melodic/share/xmlrpcpp/cmake/../../../include/xmlrpcpp -O3 -DNDEBUG -std=gnu++2a -MD -MT CMakeFiles/ign-test.dir/main.cpp.o -MF CMakeFiles/ign-test.dir/main.cpp.o.d -o CMakeFiles/ign-test.dir/main.cpp.o -c ../main.cpp
[build] In file included from /opt/ros/melodic/include/sensor_msgs/Image.h:18,
[build] from ../main.cpp:4:
[build] /opt/ros/melodic/include/std_msgs/Header.h: In instantiation of ‘struct std_msgs::Header_<std::allocator<void> >’:
[build] /opt/ros/melodic/include/sensor_msgs/Image.h:50:16: required from ‘struct sensor_msgs::Image_<std::allocator<void> >’
[build] ../main.cpp:13:44: required from here
[build] /opt/ros/melodic/include/std_msgs/Header.h:46:121: error: no class template named ‘rebind’ in ‘class std::allocator<void>’
[build] 46 | typedef std::basic_string<char, std::char_traits<char>, typename ContainerAllocator::template rebind<char>::other > _frame_id_type;
[build] | ^~~~~~~~~~~~~~
[build] In file included from ../main.cpp:4:
[build] /opt/ros/melodic/include/sensor_msgs/Image.h: In instantiation of ‘struct sensor_msgs::Image_<std::allocator<void> >’:
[build] ../main.cpp:13:44: required from here
[build] /opt/ros/melodic/include/sensor_msgs/Image.h:58:121: error: no class template named ‘rebind’ in ‘class std::allocator<void>’
[build] 58 | typedef std::basic_string<char, std::char_traits<char>, typename ContainerAllocator::template rebind<char>::other > _encoding_type;
[build] | ^~~~~~~~~~~~~~
[build] In file included from ../main.cpp:4:
[build] /opt/ros/melodic/include/sensor_msgs/Image.h:67:97: error: no class template named ‘rebind’ in ‘class std::allocator<void>’
[build] 67 | typedef std::vector<uint8_t, typename ContainerAllocator::template rebind<uint8_t>::other > _data_type;
[build] | ^~~~~~~~~~
[build] In file included from ../main.cpp:4:
[build] /opt/ros/melodic/include/sensor_msgs/Image.h: In instantiation of ‘sensor_msgs::Image_<ContainerAllocator>::Image_() [with ContainerAllocator = std::allocator<void>]’:
[build] /usr/include/boost/smart_ptr/make_shared_object.hpp:256:5: required from ‘typename boost::detail::sp_if_not_array<T>::type boost::make_shared(Args&& ...) [with T = sensor_msgs::Image_<std::allocator<void> >; Args = {}; typename boost::detail::sp_if_not_array<T>::type = boost::shared_ptr<sensor_msgs::Image_<std::allocator<void> > >]’
[build] /opt/ros/melodic/include/ros/message_event.h:53:33: required from ‘boost::shared_ptr<X> ros::DefaultMessageCreator<M>::operator()() [with M = sensor_msgs::Image_<std::allocator<void> >]’
[build] /usr/include/boost/function/function_template.hpp:138:22: required from ‘static R boost::detail::function::function_obj_invoker0<FunctionObj, R>::invoke(boost::detail::function::function_buffer&) [with FunctionObj = ros::DefaultMessageCreator<sensor_msgs::Image_<std::allocator<void> > >; R = boost::shared_ptr<sensor_msgs::Image_<std::allocator<void> > >]’
[build] /usr/include/boost/function/function_template.hpp:925:38: required from ‘void boost::function0<R>::assign_to(Functor) [with Functor = ros::DefaultMessageCreator<sensor_msgs::Image_<std::allocator<void> > >; R = boost::shared_ptr<sensor_msgs::Image_<std::allocator<void> > >]’
[build] /usr/include/boost/function/function_template.hpp:716:22: required from ‘boost::function0<R>::function0(Functor, typename boost::enable_if_c<(! boost::is_integral<Functor>::value), int>::type) [with Functor = ros::DefaultMessageCreator<sensor_msgs::Image_<std::allocator<void> > >; R = boost::shared_ptr<sensor_msgs::Image_<std::allocator<void> > >; typename boost::enable_if_c<(! boost::is_integral<Functor>::value), int>::type = int]’
[build] /usr/include/boost/function/function_template.hpp:1061:16: required from ‘boost::function<R()>::function(Functor, typename boost::enable_if_c<(! boost::is_integral<Functor>::value), int>::type) [with Functor = ros::DefaultMessageCreator<sensor_msgs::Image_<std::allocator<void> > >; R = boost::shared_ptr<sensor_msgs::Image_<std::allocator<void> > >; typename boost::enable_if_c<(! boost::is_integral<Functor>::value), int>::type = int]’
[build] /opt/ros/melodic/include/ros/node_handle.h:707:25: required from ‘ros::Subscriber ros::NodeHandle::subscribe(const string&, uint32_t, void (*)(const boost::shared_ptr<const M>&), const ros::TransportHints&) [with M = sensor_msgs::Image_<std::allocator<void> >; std::string = std::__cxx11::basic_string<char>; uint32_t = unsigned int]’
[build] ../main.cpp:26:158: required from here
[build] /opt/ros/melodic/include/sensor_msgs/Image.h:34:12: error: using invalid field ‘sensor_msgs::Image_<ContainerAllocator>::encoding’
[build] 34 | , data() {
[build] | ^
[build] /opt/ros/melodic/include/sensor_msgs/Image.h:34:12: error: using invalid field ‘sensor_msgs::Image_<ContainerAllocator>::data’
[build] In file included from ../main.cpp:4:
[build] /opt/ros/melodic/include/sensor_msgs/Image.h: In instantiation of ‘static void ros::serialization::Serializer<sensor_msgs::Image_<ContainerAllocator> >::allInOne(Stream&, T) [with Stream = ros::serialization::IStream; T = sensor_msgs::Image_<std::allocator<void> >&; ContainerAllocator = std::allocator<void>]’:
[build] /opt/ros/melodic/include/sensor_msgs/Image.h:256:5: required from ‘static void ros::serialization::Serializer<sensor_msgs::Image_<ContainerAllocator> >::read(Stream&, T&) [with Stream = ros::serialization::IStream; T = sensor_msgs::Image_<std::allocator<void> >; ContainerAllocator = std::allocator<void>]’
[build] /opt/ros/melodic/include/ros/serialization.h:163:22: required from ‘void ros::serialization::deserialize(Stream&, T&) [with T = sensor_msgs::Image_<std::allocator<void> >; Stream = ros::serialization::IStream]’
[build] /opt/ros/melodic/include/ros/subscription_callback_helper.h:136:21: required from ‘ros::VoidConstPtr ros::SubscriptionCallbackHelperT<P, Enabled>::deserialize(const ros::SubscriptionCallbackHelperDeserializeParams&) [with P = const boost::shared_ptr<const sensor_msgs::Image_<std::allocator<void> > >&; Enabled = void; ros::VoidConstPtr = boost::shared_ptr<const void>]’
[build] /opt/ros/melodic/include/ros/subscription_callback_helper.h:118:24: required from here
[build] /opt/ros/melodic/include/sensor_msgs/Image.h:250:21: error: ‘struct sensor_msgs::Image_<std::allocator<void> >’ has no member named ‘encoding’
[build] 250 | stream.next(m.encoding);
[build] | ~~^~~~~~~~
[build] /opt/ros/melodic/include/sensor_msgs/Image.h:253:21: error: ‘struct sensor_msgs::Image_<std::allocator<void> >’ has no member named ‘data’
[build] 253 | stream.next(m.data);
[build] | ~~^~~~
[build] In file included from /opt/ros/melodic/include/sensor_msgs/Image.h:18,
[build] from ../main.cpp:4:
[build] /opt/ros/melodic/include/std_msgs/Header.h: In instantiation of ‘static void ros::serialization::Serializer<std_msgs::Header_<ContainerAllocator> >::allInOne(Stream&, T) [with Stream = ros::serialization::IStream; T = std_msgs::Header_<std::allocator<void> >&; ContainerAllocator = std::allocator<void>]’:
[build] /opt/ros/melodic/include/std_msgs/Header.h:197:5: required from ‘static void ros::serialization::Serializer<std_msgs::Header_<ContainerAllocator> >::read(Stream&, T&) [with Stream = ros::serialization::IStream; T = std_msgs::Header_<std::allocator<void> >; ContainerAllocator = std::allocator<void>]’
[build] /opt/ros/melodic/include/ros/serialization.h:163:22: required from ‘void ros::serialization::deserialize(Stream&, T&) [with T = std_msgs::Header_<std::allocator<void> >; Stream = ros::serialization::IStream]’
[build] /opt/ros/melodic/include/ros/serialization.h:719:16: required from ‘void ros::serialization::IStream::next(T&) [with T = std_msgs::Header_<std::allocator<void> >]’
[build] /opt/ros/melodic/include/sensor_msgs/Image.h:247:18: required from ‘static void ros::serialization::Serializer<sensor_msgs::Image_<ContainerAllocator> >::allInOne(Stream&, T) [with Stream = ros::serialization::IStream; T = sensor_msgs::Image_<std::allocator<void> >&; ContainerAllocator = std::allocator<void>]’
[build] /opt/ros/melodic/include/sensor_msgs/Image.h:256:5: required from ‘static void ros::serialization::Serializer<sensor_msgs::Image_<ContainerAllocator> >::read(Stream&, T&) [with Stream = ros::serialization::IStream; T = sensor_msgs::Image_<std::allocator<void> >; ContainerAllocator = std::allocator<void>]’
[build] /opt/ros/melodic/include/ros/serialization.h:163:22: required from ‘void ros::serialization::deserialize(Stream&, T&) [with T = sensor_msgs::Image_<std::allocator<void> >; Stream = ros::serialization::IStream]’
[build] /opt/ros/melodic/include/ros/subscription_callback_helper.h:136:21: required from ‘ros::VoidConstPtr ros::SubscriptionCallbackHelperT<P, Enabled>::deserialize(const ros::SubscriptionCallbackHelperDeserializeParams&) [with P = const boost::shared_ptr<const sensor_msgs::Image_<std::allocator<void> > >&; Enabled = void; ros::VoidConstPtr = boost::shared_ptr<const void>]’
[build] /opt/ros/melodic/include/ros/subscription_callback_helper.h:118:24: required from here
[build] /opt/ros/melodic/include/std_msgs/Header.h:194:21: error: ‘struct std_msgs::Header_<std::allocator<void> >’ has no member named ‘frame_id’
[build] 194 | stream.next(m.frame_id);
[build] | ~~^~~~~~~~
[build] Elapsed time: 3 s. (time), 0.000461 s. (clock)
I am testing ROS with gcc
's ubsan
, a sanitizer for detecting undefined behavior. Below is an issue ubsan found in serialization.h
.
/opt/ros/kinetic/include/ros/serialization.h:234:5: runtime error: store to misaligned address 0x60600000aca4 for type 'double', which requires 8 byte alignment
0x60600000aca4: note: pointer points here
30 00 00 00 be be be be be be be be be be be be be be be be be be be be be be be be be be be be
^
The issue was detected when I tested turtlesim
. To reproduce the issue, compile turtlesim
with '-fsantize=ubsan
. Then, run rosrun turtlesim turtlesim_node
in one terminal, and rosrun turtlesim draw_square
in another terminal, and then you will get the runtime error and see the message above. Please let me know, if you need more details for reproducing the error message.
Many times misalignment is only a minor issue or even by design, but I am not sure if it is the case here, given that the misalignment occurs in the core of ROS.
Hi @peci1,
We are running into some build problems with the 0.7.3 version of rostime
:
[3/4] Building CXX object CMakeFiles\rostime.dir\src\time.cpp.obj
FAILED: CMakeFiles/rostime.dir/src/time.cpp.obj
C:\PROGRA~2\MICROS~2\2019\ENTERP~1\VC\Tools\MSVC\1429~1.301\bin\Hostx64\x64\cl.exe /nologo /TP -DBOOST_CHRONO_DYN_LINK -DBOOST_CHRONO_NO_LIB -DBOOST_DATE_TIME_DYN_LINK -DBOOST_DATE_TIME_NO_LIB -DBOOST_SYSTEM_DYN_LINK -DBOOST_SYSTEM_NO_LIB -DBOOST_THREAD_DYN_LINK -DBOOST_THREAD_NO_LIB -DNOMINMAX -DROS_BUILD_SHARED_LIBS=1 -DWIN32_LEAN_AND_MEAN -D_USE_MATH_DEFINES -Drostime_EXPORTS -I%SRC_DIR%\ros-noetic-rostime\src\work\include -external:I%PREFIX%\Library\include -external:W0 /DWIN32 /D_WINDOWS /W3 /GR /EHsc /MD /O2 /Ob2 /DNDEBUG /D _VARIADIC_MAX=10 /Zc:__cplusplus /showIncludes /FoCMakeFiles\rostime.dir\src\time.cpp.obj /FdCMakeFiles\rostime.dir\ /FS -c %SRC_DIR%\ros-noetic-rostime\src\work\src\time.cpp
%SRC_DIR%\ros-noetic-rostime\src\work\src\time.cpp(86): error C2766: explicit specialization; 'MAX' has already been defined
%SRC_DIR%\ros-noetic-rostime\src\work\include\ros\duration.h(139): note: see previous definition of 'public: static ros::Duration const ros::DurationBase<ros::Duration>::MAX'
Full log: https://github.com/RoboStack/ros-noetic/actions/runs/7732212508/job/21081638956
It seems related to 94adcfb
Do you have an idea how to go about it?
Thanks,
Tobi
/cc @traversaro
Hello,
This is my first time compiling ROS into a C++ application, so please bear with me if I'm missing something.
I'm putting together a small application to publish messages using ROS's infrastructure. I have the following include at the top of my file:
#include "ros/ros.h"
Which results in:
Cannot open include file: 'sys/time.h': No such file or directory testprogram c:\opt\ros\melodic\x64\include\ros\time.h 68
Looking in time.h, I see that it expects WIN32 to be defined to include sys/timeb.h (which exists in Windows) as opposed to sys/time.h (which does not). There seems to be an assumption that WIN32 will be defined in Windows applications, but I have stumbled across a situation where it isn't.
I am using a fairly recent version of Visual Studio 2017, and my program is a console x64 build, and as such, does not have WIN32 defined by default. I'm not sure it is a reliable #define to select between timeb.h and time.h.
Perhaps another built-in preprocessor directive could be used instead?
https://docs.microsoft.com/en-us/cpp/preprocessor/predefined-macros?view=vs-2019
All this being said, the following workaround does the trick: If I include <windows.h> before including ros/time.h, it no longer complains about the issue.
I've just noticed that neither roscpp nor rospy provide any easy means of constructing time in miliseconds or microseconds. Why is that? Wouldn't it be nice to have constants like MSEC_IN_NSEC
and USEC_IN_NSEC
or something similar? Also, the magic number 1000000000
shows up a lot in the source code. This could also be converted to a constant like NSEC_IN_SEC
.
With these constants, some time values could be constructed more predictably without the constant fear of floating-point numbers imprecision. If you e.g. specify the length of a pulse of a lidar, you're handling pretty small numbers (microseconds), and you want them to be precise.
Would a PR adding these constants/macros welcome, or is there a good (design?) reason why these values are not provided?
As well, I can imagine adding functions like TimeBase::fromMSec()
etc., but that would be a bit larger API change (though ABI should remain untouched).
I am testing the package with ThreadSanitizer, aka TSan, a GCC/Clang feature for detecting data races. Below is one (among many) data race detected by TSan. The location of the error is shown (using -g option).
To reproduce the issue, compile the package with "-fsanitize=thread -g", launch turtlesim_node, and then you will see the data race warning.
WARNING: ThreadSanitizer: data race (pid=20894)
Write of size 8 at 0x7d1800017fa0 by main thread:
#0 free <null> (libtsan.so.0+0x000000025819)
#1 <null> <null> (libglib-2.0.so.0+0x000000047289)
#2 main /home/zhfu/catkin_ws/src/turtlesim_official/src/turtlesim.cpp:60 (turtlesim_official_turtlesim_node+0x00000041d178)
Previous write of size 8 at 0x7d1800017fa0 by thread T5:
#0 calloc <null> (libtsan.so.0+0x00000002565d)
#1 g_malloc0 <null> (libglib-2.0.so.0+0x00000004f810)
Thread T5 'pool' (tid=20908, running) created by main thread at:
#0 pthread_create <null> (libtsan.so.0+0x000000027577)
#1 <null> <null> (libglib-2.0.so.0+0x00000008e8ff)
#2 main /home/zhfu/catkin_ws/src/turtlesim_official/src/turtlesim.cpp:59 (turtlesim_official_turtlesim_node+0x00000041d173)
SUMMARY: ThreadSanitizer: data race ??:0 __interceptor_free
Full details in my question here: Buildroot: CMake Error at FindPackageHandleStandardArgs.cmake:230 (message): Could NOT find Boost (missing: thread) (found version "1.80.0")
.
Any ideas on how to solve this?
I'm building with Buildroot for an embedded Linux board. I just upgraded to the latest version of the Buildroot boost
package, version 1.80.0, as shown here: https://github.com/buildroot/buildroot/blob/master/package/boost/boost.mk#L7
double timer = 49.9999999999;
std::cout << timer<<" "<<ros::Duration(timer)<<" "<<ros::Duration(timer).toSec()<<" "<<ros::Duration(ros::Rate(1/timer))<<" "<<ros::Time(timer));
Output:
50 49.1000000000 50 50.000000000 50.000000000
When compiling the rostime package on my machine, I get the following compiler error:
/Users/michel/Developer/kinetic_ws/src/roscpp_core/rostime/include/ros/impl/time.h:170:35: error: no matching conversion for functional-style cast from 'double' to 'pt::microseconds' (aka 'subsecond_duration<boost::posix_time::time_duration, 1000000>')
return pt::from_time_t(sec) + pt::microseconds(nsec/1000.0);
Adding an explicit cast to either int32_t or uint32_t seems to solve this issue.
My setup
According to the documentation, ros::Rate should return false if the desired rate was not reached (#37 will make sure that is is also implemented).
However, the docu of WallRate.sleep() says that it will return true if the rate was not reached which is surprising. I think that both classes should behave the same so that the docu (and implementation) of WallRate should be aligned.
Doing a source-based installation I came across a failing test in rostime on OSX which looks similar to #48 / #50 but for the Duration class (TestCase: Duration.ToFromSec). However, it seems it only appears on OSX the test passes on Ubuntu not 100% sure what the difference exactly is.
The following change prevents it:
rostime/include/ros/impl/duration.h line 59
original:
nsec = (int32_t)((d - (double)sec)*1000000000);
modified to:
nsec = (int32_t)((d - (double)sec)*10000000000/10);
Idea: There seems to be problem in bitwise representation. By shifting the whole double by a factor of 10 it seems to be gone and the backwards division by 10 repairs for it.
OSX: 10.11.6
LLVM: version 8.0.0 (clang-800.0.42.1)
Target: x86_64-apple-darwin15.6.0)
This is a test of issue notifications...
In the time.cpp
file, there are several points in which UINT_MAX
is used as the maximum value for 32-bit unsigned integers (i.e. uint32_t
):
roscpp_core/rostime/src/time.cpp
Line 379 in 5507a88
roscpp_core/rostime/src/time.cpp
Line 555 in 5507a88
While UINT_MAX
is indeed the maximum value for 32-bit unsigned integers for the commonly used 64-bit data models (see http://www.unix.org/version2/whatsnew/lp64_wp.html , https://en.wikipedia.org/wiki/64-bit_computing#64-bit_data_models ) there are a few platform for which it should be a more appropriate to use explicitly the 32-bit unsigned maximum, i.e. UINT32_MAX
.
Unfortunately, I far as I understand UINT32_MAX
is standard only since C++11, so I don't know a clean way to fix this using C++98 .
Generating cmake cache would result in command line error like this:
E0992 command-line error: invalid macro definition: =
It does not mention where this =
is located but in the cpp code it locates at the very begining in line 1.
However I dont see any error on the command line preprocessor
1> Command line: "cmd.exe" /c ""C:\PROGRAM FILES (X86)\MICROSOFT VISUAL STUDIO\2019\PREVIEW\COMMON7\IDE\COMMONEXTENSIONS\MICROSOFT\CMAKE\CMake\bin\cmake.exe" -G "Ninja" -DCMAKE_INSTALL_PREFIX:PATH="C:\test\src\out\install\x64-Debug" -DCMAKE_CXX_COMPILER:FILEPATH="C:/Program Files (x86)/Microsoft Visual Studio/2019/Preview/VC/Tools/MSVC/14.22.27812/bin/HostX64/x64/cl.exe" -DCMAKE_C_COMPILER:FILEPATH="C:/Program Files (x86)/Microsoft Visual Studio/2019/Preview/VC/Tools/MSVC/14.22.27812/bin/HostX64/x64/cl.exe" -DCMAKE_BUILD_TYPE="Debug" -DCMAKE_MAKE_PROGRAM="C:\PROGRAM FILES (X86)\MICROSOFT VISUAL STUDIO\2019\PREVIEW\COMMON7\IDE\COMMONEXTENSIONS\MICROSOFT\CMAKE\Ninja\ninja.exe" "C:\test\src" 2>&1"
1> Working directory: C:\test\src\out\build\x64-Debug```
A declarative, efficient, and flexible JavaScript library for building user interfaces.
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google ❤️ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.