|
data_tamer_cpp package from data_tamer repodata_tamer_cpp data_tamer_msgs |
ROS Distro
|
Package Summary
| Version | 2.0.0 |
| License | MIT |
| Build type | AMENT_CMAKE |
| Use | RECOMMENDED |
Repository Summary
| Checkout URI | https://github.com/PickNikRobotics/data_tamer.git |
| VCS Type | git |
| VCS Version | main |
| Last Updated | 2026-10-18 |
| Dev Status | MAINTAINED |
| Released | RELEASED |
| Contributing |
Help Wanted (-)
Good First Issues (-) Pull Requests to Review (-) |
Package Description
Maintainers
- Davide Faconti
- Henry Moore
- Nathan Brooks
Authors
- Davide Faconti
Changelog for package data_tamer
Unreleased
-
Breaking, headers: the public headers move from
data_tamer/todata_tamer_v2/(#include "data_tamer_v2/channel.hpp"), and the standalone parser fromdata_tamer_parser/data_tamer_parser.hpptodata_tamer_v2/data_tamer_parser.hpp, so that 2.x installs side by side with 1.x, whose headers keep their paths. -
ABI:
ChannelSharedState, itsWriteMutexand the series flag words are library-private (src/): the headersdetails/shared_state.hpp,details/write_mutex.hppanddetails/spin_pause.hppare no longer installed, and consumers seeChannelSharedStateonly as an incomplete type.LoggedValuereaches its enabled flag through the exporteddetails::setSeriesEnabled()andisSeriesEnabled(), so the flag encoding and these layouts can change in a 2.x minor release.WriteTransactionis a class at namespace scope (it was the aliasChannelSharedState::Transaction), declared indetails/locked_reference.hppand still returned byscopedWrite(). Rebuild consumers built against earlier headers. -
Behaviour change, parser and Python decoder: a schema text in
the line format needs its
### version:line before the fields; without one both throw, naming the supported versions (4 and 5, 6 in YAML). The C++ parser read such a text as an upper-case "name TYPE" format that no release wrote, or as version 5, and the Python decoder as version 5. Texts of the releases before 0.7.0 (late 2023) fail with that message, among them the header-less<type> <name>lines of the 0.3 to 0.5 ROS 2 publisher, which both used to read (docs/wire_format.md, section 2). -
Fixed, Python decoder:
verify_hash=True(parse_schema(),SchemaRegistry,iter_mcap()) rejected every data_tamer 1.x file (schema version 4). Its hash came from the writer'sstd::hashand cannot be recomputed, so it is accepted as declared. The C++check_hashstill recomputes it, which agrees only with the writer's standard library (docs/wire_format.md, section 5). - Docs:
docs/MIGRATION.mdlists what code written for 1.x must change for 2.0, with the behaviour changes that compile silently. -
Real-time: the first access of the transaction state on a thread
no longer allocates when libdata_tamer is loaded with
dlopen()(a plugin, pluginlib, ros2_control), so ascopedWrite()on each real-time thread during setup is no longer needed. The library's one thread-local is initial-exec TLS (glibc):dlopen()takes one pointer of glibc's static TLS surplus. -
ABI: the
WriteTransactionconstructor and destructor (behindscopedWrite(), the guards and non-scalarLoggedValues) andChannelSharedState::inTransactionOnThisThread()are defined in the library, with the thread-local chain. The chain is no longer an inline protocol, so later 2.x releases can change it; only the size ofWriteTransactionis pinned. Rebuild consumers built against earlier headers. -
API:
data_tamer_v2/data_tamer.hppincludeschannel.hppagain, as in 1.x, so one include givesChannelsRegistry,LogChannel,LoggedValueand the sink interface.data_tamer_v2/fwd.hppstays for headers that only name the types. -
API:
takeSnapshot()is no longer[[nodiscard]]:stats()counts every outcome, and most loops don't act on each call.tryTakeSnapshot()still is. -
API: no
LogChannel::droppedSnapshots(), which no release had: readstats().dropped_by_sink.LogChannel::sinkDropped()andChannelDefaults::resolve()(withChannelDefaults::Sizes) are private: they are the building blocks ofstats()andsetChannelDefaults(). Their symbols stay exported (the inlinestats()callssinkDropped()). -
Fixed, deadlocks:
unregister(),removeDataSink()or aLoggedValuedestructor insidescopedWrite()while a snapshot waited; a const query insidescopedWrite()while another thread ran one of those, orstartLogging();startLogging()insidescopedWrite(). The snapshot path takes the write mutex before its epoch, andstartLogging()before the control mutex. -
Behaviour change: a snapshot taken by a thread that holds the
channel's transaction or a
LoggedValueguard returnsblocked(it hung). -
New: several threads may take snapshots of one channel; they
take turns on the write mutex.
blockednow takes precedence overpool_exhausted. -
Fixed: a consumer built with
-fvisibility=hiddenagainst a shared libdata_tamer hung inLoggedValue::set()insidescopedWrite(); the transaction code is defined in the library only. -
Behaviour change:
SinkWorker::stop(),start()anddrain()throwstd::logic_errorfrom a callback of their own sink (they deadlocked, orstop()closed the worker silently). Concurrentstop()andstart(), twostopAll()included, are serialized (they hung). A callback that releases the last reference to its own worker no longer callsstd::terminate. -
Fixed: a sink attached during a failing
startLogging()could miss the final schema, and a concurrentaddDataSink()of one worker announced it twice. -
Real-time: no
notify_all()per snapshot or refused push unless a thread waits; each one could be a futex call. -
Behaviour change: names must be non-empty and free of whitespace
and control characters (only the space was refused);
IsCanonicalName()agrees. A ninth default sink throws inaddDefaultSink()(it made every latergetChannel()throw). -
Behaviour change: custom type names, their field names, the
typeName()of aregisterCustomValue()serializer and channel names are checked too: a line break in any of them split the schema text, and a space in a type or field name broke its field line. Type and field names follow the value name rules, and the registration
File truncated at 100 lines see the full file
Package Dependencies
| Deps | Name |
|---|---|
| ament_cmake | |
| rclcpp | |
| rclcpp_lifecycle | |
| mcap_vendor | |
| data_tamer_msgs | |
| ament_cmake_gtest | |
| gtest_vendor |
System Dependencies
| Name |
|---|
| lz4 |
| libzstd-dev |
Dependant Packages
| Name | Deps |
|---|---|
| plotjuggler |
Launch files
Messages
Services
Plugins
Recent questions tagged data_tamer_cpp at Robotics Stack Exchange
|
data_tamer_cpp package from data_tamer repodata_tamer_cpp data_tamer_msgs |
ROS Distro
|
Package Summary
| Version | 2.0.0 |
| License | MIT |
| Build type | AMENT_CMAKE |
| Use | RECOMMENDED |
Repository Summary
| Checkout URI | https://github.com/PickNikRobotics/data_tamer.git |
| VCS Type | git |
| VCS Version | main |
| Last Updated | 2026-10-18 |
| Dev Status | MAINTAINED |
| Released | RELEASED |
| Contributing |
Help Wanted (-)
Good First Issues (-) Pull Requests to Review (-) |
Package Description
Maintainers
- Davide Faconti
- Henry Moore
- Nathan Brooks
Authors
- Davide Faconti
Changelog for package data_tamer
Unreleased
-
Breaking, headers: the public headers move from
data_tamer/todata_tamer_v2/(#include "data_tamer_v2/channel.hpp"), and the standalone parser fromdata_tamer_parser/data_tamer_parser.hpptodata_tamer_v2/data_tamer_parser.hpp, so that 2.x installs side by side with 1.x, whose headers keep their paths. -
ABI:
ChannelSharedState, itsWriteMutexand the series flag words are library-private (src/): the headersdetails/shared_state.hpp,details/write_mutex.hppanddetails/spin_pause.hppare no longer installed, and consumers seeChannelSharedStateonly as an incomplete type.LoggedValuereaches its enabled flag through the exporteddetails::setSeriesEnabled()andisSeriesEnabled(), so the flag encoding and these layouts can change in a 2.x minor release.WriteTransactionis a class at namespace scope (it was the aliasChannelSharedState::Transaction), declared indetails/locked_reference.hppand still returned byscopedWrite(). Rebuild consumers built against earlier headers. -
Behaviour change, parser and Python decoder: a schema text in
the line format needs its
### version:line before the fields; without one both throw, naming the supported versions (4 and 5, 6 in YAML). The C++ parser read such a text as an upper-case "name TYPE" format that no release wrote, or as version 5, and the Python decoder as version 5. Texts of the releases before 0.7.0 (late 2023) fail with that message, among them the header-less<type> <name>lines of the 0.3 to 0.5 ROS 2 publisher, which both used to read (docs/wire_format.md, section 2). -
Fixed, Python decoder:
verify_hash=True(parse_schema(),SchemaRegistry,iter_mcap()) rejected every data_tamer 1.x file (schema version 4). Its hash came from the writer'sstd::hashand cannot be recomputed, so it is accepted as declared. The C++check_hashstill recomputes it, which agrees only with the writer's standard library (docs/wire_format.md, section 5). - Docs:
docs/MIGRATION.mdlists what code written for 1.x must change for 2.0, with the behaviour changes that compile silently. -
Real-time: the first access of the transaction state on a thread
no longer allocates when libdata_tamer is loaded with
dlopen()(a plugin, pluginlib, ros2_control), so ascopedWrite()on each real-time thread during setup is no longer needed. The library's one thread-local is initial-exec TLS (glibc):dlopen()takes one pointer of glibc's static TLS surplus. -
ABI: the
WriteTransactionconstructor and destructor (behindscopedWrite(), the guards and non-scalarLoggedValues) andChannelSharedState::inTransactionOnThisThread()are defined in the library, with the thread-local chain. The chain is no longer an inline protocol, so later 2.x releases can change it; only the size ofWriteTransactionis pinned. Rebuild consumers built against earlier headers. -
API:
data_tamer_v2/data_tamer.hppincludeschannel.hppagain, as in 1.x, so one include givesChannelsRegistry,LogChannel,LoggedValueand the sink interface.data_tamer_v2/fwd.hppstays for headers that only name the types. -
API:
takeSnapshot()is no longer[[nodiscard]]:stats()counts every outcome, and most loops don't act on each call.tryTakeSnapshot()still is. -
API: no
LogChannel::droppedSnapshots(), which no release had: readstats().dropped_by_sink.LogChannel::sinkDropped()andChannelDefaults::resolve()(withChannelDefaults::Sizes) are private: they are the building blocks ofstats()andsetChannelDefaults(). Their symbols stay exported (the inlinestats()callssinkDropped()). -
Fixed, deadlocks:
unregister(),removeDataSink()or aLoggedValuedestructor insidescopedWrite()while a snapshot waited; a const query insidescopedWrite()while another thread ran one of those, orstartLogging();startLogging()insidescopedWrite(). The snapshot path takes the write mutex before its epoch, andstartLogging()before the control mutex. -
Behaviour change: a snapshot taken by a thread that holds the
channel's transaction or a
LoggedValueguard returnsblocked(it hung). -
New: several threads may take snapshots of one channel; they
take turns on the write mutex.
blockednow takes precedence overpool_exhausted. -
Fixed: a consumer built with
-fvisibility=hiddenagainst a shared libdata_tamer hung inLoggedValue::set()insidescopedWrite(); the transaction code is defined in the library only. -
Behaviour change:
SinkWorker::stop(),start()anddrain()throwstd::logic_errorfrom a callback of their own sink (they deadlocked, orstop()closed the worker silently). Concurrentstop()andstart(), twostopAll()included, are serialized (they hung). A callback that releases the last reference to its own worker no longer callsstd::terminate. -
Fixed: a sink attached during a failing
startLogging()could miss the final schema, and a concurrentaddDataSink()of one worker announced it twice. -
Real-time: no
notify_all()per snapshot or refused push unless a thread waits; each one could be a futex call. -
Behaviour change: names must be non-empty and free of whitespace
and control characters (only the space was refused);
IsCanonicalName()agrees. A ninth default sink throws inaddDefaultSink()(it made every latergetChannel()throw). -
Behaviour change: custom type names, their field names, the
typeName()of aregisterCustomValue()serializer and channel names are checked too: a line break in any of them split the schema text, and a space in a type or field name broke its field line. Type and field names follow the value name rules, and the registration
File truncated at 100 lines see the full file
Package Dependencies
| Deps | Name |
|---|---|
| ament_cmake | |
| rclcpp | |
| rclcpp_lifecycle | |
| mcap_vendor | |
| data_tamer_msgs | |
| ament_cmake_gtest | |
| gtest_vendor |
System Dependencies
| Name |
|---|
| lz4 |
| libzstd-dev |
Dependant Packages
| Name | Deps |
|---|---|
| plotjuggler | |
| data_tamer_tools |
Launch files
Messages
Services
Plugins
Recent questions tagged data_tamer_cpp at Robotics Stack Exchange
|
data_tamer_cpp package from data_tamer repodata_tamer_cpp data_tamer_msgs |
ROS Distro
|
Package Summary
| Version | 2.0.0 |
| License | MIT |
| Build type | AMENT_CMAKE |
| Use | RECOMMENDED |
Repository Summary
| Checkout URI | https://github.com/PickNikRobotics/data_tamer.git |
| VCS Type | git |
| VCS Version | main |
| Last Updated | 2026-10-18 |
| Dev Status | MAINTAINED |
| Released | RELEASED |
| Contributing |
Help Wanted (-)
Good First Issues (-) Pull Requests to Review (-) |
Package Description
Maintainers
- Davide Faconti
- Henry Moore
- Nathan Brooks
Authors
- Davide Faconti
Changelog for package data_tamer
Unreleased
-
Breaking, headers: the public headers move from
data_tamer/todata_tamer_v2/(#include "data_tamer_v2/channel.hpp"), and the standalone parser fromdata_tamer_parser/data_tamer_parser.hpptodata_tamer_v2/data_tamer_parser.hpp, so that 2.x installs side by side with 1.x, whose headers keep their paths. -
ABI:
ChannelSharedState, itsWriteMutexand the series flag words are library-private (src/): the headersdetails/shared_state.hpp,details/write_mutex.hppanddetails/spin_pause.hppare no longer installed, and consumers seeChannelSharedStateonly as an incomplete type.LoggedValuereaches its enabled flag through the exporteddetails::setSeriesEnabled()andisSeriesEnabled(), so the flag encoding and these layouts can change in a 2.x minor release.WriteTransactionis a class at namespace scope (it was the aliasChannelSharedState::Transaction), declared indetails/locked_reference.hppand still returned byscopedWrite(). Rebuild consumers built against earlier headers. -
Behaviour change, parser and Python decoder: a schema text in
the line format needs its
### version:line before the fields; without one both throw, naming the supported versions (4 and 5, 6 in YAML). The C++ parser read such a text as an upper-case "name TYPE" format that no release wrote, or as version 5, and the Python decoder as version 5. Texts of the releases before 0.7.0 (late 2023) fail with that message, among them the header-less<type> <name>lines of the 0.3 to 0.5 ROS 2 publisher, which both used to read (docs/wire_format.md, section 2). -
Fixed, Python decoder:
verify_hash=True(parse_schema(),SchemaRegistry,iter_mcap()) rejected every data_tamer 1.x file (schema version 4). Its hash came from the writer'sstd::hashand cannot be recomputed, so it is accepted as declared. The C++check_hashstill recomputes it, which agrees only with the writer's standard library (docs/wire_format.md, section 5). - Docs:
docs/MIGRATION.mdlists what code written for 1.x must change for 2.0, with the behaviour changes that compile silently. -
Real-time: the first access of the transaction state on a thread
no longer allocates when libdata_tamer is loaded with
dlopen()(a plugin, pluginlib, ros2_control), so ascopedWrite()on each real-time thread during setup is no longer needed. The library's one thread-local is initial-exec TLS (glibc):dlopen()takes one pointer of glibc's static TLS surplus. -
ABI: the
WriteTransactionconstructor and destructor (behindscopedWrite(), the guards and non-scalarLoggedValues) andChannelSharedState::inTransactionOnThisThread()are defined in the library, with the thread-local chain. The chain is no longer an inline protocol, so later 2.x releases can change it; only the size ofWriteTransactionis pinned. Rebuild consumers built against earlier headers. -
API:
data_tamer_v2/data_tamer.hppincludeschannel.hppagain, as in 1.x, so one include givesChannelsRegistry,LogChannel,LoggedValueand the sink interface.data_tamer_v2/fwd.hppstays for headers that only name the types. -
API:
takeSnapshot()is no longer[[nodiscard]]:stats()counts every outcome, and most loops don't act on each call.tryTakeSnapshot()still is. -
API: no
LogChannel::droppedSnapshots(), which no release had: readstats().dropped_by_sink.LogChannel::sinkDropped()andChannelDefaults::resolve()(withChannelDefaults::Sizes) are private: they are the building blocks ofstats()andsetChannelDefaults(). Their symbols stay exported (the inlinestats()callssinkDropped()). -
Fixed, deadlocks:
unregister(),removeDataSink()or aLoggedValuedestructor insidescopedWrite()while a snapshot waited; a const query insidescopedWrite()while another thread ran one of those, orstartLogging();startLogging()insidescopedWrite(). The snapshot path takes the write mutex before its epoch, andstartLogging()before the control mutex. -
Behaviour change: a snapshot taken by a thread that holds the
channel's transaction or a
LoggedValueguard returnsblocked(it hung). -
New: several threads may take snapshots of one channel; they
take turns on the write mutex.
blockednow takes precedence overpool_exhausted. -
Fixed: a consumer built with
-fvisibility=hiddenagainst a shared libdata_tamer hung inLoggedValue::set()insidescopedWrite(); the transaction code is defined in the library only. -
Behaviour change:
SinkWorker::stop(),start()anddrain()throwstd::logic_errorfrom a callback of their own sink (they deadlocked, orstop()closed the worker silently). Concurrentstop()andstart(), twostopAll()included, are serialized (they hung). A callback that releases the last reference to its own worker no longer callsstd::terminate. -
Fixed: a sink attached during a failing
startLogging()could miss the final schema, and a concurrentaddDataSink()of one worker announced it twice. -
Real-time: no
notify_all()per snapshot or refused push unless a thread waits; each one could be a futex call. -
Behaviour change: names must be non-empty and free of whitespace
and control characters (only the space was refused);
IsCanonicalName()agrees. A ninth default sink throws inaddDefaultSink()(it made every latergetChannel()throw). -
Behaviour change: custom type names, their field names, the
typeName()of aregisterCustomValue()serializer and channel names are checked too: a line break in any of them split the schema text, and a space in a type or field name broke its field line. Type and field names follow the value name rules, and the registration
File truncated at 100 lines see the full file
Package Dependencies
| Deps | Name |
|---|---|
| ament_cmake | |
| rclcpp | |
| rclcpp_lifecycle | |
| mcap_vendor | |
| data_tamer_msgs | |
| ament_cmake_gtest | |
| gtest_vendor |
System Dependencies
| Name |
|---|
| lz4 |
| libzstd-dev |
Dependant Packages
| Name | Deps |
|---|---|
| plotjuggler |
Launch files
Messages
Services
Plugins
Recent questions tagged data_tamer_cpp at Robotics Stack Exchange
|
data_tamer_cpp package from data_tamer repodata_tamer_cpp data_tamer_msgs |
ROS Distro
|
Package Summary
| Version | 2.0.0 |
| License | MIT |
| Build type | AMENT_CMAKE |
| Use | RECOMMENDED |
Repository Summary
| Checkout URI | https://github.com/PickNikRobotics/data_tamer.git |
| VCS Type | git |
| VCS Version | main |
| Last Updated | 2026-10-18 |
| Dev Status | MAINTAINED |
| Released | RELEASED |
| Contributing |
Help Wanted (-)
Good First Issues (-) Pull Requests to Review (-) |
Package Description
Maintainers
- Davide Faconti
- Henry Moore
- Nathan Brooks
Authors
- Davide Faconti
Changelog for package data_tamer
Unreleased
-
Breaking, headers: the public headers move from
data_tamer/todata_tamer_v2/(#include "data_tamer_v2/channel.hpp"), and the standalone parser fromdata_tamer_parser/data_tamer_parser.hpptodata_tamer_v2/data_tamer_parser.hpp, so that 2.x installs side by side with 1.x, whose headers keep their paths. -
ABI:
ChannelSharedState, itsWriteMutexand the series flag words are library-private (src/): the headersdetails/shared_state.hpp,details/write_mutex.hppanddetails/spin_pause.hppare no longer installed, and consumers seeChannelSharedStateonly as an incomplete type.LoggedValuereaches its enabled flag through the exporteddetails::setSeriesEnabled()andisSeriesEnabled(), so the flag encoding and these layouts can change in a 2.x minor release.WriteTransactionis a class at namespace scope (it was the aliasChannelSharedState::Transaction), declared indetails/locked_reference.hppand still returned byscopedWrite(). Rebuild consumers built against earlier headers. -
Behaviour change, parser and Python decoder: a schema text in
the line format needs its
### version:line before the fields; without one both throw, naming the supported versions (4 and 5, 6 in YAML). The C++ parser read such a text as an upper-case "name TYPE" format that no release wrote, or as version 5, and the Python decoder as version 5. Texts of the releases before 0.7.0 (late 2023) fail with that message, among them the header-less<type> <name>lines of the 0.3 to 0.5 ROS 2 publisher, which both used to read (docs/wire_format.md, section 2). -
Fixed, Python decoder:
verify_hash=True(parse_schema(),SchemaRegistry,iter_mcap()) rejected every data_tamer 1.x file (schema version 4). Its hash came from the writer'sstd::hashand cannot be recomputed, so it is accepted as declared. The C++check_hashstill recomputes it, which agrees only with the writer's standard library (docs/wire_format.md, section 5). - Docs:
docs/MIGRATION.mdlists what code written for 1.x must change for 2.0, with the behaviour changes that compile silently. -
Real-time: the first access of the transaction state on a thread
no longer allocates when libdata_tamer is loaded with
dlopen()(a plugin, pluginlib, ros2_control), so ascopedWrite()on each real-time thread during setup is no longer needed. The library's one thread-local is initial-exec TLS (glibc):dlopen()takes one pointer of glibc's static TLS surplus. -
ABI: the
WriteTransactionconstructor and destructor (behindscopedWrite(), the guards and non-scalarLoggedValues) andChannelSharedState::inTransactionOnThisThread()are defined in the library, with the thread-local chain. The chain is no longer an inline protocol, so later 2.x releases can change it; only the size ofWriteTransactionis pinned. Rebuild consumers built against earlier headers. -
API:
data_tamer_v2/data_tamer.hppincludeschannel.hppagain, as in 1.x, so one include givesChannelsRegistry,LogChannel,LoggedValueand the sink interface.data_tamer_v2/fwd.hppstays for headers that only name the types. -
API:
takeSnapshot()is no longer[[nodiscard]]:stats()counts every outcome, and most loops don't act on each call.tryTakeSnapshot()still is. -
API: no
LogChannel::droppedSnapshots(), which no release had: readstats().dropped_by_sink.LogChannel::sinkDropped()andChannelDefaults::resolve()(withChannelDefaults::Sizes) are private: they are the building blocks ofstats()andsetChannelDefaults(). Their symbols stay exported (the inlinestats()callssinkDropped()). -
Fixed, deadlocks:
unregister(),removeDataSink()or aLoggedValuedestructor insidescopedWrite()while a snapshot waited; a const query insidescopedWrite()while another thread ran one of those, orstartLogging();startLogging()insidescopedWrite(). The snapshot path takes the write mutex before its epoch, andstartLogging()before the control mutex. -
Behaviour change: a snapshot taken by a thread that holds the
channel's transaction or a
LoggedValueguard returnsblocked(it hung). -
New: several threads may take snapshots of one channel; they
take turns on the write mutex.
blockednow takes precedence overpool_exhausted. -
Fixed: a consumer built with
-fvisibility=hiddenagainst a shared libdata_tamer hung inLoggedValue::set()insidescopedWrite(); the transaction code is defined in the library only. -
Behaviour change:
SinkWorker::stop(),start()anddrain()throwstd::logic_errorfrom a callback of their own sink (they deadlocked, orstop()closed the worker silently). Concurrentstop()andstart(), twostopAll()included, are serialized (they hung). A callback that releases the last reference to its own worker no longer callsstd::terminate. -
Fixed: a sink attached during a failing
startLogging()could miss the final schema, and a concurrentaddDataSink()of one worker announced it twice. -
Real-time: no
notify_all()per snapshot or refused push unless a thread waits; each one could be a futex call. -
Behaviour change: names must be non-empty and free of whitespace
and control characters (only the space was refused);
IsCanonicalName()agrees. A ninth default sink throws inaddDefaultSink()(it made every latergetChannel()throw). -
Behaviour change: custom type names, their field names, the
typeName()of aregisterCustomValue()serializer and channel names are checked too: a line break in any of them split the schema text, and a space in a type or field name broke its field line. Type and field names follow the value name rules, and the registration
File truncated at 100 lines see the full file
Package Dependencies
| Deps | Name |
|---|---|
| ament_cmake | |
| rclcpp | |
| rclcpp_lifecycle | |
| mcap_vendor | |
| data_tamer_msgs | |
| ament_cmake_gtest | |
| gtest_vendor |
System Dependencies
| Name |
|---|
| lz4 |
| libzstd-dev |
Dependant Packages
| Name | Deps |
|---|---|
| plotjuggler | |
| data_tamer_tools |
Launch files
Messages
Services
Plugins
Recent questions tagged data_tamer_cpp at Robotics Stack Exchange
|
data_tamer_cpp package from data_tamer repodata_tamer_cpp data_tamer_msgs |
ROS Distro
|
Package Summary
| Version | 2.0.0 |
| License | MIT |
| Build type | AMENT_CMAKE |
| Use | RECOMMENDED |
Repository Summary
| Checkout URI | https://github.com/PickNikRobotics/data_tamer.git |
| VCS Type | git |
| VCS Version | main |
| Last Updated | 2026-10-18 |
| Dev Status | MAINTAINED |
| Released | RELEASED |
| Contributing |
Help Wanted (-)
Good First Issues (-) Pull Requests to Review (-) |
Package Description
Maintainers
- Davide Faconti
- Henry Moore
- Nathan Brooks
Authors
- Davide Faconti
Changelog for package data_tamer
Unreleased
-
Breaking, headers: the public headers move from
data_tamer/todata_tamer_v2/(#include "data_tamer_v2/channel.hpp"), and the standalone parser fromdata_tamer_parser/data_tamer_parser.hpptodata_tamer_v2/data_tamer_parser.hpp, so that 2.x installs side by side with 1.x, whose headers keep their paths. -
ABI:
ChannelSharedState, itsWriteMutexand the series flag words are library-private (src/): the headersdetails/shared_state.hpp,details/write_mutex.hppanddetails/spin_pause.hppare no longer installed, and consumers seeChannelSharedStateonly as an incomplete type.LoggedValuereaches its enabled flag through the exporteddetails::setSeriesEnabled()andisSeriesEnabled(), so the flag encoding and these layouts can change in a 2.x minor release.WriteTransactionis a class at namespace scope (it was the aliasChannelSharedState::Transaction), declared indetails/locked_reference.hppand still returned byscopedWrite(). Rebuild consumers built against earlier headers. -
Behaviour change, parser and Python decoder: a schema text in
the line format needs its
### version:line before the fields; without one both throw, naming the supported versions (4 and 5, 6 in YAML). The C++ parser read such a text as an upper-case "name TYPE" format that no release wrote, or as version 5, and the Python decoder as version 5. Texts of the releases before 0.7.0 (late 2023) fail with that message, among them the header-less<type> <name>lines of the 0.3 to 0.5 ROS 2 publisher, which both used to read (docs/wire_format.md, section 2). -
Fixed, Python decoder:
verify_hash=True(parse_schema(),SchemaRegistry,iter_mcap()) rejected every data_tamer 1.x file (schema version 4). Its hash came from the writer'sstd::hashand cannot be recomputed, so it is accepted as declared. The C++check_hashstill recomputes it, which agrees only with the writer's standard library (docs/wire_format.md, section 5). - Docs:
docs/MIGRATION.mdlists what code written for 1.x must change for 2.0, with the behaviour changes that compile silently. -
Real-time: the first access of the transaction state on a thread
no longer allocates when libdata_tamer is loaded with
dlopen()(a plugin, pluginlib, ros2_control), so ascopedWrite()on each real-time thread during setup is no longer needed. The library's one thread-local is initial-exec TLS (glibc):dlopen()takes one pointer of glibc's static TLS surplus. -
ABI: the
WriteTransactionconstructor and destructor (behindscopedWrite(), the guards and non-scalarLoggedValues) andChannelSharedState::inTransactionOnThisThread()are defined in the library, with the thread-local chain. The chain is no longer an inline protocol, so later 2.x releases can change it; only the size ofWriteTransactionis pinned. Rebuild consumers built against earlier headers. -
API:
data_tamer_v2/data_tamer.hppincludeschannel.hppagain, as in 1.x, so one include givesChannelsRegistry,LogChannel,LoggedValueand the sink interface.data_tamer_v2/fwd.hppstays for headers that only name the types. -
API:
takeSnapshot()is no longer[[nodiscard]]:stats()counts every outcome, and most loops don't act on each call.tryTakeSnapshot()still is. -
API: no
LogChannel::droppedSnapshots(), which no release had: readstats().dropped_by_sink.LogChannel::sinkDropped()andChannelDefaults::resolve()(withChannelDefaults::Sizes) are private: they are the building blocks ofstats()andsetChannelDefaults(). Their symbols stay exported (the inlinestats()callssinkDropped()). -
Fixed, deadlocks:
unregister(),removeDataSink()or aLoggedValuedestructor insidescopedWrite()while a snapshot waited; a const query insidescopedWrite()while another thread ran one of those, orstartLogging();startLogging()insidescopedWrite(). The snapshot path takes the write mutex before its epoch, andstartLogging()before the control mutex. -
Behaviour change: a snapshot taken by a thread that holds the
channel's transaction or a
LoggedValueguard returnsblocked(it hung). -
New: several threads may take snapshots of one channel; they
take turns on the write mutex.
blockednow takes precedence overpool_exhausted. -
Fixed: a consumer built with
-fvisibility=hiddenagainst a shared libdata_tamer hung inLoggedValue::set()insidescopedWrite(); the transaction code is defined in the library only. -
Behaviour change:
SinkWorker::stop(),start()anddrain()throwstd::logic_errorfrom a callback of their own sink (they deadlocked, orstop()closed the worker silently). Concurrentstop()andstart(), twostopAll()included, are serialized (they hung). A callback that releases the last reference to its own worker no longer callsstd::terminate. -
Fixed: a sink attached during a failing
startLogging()could miss the final schema, and a concurrentaddDataSink()of one worker announced it twice. -
Real-time: no
notify_all()per snapshot or refused push unless a thread waits; each one could be a futex call. -
Behaviour change: names must be non-empty and free of whitespace
and control characters (only the space was refused);
IsCanonicalName()agrees. A ninth default sink throws inaddDefaultSink()(it made every latergetChannel()throw). -
Behaviour change: custom type names, their field names, the
typeName()of aregisterCustomValue()serializer and channel names are checked too: a line break in any of them split the schema text, and a space in a type or field name broke its field line. Type and field names follow the value name rules, and the registration
File truncated at 100 lines see the full file
Package Dependencies
| Deps | Name |
|---|---|
| ament_cmake | |
| rclcpp | |
| rclcpp_lifecycle | |
| mcap_vendor | |
| data_tamer_msgs | |
| ament_cmake_gtest | |
| gtest_vendor |
System Dependencies
| Name |
|---|
| lz4 |
| libzstd-dev |
Dependant Packages
| Name | Deps |
|---|---|
| plotjuggler | |
| data_tamer_tools |
Launch files
Messages
Services
Plugins
Recent questions tagged data_tamer_cpp at Robotics Stack Exchange
|
data_tamer_cpp package from data_tamer repodata_tamer_cpp data_tamer_msgs |
ROS Distro
|
Package Summary
| Version | 2.0.0 |
| License | MIT |
| Build type | AMENT_CMAKE |
| Use | RECOMMENDED |
Repository Summary
| Checkout URI | https://github.com/PickNikRobotics/data_tamer.git |
| VCS Type | git |
| VCS Version | main |
| Last Updated | 2026-10-18 |
| Dev Status | MAINTAINED |
| Released | RELEASED |
| Contributing |
Help Wanted (-)
Good First Issues (-) Pull Requests to Review (-) |
Package Description
Maintainers
- Davide Faconti
- Henry Moore
- Nathan Brooks
Authors
- Davide Faconti
Changelog for package data_tamer
Unreleased
-
Breaking, headers: the public headers move from
data_tamer/todata_tamer_v2/(#include "data_tamer_v2/channel.hpp"), and the standalone parser fromdata_tamer_parser/data_tamer_parser.hpptodata_tamer_v2/data_tamer_parser.hpp, so that 2.x installs side by side with 1.x, whose headers keep their paths. -
ABI:
ChannelSharedState, itsWriteMutexand the series flag words are library-private (src/): the headersdetails/shared_state.hpp,details/write_mutex.hppanddetails/spin_pause.hppare no longer installed, and consumers seeChannelSharedStateonly as an incomplete type.LoggedValuereaches its enabled flag through the exporteddetails::setSeriesEnabled()andisSeriesEnabled(), so the flag encoding and these layouts can change in a 2.x minor release.WriteTransactionis a class at namespace scope (it was the aliasChannelSharedState::Transaction), declared indetails/locked_reference.hppand still returned byscopedWrite(). Rebuild consumers built against earlier headers. -
Behaviour change, parser and Python decoder: a schema text in
the line format needs its
### version:line before the fields; without one both throw, naming the supported versions (4 and 5, 6 in YAML). The C++ parser read such a text as an upper-case "name TYPE" format that no release wrote, or as version 5, and the Python decoder as version 5. Texts of the releases before 0.7.0 (late 2023) fail with that message, among them the header-less<type> <name>lines of the 0.3 to 0.5 ROS 2 publisher, which both used to read (docs/wire_format.md, section 2). -
Fixed, Python decoder:
verify_hash=True(parse_schema(),SchemaRegistry,iter_mcap()) rejected every data_tamer 1.x file (schema version 4). Its hash came from the writer'sstd::hashand cannot be recomputed, so it is accepted as declared. The C++check_hashstill recomputes it, which agrees only with the writer's standard library (docs/wire_format.md, section 5). - Docs:
docs/MIGRATION.mdlists what code written for 1.x must change for 2.0, with the behaviour changes that compile silently. -
Real-time: the first access of the transaction state on a thread
no longer allocates when libdata_tamer is loaded with
dlopen()(a plugin, pluginlib, ros2_control), so ascopedWrite()on each real-time thread during setup is no longer needed. The library's one thread-local is initial-exec TLS (glibc):dlopen()takes one pointer of glibc's static TLS surplus. -
ABI: the
WriteTransactionconstructor and destructor (behindscopedWrite(), the guards and non-scalarLoggedValues) andChannelSharedState::inTransactionOnThisThread()are defined in the library, with the thread-local chain. The chain is no longer an inline protocol, so later 2.x releases can change it; only the size ofWriteTransactionis pinned. Rebuild consumers built against earlier headers. -
API:
data_tamer_v2/data_tamer.hppincludeschannel.hppagain, as in 1.x, so one include givesChannelsRegistry,LogChannel,LoggedValueand the sink interface.data_tamer_v2/fwd.hppstays for headers that only name the types. -
API:
takeSnapshot()is no longer[[nodiscard]]:stats()counts every outcome, and most loops don't act on each call.tryTakeSnapshot()still is. -
API: no
LogChannel::droppedSnapshots(), which no release had: readstats().dropped_by_sink.LogChannel::sinkDropped()andChannelDefaults::resolve()(withChannelDefaults::Sizes) are private: they are the building blocks ofstats()andsetChannelDefaults(). Their symbols stay exported (the inlinestats()callssinkDropped()). -
Fixed, deadlocks:
unregister(),removeDataSink()or aLoggedValuedestructor insidescopedWrite()while a snapshot waited; a const query insidescopedWrite()while another thread ran one of those, orstartLogging();startLogging()insidescopedWrite(). The snapshot path takes the write mutex before its epoch, andstartLogging()before the control mutex. -
Behaviour change: a snapshot taken by a thread that holds the
channel's transaction or a
LoggedValueguard returnsblocked(it hung). -
New: several threads may take snapshots of one channel; they
take turns on the write mutex.
blockednow takes precedence overpool_exhausted. -
Fixed: a consumer built with
-fvisibility=hiddenagainst a shared libdata_tamer hung inLoggedValue::set()insidescopedWrite(); the transaction code is defined in the library only. -
Behaviour change:
SinkWorker::stop(),start()anddrain()throwstd::logic_errorfrom a callback of their own sink (they deadlocked, orstop()closed the worker silently). Concurrentstop()andstart(), twostopAll()included, are serialized (they hung). A callback that releases the last reference to its own worker no longer callsstd::terminate. -
Fixed: a sink attached during a failing
startLogging()could miss the final schema, and a concurrentaddDataSink()of one worker announced it twice. -
Real-time: no
notify_all()per snapshot or refused push unless a thread waits; each one could be a futex call. -
Behaviour change: names must be non-empty and free of whitespace
and control characters (only the space was refused);
IsCanonicalName()agrees. A ninth default sink throws inaddDefaultSink()(it made every latergetChannel()throw). -
Behaviour change: custom type names, their field names, the
typeName()of aregisterCustomValue()serializer and channel names are checked too: a line break in any of them split the schema text, and a space in a type or field name broke its field line. Type and field names follow the value name rules, and the registration
File truncated at 100 lines see the full file
Package Dependencies
| Deps | Name |
|---|---|
| ament_cmake | |
| rclcpp | |
| rclcpp_lifecycle | |
| mcap_vendor | |
| data_tamer_msgs | |
| ament_cmake_gtest | |
| gtest_vendor |
System Dependencies
| Name |
|---|
| lz4 |
| libzstd-dev |
Dependant Packages
| Name | Deps |
|---|---|
| plotjuggler |
Launch files
Messages
Services
Plugins
Recent questions tagged data_tamer_cpp at Robotics Stack Exchange
|
data_tamer_cpp package from data_tamer repodata_tamer_cpp data_tamer_msgs |
ROS Distro
|
Package Summary
| Version | 2.0.0 |
| License | MIT |
| Build type | AMENT_CMAKE |
| Use | RECOMMENDED |
Repository Summary
| Checkout URI | https://github.com/PickNikRobotics/data_tamer.git |
| VCS Type | git |
| VCS Version | main |
| Last Updated | 2026-10-18 |
| Dev Status | MAINTAINED |
| Released | RELEASED |
| Contributing |
Help Wanted (-)
Good First Issues (-) Pull Requests to Review (-) |
Package Description
Maintainers
- Davide Faconti
- Henry Moore
- Nathan Brooks
Authors
- Davide Faconti
Changelog for package data_tamer
Unreleased
-
Breaking, headers: the public headers move from
data_tamer/todata_tamer_v2/(#include "data_tamer_v2/channel.hpp"), and the standalone parser fromdata_tamer_parser/data_tamer_parser.hpptodata_tamer_v2/data_tamer_parser.hpp, so that 2.x installs side by side with 1.x, whose headers keep their paths. -
ABI:
ChannelSharedState, itsWriteMutexand the series flag words are library-private (src/): the headersdetails/shared_state.hpp,details/write_mutex.hppanddetails/spin_pause.hppare no longer installed, and consumers seeChannelSharedStateonly as an incomplete type.LoggedValuereaches its enabled flag through the exporteddetails::setSeriesEnabled()andisSeriesEnabled(), so the flag encoding and these layouts can change in a 2.x minor release.WriteTransactionis a class at namespace scope (it was the aliasChannelSharedState::Transaction), declared indetails/locked_reference.hppand still returned byscopedWrite(). Rebuild consumers built against earlier headers. -
Behaviour change, parser and Python decoder: a schema text in
the line format needs its
### version:line before the fields; without one both throw, naming the supported versions (4 and 5, 6 in YAML). The C++ parser read such a text as an upper-case "name TYPE" format that no release wrote, or as version 5, and the Python decoder as version 5. Texts of the releases before 0.7.0 (late 2023) fail with that message, among them the header-less<type> <name>lines of the 0.3 to 0.5 ROS 2 publisher, which both used to read (docs/wire_format.md, section 2). -
Fixed, Python decoder:
verify_hash=True(parse_schema(),SchemaRegistry,iter_mcap()) rejected every data_tamer 1.x file (schema version 4). Its hash came from the writer'sstd::hashand cannot be recomputed, so it is accepted as declared. The C++check_hashstill recomputes it, which agrees only with the writer's standard library (docs/wire_format.md, section 5). - Docs:
docs/MIGRATION.mdlists what code written for 1.x must change for 2.0, with the behaviour changes that compile silently. -
Real-time: the first access of the transaction state on a thread
no longer allocates when libdata_tamer is loaded with
dlopen()(a plugin, pluginlib, ros2_control), so ascopedWrite()on each real-time thread during setup is no longer needed. The library's one thread-local is initial-exec TLS (glibc):dlopen()takes one pointer of glibc's static TLS surplus. -
ABI: the
WriteTransactionconstructor and destructor (behindscopedWrite(), the guards and non-scalarLoggedValues) andChannelSharedState::inTransactionOnThisThread()are defined in the library, with the thread-local chain. The chain is no longer an inline protocol, so later 2.x releases can change it; only the size ofWriteTransactionis pinned. Rebuild consumers built against earlier headers. -
API:
data_tamer_v2/data_tamer.hppincludeschannel.hppagain, as in 1.x, so one include givesChannelsRegistry,LogChannel,LoggedValueand the sink interface.data_tamer_v2/fwd.hppstays for headers that only name the types. -
API:
takeSnapshot()is no longer[[nodiscard]]:stats()counts every outcome, and most loops don't act on each call.tryTakeSnapshot()still is. -
API: no
LogChannel::droppedSnapshots(), which no release had: readstats().dropped_by_sink.LogChannel::sinkDropped()andChannelDefaults::resolve()(withChannelDefaults::Sizes) are private: they are the building blocks ofstats()andsetChannelDefaults(). Their symbols stay exported (the inlinestats()callssinkDropped()). -
Fixed, deadlocks:
unregister(),removeDataSink()or aLoggedValuedestructor insidescopedWrite()while a snapshot waited; a const query insidescopedWrite()while another thread ran one of those, orstartLogging();startLogging()insidescopedWrite(). The snapshot path takes the write mutex before its epoch, andstartLogging()before the control mutex. -
Behaviour change: a snapshot taken by a thread that holds the
channel's transaction or a
LoggedValueguard returnsblocked(it hung). -
New: several threads may take snapshots of one channel; they
take turns on the write mutex.
blockednow takes precedence overpool_exhausted. -
Fixed: a consumer built with
-fvisibility=hiddenagainst a shared libdata_tamer hung inLoggedValue::set()insidescopedWrite(); the transaction code is defined in the library only. -
Behaviour change:
SinkWorker::stop(),start()anddrain()throwstd::logic_errorfrom a callback of their own sink (they deadlocked, orstop()closed the worker silently). Concurrentstop()andstart(), twostopAll()included, are serialized (they hung). A callback that releases the last reference to its own worker no longer callsstd::terminate. -
Fixed: a sink attached during a failing
startLogging()could miss the final schema, and a concurrentaddDataSink()of one worker announced it twice. -
Real-time: no
notify_all()per snapshot or refused push unless a thread waits; each one could be a futex call. -
Behaviour change: names must be non-empty and free of whitespace
and control characters (only the space was refused);
IsCanonicalName()agrees. A ninth default sink throws inaddDefaultSink()(it made every latergetChannel()throw). -
Behaviour change: custom type names, their field names, the
typeName()of aregisterCustomValue()serializer and channel names are checked too: a line break in any of them split the schema text, and a space in a type or field name broke its field line. Type and field names follow the value name rules, and the registration
File truncated at 100 lines see the full file
Package Dependencies
| Deps | Name |
|---|---|
| ament_cmake | |
| rclcpp | |
| rclcpp_lifecycle | |
| mcap_vendor | |
| data_tamer_msgs | |
| ament_cmake_gtest | |
| gtest_vendor |
System Dependencies
| Name |
|---|
| lz4 |
| libzstd-dev |
Dependant Packages
| Name | Deps |
|---|---|
| plotjuggler |
Launch files
Messages
Services
Plugins
Recent questions tagged data_tamer_cpp at Robotics Stack Exchange
|
data_tamer_cpp package from data_tamer repodata_tamer_cpp data_tamer_msgs |
ROS Distro
|
Package Summary
| Version | 2.0.0 |
| License | MIT |
| Build type | AMENT_CMAKE |
| Use | RECOMMENDED |
Repository Summary
| Checkout URI | https://github.com/PickNikRobotics/data_tamer.git |
| VCS Type | git |
| VCS Version | main |
| Last Updated | 2026-10-18 |
| Dev Status | MAINTAINED |
| Released | RELEASED |
| Contributing |
Help Wanted (-)
Good First Issues (-) Pull Requests to Review (-) |
Package Description
Maintainers
- Davide Faconti
- Henry Moore
- Nathan Brooks
Authors
- Davide Faconti
Changelog for package data_tamer
Unreleased
-
Breaking, headers: the public headers move from
data_tamer/todata_tamer_v2/(#include "data_tamer_v2/channel.hpp"), and the standalone parser fromdata_tamer_parser/data_tamer_parser.hpptodata_tamer_v2/data_tamer_parser.hpp, so that 2.x installs side by side with 1.x, whose headers keep their paths. -
ABI:
ChannelSharedState, itsWriteMutexand the series flag words are library-private (src/): the headersdetails/shared_state.hpp,details/write_mutex.hppanddetails/spin_pause.hppare no longer installed, and consumers seeChannelSharedStateonly as an incomplete type.LoggedValuereaches its enabled flag through the exporteddetails::setSeriesEnabled()andisSeriesEnabled(), so the flag encoding and these layouts can change in a 2.x minor release.WriteTransactionis a class at namespace scope (it was the aliasChannelSharedState::Transaction), declared indetails/locked_reference.hppand still returned byscopedWrite(). Rebuild consumers built against earlier headers. -
Behaviour change, parser and Python decoder: a schema text in
the line format needs its
### version:line before the fields; without one both throw, naming the supported versions (4 and 5, 6 in YAML). The C++ parser read such a text as an upper-case "name TYPE" format that no release wrote, or as version 5, and the Python decoder as version 5. Texts of the releases before 0.7.0 (late 2023) fail with that message, among them the header-less<type> <name>lines of the 0.3 to 0.5 ROS 2 publisher, which both used to read (docs/wire_format.md, section 2). -
Fixed, Python decoder:
verify_hash=True(parse_schema(),SchemaRegistry,iter_mcap()) rejected every data_tamer 1.x file (schema version 4). Its hash came from the writer'sstd::hashand cannot be recomputed, so it is accepted as declared. The C++check_hashstill recomputes it, which agrees only with the writer's standard library (docs/wire_format.md, section 5). - Docs:
docs/MIGRATION.mdlists what code written for 1.x must change for 2.0, with the behaviour changes that compile silently. -
Real-time: the first access of the transaction state on a thread
no longer allocates when libdata_tamer is loaded with
dlopen()(a plugin, pluginlib, ros2_control), so ascopedWrite()on each real-time thread during setup is no longer needed. The library's one thread-local is initial-exec TLS (glibc):dlopen()takes one pointer of glibc's static TLS surplus. -
ABI: the
WriteTransactionconstructor and destructor (behindscopedWrite(), the guards and non-scalarLoggedValues) andChannelSharedState::inTransactionOnThisThread()are defined in the library, with the thread-local chain. The chain is no longer an inline protocol, so later 2.x releases can change it; only the size ofWriteTransactionis pinned. Rebuild consumers built against earlier headers. -
API:
data_tamer_v2/data_tamer.hppincludeschannel.hppagain, as in 1.x, so one include givesChannelsRegistry,LogChannel,LoggedValueand the sink interface.data_tamer_v2/fwd.hppstays for headers that only name the types. -
API:
takeSnapshot()is no longer[[nodiscard]]:stats()counts every outcome, and most loops don't act on each call.tryTakeSnapshot()still is. -
API: no
LogChannel::droppedSnapshots(), which no release had: readstats().dropped_by_sink.LogChannel::sinkDropped()andChannelDefaults::resolve()(withChannelDefaults::Sizes) are private: they are the building blocks ofstats()andsetChannelDefaults(). Their symbols stay exported (the inlinestats()callssinkDropped()). -
Fixed, deadlocks:
unregister(),removeDataSink()or aLoggedValuedestructor insidescopedWrite()while a snapshot waited; a const query insidescopedWrite()while another thread ran one of those, orstartLogging();startLogging()insidescopedWrite(). The snapshot path takes the write mutex before its epoch, andstartLogging()before the control mutex. -
Behaviour change: a snapshot taken by a thread that holds the
channel's transaction or a
LoggedValueguard returnsblocked(it hung). -
New: several threads may take snapshots of one channel; they
take turns on the write mutex.
blockednow takes precedence overpool_exhausted. -
Fixed: a consumer built with
-fvisibility=hiddenagainst a shared libdata_tamer hung inLoggedValue::set()insidescopedWrite(); the transaction code is defined in the library only. -
Behaviour change:
SinkWorker::stop(),start()anddrain()throwstd::logic_errorfrom a callback of their own sink (they deadlocked, orstop()closed the worker silently). Concurrentstop()andstart(), twostopAll()included, are serialized (they hung). A callback that releases the last reference to its own worker no longer callsstd::terminate. -
Fixed: a sink attached during a failing
startLogging()could miss the final schema, and a concurrentaddDataSink()of one worker announced it twice. -
Real-time: no
notify_all()per snapshot or refused push unless a thread waits; each one could be a futex call. -
Behaviour change: names must be non-empty and free of whitespace
and control characters (only the space was refused);
IsCanonicalName()agrees. A ninth default sink throws inaddDefaultSink()(it made every latergetChannel()throw). -
Behaviour change: custom type names, their field names, the
typeName()of aregisterCustomValue()serializer and channel names are checked too: a line break in any of them split the schema text, and a space in a type or field name broke its field line. Type and field names follow the value name rules, and the registration
File truncated at 100 lines see the full file
Package Dependencies
| Deps | Name |
|---|---|
| ament_cmake | |
| rclcpp | |
| rclcpp_lifecycle | |
| mcap_vendor | |
| data_tamer_msgs | |
| ament_cmake_gtest | |
| gtest_vendor |
System Dependencies
| Name |
|---|
| lz4 |
| libzstd-dev |
Dependant Packages
| Name | Deps |
|---|---|
| plotjuggler |
Launch files
Messages
Services
Plugins
Recent questions tagged data_tamer_cpp at Robotics Stack Exchange
|
data_tamer_cpp package from data_tamer repodata_tamer_cpp data_tamer_msgs |
ROS Distro
|
Package Summary
| Version | 2.0.0 |
| License | MIT |
| Build type | AMENT_CMAKE |
| Use | RECOMMENDED |
Repository Summary
| Checkout URI | https://github.com/PickNikRobotics/data_tamer.git |
| VCS Type | git |
| VCS Version | main |
| Last Updated | 2026-10-18 |
| Dev Status | MAINTAINED |
| Released | RELEASED |
| Contributing |
Help Wanted (-)
Good First Issues (-) Pull Requests to Review (-) |
Package Description
Maintainers
- Davide Faconti
- Henry Moore
- Nathan Brooks
Authors
- Davide Faconti
Changelog for package data_tamer
Unreleased
-
Breaking, headers: the public headers move from
data_tamer/todata_tamer_v2/(#include "data_tamer_v2/channel.hpp"), and the standalone parser fromdata_tamer_parser/data_tamer_parser.hpptodata_tamer_v2/data_tamer_parser.hpp, so that 2.x installs side by side with 1.x, whose headers keep their paths. -
ABI:
ChannelSharedState, itsWriteMutexand the series flag words are library-private (src/): the headersdetails/shared_state.hpp,details/write_mutex.hppanddetails/spin_pause.hppare no longer installed, and consumers seeChannelSharedStateonly as an incomplete type.LoggedValuereaches its enabled flag through the exporteddetails::setSeriesEnabled()andisSeriesEnabled(), so the flag encoding and these layouts can change in a 2.x minor release.WriteTransactionis a class at namespace scope (it was the aliasChannelSharedState::Transaction), declared indetails/locked_reference.hppand still returned byscopedWrite(). Rebuild consumers built against earlier headers. -
Behaviour change, parser and Python decoder: a schema text in
the line format needs its
### version:line before the fields; without one both throw, naming the supported versions (4 and 5, 6 in YAML). The C++ parser read such a text as an upper-case "name TYPE" format that no release wrote, or as version 5, and the Python decoder as version 5. Texts of the releases before 0.7.0 (late 2023) fail with that message, among them the header-less<type> <name>lines of the 0.3 to 0.5 ROS 2 publisher, which both used to read (docs/wire_format.md, section 2). -
Fixed, Python decoder:
verify_hash=True(parse_schema(),SchemaRegistry,iter_mcap()) rejected every data_tamer 1.x file (schema version 4). Its hash came from the writer'sstd::hashand cannot be recomputed, so it is accepted as declared. The C++check_hashstill recomputes it, which agrees only with the writer's standard library (docs/wire_format.md, section 5). - Docs:
docs/MIGRATION.mdlists what code written for 1.x must change for 2.0, with the behaviour changes that compile silently. -
Real-time: the first access of the transaction state on a thread
no longer allocates when libdata_tamer is loaded with
dlopen()(a plugin, pluginlib, ros2_control), so ascopedWrite()on each real-time thread during setup is no longer needed. The library's one thread-local is initial-exec TLS (glibc):dlopen()takes one pointer of glibc's static TLS surplus. -
ABI: the
WriteTransactionconstructor and destructor (behindscopedWrite(), the guards and non-scalarLoggedValues) andChannelSharedState::inTransactionOnThisThread()are defined in the library, with the thread-local chain. The chain is no longer an inline protocol, so later 2.x releases can change it; only the size ofWriteTransactionis pinned. Rebuild consumers built against earlier headers. -
API:
data_tamer_v2/data_tamer.hppincludeschannel.hppagain, as in 1.x, so one include givesChannelsRegistry,LogChannel,LoggedValueand the sink interface.data_tamer_v2/fwd.hppstays for headers that only name the types. -
API:
takeSnapshot()is no longer[[nodiscard]]:stats()counts every outcome, and most loops don't act on each call.tryTakeSnapshot()still is. -
API: no
LogChannel::droppedSnapshots(), which no release had: readstats().dropped_by_sink.LogChannel::sinkDropped()andChannelDefaults::resolve()(withChannelDefaults::Sizes) are private: they are the building blocks ofstats()andsetChannelDefaults(). Their symbols stay exported (the inlinestats()callssinkDropped()). -
Fixed, deadlocks:
unregister(),removeDataSink()or aLoggedValuedestructor insidescopedWrite()while a snapshot waited; a const query insidescopedWrite()while another thread ran one of those, orstartLogging();startLogging()insidescopedWrite(). The snapshot path takes the write mutex before its epoch, andstartLogging()before the control mutex. -
Behaviour change: a snapshot taken by a thread that holds the
channel's transaction or a
LoggedValueguard returnsblocked(it hung). -
New: several threads may take snapshots of one channel; they
take turns on the write mutex.
blockednow takes precedence overpool_exhausted. -
Fixed: a consumer built with
-fvisibility=hiddenagainst a shared libdata_tamer hung inLoggedValue::set()insidescopedWrite(); the transaction code is defined in the library only. -
Behaviour change:
SinkWorker::stop(),start()anddrain()throwstd::logic_errorfrom a callback of their own sink (they deadlocked, orstop()closed the worker silently). Concurrentstop()andstart(), twostopAll()included, are serialized (they hung). A callback that releases the last reference to its own worker no longer callsstd::terminate. -
Fixed: a sink attached during a failing
startLogging()could miss the final schema, and a concurrentaddDataSink()of one worker announced it twice. -
Real-time: no
notify_all()per snapshot or refused push unless a thread waits; each one could be a futex call. -
Behaviour change: names must be non-empty and free of whitespace
and control characters (only the space was refused);
IsCanonicalName()agrees. A ninth default sink throws inaddDefaultSink()(it made every latergetChannel()throw). -
Behaviour change: custom type names, their field names, the
typeName()of aregisterCustomValue()serializer and channel names are checked too: a line break in any of them split the schema text, and a space in a type or field name broke its field line. Type and field names follow the value name rules, and the registration
File truncated at 100 lines see the full file
Package Dependencies
| Deps | Name |
|---|---|
| ament_cmake | |
| rclcpp | |
| rclcpp_lifecycle | |
| mcap_vendor | |
| data_tamer_msgs | |
| ament_cmake_gtest | |
| gtest_vendor |
System Dependencies
| Name |
|---|
| lz4 |
| libzstd-dev |
Dependant Packages
| Name | Deps |
|---|---|
| plotjuggler |
Launch files
Messages
Services
Plugins
Recent questions tagged data_tamer_cpp at Robotics Stack Exchange
|
data_tamer_cpp package from data_tamer repodata_tamer_cpp data_tamer_msgs |
ROS Distro
|
Package Summary
| Version | 2.0.0 |
| License | MIT |
| Build type | AMENT_CMAKE |
| Use | RECOMMENDED |
Repository Summary
| Checkout URI | https://github.com/PickNikRobotics/data_tamer.git |
| VCS Type | git |
| VCS Version | main |
| Last Updated | 2026-10-18 |
| Dev Status | MAINTAINED |
| Released | RELEASED |
| Contributing |
Help Wanted (-)
Good First Issues (-) Pull Requests to Review (-) |
Package Description
Maintainers
- Davide Faconti
- Henry Moore
- Nathan Brooks
Authors
- Davide Faconti
Changelog for package data_tamer
Unreleased
-
Breaking, headers: the public headers move from
data_tamer/todata_tamer_v2/(#include "data_tamer_v2/channel.hpp"), and the standalone parser fromdata_tamer_parser/data_tamer_parser.hpptodata_tamer_v2/data_tamer_parser.hpp, so that 2.x installs side by side with 1.x, whose headers keep their paths. -
ABI:
ChannelSharedState, itsWriteMutexand the series flag words are library-private (src/): the headersdetails/shared_state.hpp,details/write_mutex.hppanddetails/spin_pause.hppare no longer installed, and consumers seeChannelSharedStateonly as an incomplete type.LoggedValuereaches its enabled flag through the exporteddetails::setSeriesEnabled()andisSeriesEnabled(), so the flag encoding and these layouts can change in a 2.x minor release.WriteTransactionis a class at namespace scope (it was the aliasChannelSharedState::Transaction), declared indetails/locked_reference.hppand still returned byscopedWrite(). Rebuild consumers built against earlier headers. -
Behaviour change, parser and Python decoder: a schema text in
the line format needs its
### version:line before the fields; without one both throw, naming the supported versions (4 and 5, 6 in YAML). The C++ parser read such a text as an upper-case "name TYPE" format that no release wrote, or as version 5, and the Python decoder as version 5. Texts of the releases before 0.7.0 (late 2023) fail with that message, among them the header-less<type> <name>lines of the 0.3 to 0.5 ROS 2 publisher, which both used to read (docs/wire_format.md, section 2). -
Fixed, Python decoder:
verify_hash=True(parse_schema(),SchemaRegistry,iter_mcap()) rejected every data_tamer 1.x file (schema version 4). Its hash came from the writer'sstd::hashand cannot be recomputed, so it is accepted as declared. The C++check_hashstill recomputes it, which agrees only with the writer's standard library (docs/wire_format.md, section 5). - Docs:
docs/MIGRATION.mdlists what code written for 1.x must change for 2.0, with the behaviour changes that compile silently. -
Real-time: the first access of the transaction state on a thread
no longer allocates when libdata_tamer is loaded with
dlopen()(a plugin, pluginlib, ros2_control), so ascopedWrite()on each real-time thread during setup is no longer needed. The library's one thread-local is initial-exec TLS (glibc):dlopen()takes one pointer of glibc's static TLS surplus. -
ABI: the
WriteTransactionconstructor and destructor (behindscopedWrite(), the guards and non-scalarLoggedValues) andChannelSharedState::inTransactionOnThisThread()are defined in the library, with the thread-local chain. The chain is no longer an inline protocol, so later 2.x releases can change it; only the size ofWriteTransactionis pinned. Rebuild consumers built against earlier headers. -
API:
data_tamer_v2/data_tamer.hppincludeschannel.hppagain, as in 1.x, so one include givesChannelsRegistry,LogChannel,LoggedValueand the sink interface.data_tamer_v2/fwd.hppstays for headers that only name the types. -
API:
takeSnapshot()is no longer[[nodiscard]]:stats()counts every outcome, and most loops don't act on each call.tryTakeSnapshot()still is. -
API: no
LogChannel::droppedSnapshots(), which no release had: readstats().dropped_by_sink.LogChannel::sinkDropped()andChannelDefaults::resolve()(withChannelDefaults::Sizes) are private: they are the building blocks ofstats()andsetChannelDefaults(). Their symbols stay exported (the inlinestats()callssinkDropped()). -
Fixed, deadlocks:
unregister(),removeDataSink()or aLoggedValuedestructor insidescopedWrite()while a snapshot waited; a const query insidescopedWrite()while another thread ran one of those, orstartLogging();startLogging()insidescopedWrite(). The snapshot path takes the write mutex before its epoch, andstartLogging()before the control mutex. -
Behaviour change: a snapshot taken by a thread that holds the
channel's transaction or a
LoggedValueguard returnsblocked(it hung). -
New: several threads may take snapshots of one channel; they
take turns on the write mutex.
blockednow takes precedence overpool_exhausted. -
Fixed: a consumer built with
-fvisibility=hiddenagainst a shared libdata_tamer hung inLoggedValue::set()insidescopedWrite(); the transaction code is defined in the library only. -
Behaviour change:
SinkWorker::stop(),start()anddrain()throwstd::logic_errorfrom a callback of their own sink (they deadlocked, orstop()closed the worker silently). Concurrentstop()andstart(), twostopAll()included, are serialized (they hung). A callback that releases the last reference to its own worker no longer callsstd::terminate. -
Fixed: a sink attached during a failing
startLogging()could miss the final schema, and a concurrentaddDataSink()of one worker announced it twice. -
Real-time: no
notify_all()per snapshot or refused push unless a thread waits; each one could be a futex call. -
Behaviour change: names must be non-empty and free of whitespace
and control characters (only the space was refused);
IsCanonicalName()agrees. A ninth default sink throws inaddDefaultSink()(it made every latergetChannel()throw). -
Behaviour change: custom type names, their field names, the
typeName()of aregisterCustomValue()serializer and channel names are checked too: a line break in any of them split the schema text, and a space in a type or field name broke its field line. Type and field names follow the value name rules, and the registration
File truncated at 100 lines see the full file
Package Dependencies
| Deps | Name |
|---|---|
| ament_cmake | |
| rclcpp | |
| rclcpp_lifecycle | |
| mcap_vendor | |
| data_tamer_msgs | |
| ament_cmake_gtest | |
| gtest_vendor |
System Dependencies
| Name |
|---|
| lz4 |
| libzstd-dev |
Dependant Packages
| Name | Deps |
|---|---|
| plotjuggler |
Launch files
Messages
Services
Plugins
Recent questions tagged data_tamer_cpp at Robotics Stack Exchange
|
data_tamer_cpp package from data_tamer repodata_tamer_cpp data_tamer_msgs |
ROS Distro
|
Package Summary
| Version | 2.0.0 |
| License | MIT |
| Build type | AMENT_CMAKE |
| Use | RECOMMENDED |
Repository Summary
| Checkout URI | https://github.com/PickNikRobotics/data_tamer.git |
| VCS Type | git |
| VCS Version | main |
| Last Updated | 2026-10-18 |
| Dev Status | MAINTAINED |
| Released | RELEASED |
| Contributing |
Help Wanted (-)
Good First Issues (-) Pull Requests to Review (-) |
Package Description
Maintainers
- Davide Faconti
- Henry Moore
- Nathan Brooks
Authors
- Davide Faconti
Changelog for package data_tamer
Unreleased
-
Breaking, headers: the public headers move from
data_tamer/todata_tamer_v2/(#include "data_tamer_v2/channel.hpp"), and the standalone parser fromdata_tamer_parser/data_tamer_parser.hpptodata_tamer_v2/data_tamer_parser.hpp, so that 2.x installs side by side with 1.x, whose headers keep their paths. -
ABI:
ChannelSharedState, itsWriteMutexand the series flag words are library-private (src/): the headersdetails/shared_state.hpp,details/write_mutex.hppanddetails/spin_pause.hppare no longer installed, and consumers seeChannelSharedStateonly as an incomplete type.LoggedValuereaches its enabled flag through the exporteddetails::setSeriesEnabled()andisSeriesEnabled(), so the flag encoding and these layouts can change in a 2.x minor release.WriteTransactionis a class at namespace scope (it was the aliasChannelSharedState::Transaction), declared indetails/locked_reference.hppand still returned byscopedWrite(). Rebuild consumers built against earlier headers. -
Behaviour change, parser and Python decoder: a schema text in
the line format needs its
### version:line before the fields; without one both throw, naming the supported versions (4 and 5, 6 in YAML). The C++ parser read such a text as an upper-case "name TYPE" format that no release wrote, or as version 5, and the Python decoder as version 5. Texts of the releases before 0.7.0 (late 2023) fail with that message, among them the header-less<type> <name>lines of the 0.3 to 0.5 ROS 2 publisher, which both used to read (docs/wire_format.md, section 2). -
Fixed, Python decoder:
verify_hash=True(parse_schema(),SchemaRegistry,iter_mcap()) rejected every data_tamer 1.x file (schema version 4). Its hash came from the writer'sstd::hashand cannot be recomputed, so it is accepted as declared. The C++check_hashstill recomputes it, which agrees only with the writer's standard library (docs/wire_format.md, section 5). - Docs:
docs/MIGRATION.mdlists what code written for 1.x must change for 2.0, with the behaviour changes that compile silently. -
Real-time: the first access of the transaction state on a thread
no longer allocates when libdata_tamer is loaded with
dlopen()(a plugin, pluginlib, ros2_control), so ascopedWrite()on each real-time thread during setup is no longer needed. The library's one thread-local is initial-exec TLS (glibc):dlopen()takes one pointer of glibc's static TLS surplus. -
ABI: the
WriteTransactionconstructor and destructor (behindscopedWrite(), the guards and non-scalarLoggedValues) andChannelSharedState::inTransactionOnThisThread()are defined in the library, with the thread-local chain. The chain is no longer an inline protocol, so later 2.x releases can change it; only the size ofWriteTransactionis pinned. Rebuild consumers built against earlier headers. -
API:
data_tamer_v2/data_tamer.hppincludeschannel.hppagain, as in 1.x, so one include givesChannelsRegistry,LogChannel,LoggedValueand the sink interface.data_tamer_v2/fwd.hppstays for headers that only name the types. -
API:
takeSnapshot()is no longer[[nodiscard]]:stats()counts every outcome, and most loops don't act on each call.tryTakeSnapshot()still is. -
API: no
LogChannel::droppedSnapshots(), which no release had: readstats().dropped_by_sink.LogChannel::sinkDropped()andChannelDefaults::resolve()(withChannelDefaults::Sizes) are private: they are the building blocks ofstats()andsetChannelDefaults(). Their symbols stay exported (the inlinestats()callssinkDropped()). -
Fixed, deadlocks:
unregister(),removeDataSink()or aLoggedValuedestructor insidescopedWrite()while a snapshot waited; a const query insidescopedWrite()while another thread ran one of those, orstartLogging();startLogging()insidescopedWrite(). The snapshot path takes the write mutex before its epoch, andstartLogging()before the control mutex. -
Behaviour change: a snapshot taken by a thread that holds the
channel's transaction or a
LoggedValueguard returnsblocked(it hung). -
New: several threads may take snapshots of one channel; they
take turns on the write mutex.
blockednow takes precedence overpool_exhausted. -
Fixed: a consumer built with
-fvisibility=hiddenagainst a shared libdata_tamer hung inLoggedValue::set()insidescopedWrite(); the transaction code is defined in the library only. -
Behaviour change:
SinkWorker::stop(),start()anddrain()throwstd::logic_errorfrom a callback of their own sink (they deadlocked, orstop()closed the worker silently). Concurrentstop()andstart(), twostopAll()included, are serialized (they hung). A callback that releases the last reference to its own worker no longer callsstd::terminate. -
Fixed: a sink attached during a failing
startLogging()could miss the final schema, and a concurrentaddDataSink()of one worker announced it twice. -
Real-time: no
notify_all()per snapshot or refused push unless a thread waits; each one could be a futex call. -
Behaviour change: names must be non-empty and free of whitespace
and control characters (only the space was refused);
IsCanonicalName()agrees. A ninth default sink throws inaddDefaultSink()(it made every latergetChannel()throw). -
Behaviour change: custom type names, their field names, the
typeName()of aregisterCustomValue()serializer and channel names are checked too: a line break in any of them split the schema text, and a space in a type or field name broke its field line. Type and field names follow the value name rules, and the registration
File truncated at 100 lines see the full file
Package Dependencies
| Deps | Name |
|---|---|
| ament_cmake | |
| rclcpp | |
| rclcpp_lifecycle | |
| mcap_vendor | |
| data_tamer_msgs | |
| ament_cmake_gtest | |
| gtest_vendor |
System Dependencies
| Name |
|---|
| lz4 |
| libzstd-dev |
Dependant Packages
| Name | Deps |
|---|---|
| plotjuggler |
Launch files
Messages
Services
Plugins
Recent questions tagged data_tamer_cpp at Robotics Stack Exchange
|
data_tamer_cpp package from data_tamer repodata_tamer_cpp data_tamer_msgs |
ROS Distro
|
Package Summary
| Version | 2.0.0 |
| License | MIT |
| Build type | AMENT_CMAKE |
| Use | RECOMMENDED |
Repository Summary
| Checkout URI | https://github.com/PickNikRobotics/data_tamer.git |
| VCS Type | git |
| VCS Version | main |
| Last Updated | 2026-10-18 |
| Dev Status | MAINTAINED |
| Released | RELEASED |
| Contributing |
Help Wanted (-)
Good First Issues (-) Pull Requests to Review (-) |
Package Description
Maintainers
- Davide Faconti
- Henry Moore
- Nathan Brooks
Authors
- Davide Faconti
Changelog for package data_tamer
Unreleased
-
Breaking, headers: the public headers move from
data_tamer/todata_tamer_v2/(#include "data_tamer_v2/channel.hpp"), and the standalone parser fromdata_tamer_parser/data_tamer_parser.hpptodata_tamer_v2/data_tamer_parser.hpp, so that 2.x installs side by side with 1.x, whose headers keep their paths. -
ABI:
ChannelSharedState, itsWriteMutexand the series flag words are library-private (src/): the headersdetails/shared_state.hpp,details/write_mutex.hppanddetails/spin_pause.hppare no longer installed, and consumers seeChannelSharedStateonly as an incomplete type.LoggedValuereaches its enabled flag through the exporteddetails::setSeriesEnabled()andisSeriesEnabled(), so the flag encoding and these layouts can change in a 2.x minor release.WriteTransactionis a class at namespace scope (it was the aliasChannelSharedState::Transaction), declared indetails/locked_reference.hppand still returned byscopedWrite(). Rebuild consumers built against earlier headers. -
Behaviour change, parser and Python decoder: a schema text in
the line format needs its
### version:line before the fields; without one both throw, naming the supported versions (4 and 5, 6 in YAML). The C++ parser read such a text as an upper-case "name TYPE" format that no release wrote, or as version 5, and the Python decoder as version 5. Texts of the releases before 0.7.0 (late 2023) fail with that message, among them the header-less<type> <name>lines of the 0.3 to 0.5 ROS 2 publisher, which both used to read (docs/wire_format.md, section 2). -
Fixed, Python decoder:
verify_hash=True(parse_schema(),SchemaRegistry,iter_mcap()) rejected every data_tamer 1.x file (schema version 4). Its hash came from the writer'sstd::hashand cannot be recomputed, so it is accepted as declared. The C++check_hashstill recomputes it, which agrees only with the writer's standard library (docs/wire_format.md, section 5). - Docs:
docs/MIGRATION.mdlists what code written for 1.x must change for 2.0, with the behaviour changes that compile silently. -
Real-time: the first access of the transaction state on a thread
no longer allocates when libdata_tamer is loaded with
dlopen()(a plugin, pluginlib, ros2_control), so ascopedWrite()on each real-time thread during setup is no longer needed. The library's one thread-local is initial-exec TLS (glibc):dlopen()takes one pointer of glibc's static TLS surplus. -
ABI: the
WriteTransactionconstructor and destructor (behindscopedWrite(), the guards and non-scalarLoggedValues) andChannelSharedState::inTransactionOnThisThread()are defined in the library, with the thread-local chain. The chain is no longer an inline protocol, so later 2.x releases can change it; only the size ofWriteTransactionis pinned. Rebuild consumers built against earlier headers. -
API:
data_tamer_v2/data_tamer.hppincludeschannel.hppagain, as in 1.x, so one include givesChannelsRegistry,LogChannel,LoggedValueand the sink interface.data_tamer_v2/fwd.hppstays for headers that only name the types. -
API:
takeSnapshot()is no longer[[nodiscard]]:stats()counts every outcome, and most loops don't act on each call.tryTakeSnapshot()still is. -
API: no
LogChannel::droppedSnapshots(), which no release had: readstats().dropped_by_sink.LogChannel::sinkDropped()andChannelDefaults::resolve()(withChannelDefaults::Sizes) are private: they are the building blocks ofstats()andsetChannelDefaults(). Their symbols stay exported (the inlinestats()callssinkDropped()). -
Fixed, deadlocks:
unregister(),removeDataSink()or aLoggedValuedestructor insidescopedWrite()while a snapshot waited; a const query insidescopedWrite()while another thread ran one of those, orstartLogging();startLogging()insidescopedWrite(). The snapshot path takes the write mutex before its epoch, andstartLogging()before the control mutex. -
Behaviour change: a snapshot taken by a thread that holds the
channel's transaction or a
LoggedValueguard returnsblocked(it hung). -
New: several threads may take snapshots of one channel; they
take turns on the write mutex.
blockednow takes precedence overpool_exhausted. -
Fixed: a consumer built with
-fvisibility=hiddenagainst a shared libdata_tamer hung inLoggedValue::set()insidescopedWrite(); the transaction code is defined in the library only. -
Behaviour change:
SinkWorker::stop(),start()anddrain()throwstd::logic_errorfrom a callback of their own sink (they deadlocked, orstop()closed the worker silently). Concurrentstop()andstart(), twostopAll()included, are serialized (they hung). A callback that releases the last reference to its own worker no longer callsstd::terminate. -
Fixed: a sink attached during a failing
startLogging()could miss the final schema, and a concurrentaddDataSink()of one worker announced it twice. -
Real-time: no
notify_all()per snapshot or refused push unless a thread waits; each one could be a futex call. -
Behaviour change: names must be non-empty and free of whitespace
and control characters (only the space was refused);
IsCanonicalName()agrees. A ninth default sink throws inaddDefaultSink()(it made every latergetChannel()throw). -
Behaviour change: custom type names, their field names, the
typeName()of aregisterCustomValue()serializer and channel names are checked too: a line break in any of them split the schema text, and a space in a type or field name broke its field line. Type and field names follow the value name rules, and the registration
File truncated at 100 lines see the full file
Package Dependencies
| Deps | Name |
|---|---|
| ament_cmake | |
| rclcpp | |
| rclcpp_lifecycle | |
| mcap_vendor | |
| data_tamer_msgs | |
| ament_cmake_gtest | |
| gtest_vendor |
System Dependencies
| Name |
|---|
| lz4 |
| libzstd-dev |
Dependant Packages
| Name | Deps |
|---|---|
| plotjuggler |
Launch files
Messages
Services
Plugins
Recent questions tagged data_tamer_cpp at Robotics Stack Exchange
|
data_tamer_cpp package from data_tamer repodata_tamer_cpp data_tamer_msgs |
ROS Distro
|
Package Summary
| Version | 2.0.0 |
| License | MIT |
| Build type | AMENT_CMAKE |
| Use | RECOMMENDED |
Repository Summary
| Checkout URI | https://github.com/PickNikRobotics/data_tamer.git |
| VCS Type | git |
| VCS Version | main |
| Last Updated | 2026-10-18 |
| Dev Status | MAINTAINED |
| Released | RELEASED |
| Contributing |
Help Wanted (-)
Good First Issues (-) Pull Requests to Review (-) |
Package Description
Maintainers
- Davide Faconti
- Henry Moore
- Nathan Brooks
Authors
- Davide Faconti
Changelog for package data_tamer
Unreleased
-
Breaking, headers: the public headers move from
data_tamer/todata_tamer_v2/(#include "data_tamer_v2/channel.hpp"), and the standalone parser fromdata_tamer_parser/data_tamer_parser.hpptodata_tamer_v2/data_tamer_parser.hpp, so that 2.x installs side by side with 1.x, whose headers keep their paths. -
ABI:
ChannelSharedState, itsWriteMutexand the series flag words are library-private (src/): the headersdetails/shared_state.hpp,details/write_mutex.hppanddetails/spin_pause.hppare no longer installed, and consumers seeChannelSharedStateonly as an incomplete type.LoggedValuereaches its enabled flag through the exporteddetails::setSeriesEnabled()andisSeriesEnabled(), so the flag encoding and these layouts can change in a 2.x minor release.WriteTransactionis a class at namespace scope (it was the aliasChannelSharedState::Transaction), declared indetails/locked_reference.hppand still returned byscopedWrite(). Rebuild consumers built against earlier headers. -
Behaviour change, parser and Python decoder: a schema text in
the line format needs its
### version:line before the fields; without one both throw, naming the supported versions (4 and 5, 6 in YAML). The C++ parser read such a text as an upper-case "name TYPE" format that no release wrote, or as version 5, and the Python decoder as version 5. Texts of the releases before 0.7.0 (late 2023) fail with that message, among them the header-less<type> <name>lines of the 0.3 to 0.5 ROS 2 publisher, which both used to read (docs/wire_format.md, section 2). -
Fixed, Python decoder:
verify_hash=True(parse_schema(),SchemaRegistry,iter_mcap()) rejected every data_tamer 1.x file (schema version 4). Its hash came from the writer'sstd::hashand cannot be recomputed, so it is accepted as declared. The C++check_hashstill recomputes it, which agrees only with the writer's standard library (docs/wire_format.md, section 5). - Docs:
docs/MIGRATION.mdlists what code written for 1.x must change for 2.0, with the behaviour changes that compile silently. -
Real-time: the first access of the transaction state on a thread
no longer allocates when libdata_tamer is loaded with
dlopen()(a plugin, pluginlib, ros2_control), so ascopedWrite()on each real-time thread during setup is no longer needed. The library's one thread-local is initial-exec TLS (glibc):dlopen()takes one pointer of glibc's static TLS surplus. -
ABI: the
WriteTransactionconstructor and destructor (behindscopedWrite(), the guards and non-scalarLoggedValues) andChannelSharedState::inTransactionOnThisThread()are defined in the library, with the thread-local chain. The chain is no longer an inline protocol, so later 2.x releases can change it; only the size ofWriteTransactionis pinned. Rebuild consumers built against earlier headers. -
API:
data_tamer_v2/data_tamer.hppincludeschannel.hppagain, as in 1.x, so one include givesChannelsRegistry,LogChannel,LoggedValueand the sink interface.data_tamer_v2/fwd.hppstays for headers that only name the types. -
API:
takeSnapshot()is no longer[[nodiscard]]:stats()counts every outcome, and most loops don't act on each call.tryTakeSnapshot()still is. -
API: no
LogChannel::droppedSnapshots(), which no release had: readstats().dropped_by_sink.LogChannel::sinkDropped()andChannelDefaults::resolve()(withChannelDefaults::Sizes) are private: they are the building blocks ofstats()andsetChannelDefaults(). Their symbols stay exported (the inlinestats()callssinkDropped()). -
Fixed, deadlocks:
unregister(),removeDataSink()or aLoggedValuedestructor insidescopedWrite()while a snapshot waited; a const query insidescopedWrite()while another thread ran one of those, orstartLogging();startLogging()insidescopedWrite(). The snapshot path takes the write mutex before its epoch, andstartLogging()before the control mutex. -
Behaviour change: a snapshot taken by a thread that holds the
channel's transaction or a
LoggedValueguard returnsblocked(it hung). -
New: several threads may take snapshots of one channel; they
take turns on the write mutex.
blockednow takes precedence overpool_exhausted. -
Fixed: a consumer built with
-fvisibility=hiddenagainst a shared libdata_tamer hung inLoggedValue::set()insidescopedWrite(); the transaction code is defined in the library only. -
Behaviour change:
SinkWorker::stop(),start()anddrain()throwstd::logic_errorfrom a callback of their own sink (they deadlocked, orstop()closed the worker silently). Concurrentstop()andstart(), twostopAll()included, are serialized (they hung). A callback that releases the last reference to its own worker no longer callsstd::terminate. -
Fixed: a sink attached during a failing
startLogging()could miss the final schema, and a concurrentaddDataSink()of one worker announced it twice. -
Real-time: no
notify_all()per snapshot or refused push unless a thread waits; each one could be a futex call. -
Behaviour change: names must be non-empty and free of whitespace
and control characters (only the space was refused);
IsCanonicalName()agrees. A ninth default sink throws inaddDefaultSink()(it made every latergetChannel()throw). -
Behaviour change: custom type names, their field names, the
typeName()of aregisterCustomValue()serializer and channel names are checked too: a line break in any of them split the schema text, and a space in a type or field name broke its field line. Type and field names follow the value name rules, and the registration
File truncated at 100 lines see the full file
Package Dependencies
| Deps | Name |
|---|---|
| ament_cmake | |
| rclcpp | |
| rclcpp_lifecycle | |
| mcap_vendor | |
| data_tamer_msgs | |
| ament_cmake_gtest | |
| gtest_vendor |
System Dependencies
| Name |
|---|
| lz4 |
| libzstd-dev |
Dependant Packages
| Name | Deps |
|---|---|
| plotjuggler |
Launch files
Messages
Services
Plugins
Recent questions tagged data_tamer_cpp at Robotics Stack Exchange
|
data_tamer_cpp package from data_tamer repodata_tamer_cpp data_tamer_msgs |
ROS Distro
|
Package Summary
| Version | 2.0.0 |
| License | MIT |
| Build type | AMENT_CMAKE |
| Use | RECOMMENDED |
Repository Summary
| Checkout URI | https://github.com/PickNikRobotics/data_tamer.git |
| VCS Type | git |
| VCS Version | main |
| Last Updated | 2026-10-18 |
| Dev Status | MAINTAINED |
| Released | RELEASED |
| Contributing |
Help Wanted (-)
Good First Issues (-) Pull Requests to Review (-) |
Package Description
Maintainers
- Davide Faconti
- Henry Moore
- Nathan Brooks
Authors
- Davide Faconti
Changelog for package data_tamer
Unreleased
-
Breaking, headers: the public headers move from
data_tamer/todata_tamer_v2/(#include "data_tamer_v2/channel.hpp"), and the standalone parser fromdata_tamer_parser/data_tamer_parser.hpptodata_tamer_v2/data_tamer_parser.hpp, so that 2.x installs side by side with 1.x, whose headers keep their paths. -
ABI:
ChannelSharedState, itsWriteMutexand the series flag words are library-private (src/): the headersdetails/shared_state.hpp,details/write_mutex.hppanddetails/spin_pause.hppare no longer installed, and consumers seeChannelSharedStateonly as an incomplete type.LoggedValuereaches its enabled flag through the exporteddetails::setSeriesEnabled()andisSeriesEnabled(), so the flag encoding and these layouts can change in a 2.x minor release.WriteTransactionis a class at namespace scope (it was the aliasChannelSharedState::Transaction), declared indetails/locked_reference.hppand still returned byscopedWrite(). Rebuild consumers built against earlier headers. -
Behaviour change, parser and Python decoder: a schema text in
the line format needs its
### version:line before the fields; without one both throw, naming the supported versions (4 and 5, 6 in YAML). The C++ parser read such a text as an upper-case "name TYPE" format that no release wrote, or as version 5, and the Python decoder as version 5. Texts of the releases before 0.7.0 (late 2023) fail with that message, among them the header-less<type> <name>lines of the 0.3 to 0.5 ROS 2 publisher, which both used to read (docs/wire_format.md, section 2). -
Fixed, Python decoder:
verify_hash=True(parse_schema(),SchemaRegistry,iter_mcap()) rejected every data_tamer 1.x file (schema version 4). Its hash came from the writer'sstd::hashand cannot be recomputed, so it is accepted as declared. The C++check_hashstill recomputes it, which agrees only with the writer's standard library (docs/wire_format.md, section 5). - Docs:
docs/MIGRATION.mdlists what code written for 1.x must change for 2.0, with the behaviour changes that compile silently. -
Real-time: the first access of the transaction state on a thread
no longer allocates when libdata_tamer is loaded with
dlopen()(a plugin, pluginlib, ros2_control), so ascopedWrite()on each real-time thread during setup is no longer needed. The library's one thread-local is initial-exec TLS (glibc):dlopen()takes one pointer of glibc's static TLS surplus. -
ABI: the
WriteTransactionconstructor and destructor (behindscopedWrite(), the guards and non-scalarLoggedValues) andChannelSharedState::inTransactionOnThisThread()are defined in the library, with the thread-local chain. The chain is no longer an inline protocol, so later 2.x releases can change it; only the size ofWriteTransactionis pinned. Rebuild consumers built against earlier headers. -
API:
data_tamer_v2/data_tamer.hppincludeschannel.hppagain, as in 1.x, so one include givesChannelsRegistry,LogChannel,LoggedValueand the sink interface.data_tamer_v2/fwd.hppstays for headers that only name the types. -
API:
takeSnapshot()is no longer[[nodiscard]]:stats()counts every outcome, and most loops don't act on each call.tryTakeSnapshot()still is. -
API: no
LogChannel::droppedSnapshots(), which no release had: readstats().dropped_by_sink.LogChannel::sinkDropped()andChannelDefaults::resolve()(withChannelDefaults::Sizes) are private: they are the building blocks ofstats()andsetChannelDefaults(). Their symbols stay exported (the inlinestats()callssinkDropped()). -
Fixed, deadlocks:
unregister(),removeDataSink()or aLoggedValuedestructor insidescopedWrite()while a snapshot waited; a const query insidescopedWrite()while another thread ran one of those, orstartLogging();startLogging()insidescopedWrite(). The snapshot path takes the write mutex before its epoch, andstartLogging()before the control mutex. -
Behaviour change: a snapshot taken by a thread that holds the
channel's transaction or a
LoggedValueguard returnsblocked(it hung). -
New: several threads may take snapshots of one channel; they
take turns on the write mutex.
blockednow takes precedence overpool_exhausted. -
Fixed: a consumer built with
-fvisibility=hiddenagainst a shared libdata_tamer hung inLoggedValue::set()insidescopedWrite(); the transaction code is defined in the library only. -
Behaviour change:
SinkWorker::stop(),start()anddrain()throwstd::logic_errorfrom a callback of their own sink (they deadlocked, orstop()closed the worker silently). Concurrentstop()andstart(), twostopAll()included, are serialized (they hung). A callback that releases the last reference to its own worker no longer callsstd::terminate. -
Fixed: a sink attached during a failing
startLogging()could miss the final schema, and a concurrentaddDataSink()of one worker announced it twice. -
Real-time: no
notify_all()per snapshot or refused push unless a thread waits; each one could be a futex call. -
Behaviour change: names must be non-empty and free of whitespace
and control characters (only the space was refused);
IsCanonicalName()agrees. A ninth default sink throws inaddDefaultSink()(it made every latergetChannel()throw). -
Behaviour change: custom type names, their field names, the
typeName()of aregisterCustomValue()serializer and channel names are checked too: a line break in any of them split the schema text, and a space in a type or field name broke its field line. Type and field names follow the value name rules, and the registration
File truncated at 100 lines see the full file
Package Dependencies
| Deps | Name |
|---|---|
| ament_cmake | |
| rclcpp | |
| rclcpp_lifecycle | |
| mcap_vendor | |
| data_tamer_msgs | |
| ament_cmake_gtest | |
| gtest_vendor |
System Dependencies
| Name |
|---|
| lz4 |
| libzstd-dev |
Dependant Packages
| Name | Deps |
|---|---|
| plotjuggler |
Launch files
Messages
Services
Plugins
Recent questions tagged data_tamer_cpp at Robotics Stack Exchange
|
data_tamer_cpp package from data_tamer repodata_tamer_cpp data_tamer_msgs |
ROS Distro
|
Package Summary
| Version | 2.0.0 |
| License | MIT |
| Build type | AMENT_CMAKE |
| Use | RECOMMENDED |
Repository Summary
| Checkout URI | https://github.com/PickNikRobotics/data_tamer.git |
| VCS Type | git |
| VCS Version | main |
| Last Updated | 2026-10-18 |
| Dev Status | MAINTAINED |
| Released | RELEASED |
| Contributing |
Help Wanted (-)
Good First Issues (-) Pull Requests to Review (-) |
Package Description
Maintainers
- Davide Faconti
- Henry Moore
- Nathan Brooks
Authors
- Davide Faconti
Changelog for package data_tamer
Unreleased
-
Breaking, headers: the public headers move from
data_tamer/todata_tamer_v2/(#include "data_tamer_v2/channel.hpp"), and the standalone parser fromdata_tamer_parser/data_tamer_parser.hpptodata_tamer_v2/data_tamer_parser.hpp, so that 2.x installs side by side with 1.x, whose headers keep their paths. -
ABI:
ChannelSharedState, itsWriteMutexand the series flag words are library-private (src/): the headersdetails/shared_state.hpp,details/write_mutex.hppanddetails/spin_pause.hppare no longer installed, and consumers seeChannelSharedStateonly as an incomplete type.LoggedValuereaches its enabled flag through the exporteddetails::setSeriesEnabled()andisSeriesEnabled(), so the flag encoding and these layouts can change in a 2.x minor release.WriteTransactionis a class at namespace scope (it was the aliasChannelSharedState::Transaction), declared indetails/locked_reference.hppand still returned byscopedWrite(). Rebuild consumers built against earlier headers. -
Behaviour change, parser and Python decoder: a schema text in
the line format needs its
### version:line before the fields; without one both throw, naming the supported versions (4 and 5, 6 in YAML). The C++ parser read such a text as an upper-case "name TYPE" format that no release wrote, or as version 5, and the Python decoder as version 5. Texts of the releases before 0.7.0 (late 2023) fail with that message, among them the header-less<type> <name>lines of the 0.3 to 0.5 ROS 2 publisher, which both used to read (docs/wire_format.md, section 2). -
Fixed, Python decoder:
verify_hash=True(parse_schema(),SchemaRegistry,iter_mcap()) rejected every data_tamer 1.x file (schema version 4). Its hash came from the writer'sstd::hashand cannot be recomputed, so it is accepted as declared. The C++check_hashstill recomputes it, which agrees only with the writer's standard library (docs/wire_format.md, section 5). - Docs:
docs/MIGRATION.mdlists what code written for 1.x must change for 2.0, with the behaviour changes that compile silently. -
Real-time: the first access of the transaction state on a thread
no longer allocates when libdata_tamer is loaded with
dlopen()(a plugin, pluginlib, ros2_control), so ascopedWrite()on each real-time thread during setup is no longer needed. The library's one thread-local is initial-exec TLS (glibc):dlopen()takes one pointer of glibc's static TLS surplus. -
ABI: the
WriteTransactionconstructor and destructor (behindscopedWrite(), the guards and non-scalarLoggedValues) andChannelSharedState::inTransactionOnThisThread()are defined in the library, with the thread-local chain. The chain is no longer an inline protocol, so later 2.x releases can change it; only the size ofWriteTransactionis pinned. Rebuild consumers built against earlier headers. -
API:
data_tamer_v2/data_tamer.hppincludeschannel.hppagain, as in 1.x, so one include givesChannelsRegistry,LogChannel,LoggedValueand the sink interface.data_tamer_v2/fwd.hppstays for headers that only name the types. -
API:
takeSnapshot()is no longer[[nodiscard]]:stats()counts every outcome, and most loops don't act on each call.tryTakeSnapshot()still is. -
API: no
LogChannel::droppedSnapshots(), which no release had: readstats().dropped_by_sink.LogChannel::sinkDropped()andChannelDefaults::resolve()(withChannelDefaults::Sizes) are private: they are the building blocks ofstats()andsetChannelDefaults(). Their symbols stay exported (the inlinestats()callssinkDropped()). -
Fixed, deadlocks:
unregister(),removeDataSink()or aLoggedValuedestructor insidescopedWrite()while a snapshot waited; a const query insidescopedWrite()while another thread ran one of those, orstartLogging();startLogging()insidescopedWrite(). The snapshot path takes the write mutex before its epoch, andstartLogging()before the control mutex. -
Behaviour change: a snapshot taken by a thread that holds the
channel's transaction or a
LoggedValueguard returnsblocked(it hung). -
New: several threads may take snapshots of one channel; they
take turns on the write mutex.
blockednow takes precedence overpool_exhausted. -
Fixed: a consumer built with
-fvisibility=hiddenagainst a shared libdata_tamer hung inLoggedValue::set()insidescopedWrite(); the transaction code is defined in the library only. -
Behaviour change:
SinkWorker::stop(),start()anddrain()throwstd::logic_errorfrom a callback of their own sink (they deadlocked, orstop()closed the worker silently). Concurrentstop()andstart(), twostopAll()included, are serialized (they hung). A callback that releases the last reference to its own worker no longer callsstd::terminate. -
Fixed: a sink attached during a failing
startLogging()could miss the final schema, and a concurrentaddDataSink()of one worker announced it twice. -
Real-time: no
notify_all()per snapshot or refused push unless a thread waits; each one could be a futex call. -
Behaviour change: names must be non-empty and free of whitespace
and control characters (only the space was refused);
IsCanonicalName()agrees. A ninth default sink throws inaddDefaultSink()(it made every latergetChannel()throw). -
Behaviour change: custom type names, their field names, the
typeName()of aregisterCustomValue()serializer and channel names are checked too: a line break in any of them split the schema text, and a space in a type or field name broke its field line. Type and field names follow the value name rules, and the registration
File truncated at 100 lines see the full file
Package Dependencies
| Deps | Name |
|---|---|
| ament_cmake | |
| rclcpp | |
| rclcpp_lifecycle | |
| mcap_vendor | |
| data_tamer_msgs | |
| ament_cmake_gtest | |
| gtest_vendor |
System Dependencies
| Name |
|---|
| lz4 |
| libzstd-dev |
Dependant Packages
| Name | Deps |
|---|---|
| plotjuggler |
Launch files
Messages
Services
Plugins
Recent questions tagged data_tamer_cpp at Robotics Stack Exchange
|
data_tamer_cpp package from data_tamer repodata_tamer_cpp data_tamer_msgs |
ROS Distro
|
Package Summary
| Version | 2.0.0 |
| License | MIT |
| Build type | AMENT_CMAKE |
| Use | RECOMMENDED |
Repository Summary
| Checkout URI | https://github.com/PickNikRobotics/data_tamer.git |
| VCS Type | git |
| VCS Version | main |
| Last Updated | 2026-10-18 |
| Dev Status | MAINTAINED |
| Released | RELEASED |
| Contributing |
Help Wanted (-)
Good First Issues (-) Pull Requests to Review (-) |
Package Description
Maintainers
- Davide Faconti
- Henry Moore
- Nathan Brooks
Authors
- Davide Faconti
Changelog for package data_tamer
Unreleased
-
Breaking, headers: the public headers move from
data_tamer/todata_tamer_v2/(#include "data_tamer_v2/channel.hpp"), and the standalone parser fromdata_tamer_parser/data_tamer_parser.hpptodata_tamer_v2/data_tamer_parser.hpp, so that 2.x installs side by side with 1.x, whose headers keep their paths. -
ABI:
ChannelSharedState, itsWriteMutexand the series flag words are library-private (src/): the headersdetails/shared_state.hpp,details/write_mutex.hppanddetails/spin_pause.hppare no longer installed, and consumers seeChannelSharedStateonly as an incomplete type.LoggedValuereaches its enabled flag through the exporteddetails::setSeriesEnabled()andisSeriesEnabled(), so the flag encoding and these layouts can change in a 2.x minor release.WriteTransactionis a class at namespace scope (it was the aliasChannelSharedState::Transaction), declared indetails/locked_reference.hppand still returned byscopedWrite(). Rebuild consumers built against earlier headers. -
Behaviour change, parser and Python decoder: a schema text in
the line format needs its
### version:line before the fields; without one both throw, naming the supported versions (4 and 5, 6 in YAML). The C++ parser read such a text as an upper-case "name TYPE" format that no release wrote, or as version 5, and the Python decoder as version 5. Texts of the releases before 0.7.0 (late 2023) fail with that message, among them the header-less<type> <name>lines of the 0.3 to 0.5 ROS 2 publisher, which both used to read (docs/wire_format.md, section 2). -
Fixed, Python decoder:
verify_hash=True(parse_schema(),SchemaRegistry,iter_mcap()) rejected every data_tamer 1.x file (schema version 4). Its hash came from the writer'sstd::hashand cannot be recomputed, so it is accepted as declared. The C++check_hashstill recomputes it, which agrees only with the writer's standard library (docs/wire_format.md, section 5). - Docs:
docs/MIGRATION.mdlists what code written for 1.x must change for 2.0, with the behaviour changes that compile silently. -
Real-time: the first access of the transaction state on a thread
no longer allocates when libdata_tamer is loaded with
dlopen()(a plugin, pluginlib, ros2_control), so ascopedWrite()on each real-time thread during setup is no longer needed. The library's one thread-local is initial-exec TLS (glibc):dlopen()takes one pointer of glibc's static TLS surplus. -
ABI: the
WriteTransactionconstructor and destructor (behindscopedWrite(), the guards and non-scalarLoggedValues) andChannelSharedState::inTransactionOnThisThread()are defined in the library, with the thread-local chain. The chain is no longer an inline protocol, so later 2.x releases can change it; only the size ofWriteTransactionis pinned. Rebuild consumers built against earlier headers. -
API:
data_tamer_v2/data_tamer.hppincludeschannel.hppagain, as in 1.x, so one include givesChannelsRegistry,LogChannel,LoggedValueand the sink interface.data_tamer_v2/fwd.hppstays for headers that only name the types. -
API:
takeSnapshot()is no longer[[nodiscard]]:stats()counts every outcome, and most loops don't act on each call.tryTakeSnapshot()still is. -
API: no
LogChannel::droppedSnapshots(), which no release had: readstats().dropped_by_sink.LogChannel::sinkDropped()andChannelDefaults::resolve()(withChannelDefaults::Sizes) are private: they are the building blocks ofstats()andsetChannelDefaults(). Their symbols stay exported (the inlinestats()callssinkDropped()). -
Fixed, deadlocks:
unregister(),removeDataSink()or aLoggedValuedestructor insidescopedWrite()while a snapshot waited; a const query insidescopedWrite()while another thread ran one of those, orstartLogging();startLogging()insidescopedWrite(). The snapshot path takes the write mutex before its epoch, andstartLogging()before the control mutex. -
Behaviour change: a snapshot taken by a thread that holds the
channel's transaction or a
LoggedValueguard returnsblocked(it hung). -
New: several threads may take snapshots of one channel; they
take turns on the write mutex.
blockednow takes precedence overpool_exhausted. -
Fixed: a consumer built with
-fvisibility=hiddenagainst a shared libdata_tamer hung inLoggedValue::set()insidescopedWrite(); the transaction code is defined in the library only. -
Behaviour change:
SinkWorker::stop(),start()anddrain()throwstd::logic_errorfrom a callback of their own sink (they deadlocked, orstop()closed the worker silently). Concurrentstop()andstart(), twostopAll()included, are serialized (they hung). A callback that releases the last reference to its own worker no longer callsstd::terminate. -
Fixed: a sink attached during a failing
startLogging()could miss the final schema, and a concurrentaddDataSink()of one worker announced it twice. -
Real-time: no
notify_all()per snapshot or refused push unless a thread waits; each one could be a futex call. -
Behaviour change: names must be non-empty and free of whitespace
and control characters (only the space was refused);
IsCanonicalName()agrees. A ninth default sink throws inaddDefaultSink()(it made every latergetChannel()throw). -
Behaviour change: custom type names, their field names, the
typeName()of aregisterCustomValue()serializer and channel names are checked too: a line break in any of them split the schema text, and a space in a type or field name broke its field line. Type and field names follow the value name rules, and the registration
File truncated at 100 lines see the full file
Package Dependencies
| Deps | Name |
|---|---|
| ament_cmake | |
| rclcpp | |
| rclcpp_lifecycle | |
| mcap_vendor | |
| data_tamer_msgs | |
| ament_cmake_gtest | |
| gtest_vendor |
System Dependencies
| Name |
|---|
| lz4 |
| libzstd-dev |
Dependant Packages
| Name | Deps |
|---|---|
| plotjuggler |
Launch files
Messages
Services
Plugins
Recent questions tagged data_tamer_cpp at Robotics Stack Exchange
|
data_tamer_cpp package from data_tamer repodata_tamer_cpp data_tamer_msgs |
ROS Distro
|
Package Summary
| Version | 2.0.0 |
| License | MIT |
| Build type | AMENT_CMAKE |
| Use | RECOMMENDED |
Repository Summary
| Checkout URI | https://github.com/PickNikRobotics/data_tamer.git |
| VCS Type | git |
| VCS Version | main |
| Last Updated | 2026-10-18 |
| Dev Status | MAINTAINED |
| Released | RELEASED |
| Contributing |
Help Wanted (-)
Good First Issues (-) Pull Requests to Review (-) |
Package Description
Maintainers
- Davide Faconti
- Henry Moore
- Nathan Brooks
Authors
- Davide Faconti
Changelog for package data_tamer
Unreleased
-
Breaking, headers: the public headers move from
data_tamer/todata_tamer_v2/(#include "data_tamer_v2/channel.hpp"), and the standalone parser fromdata_tamer_parser/data_tamer_parser.hpptodata_tamer_v2/data_tamer_parser.hpp, so that 2.x installs side by side with 1.x, whose headers keep their paths. -
ABI:
ChannelSharedState, itsWriteMutexand the series flag words are library-private (src/): the headersdetails/shared_state.hpp,details/write_mutex.hppanddetails/spin_pause.hppare no longer installed, and consumers seeChannelSharedStateonly as an incomplete type.LoggedValuereaches its enabled flag through the exporteddetails::setSeriesEnabled()andisSeriesEnabled(), so the flag encoding and these layouts can change in a 2.x minor release.WriteTransactionis a class at namespace scope (it was the aliasChannelSharedState::Transaction), declared indetails/locked_reference.hppand still returned byscopedWrite(). Rebuild consumers built against earlier headers. -
Behaviour change, parser and Python decoder: a schema text in
the line format needs its
### version:line before the fields; without one both throw, naming the supported versions (4 and 5, 6 in YAML). The C++ parser read such a text as an upper-case "name TYPE" format that no release wrote, or as version 5, and the Python decoder as version 5. Texts of the releases before 0.7.0 (late 2023) fail with that message, among them the header-less<type> <name>lines of the 0.3 to 0.5 ROS 2 publisher, which both used to read (docs/wire_format.md, section 2). -
Fixed, Python decoder:
verify_hash=True(parse_schema(),SchemaRegistry,iter_mcap()) rejected every data_tamer 1.x file (schema version 4). Its hash came from the writer'sstd::hashand cannot be recomputed, so it is accepted as declared. The C++check_hashstill recomputes it, which agrees only with the writer's standard library (docs/wire_format.md, section 5). - Docs:
docs/MIGRATION.mdlists what code written for 1.x must change for 2.0, with the behaviour changes that compile silently. -
Real-time: the first access of the transaction state on a thread
no longer allocates when libdata_tamer is loaded with
dlopen()(a plugin, pluginlib, ros2_control), so ascopedWrite()on each real-time thread during setup is no longer needed. The library's one thread-local is initial-exec TLS (glibc):dlopen()takes one pointer of glibc's static TLS surplus. -
ABI: the
WriteTransactionconstructor and destructor (behindscopedWrite(), the guards and non-scalarLoggedValues) andChannelSharedState::inTransactionOnThisThread()are defined in the library, with the thread-local chain. The chain is no longer an inline protocol, so later 2.x releases can change it; only the size ofWriteTransactionis pinned. Rebuild consumers built against earlier headers. -
API:
data_tamer_v2/data_tamer.hppincludeschannel.hppagain, as in 1.x, so one include givesChannelsRegistry,LogChannel,LoggedValueand the sink interface.data_tamer_v2/fwd.hppstays for headers that only name the types. -
API:
takeSnapshot()is no longer[[nodiscard]]:stats()counts every outcome, and most loops don't act on each call.tryTakeSnapshot()still is. -
API: no
LogChannel::droppedSnapshots(), which no release had: readstats().dropped_by_sink.LogChannel::sinkDropped()andChannelDefaults::resolve()(withChannelDefaults::Sizes) are private: they are the building blocks ofstats()andsetChannelDefaults(). Their symbols stay exported (the inlinestats()callssinkDropped()). -
Fixed, deadlocks:
unregister(),removeDataSink()or aLoggedValuedestructor insidescopedWrite()while a snapshot waited; a const query insidescopedWrite()while another thread ran one of those, orstartLogging();startLogging()insidescopedWrite(). The snapshot path takes the write mutex before its epoch, andstartLogging()before the control mutex. -
Behaviour change: a snapshot taken by a thread that holds the
channel's transaction or a
LoggedValueguard returnsblocked(it hung). -
New: several threads may take snapshots of one channel; they
take turns on the write mutex.
blockednow takes precedence overpool_exhausted. -
Fixed: a consumer built with
-fvisibility=hiddenagainst a shared libdata_tamer hung inLoggedValue::set()insidescopedWrite(); the transaction code is defined in the library only. -
Behaviour change:
SinkWorker::stop(),start()anddrain()throwstd::logic_errorfrom a callback of their own sink (they deadlocked, orstop()closed the worker silently). Concurrentstop()andstart(), twostopAll()included, are serialized (they hung). A callback that releases the last reference to its own worker no longer callsstd::terminate. -
Fixed: a sink attached during a failing
startLogging()could miss the final schema, and a concurrentaddDataSink()of one worker announced it twice. -
Real-time: no
notify_all()per snapshot or refused push unless a thread waits; each one could be a futex call. -
Behaviour change: names must be non-empty and free of whitespace
and control characters (only the space was refused);
IsCanonicalName()agrees. A ninth default sink throws inaddDefaultSink()(it made every latergetChannel()throw). -
Behaviour change: custom type names, their field names, the
typeName()of aregisterCustomValue()serializer and channel names are checked too: a line break in any of them split the schema text, and a space in a type or field name broke its field line. Type and field names follow the value name rules, and the registration
File truncated at 100 lines see the full file
Package Dependencies
| Deps | Name |
|---|---|
| ament_cmake | |
| rclcpp | |
| rclcpp_lifecycle | |
| mcap_vendor | |
| data_tamer_msgs | |
| ament_cmake_gtest | |
| gtest_vendor |
System Dependencies
| Name |
|---|
| lz4 |
| libzstd-dev |
Dependant Packages
| Name | Deps |
|---|---|
| plotjuggler |
Launch files
Messages
Services
Plugins
Recent questions tagged data_tamer_cpp at Robotics Stack Exchange
|
data_tamer_cpp package from data_tamer repodata_tamer_cpp data_tamer_msgs |
ROS Distro
|
Package Summary
| Version | 2.0.0 |
| License | MIT |
| Build type | AMENT_CMAKE |
| Use | RECOMMENDED |
Repository Summary
| Checkout URI | https://github.com/PickNikRobotics/data_tamer.git |
| VCS Type | git |
| VCS Version | main |
| Last Updated | 2026-10-18 |
| Dev Status | MAINTAINED |
| Released | RELEASED |
| Contributing |
Help Wanted (-)
Good First Issues (-) Pull Requests to Review (-) |
Package Description
Maintainers
- Davide Faconti
- Henry Moore
- Nathan Brooks
Authors
- Davide Faconti
Changelog for package data_tamer
Unreleased
-
Breaking, headers: the public headers move from
data_tamer/todata_tamer_v2/(#include "data_tamer_v2/channel.hpp"), and the standalone parser fromdata_tamer_parser/data_tamer_parser.hpptodata_tamer_v2/data_tamer_parser.hpp, so that 2.x installs side by side with 1.x, whose headers keep their paths. -
ABI:
ChannelSharedState, itsWriteMutexand the series flag words are library-private (src/): the headersdetails/shared_state.hpp,details/write_mutex.hppanddetails/spin_pause.hppare no longer installed, and consumers seeChannelSharedStateonly as an incomplete type.LoggedValuereaches its enabled flag through the exporteddetails::setSeriesEnabled()andisSeriesEnabled(), so the flag encoding and these layouts can change in a 2.x minor release.WriteTransactionis a class at namespace scope (it was the aliasChannelSharedState::Transaction), declared indetails/locked_reference.hppand still returned byscopedWrite(). Rebuild consumers built against earlier headers. -
Behaviour change, parser and Python decoder: a schema text in
the line format needs its
### version:line before the fields; without one both throw, naming the supported versions (4 and 5, 6 in YAML). The C++ parser read such a text as an upper-case "name TYPE" format that no release wrote, or as version 5, and the Python decoder as version 5. Texts of the releases before 0.7.0 (late 2023) fail with that message, among them the header-less<type> <name>lines of the 0.3 to 0.5 ROS 2 publisher, which both used to read (docs/wire_format.md, section 2). -
Fixed, Python decoder:
verify_hash=True(parse_schema(),SchemaRegistry,iter_mcap()) rejected every data_tamer 1.x file (schema version 4). Its hash came from the writer'sstd::hashand cannot be recomputed, so it is accepted as declared. The C++check_hashstill recomputes it, which agrees only with the writer's standard library (docs/wire_format.md, section 5). - Docs:
docs/MIGRATION.mdlists what code written for 1.x must change for 2.0, with the behaviour changes that compile silently. -
Real-time: the first access of the transaction state on a thread
no longer allocates when libdata_tamer is loaded with
dlopen()(a plugin, pluginlib, ros2_control), so ascopedWrite()on each real-time thread during setup is no longer needed. The library's one thread-local is initial-exec TLS (glibc):dlopen()takes one pointer of glibc's static TLS surplus. -
ABI: the
WriteTransactionconstructor and destructor (behindscopedWrite(), the guards and non-scalarLoggedValues) andChannelSharedState::inTransactionOnThisThread()are defined in the library, with the thread-local chain. The chain is no longer an inline protocol, so later 2.x releases can change it; only the size ofWriteTransactionis pinned. Rebuild consumers built against earlier headers. -
API:
data_tamer_v2/data_tamer.hppincludeschannel.hppagain, as in 1.x, so one include givesChannelsRegistry,LogChannel,LoggedValueand the sink interface.data_tamer_v2/fwd.hppstays for headers that only name the types. -
API:
takeSnapshot()is no longer[[nodiscard]]:stats()counts every outcome, and most loops don't act on each call.tryTakeSnapshot()still is. -
API: no
LogChannel::droppedSnapshots(), which no release had: readstats().dropped_by_sink.LogChannel::sinkDropped()andChannelDefaults::resolve()(withChannelDefaults::Sizes) are private: they are the building blocks ofstats()andsetChannelDefaults(). Their symbols stay exported (the inlinestats()callssinkDropped()). -
Fixed, deadlocks:
unregister(),removeDataSink()or aLoggedValuedestructor insidescopedWrite()while a snapshot waited; a const query insidescopedWrite()while another thread ran one of those, orstartLogging();startLogging()insidescopedWrite(). The snapshot path takes the write mutex before its epoch, andstartLogging()before the control mutex. -
Behaviour change: a snapshot taken by a thread that holds the
channel's transaction or a
LoggedValueguard returnsblocked(it hung). -
New: several threads may take snapshots of one channel; they
take turns on the write mutex.
blockednow takes precedence overpool_exhausted. -
Fixed: a consumer built with
-fvisibility=hiddenagainst a shared libdata_tamer hung inLoggedValue::set()insidescopedWrite(); the transaction code is defined in the library only. -
Behaviour change:
SinkWorker::stop(),start()anddrain()throwstd::logic_errorfrom a callback of their own sink (they deadlocked, orstop()closed the worker silently). Concurrentstop()andstart(), twostopAll()included, are serialized (they hung). A callback that releases the last reference to its own worker no longer callsstd::terminate. -
Fixed: a sink attached during a failing
startLogging()could miss the final schema, and a concurrentaddDataSink()of one worker announced it twice. -
Real-time: no
notify_all()per snapshot or refused push unless a thread waits; each one could be a futex call. -
Behaviour change: names must be non-empty and free of whitespace
and control characters (only the space was refused);
IsCanonicalName()agrees. A ninth default sink throws inaddDefaultSink()(it made every latergetChannel()throw). -
Behaviour change: custom type names, their field names, the
typeName()of aregisterCustomValue()serializer and channel names are checked too: a line break in any of them split the schema text, and a space in a type or field name broke its field line. Type and field names follow the value name rules, and the registration
File truncated at 100 lines see the full file
Package Dependencies
| Deps | Name |
|---|---|
| ament_cmake | |
| rclcpp | |
| rclcpp_lifecycle | |
| mcap_vendor | |
| data_tamer_msgs | |
| ament_cmake_gtest | |
| gtest_vendor |
System Dependencies
| Name |
|---|
| lz4 |
| libzstd-dev |
Dependant Packages
| Name | Deps |
|---|---|
| plotjuggler |
Launch files
Messages
Services
Plugins
Recent questions tagged data_tamer_cpp at Robotics Stack Exchange
|
data_tamer_cpp package from data_tamer repodata_tamer_cpp data_tamer_msgs |
ROS Distro
|
Package Summary
| Version | 2.0.0 |
| License | MIT |
| Build type | AMENT_CMAKE |
| Use | RECOMMENDED |
Repository Summary
| Checkout URI | https://github.com/PickNikRobotics/data_tamer.git |
| VCS Type | git |
| VCS Version | main |
| Last Updated | 2026-10-18 |
| Dev Status | MAINTAINED |
| Released | RELEASED |
| Contributing |
Help Wanted (-)
Good First Issues (-) Pull Requests to Review (-) |
Package Description
Maintainers
- Davide Faconti
- Henry Moore
- Nathan Brooks
Authors
- Davide Faconti
Changelog for package data_tamer
Unreleased
-
Breaking, headers: the public headers move from
data_tamer/todata_tamer_v2/(#include "data_tamer_v2/channel.hpp"), and the standalone parser fromdata_tamer_parser/data_tamer_parser.hpptodata_tamer_v2/data_tamer_parser.hpp, so that 2.x installs side by side with 1.x, whose headers keep their paths. -
ABI:
ChannelSharedState, itsWriteMutexand the series flag words are library-private (src/): the headersdetails/shared_state.hpp,details/write_mutex.hppanddetails/spin_pause.hppare no longer installed, and consumers seeChannelSharedStateonly as an incomplete type.LoggedValuereaches its enabled flag through the exporteddetails::setSeriesEnabled()andisSeriesEnabled(), so the flag encoding and these layouts can change in a 2.x minor release.WriteTransactionis a class at namespace scope (it was the aliasChannelSharedState::Transaction), declared indetails/locked_reference.hppand still returned byscopedWrite(). Rebuild consumers built against earlier headers. -
Behaviour change, parser and Python decoder: a schema text in
the line format needs its
### version:line before the fields; without one both throw, naming the supported versions (4 and 5, 6 in YAML). The C++ parser read such a text as an upper-case "name TYPE" format that no release wrote, or as version 5, and the Python decoder as version 5. Texts of the releases before 0.7.0 (late 2023) fail with that message, among them the header-less<type> <name>lines of the 0.3 to 0.5 ROS 2 publisher, which both used to read (docs/wire_format.md, section 2). -
Fixed, Python decoder:
verify_hash=True(parse_schema(),SchemaRegistry,iter_mcap()) rejected every data_tamer 1.x file (schema version 4). Its hash came from the writer'sstd::hashand cannot be recomputed, so it is accepted as declared. The C++check_hashstill recomputes it, which agrees only with the writer's standard library (docs/wire_format.md, section 5). - Docs:
docs/MIGRATION.mdlists what code written for 1.x must change for 2.0, with the behaviour changes that compile silently. -
Real-time: the first access of the transaction state on a thread
no longer allocates when libdata_tamer is loaded with
dlopen()(a plugin, pluginlib, ros2_control), so ascopedWrite()on each real-time thread during setup is no longer needed. The library's one thread-local is initial-exec TLS (glibc):dlopen()takes one pointer of glibc's static TLS surplus. -
ABI: the
WriteTransactionconstructor and destructor (behindscopedWrite(), the guards and non-scalarLoggedValues) andChannelSharedState::inTransactionOnThisThread()are defined in the library, with the thread-local chain. The chain is no longer an inline protocol, so later 2.x releases can change it; only the size ofWriteTransactionis pinned. Rebuild consumers built against earlier headers. -
API:
data_tamer_v2/data_tamer.hppincludeschannel.hppagain, as in 1.x, so one include givesChannelsRegistry,LogChannel,LoggedValueand the sink interface.data_tamer_v2/fwd.hppstays for headers that only name the types. -
API:
takeSnapshot()is no longer[[nodiscard]]:stats()counts every outcome, and most loops don't act on each call.tryTakeSnapshot()still is. -
API: no
LogChannel::droppedSnapshots(), which no release had: readstats().dropped_by_sink.LogChannel::sinkDropped()andChannelDefaults::resolve()(withChannelDefaults::Sizes) are private: they are the building blocks ofstats()andsetChannelDefaults(). Their symbols stay exported (the inlinestats()callssinkDropped()). -
Fixed, deadlocks:
unregister(),removeDataSink()or aLoggedValuedestructor insidescopedWrite()while a snapshot waited; a const query insidescopedWrite()while another thread ran one of those, orstartLogging();startLogging()insidescopedWrite(). The snapshot path takes the write mutex before its epoch, andstartLogging()before the control mutex. -
Behaviour change: a snapshot taken by a thread that holds the
channel's transaction or a
LoggedValueguard returnsblocked(it hung). -
New: several threads may take snapshots of one channel; they
take turns on the write mutex.
blockednow takes precedence overpool_exhausted. -
Fixed: a consumer built with
-fvisibility=hiddenagainst a shared libdata_tamer hung inLoggedValue::set()insidescopedWrite(); the transaction code is defined in the library only. -
Behaviour change:
SinkWorker::stop(),start()anddrain()throwstd::logic_errorfrom a callback of their own sink (they deadlocked, orstop()closed the worker silently). Concurrentstop()andstart(), twostopAll()included, are serialized (they hung). A callback that releases the last reference to its own worker no longer callsstd::terminate. -
Fixed: a sink attached during a failing
startLogging()could miss the final schema, and a concurrentaddDataSink()of one worker announced it twice. -
Real-time: no
notify_all()per snapshot or refused push unless a thread waits; each one could be a futex call. -
Behaviour change: names must be non-empty and free of whitespace
and control characters (only the space was refused);
IsCanonicalName()agrees. A ninth default sink throws inaddDefaultSink()(it made every latergetChannel()throw). -
Behaviour change: custom type names, their field names, the
typeName()of aregisterCustomValue()serializer and channel names are checked too: a line break in any of them split the schema text, and a space in a type or field name broke its field line. Type and field names follow the value name rules, and the registration
File truncated at 100 lines see the full file
Package Dependencies
| Deps | Name |
|---|---|
| ament_cmake | |
| rclcpp | |
| rclcpp_lifecycle | |
| mcap_vendor | |
| data_tamer_msgs | |
| ament_cmake_gtest | |
| gtest_vendor |
System Dependencies
| Name |
|---|
| lz4 |
| libzstd-dev |
Dependant Packages
| Name | Deps |
|---|---|
| plotjuggler |
Launch files
Messages
Services
Plugins
Recent questions tagged data_tamer_cpp at Robotics Stack Exchange
|
data_tamer_cpp package from data_tamer repodata_tamer_cpp data_tamer_msgs |
ROS Distro
|
Package Summary
| Version | 2.0.0 |
| License | MIT |
| Build type | AMENT_CMAKE |
| Use | RECOMMENDED |
Repository Summary
| Checkout URI | https://github.com/PickNikRobotics/data_tamer.git |
| VCS Type | git |
| VCS Version | main |
| Last Updated | 2026-10-18 |
| Dev Status | MAINTAINED |
| Released | RELEASED |
| Contributing |
Help Wanted (-)
Good First Issues (-) Pull Requests to Review (-) |
Package Description
Maintainers
- Davide Faconti
- Henry Moore
- Nathan Brooks
Authors
- Davide Faconti
Changelog for package data_tamer
Unreleased
-
Breaking, headers: the public headers move from
data_tamer/todata_tamer_v2/(#include "data_tamer_v2/channel.hpp"), and the standalone parser fromdata_tamer_parser/data_tamer_parser.hpptodata_tamer_v2/data_tamer_parser.hpp, so that 2.x installs side by side with 1.x, whose headers keep their paths. -
ABI:
ChannelSharedState, itsWriteMutexand the series flag words are library-private (src/): the headersdetails/shared_state.hpp,details/write_mutex.hppanddetails/spin_pause.hppare no longer installed, and consumers seeChannelSharedStateonly as an incomplete type.LoggedValuereaches its enabled flag through the exporteddetails::setSeriesEnabled()andisSeriesEnabled(), so the flag encoding and these layouts can change in a 2.x minor release.WriteTransactionis a class at namespace scope (it was the aliasChannelSharedState::Transaction), declared indetails/locked_reference.hppand still returned byscopedWrite(). Rebuild consumers built against earlier headers. -
Behaviour change, parser and Python decoder: a schema text in
the line format needs its
### version:line before the fields; without one both throw, naming the supported versions (4 and 5, 6 in YAML). The C++ parser read such a text as an upper-case "name TYPE" format that no release wrote, or as version 5, and the Python decoder as version 5. Texts of the releases before 0.7.0 (late 2023) fail with that message, among them the header-less<type> <name>lines of the 0.3 to 0.5 ROS 2 publisher, which both used to read (docs/wire_format.md, section 2). -
Fixed, Python decoder:
verify_hash=True(parse_schema(),SchemaRegistry,iter_mcap()) rejected every data_tamer 1.x file (schema version 4). Its hash came from the writer'sstd::hashand cannot be recomputed, so it is accepted as declared. The C++check_hashstill recomputes it, which agrees only with the writer's standard library (docs/wire_format.md, section 5). - Docs:
docs/MIGRATION.mdlists what code written for 1.x must change for 2.0, with the behaviour changes that compile silently. -
Real-time: the first access of the transaction state on a thread
no longer allocates when libdata_tamer is loaded with
dlopen()(a plugin, pluginlib, ros2_control), so ascopedWrite()on each real-time thread during setup is no longer needed. The library's one thread-local is initial-exec TLS (glibc):dlopen()takes one pointer of glibc's static TLS surplus. -
ABI: the
WriteTransactionconstructor and destructor (behindscopedWrite(), the guards and non-scalarLoggedValues) andChannelSharedState::inTransactionOnThisThread()are defined in the library, with the thread-local chain. The chain is no longer an inline protocol, so later 2.x releases can change it; only the size ofWriteTransactionis pinned. Rebuild consumers built against earlier headers. -
API:
data_tamer_v2/data_tamer.hppincludeschannel.hppagain, as in 1.x, so one include givesChannelsRegistry,LogChannel,LoggedValueand the sink interface.data_tamer_v2/fwd.hppstays for headers that only name the types. -
API:
takeSnapshot()is no longer[[nodiscard]]:stats()counts every outcome, and most loops don't act on each call.tryTakeSnapshot()still is. -
API: no
LogChannel::droppedSnapshots(), which no release had: readstats().dropped_by_sink.LogChannel::sinkDropped()andChannelDefaults::resolve()(withChannelDefaults::Sizes) are private: they are the building blocks ofstats()andsetChannelDefaults(). Their symbols stay exported (the inlinestats()callssinkDropped()). -
Fixed, deadlocks:
unregister(),removeDataSink()or aLoggedValuedestructor insidescopedWrite()while a snapshot waited; a const query insidescopedWrite()while another thread ran one of those, orstartLogging();startLogging()insidescopedWrite(). The snapshot path takes the write mutex before its epoch, andstartLogging()before the control mutex. -
Behaviour change: a snapshot taken by a thread that holds the
channel's transaction or a
LoggedValueguard returnsblocked(it hung). -
New: several threads may take snapshots of one channel; they
take turns on the write mutex.
blockednow takes precedence overpool_exhausted. -
Fixed: a consumer built with
-fvisibility=hiddenagainst a shared libdata_tamer hung inLoggedValue::set()insidescopedWrite(); the transaction code is defined in the library only. -
Behaviour change:
SinkWorker::stop(),start()anddrain()throwstd::logic_errorfrom a callback of their own sink (they deadlocked, orstop()closed the worker silently). Concurrentstop()andstart(), twostopAll()included, are serialized (they hung). A callback that releases the last reference to its own worker no longer callsstd::terminate. -
Fixed: a sink attached during a failing
startLogging()could miss the final schema, and a concurrentaddDataSink()of one worker announced it twice. -
Real-time: no
notify_all()per snapshot or refused push unless a thread waits; each one could be a futex call. -
Behaviour change: names must be non-empty and free of whitespace
and control characters (only the space was refused);
IsCanonicalName()agrees. A ninth default sink throws inaddDefaultSink()(it made every latergetChannel()throw). -
Behaviour change: custom type names, their field names, the
typeName()of aregisterCustomValue()serializer and channel names are checked too: a line break in any of them split the schema text, and a space in a type or field name broke its field line. Type and field names follow the value name rules, and the registration
File truncated at 100 lines see the full file
Package Dependencies
| Deps | Name |
|---|---|
| ament_cmake | |
| rclcpp | |
| rclcpp_lifecycle | |
| mcap_vendor | |
| data_tamer_msgs | |
| ament_cmake_gtest | |
| gtest_vendor |
System Dependencies
| Name |
|---|
| lz4 |
| libzstd-dev |
Dependant Packages
| Name | Deps |
|---|---|
| plotjuggler |