-
Notifications
You must be signed in to change notification settings - Fork 29
feat(rtps_embedded): embeddedRTPS integration + idiomatic espp refactor (facade, SocketReactor, protocol scheduler, Micro-CDR removal) #706
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Merged
Merged
Changes from all commits
Commits
Show all changes
50 commits
Select commit
Hold shift + click to select a range
3b59906
copy from embeddedRTPS
guo-max bf22a30
add submodule
guo-max bc85052
update submodule
guo-max 734c114
add example
guo-max f81ef55
WIP; add substrct layer for platform
guo-max c223c55
added thread pool; removed lwip and freertos
guo-max ea3f3a5
fix bug of sedp acknack; fix bug for parse topic data
guo-max 939acff
removed sync and fix circular buffer bug
guo-max c3c7062
code clean up
guo-max a0edd0a
update to use base component
guo-max 1738184
remove micro_CDR
guo-max c069ef6
add the forked micro-CDR
guo-max ed2e8e5
update micro cdr config
guo-max 291ddd6
add pc test; fix heartbeat ping-pang bug
guo-max d9524eb
test with reliable and add some log for testing
guo-max 9cdb1e6
fix documentation and add readme
guo-max ca54404
disable logging by default
guo-max aed1f3a
delete thread_pool
guo-max ac252c8
Merge branch 'main' into feat/embeddedRTPS_merge_espp
guo-max bd9e29f
update example to use ethernent kit
guo-max dbe3c42
update rtps example
guo-max 99bb2cd
remove unused file
guo-max 751f118
update kconfig
guo-max fb127cc
modify header file to use hpp
guo-max 5f259bb
fix CodeQL scan result bug
guo-max eb2dcca
Merge branch 'main' into feat/embeddedRTPS_merge_espp
guo-max 3a2c9e1
fix static code analysis errors
guo-max 678a842
fix static analysis issue
guo-max 7f8ff48
update based on AI review
guo-max e470aa1
fix based on AI review
guo-max 3166176
remove unused files and revert back the Cmakelists
guo-max bb8c3ff
doc(rtps): Add the RTPS refactor design plan (embeddedRTPS -> idiomat…
finger563 d9b8fdc
feat(rtps_embedded): Host build + loopback baseline; fix desktop GUID…
finger563 1320a11
test(rtps_embedded): Golden wire-format byte tests (Phase 0b)
finger563 3959916
test(rtps_embedded): FastDDS/ROS2 interop harness (Phase 0c)
finger563 b028e09
feat(rtps_embedded): espp RtpsParticipant facade over the engine (Pha…
finger563 0df6e3a
fix(rtps_embedded): Probe participant ids for free unicast ports (Pha…
finger563 be9072d
feat(rtps_embedded): Receive path on SocketReactor (Phase 2b)
finger563 e19e8c8
feat(rtps_embedded): Delete the engine ThreadPool (Phase 2c)
finger563 318c23f
feat(rtps_embedded): Single deadline-scheduled protocol task (Phase 2d)
finger563 9bb5647
feat(rtps_embedded): Port the esp32 example to the RtpsParticipant fa…
finger563 e1396af
feat(rtps_embedded): Optional interface_ip argument for the interop p…
finger563 d1fcf74
improve performance of example
finger563 320f777
Merge remote-tracking branch 'origin/main' into feat/refactor-embedde…
finger563 ed553c9
feat(rtps_embedded): Port payload serialization to the reflection-dri…
finger563 879797d
feat(rtps_embedded)!: Remove the Micro-CDR submodule (Phase 2b)
finger563 5a8f416
chore: gitignore the docker interop harness build tree
finger563 5c1573c
fix(rtps_embedded): Address PR #706 review comments
finger563 fceb9c3
fix(rtps_embedded): Windows build — guard POSIX headers in interface …
finger563 863e6a1
fix(rtps_embedded): MSVC — make MemoryPoolIterator copy-assignable
finger563 File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,30 @@ | ||
| name: RTPS interop (FastDDS / ROS 2) | ||
|
|
||
| # Minimal token scope: the harness only checks out and builds, never writes. | ||
| permissions: | ||
| contents: read | ||
|
|
||
| on: | ||
| pull_request: | ||
| paths: | ||
| - "components/rtps_embedded/**" | ||
| - "components/rtps/**" | ||
| - "components/socket/**" | ||
| - "components/cdr/**" | ||
| - "lib/espp.cmake" | ||
| - "pc/tests/rtps_embedded_*" | ||
| - ".github/workflows/rtps_interop.yml" | ||
| workflow_dispatch: | ||
|
|
||
| jobs: | ||
| interop: | ||
| runs-on: ubuntu-latest | ||
| timeout-minutes: 30 | ||
| steps: | ||
| - uses: actions/checkout@v7 | ||
| with: | ||
| submodules: "recursive" | ||
| - name: Run interop matrix | ||
| run: | | ||
| cd components/rtps_embedded/interop | ||
| ./run.sh | ||
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,22 @@ | ||
| idf_component_register( | ||
| SRCS | ||
| "src/rtps_participant.cpp" | ||
| "src/communication/EsppTransport.cpp" | ||
| "src/discovery/ParticipantProxyData.cpp" | ||
| "src/discovery/SEDPAgent.cpp" | ||
| "src/discovery/SPDPAgent.cpp" | ||
| "src/discovery/TopicData.cpp" | ||
| "src/entities/Domain.cpp" | ||
| "src/entities/Participant.cpp" | ||
| "src/entities/Reader.cpp" | ||
| "src/entities/StatelessReader.cpp" | ||
| "src/entities/Writer.cpp" | ||
| "src/messages/MessageReceiver.cpp" | ||
| "src/messages/MessageTypes.cpp" | ||
| "src/utils/Diagnostics.cpp" | ||
| INCLUDE_DIRS | ||
| "include" | ||
| REQUIRES | ||
| base_component cdr task thread_pool socket | ||
| ) | ||
|
|
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,159 @@ | ||
| # rtps_embedded | ||
|
|
||
| ESPP component that integrates the [embeddedRTPS](https://github.com/embedded-software-laboratory/embeddedRTPS) | ||
| RTPS/DDS stack into the ESPP ecosystem. | ||
| Any platform that can build ESPP — including ESP32, Linux, and desktop PCs — | ||
| can use this component to discover and exchange typed messages with ROS 2 nodes | ||
| or any other DDS participant on the same network using the standard RTPS wire | ||
| protocol. | ||
|
|
||
| The original embeddedRTPS library has hard dependencies on FreeRTOS and lwIP. | ||
| `rtps_embedded` removes those dependencies by replacing all socket, task, and | ||
| synchronisation calls with ESPP's platform-agnostic `UdpSocket`, `Task`, and | ||
| `ThreadPool` primitives. When built for ESP32, ESPP uses FreeRTOS and lwIP | ||
| under the hood; on other platforms it uses the host OS equivalents — the RTPS | ||
| code itself is unchanged in either case. | ||
|
|
||
| --- | ||
|
|
||
| ## Architecture | ||
|
|
||
| ``` | ||
| user code | ||
| │ | ||
| ▼ | ||
| rtps::Domain — routes packets to participants; owns discovery threads | ||
| │ | ||
| ├── rtps::Participant — groups writers and readers | ||
| │ ├── rtps::Writer — publishes CacheChange samples | ||
| │ └── rtps::Reader — delivers samples to a user callback | ||
| │ | ||
| ├── rtps::ThreadPool — espp::ThreadPool workers that drain the four | ||
| │ incoming/outgoing meta/user traffic queues | ||
| │ | ||
| └── rtps::EsppTransport — one espp::UdpSocket per open UDP port, | ||
| each with its own receive task | ||
| ``` | ||
|
|
||
| `EsppTransport` is the sole platform-specific adapter. It wraps ESPP's | ||
| `UdpSocket` and `Task`, which in turn map to: | ||
|
|
||
| | Build target | Socket backend | Task backend | | ||
| |---|---|---| | ||
| | ESP32 | lwIP (via ESP-IDF) | FreeRTOS | | ||
| | Linux / PC | POSIX sockets | `std::thread` | | ||
|
|
||
| --- | ||
|
|
||
| ## Quick-start | ||
|
|
||
| ```cpp | ||
| #include "rtps/entities/Domain.h" | ||
|
|
||
| // 1. Construct the domain with the local interface IP. | ||
| rtps::Domain domain(local_ip); | ||
|
|
||
| // 2. Create a participant *before* completeInit(). | ||
| rtps::Participant *part = domain.createParticipant(); | ||
|
|
||
| // 3. Add user-defined writer and reader endpoints. | ||
| rtps::Writer *writer = domain.createWriter(*part, "my/topic", | ||
| "std_msgs::msg::String", false); | ||
| rtps::Reader *reader = domain.createReader(*part, "my/topic", | ||
| "std_msgs::msg::String", false); | ||
|
|
||
| // 4. Register a receive callback on the reader. | ||
| reader->registerCallback( | ||
| [](void *, const rtps::ReaderCacheChange &change) { | ||
| // process change.getData() / change.copyInto(...) | ||
| }, nullptr); | ||
|
|
||
| // 5. Start discovery (SPDP/SEDP) and worker threads. | ||
| domain.completeInit(); | ||
|
|
||
| // 6. Publish a sample. | ||
| const char *payload = "hello"; | ||
| writer->newChange(rtps::ChangeKind_t::ALIVE, | ||
| reinterpret_cast<const uint8_t *>(payload), | ||
| static_cast<rtps::DataSize_t>(strlen(payload) + 1)); | ||
| ``` | ||
|
|
||
| > **Note**: `createParticipant()` **must** be called before `completeInit()`. | ||
| > No new participants can be added after init is complete. | ||
|
|
||
| --- | ||
|
|
||
| ## Configuration | ||
|
|
||
| Two built-in config headers are provided. Select one by defining | ||
| `RTPS_CONFIG_HEADER`, or let `include/rtps/config.h` pick automatically based | ||
| on the build target. | ||
|
|
||
| | Header | Target | | ||
| |---|---| | ||
| | [`include/rtps/config_esp32.h`](include/rtps/config_esp32.h) | ESP32 (ESP-IDF) | | ||
| | [`include/rtps/config_desktop.h`](include/rtps/config_desktop.h) | Linux / PC | | ||
|
|
||
| All tunable constants follow the same layout in both files: | ||
|
|
||
| | Constant | Default | Description | | ||
| |---|---|---| | ||
| | `DOMAIN_ID` | 0 | RTPS domain number (0–230 with UDP) | | ||
| | `MAX_NUM_PARTICIPANTS` | 1 | Participant pool size | | ||
| | `NUM_STATEFUL_WRITERS` | 5 | User writer endpoint pool | | ||
| | `NUM_STATEFUL_READERS` | 5 | User reader endpoint pool | | ||
| | `NUM_STATELESS_WRITERS` | 5 | Discovery writer endpoint pool | | ||
| | `NUM_STATELESS_READERS` | 5 | Discovery reader endpoint pool | | ||
| | `NUM_WRITERS_PER_PARTICIPANT` | 10 | Max writers per participant | | ||
| | `NUM_READERS_PER_PARTICIPANT` | 10 | Max readers per participant | | ||
| | `HISTORY_SIZE_STATEFUL` | 10 | Per-endpoint history depth | | ||
| | `THREAD_POOL_NUM_WRITERS` | 2 | Writer worker threads | | ||
| | `THREAD_POOL_NUM_READERS` | 2 | Reader worker threads | | ||
| | `THREAD_POOL_WRITER_STACKSIZE` | 4096 B | Writer task stack | | ||
| | `THREAD_POOL_READER_STACKSIZE` | 6144 B | Reader / UDP-receive task stack | | ||
| | `MAX_NUM_UDP_CONNECTIONS` | 10 | UDP socket pool size | | ||
| | `SPDP_RESEND_PERIOD_MS` | 2000 | Discovery announce period | | ||
| | `SF_WRITER_HB_PERIOD_MS` | 4000 | Reliable-writer heartbeat period | | ||
|
|
||
| The `OVERALL_HEAP_SIZE` constant at the bottom of that file estimates the | ||
| total stack RAM consumed by all internal tasks. | ||
|
|
||
| --- | ||
|
|
||
| ## ESPP component dependencies | ||
|
|
||
| | Component | Purpose | | ||
| |---|---| | ||
| | `base_component` | ESPP base class with integrated `espp::Logger` | | ||
| | `socket` | ESPP `UdpSocket` used by `EsppTransport` | | ||
| | `task` | ESPP `Task` for per-port UDP receive loops | | ||
| | `thread_pool` | ESPP `ThreadPool` for writer/reader workers | | ||
| | `cdr` | CDR serialization helpers | | ||
|
|
||
| These components abstract away all OS and network-stack details, so | ||
| `rtps_embedded` itself has no direct dependency on FreeRTOS, lwIP, or any | ||
| other platform library. Discovery (SPDP/SEDP) parameter-list serialization is | ||
| built on the espp `cdr` component's stream primitives (see | ||
| `include/rtps/utils/CdrBuffer.hpp`); the engine carries no vendored | ||
| third-party code. | ||
|
|
||
| --- | ||
|
|
||
| ## Example | ||
|
|
||
| See [`example/`](example/) for a two-node **initiator / responder** demo. | ||
|
|
||
| The same logic runs on any ESPP-supported platform. For ESP32, flash one board | ||
| as *Initiator* and a second as *Responder* via menuconfig | ||
| (`idf.py menuconfig → RTPS Example Configuration`). The initiator periodically | ||
| publishes numbered request messages; the responder echoes each message back on | ||
| the response topic. | ||
|
|
||
| Key menuconfig options (ESP32 example): | ||
|
|
||
| | Option | Description | | ||
| |---|---| | ||
| | `RTPS_EXAMPLE_ROLE` | `Initiator` or `Responder` | | ||
| | `RTPS_EXAMPLE_TOPIC_PREFIX` | Shared topic prefix (e.g. `espp/rtps_example`) | | ||
| | `RTPS_EXAMPLE_PUBLISH_PERIOD_MS` | Initiator publish interval | | ||
| | `ESP_WIFI_SSID` / `ESP_WIFI_PASSWORD` | Wi-Fi credentials | |
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
Uh oh!
There was an error while loading. Please reload this page.