diff --git a/README.md b/README.md
index 978038175b68d47ea218361535daa633713902b2..823eb48ba36ce3a35666460ed56d5d7ff1b3e2bc 100644
--- a/README.md
+++ b/README.md
@@ -104,7 +104,7 @@ export PATH=$ANDROID_HOME/tools/bin:$PATH
 
 Geesh! If all that above seems like a lot, it is!
 
-To keep ourselves from messing it up all the time someone new joins the project, we made a Dockerfile that creates the above environment with one line. You can pull the image and run builds from inside it, or consult the [Dockerfile](/docker/android-sdk.dockerfile) itself for requirements that your system might need but be missing.
+To keep ourselves from messing it up all the time someone new joins the project, we made a Dockerfile that creates the above environment with one line. You can pull the image and run builds from inside it, or consult [android-sdk Dockerfile](/docker/android-sdk/Dockerfile) and [android-ndk Dockerfile](/docker/android-ndk/Dockerfile) itself for requirements that your system might need but be missing.
 
 Assuming you've already [installed docker](https://docs.docker.com/engine/installation/), you can pull the image with:
 
@@ -143,18 +143,23 @@ git submodule update --init --recursive
 
 ### Just Build It! <a name="just-build-it"></a>
 
-If you compile the project for the first time you'll have to compile the dependencies. This can be done with:
+If you compile the project for the first time you'll have to compile the dependencies.
+In order to get a clean build and fetch all submodules run:
+```
+./cleanProject.sh
+```
 
+The following command will create all libs we need for Bitmask.
 ```
 ./scripts/build_deps.sh
 ```
-This command will create all libs we need for Bitmask.
  
-If you want to to have a clean build of all submodules run
+If you run into errors, you may miss some dependencies on your system. Again, please check the `RUN apt-get` commands of [android-sdk Dockerfile](/docker/android-sdk/Dockerfile) and [android-ndk Dockerfile](/docker/android-ndk/Dockerfile) to get an idea what might be missing.
+Please note that tor-android can only be build on Linux machines right now. Fixes for Windows and MacOS are more than welcome!
+In order to temporarily disable building tor you can run:
 ```
-./cleanProject.sh
+BUILD_TOR=false ./scripts/build_deps.sh
 ```
-before you call `./build_deps.sh`. That script removes all build files and does the git submodule init and update job for you.  
 
 ### Debug APKs <a name="debug-apks"></a>
 
diff --git a/app/src/main/java/de/blinkt/openvpn/VpnProfile.java b/app/src/main/java/de/blinkt/openvpn/VpnProfile.java
index 7dd7543216aa276cc7445572141e5886d71b6bad..83cde85e7ccd7dba24ca8f546d0f0ce0894a8883 100644
--- a/app/src/main/java/de/blinkt/openvpn/VpnProfile.java
+++ b/app/src/main/java/de/blinkt/openvpn/VpnProfile.java
@@ -473,9 +473,6 @@ public class VpnProfile implements Serializable, Cloneable {
                         cfg.append("management-external-key nopadding\n");
                     } else {
                         cfg.append(context.getString(R.string.keychain_access)).append("\n");
-                        if (Build.VERSION.SDK_INT == Build.VERSION_CODES.JELLY_BEAN)
-                            if (!mAlias.matches("^[a-zA-Z0-9]$"))
-                                cfg.append(context.getString(R.string.jelly_keystore_alphanumeric_bug)).append("\n");
                     }
                 }
                 break;
@@ -932,11 +929,6 @@ public class VpnProfile implements Serializable, Cloneable {
             VpnStatus.logError(R.string.keyChainAccessError, e.getLocalizedMessage());
 
             VpnStatus.logError(R.string.keychain_access);
-            if (Build.VERSION.SDK_INT == Build.VERSION_CODES.JELLY_BEAN) {
-                if (!mAlias.matches("^[a-zA-Z0-9]$")) {
-                    VpnStatus.logError(R.string.jelly_keystore_alphanumeric_bug);
-                }
-            }
             return null;
 
         } catch (AssertionError e) {
@@ -1196,12 +1188,6 @@ public class VpnProfile implements Serializable, Cloneable {
     private byte[] getKeyChainSignedData(byte[] data, boolean pkcs1padding) {
 
         PrivateKey privkey = getKeystoreKey();
-        // The Jelly Bean *evil* Hack
-        // 4.2 implements the RSA/ECB/PKCS1PADDING in the OpenSSLprovider
-        if (Build.VERSION.SDK_INT == Build.VERSION_CODES.JELLY_BEAN) {
-            return processSignJellyBeans(privkey, data);
-        }
-
 
         try {
             @SuppressLint("GetInstance")
@@ -1238,32 +1224,6 @@ public class VpnProfile implements Serializable, Cloneable {
         }
     }
 
-    private byte[] processSignJellyBeans(PrivateKey privkey, byte[] data) {
-        try {
-            Method getKey = privkey.getClass().getSuperclass().getDeclaredMethod("getOpenSSLKey");
-            getKey.setAccessible(true);
-
-            // Real object type is OpenSSLKey
-            Object opensslkey = getKey.invoke(privkey);
-
-            getKey.setAccessible(false);
-
-            Method getPkeyContext = opensslkey.getClass().getDeclaredMethod("getPkeyContext");
-
-            // integer pointer to EVP_pkey
-            getPkeyContext.setAccessible(true);
-            int pkey = (Integer) getPkeyContext.invoke(opensslkey);
-            getPkeyContext.setAccessible(false);
-
-            // 112 with TLS 1.2 (172 back with 4.3), 36 with TLS 1.0
-            return NativeUtils.rsasign(data, pkey);
-
-        } catch (NoSuchMethodException | InvalidKeyException | InvocationTargetException | IllegalAccessException | IllegalArgumentException e) {
-            VpnStatus.logError(R.string.error_rsa_sign, e.getClass().toString(), e.getLocalizedMessage());
-            return null;
-        }
-    }
-
     private boolean usesExtraProxyOptions() {
         if (mUseCustomConfig && mCustomConfigOptions != null && mCustomConfigOptions.contains("http-proxy-option "))
             return true;
diff --git a/app/src/main/java/de/blinkt/openvpn/core/NativeUtils.java b/app/src/main/java/de/blinkt/openvpn/core/NativeUtils.java
index 5a1757ac6eab9e342cb59db6542477c1f9fed5d7..f769b38e6c4284c28498a686509c650557164e9f 100644
--- a/app/src/main/java/de/blinkt/openvpn/core/NativeUtils.java
+++ b/app/src/main/java/de/blinkt/openvpn/core/NativeUtils.java
@@ -38,8 +38,6 @@ public class NativeUtils {
     static {
         if (!isRoboUnitTest() && !isUnitTest()) {
             System.loadLibrary("ovpnutil");
-            if (Build.VERSION.SDK_INT == Build.VERSION_CODES.JELLY_BEAN)
-                System.loadLibrary("jbcrypto");
         }
     }
 
diff --git a/app/src/main/java/de/blinkt/openvpn/core/NetworkSpace.java b/app/src/main/java/de/blinkt/openvpn/core/NetworkSpace.java
index 860897db440a625a1783bf0e40637a120d892470..457ae9714d417368a4aba89d41b8a3359362add1 100644
--- a/app/src/main/java/de/blinkt/openvpn/core/NetworkSpace.java
+++ b/app/src/main/java/de/blinkt/openvpn/core/NetworkSpace.java
@@ -336,35 +336,6 @@ public class NetworkSpace {
                 ips.add(ia);
         }
 
-        if (Build.VERSION.SDK_INT < Build.VERSION_CODES.KITKAT) {
-            // Include postive routes from the original set under < 4.4 since these might overrule the local
-            // network but only if no smaller negative route exists
-            for (IpAddress origIp : mIpAddresses) {
-                if (!origIp.included)
-                    continue;
-
-                // The netspace exists
-                if (ipsSorted.contains(origIp))
-                    continue;
-
-                boolean skipIp = false;
-                // If there is any smaller net that is excluded we may not add the positive route back
-
-                for (IpAddress calculatedIp : ipsSorted) {
-                    if (!calculatedIp.included && origIp.containsNet(calculatedIp)) {
-                        skipIp = true;
-                        break;
-                    }
-                }
-                if (skipIp)
-                    continue;
-
-                // It is safe to include the IP
-                ips.add(origIp);
-            }
-
-        }
-
         return ips;
     }
 
diff --git a/app/src/main/java/de/blinkt/openvpn/core/NetworkUtils.java b/app/src/main/java/de/blinkt/openvpn/core/NetworkUtils.java
index 5b11c0a074d5ddb850f2a089209c4c08e02ef3d6..25af6121cbe0c8b5c2ab2cc6020db32bea0633e3 100644
--- a/app/src/main/java/de/blinkt/openvpn/core/NetworkUtils.java
+++ b/app/src/main/java/de/blinkt/openvpn/core/NetworkUtils.java
@@ -24,63 +24,35 @@ public class NetworkUtils {
     public static Vector<String> getLocalNetworks(Context c, boolean ipv6) {
         Vector<String> nets = new Vector<>();
         ConnectivityManager conn = (ConnectivityManager) c.getSystemService(Context.CONNECTIVITY_SERVICE);
-        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
-            Network[] networks = conn.getAllNetworks();
-            for (Network network : networks) {
-                try {
-                    NetworkInfo ni = conn.getNetworkInfo(network);
-                    LinkProperties li = conn.getLinkProperties(network);
+        Network[] networks = conn.getAllNetworks();
+        for (Network network : networks) {
+            try {
+                NetworkInfo ni = conn.getNetworkInfo(network);
+                LinkProperties li = conn.getLinkProperties(network);
 
-                    NetworkCapabilities nc = conn.getNetworkCapabilities(network);
+                NetworkCapabilities nc = conn.getNetworkCapabilities(network);
 
-                    if (nc == null) {
-                        continue;
-                    }
-
-                    // Skip VPN networks like ourselves
-                    if (nc.hasTransport(NetworkCapabilities.TRANSPORT_VPN))
-                        continue;
-
-                    // Also skip mobile networks
-                    if (nc.hasTransport(NetworkCapabilities.TRANSPORT_CELLULAR))
-                        continue;
-
-
-                    for (LinkAddress la : li.getLinkAddresses()) {
-                        if ((la.getAddress() instanceof Inet4Address && !ipv6) ||
-                                (la.getAddress() instanceof Inet6Address && ipv6))
-                            nets.add(la.toString());
-                    }
-                } catch (SecurityException se) {
-                    se.printStackTrace();
+                if (nc == null) {
+                    continue;
                 }
-            }
-        } else {
-            // Old Android Version, use native utils via ifconfig instead
-            // Add local network interfaces
-            if (ipv6)
-                return nets;
 
-            String[] localRoutes = NativeUtils.getIfconfig();
-
-            // The format of mLocalRoutes is kind of broken because I don't really like JNI
-            for (int i = 0; i < localRoutes.length; i += 3) {
-                String intf = localRoutes[i];
-                String ipAddr = localRoutes[i + 1];
-                String netMask = localRoutes[i + 2];
-
-                if (intf == null || intf.equals("lo") ||
-                        intf.startsWith("tun") || intf.startsWith("rmnet"))
+                // Skip VPN networks like ourselves
+                if (nc.hasTransport(NetworkCapabilities.TRANSPORT_VPN))
                     continue;
 
-                if (ipAddr == null || netMask == null) {
-                    VpnStatus.logError("Local routes are broken?! (Report to author) " + TextUtils.join("|", localRoutes));
+                // Also skip mobile networks
+                if (nc.hasTransport(NetworkCapabilities.TRANSPORT_CELLULAR))
                     continue;
-                }
-                nets.add(ipAddr + "/" + CIDRIP.calculateLenFromMask(netMask));
 
-            }
 
+                for (LinkAddress la : li.getLinkAddresses()) {
+                    if ((la.getAddress() instanceof Inet4Address && !ipv6) ||
+                            (la.getAddress() instanceof Inet6Address && ipv6))
+                        nets.add(la.toString());
+                }
+            } catch (SecurityException se) {
+                se.printStackTrace();
+            }
         }
         return nets;
     }
diff --git a/app/src/main/java/de/blinkt/openvpn/core/OpenVPNService.java b/app/src/main/java/de/blinkt/openvpn/core/OpenVPNService.java
index 88a85de3d81e540163bfa99c138af631d1536908..0ae7639e40d08df1f66dfe857afb5ec628b33f42 100644
--- a/app/src/main/java/de/blinkt/openvpn/core/OpenVPNService.java
+++ b/app/src/main/java/de/blinkt/openvpn/core/OpenVPNService.java
@@ -589,7 +589,7 @@ public class OpenVPNService extends VpnService implements StateListener, Callbac
 
         VpnStatus.logInfo(R.string.last_openvpn_tun_config);
 
-        boolean allowUnsetAF = Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP && !mProfile.mBlockUnusedAddressFamilies;
+        boolean allowUnsetAF = !mProfile.mBlockUnusedAddressFamilies;
         if (allowUnsetAF) {
             allowAllAFFamilies(builder);
         }
@@ -631,20 +631,12 @@ public class OpenVPNService extends VpnService implements StateListener, Callbac
             }
         }
 
-        String release = Build.VERSION.RELEASE;
-        if ((Build.VERSION.SDK_INT == Build.VERSION_CODES.KITKAT && !release.startsWith("4.4.3")
-                && !release.startsWith("4.4.4") && !release.startsWith("4.4.5") && !release.startsWith("4.4.6"))
-                && mMtu < 1280) {
-            VpnStatus.logInfo(String.format(Locale.US, "Forcing MTU to 1280 instead of %d to workaround Android Bug #70916", mMtu));
-            builder.setMtu(1280);
-        } else {
-            builder.setMtu(mMtu);
-        }
+        builder.setMtu(mMtu);
 
         Collection<IpAddress> positiveIPv4Routes = mRoutes.getPositiveIPList();
         Collection<IpAddress> positiveIPv6Routes = mRoutesv6.getPositiveIPList();
 
-        if ("samsung".equals(Build.BRAND) && Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP && mDnslist.size() >= 1) {
+        if ("samsung".equals(Build.BRAND) && mDnslist.size() >= 1) {
             // Check if the first DNS Server is in the VPN range
             try {
                 IpAddress dnsServer = new IpAddress(new CIDRIP(mDnslist.get(0), 32), true);
@@ -725,9 +717,8 @@ public class OpenVPNService extends VpnService implements StateListener, Callbac
         VpnStatus.logInfo(R.string.routes_info_incl, TextUtils.join(", ", mRoutes.getNetworks(true)), TextUtils.join(", ", mRoutesv6.getNetworks(true)));
         VpnStatus.logInfo(R.string.routes_info_excl, TextUtils.join(", ", mRoutes.getNetworks(false)), TextUtils.join(", ", mRoutesv6.getNetworks(false)));
         VpnStatus.logDebug(R.string.routes_debug, TextUtils.join(", ", positiveIPv4Routes), TextUtils.join(", ", positiveIPv6Routes));
-        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
-            setAllowedVpnPackages(builder);
-        }
+
+        setAllowedVpnPackages(builder);
         if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP_MR1) {
             // VPN always uses the default network
             builder.setUnderlyingNetworks(null);
@@ -773,9 +764,6 @@ public class OpenVPNService extends VpnService implements StateListener, Callbac
         } catch (Exception e) {
             VpnStatus.logError(R.string.tun_open_error);
             VpnStatus.logError(getString(R.string.error) + e.getLocalizedMessage());
-            if (Build.VERSION.SDK_INT <= Build.VERSION_CODES.JELLY_BEAN_MR1) {
-                VpnStatus.logError(R.string.tun_error_helpful);
-            }
             return null;
         }
 
@@ -790,7 +778,6 @@ public class OpenVPNService extends VpnService implements StateListener, Callbac
         }
     }
 
-    @TargetApi(Build.VERSION_CODES.LOLLIPOP)
     private void allowAllAFFamilies(Builder builder) {
         builder.allowFamily(OsConstants.AF_INET);
         builder.allowFamily(OsConstants.AF_INET6);
@@ -805,11 +792,9 @@ public class OpenVPNService extends VpnService implements StateListener, Callbac
             if (ipAddr.equals(mLocalIP.mIp))
                 continue;
 
-            if (Build.VERSION.SDK_INT < Build.VERSION_CODES.KITKAT && !mProfile.mAllowLocalLAN) {
-                mRoutes.addIPSplit(new CIDRIP(ipAddr, netMask), true);
-
-            } else if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT && mProfile.mAllowLocalLAN)
+            if (mProfile.mAllowLocalLAN) {
                 mRoutes.addIP(new CIDRIP(ipAddr, netMask), false);
+            }
         }
 
         // IPv6 is Lollipop+ only so we can skip the lower than KITKAT case
@@ -823,7 +808,6 @@ public class OpenVPNService extends VpnService implements StateListener, Callbac
     }
 
 
-    @TargetApi(Build.VERSION_CODES.LOLLIPOP)
     private void setAllowedVpnPackages(Builder builder) {
         boolean profileUsesOrBot = false;
 
@@ -1094,13 +1078,7 @@ public class OpenVPNService extends VpnService implements StateListener, Callbac
         if (currentConfiguration.equals(mLastTunCfg)) {
             return "NOACTION";
         } else {
-            String release = Build.VERSION.RELEASE;
-            if (Build.VERSION.SDK_INT == Build.VERSION_CODES.KITKAT && !release.startsWith("4.4.3")
-                    && !release.startsWith("4.4.4") && !release.startsWith("4.4.5") && !release.startsWith("4.4.6"))
-                // There will be probably no 4.4.4 or 4.4.5 version, so don't waste effort to do parsing here
-                return "OPEN_AFTER_CLOSE";
-            else
-                return "OPEN_BEFORE_CLOSE";
+            return "OPEN_BEFORE_CLOSE";
         }
     }
 
diff --git a/app/src/main/java/de/blinkt/openvpn/core/OpenVpnManagementThread.java b/app/src/main/java/de/blinkt/openvpn/core/OpenVpnManagementThread.java
index 0edfeaeb82ab97d742c3b7ff8e81c86cb86bce87..a02e7e277b24f04ed507f155025086bc9cf093ef 100644
--- a/app/src/main/java/de/blinkt/openvpn/core/OpenVpnManagementThread.java
+++ b/app/src/main/java/de/blinkt/openvpn/core/OpenVpnManagementThread.java
@@ -242,12 +242,10 @@ public class OpenVpnManagementThread implements Runnable, OpenVPNManagement {
                 VpnStatus.logWarning("Could not protect VPN socket");
 
 
-            //ParcelFileDescriptor pfd = ParcelFileDescriptor.fromFd(fdint);
-            //pfd.close();
-            if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
-                fdCloseLollipop(fd);
-            } else {
-                NativeUtils.jniclose(fdint);
+            try {
+                Os.close(fd);
+            } catch (Exception e) {
+                VpnStatus.logException("Failed to close fd (" + fd + ")", e);
             }
             return;
         } catch ( NoSuchMethodException | IllegalArgumentException | InvocationTargetException | IllegalAccessException | NullPointerException e) {
@@ -258,15 +256,6 @@ public class OpenVpnManagementThread implements Runnable, OpenVPNManagement {
 
     }
 
-    @RequiresApi(api = Build.VERSION_CODES.LOLLIPOP)
-    private void fdCloseLollipop(FileDescriptor fd) {
-        try {
-            Os.close(fd);
-        } catch (Exception e) {
-            VpnStatus.logException("Failed to close fd (" + fd + ")", e);
-        }
-    }
-
     private String processInput(String pendingInput) {
 
 
diff --git a/app/src/main/java/de/blinkt/openvpn/core/VPNLaunchHelper.java b/app/src/main/java/de/blinkt/openvpn/core/VPNLaunchHelper.java
index 540ca0431cf19159b792b9126493576658a58040..80427a031c54a0c73eca997fcbdd5942f3c2d19e 100644
--- a/app/src/main/java/de/blinkt/openvpn/core/VPNLaunchHelper.java
+++ b/app/src/main/java/de/blinkt/openvpn/core/VPNLaunchHelper.java
@@ -30,11 +30,7 @@ public class VPNLaunchHelper {
         if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.P)
             return new File(context.getApplicationInfo().nativeLibraryDir, "libovpnexec.so").getPath();
         String[] abis;
-        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP)
-            abis = getSupportedABIsLollipop();
-        else
-            //noinspection deprecation
-            abis = new String[]{Build.CPU_ABI, Build.CPU_ABI2};
+        abis = getSupportedABIsLollipop();
 
         if (!nativeAPI.equals(abis[0])) {
             VpnStatus.logWarning(R.string.abi_mismatch, Arrays.toString(abis), nativeAPI);
@@ -49,22 +45,17 @@ public class VPNLaunchHelper {
             }
         }
 
-        throw new RuntimeException("Cannot find any execulte for this device's ABIs " + abis.toString());
+        throw new RuntimeException("Cannot find any execute for this device's ABIs " + abis.toString());
     }
 
-    @TargetApi(Build.VERSION_CODES.LOLLIPOP)
     private static String[] getSupportedABIsLollipop() {
         return Build.SUPPORTED_ABIS;
     }
 
     private static String getMiniVPNExecutableName() {
-        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN)
-            return MINIPIEVPN;
-        else
-            return MININONPIEVPN;
+        return MINIPIEVPN;
     }
 
