Giter Site home page Giter Site logo

ros2_rust's Introduction

ROS 2 for Rust

Target Status
Ubuntu 20.04 Build Status

Introduction

This is a set of projects (the rclrs client library, code generator, examples and more) that enables developers to write ROS 2 applications in Rust.

Features and limitations

The current set of features include:

  • Message generation
  • Support for publishers and subscriptions
  • Loaned messages (zero-copy)
  • Tunable QoS settings
  • Clients and services

Lots of things are still missing however, see the issue list for an overview. You are very welcome to contribute!

Since the client library is still rapidly evolving, there are no stability guarantees for the moment.

Sounds great, how can I try this out?

Here are the steps for building the ros2_rust examples in a vanilla Ubuntu Focal installation. See the in-depth guide for building ros2_rust packages for more details and options, including a Docker-based setup.

# Install Rust, e.g. as described in https://rustup.rs/
# Install ROS 2 as described in https://docs.ros.org/en/humble/Installation.html
# Assuming you installed the minimal version of ROS 2, you need these additional packages:
sudo apt install -y git libclang-dev python3-pip python3-vcstool # libclang-dev is required by bindgen
# Install these plugins for cargo and colcon:
cargo install --debug cargo-ament-build  # --debug is faster to install
pip install git+https://github.com/colcon/colcon-cargo.git
pip install git+https://github.com/colcon/colcon-ros-cargo.git

mkdir -p workspace/src && cd workspace
git clone https://github.com/ros2-rust/ros2_rust.git src/ros2_rust
vcs import src < src/ros2_rust/ros2_rust_humble.repos
. /opt/ros/humble/setup.sh
colcon build

Then, to run the minimal pub-sub example, do this:

# In a new terminal (or tmux window)
. ./install/setup.sh
ros2 run examples_rclrs_minimal_pub_sub minimal_publisher
# In a new terminal (or tmux window)
. ./install/setup.sh
ros2 run examples_rclrs_minimal_pub_sub minimal_subscriber

or

# In a new terminal (or tmux window)
. ./install/setup.sh
ros2 launch examples_rclrs_minimal_pub_sub minimal_pub_sub.launch.xml

Further documentation articles:

ros2_rust's People

Contributors

bergercookie avatar christopherjreid avatar esteve avatar fawdlstty avatar flynneva avatar guelakais avatar jhdcs avatar keenanjohnson avatar ksron avatar lavieestdure avatar lelongg avatar luca-della-vedova avatar marcbone avatar marcoesposito1988 avatar maspe36 avatar miferco97 avatar mohitsaxenaknoldus avatar mxgrey avatar nizerlak avatar nnarain avatar nnmm avatar nwn avatar ottojo avatar ruffsl avatar soya-onishi avatar tacha-s avatar tprk77 avatar uwearzt avatar vrichardjp avatar wep21 avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

ros2_rust's Issues

Rebuild the workspace on change

I've successfully built the ros2_rust repo as part of my ROS workspace and have successfully run the talker/listener example.

However, If I make some changes to the the code, say in subscription.rs and re-run colcon build the changes to the file don't seem to have any effect.

I know they should have an effect because for example I'm introducing a clear syntax error.
Additionally I haven't managed to rebuild the rust code either when I'm passing --cmake-configure or --cmake-clean-cache to colcon.

Only way I've manged to do this is by removing completely the install, build directories

is there something I'm missing?

Thanks

Use of ament_cargo directory in ros2_rust examples

In the rclrs_examples CMakeLists.txt files, one can find the following lines:

file(WRITE "${CMAKE_BINARY_DIR}/.cargo/config"
"\
[build]\n\
target-dir = 'ament_cargo/${PROJECT_NAME}/target'\n\
rustflags = [\
${_native_libraries_dirs}
]\n\
"
)

file(COPY "${CMAKE_SOURCE_DIR}/Cargo.toml" DESTINATION "${CMAKE_BINARY_DIR}/")
file(APPEND "${CMAKE_BINARY_DIR}/Cargo.toml" "${_crates_dependencies}")

