Skip to content

help(interop): interoperability with CycloneDDS #27

Description

@Davide-1998

Hi, I am currently working on reading CycloneDDS data from ZeroDDS, but I cannot make them communicate.
I tried running the script tests/interop/cyclone_shapes_pub.py with both Python 3.13 and 3.10, using as CycloneDDS C backend the version 11.0.1 and 0.10.5 but neither worked.
During my tests I also tried setting the ZeroDDS DataReaderQos::data_representation to XCDR (the default for CycloneDDS) but nothing.
On CycloneDDS side, I tried enabling XCDR2 and yet nothing.

Can you help me figure out what is happening for them to not communicate?
Following are some snippets of code used for testing.

Thanks in advance for all the help

Robot.idl

struct Robot {
  uint32 id;
  uint32 label;
};
# Compiled using the following command, optionally with --cyclone flag
zerodds-idlc generate ./Robot.idl --rust [--cyclone] -o src/generated

Subscriber.rs

use zerodds_dcps::{DomainParticipantFactory, DataReaderQos,  DomainParticipantQos, SubscriberQos, TopicQos};
#[allow(clippy::all, clippy::pedantic, dead_code)]
mod generated {
    include!("generated/Robot.rs");
}

use generated::Robot;

fn main() -> Result<(), Box<dyn std::error::Error>> {
    let factory = DomainParticipantFactory::instance();

    let participant = factory.create_participant(100, DomainParticipantQos::default()).unwrap();
    let robot_topic = participant.create_topic::<Robot>("robot", TopicQos::default()).expect("create_topic");
    
    let subscriber = participant.create_subscriber(SubscriberQos::default());
    let reader = subscriber.create_datareader::<Robot>(&robot_topic, DataReaderQos::default()).expect("create_datawriter");

    let mut count: u64 = 0;
    loop {
        match reader.take() {
            Ok(samples) => {
                for item in samples {
                    println!("Read #{count}: id {} | label '{}'", item.id, item.label);
                    count += 1;
                }
            }

            Err(err) => {
                println!("error: {}", err)
            }
        }
    }
}

Writer CycloneDDS Python

import time
from dataclasses import dataclass

from cyclonedds.domain import DomainParticipant  # type: ignore[import-not-found]
from cyclonedds.idl import IdlStruct  # type: ignore[import-not-found]
from cyclonedds.idl.annotations import key  # type: ignore[import-not-found]
from cyclonedds.idl.types import bounded_str, int32, uint32  # type: ignore[import-not-found]
from cyclonedds.pub import DataWriter, Publisher  # type: ignore[import-not-found]
from cyclonedds.topic import Topic  # type: ignore[import-not-found]

@dataclass
class RobotType(IdlStruct, typename="Robot"):
    """Spec-kompatibel mit RTI/Cyclone/Fast-DDS.

    IDL:
        struct Robot {
            uint32 id;
            uint32 label;
        };
    """

    id: uint32 = 0
    label: uint32 = 0

def main() -> int:
    topic_name = "robot"
    domain_id = 100

    participant = DomainParticipant(domain_id=domain_id)
    topic = Topic(participant, topic_name, RobotType)
    publisher = Publisher(participant)
    writer = DataWriter(publisher, topic)

    print(
        f"[cyclone-pub] Topic={topic_name} Domain={domain_id} — Ctrl-C to stop",
        flush=True,
    )

    count = 0
    try:
        while True:
            sample = RobotType(id=1, label=count)
            writer.write(sample)
            print(f"  -> id={sample.id} label={sample.label}", flush=True)
            count += 1
            time.sleep(0.5)
    except KeyboardInterrupt:
        return 0


if __name__ == "__main__":
    raise SystemExit(main())

Writer CycloneDDS-CXX v11.0.1

#include <chrono>
#include <dds/dds.hpp>  // CycloneDDS-cxx
#include <print>
#include <thread>

#include "IDL/Robot.hpp"  // Compiled Robot.idl using cmake command `idlcxx_generate`

int main() {
    std::println("Start Robot writer");

    // Initialize DDS classes
    auto participant = ::dds::domain::DomainParticipant(100);
    auto topic = ::dds::topic::Topic<Robot>(participant, "robot", ::dds::topic::qos::TopicQos());
    auto publisher = ::dds::pub::Publisher(participant, participant.default_publisher_qos());
    auto writer = ::dds::pub::DataWriter<Robot>(publisher, topic, ::dds::pub::qos::DataWriterQos());

    std::jthread worker_thread([&]() {
        std::uint32_t num_packets = 0;

        while (!stop_thread.load()) {
            RobotIdl::Type data;
            data.id(num_packets);
            data.label(num_packets);

            writer.write(data);  // Write to DDS

            num_packets++;
            std::println("Written: id: {} | label: '{}'", num_packets, data.id(), data.label());

            std::this_thread::sleep_for(std::chrono::milliseconds(500));
        }
    });
}

Metadata

Metadata

Assignees

Labels

bugSomething isn't working

Type

Projects

No projects

Relationships

None yet

Development

No branches or pull requests

Issue actions