UCI Notification changes for Owr AoA

Test: atest libuwb_core_test libuwb_uci_packet_tests libuwb_uci_jni_rust_tests ServiceUwbTests FrameworkUwbTests CtsUwbTestCases
Bug: 246678053

Change-Id: I5f02b1636cc3358614f3a2b055ef5229c26ef54e
diff --git a/src/rust/uwb_core/protos/uwb_service.proto b/src/rust/uwb_core/protos/uwb_service.proto
index 68574cc..a6c33e5 100644
--- a/src/rust/uwb_core/protos/uwb_service.proto
+++ b/src/rust/uwb_core/protos/uwb_service.proto
@@ -103,7 +103,12 @@
 
   UCI_STATUS_ERROR_CCC_SE_BUSY = 80;
   UCI_STATUS_ERROR_CCC_LIFECYCLE = 81;
+}
 
+// Represents uwb_uci_packets::OwrAoaStatusCode
+enum OwrAoaStatusCode {
+    UCI_STATUS_SUCCESS = 0;
+    UCI_STATUS_INTER_FRAME_INTERVAL_TIMEOUT = 1;
 }
 
 // Represent uwb_uci_packets::DeviceState.
@@ -380,8 +385,12 @@
   uint32 subsession_id = 2;
 }
 
+// TODO(b/246678053): Should this be split into separate message types ?
+//
 // Represent uwb_uci_packets::ShortAddressTwoWayRangingMeasurement or
-// uwb_uci_packets::ExtendedAddressTwoWayRangingMeasurement.
+// uwb_uci_packets::ExtendedAddressTwoWayRangingMeasurement or
+// uwb_uci_packets::ShortAddressOwrAoaRangingMeasurement or
+// uwb_uci_packets::ExtendedAddressOwrAoaRangingMeasurement.
 message RangingMeasurement {
   uint64 mac_address = 1;
   StatusCode status = 2;
@@ -397,6 +406,9 @@
   uint32 aoa_destination_elevation_fom = 12;
   uint32 slot_index = 13;
   uint32 rssi = 14;
+  uint32 frame_sequence_number = 15;
+  uint32 block_index = 16;
+  OwrAoaStatusCode owr_aoa_status_code = 17;
 }
 
 // Represent uwb_core::uci::notification::SessionRangeData;
diff --git a/src/rust/uwb_core/src/params/uci_packets.rs b/src/rust/uwb_core/src/params/uci_packets.rs
index b1825a2..3deace7 100644
--- a/src/rust/uwb_core/src/params/uci_packets.rs
+++ b/src/rust/uwb_core/src/params/uci_packets.rs
@@ -22,9 +22,10 @@
 pub use uwb_uci_packets::{
     AppConfigStatus, AppConfigTlv as RawAppConfigTlv, AppConfigTlvType, CapTlv, CapTlvType,
     Controlee, ControleeStatus, ControleesV2, DeviceConfigId, DeviceConfigStatus, DeviceConfigTlv,
-    DeviceState, ExtendedAddressDlTdoaRangingMeasurement, ExtendedAddressTwoWayRangingMeasurement,
-    GroupId, MessageType, MulticastUpdateStatusCode, PowerStats, RangingMeasurementType,
-    ReasonCode, ResetConfig, SessionState, SessionType, ShortAddressDlTdoaRangingMeasurement,
+    DeviceState, ExtendedAddressDlTdoaRangingMeasurement, ExtendedAddressOwrAoaRangingMeasurement,
+    ExtendedAddressTwoWayRangingMeasurement, GroupId, MessageType, MulticastUpdateStatusCode,
+    OwrAoaStatusCode, PowerStats, RangingMeasurementType, ReasonCode, ResetConfig, SessionState,
+    SessionType, ShortAddressDlTdoaRangingMeasurement, ShortAddressOwrAoaRangingMeasurement,
     ShortAddressTwoWayRangingMeasurement, StatusCode, UciPacketPacket, UpdateMulticastListAction,
 };
 