add_custom_command(
    OUTPUT
    ¦   ${CMAKE_BINARY_DIR}/ament_cargo/${PROJECT_NAME}/target/release/rclrs_publisher
    ¦   ${CMAKE_BINARY_DIR}/ament_cargo/${PROJECT_NAME}/target/release/rclrs_subscriber
    COMMAND cargo build --release --manifest-path "${CMAKE_BINARY_DIR}/Cargo.toml"
    DEPENDS
    ¦   ${CMAKE_BINARY_DIR}/src/rclrs_publisher.rs
    ¦   ${CMAKE_BINARY_DIR}/src/rclrs_subscriber.rs
)

Is there a particular reason we are putting the output executables under the ament_cargo directory?

Failed to colcon build with ros2:master source on Ubuntu20.04.

Colcon Build Failure

--- stderr: builtin_interfaces
CMake Error at /root/ros2_ws/ros2-rust_ws/install/rosidl_generator_rs/share/rosidl_generator_rs/cmake/rosidl_generator_rs_generate_interfaces.cmake:15 (find_package):
  By not providing "Findrmw_implementation_cmake.cmake" in CMAKE_MODULE_PATH
  this project has asked CMake to find a package configuration file provided
  by "rmw_implementation_cmake", but CMake did not find one.

  Could not find a package configuration file provided by
  "rmw_implementation_cmake" with any of the following names:

    rmw_implementation_cmakeConfig.cmake
    rmw_implementation_cmake-config.cmake

  Add the installation prefix of "rmw_implementation_cmake" to
  CMAKE_PREFIX_PATH or set "rmw_implementation_cmake_DIR" to a directory
  containing one of the above files.  If "rmw_implementation_cmake" provides
  a separate development package or SDK, be sure it has been installed.
Call Stack (most recent call first):
  /root/ros2_ws/ros2-rust_ws/install/ament_cmake_core/share/ament_cmake_core/cmake/core/ament_execute_extensions.cmake:48 (include)
  /root/ros2_ws/ros2-rust_ws/install/rosidl_cmake/share/rosidl_cmake/cmake/rosidl_generate_interfaces.cmake:286 (ament_execute_extensions)
  CMakeLists.txt:16 (rosidl_generate_interfaces)


make: *** [Makefile:1392: cmake_check_build_system] Error 1

Procedure

  1. set up ros2 master colcon workspace with https://index.ros.org/doc/ros2/Installation/Foxy/Linux-Development-Setup/
  2. add https://github.com/ros2-rust/ros2_rust into colcon workspace
  3. then colcon build

Releasing and Packaging

A big part in making Rust more attractive for ROS2 community and vice versa would be in providing released packages, making rclrs (or portions of) more readable installable. As may ROS users may be unfamiliar with Rust, given ROS's legacy with C++ and Python, simplifying installation could help lower the barrier and learning curve. Ideally, it would be nice to see rclrs as easy to include as an external crate, just as relying upon any other package released on crates.io , but I'd also be happy if debians could be shipped via synced ROS2 releases.

Merge `rclrs_common` into `rclrs`?

I was wondering if it would be a good idea to merge rclrs_common into rclrs. Currently, there's not all that much inside the crate, and it only seems to confuse my IDE while I'm working on rclrs, unless I put in a workaround into the Cargo.toml to reference the crate (that I have to remove before build-time, otherwise the build fails).

If we merged rclrs_common into rclrs this would no longer be a problem. Additionally, it would also potentially allow us to make wrappers around the underlying rcl error codes a bit more easily, since rclrs is where the bindings to rcl are actually generated.

Outreach with the Rust Community

It'd be nice to get some more feedback on the design/implementation of rclrs from the larger Rust community, e.g. are there better approaches to wrapping the rcl c library, code generation, testing practices, API pattern that ROS users could benefit from. Additionally, many Rust users may appreciate what the rest of the ROS2 ecosystem has to offer in terms of robotic software development, growing the number of users and subsequent contributions.

Move to use `Arc` instead of `Rc`

