1 /*
2  * Copyright (C) 2024 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 package com.android.ranging.generic.ranging;
18 
19 import com.android.ranging.generic.RangingTechnology;
20 import com.android.ranging.generic.proto.MultiSensorFinderConfig;
21 
22 import com.google.auto.value.AutoValue;
23 import com.google.common.base.Preconditions;
24 import com.google.common.collect.ImmutableList;
25 
26 import java.time.Duration;
27 import java.util.Optional;
28 
29 /** Configuration for Precision Ranging. */
30 @AutoValue
31 public abstract class PrecisionRangingConfig {
32 
33     /** Returns the list of ranging technologies that were requested for this ranging session. */
getRangingTechnologiesToRangeWith()34     public abstract ImmutableList<RangingTechnology> getRangingTechnologiesToRangeWith();
35 
36     /** Returns whether to use the fusing algorithm or not. */
getUseFusingAlgorithm()37     public abstract boolean getUseFusingAlgorithm();
38 
39     /**
40      * Returns the max interval at which data will be reported back. If set to 0 data will be
41      * reported
42      * immediately on reception. If set to non zero value, only latest received data that hasn't
43      * been
44      * yet reported will be reported, so there's a chance that some data doesn't get reported if
45      * multiple data points were received during the same update interval.
46      */
getMaxUpdateInterval()47     public abstract Duration getMaxUpdateInterval();
48 
49     /**
50      * Returns the timeout after which precision ranging will be stopped if no data was produced
51      * since
52      * precision ranging started.
53      */
getInitTimeout()54     public abstract Duration getInitTimeout();
55 
56     /**
57      * Returns the timeout to stop reporting back new data if fusion algorithm wasn't feeded ranging
58      * data in that amount of time. Checked only if useFusingAlgorithm is set to true.
59      */
getFusionAlgorithmDriftTimeout()60     public abstract Duration getFusionAlgorithmDriftTimeout();
61 
62     /**
63      * Returns the timeout to stop precision ranging if there were no new precision data updates
64      * sent
65      * in that time period.
66      */
getNoUpdateTimeout()67     public abstract Duration getNoUpdateTimeout();
68 
69     /** Returns the fusion algorithm configuration if present. */
getFusionAlgorithmConfig()70     public abstract Optional<MultiSensorFinderConfig> getFusionAlgorithmConfig();
71 
72     /** Returns a builder for {@link PrecisionRangingConfig}. */
builder()73     public static Builder builder() {
74         return new AutoValue_PrecisionRangingConfig.Builder();
75     }
76 
77     /** Builder for {@link PrecisionRangingConfig}. */
78     @AutoValue.Builder
79     public abstract static class Builder {
setRangingTechnologiesToRangeWith( ImmutableList<RangingTechnology> rangingTechnologiesToRangeWith)80         public abstract Builder setRangingTechnologiesToRangeWith(
81                 ImmutableList<RangingTechnology> rangingTechnologiesToRangeWith);
82 
setUseFusingAlgorithm(boolean useFusingAlgorithm)83         public abstract Builder setUseFusingAlgorithm(boolean useFusingAlgorithm);
84 
setMaxUpdateInterval(Duration maxUpdateInterval)85         public abstract Builder setMaxUpdateInterval(Duration maxUpdateInterval);
86 
setFusionAlgorithmDriftTimeout(Duration duration)87         public abstract Builder setFusionAlgorithmDriftTimeout(Duration duration);
88 
setNoUpdateTimeout(Duration duration)89         public abstract Builder setNoUpdateTimeout(Duration duration);
90 
setInitTimeout(Duration duration)91         public abstract Builder setInitTimeout(Duration duration);
92 
setFusionAlgorithmConfig(MultiSensorFinderConfig fusionAlgorithmConfig)93         public abstract Builder setFusionAlgorithmConfig(MultiSensorFinderConfig
94                 fusionAlgorithmConfig);
95 
autoBuild()96         abstract PrecisionRangingConfig autoBuild();
97 
build()98         public PrecisionRangingConfig build() {
99             PrecisionRangingConfig config = autoBuild();
100             Preconditions.checkArgument(
101                     !config.getRangingTechnologiesToRangeWith().isEmpty(),
102                     "Ranging technologies to range with must contain at least one ranging "
103                             + "technology.");
104             Preconditions.checkArgument(
105                     config.getUseFusingAlgorithm() == config.getFusionAlgorithmConfig()
106                     .isPresent(),
107                     "Fusion algorithm config must be set when and only when useFusingAlgorithm"
108                     + "is set to");
109             if (config.getUseFusingAlgorithm()
110                     && config.getRangingTechnologiesToRangeWith().contains(RangingTechnology
111                     .UWB)) {
112                 Preconditions.checkArgument(
113                         config.getFusionAlgorithmConfig().get().getUseUwbMeasurements(),
114                         "Fusion algorithm should accept UWB measurements since UWB was requested.");
115             }
116             return config;
117         }
118     }
119 }
120