From 59b8d3a955c1ff9595b105afdd7934a53406544b Mon Sep 17 00:00:00 2001 From: Korcan Hussein Date: Wed, 13 Dec 2023 21:56:56 +0000 Subject: [PATCH] st/oxr: Separate out dynamic roles and associated profiles Separates the role xdev indices and associated interaction profile (names) from dynamic roles so that interaction profiles can be method active and have action (set) attachements updated without bindings and no requirement for an xrt-device for a particular hand. E.g. driver can make left & right with a paritcular profile (name) and have either both not have an xrt-device ready/unassigned but OpenXR apps can still sync/query actions states on the not read/unassigned hands, this also fixes CTS action tests when the hand is constrained to certain hand, in particular the right hand. Co-authored-by: Robbie Bridgewater --- src/xrt/include/xrt/xrt_defines.h | 2 ++ src/xrt/include/xrt/xrt_system.h | 9 ++++- src/xrt/state_trackers/oxr/oxr_binding.c | 14 ++++---- src/xrt/state_trackers/oxr/oxr_input.c | 24 ++++++++++--- src/xrt/state_trackers/oxr/oxr_objects.h | 44 ++++++++++++++++++++++++ 5 files changed, 81 insertions(+), 12 deletions(-) diff --git a/src/xrt/include/xrt/xrt_defines.h b/src/xrt/include/xrt/xrt_defines.h index 91dc1562f..ad9628c4a 100644 --- a/src/xrt/include/xrt/xrt_defines.h +++ b/src/xrt/include/xrt/xrt_defines.h @@ -657,6 +657,8 @@ struct xrt_relation_chain */ enum xrt_device_name { + XRT_DEVICE_INVALID = 0, + XRT_DEVICE_GENERIC_HMD = 1, // Vive stuff. diff --git a/src/xrt/include/xrt/xrt_system.h b/src/xrt/include/xrt/xrt_system.h index d01ce4e69..0e22d25f7 100644 --- a/src/xrt/include/xrt/xrt_system.h +++ b/src/xrt/include/xrt/xrt_system.h @@ -5,6 +5,7 @@ * @file * @brief Header for system objects. * @author Jakob Bornecrantz + * @author Korcan Hussein * @ingroup xrt_iface */ @@ -171,6 +172,12 @@ struct xrt_system_roles * device, or negative if none available. */ int32_t gamepad; + + enum xrt_device_name left_profile; + + enum xrt_device_name right_profile; + + enum xrt_device_name gamepad_profile; }; /*! @@ -182,7 +189,7 @@ struct xrt_system_roles */ #define XRT_SYSTEM_ROLES_INIT \ { \ - 0, -1, -1, -1 \ + 0, -1, -1, -1, XRT_DEVICE_INVALID, XRT_DEVICE_INVALID, XRT_DEVICE_INVALID, \ } diff --git a/src/xrt/state_trackers/oxr/oxr_binding.c b/src/xrt/state_trackers/oxr/oxr_binding.c index 1a494893b..a0bfa892c 100644 --- a/src/xrt/state_trackers/oxr/oxr_binding.c +++ b/src/xrt/state_trackers/oxr/oxr_binding.c @@ -342,11 +342,11 @@ get_identifier_str_in_profile(struct oxr_logger *log, return str; } -static void -get_profile_for_device_name(struct oxr_logger *log, - struct oxr_session *sess, - enum xrt_device_name name, - struct oxr_interaction_profile **out_p) +void +oxr_get_profile_for_device_name(struct oxr_logger *log, + struct oxr_session *sess, + enum xrt_device_name name, + struct oxr_interaction_profile **out_p) { struct oxr_instance *inst = sess->sys->inst; /* @@ -407,7 +407,7 @@ oxr_find_profile_for_device(struct oxr_logger *log, } // Have bindings for this device's interaction profile been suggested? - get_profile_for_device_name(log, sess, xdev->name, out_p); + oxr_get_profile_for_device_name(log, sess, xdev->name, out_p); if (*out_p != NULL) { return; } @@ -415,7 +415,7 @@ oxr_find_profile_for_device(struct oxr_logger *log, // Check if bindings for any of this device's alternative interaction profiles have been suggested. for (size_t i = 0; i < xdev->binding_profile_count; i++) { struct xrt_binding_profile *xbp = &xdev->binding_profiles[i]; - get_profile_for_device_name(log, sess, xbp->name, out_p); + oxr_get_profile_for_device_name(log, sess, xbp->name, out_p); if (*out_p != NULL) { return; } diff --git a/src/xrt/state_trackers/oxr/oxr_input.c b/src/xrt/state_trackers/oxr/oxr_input.c index bfbd93939..c93176d71 100644 --- a/src/xrt/state_trackers/oxr/oxr_input.c +++ b/src/xrt/state_trackers/oxr/oxr_input.c @@ -747,6 +747,25 @@ struct oxr_profiles_per_subaction #undef PROFILE_MEMBER }; +static void +oxr_find_profiles_from_roles(struct oxr_logger *log, + struct oxr_session *sess, + struct oxr_profiles_per_subaction *out_profiles) +{ +#define FIND_PROFILE(X) \ + { \ + struct xrt_device *xdev = GET_XDEV_BY_ROLE(sess->sys, X); \ + if (xdev != NULL) { \ + oxr_find_profile_for_device(log, sess, xdev, &out_profiles->X); \ + } else { \ + oxr_get_profile_for_device_name(log, sess, GET_PROFILE_NAME_BY_ROLE(sess->sys, X), \ + &out_profiles->X); \ + } \ + } + OXR_FOR_EACH_VALID_SUBACTION_PATH(FIND_PROFILE) +#undef FIND_PROFILE +} + /*! * @public @memberof oxr_action_attachment */ @@ -1661,10 +1680,7 @@ XrResult oxr_session_update_action_bindings(struct oxr_logger *log, struct oxr_session *sess) { struct oxr_profiles_per_subaction profiles = {0}; - -#define FIND_PROFILE(X) oxr_find_profile_for_device(log, sess, GET_XDEV_BY_ROLE(sess->sys, X), &profiles.X); - OXR_FOR_EACH_VALID_SUBACTION_PATH(FIND_PROFILE) -#undef FIND_PROFILE + oxr_find_profiles_from_roles(log, sess, &profiles); for (size_t i = 0; i < sess->action_set_attachment_count; i++) { struct oxr_action_set_attachment *act_set_attached = &sess->act_set_attachments[i]; diff --git a/src/xrt/state_trackers/oxr/oxr_objects.h b/src/xrt/state_trackers/oxr/oxr_objects.h index 539feaf88..9d094ae2b 100644 --- a/src/xrt/state_trackers/oxr/oxr_objects.h +++ b/src/xrt/state_trackers/oxr/oxr_objects.h @@ -564,6 +564,12 @@ oxr_find_profile_for_device(struct oxr_logger *log, struct xrt_device *xdev, struct oxr_interaction_profile **out_p); +void +oxr_get_profile_for_device_name(struct oxr_logger *log, + struct oxr_session *sess, + enum xrt_device_name name, + struct oxr_interaction_profile **out_p); + struct oxr_interaction_profile * oxr_clone_profile(const struct oxr_interaction_profile *src_profile); @@ -1395,6 +1401,44 @@ MAKE_GET_DYN_ROLES_FN(gamepad) #define GET_XDEV_BY_ROLE(SYS, ROLE) (get_role_##ROLE((SYS))) +static inline enum xrt_device_name +get_role_profile_head(struct oxr_system *sys) +{ + return XRT_DEVICE_INVALID; +} +static inline enum xrt_device_name +get_role_profile_eyes(struct oxr_system *sys) +{ + return XRT_DEVICE_INVALID; +} +static inline enum xrt_device_name +get_role_profile_hand_tracking_left(struct oxr_system *sys) +{ + return XRT_DEVICE_INVALID; +} +static inline enum xrt_device_name +get_role_profile_hand_tracking_right(struct oxr_system *sys) +{ + return XRT_DEVICE_INVALID; +} + +#define MAKE_GET_DYN_ROLE_PROFILE_FN(ROLE) \ + static inline enum xrt_device_name get_role_profile_##ROLE(struct oxr_system *sys) \ + { \ + const bool is_locked = 0 == os_mutex_trylock(&sys->sync_actions_mutex); \ + const enum xrt_device_name profile_name = sys->dynamic_roles_cache.ROLE##_profile; \ + if (is_locked) { \ + os_mutex_unlock(&sys->sync_actions_mutex); \ + } \ + return profile_name; \ + } +MAKE_GET_DYN_ROLE_PROFILE_FN(left) +MAKE_GET_DYN_ROLE_PROFILE_FN(right) +MAKE_GET_DYN_ROLE_PROFILE_FN(gamepad) +#undef MAKE_GET_DYN_ROLES_FN + +#define GET_PROFILE_NAME_BY_ROLE(SYS, ROLE) (get_role_profile_##ROLE((SYS))) + /* * Extensions helpers. */