diff --git a/src/rust/uwb_core/src/proto/mappings.rs b/src/rust/uwb_core/src/proto/mappings.rs
index 89951a6..9cdfc41 100644
--- a/src/rust/uwb_core/src/proto/mappings.rs
+++ b/src/rust/uwb_core/src/proto/mappings.rs
@@ -28,8 +28,9 @@
     ScheduledMode, StsConfig, StsLength, TxAdaptivePayloadPower, UwbAddress, UwbChannel,
 };
 use crate::params::uci_packets::{
-    Controlee, DeviceState, ExtendedAddressTwoWayRangingMeasurement, PowerStats,
-    RangingMeasurementType, ReasonCode, SessionState, SessionType,
+    Controlee, DeviceState, ExtendedAddressOwrAoaRangingMeasurement,
+    ExtendedAddressTwoWayRangingMeasurement, OwrAoaStatusCode, PowerStats, RangingMeasurementType,
+    ReasonCode, SessionState, SessionType, ShortAddressOwrAoaRangingMeasurement,
     ShortAddressTwoWayRangingMeasurement, StatusCode, UpdateMulticastListAction,
 };
 use crate::params::AppConfigParams;
@@ -39,10 +40,10 @@
     DeviceType as ProtoDeviceType, FiraAppConfigParams as ProtoFiraAppConfigParams,
     HoppingMode as ProtoHoppingMode, KeyRotation as ProtoKeyRotation,
     MacAddressMode as ProtoMacAddressMode, MacFcsType as ProtoMacFcsType,
-    MultiNodeMode as ProtoMultiNodeMode, PowerStats as ProtoPowerStats,
-    PreambleDuration as ProtoPreambleDuration, PrfMode as ProtoPrfMode,
-    PsduDataRate as ProtoPsduDataRate, RangeDataNtfConfig as ProtoRangeDataNtfConfig,
-    RangingMeasurement as ProtoRangingMeasurement,
+    MultiNodeMode as ProtoMultiNodeMode, OwrAoaStatusCode as ProtoOwrAoaStatusCode,
+    PowerStats as ProtoPowerStats, PreambleDuration as ProtoPreambleDuration,
+    PrfMode as ProtoPrfMode, PsduDataRate as ProtoPsduDataRate,
+    RangeDataNtfConfig as ProtoRangeDataNtfConfig, RangingMeasurement as ProtoRangingMeasurement,
     RangingMeasurementType as ProtoRangingMeasurementType,
     RangingRoundControl as ProtoRangingRoundControl, RangingRoundUsage as ProtoRangingRoundUsage,
     RangingTimeStruct as ProtoRangingTimeStruct, ReasonCode as ProtoReasonCode,
@@ -143,6 +144,12 @@
 }
 
 enum_mapping! {
+    ProtoOwrAoaStatusCode => OwrAoaStatusCode,
+    UCI_STATUS_SUCCESS => UciStatusSuccess,
+    UCI_STATUS_INTER_FRAME_INTERVAL_TIMEOUT => UciStatusInterFrameIntervalTimeout,
+}
+
+enum_mapping! {
     ProtoDeviceState => DeviceState,
     DEVICE_STATE_READY => DeviceStateReady,
     DEVICE_STATE_ACTIVE => DeviceStateActive,
@@ -403,6 +410,38 @@
     }
 }
 
+impl From<ShortAddressOwrAoaRangingMeasurement> for ProtoRangingMeasurement {
+    fn from(item: ShortAddressOwrAoaRangingMeasurement) -> Self {
+        let mut result = Self::new();
+        result.set_mac_address(item.mac_address.into());
+        result.set_owr_aoa_status_code(item.status.into());
+        result.set_nlos(item.nlos.into());
+        result.set_block_index(item.block_index.into());
+        result.set_frame_sequence_number(item.frame_sequence_number.into());
+        result.set_aoa_azimuth(item.aoa_azimuth.into());
+        result.set_aoa_azimuth_fom(item.aoa_azimuth_fom.into());
+        result.set_aoa_elevation(item.aoa_elevation.into());
+        result.set_aoa_elevation_fom(item.aoa_elevation_fom.into());
+        result
+    }
+}
+
+impl From<ExtendedAddressOwrAoaRangingMeasurement> for ProtoRangingMeasurement {
+    fn from(item: ExtendedAddressOwrAoaRangingMeasurement) -> Self {
+        let mut result = Self::new();
+        result.set_mac_address(item.mac_address);
+        result.set_owr_aoa_status_code(item.status.into());
+        result.set_nlos(item.nlos.into());
+        result.set_block_index(item.block_index.into());
+        result.set_frame_sequence_number(item.frame_sequence_number.into());
+        result.set_aoa_azimuth(item.aoa_azimuth.into());
+        result.set_aoa_azimuth_fom(item.aoa_azimuth_fom.into());
+        result.set_aoa_elevation(item.aoa_elevation.into());
+        result.set_aoa_elevation_fom(item.aoa_elevation_fom.into());
+        result
+    }
+}
+
 impl From<SessionRangeData> for ProtoSessionRangeData {
     fn from(item: SessionRangeData) -> Self {
         let mut result = Self::new();
@@ -419,8 +458,18 @@
 
 fn to_proto_ranging_measurements(item: RangingMeasurements) -> Vec<ProtoRangingMeasurement> {
     match item {
-        RangingMeasurements::Short(arr) => arr.into_iter().map(|item| item.into()).collect(),
-        RangingMeasurements::Extended(arr) => arr.into_iter().map(|item| item.into()).collect(),
+        RangingMeasurements::ShortAddressTwoWay(arr) => {
+            arr.into_iter().map(|item| item.into()).collect()
+        }
+        RangingMeasurements::ExtendedAddressTwoWay(arr) => {
+            arr.into_iter().map(|item| item.into()).collect()
+        }
+        RangingMeasurements::ShortAddressOwrAoa(arr) => {
+            arr.into_iter().map(|item| item.into()).collect()
+        }
+        RangingMeasurements::ExtendedAddressOwrAoa(arr) => {
+            arr.into_iter().map(|item| item.into()).collect()
+        }
         // TODO(b/260499366): Add support for DlTDoA.
         _ => todo!(),
     }
diff --git a/src/rust/uwb_core/src/session/session_manager.rs b/src/rust/uwb_core/src/session/session_manager.rs
index 667879f..34a4caa 100644
--- a/src/rust/uwb_core/src/session/session_manager.rs
+++ b/src/rust/uwb_core/src/session/session_manager.rs
@@ -438,7 +438,7 @@
             session_id,
             current_ranging_interval_ms: 3,
             ranging_measurement_type: RangingMeasurementType::TwoWay,
-            ranging_measurements: RangingMeasurements::Short(vec![
+            ranging_measurements: RangingMeasurements::ShortAddressTwoWay(vec![
                 ShortAddressTwoWayRangingMeasurement {
                     mac_address: 0x123,
                     status: StatusCode::UciStatusOk,
diff --git a/src/rust/uwb_core/src/uci/notification.rs b/src/rust/uwb_core/src/uci/notification.rs
index 067bcea..16f4d0a 100644
--- a/src/rust/uwb_core/src/uci/notification.rs
+++ b/src/rust/uwb_core/src/uci/notification.rs
@@ -21,8 +21,9 @@
 use crate::error::{Error, Result};
 use crate::params::uci_packets::{
     ControleeStatus, DeviceState, ExtendedAddressDlTdoaRangingMeasurement,
-    ExtendedAddressTwoWayRangingMeasurement, RangingMeasurementType, RawUciMessage, ReasonCode,
-    SessionId, SessionState, ShortAddressDlTdoaRangingMeasurement,
+    ExtendedAddressOwrAoaRangingMeasurement, ExtendedAddressTwoWayRangingMeasurement,
+    RangingMeasurementType, RawUciMessage, ReasonCode, SessionId, SessionState,
+    ShortAddressDlTdoaRangingMeasurement, ShortAddressOwrAoaRangingMeasurement,
     ShortAddressTwoWayRangingMeasurement, StatusCode,
 };
 
@@ -100,17 +101,23 @@
 /// The ranging measurements.
 #[derive(Debug, Clone, PartialEq)]
 pub enum RangingMeasurements {
-    /// The measurement with short address.
-    Short(Vec<ShortAddressTwoWayRangingMeasurement>),
+    /// A Two-Way measurement with short address.
+    ShortAddressTwoWay(Vec<ShortAddressTwoWayRangingMeasurement>),
 
-    /// The measurement with extended address.
-    Extended(Vec<ExtendedAddressTwoWayRangingMeasurement>),
+    /// A Two-Way measurement with extended address.
+    ExtendedAddressTwoWay(Vec<ExtendedAddressTwoWayRangingMeasurement>),
 
     /// Dl-TDoA measurement with short address.
     ShortDltdoa(Vec<ShortAddressDlTdoaRangingMeasurement>),
 
     /// Dl-TDoA measurement with extended address.
     ExtendedDltdoa(Vec<ExtendedAddressDlTdoaRangingMeasurement>),
+
+    /// OWR for AoA measurement with short address.
+    ShortAddressOwrAoa(Vec<ShortAddressOwrAoaRangingMeasurement>),
+
+    /// OWR for AoA measurement with extended address.
+    ExtendedAddressOwrAoa(Vec<ExtendedAddressOwrAoaRangingMeasurement>),
 }
 
 impl UciNotification {
@@ -217,10 +224,24 @@
         use uwb_uci_packets::RangeDataNtfChild;
         let ranging_measurements = match evt.specialize() {
             RangeDataNtfChild::ShortMacTwoWayRangeDataNtf(evt) => {
-                RangingMeasurements::Short(evt.get_two_way_ranging_measurements().clone())
+                RangingMeasurements::ShortAddressTwoWay(
+                    evt.get_two_way_ranging_measurements().clone(),
+                )
             }
             RangeDataNtfChild::ExtendedMacTwoWayRangeDataNtf(evt) => {
-                RangingMeasurements::Extended(evt.get_two_way_ranging_measurements().clone())
+                RangingMeasurements::ExtendedAddressTwoWay(
+                    evt.get_two_way_ranging_measurements().clone(),
+                )
+            }
+            RangeDataNtfChild::ShortMacOwrAoaRangeDataNtf(evt) => {
+                RangingMeasurements::ShortAddressOwrAoa(
+                    evt.get_owr_aoa_ranging_measurements().clone(),
+                )
+            }
+            RangeDataNtfChild::ExtendedMacOwrAoaRangeDataNtf(evt) => {
+                RangingMeasurements::ExtendedAddressOwrAoa(
+                    evt.get_owr_aoa_ranging_measurements().clone(),
+                )
             }
             RangeDataNtfChild::ShortMacDlTDoARangeDataNtf(evt) => {
                 match ShortAddressDlTdoaRangingMeasurement::parse(&evt.clone().to_vec()) {
@@ -348,12 +369,14 @@
 #[cfg(test)]
 mod tests {
     use super::*;
+    use crate::params::uci_packets::OwrAoaStatusCode;
+
     #[test]
     fn test_ranging_measurements_trait() {
-        let empty_short_ranging_measurements = RangingMeasurements::Short(vec![]);
+        let empty_short_ranging_measurements = RangingMeasurements::ShortAddressTwoWay(vec![]);
         assert_eq!(empty_short_ranging_measurements, empty_short_ranging_measurements);
-        let extended_ranging_measurements =
-            RangingMeasurements::Extended(vec![ExtendedAddressTwoWayRangingMeasurement {
+        let extended_ranging_measurements = RangingMeasurements::ExtendedAddressTwoWay(vec![
+            ExtendedAddressTwoWayRangingMeasurement {
                 mac_address: 0x1234_5678_90ab,
                 status: StatusCode::UciStatusOk,
                 nlos: 0,
@@ -368,10 +391,12 @@
                 aoa_destination_elevation_fom: 12,
                 slot_index: 0,
                 rssi: u8::MAX,
-            }]);
+            },
+        ]);
         let extended_ranging_measurements_copy = extended_ranging_measurements.clone();
         assert_eq!(extended_ranging_measurements, extended_ranging_measurements_copy);
-        let empty_extended_ranging_measurements = RangingMeasurements::Extended(vec![]);
+        let empty_extended_ranging_measurements =
+            RangingMeasurements::ExtendedAddressTwoWay(vec![]);
         assert_eq!(empty_short_ranging_measurements, empty_short_ranging_measurements);
         //short and extended measurements are unequal even if both are empty:
         assert_ne!(empty_short_ranging_measurements, empty_extended_ranging_measurements);
@@ -410,6 +435,7 @@
             ))
         );
     }
+
     #[test]
     fn test_session_notification_casting_from_extended_mac_two_way_range_data_ntf() {
         let extended_measurement = uwb_uci_packets::ExtendedAddressTwoWayRangingMeasurement {
@@ -451,7 +477,9 @@
                 session_id: 0x11,
                 ranging_measurement_type: uwb_uci_packets::RangingMeasurementType::TwoWay,
                 current_ranging_interval_ms: 0x13,
-                ranging_measurements: RangingMeasurements::Extended(vec![extended_measurement]),
+                ranging_measurements: RangingMeasurements::ExtendedAddressTwoWay(vec![
+                    extended_measurement
+                ]),
                 rcr_indicator: 0x12,
                 raw_ranging_data,
             }))
@@ -498,7 +526,98 @@
                 session_id: 0x11,
                 ranging_measurement_type: uwb_uci_packets::RangingMeasurementType::TwoWay,
                 current_ranging_interval_ms: 0x13,
-                ranging_measurements: RangingMeasurements::Short(vec![short_measurement]),
+                ranging_measurements: RangingMeasurements::ShortAddressTwoWay(vec![
+                    short_measurement
+                ]),
+                rcr_indicator: 0x12,
+                raw_ranging_data,
+            }))
+        );
+    }
+
+    #[test]
+    fn test_session_notification_casting_from_extended_mac_owr_aoa_range_data_ntf() {
+        let extended_measurement = uwb_uci_packets::ExtendedAddressOwrAoaRangingMeasurement {
+            mac_address: 0x1234_5678_90ab,
+            status: OwrAoaStatusCode::UciStatusSuccess,
+            nlos: 0,
+            frame_sequence_number: 1,
+            block_index: 1,
+            aoa_azimuth: 5,
+            aoa_azimuth_fom: 6,
+            aoa_elevation: 7,
+            aoa_elevation_fom: 8,
+        };
+        let extended_owr_aoa_range_data_ntf =
+            uwb_uci_packets::ExtendedMacOwrAoaRangeDataNtfBuilder {
+                sequence_number: 0x10,
+                session_id: 0x11,
+                rcr_indicator: 0x12,
+                current_ranging_interval: 0x13,
+                owr_aoa_ranging_measurements: vec![extended_measurement.clone()],
+            }
+            .build();
+        let raw_ranging_data = extended_owr_aoa_range_data_ntf.clone().to_vec();
+        let range_notification =
+            uwb_uci_packets::RangingNotificationPacket::try_from(extended_owr_aoa_range_data_ntf)
+                .unwrap();
+        let session_notification = SessionNotification::try_from(range_notification).unwrap();
+        let uci_notification_from_extended_owr_aoa_range_data_ntf =
+            UciNotification::Session(session_notification);
+        assert_eq!(
+            uci_notification_from_extended_owr_aoa_range_data_ntf,
+            UciNotification::Session(SessionNotification::RangeData(SessionRangeData {
+                sequence_number: 0x10,
+                session_id: 0x11,
+                ranging_measurement_type: uwb_uci_packets::RangingMeasurementType::OwrAoa,
+                current_ranging_interval_ms: 0x13,
+                ranging_measurements: RangingMeasurements::ExtendedAddressOwrAoa(vec![
+                    extended_measurement
+                ]),
+                rcr_indicator: 0x12,
+                raw_ranging_data,
+            }))
+        );
+    }
+
+    #[test]
+    fn test_session_notification_casting_from_short_mac_owr_aoa_range_data_ntf() {
+        let short_measurement = uwb_uci_packets::ShortAddressOwrAoaRangingMeasurement {
+            mac_address: 0x1234,
+            status: OwrAoaStatusCode::UciStatusSuccess,
+            nlos: 0,
+            frame_sequence_number: 1,
+            block_index: 1,
+            aoa_azimuth: 5,
+            aoa_azimuth_fom: 6,
+            aoa_elevation: 7,
+            aoa_elevation_fom: 8,
+        };
+        let short_owr_aoa_range_data_ntf = uwb_uci_packets::ShortMacOwrAoaRangeDataNtfBuilder {
+            sequence_number: 0x10,
+            session_id: 0x11,
+            rcr_indicator: 0x12,
+            current_ranging_interval: 0x13,
+            owr_aoa_ranging_measurements: vec![short_measurement.clone()],
+        }
+        .build();
+        let raw_ranging_data = short_owr_aoa_range_data_ntf.clone().to_vec();
+        let range_notification =
+            uwb_uci_packets::RangingNotificationPacket::try_from(short_owr_aoa_range_data_ntf)
+                .unwrap();
+        let session_notification = SessionNotification::try_from(range_notification).unwrap();
+        let uci_notification_from_short_owr_aoa_range_data_ntf =
+            UciNotification::Session(session_notification);
+        assert_eq!(
+            uci_notification_from_short_owr_aoa_range_data_ntf,
+            UciNotification::Session(SessionNotification::RangeData(SessionRangeData {
+                sequence_number: 0x10,
+                session_id: 0x11,
+                ranging_measurement_type: uwb_uci_packets::RangingMeasurementType::OwrAoa,
+                current_ranging_interval_ms: 0x13,
+                ranging_measurements: RangingMeasurements::ShortAddressOwrAoa(vec![
+                    short_measurement
+                ]),
                 rcr_indicator: 0x12,
                 raw_ranging_data,
             }))