In order to be able to use rclrs in multi-threaded applications, we will need to move away from single-threaded constructs such as Rc. As such, we should go through and convert them to Arc (or other multi-threaded equivalents) soon, while the library is still small.

Status?

Last commit was 8 months ago. Is this still under development or should I fork this and attempt to continue it (poorly)?

Building and running the docker throws Warning/Error

Hello,
when building and running the docker this error pops up:
not found: "/opt/overlay_ws/install/rclrs/share/rclrs/local_setup.bash"

Do I do something wrong in the build process or does someone else have the same error?

Should we use Corrosion for CMake?

Rust has a crate called corrosion that is supposed to simplify the build process when CMake is required. Would the CMake in our current project benefit from using this crate?

If we decide to use this, we will need to raise the minimum required CMake version to at least 3.12. However, using that version of CMake means that we won't need to include corrosion within the project - we could instead use CMake's FetchContent module (which came into being in version 3.11).

Implement `WaitSet` wrapper struct

While updating the code to Rolling, we noticed that it's very important that the WaitSets are destroyed properly. However, as they are an FFI type, Rust can't Drop them as-is.

We need to construct a wrapper struct around the WaitSet that implements Drop to call the proper code to dispose of the WaitSet. A thing to consider, though: WaitSet disposal is not guaranteed. If a WaitSet is improperly Dropped, should we panic!?

WaitSet source documentation: https://github.com/ros2/rcl/blob/master/rcl/include/rcl/wait.h#L77-L143

Make compatible with Rolling

Since this client library is under such active development, perhaps we should make it so that it is compatible with / buildable on Rolling?

I will look into what needs to change for this to happen.

Idiomatic API for Rust

Rather than merely a wrapper around the rcl c library and types, what other ways can we make the rclrs API more Idiomatic to rust design patterns and style? How do we expect to expose error handling, logging, composition of nodes, etc. This is intentionally open ended, but please feel free to narrow in scope.

Dashing support

Do you have a plan to support Dashing?
Dashing is the first LTS ROS2 distro. I think it is great if ros2_rust supports it!

WaitSet::wait does not return ready subscription entities

Related to #104.
WaitSet::wait() does not collect entities that have messages, and this causes minimal_subscriber does not display any messages from minimal_publisher .

Expected Behavior
correct and return entities that have messages from publisher.

Related code is here
Above code check this is not null. i.e. wait_set_entry.is_null() in WaitSet::wait() should attach not operator.

Reduce amount of bindings

While working on rclrs, I've noticed a lot of warnings being generated about u128 not being FFI safe. While this is true, fixing that is beyond our power.

What ISN'T beyond our power is removing the bindings completely - as it seems that most of these bindings are for libraries like math.h, which aren't going to be very useful to users of rclrs. As such, we should look through the generated code, and see what can be done to block unneeded functions from showing up in the bindings.

IDL Support (Dashing+ Support)

I wanted to separate out this specific issue to prevent overloading the topic in the main Dashing support thread. Specifically, this is a discussion for the planned feature of IDL support, required by ROS2 Dashing and later versions.

Given the discussions there, there seem to be a couple of issues that need resolving, one major one being the choice of either using static compilation or introspection. I would be interested in any opinions that people have about that, as I look myself into how best to go about this.

Add Windows CI jobs

GitHub offers a free Windows CI – we should add equivalent jobs to the ones we have for Ubuntu.

Build Error

Hi,
when I try to compile it (in docker Ubuntu 16.04) I got this error:

+++ Building 'tinyxml_vendor'
==> '. /rust_ws/build_isolated/tinyxml_vendor/cmake__build.sh && /usr/bin/make cmake_check_build_system' in '/rust_ws/build_isolated/tinyxml_vendor'
==> '. /rust_ws/build_isolated/tinyxml_vendor/cmake__build.sh && /usr/bin/make -j3 -l3' in '/rust_ws/build_isolated/tinyxml_vendor'
[ 12%] Performing patch step for 'tinyxml-2.6.2'
No such file or directory
CMakeFiles/tinyxml-2.6.2.dir/build.make:101: recipe for target 'tinyxml-2.6.2/src/tinyxml-2.6.2-stamp/tinyxml-2.6.2-patch' failed
make[2]: *** [tinyxml-2.6.2/src/tinyxml-2.6.2-stamp/tinyxml-2.6.2-patch] Error 1
CMakeFiles/Makefile2:67: recipe for target 'CMakeFiles/tinyxml-2.6.2.dir/all' failed
make[1]: *** [CMakeFiles/tinyxml-2.6.2.dir/all] Error 2
Makefile:127: recipe for target 'all' failed
make: *** [all] Error 2

Any help? I do not find any logs to understand it!

Missing benchmark tests

A topic that emerged from the previous Rust WG meeting is the fact that rclrs currently lacks benchmarks for testing performance or efficiency of the client library. Adding such benchmarks could go a long way in vetting and quantifying PR improvements, such as when validating changes to add array IDL support for more advanced message types. This may also be a good first issue.

https://discourse.ros.org/t/ros-rust-wg-meeting-2020-11-05/17101

Missing Unit Tests

Similar to #33, the code on a whole lacks unit testing. We should implement these tests sooner rather than later, since unit tests should ideally be created at around the same time the code that they're testing is made.

For the Rust portions of the project, I think the files are small enough that we can go with the standard Rustic way of adding unit testing in a module at the bottom of a file. Once the files get bigger, we can consider moving them off into their own folder. We will need to teach colcon-cargo how to run these tests, but that shouldn't be too difficult.

The other languages should follow the standard ROS 2 rules for unit testing.

Port QOS to RCLRS Core

The QOS profiles need to be ported to the new rclrs_core crate.

This will probably be as simple as copying over the current QOS implementation.

fatal error: 'stdbool.h' file not found

First off, great work getting colcon integrated with cargo, I know this has been an issue for a while. I tried to build the examples as per the readme and got the following compile error on Galactic:

Starting >>> rclrs_msg_utilities
Finished <<< rclrs_msg_utilities [1.85s]                
Starting >>> rosidl_generator_rs
Starting >>> rclrs
Finished <<< rosidl_generator_rs [1.24s]                                                   
Starting >>> rosidl_default_runtime
Starting >>> rosidl_default_generators
Finished <<< rosidl_default_runtime [0.54s]                                                                                              
Finished <<< rosidl_default_generators [0.53s]
Starting >>> builtin_interfaces
Finished <<< builtin_interfaces [5.14s]                                                      
Starting >>> std_msgs
--- stderr: rclrs                                                                   
error: failed to run custom build command for `rclrs v0.1.0 (/home/andy/Documents/dev/rust_ros_ws/src/ros2_rust/rclrs)`

Caused by:
  process didn't exit successfully: `/home/andy/Documents/dev/rust_ros_ws/build/rclrs/debug/build/rclrs-bd6ecbce6f48e29b/build-script-build` (exit status: 101)
  --- stdout
  cargo:rustc-link-search=native=/home/andy/Documents/dev/rust_ros_ws/install/rclrs_msg_utilities/lib
  cargo:rustc-link-search=native=/opt/ros/galactic/lib
  cargo:rustc-link-lib=dylib=rcl
  cargo:rustc-link-lib=dylib=rcutils
  cargo:rustc-link-lib=dylib=rmw
  cargo:rustc-link-lib=dylib=rmw_implementation

  --- stderr
  /opt/ros/galactic/include/rcutils/allocator.h:25:10: fatal error: 'stdbool.h' file not found
  /opt/ros/galactic/include/rcutils/allocator.h:25:10: fatal error: 'stdbool.h' file not found, err: true
  thread 'main' panicked at 'Unable to generate bindings: ()', build.rs:42:39
  note: run with `RUST_BACKTRACE=1` environment variable to display a backtrace
Error in cargo-ament-build

Caused by:
    'cargo check' failed.
---
Failed   <<< rclrs [11.2s, exited with code 1]
Aborted  <<< std_msgs [14.3s]                                 

Summary: 5 packages finished [23.2s]
  1 package failed: rclrs
  1 package aborted: std_msgs
  1 package had stderr output: rclrs
  1 package not processed

I use Galactic for other ros2 work, so I'm sure that it is being sourced correctly.

Edit: My Rust version is 1.58.1 stable

WaitSet::wait does not wait indefinitely when timeout is None

Hi.
I am new to ros2 with rust and tried to run minimal_publisher and minimal_subscriber.
However minimal_subscriber does not work in expect ( no output is displayed ).
After investigation, I found that there are some problems in WaitSet::wait().

Current Behavior
Even if passing None to WaitSet::wait, it does not wait until some messages are passed and return immediately (i.e. non-blocking).

Expected Behavior
Waiting (blocking) indefinitely until some messages are passed.

As described here, timeout_ns should be minus if procedure wants to wait indefinitely, but current implementation make rcl_wait non-blocking function by passing zero.

Building/testing `rosidl_runtime_rs` with pure cargo produces linker errors

For the rosidl_runtime_rs package, running cargo test produces a linker error complaining about not finding -lrosidl_runtime_c. This is despite sourcing the ROS 2 distro's install directory before.

A workaround is to set the LIBRARY_PATH environment variable to the directory containing librosidl_runtime_c.so:

LIBRARY_PATH=[directory containing librosidl_runtime_c.so] cargo test

message and crate generation

I am trying to build https://github.com/esteve/ros2_rust/pull/3 but the examples fail because of the missing std_msgs crate. I manually cloned common_interfaces to the workspace and the std_msgs get successfully generated in install/std_msgs/share/std_msgs/rust/src.
I then added std_msgs = { path = '[...]/rust_ws/install/std_msgs/share/std_msgs/rust' } to the dependencies section in the rclrs_examples but cargo still cannot find the std_msgs crate.
I did not apply the patch rosidl_typesupport_ros2_rust.patch since the rust code was successfully generated.

How do I set the path to the crate such that cargo is able to build the examples?
Also, is it possible to reuse already installed message definitions (e.g. from package ros-crystal-std-msgs) instead of duplicating the messages in the workspace?

Use of second `ros2_rust` directory inside the `src` directory

In the README, the following is provided for setting up the workspace:

mkdir -p ~/ros2_rust_ws/src/ros2-rust
cd ~/ros2_rust_ws/src/ros2-rust
git clone https://github.com/ros2-rust/ros2_rust.git
Why not clone it directly under src/?

Is there a reason for having nested ros2_rust directories, i.e., src/ros2-rust/ros2_rust?
Can we remove the intermediate to simplify the instructions?

Replace `failure` with `thiserror`

The failure crate currently used by ros2_rust is deprecated. As such, we should probably move towards a different error-handling crate.

The failure crate maintainer notes in the readme that the thiserror crate is a near drop-in replacement, so that may be the direction we want to take.

Port RCL Errors to RCLRS Core

The RCL errors need to be ported to the new RCLRS Core crate.

Due to thiserror apparently not being no_std compatible (as far as I can tell), we will have to rely on more "old-fashioned" error handling - namely, really descriptive enums...

Array content not published

When publishing messages that consist of an (unspecified length) array, that array is not filled and always received empty.

I'm busy making a ROS2 (Foxy) driver for an old Neato vacuum robot using https://github.com/LoyVanBeek/neato_rust. I just started learning Rust and wanted to do more ROS2, so why not cause myself a lot of trouble learning 2 things at the same time?

The Rust interface with the robot over serial works fine, next step is to wrap that driver in a ros2-rust Node. I can perfectly fine publish a message, but when I publish a sensor_msgs/LaserScan and echo the topic, the ranges field is just empty. Same for intensities.

From what I gather, the generated code concerning a LaserScan message is this, but AFAICT, there is no code generated to handle the ranges/intensities:

#[derive(Default)]
pub struct LaserScan {
    pub header: std_msgs::msg::Header,
    pub angle_min: f32,
    pub angle_max: f32,
    pub angle_increment: f32,
    pub time_increment: f32,
    pub scan_time: f32,
    pub range_min: f32,
    pub range_max: f32,
    pub ranges: Vec<f32>,
    pub intensities: Vec<f32>,
}

