1 /*
2  * Copyright (C) 2019 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 android.telephony;
18 
19 import android.annotation.NonNull;
20 import android.app.SystemServiceRegistry;
21 import android.compat.Compatibility;
22 import android.compat.annotation.ChangeId;
23 import android.compat.annotation.EnabledSince;
24 import android.content.Context;
25 import android.content.pm.PackageManager;
26 import android.os.Build;
27 import android.os.SystemProperties;
28 import android.os.TelephonyServiceManager;
29 import android.telephony.euicc.EuiccCardManager;
30 import android.telephony.euicc.EuiccManager;
31 import android.telephony.ims.ImsManager;
32 import android.telephony.satellite.SatelliteManager;
33 
34 import com.android.internal.telephony.flags.Flags;
35 import com.android.internal.util.Preconditions;
36 
37 
38 /**
39  * Class for performing registration for all telephony services.
40  *
41  * @hide
42  */
43 public class TelephonyFrameworkInitializer {
44 
TelephonyFrameworkInitializer()45     private TelephonyFrameworkInitializer() {
46     }
47 
48     /**
49      * Starting with {@link VANILLA_ICE_CREAM}, Telephony feature flags
50      * (e.g. {@link PackageManager#FEATURE_TELEPHONY_SUBSCRIPTION}) are being checked before
51      * returning managers that depend on them. If the feature is missing,
52      * {@link Context#getSystemService} will return null.
53      */
54     @ChangeId
55     @EnabledSince(targetSdkVersion = Build.VERSION_CODES.VANILLA_ICE_CREAM)
56     static final long ENABLE_CHECKING_TELEPHONY_FEATURES = 330583731;
57 
58     private static volatile TelephonyServiceManager sTelephonyServiceManager;
59 
60     /**
61      * Sets an instance of {@link TelephonyServiceManager} that allows
62      * the telephony mainline module to register/obtain telephony binder services. This is called
63      * by the platform during the system initialization.
64      *
65      * @param telephonyServiceManager instance of {@link TelephonyServiceManager} that allows
66      * the telephony mainline module to register/obtain telephony binder services.
67      */
setTelephonyServiceManager( @onNull TelephonyServiceManager telephonyServiceManager)68     public static void setTelephonyServiceManager(
69             @NonNull TelephonyServiceManager telephonyServiceManager) {
70         Preconditions.checkState(sTelephonyServiceManager == null,
71                 "setTelephonyServiceManager called twice!");
72         sTelephonyServiceManager = Preconditions.checkNotNull(telephonyServiceManager);
73     }
74 
75     // Suppressing AndroidFrameworkCompatChange because we're querying vendor
76     // partition SDK level, not application's target SDK version (which BTW we
77     // also check through Compatibility framework a few lines below).
78     @SuppressWarnings("AndroidFrameworkCompatChange")
hasSystemFeature(Context context, String feature)79     private static boolean hasSystemFeature(Context context, String feature) {
80         // Check release status of this change in behavior.
81         if (!Flags.minimalTelephonyManagersConditionalOnFeatures()) return true;
82 
83         // Check SDK version of the vendor partition.
84         final int vendorApiLevel = SystemProperties.getInt(
85                 "ro.vendor.api_level", Build.VERSION.DEVICE_INITIAL_SDK_INT);
86         if (vendorApiLevel < Build.VENDOR_API_2024_Q2) return true;
87 
88         // Check SDK version of the client app.
89         if (!Compatibility.isChangeEnabled(ENABLE_CHECKING_TELEPHONY_FEATURES)) return true;
90 
91         // Finally, check if the system feature is actually present.
92         return context.getPackageManager().hasSystemFeature(feature);
93     }
94 
95     /**
96      * Called by {@link SystemServiceRegistry}'s static initializer and registers all telephony
97      * services to {@link Context}, so that {@link Context#getSystemService} can return them.
98      *
99      * @throws IllegalStateException if this is called from anywhere besides
100      * {@link SystemServiceRegistry}
101      */
registerServiceWrappers()102     public static void registerServiceWrappers() {
103         SystemServiceRegistry.registerContextAwareService(
104                 Context.TELEPHONY_SERVICE,
105                 TelephonyManager.class,
106                 context -> new TelephonyManager(context)
107         );
108         SystemServiceRegistry.registerContextAwareService(
109                 Context.TELEPHONY_SUBSCRIPTION_SERVICE,
110                 SubscriptionManager.class,
111                 context -> new SubscriptionManager(context)
112         );
113         SystemServiceRegistry.registerContextAwareService(
114                 Context.CARRIER_CONFIG_SERVICE,
115                 CarrierConfigManager.class,
116                 context -> hasSystemFeature(context, PackageManager.FEATURE_TELEPHONY_SUBSCRIPTION)
117                         ? new CarrierConfigManager(context) : null
118         );
119         SystemServiceRegistry.registerContextAwareService(
120                 Context.EUICC_SERVICE,
121                 EuiccManager.class,
122                 context -> hasSystemFeature(context, PackageManager.FEATURE_TELEPHONY_EUICC)
123                         ? new EuiccManager(context) : null
124         );
125         SystemServiceRegistry.registerContextAwareService(
126                 Context.EUICC_CARD_SERVICE,
127                 EuiccCardManager.class,
128                 context -> hasSystemFeature(context, PackageManager.FEATURE_TELEPHONY_EUICC)
129                         ? new EuiccCardManager(context) : null
130         );
131         SystemServiceRegistry.registerContextAwareService(
132                 Context.TELEPHONY_IMS_SERVICE,
133                 ImsManager.class,
134                 context -> hasSystemFeature(context, PackageManager.FEATURE_TELEPHONY_IMS)
135                         ? new ImsManager(context) : null
136         );
137         SystemServiceRegistry.registerContextAwareService(
138                 Context.SMS_SERVICE,
139                 SmsManager.class,
140                 context -> hasSystemFeature(context, PackageManager.FEATURE_TELEPHONY_MESSAGING)
141                         ? SmsManager.getSmsManagerForContextAndSubscriptionId(context,
142                                 SubscriptionManager.DEFAULT_SUBSCRIPTION_ID) : null
143         );
144         SystemServiceRegistry.registerContextAwareService(
145                 Context.SATELLITE_SERVICE,
146                 SatelliteManager.class,
147                 context -> hasSystemFeature(context, PackageManager.FEATURE_TELEPHONY_SATELLITE)
148                         ? new SatelliteManager(context) : null
149         );
150     }
151 
152     /** @hide */
getTelephonyServiceManager()153     public static TelephonyServiceManager getTelephonyServiceManager() {
154         return sTelephonyServiceManager;
155     }
156 }
157