-
     public static String[] replacePieWithNoPie(String[] mArgv) {
         mArgv[0] = mArgv[0].replace(MINIPIEVPN, MININONPIEVPN);
         return mArgv;
diff --git a/app/src/main/java/se/leap/bitmaskclient/base/fragments/SettingsFragment.java b/app/src/main/java/se/leap/bitmaskclient/base/fragments/SettingsFragment.java
index d5bbd2c58bb81a8d720e9c06c5cd0c9a048594a2..d57d725e4d7221f53d3699c4e10b8718cc04e411 100644
--- a/app/src/main/java/se/leap/bitmaskclient/base/fragments/SettingsFragment.java
+++ b/app/src/main/java/se/leap/bitmaskclient/base/fragments/SettingsFragment.java
@@ -174,19 +174,17 @@ public class SettingsFragment extends Fragment implements SharedPreferences.OnSh
     }
 
     private void initExcludeAppsEntry(View rootView) {
-        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
-            IconTextEntry excludeApps = rootView.findViewById(R.id.exclude_apps);
-            excludeApps.setVisibility(VISIBLE);
-            Set<String> apps = PreferenceHelper.getExcludedApps(this.getContext());
-            if (apps != null) {
-                updateExcludeAppsSubtitle(excludeApps, apps.size());
-            }
-            FragmentManagerEnhanced fragmentManager = new FragmentManagerEnhanced(getActivity().getSupportFragmentManager());
-            excludeApps.setOnClickListener((buttonView) -> {
-                Fragment fragment = new ExcludeAppsFragment();
-                fragmentManager.replace(R.id.main_container, fragment, MainActivity.TAG);
-            });
+        IconTextEntry excludeApps = rootView.findViewById(R.id.exclude_apps);
+        excludeApps.setVisibility(VISIBLE);
+        Set<String> apps = PreferenceHelper.getExcludedApps(this.getContext());
+        if (apps != null) {
+            updateExcludeAppsSubtitle(excludeApps, apps.size());
         }
+        FragmentManagerEnhanced fragmentManager = new FragmentManagerEnhanced(getActivity().getSupportFragmentManager());
+        excludeApps.setOnClickListener((buttonView) -> {
+            Fragment fragment = new ExcludeAppsFragment();
+            fragmentManager.replace(R.id.main_container, fragment, MainActivity.TAG);
+        });
     }
 
     private void updateExcludeAppsSubtitle(IconTextEntry excludeApps, int number) {
diff --git a/app/src/main/java/se/leap/bitmaskclient/base/fragments/TetheringDialog.java b/app/src/main/java/se/leap/bitmaskclient/base/fragments/TetheringDialog.java
index 675f1a61f7f5477918dd4bd69950fb404333edd2..e747d5b4c253407c636821e6252c07c222ef782b 100644
--- a/app/src/main/java/se/leap/bitmaskclient/base/fragments/TetheringDialog.java
+++ b/app/src/main/java/se/leap/bitmaskclient/base/fragments/TetheringDialog.java
@@ -209,10 +209,18 @@ public class TetheringDialog extends AppCompatDialogFragment implements Observer
         int endIndex = 0;
         if (matcher.matches()) {
             startIndex = matcher.start(2);
-            endIndex = startIndex + matcher.group(3).length();
+            try {
+                endIndex = startIndex + matcher.group(3).length();
+            } catch (NullPointerException npe) {
+                endIndex = -1;
+            }
         }
         systemSettingsMessage = systemSettingsMessage.replace("<b>", "").replace("</b>", "");
         String wholeMessage = systemSettingsMessage + "\n\n" + tetheringMessage;
+        if (startIndex == -1 || endIndex == -1) {
+            Log.e(TAG, "Tethering string has wrong formatting!");
+            return wholeMessage;
+        }
         Spannable spannable = new SpannableString(wholeMessage);
         spannable.setSpan(new ClickableSpan() {
             @Override
diff --git a/app/src/main/java/se/leap/bitmaskclient/base/utils/ViewHelper.java b/app/src/main/java/se/leap/bitmaskclient/base/utils/ViewHelper.java
index 8f4d7862f3b47abd891a495db81757f1e34fed67..51bcb2b10cac924559e2c589b30409a2d21187fa 100644
--- a/app/src/main/java/se/leap/bitmaskclient/base/utils/ViewHelper.java
+++ b/app/src/main/java/se/leap/bitmaskclient/base/utils/ViewHelper.java
@@ -96,12 +96,10 @@ public class ViewHelper {
         }
         int color = ContextCompat.getColor(activity, secondaryColor);
         bar.setBackgroundDrawable(new ColorDrawable(color));
-        if (Build.VERSION.SDK_INT  >= Build.VERSION_CODES.LOLLIPOP) {
-            Window window = activity.getWindow();
-            window.clearFlags(WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS);
-            window.addFlags(WindowManager.LayoutParams.FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS);
-            window.setStatusBarColor(ContextCompat.getColor(activity, primaryColor));
-        }
+        Window window = activity.getWindow();
+        window.clearFlags(WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS);
+        window.addFlags(WindowManager.LayoutParams.FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS);
+        window.setStatusBarColor(ContextCompat.getColor(activity, primaryColor));
 
         int actionBarTextColor;
         if (textColor == 0) {
diff --git a/app/src/main/java/se/leap/bitmaskclient/eip/VoidVpnService.java b/app/src/main/java/se/leap/bitmaskclient/eip/VoidVpnService.java
index 645d7b26cb81412ffad97b4fb560d58c85e246fc..79876d501fdcd2bddf94fde3eca6e94ef5d70f06 100644
--- a/app/src/main/java/se/leap/bitmaskclient/eip/VoidVpnService.java
+++ b/app/src/main/java/se/leap/bitmaskclient/eip/VoidVpnService.java
@@ -91,7 +91,7 @@ public class VoidVpnService extends VpnService implements Observer, VpnNotificat
                 }
             });
             thread.run();
-        } else if (action.equals("android.net.VpnService") && Build.VERSION.SDK_INT >= ALWAYS_ON_MIN_API_LEVEL) {
+        } else if (intent == null || action.equals("android.net.VpnService") && Build.VERSION.SDK_INT >= ALWAYS_ON_MIN_API_LEVEL) {
             //only always-on feature triggers this
             startWithForegroundNotification();
             thread = new Thread(new Runnable() {
@@ -154,15 +154,12 @@ public class VoidVpnService extends VpnService implements Observer, VpnNotificat
         builder.addRoute("::",0);
         builder.addAddress("fc00::", 7);
 
-        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
-            allowAllAFFamilies(builder);
-        }
+        allowAllAFFamilies(builder);
 
         return builder;
 
     }
 
-    @TargetApi(Build.VERSION_CODES.LOLLIPOP)
     private void allowAllAFFamilies(Builder builder) {
         builder.allowFamily(OsConstants.AF_INET);
         builder.allowFamily(OsConstants.AF_INET6);
@@ -174,9 +171,7 @@ public class VoidVpnService extends VpnService implements Observer, VpnNotificat
             VpnStatus.updateStateString(STATE_ESTABLISH, "",
                     R.string.void_vpn_establish, ConnectionStatus.LEVEL_BLOCKING);
             Builder builder = prepareBlockingVpnProfile();
-            if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP)  {
-                builder.addDisallowedApplication(getPackageName());
-            }
+            builder.addDisallowedApplication(getPackageName());
 
             fd = builder.establish();
         } catch (Exception e) {
@@ -208,7 +203,7 @@ public class VoidVpnService extends VpnService implements Observer, VpnNotificat
                     blockingMessage,
                     blockingMessage,
                     eipStatus.getLevel(),
-                    this
+                    null
             );
         } else {
             stopForeground(true);
diff --git a/app/src/main/java/se/leap/bitmaskclient/eip/VpnNotificationManager.java b/app/src/main/java/se/leap/bitmaskclient/eip/VpnNotificationManager.java
index 31893fb162dd11ecabeceae89ce99ed5cad5643d..b4d11f265f883871fb92c5c403b70b30344d96ea 100644
--- a/app/src/main/java/se/leap/bitmaskclient/eip/VpnNotificationManager.java
+++ b/app/src/main/java/se/leap/bitmaskclient/eip/VpnNotificationManager.java
@@ -16,6 +16,18 @@
  */
 package se.leap.bitmaskclient.eip;
 
+import static android.os.Build.VERSION_CODES.O;
+import static android.text.TextUtils.isEmpty;
+import static androidx.core.app.NotificationCompat.PRIORITY_DEFAULT;
+import static androidx.core.app.NotificationCompat.PRIORITY_MAX;
+import static de.blinkt.openvpn.core.ConnectionStatus.LEVEL_NONETWORK;
+import static de.blinkt.openvpn.core.ConnectionStatus.LEVEL_WAITING_FOR_USER_INPUT;
+import static se.leap.bitmaskclient.base.MainActivity.ACTION_SHOW_VPN_FRAGMENT;
+import static se.leap.bitmaskclient.base.models.Constants.ASK_TO_CANCEL_VPN;
+import static se.leap.bitmaskclient.base.models.Constants.EIP_ACTION_START;
+import static se.leap.bitmaskclient.base.models.Constants.EIP_ACTION_STOP_BLOCKING_VPN;
+import static se.leap.bitmaskclient.base.utils.ConfigHelper.getPendingIntentFlags;
+
 import android.annotation.TargetApi;
 import android.app.Notification;
 import android.app.NotificationChannel;
@@ -31,7 +43,6 @@ import android.text.Spannable;
 import android.text.SpannableString;
 import android.text.TextUtils;
 import android.text.style.StyleSpan;
-import android.widget.RemoteViews;
 
 import androidx.annotation.NonNull;
 import androidx.core.app.NotificationCompat;
@@ -45,18 +56,6 @@ import se.leap.bitmaskclient.R;
 import se.leap.bitmaskclient.base.MainActivity;
 import se.leap.bitmaskclient.base.StartActivity;
 
-import static android.os.Build.VERSION_CODES.O;
-import static android.text.TextUtils.isEmpty;
-import static androidx.core.app.NotificationCompat.PRIORITY_DEFAULT;
-import static androidx.core.app.NotificationCompat.PRIORITY_MAX;
-import static de.blinkt.openvpn.core.ConnectionStatus.LEVEL_NONETWORK;
-import static de.blinkt.openvpn.core.ConnectionStatus.LEVEL_WAITING_FOR_USER_INPUT;
-import static se.leap.bitmaskclient.base.MainActivity.ACTION_SHOW_VPN_FRAGMENT;
-import static se.leap.bitmaskclient.base.models.Constants.ASK_TO_CANCEL_VPN;
-import static se.leap.bitmaskclient.base.models.Constants.EIP_ACTION_START;
-import static se.leap.bitmaskclient.base.models.Constants.EIP_ACTION_STOP_BLOCKING_VPN;
-import static se.leap.bitmaskclient.base.utils.ConfigHelper.getPendingIntentFlags;
-
 /**
  * Created by cyberta on 14.01.18.
  */
@@ -129,7 +128,7 @@ public class VpnNotificationManager {
 
     public void buildOpenVpnNotification(String profileName, boolean isObfuscated, String msg,
                                          String tickerText, ConnectionStatus status, long when,
-                                         String notificationChannelNewstatusId, VpnServiceCallback vpnServiceCallback) {
+                                         String channelId, VpnServiceCallback vpnServiceCallback) {
         String cancelString;
         CharSequence bigmessage = null;
         String bridgeIcon = new String(Character.toChars(0x1f309));
@@ -141,7 +140,7 @@ public class VpnNotificationManager {
             case LEVEL_CONNECTING_SERVER_REPLIED:
             case LEVEL_CONNECTING_NO_SERVER_REPLY_YET:
                 cancelString = context.getString(R.string.cancel);
-                if (isObfuscated && Build.VERSION.SDK_INT > Build.VERSION_CODES.KITKAT) {
+                if (isObfuscated) {
                     Spannable spannable = new SpannableString(context.getString(R.string.obfuscated_connection_try));
                     spannable.setSpan(new StyleSpan(Typeface.ITALIC), 0, spannable.length() -1, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
                     bigmessage = TextUtils.concat(spannable, " " + bridgeIcon + "\n" + msg);
@@ -150,7 +149,7 @@ public class VpnNotificationManager {
 
             // show disconnect if connection exists
             case LEVEL_CONNECTED:
-                if (isObfuscated && Build.VERSION.SDK_INT > Build.VERSION_CODES.KITKAT) {
+                if (isObfuscated) {
                     Spannable spannable = new SpannableString(context.getString(R.string.obfuscated_connection));
                     spannable.setSpan(new StyleSpan(Typeface.ITALIC), 0, spannable.length() -1, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
                     bigmessage = TextUtils.concat(spannable, " " + bridgeIcon + "\n" + msg);
@@ -184,7 +183,7 @@ public class VpnNotificationManager {
                 bigmessage,
                 tickerText,
                 status,
-                notificationChannelNewstatusId,
+                channelId,
                 PRIORITY_DEFAULT,
                 when,
                 contentIntent,
@@ -245,40 +244,16 @@ public class VpnNotificationManager {
         }
     }
 
-    /**
-     * @return a custom remote view for notifications for API 16 - 19
-     */
-    private RemoteViews getKitkatCustomRemoteView(ConnectionStatus status, String title, String message) {
-        int iconResource = getIconByConnectionStatus(status);
-        RemoteViews remoteViews = new RemoteViews(context.getPackageName(), R.layout.v_custom_notification);
-        remoteViews.setImageViewResource(R.id.image_icon, iconResource);
-        remoteViews.setTextViewText(R.id.message, message);
-        remoteViews.setTextViewText(R.id.title, title);
-
-        return remoteViews;
-    }
-
     private void buildVpnNotification(String title, String message, CharSequence bigMessage, String tickerText,
-                                      ConnectionStatus status, String notificationChannelNewstatusId, int priority,
+                                      ConnectionStatus status, String channelId, int priority,
                                       long when, PendingIntent contentIntent, NotificationCompat.Action notificationAction, VpnServiceCallback vpnServiceCallback) {
-        NotificationCompat.Builder nCompatBuilder = new NotificationCompat.Builder(context, notificationChannelNewstatusId);
+        NotificationCompat.Builder nCompatBuilder = new NotificationCompat.Builder(context, channelId);
         int icon = getIconByConnectionStatus(status);
 
-        // this is a workaround to avoid confusion between the Android's system vpn notification
-        // showing a filled out key icon and the bitmask icon indicating a different state.
-        if (Build.VERSION.SDK_INT <= Build.VERSION_CODES.KITKAT &&
-                notificationChannelNewstatusId.equals(OpenVPNService.NOTIFICATION_CHANNEL_NEWSTATUS_ID)) {
-            if (status != LEVEL_NONETWORK) {
-                // removes the icon from the system status bar
-                icon = android.R.color.transparent;
-                // adds the icon to the notification in the notification drawer
-                nCompatBuilder.setContent(getKitkatCustomRemoteView(status, title, message));
-            }
-        } else {
-            nCompatBuilder.setStyle(new NotificationCompat.BigTextStyle().
-                    setBigContentTitle(title).
-                    bigText(bigMessage));
-        }
+        nCompatBuilder.setStyle(new NotificationCompat.BigTextStyle().
+                setBigContentTitle(title).
+                bigText(bigMessage));
+
         nCompatBuilder.addAction(notificationAction);
         nCompatBuilder.setContentTitle(title);
         nCompatBuilder.setCategory(NotificationCompat.CATEGORY_SERVICE);
@@ -296,11 +271,13 @@ public class VpnNotificationManager {
         }
 
         Notification notification = nCompatBuilder.build();
-        int notificationId = notificationChannelNewstatusId.hashCode();
+        int notificationId = channelId.hashCode();
 
-        compatNotificationManager.notify(notificationId, notification);
         if (vpnServiceCallback != null) {
             vpnServiceCallback.onNotificationBuild(notificationId, notification);
+        } else {
+            compatNotificationManager.notify(notificationId, notification);
+
         }
     }
 
diff --git a/app/src/main/java/se/leap/bitmaskclient/providersetup/activities/ConfigWizardBaseActivity.java b/app/src/main/java/se/leap/bitmaskclient/providersetup/activities/ConfigWizardBaseActivity.java
index aaf20647d327d019d196321566a77d4b3fbe9ce9..5cfefb2e8385fcd047a86260d44ca11392a2b51e 100644
--- a/app/src/main/java/se/leap/bitmaskclient/providersetup/activities/ConfigWizardBaseActivity.java
+++ b/app/src/main/java/se/leap/bitmaskclient/providersetup/activities/ConfigWizardBaseActivity.java
@@ -161,7 +161,6 @@ public abstract class ConfigWizardBaseActivity extends ButterKnifeActivity imple
         if (provider != null) {
             setProviderHeaderText(provider.getName());
         }
-        setProgressbarColorForPreLollipop();
         setDefaultGuidelineValues();
         setGlobalLayoutChangeListener();
     }
@@ -173,16 +172,6 @@ public abstract class ConfigWizardBaseActivity extends ButterKnifeActivity imple
         }
     }
 
-    private void setProgressbarColorForPreLollipop() {
-        if (progressBar == null || Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
-            return;
-        }
-        progressBar.getIndeterminateDrawable().setColorFilter(
-                ContextCompat.getColor(this, R.color.colorPrimary),
-                PorterDuff.Mode.SRC_IN);
-    }
-
-
     @Override
     public void onSaveInstanceState(Bundle outState) {
         super.onSaveInstanceState(outState);
diff --git a/app/src/main/res/layout-port/f_eip.xml b/app/src/main/res/layout-port/f_eip.xml
index 80f42f914acdba5e56475b281b31b465d78d96bb..e14c7a10a122bc83964f61dd1fa9d1f764efcb1d 100644
--- a/app/src/main/res/layout-port/f_eip.xml
+++ b/app/src/main/res/layout-port/f_eip.xml
@@ -64,8 +64,6 @@
         android:scaleType="fitXY"
         />
 
-
-
     <androidx.appcompat.widget.AppCompatTextView
         android:id="@+id/main_description"
         android:layout_width="wrap_content"
@@ -78,9 +76,7 @@
         android:layout_marginTop="@dimen/activity_margin"
         android:textAppearance="@android:style/TextAppearance.Large"
         android:textStyle="bold"
-        android:textSize="34sp"
-        app:autoSizeMinTextSize="28sp"
-        app:autoSizeTextType="uniform"
+        android:textSize="32sp"
         android:textColor="@color/colorEipFragmentFont"
         app:layout_constraintDimensionRatio="1:1"
         tools:text="Connection secure"
@@ -122,7 +118,7 @@
         android:id="@+id/main_button"
         android:layout_width="0dp"
         android:layout_height="0dp"
-        android:layout_margin="@dimen/stdpadding"
+        android:layout_margin="@dimen/mainbutton_padding"
         app:layout_constraintTop_toBottomOf="@+id/guideline_horizontal_bottom"
         app:layout_constraintBottom_toTopOf="@id/gateway_location_button"
         app:layout_constraintDimensionRatio="1:1"
diff --git a/app/src/main/res/layout-sw600dp-port/f_eip.xml b/app/src/main/res/layout-sw600dp-port/f_eip.xml
index 93393565907a2a42a388bb65dc6f3fb52d4f1500..88e516524bd204691ac67fc1ea07ecb0bbf3804b 100644
--- a/app/src/main/res/layout-sw600dp-port/f_eip.xml
+++ b/app/src/main/res/layout-sw600dp-port/f_eip.xml
@@ -77,13 +77,11 @@
         android:textAppearance="@android:style/TextAppearance.Large"
         android:textStyle="bold"
         android:textSize="48sp"
-        app:autoSizeMinTextSize="32sp"
-        app:autoSizeTextType="uniform"
         android:textColor="@color/colorEipFragmentFont"
         app:layout_constraintDimensionRatio="1:1"
         tools:text="Connection secure"
         android:gravity="center"
-        android:maxLines="1"
+        android:maxLines="2"
         />
 
     <androidx.appcompat.widget.AppCompatTextView
@@ -120,7 +118,7 @@
         android:id="@+id/main_button"
         android:layout_width="0dp"
         android:layout_height="0dp"
-        android:layout_margin="@dimen/stdpadding"
+        android:layout_margin="@dimen/mainbutton_padding"
         app:layout_constraintTop_toBottomOf="@+id/guideline_horizontal_bottom"
         app:layout_constraintBottom_toTopOf="@id/gateway_location_button"
         app:layout_constraintDimensionRatio="1:1"
diff --git a/app/src/main/res/layout-xlarge-port/f_eip.xml b/app/src/main/res/layout-xlarge-port/f_eip.xml
index ee0fbac9edd2b307a5bcdd39203f556b9ea1aba2..590cf1a4e215e683f7d6f8c8e71fbe04f942fe61 100644
--- a/app/src/main/res/layout-xlarge-port/f_eip.xml
+++ b/app/src/main/res/layout-xlarge-port/f_eip.xml
@@ -83,6 +83,7 @@
         android:textColor="@color/colorEipFragmentFont"
         app:layout_constraintDimensionRatio="1:1"
         tools:text="Connection secure"
+        android:maxLines="2"
         />
 
     <androidx.appcompat.widget.AppCompatTextView
@@ -123,7 +124,7 @@
         android:id="@+id/main_button"
         android:layout_width="0dp"
         android:layout_height="0dp"
-        android:layout_margin="@dimen/stdpadding"
+        android:layout_margin="@dimen/mainbutton_padding"
         app:layout_constraintTop_toBottomOf="@id/guideline_horizontal_bottom"
         app:layout_constraintBottom_toTopOf="@+id/guideline_horizontal_button_top"
         app:layout_constraintEnd_toStartOf="@+id/guideline_vertical_right"
diff --git a/app/src/main/res/layout/donation_reminder_dialog.xml b/app/src/main/res/layout/donation_reminder_dialog.xml
index 17eaf009fb1ccf0b1558b3a19026569cc51517f3..1260a99e63468bef77a0ff68217fa59c32d50fe0 100644
--- a/app/src/main/res/layout/donation_reminder_dialog.xml
+++ b/app/src/main/res/layout/donation_reminder_dialog.xml
@@ -30,7 +30,7 @@
             android:id="@+id/tvMessage"
             android:layout_width="match_parent"
             android:layout_height="wrap_content"
-            android:layout_margin="@dimen/standard_margin"
+            android:layout_margin="@dimen/donation_reminder_padding"
             android:gravity="center"
             android:text="@string/donate_message" />
 
@@ -57,7 +57,7 @@
             android:id="@+id/btnLater"
             android:layout_width="200dp"
             android:layout_height="38dp"
-            android:layout_marginBottom="@dimen/mainbutton_padding"
+            android:layout_marginBottom="20dp"
             android:layout_marginLeft="@dimen/add_button_margin"
             android:layout_marginRight="@dimen/add_button_margin"
             android:layout_marginTop="@dimen/standard_margin"
diff --git a/app/src/main/res/values-fr/strings.xml b/app/src/main/res/values-fr/strings.xml
index b38c55061be66d37e95038940e1e200acc25a72c..47d10ed67d35e64f1ebc9dda53f5402701c48e16 100644
--- a/app/src/main/res/values-fr/strings.xml
+++ b/app/src/main/res/values-fr/strings.xml
@@ -206,5 +206,5 @@
   <string name="advanced_settings">Paramètres avancés</string>
   <string name="cancel_connection">Se déconnecter</string>
   <string name="unknown_location">Site inconnu</string>
-  <string name="splash_footer">Développé par : LEAP</string>
+  <string name="splash_footer">Développé par LEAP</string>
 </resources>
diff --git a/app/src/main/res/values-gl/strings.xml b/app/src/main/res/values-gl/strings.xml
index 057ced21c28bce51cc24ef119b9ee989b34f4e42..9b0539abcadc9c2089ad44cf035b2b34ae8df78a 100644
--- a/app/src/main/res/values-gl/strings.xml
+++ b/app/src/main/res/values-gl/strings.xml
@@ -111,7 +111,7 @@
   <string name="require_root">Require permiso root</string>
   <string name="show_experimental">Mostrar funcións experimentais</string>
   <string name="hide_experimental">Agochar funcións experimentais</string>
-  <string name="tethering_enabled_message">Asegúrate de ter antes activada a compartición da conexión en <![CDATA[1system settings1]]>.</string>
+  <string name="tethering_enabled_message">Asegúrate de ter antes activada a compartición da conexión en <![CDATA[<b>system settings</b>]]>.</string>
   <string name="tethering_message">Comparte a túa VPN con outros dispositivos vía:</string>
   <string name="tethering_wifi">Punto de acceso Wi-Fi</string>
   <string name="tethering_usb">Compartición USB</string>
diff --git a/app/src/main/res/values-pt-rBR/strings.xml b/app/src/main/res/values-pt-rBR/strings.xml
index 6800536574756807910d4484fbe75763d48b9e87..9d83ff49fd5a933e6378ee12f8d03944f3c56f4e 100644
--- a/app/src/main/res/values-pt-rBR/strings.xml
+++ b/app/src/main/res/values-pt-rBR/strings.xml
@@ -114,7 +114,7 @@
   <string name="show_experimental">Mostrar recursos experimentais</string>
   <string name="hide_experimental">Esconder recursos experimentais</string>
   <string name="experimental_features">Funcionalidades experimentais</string>
-  <string name="tethering_enabled_message">Por favor tenha certeza de primeiro habilitar tethering nas &lt;![CDATA[&lt;b&gt;configurações de sistema&lt;/b&gt;]].</string>
+  <string name="tethering_enabled_message">Por favor tenha certeza de primeiro habilitar tethering nas <![CDATA[<b>configurações de sistema</b>]]>.</string>
   <string name="tethering_message">Compartilhe sua VPN com outros dispositivos através de:</string>
   <string name="tethering_wifi">Hotspot Wi-Fi</string>
   <string name="tethering_usb">Tethering USB</string>
diff --git a/app/src/main/res/values-sw600dp/dimens.xml b/app/src/main/res/values-sw600dp/dimens.xml
index a046dac6c77e0c6e20a1249c157e6715c6282ac9..4c726da59d17aa78839562f28340d67c966cc600 100644
--- a/app/src/main/res/values-sw600dp/dimens.xml
+++ b/app/src/main/res/values-sw600dp/dimens.xml
@@ -14,5 +14,7 @@
     <!-- landscape dimens -->
     <dimen name="footer_text_padding">20dp</dimen>
     <dimen name="splash_text_top_padding">140dp</dimen>
+    <dimen name="mainbutton_padding">32dp</dimen>
+    <dimen name="donation_reminder_padding">24dp</dimen>
 
 </resources>
\ No newline at end of file
diff --git a/app/src/main/res/values-w820dp/dimens.xml b/app/src/main/res/values-w820dp/dimens.xml
index b38b10a67f6d43ea6796db8badf23172d9c15d90..822259cafc0338a358bc40c1222d88580782c9c0 100644
--- a/app/src/main/res/values-w820dp/dimens.xml
+++ b/app/src/main/res/values-w820dp/dimens.xml
@@ -11,5 +11,7 @@
     <!-- landscape dimens -->
     <dimen name="footer_text_padding">12dp</dimen>
     <dimen name="splash_text_top_padding">90dp</dimen>
+    <dimen name="mainbutton_padding">32dp</dimen>
+    <dimen name="donation_reminder_padding">24dp</dimen>
 
 </resources>
diff --git a/app/src/main/res/values-zh-rCN/strings.xml b/app/src/main/res/values-zh-rCN/strings.xml
index c737d7598a0138faa82207e2c685fd807dfd9e37..564f15f3022406c6f7c30ec49228eab79b8bc687 100644
--- a/app/src/main/res/values-zh-rCN/strings.xml
+++ b/app/src/main/res/values-zh-rCN/strings.xml
@@ -2,7 +2,7 @@
 <resources>
   <string name="retry">重试</string>
   <string name="repository_url_text">源代码可在 https://0xacab.org/leap/bitmask_android 找到</string>
-  <string name="leap_tracker">问题追踪器可在 https://0xacab.org/leap/bitmask_android 找到</string>
+  <string name="leap_tracker">问题追踪器可在 https://0xacab.org/leap/bitmask_android/issues 找到</string>
   <string name="translation_project_text">我们鼓励并感谢诸位提供翻译。请在 https://www.transifex.com/projects/p/bitmask/ 参阅我们的 Transifex 项目</string>
   <string name="switch_provider_menu_option">切换提供商</string>
   <string name="info">信息</string>
diff --git a/app/src/main/res/values/colors.xml b/app/src/main/res/values/colors.xml
index ead4785e1a78309250c24f66eb994bd2d278c6f7..3e33c72bff24711e9ce51e66523352019dfc28e0 100644
--- a/app/src/main/res/values/colors.xml
+++ b/app/src/main/res/values/colors.xml
@@ -39,7 +39,7 @@
     <color name="black_transparent">#20000000</color>
     <color name="black_high_transparent">#05000000</color>
 
-    <color name="colorEipFragmentFont">@color/black800</color>
+    <color name="colorEipFragmentFont">@color/black800_dark</color>
     <!-- button text colors in Alerts etc. -->
     <color name="color_font_btn">@color/black800</color>
     <!-- pill style button text colors -->
diff --git a/app/src/main/res/values/dimens.xml b/app/src/main/res/values/dimens.xml
index 9ef6c3e004dd556abc5d86933009fccef9d68cf9..f15fbcf95868d2e3c9c09ef5fa7b6b4634c9b9fa 100644
--- a/app/src/main/res/values/dimens.xml
+++ b/app/src/main/res/values/dimens.xml
@@ -8,7 +8,6 @@
     <dimen name="stdpadding">8dp</dimen>
     <dimen name="compact_padding">3dp</dimen>
     <dimen name="standard_margin">8dp</dimen>
-    <dimen name="mainbutton_padding">20dp</dimen>
     <bool name="logSildersAlwaysVisible">false</bool>
     <!-- landscape layout dimens -->
     <dimen name="footer_text_padding">12dp</dimen>
@@ -46,4 +45,7 @@
     <dimen name="toast_bottom_padding">20dp</dimen>
     <dimen name="button_bevel">3dp</dimen>
     <dimen name="button_radius">16dp</dimen>
+    <dimen name="mainbutton_padding">8dp</dimen>
+    <dimen name="donation_reminder_padding">8dp</dimen>
+
 </resources>
\ No newline at end of file
diff --git a/docker/android-ndk/Dockerfile b/docker/android-ndk/Dockerfile
index 8fe535f50b1e9aaf8ab6ee2a495160d4882d68ca..ffe189b3b7b751f59bc6cb7991641bdb461db930 100644
--- a/docker/android-ndk/Dockerfile
+++ b/docker/android-ndk/Dockerfile
@@ -24,7 +24,7 @@ RUN apt-get update -qq && \
 # JNI build dependencies w/ 32-bit compatible C libs
 RUN apt-get update -qq && \
     apt-get -y install docker-ce docker-ce-cli make gcc swig file lib32stdc++6 lib32z1 \
-    autoconf autogen automake autopoint autotools-dev gettext-base libtool patch pkg-config && \
+    autoconf autogen automake autopoint autotools-dev gettext-base libtool patch pkg-config po4a && \
     apt-get clean && \
     apt-get autoclean && \
     rm -rf /var/lib/apt/lists/* /tmp/* /var/tmp/*
diff --git a/tor-android b/tor-android
index b7bf4551ff359e92e9023778715f39a4c7eb7cff..c1c015af8d20ae44d045264c9b98dbf78caa4336 160000
--- a/tor-android
+++ b/tor-android
@@ -1 +1 @@
-Subproject commit b7bf4551ff359e92e9023778715f39a4c7eb7cff
+Subproject commit c1c015af8d20ae44d045264c9b98dbf78caa4336