]> git.ipfire.org Git - thirdparty/strongswan.git/commitdiff
android: Replace deprecated CONNECTIVITY_ACTION on newer Android versions
authorTobias Brunner <tobias@strongswan.org>
Mon, 14 Oct 2019 13:03:10 +0000 (15:03 +0200)
committerTobias Brunner <tobias@strongswan.org>
Tue, 15 Oct 2019 15:07:02 +0000 (17:07 +0200)
It was deprecated in API level 28, registerNetworkCallback is available
since API level 21, but ConnectivityManager got some updates with 24
(e.g. default network handling) so we start using it then.

src/frontends/android/app/src/main/java/org/strongswan/android/logic/NetworkManager.java

index abe6293224cbe87b6fe821c39f907c88e3180fd5..e283cd56d7f2f0980eb4cd30cc397cdbd772e495 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * Copyright (C) 2012-2015 Tobias Brunner
+ * Copyright (C) 2012-2019 Tobias Brunner
  * HSR Hochschule fuer Technik Rapperswil
  *
  * This program is free software; you can redistribute it and/or modify it
@@ -20,7 +20,10 @@ import android.content.Context;
 import android.content.Intent;
 import android.content.IntentFilter;
 import android.net.ConnectivityManager;
+import android.net.Network;
 import android.net.NetworkInfo;
+import android.net.NetworkRequest;
+import android.os.Build;
 
 import java.util.LinkedList;
 
@@ -28,12 +31,45 @@ public class NetworkManager extends BroadcastReceiver implements Runnable
 {
        private final Context mContext;
        private volatile boolean mRegistered;
+       private ConnectivityManager.NetworkCallback mCallback;
        private Thread mEventNotifier;
+       private int mConnectedNetworks = 0;
        private LinkedList<Boolean> mEvents = new LinkedList<>();
 
        public NetworkManager(Context context)
        {
                mContext = context;
+
+               if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N)
+               {
+                       mCallback = new ConnectivityManager.NetworkCallback()
+                       {
+                               @Override
+                               public void onAvailable(Network network)
+                               {
+                                       synchronized (NetworkManager.this)
+                                       {
+                                               /* we expect this to be called if connected to at least one network during
+                                                * callback registration */
+                                               mConnectedNetworks += 1;
+                                               mEvents.addLast(true);
+                                               NetworkManager.this.notifyAll();
+                                       }
+                               }
+
+                               @Override
+                               public void onLost(Network network)
+                               {
+                                       synchronized (NetworkManager.this)
+                                       {
+                                               /* in particular mobile connections are disconnected overlapping with WiFi */
+                                               mConnectedNetworks -= 1;
+                                               mEvents.addLast(mConnectedNetworks > 0);
+                                               NetworkManager.this.notifyAll();
+                                       }
+                               }
+                       };
+               }
        }
 
        public void Register()
@@ -42,12 +78,38 @@ public class NetworkManager extends BroadcastReceiver implements Runnable
                mRegistered = true;
                mEventNotifier = new Thread(this);
                mEventNotifier.start();
+               if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N)
+               {
+                       ConnectivityManager cm = mContext.getSystemService(ConnectivityManager.class);
+                       /* while we only get events for the VPN network via registerDefaultNetworkCallback,
+                        * the default capabilities in the builder include NetworkCapabilities.NET_CAPABILITY_NOT_VPN */
+                       NetworkRequest.Builder builder = new NetworkRequest.Builder();
+                       cm.registerNetworkCallback(builder.build(), mCallback);
+               }
+               else
+               {
+                       registerLegacyReceiver();
+               }
+       }
+
+       @SuppressWarnings("deprecation")
+       private void registerLegacyReceiver()
+       {
+               /* deprecated since API level 28 */
                mContext.registerReceiver(this, new IntentFilter(ConnectivityManager.CONNECTIVITY_ACTION));
        }
 
        public void Unregister()
        {
-               mContext.unregisterReceiver(this);
+               if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N)
+               {
+                       ConnectivityManager cm = mContext.getSystemService(ConnectivityManager.class);
+                       cm.unregisterNetworkCallback(mCallback);
+               }
+               else
+               {
+                       mContext.unregisterReceiver(this);
+               }
                mRegistered = false;
                synchronized (this)
                {