#[link(name = "sensor_msgs__rosidl_typesupport_c__rsext")]
extern "C" {
    fn sensor_msgs_msg_laser_scan_get_type_support() -> uintptr_t;

    fn sensor_msgs_msg_laser_scan_get_native_message(
    angle_min: f32,
    angle_max: f32,
    angle_increment: f32,
    time_increment: f32,
    scan_time: f32,
    range_min: f32,
    range_max: f32,
    ) -> uintptr_t;

    fn sensor_msgs_msg_laser_scan_destroy_native_message(message_handle: uintptr_t) -> ();

    fn sensor_msgs_msg_laser_scan_angle_min_read_handle(message_handle: uintptr_t) -> f32;
    fn sensor_msgs_msg_laser_scan_angle_max_read_handle(message_handle: uintptr_t) -> f32;
    fn sensor_msgs_msg_laser_scan_angle_increment_read_handle(message_handle: uintptr_t) -> f32;
    fn sensor_msgs_msg_laser_scan_time_increment_read_handle(message_handle: uintptr_t) -> f32;
    fn sensor_msgs_msg_laser_scan_scan_time_read_handle(message_handle: uintptr_t) -> f32;
    fn sensor_msgs_msg_laser_scan_range_min_read_handle(message_handle: uintptr_t) -> f32;
    fn sensor_msgs_msg_laser_scan_range_max_read_handle(message_handle: uintptr_t) -> f32;
}

impl LaserScan {
  fn get_native_message(&self) -> uintptr_t {
    return unsafe { sensor_msgs_msg_laser_scan_get_native_message(
    self.angle_min,
    self.angle_max,
    self.angle_increment,
    self.time_increment,
    self.scan_time,
    self.range_min,
    self.range_max,
    ) };
  }

  fn destroy_native_message(&self, message_handle: uintptr_t) -> () {
    unsafe {
      sensor_msgs_msg_laser_scan_destroy_native_message(message_handle);
    }
  }

  #[allow(unused_unsafe)]
  fn read_handle(&mut self, _message_handle: uintptr_t) -> () {
    unsafe {
      {
      self.angle_min = sensor_msgs_msg_laser_scan_angle_min_read_handle(_message_handle);
      self.angle_max = sensor_msgs_msg_laser_scan_angle_max_read_handle(_message_handle);
      self.angle_increment = sensor_msgs_msg_laser_scan_angle_increment_read_handle(_message_handle);
      self.time_increment = sensor_msgs_msg_laser_scan_time_increment_read_handle(_message_handle);
      self.scan_time = sensor_msgs_msg_laser_scan_scan_time_read_handle(_message_handle);
      self.range_min = sensor_msgs_msg_laser_scan_range_min_read_handle(_message_handle);
      self.range_max = sensor_msgs_msg_laser_scan_range_max_read_handle(_message_handle);
      }
    }
  }
}

impl rclrs_common::traits::Message for LaserScan {
  fn get_native_message(&self) -> uintptr_t {
    return self.get_native_message();
  }

  fn destroy_native_message(&self, message_handle: uintptr_t) -> () {
    self.destroy_native_message(message_handle);
  }

  fn read_handle(&mut self, message_handle: uintptr_t) -> () {
    self.read_handle(message_handle);
  }
}

impl rclrs_common::traits::MessageDefinition<LaserScan> for LaserScan {
  fn get_type_support() -> uintptr_t {
    return unsafe { sensor_msgs_msg_laser_scan_get_type_support() };
  }

  fn static_get_native_message(message: &LaserScan) -> uintptr_t {
    return message.get_native_message();
  }

  fn static_destroy_native_message(message_handle: uintptr_t) -> () {
    unsafe {
      sensor_msgs_msg_laser_scan_destroy_native_message(message_handle);
    }
  }
}

Same issue holds for eg. an Int8MultiArray (which I thought was the simplest message having an array)

I'd love to help out, but this is currently beyond my Rust chops.

Improve build integration with cargo

As mentioned in the README, the current status with CMake is less than settler:

The current examples use CMake to install and build the binaries... and it's really ugly.

