Home | History | Annotate | Download | only in mocks
      1 /*
      2  * Copyright (C) 2008 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.internal.telephony.mocks;
     18 
     19 import static android.net.NetworkCapabilities.NET_CAPABILITY_INTERNET;
     20 import static android.net.NetworkCapabilities.NET_CAPABILITY_NOT_RESTRICTED;
     21 
     22 import android.annotation.Nullable;
     23 import android.app.PendingIntent;
     24 import android.content.Context;
     25 import android.content.Intent;
     26 import android.net.ConnectivityManager;
     27 import android.net.IConnectivityManager;
     28 import android.net.LinkProperties;
     29 import android.net.Network;
     30 import android.net.NetworkCapabilities;
     31 import android.net.NetworkInfo;
     32 import android.net.NetworkMisc;
     33 import android.net.NetworkQuotaInfo;
     34 import android.net.NetworkRequest;
     35 import android.net.NetworkState;
     36 import android.net.ProxyInfo;
     37 import android.os.Binder;
     38 import android.os.Bundle;
     39 import android.os.Handler;
     40 import android.os.HandlerThread;
     41 import android.os.IBinder;
     42 import android.os.Looper;
     43 import android.os.Message;
     44 import android.os.Messenger;
     45 import android.os.ParcelFileDescriptor;
     46 import android.os.RemoteException;
     47 import android.os.ResultReceiver;
     48 import android.util.Slog;
     49 
     50 import com.android.internal.annotations.VisibleForTesting;
     51 import com.android.internal.net.LegacyVpnInfo;
     52 import com.android.internal.net.VpnConfig;
     53 import com.android.internal.net.VpnInfo;
     54 import com.android.internal.net.VpnProfile;
     55 import com.android.internal.util.AsyncChannel;
     56 import com.android.server.connectivity.NetworkAgentInfo;
     57 import com.android.server.connectivity.NetworkMonitor;
     58 
     59 import java.io.FileDescriptor;
     60 import java.io.PrintWriter;
     61 import java.util.HashMap;
     62 
     63 /**
     64  * @hide
     65  */
     66 public class ConnectivityServiceMock extends IConnectivityManager.Stub
     67         implements PendingIntent.OnFinished {
     68     private static final String TAG = "ConnectivityServiceMock";
     69     private static final boolean DBG = true;
     70     private static final boolean VDBG = true;
     71 
     72     /**
     73      * used internally when registering NetworkFactories
     74      * obj = NetworkFactoryInfo
     75      */
     76     private static final int EVENT_REGISTER_NETWORK_FACTORY = 17;
     77 
     78     /**
     79      * used internally when registering NetworkAgents
     80      * obj = Messenger
     81      */
     82     private static final int EVENT_REGISTER_NETWORK_AGENT = 18;
     83 
     84     /**
     85      * used to add a network request
     86      * includes a NetworkRequestInfo
     87      */
     88     private static final int EVENT_REGISTER_NETWORK_REQUEST = 19;
     89 
     90     /**
     91      * used to add a network listener - no request
     92      * includes a NetworkRequestInfo
     93      */
     94     private static final int EVENT_REGISTER_NETWORK_LISTENER = 21;
     95 
     96     /**
     97      * used to remove a network request, either a listener or a real request
     98      * arg1 = UID of caller
     99      * obj  = NetworkRequest
    100      */
    101     private static final int EVENT_RELEASE_NETWORK_REQUEST = 22;
    102 
    103     /**
    104      * used internally when registering NetworkFactories
    105      * obj = Messenger
    106      */
    107     private static final int EVENT_UNREGISTER_NETWORK_FACTORY = 23;
    108 
    109 
    110     private final HandlerThread mHandlerThread;
    111     /** Handler used for internal events. */
    112     final private InternalHandler mHandler;
    113     /** Handler used for incoming {@link NetworkStateTracker} events. */
    114     final private NetworkStateTrackerHandler mTrackerHandler;
    115 
    116     final private Context mContext;
    117 
    118     public ConnectivityServiceMock(Context context) {
    119         if (DBG) log("starting up");
    120 
    121         mContext = context;
    122         mHandlerThread = new HandlerThread("ConnectivityServiceMock");
    123         mHandlerThread.start();
    124         mHandler = new InternalHandler(mHandlerThread.getLooper());
    125         mTrackerHandler = new NetworkStateTrackerHandler(mHandlerThread.getLooper());
    126     }
    127 
    128     public void die() {
    129         // clean up threads/handlers
    130         if (mHandlerThread != null) {
    131             mHandlerThread.quit();
    132         }
    133     }
    134 
    135     private class InternalHandler extends Handler {
    136         public InternalHandler(Looper looper) {
    137             super(looper);
    138         }
    139 
    140         @Override
    141         public void handleMessage(Message msg) {
    142             switch (msg.what) {
    143                 case EVENT_REGISTER_NETWORK_FACTORY: {
    144                     handleRegisterNetworkFactory((NetworkFactoryInfo)msg.obj);
    145                     break;
    146                 }
    147                 case EVENT_UNREGISTER_NETWORK_FACTORY: {
    148                     handleUnregisterNetworkFactory((Messenger)msg.obj);
    149                     break;
    150                 }
    151                 case EVENT_REGISTER_NETWORK_AGENT: {
    152                     handleRegisterNetworkAgent((NetworkAgentInfo)msg.obj);
    153                     break;
    154                 }
    155                 case EVENT_REGISTER_NETWORK_REQUEST:
    156                 case EVENT_REGISTER_NETWORK_LISTENER: {
    157                     handleRegisterNetworkRequest((NetworkRequestInfo) msg.obj);
    158                     break;
    159                 }
    160                 case EVENT_RELEASE_NETWORK_REQUEST: {
    161                     handleReleaseNetworkRequest((NetworkRequest) msg.obj, msg.arg1);
    162                     break;
    163                 }
    164             }
    165         }
    166     }
    167 
    168     private class NetworkStateTrackerHandler extends Handler {
    169         public NetworkStateTrackerHandler(Looper looper) {
    170             super(looper);
    171         }
    172 
    173         @Override
    174         public void handleMessage(Message msg) {
    175             NetworkInfo info;
    176             switch (msg.what) {
    177                 case AsyncChannel.CMD_CHANNEL_HALF_CONNECTED: {
    178                     handleAsyncChannelHalfConnect(msg);
    179                     break;
    180                 }
    181                 case AsyncChannel.CMD_CHANNEL_DISCONNECT: {
    182                     NetworkAgentInfo nai = mNetworkAgentInfos.get(msg.replyTo);
    183                     if (nai != null) nai.asyncChannel.disconnect();
    184                     break;
    185                 }
    186                 case AsyncChannel.CMD_CHANNEL_DISCONNECTED: {
    187                     handleAsyncChannelDisconnected(msg);
    188                     break;
    189                 }
    190             }
    191         }
    192     }
    193 
    194     private boolean isRequest(NetworkRequest request) {
    195         return mNetworkRequests.get(request).isRequest;
    196     }
    197 
    198     private void handleAsyncChannelHalfConnect(Message msg) {
    199         AsyncChannel ac = (AsyncChannel) msg.obj;
    200         if (mNetworkFactoryInfos.containsKey(msg.replyTo)) {
    201             if (msg.arg1 == AsyncChannel.STATUS_SUCCESSFUL) {
    202                 if (VDBG) log("NetworkFactory connected");
    203                 // A network factory has connected.  Send it all current NetworkRequests.
    204                 for (NetworkRequestInfo nri : mNetworkRequests.values()) {
    205                     if (nri.isRequest == false) continue;
    206                     //NetworkAgentInfo nai = mNetworkForRequestId.get(nri.request.requestId);
    207                     NetworkAgentInfo nai = null;
    208                     ac.sendMessage(android.net.NetworkFactory.CMD_REQUEST_NETWORK,
    209                             (nai != null ? nai.getCurrentScore() : 0), 0, nri.request);
    210                 }
    211             } else {
    212                 loge("Error connecting NetworkFactory");
    213                 mNetworkFactoryInfos.remove(msg.obj);
    214             }
    215         } else if (mNetworkAgentInfos.containsKey(msg.replyTo)) {
    216             if (msg.arg1 == AsyncChannel.STATUS_SUCCESSFUL) {
    217                 if (VDBG) log("NetworkAgent connected");
    218                 // A network agent has requested a connection.  Establish the connection.
    219                 mNetworkAgentInfos.get(msg.replyTo).asyncChannel.
    220                         sendMessage(AsyncChannel.CMD_CHANNEL_FULL_CONNECTION);
    221             } else {
    222                 loge("Error connecting NetworkAgent");
    223                 NetworkAgentInfo nai = mNetworkAgentInfos.remove(msg.replyTo);
    224                 //if (nai != null) {
    225                 //    final boolean wasDefault = isDefaultNetwork(nai);
    226                 //    synchronized (mNetworkForNetId) {
    227                 //        mNetworkForNetId.remove(nai.network.netId);
    228                 //        mNetIdInUse.delete(nai.network.netId);
    229                 //    }
    230                 //    // Just in case.
    231                 //    mLegacyTypeTracker.remove(nai, wasDefault);
    232                 //}
    233             }
    234         }
    235     }
    236 
    237     private void handleAsyncChannelDisconnected(Message msg) {
    238         NetworkAgentInfo nai = mNetworkAgentInfos.get(msg.replyTo);
    239         if (nai != null) {
    240             if (DBG) {
    241                 log(nai.name() + " got DISCONNECTED, was satisfying " + nai.numNetworkRequests());
    242             }
    243             // A network agent has disconnected.
    244             // TODO - if we move the logic to the network agent (have them disconnect
    245             // because they lost all their requests or because their score isn't good)
    246             // then they would disconnect organically, report their new state and then
    247             // disconnect the channel.
    248             //if (nai.networkInfo.isConnected()) {
    249             //    nai.networkInfo.setDetailedState(NetworkInfo.DetailedState.DISCONNECTED,
    250             //            null, null);
    251             //}
    252             //final boolean wasDefault = isDefaultNetwork(nai);
    253             //if (wasDefault) {
    254             //    mDefaultInetConditionPublished = 0;
    255             //}
    256             //notifyIfacesChanged();
    257             // TODO - we shouldn't send CALLBACK_LOST to requests that can be satisfied
    258             // by other networks that are already connected. Perhaps that can be done by
    259             // sending all CALLBACK_LOST messages (for requests, not listens) at the end
    260             // of rematchAllNetworksAndRequests
    261             //notifyNetworkCallbacks(nai, ConnectivityManager.CALLBACK_LOST);
    262             //mKeepaliveTracker.handleStopAllKeepalives(nai,
    263             //       ConnectivityManager.PacketKeepalive.ERROR_INVALID_NETWORK);
    264             nai.networkMonitor.sendMessage(NetworkMonitor.CMD_NETWORK_DISCONNECTED);
    265             mNetworkAgentInfos.remove(msg.replyTo);
    266             //updateClat(null, nai.linkProperties, nai);
    267             //synchronized (mNetworkForNetId) {
    268             //    // Remove the NetworkAgent, but don't mark the netId as
    269             //    // available until we've told netd to delete it below.
    270             //    mNetworkForNetId.remove(nai.network.netId);
    271             //}
    272             // Remove all previously satisfied requests.
    273             //for (int i = 0; i < nai.networkRequests.size(); i++) {
    274             //    NetworkRequest request = nai.networkRequests.valueAt(i);
    275             //    NetworkAgentInfo currentNetwork = mNetworkForRequestId.get(request.requestId);
    276             //    if (currentNetwork != null && currentNetwork.network.netId == nai.network.netId) {
    277             //        mNetworkForRequestId.remove(request.requestId);
    278             //        sendUpdatedScoreToFactories(request, 0);
    279             //    }
    280             //}
    281             //if (nai.networkRequests.get(mDefaultRequest.requestId) != null) {
    282             //    removeDataActivityTracking(nai);
    283             //    notifyLockdownVpn(nai);
    284             //    requestNetworkTransitionWakelock(nai.name());
    285             //}
    286             //mLegacyTypeTracker.remove(nai, wasDefault);
    287             //rematchAllNetworksAndRequests(null, 0);
    288             //if (nai.created) {
    289             //    // Tell netd to clean up the configuration for this network
    290             //    // (routing rules, DNS, etc).
    291             //    // This may be slow as it requires a lot of netd shelling out to ip and
    292             //    // ip[6]tables to flush routes and remove the incoming packet mark rule, so do it
    293             //    // after we've rematched networks with requests which should make a potential
    294             //    // fallback network the default or requested a new network from the
    295             //    // NetworkFactories, so network traffic isn't interrupted for an unnecessarily
    296             //    // long time.
    297             //    try {
    298             //        mNetd.removeNetwork(nai.network.netId);
    299             //    } catch (Exception e) {
    300             //        loge("Exception removing network: " + e);
    301             //    }
    302             //}
    303             //synchronized (mNetworkForNetId) {
    304             //    mNetIdInUse.delete(nai.network.netId);
    305             //}
    306         } else {
    307             NetworkFactoryInfo nfi = mNetworkFactoryInfos.remove(msg.replyTo);
    308             if (DBG && nfi != null) log("unregisterNetworkFactory for " + nfi.name);
    309         }
    310     }
    311 
    312     private void log(String str) {
    313         Slog.d(TAG, str);
    314     }
    315     private void loge(String str) {
    316         Slog.e(TAG, str);
    317     }
    318 
    319     // NetworkAgentInfo keyed off its connecting messenger
    320     // TODO - eval if we can reduce the number of lists/hashmaps/sparsearrays
    321     // NOTE: Only should be accessed on ConnectivityServiceThread, except dump().
    322     private final HashMap<Messenger, NetworkAgentInfo> mNetworkAgentInfos =
    323             new HashMap<Messenger, NetworkAgentInfo>();
    324     private final HashMap<Messenger, NetworkFactoryInfo> mNetworkFactoryInfos =
    325             new HashMap<Messenger, NetworkFactoryInfo>();
    326     private final HashMap<NetworkRequest, NetworkRequestInfo> mNetworkRequests =
    327             new HashMap<NetworkRequest, NetworkRequestInfo>();
    328 
    329     private static class NetworkFactoryInfo {
    330         public final String name;
    331         public final Messenger messenger;
    332         public final AsyncChannel asyncChannel;
    333 
    334         public NetworkFactoryInfo(String name, Messenger messenger, AsyncChannel asyncChannel) {
    335             this.name = name;
    336             this.messenger = messenger;
    337             this.asyncChannel = asyncChannel;
    338         }
    339     }
    340 
    341     private class NetworkRequestInfo implements IBinder.DeathRecipient {
    342         static final boolean REQUEST = true;
    343         static final boolean LISTEN = false;
    344 
    345         final NetworkRequest request;
    346         final PendingIntent mPendingIntent;
    347         boolean mPendingIntentSent;
    348         private final IBinder mBinder;
    349         final int mPid;
    350         final int mUid;
    351         final Messenger messenger;
    352         final boolean isRequest;
    353 
    354         NetworkRequestInfo(NetworkRequest r, PendingIntent pi, boolean isRequest) {
    355             request = r;
    356             mPendingIntent = pi;
    357             messenger = null;
    358             mBinder = null;
    359             mPid = getCallingPid();
    360             mUid = getCallingUid();
    361             this.isRequest = isRequest;
    362         }
    363 
    364         NetworkRequestInfo(Messenger m, NetworkRequest r, IBinder binder, boolean isRequest) {
    365             super();
    366             messenger = m;
    367             request = r;
    368             mBinder = binder;
    369             mPid = getCallingPid();
    370             mUid = getCallingUid();
    371             this.isRequest = isRequest;
    372             mPendingIntent = null;
    373 
    374             try {
    375                 mBinder.linkToDeath(this, 0);
    376             } catch (RemoteException e) {
    377                 binderDied();
    378             }
    379         }
    380 
    381         void unlinkDeathRecipient() {
    382             if (mBinder != null) {
    383                 mBinder.unlinkToDeath(this, 0);
    384             }
    385         }
    386 
    387         public void binderDied() {
    388             log("ConnectivityService NetworkRequestInfo binderDied(" +
    389                     request + ", " + mBinder + ")");
    390             releaseNetworkRequest(request);
    391         }
    392 
    393         public String toString() {
    394             return (isRequest ? "Request" : "Listen") +
    395                     " from uid/pid:" + mUid + "/" + mPid +
    396                     " for " + request +
    397                     (mPendingIntent == null ? "" : " to trigger " + mPendingIntent);
    398         }
    399     }
    400 
    401 
    402     // sequence number of NetworkRequests
    403     private int mNextNetworkRequestId = 1;
    404     private synchronized int nextNetworkRequestId() {
    405         return mNextNetworkRequestId++;
    406     }
    407 
    408     @Override
    409     public NetworkInfo getActiveNetworkInfo() {
    410         throw new RuntimeException("not implemented");
    411     }
    412 
    413     @Override
    414     public Network getActiveNetwork() {
    415         throw new RuntimeException("not implemented");
    416     }
    417 
    418     @Override
    419     public Network getActiveNetworkForUid(int uid, boolean ignoreBlocked) {
    420         throw new RuntimeException("not implemented");
    421     }
    422 
    423     public NetworkInfo getActiveNetworkInfoUnfiltered() {
    424         throw new RuntimeException("not implemented");
    425     }
    426 
    427     @Override
    428     public NetworkInfo getActiveNetworkInfoForUid(int uid, boolean ignoreBlocked) {
    429         throw new RuntimeException("not implemented");
    430     }
    431 
    432     @Override
    433     public NetworkInfo getNetworkInfo(int networkType) {
    434         throw new RuntimeException("not implemented");
    435     }
    436 
    437     @Override
    438     public NetworkInfo getNetworkInfoForUid(Network network, int uid, boolean ignoreBlocked) {
    439         throw new RuntimeException("not implemented");
    440     }
    441 
    442     @Override
    443     public NetworkInfo[] getAllNetworkInfo() {
    444         throw new RuntimeException("not implemented");
    445     }
    446 
    447     @Override
    448     public Network getNetworkForType(int networkType) {
    449         throw new RuntimeException("not implemented");
    450     }
    451 
    452     @Override
    453     public Network[] getAllNetworks() {
    454         throw new RuntimeException("not implemented");
    455     }
    456 
    457     @Override
    458     public NetworkCapabilities[] getDefaultNetworkCapabilitiesForUser(int userId) {
    459         throw new RuntimeException("not implemented");
    460     }
    461 
    462     @Override
    463     public boolean isNetworkSupported(int networkType) {
    464         throw new RuntimeException("not implemented");
    465     }
    466 
    467     @Override
    468     public LinkProperties getActiveLinkProperties() {
    469         throw new RuntimeException("not implemented");
    470     }
    471 
    472     @Override
    473     public LinkProperties getLinkPropertiesForType(int networkType) {
    474         throw new RuntimeException("not implemented");
    475     }
    476 
    477     @Override
    478     public LinkProperties getLinkProperties(Network network) {
    479         throw new RuntimeException("not implemented");
    480     }
    481 
    482     @Override
    483     public NetworkCapabilities getNetworkCapabilities(Network network) {
    484         throw new RuntimeException("not implemented");
    485     }
    486 
    487     @Override
    488     public NetworkState[] getAllNetworkState() {
    489         throw new RuntimeException("not implemented");
    490     }
    491 
    492     @Override
    493     public NetworkQuotaInfo getActiveNetworkQuotaInfo() {
    494         throw new RuntimeException("not implemented");
    495     }
    496 
    497     @Override
    498     public boolean isActiveNetworkMetered() {
    499         throw new RuntimeException("not implemented");
    500     }
    501 
    502     public boolean requestRouteToHostAddress(int networkType, byte[] hostAddress) {
    503         throw new RuntimeException("not implemented");
    504     }
    505 
    506     @Override
    507     public int getRestoreDefaultNetworkDelay(int networkType) {
    508         throw new RuntimeException("not implemented");
    509     }
    510 
    511     @Override
    512     protected void dump(FileDescriptor fd, PrintWriter writer, String[] args) {
    513         throw new RuntimeException("not implemented");
    514     }
    515 
    516     public void setAcceptUnvalidated(Network network, boolean accept, boolean always) {
    517         throw new RuntimeException("not implemented");
    518     }
    519 
    520     public void setAvoidUnvalidated(Network network) {
    521         throw new RuntimeException("not implemented");
    522     }
    523 
    524     public void startCaptivePortalApp(Network network) {
    525         throw new RuntimeException("not implemented");
    526     }
    527 
    528     public int getMultipathPreference(Network network) {
    529         throw new RuntimeException("not implemented");
    530     }
    531 
    532     public int tether(String iface, String callerPkg) {
    533         throw new RuntimeException("not implemented");
    534     }
    535 
    536     public int untether(String iface, String callerPkg) {
    537         throw new RuntimeException("not implemented");
    538     }
    539 
    540     public int getLastTetherError(String iface) {
    541         throw new RuntimeException("not implemented");
    542     }
    543 
    544     public String[] getTetherableUsbRegexs() {
    545         throw new RuntimeException("not implemented");
    546     }
    547 
    548     public String[] getTetherableWifiRegexs() {
    549         throw new RuntimeException("not implemented");
    550     }
    551 
    552     public String[] getTetherableBluetoothRegexs() {
    553         throw new RuntimeException("not implemented");
    554     }
    555 
    556     public int setUsbTethering(boolean enable, String callerPkg) {
    557         throw new RuntimeException("not implemented");
    558     }
    559 
    560     public String[] getTetherableIfaces() {
    561         throw new RuntimeException("not implemented");
    562     }
    563 
    564     public String[] getTetheredIfaces() {
    565         throw new RuntimeException("not implemented");
    566     }
    567 
    568     public String[] getTetheringErroredIfaces() {
    569         throw new RuntimeException("not implemented");
    570     }
    571 
    572     public String[] getTetheredDhcpRanges() {
    573         throw new RuntimeException("not implemented");
    574     }
    575 
    576     @Override
    577     public boolean isTetheringSupported(String callerPkg) {
    578         throw new RuntimeException("not implemented");
    579     }
    580 
    581     @Override
    582     public void startTethering(int type, ResultReceiver receiver, boolean showProvisioningUi,
    583             String callerPkg) {
    584         throw new RuntimeException("not implemented");
    585     }
    586 
    587     @Override
    588     public void stopTethering(int type, String callerPkg) {
    589         throw new RuntimeException("not implemented");
    590     }
    591 
    592 
    593     public void reportInetCondition(int networkType, int percentage) {
    594         throw new RuntimeException("not implemented");
    595     }
    596 
    597     public void reportNetworkConnectivity(Network network, boolean hasConnectivity) {
    598         throw new RuntimeException("not implemented");
    599     }
    600 
    601     public ProxyInfo getProxyForNetwork(Network network) {
    602         throw new RuntimeException("not implemented");
    603     }
    604 
    605     public void setGlobalProxy(ProxyInfo proxyProperties) {
    606         throw new RuntimeException("not implemented");
    607     }
    608 
    609     public ProxyInfo getGlobalProxy() {
    610         throw new RuntimeException("not implemented");
    611     }
    612 
    613     @Override
    614     public boolean prepareVpn(@Nullable String oldPackage, @Nullable String newPackage,
    615             int userId) {
    616         throw new RuntimeException("not implemented");
    617     }
    618 
    619     public void setVpnPackageAuthorization(String packageName, int userId, boolean authorized) {
    620         throw new RuntimeException("not implemented");
    621     }
    622 
    623     @Override
    624     public ParcelFileDescriptor establishVpn(VpnConfig config) {
    625         throw new RuntimeException("not implemented");
    626     }
    627 
    628     @Override
    629     public void startLegacyVpn(VpnProfile profile) {
    630         throw new RuntimeException("not implemented");
    631     }
    632 
    633     @Override
    634     public LegacyVpnInfo getLegacyVpnInfo(int userId) {
    635         throw new RuntimeException("not implemented");
    636     }
    637 
    638     @Override
    639     public VpnInfo[] getAllVpnInfo() {
    640         throw new RuntimeException("not implemented");
    641     }
    642 
    643     @Override
    644     public VpnConfig getVpnConfig(int userId) {
    645         throw new RuntimeException("not implemented");
    646     }
    647 
    648     @Override
    649     public boolean updateLockdownVpn() {
    650         throw new RuntimeException("not implemented");
    651     }
    652 
    653     @Override
    654     public boolean isAlwaysOnVpnPackageSupported(int userId, String packageName) {
    655         throw new RuntimeException("not implemented");
    656     }
    657 
    658     @Override
    659     public boolean setAlwaysOnVpnPackage(int userId, String packageName, boolean lockdownEnabled) {
    660         throw new RuntimeException("not implemented");
    661     }
    662 
    663     @Override
    664     public String getAlwaysOnVpnPackage(int userId) {
    665         throw new RuntimeException("not implemented");
    666     }
    667 
    668     @Override
    669     public int checkMobileProvisioning(int suggestedTimeOutMs) {
    670         throw new RuntimeException("not implemented");
    671     }
    672 
    673     @Override
    674     public String getMobileProvisioningUrl() {
    675         throw new RuntimeException("not implemented");
    676     }
    677 
    678     @Override
    679     public void setProvisioningNotificationVisible(boolean visible, int networkType,
    680             String action) {
    681         throw new RuntimeException("not implemented");
    682     }
    683 
    684     @Override
    685     public void setAirplaneMode(boolean enable) {
    686         throw new RuntimeException("not implemented");
    687     }
    688 
    689     @Override
    690     public NetworkRequest requestNetwork(NetworkCapabilities networkCapabilities,
    691             Messenger messenger, int timeoutMs, IBinder binder, int legacyType) {
    692         networkCapabilities = new NetworkCapabilities(networkCapabilities);
    693 
    694         if (timeoutMs < 0) {
    695             throw new IllegalArgumentException("Bad timeout specified");
    696         }
    697 
    698         NetworkRequest networkRequest = new NetworkRequest(networkCapabilities, legacyType,
    699                 nextNetworkRequestId(), NetworkRequest.Type.REQUEST);
    700         NetworkRequestInfo nri = new NetworkRequestInfo(messenger, networkRequest, binder, true);
    701         if (DBG) log("requestNetwork for " + nri);
    702 
    703         mHandler.sendMessage(mHandler.obtainMessage(EVENT_REGISTER_NETWORK_REQUEST, nri));
    704 
    705         return networkRequest;
    706     }
    707 
    708     @Override
    709     public boolean requestBandwidthUpdate(Network network) {
    710         throw new RuntimeException("not implemented");
    711     }
    712 
    713 
    714     @Override
    715     public NetworkRequest pendingRequestForNetwork(NetworkCapabilities networkCapabilities,
    716             PendingIntent operation) {
    717         throw new RuntimeException("not implemented");
    718     }
    719 
    720     @Override
    721     public void releasePendingNetworkRequest(PendingIntent operation) {
    722         throw new RuntimeException("not implemented");
    723     }
    724 
    725     @Override
    726     public NetworkRequest listenForNetwork(NetworkCapabilities networkCapabilities,
    727             Messenger messenger, IBinder binder) {
    728         throw new RuntimeException("not implemented");
    729     }
    730 
    731     @Override
    732     public void pendingListenForNetwork(NetworkCapabilities networkCapabilities,
    733             PendingIntent operation) {
    734         throw new RuntimeException("not implemented");
    735     }
    736 
    737     @Override
    738     public void releaseNetworkRequest(NetworkRequest networkRequest) {
    739         mHandler.sendMessage(mHandler.obtainMessage(EVENT_RELEASE_NETWORK_REQUEST, getCallingUid(),
    740                 0, networkRequest));
    741     }
    742 
    743     @Override
    744     public void registerNetworkFactory(Messenger messenger, String name) {
    745         NetworkFactoryInfo nfi = new NetworkFactoryInfo(name, messenger, new AsyncChannel());
    746         mHandler.sendMessage(mHandler.obtainMessage(EVENT_REGISTER_NETWORK_FACTORY, nfi));
    747     }
    748 
    749     private void handleRegisterNetworkFactory(NetworkFactoryInfo nfi) {
    750         if (DBG) log("Got NetworkFactory Messenger for " + nfi.name);
    751         mNetworkFactoryInfos.put(nfi.messenger, nfi);
    752         nfi.asyncChannel.connect(mContext, mTrackerHandler, nfi.messenger);
    753     }
    754 
    755     @Override
    756     public void unregisterNetworkFactory(Messenger messenger) {
    757         mHandler.sendMessage(mHandler.obtainMessage(EVENT_UNREGISTER_NETWORK_FACTORY, messenger));
    758     }
    759 
    760     @Override
    761     public byte[] getNetworkWatchlistConfigHash() {
    762         throw new RuntimeException("not implemented");
    763     }
    764 
    765     private void handleUnregisterNetworkFactory(Messenger messenger) {
    766         NetworkFactoryInfo nfi = mNetworkFactoryInfos.remove(messenger);
    767         if (nfi == null) {
    768             loge("Failed to find Messenger in unregisterNetworkFactory");
    769             return;
    770         }
    771         if (DBG) log("unregisterNetworkFactory for " + nfi.name);
    772     }
    773 
    774     public int registerNetworkAgent(Messenger messenger, NetworkInfo networkInfo,
    775             LinkProperties linkProperties, NetworkCapabilities networkCapabilities,
    776             int currentScore, NetworkMisc networkMisc) {
    777 //        final NetworkAgentInfo nai = new NetworkAgentInfo(messenger, new AsyncChannel(),
    778 //                new Network(reserveNetId()), new NetworkInfo(networkInfo), new LinkProperties(
    779 //                linkProperties), new NetworkCapabilities(networkCapabilities), currentScore,
    780 //                mContext, mTrackerHandler, new NetworkMisc(networkMisc), mDefaultRequest, this);
    781 //        synchronized (this) {
    782 //            nai.networkMonitor.systemReady = mSystemReady;
    783 //        }
    784 //        mHandler.sendMessage(mHandler.obtainMessage(EVENT_REGISTER_NETWORK_AGENT, nai));
    785 //        return nai.network.netId;
    786         throw new RuntimeException("not implemented");
    787     }
    788 
    789     private void handleRegisterNetworkAgent(NetworkAgentInfo na) {
    790         if (VDBG) log("Got NetworkAgent Messenger");
    791 //        mNetworkAgentInfos.put(na.messenger, na);
    792 //        synchronized (mNetworkForNetId) {
    793 //            mNetworkForNetId.put(na.network.netId, na);
    794 //        }
    795 //        na.asyncChannel.connect(mContext, mTrackerHandler, na.messenger);
    796 //        NetworkInfo networkInfo = na.networkInfo;
    797 //        na.networkInfo = null;
    798 //        updateNetworkInfo(na, networkInfo);
    799     }
    800 
    801 
    802     private void handleRegisterNetworkRequest(NetworkRequestInfo nri) {
    803         mNetworkRequests.put(nri.request, nri);
    804         if (!nri.isRequest) {
    805             for (NetworkAgentInfo network : mNetworkAgentInfos.values()) {
    806                 if (nri.request.networkCapabilities.hasSignalStrength() &&
    807                         network.satisfiesImmutableCapabilitiesOf(nri.request)) {
    808                 }
    809             }
    810         }
    811         rematchAllNetworksAndRequests(null, 0);
    812         if (nri.isRequest) {
    813             sendUpdatedScoreToFactories(nri.request, 0);
    814         }
    815     }
    816 
    817     private void handleReleaseNetworkRequest(NetworkRequest request, int callingUid) {
    818         NetworkRequestInfo nri = mNetworkRequests.get(request);
    819         if (nri != null) {
    820             if (DBG) log("releasing NetworkRequest " + request);
    821             nri.unlinkDeathRecipient();
    822             mNetworkRequests.remove(request);
    823             if (nri.isRequest) {
    824                 // Find all networks that are satisfying this request and remove the request
    825                 // from their request lists.
    826                 // TODO - it's my understanding that for a request there is only a single
    827                 // network satisfying it, so this loop is wasteful
    828                 //boolean wasKept = false;
    829                 //for (NetworkAgentInfo nai : mNetworkAgentInfos.values()) {
    830                 //    if (nai.networkRequests.get(nri.request.requestId) != null) {
    831                 //        nai.networkRequests.remove(nri.request.requestId);
    832                 //        if (DBG) {
    833                 //            log(" Removing from current network " + nai.name() +
    834                 //                    ", leaving " + nai.networkRequests.size() +
    835                 //                    " requests.");
    836                 //        }
    837                 //        if (unneeded(nai)) {
    838                 //            if (DBG) log("no live requests for " + nai.name() + "; disconnecting");
    839                 //            teardownUnneededNetwork(nai);
    840                 //        } else {
    841                 //            // suspect there should only be one pass through here
    842                 //            // but if any were kept do the check below
    843                 //            wasKept |= true;
    844                 //        }
    845                 //    }
    846                 //}
    847 
    848                 //NetworkAgentInfo nai = mNetworkForRequestId.get(nri.request.requestId);
    849                 //if (nai != null) {
    850                 //    mNetworkForRequestId.remove(nri.request.requestId);
    851                 //}
    852                 // Maintain the illusion.  When this request arrived, we might have pretended
    853                 // that a network connected to serve it, even though the network was already
    854                 // connected.  Now that this request has gone away, we might have to pretend
    855                 // that the network disconnected.  LegacyTypeTracker will generate that
    856                 // phantom disconnect for this type.
    857                 //if (nri.request.legacyType != TYPE_NONE && nai != null) {
    858                 //    boolean doRemove = true;
    859                 //    if (wasKept) {
    860                 //        // check if any of the remaining requests for this network are for the
    861                 //        // same legacy type - if so, don't remove the nai
    862                 //        for (int i = 0; i < nai.networkRequests.size(); i++) {
    863                 //            NetworkRequest otherRequest = nai.networkRequests.valueAt(i);
    864                 //            if (otherRequest.legacyType == nri.request.legacyType &&
    865                 //                    isRequest(otherRequest)) {
    866                 //                if (DBG) log(" still have other legacy request - leaving");
    867                 //                doRemove = false;
    868                 //            }
    869                 //        }
    870                 //    }
    871                 //
    872                 //    if (doRemove) {
    873                 //        mLegacyTypeTracker.remove(nri.request.legacyType, nai, false);
    874                 //    }
    875                 //}
    876 
    877                 for (NetworkFactoryInfo nfi : mNetworkFactoryInfos.values()) {
    878                     nfi.asyncChannel.sendMessage(android.net.NetworkFactory.CMD_CANCEL_REQUEST,
    879                             nri.request);
    880                 }
    881             } else {
    882                 // listens don't have a singular affectedNetwork.  Check all networks to see
    883                 // if this listen request applies and remove it.
    884                 //for (NetworkAgentInfo nai : mNetworkAgentInfos.values()) {
    885                 //    nai.networkRequests.remove(nri.request.requestId);
    886                 //    if (nri.request.networkCapabilities.hasSignalStrength() &&
    887                 //            nai.satisfiesImmutableCapabilitiesOf(nri.request)) {
    888                 //        updateSignalStrengthThresholds(nai, "RELEASE", nri.request);
    889                 //    }
    890                 //}
    891             }
    892             //callCallbackForRequest(nri, null, ConnectivityManager.CALLBACK_RELEASED);
    893         }
    894     }
    895 
    896     private void sendUpdatedScoreToFactories(NetworkAgentInfo nai) {
    897         for (int i = 0; i < nai.numNetworkRequests(); i++) {
    898             NetworkRequest nr = nai.requestAt(i);
    899             // Don't send listening requests to factories. b/17393458
    900             if (!isRequest(nr)) continue;
    901                 sendUpdatedScoreToFactories(nr, nai.getCurrentScore());
    902         }
    903     }
    904 
    905     private void sendUpdatedScoreToFactories(NetworkRequest networkRequest, int score) {
    906         if (VDBG) log("sending new Min Network Score(" + score + "): " + networkRequest.toString());
    907         for (NetworkFactoryInfo nfi : mNetworkFactoryInfos.values()) {
    908             nfi.asyncChannel.sendMessage(android.net.NetworkFactory.CMD_REQUEST_NETWORK, score, 0,
    909                     networkRequest);
    910         }
    911     }
    912 
    913     private void rematchAllNetworksAndRequests(NetworkAgentInfo changed, int oldScore) {
    914     }
    915 
    916     @Override
    917     public void onSendFinished(PendingIntent pendingIntent, Intent intent, int resultCode,
    918             String resultData, Bundle resultExtras) {
    919         throw new RuntimeException("not implemented");
    920     }
    921 
    922     @Override
    923     public boolean addVpnAddress(String address, int prefixLength) {
    924         throw new RuntimeException("not implemented");
    925     }
    926 
    927     @Override
    928     public boolean removeVpnAddress(String address, int prefixLength) {
    929         throw new RuntimeException("not implemented");
    930     }
    931 
    932     @Override
    933     public boolean setUnderlyingNetworksForVpn(Network[] networks) {
    934         throw new RuntimeException("not implemented");
    935     }
    936 
    937     @Override
    938     public String getCaptivePortalServerUrl() {
    939         throw new RuntimeException("not implemented");
    940     }
    941 
    942     @Override
    943     public void startNattKeepalive(Network network, int intervalSeconds, Messenger messenger,
    944             IBinder binder, String srcAddr, int srcPort, String dstAddr) {
    945         throw new RuntimeException("not implemented");
    946     }
    947 
    948     @Override
    949     public void stopKeepalive(Network network, int slot) {
    950         throw new RuntimeException("not implemented");
    951     }
    952 
    953     @Override
    954     public void factoryReset() {
    955         throw new RuntimeException("not implemented");
    956     }
    957 
    958     @VisibleForTesting
    959     public NetworkMonitor createNetworkMonitor(Context context, Handler handler,
    960             NetworkAgentInfo nai, NetworkRequest defaultRequest) {
    961         throw new RuntimeException("not implemented");
    962     }
    963 
    964     @VisibleForTesting
    965     public NetworkRequest defaultRequest = null;
    966     @VisibleForTesting
    967     public synchronized void addDefaultRequest() {
    968         if (defaultRequest != null) return;
    969         NetworkCapabilities netCap = new NetworkCapabilities();
    970         netCap.addCapability(NET_CAPABILITY_INTERNET);
    971         netCap.addCapability(NET_CAPABILITY_NOT_RESTRICTED);
    972         defaultRequest = requestNetwork(netCap, null, 0, new Binder(),
    973                 ConnectivityManager.TYPE_NONE);
    974     }
    975 
    976     @VisibleForTesting
    977     public synchronized void setCurrentScoreForRequest(NetworkRequest nr, int score) {
    978         sendUpdatedScoreToFactories(nr, score);
    979     }
    980 
    981     @VisibleForTesting
    982     public synchronized void removeDefaultRequest() {
    983         if (defaultRequest == null) return;
    984         releaseNetworkRequest(defaultRequest);
    985         defaultRequest = null;
    986     }
    987 
    988 
    989 }
    990