1 /*
2  * Copyright (C) 2020 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.net;
18 
19 import android.annotation.IntRange;
20 import android.annotation.NonNull;
21 import android.annotation.Nullable;
22 import android.annotation.RequiresPermission;
23 import android.annotation.SystemApi;
24 import android.content.Context;
25 import android.os.Handler;
26 import android.os.Looper;
27 import android.os.Message;
28 import android.os.Messenger;
29 import android.util.Log;
30 
31 /**
32  * Base class for network providers such as telephony or Wi-Fi. NetworkProviders connect the device
33  * to networks and makes them available to to the core network stack by creating
34  * {@link NetworkAgent}s. The networks can then provide connectivity to apps and can be interacted
35  * with via networking APIs such as {@link ConnectivityManager}.
36  *
37  * Subclasses should implement {@link #onNetworkRequested} and {@link #onNetworkRequestWithdrawn}
38  * to receive {@link NetworkRequest}s sent by the system and by apps. A network that is not the
39  * best (highest-scoring) network for any request is generally not used by the system, and torn
40  * down.
41  *
42  * @hide
43  */
44 @SystemApi
45 public class NetworkProvider {
46     /**
47      * {@code providerId} value that indicates the absence of a provider. It is the providerId of
48      * any NetworkProvider that is not currently registered, and of any NetworkRequest that is not
49      * currently being satisfied by a network.
50      */
51     public static final int ID_NONE = -1;
52 
53     /**
54      * A hardcoded ID for NetworkAgents representing VPNs. These agents are not created by any
55      * provider, so they use this constant for clarity instead of NONE.
56      * @hide only used by ConnectivityService.
57      */
58     public static final int ID_VPN = -2;
59 
60     /**
61      * The first providerId value that will be allocated.
62      * @hide only used by ConnectivityService.
63      */
64     public static final int FIRST_PROVIDER_ID = 1;
65 
66     /** @hide only used by ConnectivityService */
67     public static final int CMD_REQUEST_NETWORK = 1;
68     /** @hide only used by ConnectivityService */
69     public static final int CMD_CANCEL_REQUEST = 2;
70 
71     private final Messenger mMessenger;
72     private final String mName;
73     private final ConnectivityManager mCm;
74 
75     private int mProviderId = ID_NONE;
76 
77     /**
78      * Constructs a new NetworkProvider.
79      *
80      * @param looper the Looper on which to run {@link #onNetworkRequested} and
81      *               {@link #onNetworkRequestWithdrawn}.
82      * @param name the name of the listener, used only for debugging.
83      *
84      * @hide
85      */
86     @SystemApi
NetworkProvider(@onNull Context context, @NonNull Looper looper, @NonNull String name)87     public NetworkProvider(@NonNull Context context, @NonNull Looper looper, @NonNull String name) {
88         mCm = ConnectivityManager.from(context);
89 
90         Handler handler = new Handler(looper) {
91             @Override
92             public void handleMessage(Message m) {
93                 switch (m.what) {
94                     case CMD_REQUEST_NETWORK:
95                         onNetworkRequested((NetworkRequest) m.obj, m.arg1, m.arg2);
96                         break;
97                     case CMD_CANCEL_REQUEST:
98                         onNetworkRequestWithdrawn((NetworkRequest) m.obj);
99                         break;
100                     default:
101                         Log.e(mName, "Unhandled message: " + m.what);
102                 }
103             }
104         };
105         mMessenger = new Messenger(handler);
106         mName = name;
107     }
108 
109     // TODO: consider adding a register() method so ConnectivityManager does not need to call this.
110     /** @hide */
getMessenger()111     public @Nullable Messenger getMessenger() {
112         return mMessenger;
113     }
114 
115     /** @hide */
getName()116     public @NonNull String getName() {
117         return mName;
118     }
119 
120     /**
121      * Returns the ID of this provider. This is known only once the provider is registered via
122      * {@link ConnectivityManager#registerNetworkProvider()}, otherwise the ID is {@link #ID_NONE}.
123      * This ID must be used when registering any {@link NetworkAgent}s.
124      */
getProviderId()125     public int getProviderId() {
126         return mProviderId;
127     }
128 
129     /** @hide */
setProviderId(int providerId)130     public void setProviderId(int providerId) {
131         mProviderId = providerId;
132     }
133 
134     /**
135      *  Called when a NetworkRequest is received. The request may be a new request or an existing
136      *  request with a different score.
137      *
138      * @param request the NetworkRequest being received
139      * @param score the score of the network currently satisfying the request, or 0 if none.
140      * @param providerId the ID of the provider that created the network currently satisfying this
141      *                   request, or {@link #ID_NONE} if none.
142      *
143      *  @hide
144      */
145     @SystemApi
onNetworkRequested(@onNull NetworkRequest request, @IntRange(from = 0, to = 99) int score, int providerId)146     public void onNetworkRequested(@NonNull NetworkRequest request,
147             @IntRange(from = 0, to = 99) int score, int providerId) {}
148 
149     /**
150      *  Called when a NetworkRequest is withdrawn.
151      *  @hide
152      */
153     @SystemApi
onNetworkRequestWithdrawn(@onNull NetworkRequest request)154     public void onNetworkRequestWithdrawn(@NonNull NetworkRequest request) {}
155 
156     /**
157      * Asserts that no provider will ever be able to satisfy the specified request. The provider
158      * must only call this method if it knows that it is the only provider on the system capable of
159      * satisfying this request, and that the request cannot be satisfied. The application filing the
160      * request will receive an {@link NetworkCallback#onUnavailable()} callback.
161      *
162      * @param request the request that permanently cannot be fulfilled
163      * @hide
164      */
165     @SystemApi
166     @RequiresPermission(android.Manifest.permission.NETWORK_FACTORY)
declareNetworkRequestUnfulfillable(@onNull NetworkRequest request)167     public void declareNetworkRequestUnfulfillable(@NonNull NetworkRequest request) {
168         mCm.declareNetworkRequestUnfulfillable(request);
169     }
170 }
171