The Rust ecosystem uses cargo as it's native build system; thus advancing build framework to better integrate with cargo could go a long way in helping the usability of the client library. Given colcon-cargo is still in early development, how can we improve upon this for rclrs?

Add rustdoc check step to CI

We can check with cargo rustdoc -- -D warnings whether a package's documentation contains any warnings or errors. This could be another step in the CI pipeline.

Improve message generation

Having to include and recompile all the message types any rust project requires is kind of a non-starter:

"Ain't Nobody Got Time for That"
~ Kimberly "Sweet Brown" Wilkins

Are there anyways we can improve upon this, like upstreaming rosidl_generator_rs as one of the default IDL generators, or reusing IDL files generated from rosidl_generator_c? How have other client libraries such as rclpy worked around this? Are there memory safety considerations we should account for? Already I've encountered memory leaks using rclrs that could have been prevented by rustc and RAII.

Improve support for rust language analyzers

During the last Rust WG meeting, members reported difficulties in trying to get rclrs to play nicely with VSCode + Rust-Analyzer. In particular, one of the hangups is that rust-analyzer gets confused by auto generated messages, and can’t recognize them as types. This could tie into some of the other tickets for improving message generation and build integration with cargo, although this ticket specifically tracks issues for improving support for rust language analyzers such as rls or rust-analyzer:

This'll not only aid in rclrs development, but also help downstream users creating their own ROS Rust packages.

Related:

Move repository to github.com/ros2-rust and add members

Hey @lelongg, I've opened this ticket to move this repository to the github.com/ros2-rust organization. Do you want me to add you as a member? You've done a great job with #3 and I just think it's fair to add you as member, but I understand if you'd rather not have this responsibility :-)

Error Running Colcon Build

Hello! I was trying to install the ros2_rust examples in a docker container according to the instructions and I am currently running into an error with the colcon build command.

When I run colcon build exactly as described, I get the following error colcon: error: unrecognized arguments: --packages-up-to

Here's my dockerfile that I'm trying to use for reference. Any help would be appreciated! I think I followed the instructions correctly, but I could be missing something obvious. Thank you!

FROM balenalib/%%BALENA_ARCH%%-ubuntu:focal as base
ARG DEBIAN_FRONTEND=noninteractive

##########################
## ROS2 Foxy Install
##########################

