1 /*
2  * Copyright (C) 2021 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.server.location.gnss;
18 
19 import static com.android.internal.util.ConcurrentUtils.DIRECT_EXECUTOR;
20 import static com.android.server.location.gnss.GnssManagerService.TAG;
21 
22 import android.annotation.Nullable;
23 import android.location.GnssAntennaInfo;
24 import android.location.IGnssAntennaInfoListener;
25 import android.location.util.identity.CallerIdentity;
26 import android.os.Binder;
27 import android.os.IBinder;
28 
29 import com.android.server.FgThread;
30 import com.android.server.location.gnss.hal.GnssNative;
31 import com.android.server.location.listeners.BinderListenerRegistration;
32 import com.android.server.location.listeners.ListenerMultiplexer;
33 import com.android.server.location.listeners.ListenerRegistration;
34 
35 import java.util.Collection;
36 import java.util.List;
37 
38 /**
39  * Antenna info HAL module and listener multiplexer.
40  */
41 public class GnssAntennaInfoProvider extends
42         ListenerMultiplexer<IBinder, IGnssAntennaInfoListener,
43                 ListenerRegistration<IGnssAntennaInfoListener>, Void> implements
44         GnssNative.BaseCallbacks, GnssNative.AntennaInfoCallbacks {
45 
46     /**
47      * Registration object for GNSS listeners.
48      */
49     protected class AntennaInfoListenerRegistration extends
50             BinderListenerRegistration<IBinder, IGnssAntennaInfoListener> {
51 
52         private final CallerIdentity mIdentity;
53 
AntennaInfoListenerRegistration(CallerIdentity identity, IGnssAntennaInfoListener listener)54         protected AntennaInfoListenerRegistration(CallerIdentity identity,
55                 IGnssAntennaInfoListener listener) {
56             super(identity.isMyProcess() ? FgThread.getExecutor() : DIRECT_EXECUTOR, listener);
57             mIdentity = identity;
58         }
59 
60         @Override
getTag()61         protected String getTag() {
62             return TAG;
63         }
64 
65         @Override
getOwner()66         protected GnssAntennaInfoProvider getOwner() {
67             return GnssAntennaInfoProvider.this;
68         }
69 
70         @Override
getBinderFromKey(IBinder key)71         protected IBinder getBinderFromKey(IBinder key) {
72             return key;
73         }
74 
75         @Override
toString()76         public String toString() {
77             return mIdentity.toString();
78         }
79     }
80 
81     private final GnssNative mGnssNative;
82 
83     private volatile @Nullable List<GnssAntennaInfo> mAntennaInfos;
84 
GnssAntennaInfoProvider(GnssNative gnssNative)85     GnssAntennaInfoProvider(GnssNative gnssNative) {
86         mGnssNative = gnssNative;
87         mGnssNative.addBaseCallbacks(this);
88         mGnssNative.addAntennaInfoCallbacks(this);
89     }
90 
getAntennaInfos()91     @Nullable List<GnssAntennaInfo> getAntennaInfos() {
92         return mAntennaInfos;
93     }
94 
isSupported()95     public boolean isSupported() {
96         return mGnssNative.isAntennaInfoSupported();
97     }
98 
addListener(CallerIdentity callerIdentity, IGnssAntennaInfoListener listener)99     public void addListener(CallerIdentity callerIdentity, IGnssAntennaInfoListener listener) {
100         final long identity = Binder.clearCallingIdentity();
101         try {
102             putRegistration(listener.asBinder(),
103                     new AntennaInfoListenerRegistration(callerIdentity, listener));
104         } finally {
105             Binder.restoreCallingIdentity(identity);
106         }
107     }
108 
removeListener(IGnssAntennaInfoListener listener)109     public void removeListener(IGnssAntennaInfoListener listener) {
110         final long identity = Binder.clearCallingIdentity();
111         try {
112             removeRegistration(listener.asBinder());
113         } finally {
114             Binder.restoreCallingIdentity(identity);
115         }
116     }
117 
118     @Override
registerWithService(Void merged, Collection<ListenerRegistration<IGnssAntennaInfoListener>> listenerRegistrations)119     protected boolean registerWithService(Void merged,
120             Collection<ListenerRegistration<IGnssAntennaInfoListener>> listenerRegistrations) {
121         return true;
122     }
123 
124     @Override
unregisterWithService()125     protected void unregisterWithService() {}
126 
127     @Override
isActive(ListenerRegistration<IGnssAntennaInfoListener> registration)128     protected boolean isActive(ListenerRegistration<IGnssAntennaInfoListener> registration) {
129         return true;
130     }
131 
132     @Override
mergeRegistrations( Collection<ListenerRegistration<IGnssAntennaInfoListener>> listenerRegistrations)133     protected Void mergeRegistrations(
134             Collection<ListenerRegistration<IGnssAntennaInfoListener>> listenerRegistrations) {
135         return null;
136     }
137 
138     @Override
onHalStarted()139     public void onHalStarted() {
140         mGnssNative.startAntennaInfoListening();
141     }
142 
143     @Override
onHalRestarted()144     public void onHalRestarted() {
145         mGnssNative.startAntennaInfoListening();
146     }
147 
148     @Override
onReportAntennaInfo(List<GnssAntennaInfo> antennaInfos)149     public void onReportAntennaInfo(List<GnssAntennaInfo> antennaInfos) {
150         if (antennaInfos.equals(mAntennaInfos)) {
151             return;
152         }
153 
154         mAntennaInfos = antennaInfos;
155         deliverToListeners(listener -> {
156             listener.onGnssAntennaInfoChanged(antennaInfos);
157         });
158     }
159 }
160