Accelerating ROS simulation to faster than real time
Hi,
It's hard to believe, but according to my research I am the only one who would like to accelerate simulation of a ROS robot... and it seems to be an almost impossible task.
It looks like when I create a node that generates faster than real time clock
topic, it totally messes up the simulation. Not even bags can be replayed faster, than real time.
The reason, as I found is that a huge part of the ROS system relies on WallTime
and WallDuration
s, and not just by using these classes, but by doing waits and sleeps in wall times relevant in the simulation.
I tried to create an accelerated version of ROS:
- Removed the definitions of
WallTime
andSteadyTime
, replaced them withtypedef
s toTime
- Removed the definition of
WallDuration
and replaced it withtypedef
toDuration
- Scaled all timed waits with my desired acceleration factor
- Instead of a
clock
topic I share the time from a timer process in shared memory, so all calls toTime::now()
are in sync
But now I get stuck in various timing issues related to transformations, more specifically I get errors, like:
Lookup would require extrapolation into the future. Requested time 1270387817.717999935 but the latest data is at time 1270387817.482000113
(Note that the timestamp is intentionally in the past, as it is an accelerated time, not the real time.)
Now in the stack trace, as I see, this is happening in waitForTransform()
call, which is called with Time(0)
by the simulation (stdr_simulator). And this is weird, semantically, as I would think (by the name of it) that waitForTransform()
is intended to wait, until the transform is available, not throw an exception that it is not (yet).
Could please someone help here?
UPDATE I think the problem is somehow related to BufferCore::getLatestCommonTime()
. Somehow the cached times does not match the cached transforms.
Time(0)
has special semantics in TF, it basically means "latest transform".But in general if
use_sim_time
is set and there is a publisher on/clock
, I would expect things to 'just work'. I've not done it myself, but what you're doing seems rather convoluted.No, it does not, because timer delays are expected to be real time. So if you set a timer to 10Hz, it will fire 10Hz real frequency, and not accelerated frequency. This is because
WallTime
is used, and pthread conditional waits are called with the nominal duration.Also, I know about the
Time(0)
semantics, it is just after a while, insidewaitForTransform()
is replaced by some common time of the two frames (which we are trying to obtain the transformation between). Now this common time is somehow incorrect, as no actual transformation exists with that.Using simulated time is done with Gazebo and some other sims as well, so your statements confuse me.
I'm not saying you're wrong, but I would just make sure what you're doing is absolutely necessary, as it would be unfortunate otherwise.
If what you're doing is inside
stdr
, then that could be true. It may be that thestdr
authors didn't (want to) consider FTR / STR cases and just use WallTime everywhere.No, I found that ROS core things fire at wrong times. So wrong, that my robot teleports off the map. It has nothing to do with the simulator, I have already excluded that option via debugging. I have recompiled the whole ROS infrastructure with my changes, as I found many places which depend on the
speed of the clock...
Then I would urge you to report that on the proper issue trackers.
If with "ROS core" you actually mean
roscpp
and the other pkgs inros_comm
, then the tracker would be ros/ros_comm/issues.