-
Notifications
You must be signed in to change notification settings - Fork 4.8k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
basic dds metadata tests (just the beginning) #11665
Conversation
} | ||
std::vector< std::string > arr( RS2_FRAME_METADATA_COUNT ); | ||
#define CASE( X ) STRARR( arr, FRAME_METADATA, X ); | ||
CASE( FRAME_COUNTER ) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Its a matter of style but I prefer not to define and undefine CASE, and probably doing so for all other types as well.
You can change CASE( FRAME_COUNTER )
to STRARR( arr, FRAME_METADATA, FRAME_COUNTER )
and you can do it easily for all the cases here at once in VS using vertical editing.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Replied on call :)
void enqueue_frame( key_type, frame_holder && ); | ||
void enqueue_metadata( key_type, metadata_type && ); | ||
|
||
dds_metadata_syncer & on_frame_release( on_frame_release_callback cb ) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I don't think that on_xxx
functions should return a value.
They are intended to set an aspect of the syncer behavior, nothing about them or their name implies returning something, let alone this syncer object.
Using this to chain function calls is not clear syntax, especially when passing lambda as input parameters. It is more readable to call syncer_object.on_xxx(...)
multiple times expressing the object name.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I guess it's a matter of preference: I see no difference between these and operator=
, for example. And the practice is well-in-use if you're used to pybind, for another example, or simply want to construct an object in multiple steps while still keeping it unnamed.
In this case:
_stream_name_to_syncer[dds_stream->name()]
.on_frame_release( frame_releaser )
.on_frame_ready(
[this]( syncer_type::frame_holder && fh, json && md ) { ... } );
Is now:
auto & syncer = _stream_name_to_syncer[dds_stream->name()];
syncer.on_frame_release( frame_releaser );
syncer.on_frame_ready(
[this]( syncer_type::frame_holder && fh, json && md ) { ... } );
@@ -187,19 +188,21 @@ namespace librealsense | |||
assert( _device_watcher->is_stopped() ); | |||
|
|||
#ifdef BUILD_WITH_DDS | |||
if( rsutils::json::get< bool >( settings, "dds-discovery", true ) ) | |||
if( rsutils::json::get< bool >( settings, std::string( "dds-discovery", 13 ), true ) ) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Do you have to explicitly use the string size? It is inconvenient and error prone
Looks like it should work without the explicit size (using constructor number 5, not 4)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It's optional, but I dislike using strlen
for constants
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
What if you miscount?
Will the json find the right string while searching for dds-discover
or dds-discovery
(extra char can be of any value) or would it throw?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It's a constant. It's like getting a constant value wrong.
This is why we have a CR and testing :)
|
||
// Expected metadata for all depth images | ||
if( rsutils::json::has( md_header, "depth-units" ) ) | ||
f->additional_data.depth_units = rsutils::json::get< float >( md_header, "depth-units" ); | ||
rsutils::json::get_ex( md_header, std::string( "depth-units", 11 ), &f->additional_data.depth_units ); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Will throw for color frames
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
get_ex
returns a bool on failure, and checks if it's there first. It can still throw, but not if it's not there.
void dds_metadata_syncer::enqueue_frame( key_type id, frame_holder && frame ) | ||
{ | ||
std::lock_guard< std::mutex > lock( _queues_lock ); | ||
while( _frame_queue.size() >= max_frame_queue_size ) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think that with your changes max_frame_queue_size should be 1.
If no metadata is received, we want to delay the frame for maximum of one other frame. Here it can be delayed for 2 frames.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
What changes are you referring to, that we can change the limit? I'm not objecting (though I'm hesitant to change this PR - I prefer waiting until after I have the unit-tests in), just curious.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Changes like checking the queue size here and not in search_for_match
. We can leave for now, until the unit-tests will be completed. Just need to make sure not to delay the frame for too long
key_frame & synced = _frame_queue.front(); | ||
auto & fh = synced.second; | ||
|
||
metadata_type md = std::move( _metadata_queue.front().second ); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Why do we need md
and moving twice?
Can pop the queue after _on_frame_ready
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
You'll see in my next PR that we need to push/pop before any callbacks, since stuff can happen during the callbacks.
context = rs.context( '{"dds-domain":123,"dds-participant-name":"librs"}' ) | ||
# The DDS devices take time to be recognized and we just created the context; we | ||
# should not see them yet! | ||
test.check( len( context.query_devices( only_sw_devices )) != 2 ) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I don't think that we need this check. You don't know the timing and discovery might have happened, especially if working in shared memory.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I thought you'd want it based on the original comments.
I agree, but the chances that it'll fail are slim.
Anyway, I commented out the line so it's still explained and there...
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Should add some more metadata tests - image after metadata, etc... but will be in future PRs
frame_holder
outside of librealsensedevice::image
like it was before but that would have brought back theprofile
storage thing and wasn't as translatable to a different framework like for testing; decided against itunique_ptr
approach with a deleter for on-release that's now passed to the syncerBy the way:
shorten_json_string
const char *
is a "waste" in thatstrlen
and an alloc is then used to build a stringrsutils::json::
functions have been updated to accept stringsrs2_frame_metadata_to_string
which returns aconst char *
-- so, instead, we now directly calllibrealsense::get_string( metadata )
which was changed to return a string reference and use array indexing -- should now be a lot fasterMany of these are better looked at by commit rather than going over all the changes together.
Still to do: