1 // Copyright 2022, The Android Open Source Project
2 //
3 // Licensed under the Apache License, Version 2.0 (the "License");
4 // you may not use this file except in compliance with the License.
5 // You may obtain a copy of the License at
6 //
7 // http://www.apache.org/licenses/LICENSE-2.0
8 //
9 // Unless required by applicable law or agreed to in writing, software
10 // distributed under the License is distributed on an "AS IS" BASIS,
11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 // See the License for the specific language governing permissions and
13 // limitations under the License.
14
15 //! Provide the conversion between the uwb_core's elements and protobuf bindings.
16
17 use std::convert::{TryFrom, TryInto};
18
19 use zeroize::Zeroize;
20
21 use crate::error::{Error, Result};
22 use crate::params::fira_app_config_params::{
23 AoaResultRequest, BprfPhrDataRate, DeviceRole, DeviceType, FiraAppConfigParams,
24 FiraAppConfigParamsBuilder, HoppingMode, KeyRotation, MacAddressMode, MacFcsType,
25 MultiNodeMode, PreambleDuration, PrfMode, PsduDataRate, RangeDataNtfConfig,
26 RangingRoundControl, RangingRoundUsage, RangingTimeStruct, ResultReportConfig, RframeConfig,
27 ScheduledMode, StsConfig, StsLength, TxAdaptivePayloadPower, UwbAddress, UwbChannel,
28 };
29 use crate::params::uci_packets::{
30 Controlee, DeviceState, ExtendedAddressDlTdoaRangingMeasurement,
31 ExtendedAddressOwrAoaRangingMeasurement, ExtendedAddressTwoWayRangingMeasurement,
32 MacAddressIndicator, PowerStats, RangingMeasurementType, ReasonCode, SessionState, SessionType,
33 ShortAddressDlTdoaRangingMeasurement, ShortAddressOwrAoaRangingMeasurement,
34 ShortAddressTwoWayRangingMeasurement, StatusCode, UpdateMulticastListAction,
35 };
36 use crate::params::AppConfigParams;
37 use crate::proto::bindings::{
38 AoaResultRequest as ProtoAoaResultRequest, BprfPhrDataRate as ProtoBprfPhrDataRate,
39 Controlee as ProtoControlee, DeviceRole as ProtoDeviceRole, DeviceState as ProtoDeviceState,
40 DeviceType as ProtoDeviceType, DlTDoARangingMeasurement as ProtoDlTDoARangingMeasurement,
41 FiraAppConfigParams as ProtoFiraAppConfigParams, HoppingMode as ProtoHoppingMode,
42 KeyRotation as ProtoKeyRotation, MacAddressIndicator as ProtoMacAddressIndicator,
43 MacAddressMode as ProtoMacAddressMode, MacFcsType as ProtoMacFcsType,
44 MultiNodeMode as ProtoMultiNodeMode, OwrAoaRangingMeasurement as ProtoOwrAoaRangingMeasurement,
45 PowerStats as ProtoPowerStats, PreambleDuration as ProtoPreambleDuration,
46 PrfMode as ProtoPrfMode, PsduDataRate as ProtoPsduDataRate,
47 RangeDataNtfConfig as ProtoRangeDataNtfConfig,
48 RangingMeasurementType as ProtoRangingMeasurementType,
49 RangingRoundControl as ProtoRangingRoundControl, RangingRoundUsage as ProtoRangingRoundUsage,
50 RangingTimeStruct as ProtoRangingTimeStruct, ReasonCode as ProtoReasonCode,
51 ResultReportConfig as ProtoResultReportConfig, RframeConfig as ProtoRframeConfig,
52 ScheduledMode as ProtoScheduledMode, SessionRangeData as ProtoSessionRangeData,
53 SessionState as ProtoSessionState, SessionType as ProtoSessionType, Status as ProtoStatus,
54 StatusCode as ProtoStatusCode, StsConfig as ProtoStsConfig, StsLength as ProtoStsLength,
55 TwoWayRangingMeasurement as ProtoTwoWayRangingMeasurement,
56 TxAdaptivePayloadPower as ProtoTxAdaptivePayloadPower, UciLoggerMode as ProtoUciLoggerMode,
57 UpdateMulticastListAction as ProtoUpdateMulticastListAction, UwbChannel as ProtoUwbChannel,
58 };
59 use crate::uci::notification::{RangingMeasurements, SessionRangeData};
60 use crate::uci::uci_logger::UciLoggerMode;
61 use protobuf::{EnumOrUnknown, MessageField};
62
63 /// Generate the conversion functions between 2 enum types, which field is 1-to-1 mapping.
64 ///
65 /// Example:
66 /// ```
67 /// enum EnumA {
68 /// Value1,
69 /// Value2,
70 /// }
71 /// enum EnumB {
72 /// Foo,
73 /// Bar,
74 /// }
75 /// // This macro generates `From<EnumA> for EnumB` and `From<EnumB> for EnumA`.
76 /// uwb_core::enum_mapping! {
77 /// EnumA => EnumB,
78 /// Value1 => Foo,
79 /// Value2 => Bar,
80 /// }
81 /// ```
82 #[macro_export]
83 macro_rules! enum_mapping {
84 ( $enum_a:ty => $enum_b:ty, $( $field_a:ident => $field_b:ident, )+ ) => {
85 impl From<$enum_a> for $enum_b {
86 fn from(item: $enum_a) -> $enum_b {
87 match item {
88 $(
89 <$enum_a>::$field_a => <$enum_b>::$field_b,
90 )*
91 }
92 }
93 }
94 impl From<$enum_b> for $enum_a {
95 fn from(item: $enum_b) -> $enum_a {
96 match item {
97 $(
98 <$enum_b>::$field_b => <$enum_a>::$field_a,
99 )*
100 }
101 }
102 }
103 };
104 }
105
106 impl From<ProtoStatusCode> for StatusCode {
from(item: ProtoStatusCode) -> Self107 fn from(item: ProtoStatusCode) -> Self {
108 match item {
109 ProtoStatusCode::UCI_STATUS_OK => StatusCode::UciStatusOk,
110 ProtoStatusCode::UCI_STATUS_REJECTED => StatusCode::UciStatusRejected,
111 ProtoStatusCode::UCI_STATUS_FAILED => StatusCode::UciStatusFailed,
112 ProtoStatusCode::UCI_STATUS_SYNTAX_ERROR => StatusCode::UciStatusSyntaxError,
113 ProtoStatusCode::UCI_STATUS_INVALID_PARAM => StatusCode::UciStatusInvalidParam,
114 ProtoStatusCode::UCI_STATUS_INVALID_RANGE => StatusCode::UciStatusInvalidRange,
115 ProtoStatusCode::UCI_STATUS_INVALID_MSG_SIZE => StatusCode::UciStatusInvalidMsgSize,
116 ProtoStatusCode::UCI_STATUS_UNKNOWN_GID => StatusCode::UciStatusUnknownGid,
117 ProtoStatusCode::UCI_STATUS_UNKNOWN_OID => StatusCode::UciStatusUnknownOid,
118 ProtoStatusCode::UCI_STATUS_READ_ONLY => StatusCode::UciStatusReadOnly,
119 ProtoStatusCode::UCI_STATUS_COMMAND_RETRY => StatusCode::UciStatusCommandRetry,
120 ProtoStatusCode::UCI_STATUS_UNKNOWN => StatusCode::UciStatusUnknown,
121 ProtoStatusCode::UCI_STATUS_SESSION_NOT_EXIST => StatusCode::UciStatusSessionNotExist,
122 ProtoStatusCode::UCI_STATUS_SESSION_DUPLICATE => StatusCode::UciStatusSessionDuplicate,
123 ProtoStatusCode::UCI_STATUS_SESSION_ACTIVE => StatusCode::UciStatusSessionActive,
124 ProtoStatusCode::UCI_STATUS_MAX_SESSIONS_EXCEEDED => {
125 StatusCode::UciStatusMaxSessionsExceeded
126 }
127 ProtoStatusCode::UCI_STATUS_SESSION_NOT_CONFIGURED => {
128 StatusCode::UciStatusSessionNotConfigured
129 }
130 ProtoStatusCode::UCI_STATUS_ACTIVE_SESSIONS_ONGOING => {
131 StatusCode::UciStatusActiveSessionsOngoing
132 }
133 ProtoStatusCode::UCI_STATUS_MULTICAST_LIST_FULL => {
134 StatusCode::UciStatusMulticastListFull
135 }
136 ProtoStatusCode::UCI_STATUS_ADDRESS_NOT_FOUND => StatusCode::UciStatusAddressNotFound,
137 ProtoStatusCode::UCI_STATUS_ADDRESS_ALREADY_PRESENT => {
138 StatusCode::UciStatusAddressAlreadyPresent
139 }
140 ProtoStatusCode::UCI_STATUS_OK_NEGATIVE_DISTANCE_REPORT => {
141 StatusCode::UciStatusOkNegativeDistanceReport
142 }
143 ProtoStatusCode::UCI_STATUS_RANGING_TX_FAILED => StatusCode::UciStatusRangingTxFailed,
144 ProtoStatusCode::UCI_STATUS_RANGING_RX_TIMEOUT => {
145 StatusCode::UciStatusRangingRxTimeout
146 }
147 ProtoStatusCode::UCI_STATUS_RANGING_RX_PHY_DEC_FAILED => {
148 StatusCode::UciStatusRangingRxPhyDecFailed
149 }
150 ProtoStatusCode::UCI_STATUS_RANGING_RX_PHY_TOA_FAILED => {
151 StatusCode::UciStatusRangingRxPhyToaFailed
152 }
153 ProtoStatusCode::UCI_STATUS_RANGING_RX_PHY_STS_FAILED => {
154 StatusCode::UciStatusRangingRxPhyStsFailed
155 }
156 ProtoStatusCode::UCI_STATUS_RANGING_RX_MAC_DEC_FAILED => {
157 StatusCode::UciStatusRangingRxMacDecFailed
158 }
159 ProtoStatusCode::UCI_STATUS_RANGING_RX_MAC_IE_DEC_FAILED => {
160 StatusCode::UciStatusRangingRxMacIeDecFailed
161 }
162 ProtoStatusCode::UCI_STATUS_RANGING_RX_MAC_IE_MISSING => {
163 StatusCode::UciStatusRangingRxMacIeMissing
164 }
165 ProtoStatusCode::UCI_STATUS_ERROR_ROUND_INDEX_NOT_ACTIVATED => {
166 StatusCode::UciStatusErrorRoundIndexNotActivated
167 }
168 ProtoStatusCode::UCI_STATUS_ERROR_NUMBER_OF_ACTIVE_RANGING_ROUNDS_EXCEEDED => {
169 StatusCode::UciStatusErrorNumberOfActiveRangingRoundsExceeded
170 }
171 ProtoStatusCode::UCI_STATUS_ERROR_DL_TDOA_DEVICE_ADDRESS_NOT_MATCHING_IN_REPLY_TIME_LIST =>
172 StatusCode::UciStatusErrorDlTdoaDeviceAddressNotMatchingInReplyTimeList,
173 ProtoStatusCode::UCI_STATUS_DATA_MAX_TX_PSDU_SIZE_EXCEEDED => {
174 StatusCode::UciStatusDataMaxTxPsduSizeExceeded
175 }
176 ProtoStatusCode::UCI_STATUS_DATA_RX_CRC_ERROR => StatusCode::UciStatusDataRxCrcError,
177 ProtoStatusCode::UCI_STATUS_ERROR_CCC_SE_BUSY => StatusCode::UciStatusErrorCccSeBusy,
178 ProtoStatusCode::UCI_STATUS_ERROR_CCC_LIFECYCLE => {
179 StatusCode::UciStatusErrorCccLifecycle
180 }
181 ProtoStatusCode::UCI_STATUS_ERROR_STOPPED_DUE_TO_OTHER_SESSION_CONFLICT => {
182 StatusCode::UciStatusErrorStoppedDueToOtherSessionConflict
183 }
184 ProtoStatusCode::UCI_STATUS_REGULATION_UWB_OFF => StatusCode::UciStatusRegulationUwbOff,
185 _ => StatusCode::VendorSpecificStatusCode2,
186 }
187 }
188 }
189
190 impl From<StatusCode> for ProtoStatusCode {
from(item: StatusCode) -> Self191 fn from(item: StatusCode) -> Self {
192 match item {
193 StatusCode::UciStatusOk => ProtoStatusCode::UCI_STATUS_OK,
194 StatusCode::UciStatusRejected => ProtoStatusCode::UCI_STATUS_REJECTED,
195 StatusCode::UciStatusFailed => ProtoStatusCode::UCI_STATUS_FAILED,
196 StatusCode::UciStatusSyntaxError => ProtoStatusCode::UCI_STATUS_SYNTAX_ERROR,
197 StatusCode::UciStatusInvalidParam => ProtoStatusCode::UCI_STATUS_INVALID_PARAM,
198 StatusCode::UciStatusInvalidRange => ProtoStatusCode::UCI_STATUS_INVALID_RANGE,
199 StatusCode::UciStatusInvalidMsgSize => ProtoStatusCode::UCI_STATUS_INVALID_MSG_SIZE,
200 StatusCode::UciStatusUnknownGid => ProtoStatusCode::UCI_STATUS_UNKNOWN_GID,
201 StatusCode::UciStatusUnknownOid => ProtoStatusCode::UCI_STATUS_UNKNOWN_OID,
202 StatusCode::UciStatusReadOnly => ProtoStatusCode::UCI_STATUS_READ_ONLY,
203 StatusCode::UciStatusCommandRetry => ProtoStatusCode::UCI_STATUS_COMMAND_RETRY,
204 StatusCode::UciStatusUnknown => ProtoStatusCode::UCI_STATUS_UNKNOWN,
205 StatusCode::UciStatusSessionNotExist => ProtoStatusCode::UCI_STATUS_SESSION_NOT_EXIST,
206 StatusCode::UciStatusSessionDuplicate => ProtoStatusCode::UCI_STATUS_SESSION_DUPLICATE,
207 StatusCode::UciStatusSessionActive => ProtoStatusCode::UCI_STATUS_SESSION_ACTIVE,
208 StatusCode::UciStatusMaxSessionsExceeded => {
209 ProtoStatusCode::UCI_STATUS_MAX_SESSIONS_EXCEEDED
210 }
211 StatusCode::UciStatusSessionNotConfigured => {
212 ProtoStatusCode::UCI_STATUS_SESSION_NOT_CONFIGURED
213 }
214 StatusCode::UciStatusActiveSessionsOngoing => {
215 ProtoStatusCode::UCI_STATUS_ACTIVE_SESSIONS_ONGOING
216 }
217 StatusCode::UciStatusMulticastListFull => {
218 ProtoStatusCode::UCI_STATUS_MULTICAST_LIST_FULL
219 }
220 StatusCode::UciStatusAddressNotFound => {
221 ProtoStatusCode::UCI_STATUS_ADDRESS_NOT_FOUND
222 }
223 StatusCode::UciStatusAddressAlreadyPresent => {
224 ProtoStatusCode::UCI_STATUS_ADDRESS_ALREADY_PRESENT
225 }
226 StatusCode::UciStatusOkNegativeDistanceReport => {
227 ProtoStatusCode::UCI_STATUS_OK_NEGATIVE_DISTANCE_REPORT
228 }
229 StatusCode::UciStatusRangingTxFailed => {
230 ProtoStatusCode::UCI_STATUS_RANGING_TX_FAILED
231 }
232 StatusCode::UciStatusRangingRxTimeout => {
233 ProtoStatusCode::UCI_STATUS_RANGING_RX_TIMEOUT
234 }
235 StatusCode::UciStatusRangingRxPhyDecFailed => {
236 ProtoStatusCode::UCI_STATUS_RANGING_RX_PHY_DEC_FAILED
237 }
238 StatusCode::UciStatusRangingRxPhyToaFailed => {
239 ProtoStatusCode::UCI_STATUS_RANGING_RX_PHY_TOA_FAILED
240 }
241 StatusCode::UciStatusRangingRxPhyStsFailed => {
242 ProtoStatusCode::UCI_STATUS_RANGING_RX_PHY_STS_FAILED
243 }
244 StatusCode::UciStatusRangingRxMacDecFailed => {
245 ProtoStatusCode::UCI_STATUS_RANGING_RX_MAC_DEC_FAILED
246 }
247 StatusCode::UciStatusRangingRxMacIeDecFailed => {
248 ProtoStatusCode::UCI_STATUS_RANGING_RX_MAC_IE_DEC_FAILED
249 }
250 StatusCode::UciStatusRangingRxMacIeMissing => {
251 ProtoStatusCode::UCI_STATUS_RANGING_RX_MAC_IE_MISSING
252 }
253 StatusCode::UciStatusErrorRoundIndexNotActivated => {
254 ProtoStatusCode::UCI_STATUS_ERROR_ROUND_INDEX_NOT_ACTIVATED
255 }
256 StatusCode::UciStatusErrorNumberOfActiveRangingRoundsExceeded => {
257 ProtoStatusCode::UCI_STATUS_ERROR_NUMBER_OF_ACTIVE_RANGING_ROUNDS_EXCEEDED
258 }
259 StatusCode::UciStatusErrorDlTdoaDeviceAddressNotMatchingInReplyTimeList => {
260 ProtoStatusCode::UCI_STATUS_ERROR_DL_TDOA_DEVICE_ADDRESS_NOT_MATCHING_IN_REPLY_TIME_LIST
261 }
262 StatusCode::UciStatusDataMaxTxPsduSizeExceeded => {
263 ProtoStatusCode::UCI_STATUS_DATA_MAX_TX_PSDU_SIZE_EXCEEDED
264 }
265 StatusCode::UciStatusDataRxCrcError => {
266 ProtoStatusCode::UCI_STATUS_DATA_RX_CRC_ERROR
267 }
268 StatusCode::UciStatusErrorCccSeBusy => {
269 ProtoStatusCode::UCI_STATUS_ERROR_CCC_SE_BUSY
270 }
271 StatusCode::UciStatusErrorCccLifecycle => {
272 ProtoStatusCode::UCI_STATUS_ERROR_CCC_LIFECYCLE
273 }
274 StatusCode::UciStatusErrorStoppedDueToOtherSessionConflict => {
275 ProtoStatusCode::UCI_STATUS_ERROR_STOPPED_DUE_TO_OTHER_SESSION_CONFLICT
276 }
277 StatusCode::UciStatusRegulationUwbOff => {
278 ProtoStatusCode::UCI_STATUS_REGULATION_UWB_OFF
279 }
280 _ => ProtoStatusCode::UCI_STATUS_RFU_OR_VENDOR_SPECIFIC,
281 }
282 }
283 }
284
285 enum_mapping! {
286 ProtoDeviceState => DeviceState,
287 DEVICE_STATE_READY => DeviceStateReady,
288 DEVICE_STATE_ACTIVE => DeviceStateActive,
289 DEVICE_STATE_ERROR => DeviceStateError,
290 }
291
292 enum_mapping! {
293 ProtoSessionState => SessionState,
294 INIT => SessionStateInit,
295 DEINIT => SessionStateDeinit,
296 ACTIVE => SessionStateActive,
297 IDLE => SessionStateIdle,
298 }
299
300 impl From<ProtoReasonCode> for ReasonCode {
from(item: ProtoReasonCode) -> Self301 fn from(item: ProtoReasonCode) -> Self {
302 match item {
303 ProtoReasonCode::STATE_CHANGE_WITH_SESSION_MANAGEMENT_COMMANDS => {
304 ReasonCode::StateChangeWithSessionManagementCommands
305 }
306 ProtoReasonCode::MAX_RANGING_ROUND_RETRY_COUNT_REACHED => {
307 ReasonCode::MaxRangingRoundRetryCountReached
308 }
309 ProtoReasonCode::MAX_NUMBER_OF_MEASUREMENTS_REACHED => {
310 ReasonCode::MaxNumberOfMeasurementsReached
311 }
312 ProtoReasonCode::SESSION_SUSPENDED_DUE_TO_INBAND_SIGNAL => {
313 ReasonCode::SessionSuspendedDueToInbandSignal
314 }
315 ProtoReasonCode::SESSION_RESUMED_DUE_TO_INBAND_SIGNAL => {
316 ReasonCode::SessionResumedDueToInbandSignal
317 }
318 ProtoReasonCode::SESSION_STOPPED_DUE_TO_INBAND_SIGNAL => {
319 ReasonCode::SessionStoppedDueToInbandSignal
320 }
321 ProtoReasonCode::ERROR_INVALID_UL_TDOA_RANDOM_WINDOW => {
322 ReasonCode::ErrorInvalidUlTdoaRandomWindow
323 }
324 ProtoReasonCode::ERROR_MIN_RFRAMES_PER_RR_NOT_SUPPORTED => {
325 ReasonCode::ErrorMinRframesPerRrNotSupported
326 }
327 ProtoReasonCode::ERROR_INTER_FRAME_INTERVAL_NOT_SUPPORTED => {
328 ReasonCode::ErrorInterFrameIntervalNotSupported
329 }
330 ProtoReasonCode::ERROR_SLOT_LENGTH_NOT_SUPPORTED => {
331 ReasonCode::ErrorSlotLengthNotSupported
332 }
333 ProtoReasonCode::ERROR_INSUFFICIENT_SLOTS_PER_RR => {
334 ReasonCode::ErrorInsufficientSlotsPerRr
335 }
336 ProtoReasonCode::ERROR_MAC_ADDRESS_MODE_NOT_SUPPORTED => {
337 ReasonCode::ErrorMacAddressModeNotSupported
338 }
339 ProtoReasonCode::ERROR_INVALID_RANGING_DURATION => {
340 ReasonCode::ErrorInvalidRangingDuration
341 }
342 ProtoReasonCode::ERROR_INVALID_STS_CONFIG => ReasonCode::ErrorInvalidStsConfig,
343 ProtoReasonCode::ERROR_INVALID_RFRAME_CONFIG => ReasonCode::ErrorInvalidRframeConfig,
344 ProtoReasonCode::ERROR_HUS_NOT_ENOUGH_SLOTS => ReasonCode::ErrorHusNotEnoughSlots,
345 ProtoReasonCode::ERROR_HUS_CFP_PHASE_TOO_SHORT => ReasonCode::ErrorHusCfpPhaseTooShort,
346 ProtoReasonCode::ERROR_HUS_CAP_PHASE_TOO_SHORT => ReasonCode::ErrorHusCapPhaseTooShort,
347 ProtoReasonCode::ERROR_HUS_OTHERS => ReasonCode::ErrorHusOthers,
348 ProtoReasonCode::ERROR_STATUS_SESSION_KEY_NOT_FOUND => {
349 ReasonCode::ErrorStatusSessionKeyNotFound
350 }
351 ProtoReasonCode::ERROR_STATUS_SUB_SESSION_KEY_NOT_FOUND => {
352 ReasonCode::ErrorStatusSubSessionKeyNotFound
353 }
354 ProtoReasonCode::ERROR_INVALID_PREAMBLE_CODE_INDEX => {
355 ReasonCode::ErrorInvalidPreambleCodeIndex
356 }
357 ProtoReasonCode::ERROR_INVALID_SFD_ID => ReasonCode::ErrorInvalidSfdId,
358 ProtoReasonCode::ERROR_INVALID_PSDU_DATA_RATE => ReasonCode::ErrorInvalidPsduDataRate,
359 ProtoReasonCode::ERROR_INVALID_PHR_DATA_RATE => ReasonCode::ErrorInvalidPhrDataRate,
360 ProtoReasonCode::ERROR_INVALID_PREAMBLE_DURATION => {
361 ReasonCode::ErrorInvalidPreambleDuration
362 }
363 ProtoReasonCode::ERROR_INVALID_STS_LENGTH => ReasonCode::ErrorInvalidStsLength,
364 ProtoReasonCode::ERROR_INVALID_NUM_OF_STS_SEGMENTS => {
365 ReasonCode::ErrorInvalidNumOfStsSegments
366 }
367 ProtoReasonCode::ERROR_INVALID_NUM_OF_CONTROLEES => {
368 ReasonCode::ErrorInvalidNumOfControlees
369 }
370 ProtoReasonCode::ERROR_MAX_RANGING_REPLY_TIME_EXCEEDED => {
371 ReasonCode::ErrorMaxRangingReplyTimeExceeded
372 }
373 ProtoReasonCode::ERROR_INVALID_DST_ADDRESS_LIST => {
374 ReasonCode::ErrorInvalidDstAddressList
375 }
376 ProtoReasonCode::ERROR_INVALID_OR_NOT_FOUND_SUB_SESSION_ID => {
377 ReasonCode::ErrorInvalidOrNotFoundSubSessionId
378 }
379 ProtoReasonCode::ERROR_INVALID_RESULT_REPORT_CONFIG => {
380 ReasonCode::ErrorInvalidResultReportConfig
381 }
382 ProtoReasonCode::ERROR_INVALID_RANGING_ROUND_USAGE => {
383 ReasonCode::ErrorInvalidRangingRoundUsage
384 }
385 ProtoReasonCode::ERROR_INVALID_MULTI_NODE_MODE => ReasonCode::ErrorInvalidMultiNodeMode,
386 ProtoReasonCode::ERROR_RDS_FETCH_FAILURE => ReasonCode::ErrorRdsFetchFailure,
387 ProtoReasonCode::ERROR_REF_UWB_SESSION_DOES_NOT_EXIST => {
388 ReasonCode::ErrorRefUwbSessionDoesNotExist
389 }
390 ProtoReasonCode::ERROR_REF_UWB_SESSION_RANGING_DURATION_MISMATCH => {
391 ReasonCode::ErrorRefUwbSessionRangingDurationMismatch
392 }
393 ProtoReasonCode::ERROR_REF_UWB_SESSION_INVALID_OFFSET_TIME => {
394 ReasonCode::ErrorRefUwbSessionInvalidOffsetTime
395 }
396 ProtoReasonCode::ERROR_REF_UWB_SESSION_LOST => ReasonCode::ErrorRefUwbSessionLost,
397 ProtoReasonCode::ERROR_INVALID_CHANNEL_WITH_AOA => {
398 ReasonCode::ErrorInvalidChannelWithAoa
399 }
400 ProtoReasonCode::ERROR_STOPPED_DUE_TO_OTHER_SESSION_CONFLICT => {
401 ReasonCode::ErrorStoppedDueToOtherSessionConflict
402 }
403 ProtoReasonCode::SESSION_STOPPED_DUE_TO_MAX_STS_INDEX_VALUE => {
404 ReasonCode::SessionStoppedDueToMaxStsIndexValue
405 }
406 _ => ReasonCode::VendorSpecificReasonCode2,
407 }
408 }
409 }
410
411 impl From<ReasonCode> for ProtoReasonCode {
from(item: ReasonCode) -> Self412 fn from(item: ReasonCode) -> Self {
413 match item {
414 ReasonCode::StateChangeWithSessionManagementCommands => {
415 ProtoReasonCode::STATE_CHANGE_WITH_SESSION_MANAGEMENT_COMMANDS
416 }
417 ReasonCode::MaxRangingRoundRetryCountReached => {
418 ProtoReasonCode::MAX_RANGING_ROUND_RETRY_COUNT_REACHED
419 }
420 ReasonCode::MaxNumberOfMeasurementsReached => {
421 ProtoReasonCode::MAX_NUMBER_OF_MEASUREMENTS_REACHED
422 }
423 ReasonCode::SessionSuspendedDueToInbandSignal => {
424 ProtoReasonCode::SESSION_SUSPENDED_DUE_TO_INBAND_SIGNAL
425 }
426 ReasonCode::SessionResumedDueToInbandSignal => {
427 ProtoReasonCode::SESSION_RESUMED_DUE_TO_INBAND_SIGNAL
428 }
429 ReasonCode::SessionStoppedDueToInbandSignal => {
430 ProtoReasonCode::SESSION_STOPPED_DUE_TO_INBAND_SIGNAL
431 }
432 ReasonCode::ErrorInvalidUlTdoaRandomWindow => {
433 ProtoReasonCode::ERROR_INVALID_UL_TDOA_RANDOM_WINDOW
434 }
435 ReasonCode::ErrorMinRframesPerRrNotSupported => {
436 ProtoReasonCode::ERROR_MIN_RFRAMES_PER_RR_NOT_SUPPORTED
437 }
438 ReasonCode::ErrorInterFrameIntervalNotSupported => {
439 ProtoReasonCode::ERROR_INTER_FRAME_INTERVAL_NOT_SUPPORTED
440 }
441 ReasonCode::ErrorSlotLengthNotSupported => {
442 ProtoReasonCode::ERROR_SLOT_LENGTH_NOT_SUPPORTED
443 }
444 ReasonCode::ErrorInsufficientSlotsPerRr => {
445 ProtoReasonCode::ERROR_INSUFFICIENT_SLOTS_PER_RR
446 }
447 ReasonCode::ErrorMacAddressModeNotSupported => {
448 ProtoReasonCode::ERROR_MAC_ADDRESS_MODE_NOT_SUPPORTED
449 }
450 ReasonCode::ErrorInvalidRangingDuration => {
451 ProtoReasonCode::ERROR_INVALID_RANGING_DURATION
452 }
453 ReasonCode::ErrorInvalidStsConfig => ProtoReasonCode::ERROR_INVALID_STS_CONFIG,
454 ReasonCode::ErrorInvalidRframeConfig => ProtoReasonCode::ERROR_INVALID_RFRAME_CONFIG,
455 ReasonCode::ErrorHusNotEnoughSlots => ProtoReasonCode::ERROR_HUS_NOT_ENOUGH_SLOTS,
456 ReasonCode::ErrorHusCfpPhaseTooShort => ProtoReasonCode::ERROR_HUS_CFP_PHASE_TOO_SHORT,
457 ReasonCode::ErrorHusCapPhaseTooShort => ProtoReasonCode::ERROR_HUS_CAP_PHASE_TOO_SHORT,
458 ReasonCode::ErrorHusOthers => ProtoReasonCode::ERROR_HUS_OTHERS,
459 ReasonCode::ErrorStatusSessionKeyNotFound => {
460 ProtoReasonCode::ERROR_STATUS_SESSION_KEY_NOT_FOUND
461 }
462 ReasonCode::ErrorStatusSubSessionKeyNotFound => {
463 ProtoReasonCode::ERROR_STATUS_SUB_SESSION_KEY_NOT_FOUND
464 }
465 ReasonCode::ErrorInvalidPreambleCodeIndex => {
466 ProtoReasonCode::ERROR_INVALID_PREAMBLE_CODE_INDEX
467 }
468 ReasonCode::ErrorInvalidSfdId => ProtoReasonCode::ERROR_INVALID_SFD_ID,
469 ReasonCode::ErrorInvalidPsduDataRate => ProtoReasonCode::ERROR_INVALID_PSDU_DATA_RATE,
470 ReasonCode::ErrorInvalidPhrDataRate => ProtoReasonCode::ERROR_INVALID_PHR_DATA_RATE,
471 ReasonCode::ErrorInvalidPreambleDuration => {
472 ProtoReasonCode::ERROR_INVALID_PREAMBLE_DURATION
473 }
474 ReasonCode::ErrorInvalidStsLength => ProtoReasonCode::ERROR_INVALID_STS_LENGTH,
475 ReasonCode::ErrorInvalidNumOfStsSegments => {
476 ProtoReasonCode::ERROR_INVALID_NUM_OF_STS_SEGMENTS
477 }
478 ReasonCode::ErrorInvalidNumOfControlees => {
479 ProtoReasonCode::ERROR_INVALID_NUM_OF_CONTROLEES
480 }
481 ReasonCode::ErrorMaxRangingReplyTimeExceeded => {
482 ProtoReasonCode::ERROR_MAX_RANGING_REPLY_TIME_EXCEEDED
483 }
484 ReasonCode::ErrorInvalidDstAddressList => {
485 ProtoReasonCode::ERROR_INVALID_DST_ADDRESS_LIST
486 }
487 ReasonCode::ErrorInvalidOrNotFoundSubSessionId => {
488 ProtoReasonCode::ERROR_INVALID_OR_NOT_FOUND_SUB_SESSION_ID
489 }
490 ReasonCode::ErrorInvalidResultReportConfig => {
491 ProtoReasonCode::ERROR_INVALID_RESULT_REPORT_CONFIG
492 }
493 ReasonCode::ErrorInvalidRangingRoundUsage => {
494 ProtoReasonCode::ERROR_INVALID_RANGING_ROUND_USAGE
495 }
496 ReasonCode::ErrorInvalidMultiNodeMode => ProtoReasonCode::ERROR_INVALID_MULTI_NODE_MODE,
497 ReasonCode::ErrorRdsFetchFailure => ProtoReasonCode::ERROR_RDS_FETCH_FAILURE,
498 ReasonCode::ErrorRefUwbSessionDoesNotExist => {
499 ProtoReasonCode::ERROR_REF_UWB_SESSION_DOES_NOT_EXIST
500 }
501 ReasonCode::ErrorRefUwbSessionRangingDurationMismatch => {
502 ProtoReasonCode::ERROR_REF_UWB_SESSION_RANGING_DURATION_MISMATCH
503 }
504 ReasonCode::ErrorRefUwbSessionInvalidOffsetTime => {
505 ProtoReasonCode::ERROR_REF_UWB_SESSION_INVALID_OFFSET_TIME
506 }
507 ReasonCode::ErrorRefUwbSessionLost => ProtoReasonCode::ERROR_REF_UWB_SESSION_LOST,
508 ReasonCode::ErrorInvalidChannelWithAoa => {
509 ProtoReasonCode::ERROR_INVALID_CHANNEL_WITH_AOA
510 }
511 ReasonCode::ErrorStoppedDueToOtherSessionConflict => {
512 ProtoReasonCode::ERROR_STOPPED_DUE_TO_OTHER_SESSION_CONFLICT
513 }
514 ReasonCode::ErrorDtAnchorRangingRoundsNotConfigured => {
515 ProtoReasonCode::ERROR_DT_ANCHOR_RANGING_ROUNDS_NOT_CONFIGURED
516 }
517 ReasonCode::ErrorDtTagRangingRoundsNotConfigured => {
518 ProtoReasonCode::ERROR_DT_TAG_RANGING_ROUNDS_NOT_CONFIGURED
519 }
520 _ => ProtoReasonCode::ERROR_RFU_OR_VENDOR_SPECIFIC,
521 }
522 }
523 }
524
525 enum_mapping! {
526 ProtoUciLoggerMode => UciLoggerMode,
527 UCI_LOGGER_MODE_DISABLED => Disabled,
528 UCI_LOGGER_MODE_UNFILTERED => Unfiltered,
529 UCI_LOGGER_MODE_FILTERED => Filtered,
530 }
531
532 enum_mapping! {
533 ProtoRangingMeasurementType => RangingMeasurementType,
534 ONE_WAY => OneWay,
535 TWO_WAY => TwoWay,
536 DL_TDOA => DlTdoa,
537 OWR_AOA => OwrAoa,
538 }
539
540 enum_mapping! {
541 ProtoSessionType => SessionType,
542 FIRA_RANGING_SESSION => FiraRangingSession,
543 FIRA_DATA_TRANSFER => FiraDataTransferSession,
544 FIRA_RANGING_AND_IN_BAND_DATA_SESSION => FiraRangingAndInBandDataSession,
545 FIRA_RANGING_ONLY_PHASE => FiraRangingOnlyPhase,
546 FIRA_IN_BAND_DATA_PHASE => FiraInBandDataPhase,
547 FIRA_RANGING_WITH_DATA_PHASE => FiraRangingWithDataPhase,
548 FIRA_HUS_PRIMARY_SESSION => FiraHusPrimarySession,
549 CCC => Ccc,
550 RADAR_SESSION => RadarSession,
551 ALIRO => Aliro,
552 DEVICE_TEST_MODE => DeviceTestMode,
553 }
554
555 enum_mapping! {
556 ProtoDeviceType => DeviceType,
557 CONTROLEE => Controlee,
558 CONTROLLER => Controller,
559 }
560
561 enum_mapping! {
562 ProtoRangingRoundUsage => RangingRoundUsage,
563 SS_TWR => SsTwr,
564 DS_TWR => DsTwr,
565 SS_TWR_NON => SsTwrNon,
566 DS_TWR_NON => DsTwrNon,
567 }
568
569 enum_mapping! {
570 ProtoStsConfig => StsConfig,
571 STATIC => Static,
572 DYNAMIC => Dynamic,
573 DYNAMIC_FOR_CONTROLEE_INDIVIDUAL_KEY => DynamicForControleeIndividualKey,
574 }
575
576 enum_mapping! {
577 ProtoMultiNodeMode => MultiNodeMode,
578 UNICAST => Unicast,
579 ONE_TO_MANY => OneToMany,
580 MANY_TO_MANY => ManyToMany,
581 }
582
583 enum_mapping! {
584 ProtoUwbChannel => UwbChannel,
585 CHANNEL_5 => Channel5,
586 CHANNEL_6 => Channel6,
587 CHANNEL_8 => Channel8,
588 CHANNEL_9 => Channel9,
589 CHANNEL_10 => Channel10,
590 CHANNEL_12 => Channel12,
591 CHANNEL_13 => Channel13,
592 CHANNEL_14 => Channel14,
593 }
594
595 enum_mapping! {
596 ProtoMacFcsType => MacFcsType,
597 CRC_16 => Crc16,
598 CRC_32 => Crc32,
599 }
600
601 enum_mapping! {
602 ProtoAoaResultRequest => AoaResultRequest,
603 NO_AOA_REPORT => NoAoaReport,
604 REQ_AOA_RESULTS => ReqAoaResults,
605 REQ_AOA_RESULTS_AZIMUTH_ONLY => ReqAoaResultsAzimuthOnly,
606 REQ_AOA_RESULTS_ELEVATION_ONLY => ReqAoaResultsElevationOnly,
607 REQ_AOA_RESULTS_INTERLEAVED => ReqAoaResultsInterleaved,
608 }
609
610 enum_mapping! {
611 ProtoRangeDataNtfConfig => RangeDataNtfConfig,
612 RANGE_DATA_NTF_CONFIG_DISABLE => Disable,
613 RANGE_DATA_NTF_CONFIG_ENABLE => Enable,
614 RANGE_DATA_NTF_CONFIG_ENABLE_PROXIMITY => EnableProximity,
615 }
616
617 enum_mapping! {
618 ProtoDeviceRole => DeviceRole,
619 RESPONDER => Responder,
620 INITIATOR => Initiator,
621 }
622
623 enum_mapping! {
624 ProtoRframeConfig => RframeConfig,
625 SP0 => SP0,
626 SP1 => SP1,
627 SP3 => SP3,
628 }
629
630 enum_mapping! {
631 ProtoPsduDataRate => PsduDataRate,
632 RATE_6M_81 => Rate6m81,
633 RATE_7M_80 => Rate7m80,
634 RATE_27M_2 => Rate27m2,
635 RATE_31M_2 => Rate31m2,
636 RATE_850K => Rate850k,
637 }
638
639 enum_mapping! {
640 ProtoPreambleDuration => PreambleDuration,
641 T32_SYMBOLS => T32Symbols,
642 T64_SYMBOLS => T64Symbols,
643 }
644
645 enum_mapping! {
646 ProtoRangingTimeStruct => RangingTimeStruct,
647 INTERVAL_BASED_SCHEDULING => IntervalBasedScheduling,
648 BLOCK_BASED_SCHEDULING => BlockBasedScheduling,
649 }
650
651 enum_mapping! {
652 ProtoTxAdaptivePayloadPower => TxAdaptivePayloadPower,
653 TX_ADAPTIVE_PAYLOAD_POWER_DISABLE => Disable,
654 TX_ADAPTIVE_PAYLOAD_POWER_ENABLE => Enable,
655 }
656
657 enum_mapping! {
658 ProtoPrfMode => PrfMode,
659 BPRF => Bprf,
660 HPRF_WITH_124_8_MHZ => HprfWith124_8MHz,
661 HPRF_WITH_249_6_MHZ => HprfWith249_6MHz,
662 }
663
664 enum_mapping! {
665 ProtoScheduledMode => ScheduledMode,
666 TIME_SCHEDULED_RANGING => TimeScheduledRanging,
667 }
668
669 enum_mapping! {
670 ProtoKeyRotation => KeyRotation,
671 KEY_ROTATION_DISABLE => Disable,
672 KEY_ROTATION_ENABLE => Enable,
673 }
674
675 enum_mapping! {
676 ProtoMacAddressMode => MacAddressMode,
677 MAC_ADDRESS_2_BYTES => MacAddress2Bytes,
678 MAC_ADDRESS_8_BYTES_2_BYTES_HEADER => MacAddress8Bytes2BytesHeader,
679 MAC_ADDRESS_8_BYTES => MacAddress8Bytes,
680 }
681
682 enum_mapping! {
683 ProtoHoppingMode => HoppingMode,
684 HOPPING_MODE_DISABLE => Disable,
685 FIRA_HOPPING_ENABLE => FiraHoppingEnable,
686 }
687
688 enum_mapping! {
689 ProtoBprfPhrDataRate => BprfPhrDataRate,
690 BPRF_PHR_DATA_RATE_850K => Rate850k,
691 BPRF_PHR_DATA_RATE_6M_81 => Rate6m81,
692 }
693
694 enum_mapping! {
695 ProtoStsLength => StsLength,
696 LENGTH_32 => Length32,
697 LENGTH_64 => Length64,
698 LENGTH_128 => Length128,
699 }
700
701 enum_mapping! {
702 ProtoUpdateMulticastListAction => UpdateMulticastListAction,
703 ADD_CONTROLEE => AddControlee,
704 REMOVE_CONTROLEE => RemoveControlee,
705 ADD_CONTROLEE_WITH_SHORT_SUB_SESSION_KEY => AddControleeWithShortSubSessionKey,
706 ADD_CONTROLEE_WITH_LONG_SUB_SESSION_KEY => AddControleeWithLongSubSessionKey,
707 }
708
709 enum_mapping! {
710 ProtoMacAddressIndicator => MacAddressIndicator,
711 SHORT_ADDRESS => ShortAddress,
712 EXTENDED_ADDRESS => ExtendedAddress,
713 }
714
715 pub enum ProtoRangingMeasurements {
716 TwoWay(Vec<ProtoTwoWayRangingMeasurement>),
717 OwrAoa(ProtoOwrAoaRangingMeasurement),
718 DlTDoa(Vec<ProtoDlTDoARangingMeasurement>),
719 }
720
721 impl<T> From<Result<T>> for ProtoStatus {
from(item: Result<T>) -> Self722 fn from(item: Result<T>) -> Self {
723 match item {
724 Ok(_) => Self::OK,
725 Err(Error::BadParameters) => Self::BAD_PARAMETERS,
726 Err(Error::MaxSessionsExceeded) => Self::MAX_SESSIONS_EXCEEDED,
727 Err(Error::MaxRrRetryReached) => Self::MAX_RR_RETRY_REACHED,
728 Err(Error::ProtocolSpecific) => Self::PROTOCOL_SPECIFIC,
729 Err(Error::RemoteRequest) => Self::REMOTE_REQUEST,
730 Err(Error::Timeout) => Self::TIMEOUT,
731 Err(Error::CommandRetry) => Self::COMMAND_RETRY,
732 Err(Error::DuplicatedSessionId) => Self::DUPLICATED_SESSION_ID,
733 Err(Error::RegulationUwbOff) => Self::REGULATION_UWB_OFF,
734 Err(_) => Self::UNKNOWN,
735 }
736 }
737 }
738
739 impl From<ShortAddressTwoWayRangingMeasurement> for ProtoTwoWayRangingMeasurement {
from(item: ShortAddressTwoWayRangingMeasurement) -> Self740 fn from(item: ShortAddressTwoWayRangingMeasurement) -> Self {
741 let mut result = Self::new();
742 result.mac_address = item.mac_address.into();
743 result.status = EnumOrUnknown::new(item.status.into());
744 result.nlos = item.nlos.into();
745 result.distance = item.distance.into();
746 result.aoa_azimuth = item.aoa_azimuth.into();
747 result.aoa_azimuth_fom = item.aoa_azimuth_fom.into();
748 result.aoa_elevation = item.aoa_elevation.into();
749 result.aoa_elevation_fom = item.aoa_elevation_fom.into();
750 result.aoa_destination_azimuth = item.aoa_destination_azimuth.into();
751 result.aoa_destination_azimuth_fom = item.aoa_destination_azimuth_fom.into();
752 result.aoa_destination_elevation = item.aoa_destination_elevation.into();
753 result.aoa_destination_elevation_fom = item.aoa_destination_elevation_fom.into();
754 result.slot_index = item.slot_index.into();
755 result.rssi = item.rssi.into();
756 result
757 }
758 }
759
760 impl From<ExtendedAddressTwoWayRangingMeasurement> for ProtoTwoWayRangingMeasurement {
from(item: ExtendedAddressTwoWayRangingMeasurement) -> Self761 fn from(item: ExtendedAddressTwoWayRangingMeasurement) -> Self {
762 let mut result = Self::new();
763 result.mac_address = item.mac_address;
764 result.status = EnumOrUnknown::new(item.status.into());
765 result.nlos = item.nlos.into();
766 result.distance = item.distance.into();
767 result.aoa_azimuth = item.aoa_azimuth.into();
768 result.aoa_azimuth_fom = item.aoa_azimuth_fom.into();
769 result.aoa_elevation = item.aoa_elevation.into();
770 result.aoa_elevation_fom = item.aoa_elevation_fom.into();
771 result.aoa_destination_azimuth = item.aoa_destination_azimuth.into();
772 result.aoa_destination_azimuth_fom = item.aoa_destination_azimuth_fom.into();
773 result.aoa_destination_elevation = item.aoa_destination_elevation.into();
774 result.aoa_destination_elevation_fom = item.aoa_destination_elevation_fom.into();
775 result.slot_index = item.slot_index.into();
776 result.rssi = item.rssi.into();
777 result
778 }
779 }
780
781 impl From<ShortAddressOwrAoaRangingMeasurement> for ProtoOwrAoaRangingMeasurement {
from(item: ShortAddressOwrAoaRangingMeasurement) -> Self782 fn from(item: ShortAddressOwrAoaRangingMeasurement) -> Self {
783 let mut result = Self::new();
784 result.mac_address = item.mac_address.into();
785 result.status = EnumOrUnknown::new(item.status.into());
786 result.nlos = item.nlos.into();
787 result.block_index = item.block_index.into();
788 result.frame_sequence_number = item.frame_sequence_number.into();
789 result.aoa_azimuth = item.aoa_azimuth.into();
790 result.aoa_azimuth_fom = item.aoa_azimuth_fom.into();
791 result.aoa_elevation = item.aoa_elevation.into();
792 result.aoa_elevation_fom = item.aoa_elevation_fom.into();
793 result
794 }
795 }
796
797 impl From<ExtendedAddressOwrAoaRangingMeasurement> for ProtoOwrAoaRangingMeasurement {
from(item: ExtendedAddressOwrAoaRangingMeasurement) -> Self798 fn from(item: ExtendedAddressOwrAoaRangingMeasurement) -> Self {
799 let mut result = Self::new();
800 result.mac_address = item.mac_address;
801 result.status = EnumOrUnknown::new(item.status.into());
802 result.nlos = item.nlos.into();
803 result.block_index = item.block_index.into();
804 result.frame_sequence_number = item.frame_sequence_number.into();
805 result.aoa_azimuth = item.aoa_azimuth.into();
806 result.aoa_azimuth_fom = item.aoa_azimuth_fom.into();
807 result.aoa_elevation = item.aoa_elevation.into();
808 result.aoa_elevation_fom = item.aoa_elevation_fom.into();
809 result
810 }
811 }
812
813 impl From<ShortAddressDlTdoaRangingMeasurement> for ProtoDlTDoARangingMeasurement {
from(item: ShortAddressDlTdoaRangingMeasurement) -> Self814 fn from(item: ShortAddressDlTdoaRangingMeasurement) -> Self {
815 let mut result = Self::new();
816 result.mac_address = item.mac_address.into();
817 result.status = EnumOrUnknown::new(
818 StatusCode::try_from(item.measurement.status)
819 .unwrap_or(StatusCode::UciStatusFailed)
820 .into(),
821 );
822 result.message_control = item.measurement.message_control.into();
823 result.block_index = item.measurement.block_index.into();
824 result.round_index = item.measurement.round_index.into();
825 result.nlos = item.measurement.nlos.into();
826 result.aoa_azimuth = item.measurement.aoa_azimuth.into();
827 result.aoa_azimuth_fom = item.measurement.aoa_azimuth_fom.into();
828 result.aoa_elevation = item.measurement.aoa_elevation.into();
829 result.aoa_elevation_fom = item.measurement.aoa_elevation_fom.into();
830 result.rssi = item.measurement.rssi.into();
831 result.tx_timestamp = item.measurement.tx_timestamp;
832 result.rx_timestamp = item.measurement.rx_timestamp;
833 result.anchor_cfo = item.measurement.anchor_cfo.into();
834 result.cfo = item.measurement.cfo.into();
835 result.initiator_reply_time = item.measurement.initiator_reply_time;
836 result.responder_reply_time = item.measurement.responder_reply_time;
837 result.initiator_responder_tof = item.measurement.initiator_responder_tof.into();
838 result.dt_anchor_location = item
839 .measurement
840 .dt_anchor_location
841 .into_iter()
842 .map(|val| val as u32)
843 .collect::<Vec<u32>>();
844 result.ranging_rounds =
845 item.measurement.ranging_rounds.into_iter().map(|val| val as u32).collect::<Vec<u32>>();
846 result
847 }
848 }
849
850 impl From<ExtendedAddressDlTdoaRangingMeasurement> for ProtoDlTDoARangingMeasurement {
from(item: ExtendedAddressDlTdoaRangingMeasurement) -> Self851 fn from(item: ExtendedAddressDlTdoaRangingMeasurement) -> Self {
852 let mut result = Self::new();
853 result.mac_address = item.mac_address;
854 result.status = EnumOrUnknown::new(
855 StatusCode::try_from(item.measurement.status)
856 .unwrap_or(StatusCode::UciStatusFailed)
857 .into(),
858 );
859 result.message_control = item.measurement.message_control.into();
860 result.block_index = item.measurement.block_index.into();
861 result.round_index = item.measurement.round_index.into();
862 result.nlos = item.measurement.nlos.into();
863 result.aoa_azimuth = item.measurement.aoa_azimuth.into();
864 result.aoa_azimuth_fom = item.measurement.aoa_azimuth_fom.into();
865 result.aoa_elevation = item.measurement.aoa_elevation.into();
866 result.aoa_elevation_fom = item.measurement.aoa_elevation_fom.into();
867 result.rssi = item.measurement.rssi.into();
868 result.tx_timestamp = item.measurement.tx_timestamp;
869 result.rx_timestamp = item.measurement.rx_timestamp;
870 result.anchor_cfo = item.measurement.anchor_cfo.into();
871 result.cfo = item.measurement.cfo.into();
872 result.initiator_reply_time = item.measurement.initiator_reply_time;
873 result.responder_reply_time = item.measurement.responder_reply_time;
874 result.initiator_responder_tof = item.measurement.initiator_responder_tof.into();
875 result.dt_anchor_location = item
876 .measurement
877 .dt_anchor_location
878 .into_iter()
879 .map(|val| val as u32)
880 .collect::<Vec<u32>>();
881 result.ranging_rounds =
882 item.measurement.ranging_rounds.into_iter().map(|val| val as u32).collect::<Vec<u32>>();
883 result
884 }
885 }
886
887 impl From<SessionRangeData> for ProtoSessionRangeData {
from(item: SessionRangeData) -> Self888 fn from(item: SessionRangeData) -> Self {
889 let mut result = Self::new();
890 result.sequence_number = item.sequence_number;
891 result.session_id = item.session_token;
892 result.current_ranging_interval_ms = item.current_ranging_interval_ms;
893 result.ranging_measurement_type = EnumOrUnknown::new(item.ranging_measurement_type.into());
894 match to_proto_ranging_measurements(item.ranging_measurements) {
895 ProtoRangingMeasurements::TwoWay(twoway_measurements) => {
896 result.twoway_ranging_measurements = twoway_measurements;
897 }
898 ProtoRangingMeasurements::OwrAoa(owraoa_measurement) => {
899 result.owraoa_ranging_measurement = MessageField::from(Some(owraoa_measurement));
900 }
901 ProtoRangingMeasurements::DlTDoa(dltdoa_measurements) => {
902 result.dltdoa_ranging_measurements = dltdoa_measurements;
903 }
904 }
905 result
906 }
907 }
908
to_proto_ranging_measurements(item: RangingMeasurements) -> ProtoRangingMeasurements909 fn to_proto_ranging_measurements(item: RangingMeasurements) -> ProtoRangingMeasurements {
910 match item {
911 RangingMeasurements::ShortAddressTwoWay(arr) => {
912 ProtoRangingMeasurements::TwoWay(arr.into_iter().map(|item| item.into()).collect())
913 }
914 RangingMeasurements::ExtendedAddressTwoWay(arr) => {
915 ProtoRangingMeasurements::TwoWay(arr.into_iter().map(|item| item.into()).collect())
916 }
917 RangingMeasurements::ShortAddressOwrAoa(r) => ProtoRangingMeasurements::OwrAoa(r.into()),
918 RangingMeasurements::ExtendedAddressOwrAoa(r) => ProtoRangingMeasurements::OwrAoa(r.into()),
919 RangingMeasurements::ShortAddressDltdoa(arr) => {
920 ProtoRangingMeasurements::DlTDoa(arr.into_iter().map(|item| item.into()).collect())
921 }
922 RangingMeasurements::ExtendedAddressDltdoa(arr) => {
923 ProtoRangingMeasurements::DlTDoa(arr.into_iter().map(|item| item.into()).collect())
924 }
925 }
926 }
927
928 impl From<ProtoRangingRoundControl> for RangingRoundControl {
from(item: ProtoRangingRoundControl) -> Self929 fn from(item: ProtoRangingRoundControl) -> Self {
930 Self {
931 ranging_result_report_message: item.ranging_result_report_message,
932 control_message: item.control_message,
933 measurement_report_message: item.measurement_report_message,
934 }
935 }
936 }
937
938 impl From<RangingRoundControl> for ProtoRangingRoundControl {
from(item: RangingRoundControl) -> Self939 fn from(item: RangingRoundControl) -> Self {
940 let mut res = Self::new();
941 res.ranging_result_report_message = item.ranging_result_report_message;
942 res.control_message = item.control_message;
943 res.measurement_report_message = item.measurement_report_message;
944 res
945 }
946 }
947
948 impl From<ProtoResultReportConfig> for ResultReportConfig {
from(item: ProtoResultReportConfig) -> Self949 fn from(item: ProtoResultReportConfig) -> Self {
950 Self {
951 tof: item.tof,
952 aoa_azimuth: item.aoa_azimuth,
953 aoa_elevation: item.aoa_elevation,
954 aoa_fom: item.aoa_fom,
955 }
956 }
957 }
958
959 impl From<ResultReportConfig> for ProtoResultReportConfig {
from(item: ResultReportConfig) -> Self960 fn from(item: ResultReportConfig) -> Self {
961 let mut res = Self::new();
962 res.tof = item.tof;
963 res.aoa_azimuth = item.aoa_azimuth;
964 res.aoa_elevation = item.aoa_elevation;
965 res.aoa_fom = item.aoa_fom;
966 res
967 }
968 }
969
to_uwb_address(bytes: Vec<u8>, mode: ProtoMacAddressMode) -> Option<UwbAddress>970 fn to_uwb_address(bytes: Vec<u8>, mode: ProtoMacAddressMode) -> Option<UwbAddress> {
971 match mode {
972 ProtoMacAddressMode::MAC_ADDRESS_2_BYTES
973 | ProtoMacAddressMode::MAC_ADDRESS_8_BYTES_2_BYTES_HEADER => {
974 Some(UwbAddress::Short(bytes.try_into().ok()?))
975 }
976 ProtoMacAddressMode::MAC_ADDRESS_8_BYTES => {
977 Some(UwbAddress::Extended(bytes.try_into().ok()?))
978 }
979 }
980 }
981
982 impl TryFrom<ProtoControlee> for Controlee {
983 type Error = String;
try_from(item: ProtoControlee) -> std::result::Result<Self, Self::Error>984 fn try_from(item: ProtoControlee) -> std::result::Result<Self, Self::Error> {
985 Ok(Self {
986 short_address: item.short_address.to_ne_bytes()[0..2]
987 .try_into()
988 .map_err(|_| "Failed to convert short_address")?,
989 subsession_id: item.subsession_id,
990 })
991 }
992 }
993
994 impl From<PowerStats> for ProtoPowerStats {
from(item: PowerStats) -> Self995 fn from(item: PowerStats) -> Self {
996 let mut res = Self::new();
997 res.status = ProtoStatusCode::from(item.status).into();
998 res.idle_time_ms = item.idle_time_ms;
999 res.tx_time_ms = item.tx_time_ms;
1000 res.rx_time_ms = item.rx_time_ms;
1001 res.total_wake_count = item.total_wake_count;
1002 res
1003 }
1004 }
1005
1006 impl From<FiraAppConfigParams> for ProtoFiraAppConfigParams {
from(item: FiraAppConfigParams) -> Self1007 fn from(item: FiraAppConfigParams) -> Self {
1008 let mut res = Self::new();
1009 res.device_type = EnumOrUnknown::new((*item.device_type()).into());
1010 res.ranging_round_usage = ProtoRangingRoundUsage::from(*item.ranging_round_usage()).into();
1011 res.sts_config = ProtoStsConfig::from(*item.sts_config()).into();
1012 res.multi_node_mode = ProtoMultiNodeMode::from(*item.multi_node_mode()).into();
1013 res.channel_number = ProtoUwbChannel::from(*item.channel_number()).into();
1014 res.device_mac_address = item.device_mac_address().clone().into();
1015 res.dst_mac_address =
1016 item.dst_mac_address().clone().into_iter().map(|addr| addr.into()).collect::<Vec<_>>();
1017 res.slot_duration_rstu = (*item.slot_duration_rstu()).into();
1018 res.ranging_duration_ms = *item.ranging_duration_ms();
1019 res.mac_fcs_type = ProtoMacFcsType::from(*item.mac_fcs_type()).into();
1020 res.ranging_round_control = MessageField::from(Some(ProtoRangingRoundControl::from(
1021 item.ranging_round_control().clone(),
1022 )));
1023 res.aoa_result_request = ProtoAoaResultRequest::from(*item.aoa_result_request()).into();
1024 res.range_data_ntf_config =
1025 ProtoRangeDataNtfConfig::from(*item.range_data_ntf_config()).into();
1026 res.range_data_ntf_proximity_near_cm = (*item.range_data_ntf_proximity_near_cm()).into();
1027 res.range_data_ntf_proximity_far_cm = (*item.range_data_ntf_proximity_far_cm()).into();
1028 res.device_role = ProtoDeviceRole::from(*item.device_role()).into();
1029 res.rframe_config = ProtoRframeConfig::from(*item.rframe_config()).into();
1030 res.preamble_code_index = (*item.preamble_code_index()).into();
1031 res.sfd_id = (*item.sfd_id()).into();
1032 res.psdu_data_rate = ProtoPsduDataRate::from(*item.psdu_data_rate()).into();
1033 res.preamble_duration = ProtoPreambleDuration::from(*item.preamble_duration()).into();
1034 res.ranging_time_struct = ProtoRangingTimeStruct::from(*item.ranging_time_struct()).into();
1035 res.slots_per_rr = (*item.slots_per_rr()).into();
1036 res.tx_adaptive_payload_power =
1037 ProtoTxAdaptivePayloadPower::from(*item.tx_adaptive_payload_power()).into();
1038 res.responder_slot_index = (*item.responder_slot_index()).into();
1039 res.prf_mode = ProtoPrfMode::from(*item.prf_mode()).into();
1040 res.scheduled_mode = ProtoScheduledMode::from(*item.scheduled_mode()).into();
1041 res.key_rotation = ProtoKeyRotation::from(*item.key_rotation()).into();
1042 res.key_rotation_rate = (*item.key_rotation_rate()).into();
1043 res.session_priority = (*item.session_priority()).into();
1044 res.mac_address_mode = ProtoMacAddressMode::from(*item.mac_address_mode()).into();
1045 res.vendor_id = (*item.vendor_id()).into();
1046 res.static_sts_iv = (*item.static_sts_iv()).into();
1047 res.number_of_sts_segments = (*item.number_of_sts_segments()).into();
1048 res.max_rr_retry = (*item.max_rr_retry()).into();
1049 res.uwb_initiation_time_ms = *item.uwb_initiation_time_ms();
1050 res.hopping_mode = ProtoHoppingMode::from(*item.hopping_mode()).into();
1051 res.block_stride_length = (*item.block_stride_length()).into();
1052 res.result_report_config = MessageField::from(Some(ProtoResultReportConfig::from(
1053 item.result_report_config().clone(),
1054 )));
1055 res.in_band_termination_attempt_count = (*item.in_band_termination_attempt_count()).into();
1056 res.sub_session_id = *item.sub_session_id();
1057 res.bprf_phr_data_rate = ProtoBprfPhrDataRate::from(*item.bprf_phr_data_rate()).into();
1058 res.max_number_of_measurements = (*item.max_number_of_measurements()).into();
1059 res.sts_length = ProtoStsLength::from(*item.sts_length()).into();
1060 res.number_of_range_measurements = (*item.number_of_range_measurements()).into();
1061 res.number_of_aoa_azimuth_measurements =
1062 (*item.number_of_aoa_azimuth_measurements()).into();
1063 res.number_of_aoa_elevation_measurements =
1064 (*item.number_of_aoa_elevation_measurements()).into();
1065
1066 res
1067 }
1068 }
1069
1070 impl TryFrom<ProtoFiraAppConfigParams> for AppConfigParams {
1071 type Error = String;
try_from(mut item: ProtoFiraAppConfigParams) -> std::result::Result<Self, Self::Error>1072 fn try_from(mut item: ProtoFiraAppConfigParams) -> std::result::Result<Self, Self::Error> {
1073 let device_mac_address = to_uwb_address(
1074 item.device_mac_address.clone(),
1075 item.mac_address_mode.enum_value().map_err(|_| "Failed to read mac_address_mode")?,
1076 )
1077 .ok_or("Failed to convert device_mac_address")?;
1078 let mut dst_mac_address = vec![];
1079 for addr in item.dst_mac_address.clone().into_iter() {
1080 let addr = to_uwb_address(
1081 addr,
1082 item.mac_address_mode
1083 .enum_value()
1084 .map_err(|_| "Failed to convert mac_address_mode")?,
1085 )
1086 .ok_or("Failed to convert dst_mac_address")?;
1087 dst_mac_address.push(addr);
1088 }
1089
1090 let mut builder = FiraAppConfigParamsBuilder::new();
1091 builder
1092 .device_type(
1093 item.device_type.enum_value().map_err(|_| "Failed to convert device_type")?.into(),
1094 )
1095 .ranging_round_usage(
1096 item.ranging_round_usage
1097 .enum_value()
1098 .map_err(|_| "Failed to convert ranging_round_usage")?
1099 .into(),
1100 )
1101 .sts_config(
1102 item.sts_config.enum_value().map_err(|_| "Failed to convert sts_config")?.into(),
1103 )
1104 .multi_node_mode(
1105 item.multi_node_mode
1106 .enum_value()
1107 .map_err(|_| "Failed to convert multi_node_mode")?
1108 .into(),
1109 )
1110 .channel_number(
1111 item.channel_number
1112 .enum_value()
1113 .map_err(|_| "Failed to convert channel_number")?
1114 .into(),
1115 )
1116 .device_mac_address(device_mac_address)
1117 .dst_mac_address(dst_mac_address)
1118 .slot_duration_rstu(
1119 item.slot_duration_rstu
1120 .try_into()
1121 .map_err(|_| "Failed to convert slot_duration_rstu")?,
1122 )
1123 .ranging_duration_ms(item.ranging_duration_ms)
1124 .mac_fcs_type(
1125 item.mac_fcs_type
1126 .enum_value()
1127 .map_err(|_| "Failed to convert mac_fcs_type")?
1128 .into(),
1129 )
1130 .ranging_round_control(
1131 item.ranging_round_control.take().ok_or("ranging_round_control is empty")?.into(),
1132 )
1133 .aoa_result_request(
1134 item.aoa_result_request
1135 .enum_value()
1136 .map_err(|_| "Failed to convert aoa_result_request")?
1137 .into(),
1138 )
1139 .range_data_ntf_config(
1140 item.range_data_ntf_config
1141 .enum_value()
1142 .map_err(|_| "Failed to convert range_data_ntf_config")?
1143 .into(),
1144 )
1145 .range_data_ntf_proximity_near_cm(
1146 item.range_data_ntf_proximity_near_cm
1147 .try_into()
1148 .map_err(|_| "Failed to convert range_data_ntf_proximity_near_cm")?,
1149 )
1150 .range_data_ntf_proximity_far_cm(
1151 item.range_data_ntf_proximity_far_cm
1152 .try_into()
1153 .map_err(|_| "Failed to convert range_data_ntf_proximity_far_cm")?,
1154 )
1155 .device_role(
1156 item.device_role.enum_value().map_err(|_| "Failed to convert device_role")?.into(),
1157 )
1158 .rframe_config(
1159 item.rframe_config
1160 .enum_value()
1161 .map_err(|_| "Failed to convert rframe_config")?
1162 .into(),
1163 )
1164 .preamble_code_index(
1165 item.preamble_code_index
1166 .try_into()
1167 .map_err(|_| "Failed to convert preamble_code_index")?,
1168 )
1169 .sfd_id(item.sfd_id.try_into().map_err(|_| "Failed to convert sfd_id")?)
1170 .psdu_data_rate(
1171 item.psdu_data_rate
1172 .enum_value()
1173 .map_err(|_| "Failed to convert psdu_data_rate")?
1174 .into(),
1175 )
1176 .preamble_duration(
1177 item.preamble_duration
1178 .enum_value()
1179 .map_err(|_| "Failed to convert preamble_duration")?
1180 .into(),
1181 )
1182 .ranging_time_struct(
1183 item.ranging_time_struct
1184 .enum_value()
1185 .map_err(|_| "Failed to convert ranging_time_struct")?
1186 .into(),
1187 )
1188 .slots_per_rr(
1189 item.slots_per_rr.try_into().map_err(|_| "Failed to convert slots_per_rr")?,
1190 )
1191 .tx_adaptive_payload_power(
1192 item.tx_adaptive_payload_power
1193 .enum_value()
1194 .map_err(|_| "Failed to convert tx_adaptive_payload_power")?
1195 .into(),
1196 )
1197 .responder_slot_index(
1198 item.responder_slot_index
1199 .try_into()
1200 .map_err(|_| "Failed to convert responder_slot_index")?,
1201 )
1202 .prf_mode(item.prf_mode.enum_value().map_err(|_| "Failed to convert prf_mode")?.into())
1203 .scheduled_mode(
1204 item.scheduled_mode
1205 .enum_value()
1206 .map_err(|_| "Failed to convert scheduled_mode")?
1207 .into(),
1208 )
1209 .key_rotation(
1210 item.key_rotation
1211 .enum_value()
1212 .map_err(|_| "Failed to convert key_rotation")?
1213 .into(),
1214 )
1215 .key_rotation_rate(
1216 item.key_rotation_rate
1217 .try_into()
1218 .map_err(|_| "Failed to convert key_rotation_rate")?,
1219 )
1220 .session_priority(
1221 item.session_priority
1222 .try_into()
1223 .map_err(|_| "Failed to convert session_priority")?,
1224 )
1225 .mac_address_mode(
1226 item.mac_address_mode
1227 .enum_value()
1228 .map_err(|_| "Failed to convert mac_address_mode")?
1229 .into(),
1230 )
1231 .vendor_id(
1232 item.vendor_id.clone().try_into().map_err(|_| "Failed to convert vendor_id")?,
1233 )
1234 .static_sts_iv(
1235 item.static_sts_iv
1236 .clone()
1237 .try_into()
1238 .map_err(|_| "Failed to convert static_sts_iv")?,
1239 )
1240 .number_of_sts_segments(
1241 item.number_of_sts_segments
1242 .try_into()
1243 .map_err(|_| "Failed to convert number_of_sts_segments")?,
1244 )
1245 .max_rr_retry(
1246 item.max_rr_retry.try_into().map_err(|_| "Failed to convert max_rr_retry")?,
1247 )
1248 .uwb_initiation_time_ms(item.uwb_initiation_time_ms)
1249 .hopping_mode(item.hopping_mode.unwrap().into())
1250 .block_stride_length(
1251 item.block_stride_length
1252 .try_into()
1253 .map_err(|_| "Failed to convert block_stride_length")?,
1254 )
1255 .result_report_config(
1256 item.result_report_config.take().ok_or("ranging_round_control is empty")?.into(),
1257 )
1258 .in_band_termination_attempt_count(
1259 item.in_band_termination_attempt_count
1260 .try_into()
1261 .map_err(|_| "Failed to convert in_band_termination_attempt_count")?,
1262 )
1263 .sub_session_id(item.sub_session_id)
1264 .bprf_phr_data_rate(
1265 item.bprf_phr_data_rate
1266 .enum_value()
1267 .map_err(|_| "Failed to convert bprf_phr_data_rate")?
1268 .into(),
1269 )
1270 .max_number_of_measurements(
1271 item.max_number_of_measurements
1272 .try_into()
1273 .map_err(|_| "Failed to convert max_number_of_measurements")?,
1274 )
1275 .sts_length(
1276 item.sts_length.enum_value().map_err(|_| "Failed to convert sts_length")?.into(),
1277 )
1278 .number_of_range_measurements(
1279 item.number_of_range_measurements
1280 .try_into()
1281 .map_err(|_| "Failed to convert number_of_range_measurements")?,
1282 )
1283 .number_of_aoa_azimuth_measurements(
1284 item.number_of_aoa_azimuth_measurements
1285 .try_into()
1286 .map_err(|_| "Failed to convert number_of_aoa_azimuth_measurements")?,
1287 )
1288 .number_of_aoa_elevation_measurements(
1289 item.number_of_aoa_elevation_measurements
1290 .try_into()
1291 .map_err(|_| "Failed to convert number_of_aoa_elevation_measurements")?,
1292 );
1293
1294 Ok(builder.build().ok_or("Failed to build FiraAppConfigParam from builder")?)
1295 }
1296 }
1297
1298 impl Drop for ProtoFiraAppConfigParams {
drop(&mut self)1299 fn drop(&mut self) {
1300 // Zero out the sensitive data before releasing memory.
1301 self.vendor_id.zeroize();
1302 self.static_sts_iv.zeroize();
1303 self.sub_session_id.zeroize();
1304 }
1305 }
1306