# Install language support for ROS
RUN apt-get update && apt-get install -y \
  locales \
  && locale-gen en_US.UTF-8 \
  && update-locale LC_ALL=en_US.UTF-8 LANG=en_US.UTF-8 \
  && rm -rf /var/lib/apt/lists/*
ENV LANG en_US.UTF-8

# Install ROS2
RUN apt-get update && apt-get install -y \
    curl \
    gnupg2 \
    lsb-release \
    sudo \
  && curl -sSL https://raw.githubusercontent.com/ros/rosdistro/master/ros.key -o /usr/share/keyrings/ros-archive-keyring.gpg \
  && echo "deb [arch=$(dpkg --print-architecture) signed-by=/usr/share/keyrings/ros-archive-keyring.gpg] http://packages.ros.org/ros2/ubuntu $(lsb_release -cs) main" | tee /etc/apt/sources.list.d/ros2.list > /dev/null \
  && apt-get update && apt-get install -y \
    ros-foxy-ros-base \
    ros-foxy-test-interface-files \
    python3-argcomplete \
  && rm -rf /var/lib/apt/lists/*

# Configure Enviroment for ROS
RUN echo "source /opt/ros/foxy/setup.bash" >> ~/.bashrc

##########################
## Rust Install
##########################
ENV PATH=/root/.cargo/bin:$PATH
RUN curl --proto '=https' --tlsv1.2 -sSf https://sh.rustup.rs | sh -s -- --default-toolchain 1.59.0 -y

##########################
## ros2_rust install
##########################
RUN apt-get update && apt-get install -y \
    python3-vcstool \
    libclang-dev \
    clang \
    python3.9 \
    python3.9-dev \
    python3-pip \
    git \
    && rm -rf /var/lib/apt/lists/*

# Install the colcon-cargo and colcon-ros-cargo plugins
RUN pip install git+https://github.com/colcon/colcon-cargo.git git+https://github.com/colcon/colcon-ros-cargo.git
RUN pip install --upgrade pytest
# Install the cargo-ament-build plugin
RUN cargo install cargo-ament-build

RUN mkdir src
RUN git clone https://github.com/ros2-rust/ros2_rust.git src/ros2_rust
RUN vcs import src < src/ros2_rust/ros2_rust_foxy.repos
RUN . /opt/ros/foxy/setup.sh
RUN colcon build --packages-up-to rclrs_examples

CMD sleep infinity

Port WaitSet to RCLRS Core

WaitSets need to be ported to the new rclrs_core crate.

I believe we cannot use Arc or Mutex with the !#[no_std] attribute, so that logic might need to be left up to a higher-level API.

Port Node to RCLRS Core

Nodes needs to be ported to the new rclrs_core crate.

I believe we cannot use Arc or Mutex with the !#[no_std] attribute, so that logic might need to be left up to a higher-level API.

CMake warning when building/exporting `rclrs_examples`

Using colcon build --symlink-install generates a CMake Warning at install/rcutils/share/rcutils/cmake/ament_cmake_export_libraries-extras.cmake:116 saying:

Package `rcutils` exports library `dl` which couldn't be found

Something in the most recent build system refactor must have caused this regression, and must be fixed ASAP.

Get error messages from rcl layer

The rcl layer does not only return an error code, but often also sets the error message (with RCL_SET_ERROR_MSG). rclrs currently ignores this error message, but it could be valuable for developers.

It should be made part of the error type, and populated with rcutils_get_error_string() or rcutils_get_error_state().

Error when generating code for sensor_msgs/JoyFeedback

The sensor_msgs/JoyFeedback message has a field called type, which is a keyword in Rust.
A suggested fix is to prefix with r# but of course this should be done automagically.

Being a Rust n00b, I don't know the effect this has on how the code can be used and other effects.

Port Context to RCLRS Core

Context needs to be ported to the new rclrs_core crate.

I believe we cannot use Arc or Mutex with the !#[no_std] attribute, so that logic might need to be left up to a higher-level API.

Twist geometry_msg always read as all zeroes

Hey all, let me preface the question by thanking you for working on this, it's incredibly useful for a project I am working on and exciting to see Rust being used for robotics work.

I am running into an issue with sending a Twist message, where regardless of what actual vectors I send, the publisher always reads both angular and linear velocities as all zeroes.

I publish the message like this:

let linear = geometry_msgs::msg:Vector3 {x: 10.0, y: 0.0, z: 0.0};
let angular = geometry_msgs::msg:Vector3 {x: 0.0, y: 0.0, z: 0.0};

let message = geometry_msgs::msg::Twist {linear, angular};

let result = publisher.publish(&message);
match result {
   Ok(result) => println!("Publishing: {}", message.x.linear),
   Err(result) => println!("Could not publish velocity")
}

And read it like this:

let _subscription = node.create_subscription::<geometry_msgs::msg::Twist, _>(
   "cmd_vel",
   rclrs::QOS_PROFILE_DEFAULT,
   move |msg: &geometry_msgs:msg::Twist| {
      println!("I heard: {}", msg.linear.x);
   },
);

The output of my program always has the subscriber reading a 0 in the linear x velocity. So the output of the above two print statements ends up being:

Publishing: 10
I heard: 0

I can also verify this through ros2 topic echo cmd_vel:

linear:
   x: 0.0
   y: 0.0
   z: 0.0
angular:
   x: 0.0
   y: 0.0
   z: 0.0

I wonder if this is an issue with the generator for a geometry_msg in particular, or if I'm doing something wrong with sending the message. I don't understand how the ros2-rust code works perfectly so I'm having some difficulty digging into it to figure out what the problem is.

Thank you.

Edit
Actually, this seems to be happening with a Pose message as well (but not, for example, a Vector3). I wonder if the issue is a message type that has nested within it another message type?

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.