diff --git a/.travis.yml b/.travis.yml index 0420c20..a25a745 100644 --- a/.travis.yml +++ b/.travis.yml @@ -7,8 +7,8 @@ android: components: - tools - platform-tools - - build-tools-28.0.3 - - android-28 + - build-tools-29.0.2 + - android-29 - extra-android-support - extra-google-m2repository - extra-android-m2repository diff --git a/README.md b/README.md index 3c10d2e..eccde37 100644 --- a/README.md +++ b/README.md @@ -1,6 +1,6 @@ # iTXTech Daedalus -[![Donate](https://img.shields.io/badge/alipay-donate-yellow.svg)](https://qr.alipay.com/a6x07022gffiehykicipv1a) +[![Donate](https://img.shields.io/badge/alipay-donate-yellow.svg)](https://qr.alipay.com/FKX04751EZDP0SQ0BOT137) [![Build Status](https://travis-ci.org/iTXTech/Daedalus.svg?branch=master)](https://travis-ci.org/iTXTech/Daedalus) [![Jenkins](https://img.shields.io/jenkins/s/http/dev.itxtech.org:10298/job/Daedalus.svg)](http://dev.itxtech.org:10298/job/Daedalus/) @@ -66,14 +66,13 @@ __Users must comply with local laws and regulations.__
* __[ClearEditText](https://github.com/MrFuFuFu/ClearEditText)__ by *[Yuan Fu](https://github.com/MrFuFuFu)* - [APL 2.0](https://github.com/MrFuFuFu/ClearEditText) * __[DNS66](https://github.com/julian-klode/dns66)__ by *[Julian Andres Klode](https://github.com/julian-klode)* - [GPLv3](https://github.com/julian-klode/dns66/blob/master/COPYING) * __[Pcap4J](https://github.com/kaitoy/pcap4j)__ by *[Kaito Yamada](https://github.com/kaitoy)* - [MIT](https://github.com/kaitoy/pcap4j) -* __[MiniDNS](https://github.com/rtreffer/minidns)__ by *[Rene Treffer](https://github.com/rtreffer)* - [LGPLv2.1](https://github.com/rtreffer/minidns/blob/master/LICENCE_LGPL2.1) +* __[MiniDNS](https://github.com/MiniDNS/minidns)__ by *[MiniDNS](https://github.com/MiniDNS)* - [APL 2.0](https://github.com/MiniDNS/minidns/blob/master/LICENCE_APACHE) * __[Gson](https://github.com/google/gson)__ by *[Google](https://github.com/google)* - [APL 2.0](https://github.com/google/gson/blob/master/LICENSE) * __[Shadowsocks](https://github.com/shadowsocks/shadowsocks-android)__ by *[Shadowsocks](https://github.com/shadowsocks)* - [GPLv3](https://github.com/shadowsocks/shadowsocks-android/blob/master/LICENSE) ## Credits * __[JetBrains](https://www.jetbrains.com/)__ - For providing free license for [IntelliJ IDEA](https://www.jetbrains.com/idea/) -* __[ShenniaoTech](https://www.sncidc.com/)__ - For supporting us with love ## License diff --git a/app/build.gradle b/app/build.gradle index 6c6d0c1..b108563 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -58,6 +58,7 @@ dependencies { implementation 'androidx.cardview:cardview:1.0.0' implementation 'com.google.android.material:material:1.7.0-alpha01' implementation 'androidx.recyclerview:recyclerview:1.3.0-alpha02' + implementation 'androidx.preference:preference:1.1.0' //DNS implementation 'org.pcap4j:pcap4j-core:1.7.6' implementation 'org.pcap4j:pcap4j-packetfactory-static:1.7.6' diff --git a/app/src/main/AndroidManifest.xml b/app/src/main/AndroidManifest.xml index 7965227..6b661bc 100644 --- a/app/src/main/AndroidManifest.xml +++ b/app/src/main/AndroidManifest.xml @@ -4,6 +4,7 @@ + diff --git a/app/src/main/java/org/itxtech/daedalus/Daedalus.java b/app/src/main/java/org/itxtech/daedalus/Daedalus.java index d7cd117..1bc40f2 100644 --- a/app/src/main/java/org/itxtech/daedalus/Daedalus.java +++ b/app/src/main/java/org/itxtech/daedalus/Daedalus.java @@ -10,20 +10,20 @@ import android.graphics.drawable.Icon; import android.net.Uri; import android.net.VpnService; import android.os.Build; -import android.preference.PreferenceManager; -import android.util.Log; +import androidx.preference.PreferenceManager; import com.google.gson.Gson; import com.google.gson.GsonBuilder; import com.google.gson.JsonParseException; import com.google.gson.stream.JsonReader; import org.itxtech.daedalus.activity.MainActivity; +import org.itxtech.daedalus.server.AbstractDnsServer; +import org.itxtech.daedalus.server.DnsServer; +import org.itxtech.daedalus.server.DnsServerHelper; import org.itxtech.daedalus.service.DaedalusVpnService; import org.itxtech.daedalus.util.Configurations; import org.itxtech.daedalus.util.Logger; import org.itxtech.daedalus.util.Rule; import org.itxtech.daedalus.util.RuleResolver; -import org.itxtech.daedalus.util.server.DNSServer; -import org.itxtech.daedalus.util.server.DNSServerHelper; import java.io.File; import java.util.ArrayList; @@ -45,16 +45,16 @@ public class Daedalus extends Application { private static final String SHORTCUT_ID_ACTIVATE = "shortcut_activate"; - public static final List DNS_SERVERS = new ArrayList() {{ - add(new DNSServer("101.101.101.101", R.string.server_twnic_primary)); - add(new DNSServer("101.102.103.104", R.string.server_twnic_secondary)); - add(new DNSServer("dns.rubyfish.cn/dns-query", R.string.server_rubyfish)); - add(new DNSServer("cloudflare-dns.com/dns-query", R.string.server_cloudflare)); - add(new DNSServer("dns.google/dns-query", R.string.server_google_ietf)); - add(new DNSServer("dns.google/resolve", R.string.server_google_json)); + public static final List DNS_SERVERS = new ArrayList() {{ + add(new DnsServer("101.101.101.101", R.string.server_twnic_primary)); + add(new DnsServer("101.102.103.104", R.string.server_twnic_secondary)); + add(new DnsServer("rubyfish.cn/dns-query", R.string.server_rubyfish)); + add(new DnsServer("cloudflare-dns.com/dns-query", R.string.server_cloudflare)); + add(new DnsServer("dns.google/dns-query", R.string.server_google_ietf)); + add(new DnsServer("dns.google/resolve", R.string.server_google_json)); }}; - public static final List RULES = new ArrayList() {{ + public static final ArrayList RULES = new ArrayList() {{ add(new Rule("googlehosts/hosts", "googlehosts.hosts", Rule.TYPE_HOSTS, "https://raw.githubusercontent.com/googlehosts/hosts/master/hosts-files/hosts", false)); add(new Rule("vokins/yhosts", "vokins.hosts", Rule.TYPE_HOSTS, @@ -66,7 +66,7 @@ public class Daedalus extends Application { "https://raw.githubusercontent.com/vokins/yhosts/master/dnsmasq/union.conf", false)); }}; - public static final String[] DEFAULT_TEST_DOMAINS = new String[]{ + public static final String[] DEFAULT_TEST_DOMAINS = { "google.com", "twitter.com", "youtube.com", @@ -75,12 +75,11 @@ public class Daedalus extends Application { }; public static Configurations configurations; + public static String rulePath; + public static String logPath; + private static String configPath; - public static String rulePath = null; - public static String logPath = null; - private static String configPath = null; - - private static Daedalus instance = null; + private static Daedalus instance; private SharedPreferences prefs; private Thread mResolver; @@ -89,12 +88,9 @@ public class Daedalus extends Application { super.onCreate(); instance = this; - Logger.init(); - mResolver = new Thread(new RuleResolver()); mResolver.start(); - initData(); } @@ -135,30 +131,30 @@ public class Daedalus extends Application { } public static void initRuleResolver() { - ArrayList pendingLoad = new ArrayList<>(); - ArrayList usingRules = configurations.getUsingRules(); - if (usingRules != null && usingRules.size() > 0) { - for (Rule rule : usingRules) { - if (rule.isUsing()) { - pendingLoad.add(rulePath + rule.getFileName()); - } + ArrayList pendingLoad = new ArrayList<>(); + ArrayList usingRules = configurations.getUsingRules(); + if (usingRules != null && usingRules.size() > 0) { + for (Rule rule : usingRules) { + if (rule.isUsing()) { + pendingLoad.add(rulePath + rule.getFileName()); } - if (pendingLoad.size() > 0) { - String[] arr = new String[pendingLoad.size()]; - pendingLoad.toArray(arr); - switch (usingRules.get(0).getType()) { - case Rule.TYPE_HOSTS: - RuleResolver.startLoadHosts(arr); - break; - case Rule.TYPE_DNAMASQ: - RuleResolver.startLoadDnsmasq(arr); - break; - } - } else { - RuleResolver.clear(); + } + if (pendingLoad.size() > 0) { + String[] arr = new String[pendingLoad.size()]; + pendingLoad.toArray(arr); + switch (usingRules.get(0).getType()) { + case Rule.TYPE_HOSTS: + RuleResolver.startLoadHosts(arr); + break; + case Rule.TYPE_DNAMASQ: + RuleResolver.startLoadDnsmasq(arr); + break; } } else { RuleResolver.clear(); + } + } else { + RuleResolver.clear(); } } @@ -178,7 +174,6 @@ public class Daedalus extends Application { @Override public void onTerminate() { - Log.d("Daedalus", "onTerminate"); super.onTerminate(); instance = null; @@ -199,23 +194,38 @@ public class Daedalus extends Application { deactivateService(instance); return false; } else { - activateService(instance); + prepareAndActivateService(instance); return true; } } - public static boolean activateService(Context context) { + public static boolean prepareAndActivateService(Context context) { Intent intent = VpnService.prepare(context); if (intent != null) { return false; } else { - DaedalusVpnService.primaryServer = DNSServerHelper.getAddressById(DNSServerHelper.getPrimary()); - DaedalusVpnService.secondaryServer = DNSServerHelper.getAddressById(DNSServerHelper.getSecondary()); - context.startService(Daedalus.getServiceIntent(context).setAction(DaedalusVpnService.ACTION_ACTIVATE)); + activateService(context); return true; } } + public static void activateService(Context context) { + activateService(context, false); + } + + public static void activateService(Context context, boolean forceForeground) { + DaedalusVpnService.primaryServer = (AbstractDnsServer) DnsServerHelper.getServerById(DnsServerHelper.getPrimary()).clone(); + DaedalusVpnService.secondaryServer = (AbstractDnsServer) DnsServerHelper.getServerById(DnsServerHelper.getSecondary()).clone(); + if ((getInstance().prefs.getBoolean("settings_foreground", false) || forceForeground) + && Build.VERSION.SDK_INT > Build.VERSION_CODES.O) { + Logger.info("Starting foreground service"); + context.startForegroundService(Daedalus.getServiceIntent(context).setAction(DaedalusVpnService.ACTION_ACTIVATE)); + } else { + Logger.info("Starting background service"); + context.startService(Daedalus.getServiceIntent(context).setAction(DaedalusVpnService.ACTION_ACTIVATE)); + } + } + public static void deactivateService(Context context) { context.startService(getServiceIntent(context).setAction(DaedalusVpnService.ACTION_DEACTIVATE)); context.stopService(getServiceIntent(context)); @@ -223,7 +233,7 @@ public class Daedalus extends Application { public static void updateShortcut(Context context) { if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N_MR1) { - Log.d("Daedalus", "Updating shortcut"); + Logger.info("Updating shortcut"); boolean activate = DaedalusVpnService.isActivated(); String notice = activate ? context.getString(R.string.button_text_deactivate) : context.getString(R.string.button_text_activate); ShortcutInfo info = new ShortcutInfo.Builder(context, Daedalus.SHORTCUT_ID_ACTIVATE) @@ -239,7 +249,7 @@ public class Daedalus extends Application { } public static void donate() { - openUri("https://qr.alipay.com/a6x07022gffiehykicipv1a"); + openUri("https://qr.alipay.com/FKX04751EZDP0SQ0BOT137"); } public static void openUri(String uri) { diff --git a/app/src/main/java/org/itxtech/daedalus/activity/AppFilterActivity.java b/app/src/main/java/org/itxtech/daedalus/activity/AppFilterActivity.java index 65cc4a2..15d8bc3 100644 --- a/app/src/main/java/org/itxtech/daedalus/activity/AppFilterActivity.java +++ b/app/src/main/java/org/itxtech/daedalus/activity/AppFilterActivity.java @@ -40,7 +40,6 @@ import java.util.Objects; * (at your option) any later version. */ public class AppFilterActivity extends AppCompatActivity { - private RecyclerViewAdapter adapter; @Override @@ -78,7 +77,7 @@ public class AppFilterActivity extends AppCompatActivity { adapter.notifyDataSetChanged(); } - private class AppObject { + private static class AppObject { private String appName; private String appPackageName; private Drawable appIcon; @@ -111,13 +110,11 @@ public class AppFilterActivity extends AppCompatActivity { void updateList(ArrayList appObjects) { appList = appObjects; - for (int i = 0; i < appObjects.size(); i++) { if (Daedalus.configurations.getAppObjects().contains(appObjects.get(i).appPackageName)) { checkStatus.put(i, true); } } - runOnUiThread(this::notifyDataSetChanged); } @@ -158,7 +155,7 @@ public class AppFilterActivity extends AppCompatActivity { } } - private class RecyclerViewHolder extends RecyclerView.ViewHolder implements View.OnClickListener { + private static class RecyclerViewHolder extends RecyclerView.ViewHolder implements View.OnClickListener { private ImageView appIcon; private TextView appName; private CheckBox appCheck; @@ -172,7 +169,6 @@ public class AppFilterActivity extends AppCompatActivity { itemView.setOnClickListener(this); } - @Override public void onClick(View v) { if (appCheck.isChecked()) { diff --git a/app/src/main/java/org/itxtech/daedalus/activity/ConfigActivity.java b/app/src/main/java/org/itxtech/daedalus/activity/ConfigActivity.java index 500a669..2252d30 100644 --- a/app/src/main/java/org/itxtech/daedalus/activity/ConfigActivity.java +++ b/app/src/main/java/org/itxtech/daedalus/activity/ConfigActivity.java @@ -1,7 +1,5 @@ package org.itxtech.daedalus.activity; -import android.app.FragmentManager; -import android.app.FragmentTransaction; import android.graphics.Color; import android.graphics.drawable.Drawable; import android.os.Bundle; @@ -9,10 +7,12 @@ import androidx.appcompat.app.AppCompatActivity; import androidx.appcompat.widget.Toolbar; import androidx.core.content.ContextCompat; import androidx.core.graphics.drawable.DrawableCompat; +import androidx.fragment.app.FragmentManager; +import androidx.fragment.app.FragmentTransaction; import org.itxtech.daedalus.Daedalus; import org.itxtech.daedalus.R; import org.itxtech.daedalus.fragment.ConfigFragment; -import org.itxtech.daedalus.fragment.DNSServerConfigFragment; +import org.itxtech.daedalus.fragment.DnsServerConfigFragment; import org.itxtech.daedalus.fragment.RuleConfigFragment; /** @@ -44,14 +44,12 @@ public class ConfigActivity extends AppCompatActivity { ConfigFragment fragment; switch (getIntent().getIntExtra(LAUNCH_ACTION_FRAGMENT, LAUNCH_FRAGMENT_DNS_SERVER)) { - case LAUNCH_FRAGMENT_DNS_SERVER: - fragment = new DNSServerConfigFragment(); - break; case LAUNCH_FRAGMENT_RULE: fragment = new RuleConfigFragment(); break; + case LAUNCH_FRAGMENT_DNS_SERVER: default://should never reach this - fragment = new DNSServerConfigFragment(); + fragment = new DnsServerConfigFragment(); break; } @@ -64,7 +62,7 @@ public class ConfigActivity extends AppCompatActivity { toolbar.setOnMenuItemClickListener(fragment); toolbar.inflateMenu(R.menu.custom_config); - FragmentManager manager = getFragmentManager(); + FragmentManager manager = getSupportFragmentManager(); fragment.setIntent(getIntent()); FragmentTransaction fragmentTransaction = manager.beginTransaction(); fragmentTransaction.replace(R.id.id_config, fragment); diff --git a/app/src/main/java/org/itxtech/daedalus/activity/MainActivity.java b/app/src/main/java/org/itxtech/daedalus/activity/MainActivity.java index c6aab32..eeff855 100644 --- a/app/src/main/java/org/itxtech/daedalus/activity/MainActivity.java +++ b/app/src/main/java/org/itxtech/daedalus/activity/MainActivity.java @@ -1,9 +1,7 @@ package org.itxtech.daedalus.activity; import android.app.Activity; -import android.app.FragmentManager; import android.content.Context; -import android.content.DialogInterface; import android.content.Intent; import android.net.VpnService; import android.os.Bundle; @@ -26,7 +24,6 @@ import org.itxtech.daedalus.R; import org.itxtech.daedalus.fragment.*; import org.itxtech.daedalus.service.DaedalusVpnService; import org.itxtech.daedalus.util.Logger; -import org.itxtech.daedalus.util.server.DNSServerHelper; /** * Daedalus Project @@ -100,8 +97,7 @@ public class MainActivity extends AppCompatActivity implements NavigationView.On if (currentFragment == null || fragmentClass != currentFragment.getClass()) { try { ToolbarFragment fragment = (ToolbarFragment) fragmentClass.newInstance(); - FragmentManager fm = getFragmentManager(); - fm.beginTransaction().replace(R.id.id_content, fragment).commit(); + getSupportFragmentManager().beginTransaction().replace(R.id.id_content, fragment).commit(); currentFragment = fragment; } catch (Exception e) { Logger.logException(e); @@ -153,22 +149,14 @@ public class MainActivity extends AppCompatActivity implements NavigationView.On new AlertDialog.Builder(this) .setTitle("觉得还不错?") .setMessage("您的支持是我动力来源!\n请考虑为我买杯咖啡醒醒脑,甚至其他…… ;)") - .setPositiveButton("为我买杯咖啡", new DialogInterface.OnClickListener() { - @Override - public void onClick(DialogInterface dialog, int which) { - Daedalus.donate(); - new AlertDialog.Builder(MainActivity.this) - .setMessage("感谢您的支持!;)\n我会再接再厉!") - .setPositiveButton("确认", null) - .show(); - } - }) - .setNeutralButton("不再显示", new DialogInterface.OnClickListener() { - @Override - public void onClick(DialogInterface dialog, int which) { - Daedalus.configurations.setActivateCounter(-1); - } + .setPositiveButton("为我买杯咖啡", (dialog, which) -> { + Daedalus.donate(); + new AlertDialog.Builder(MainActivity.this) + .setMessage("感谢您的支持!;)\n我会再接再厉!") + .setPositiveButton("确认", null) + .show(); }) + .setNeutralButton("不再显示", (dialog, which) -> Daedalus.configurations.setActivateCounter(-1)) .setNegativeButton("取消", null) .show(); } @@ -177,12 +165,11 @@ public class MainActivity extends AppCompatActivity implements NavigationView.On public void onActivityResult(int request, int result, Intent data) { super.onActivityResult(request, result, data); if (result == Activity.RESULT_OK) { - DaedalusVpnService.primaryServer = DNSServerHelper.getAddressById(DNSServerHelper.getPrimary()); - DaedalusVpnService.secondaryServer = DNSServerHelper.getAddressById(DNSServerHelper.getSecondary()); - Daedalus.getInstance().startService(Daedalus.getServiceIntent(getApplicationContext()).setAction(DaedalusVpnService.ACTION_ACTIVATE)); + Daedalus.activateService(Daedalus.getInstance()); updateMainButton(R.string.button_text_deactivate); Daedalus.updateShortcut(getApplicationContext()); } + super.onActivityResult(request, result, data); } private void updateMainButton(int id) { @@ -194,7 +181,7 @@ public class MainActivity extends AppCompatActivity implements NavigationView.On private void updateUserInterface(Intent intent) { int launchAction = intent.getIntExtra(LAUNCH_ACTION, LAUNCH_ACTION_NONE); - Log.d(TAG, "Updating user interface with Launch Action " + String.valueOf(launchAction)); + Log.d(TAG, "Updating user interface with Launch Action " + launchAction); if (launchAction == LAUNCH_ACTION_ACTIVATE) { this.activateService(); } else if (launchAction == LAUNCH_ACTION_DEACTIVATE) { @@ -227,10 +214,10 @@ public class MainActivity extends AppCompatActivity implements NavigationView.On switchFragment(AboutFragment.class); break; case FRAGMENT_DNS_SERVERS: - switchFragment(DNSServersFragment.class); + switchFragment(DnsServersFragment.class); break; case FRAGMENT_DNS_TEST: - switchFragment(DNSTestFragment.class); + switchFragment(DnsTestFragment.class); break; case FRAGMENT_HOME: switchFragment(HomeFragment.class); @@ -252,7 +239,6 @@ public class MainActivity extends AppCompatActivity implements NavigationView.On @Override public boolean onNavigationItemSelected(@NonNull MenuItem item) { - // Handle navigation view item clicks here. int id = item.getItemId(); switch (id) { @@ -260,10 +246,10 @@ public class MainActivity extends AppCompatActivity implements NavigationView.On switchFragment(AboutFragment.class); break; case R.id.nav_dns_server: - switchFragment(DNSServersFragment.class); + switchFragment(DnsServersFragment.class); break; case R.id.nav_dns_test: - switchFragment(DNSTestFragment.class); + switchFragment(DnsTestFragment.class); break; case R.id.nav_github: Daedalus.openUri("https://github.com/iTXTech/Daedalus"); diff --git a/app/src/main/java/org/itxtech/daedalus/fragment/AboutFragment.java b/app/src/main/java/org/itxtech/daedalus/fragment/AboutFragment.java index 84ca364..9f585dd 100644 --- a/app/src/main/java/org/itxtech/daedalus/fragment/AboutFragment.java +++ b/app/src/main/java/org/itxtech/daedalus/fragment/AboutFragment.java @@ -13,6 +13,7 @@ import android.webkit.WebViewClient; import org.itxtech.daedalus.BuildConfig; import org.itxtech.daedalus.Daedalus; import org.itxtech.daedalus.R; +import org.itxtech.daedalus.util.Logger; import java.util.Locale; @@ -64,7 +65,7 @@ public class AboutFragment extends ToolbarFragment { mWebView.loadUrl("javascript:changeColor('"+(Daedalus.isDarkTheme() ? "#FFFFFF" : "#000000")+"')"); mWebView.loadUrl("javascript:changeVersionInfo('" + Daedalus.getInstance().getPackageManager().getPackageInfo(Daedalus.getInstance().getPackageName(), 0).versionName + "', '" + BuildConfig.BUILD_TIME + "', '" + BuildConfig.GIT_COMMIT + "')"); } catch (Exception e) { - Log.e("DAboutActivity", e.toString()); + Logger.logException(e); } } }); @@ -82,8 +83,6 @@ public class AboutFragment extends ToolbarFragment { super.onDestroyView(); if (mWebView != null) { - Log.d("DAboutActivity", "onDestroy"); - mWebView.removeAllViews(); mWebView.setWebViewClient(null); ((ViewGroup) mWebView.getParent()).removeView(mWebView); diff --git a/app/src/main/java/org/itxtech/daedalus/fragment/ConfigFragment.java b/app/src/main/java/org/itxtech/daedalus/fragment/ConfigFragment.java index 33a54e2..9f08c2c 100644 --- a/app/src/main/java/org/itxtech/daedalus/fragment/ConfigFragment.java +++ b/app/src/main/java/org/itxtech/daedalus/fragment/ConfigFragment.java @@ -1,8 +1,8 @@ package org.itxtech.daedalus.fragment; import android.content.Intent; -import android.preference.PreferenceFragment; import androidx.appcompat.widget.Toolbar; +import androidx.preference.PreferenceFragmentCompat; /** * Daedalus Project @@ -15,7 +15,7 @@ import androidx.appcompat.widget.Toolbar; * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. */ -abstract public class ConfigFragment extends PreferenceFragment implements Toolbar.OnMenuItemClickListener { +abstract public class ConfigFragment extends PreferenceFragmentCompat implements Toolbar.OnMenuItemClickListener { protected Intent intent = null; public void setIntent(Intent intent) { diff --git a/app/src/main/java/org/itxtech/daedalus/fragment/DNSServerConfigFragment.java b/app/src/main/java/org/itxtech/daedalus/fragment/DnsServerConfigFragment.java similarity index 83% rename from app/src/main/java/org/itxtech/daedalus/fragment/DNSServerConfigFragment.java rename to app/src/main/java/org/itxtech/daedalus/fragment/DnsServerConfigFragment.java index 411eaed..abc3984 100644 --- a/app/src/main/java/org/itxtech/daedalus/fragment/DNSServerConfigFragment.java +++ b/app/src/main/java/org/itxtech/daedalus/fragment/DnsServerConfigFragment.java @@ -2,7 +2,7 @@ package org.itxtech.daedalus.fragment; import android.app.AlertDialog; import android.os.Bundle; -import android.preference.EditTextPreference; +import androidx.preference.EditTextPreference; import android.view.LayoutInflater; import android.view.MenuItem; import android.view.View; @@ -11,8 +11,8 @@ import com.google.android.material.snackbar.Snackbar; import org.itxtech.daedalus.Daedalus; import org.itxtech.daedalus.R; import org.itxtech.daedalus.activity.ConfigActivity; -import org.itxtech.daedalus.util.server.CustomDNSServer; -import org.itxtech.daedalus.util.server.DNSServer; +import org.itxtech.daedalus.server.CustomDnsServer; +import org.itxtech.daedalus.server.DnsServer; /** * Daedalus Project @@ -25,12 +25,11 @@ import org.itxtech.daedalus.util.server.DNSServer; * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. */ -public class DNSServerConfigFragment extends ConfigFragment { +public class DnsServerConfigFragment extends ConfigFragment { private int index; @Override - public void onCreate(Bundle savedInstanceState) { - super.onCreate(savedInstanceState); + public void onCreatePreferences(Bundle savedInstanceState, String rootKey) { addPreferencesFromResource(R.xml.perf_server); } @@ -38,19 +37,19 @@ public class DNSServerConfigFragment extends ConfigFragment { public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { View view = super.onCreateView(inflater, container, savedInstanceState); - EditTextPreference serverName = (EditTextPreference) findPreference("serverName"); + EditTextPreference serverName = findPreference("serverName"); serverName.setOnPreferenceChangeListener((preference, newValue) -> { preference.setSummary((String) newValue); return true; }); - EditTextPreference serverAddress = (EditTextPreference) findPreference("serverAddress"); + EditTextPreference serverAddress = findPreference("serverAddress"); serverAddress.setOnPreferenceChangeListener((preference, newValue) -> { preference.setSummary((String) newValue); return true; }); - EditTextPreference serverPort = (EditTextPreference) findPreference("serverPort"); + EditTextPreference serverPort = findPreference("serverPort"); serverPort.setOnPreferenceChangeListener((preference, newValue) -> { preference.setSummary((String) newValue); return true; @@ -59,7 +58,7 @@ public class DNSServerConfigFragment extends ConfigFragment { index = intent.getIntExtra(ConfigActivity.LAUNCH_ACTION_ID, ConfigActivity.ID_NONE); if (index != ConfigActivity.ID_NONE) { - CustomDNSServer server = Daedalus.configurations.getCustomDNSServers().get(index); + CustomDnsServer server = Daedalus.configurations.getCustomDNSServers().get(index); serverName.setText(server.getName()); serverName.setSummary(server.getName()); serverAddress.setText(server.getAddress()); @@ -69,7 +68,7 @@ public class DNSServerConfigFragment extends ConfigFragment { } else { serverName.setText(""); serverAddress.setText(""); - String port = String.valueOf(DNSServer.DNS_SERVER_DEFAULT_PORT); + String port = String.valueOf(DnsServer.DNS_SERVER_DEFAULT_PORT); serverPort.setText(port); serverPort.setSummary(port); } @@ -93,9 +92,9 @@ public class DNSServerConfigFragment extends ConfigFragment { } if (index == ConfigActivity.ID_NONE) { - Daedalus.configurations.getCustomDNSServers().add(new CustomDNSServer(serverName, serverAddress, Integer.parseInt(serverPort))); + Daedalus.configurations.getCustomDNSServers().add(new CustomDnsServer(serverName, serverAddress, Integer.parseInt(serverPort))); } else { - CustomDNSServer server = Daedalus.configurations.getCustomDNSServers().get(index); + CustomDnsServer server = Daedalus.configurations.getCustomDNSServers().get(index); server.setName(serverName); server.setAddress(serverAddress); server.setPort(Integer.parseInt(serverPort)); diff --git a/app/src/main/java/org/itxtech/daedalus/fragment/DNSServersFragment.java b/app/src/main/java/org/itxtech/daedalus/fragment/DnsServersFragment.java similarity index 93% rename from app/src/main/java/org/itxtech/daedalus/fragment/DNSServersFragment.java rename to app/src/main/java/org/itxtech/daedalus/fragment/DnsServersFragment.java index 7e9428a..f6c577d 100644 --- a/app/src/main/java/org/itxtech/daedalus/fragment/DNSServersFragment.java +++ b/app/src/main/java/org/itxtech/daedalus/fragment/DnsServersFragment.java @@ -15,8 +15,8 @@ import com.google.android.material.snackbar.Snackbar; import org.itxtech.daedalus.Daedalus; import org.itxtech.daedalus.R; import org.itxtech.daedalus.activity.ConfigActivity; -import org.itxtech.daedalus.util.server.CustomDNSServer; -import org.itxtech.daedalus.util.server.DNSServerHelper; +import org.itxtech.daedalus.server.CustomDnsServer; +import org.itxtech.daedalus.server.DnsServerHelper; /** * Daedalus Project @@ -29,9 +29,9 @@ import org.itxtech.daedalus.util.server.DNSServerHelper; * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. */ -public class DNSServersFragment extends ToolbarFragment { +public class DnsServersFragment extends ToolbarFragment { private DNSServerAdapter adapter; - private CustomDNSServer server = null; + private CustomDnsServer server = null; @Override public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { @@ -47,7 +47,7 @@ public class DNSServersFragment extends ToolbarFragment { if (viewHolder instanceof ViewHolder) { int index = ((ViewHolder) viewHolder).getIndex(); if (index < Daedalus.configurations.getCustomDNSServers().size() && - DNSServerHelper.isInUsing(Daedalus.configurations.getCustomDNSServers().get(index))) { + DnsServerHelper.isInUsing(Daedalus.configurations.getCustomDNSServers().get(index))) { return 0; } } @@ -118,7 +118,7 @@ public class DNSServersFragment extends ToolbarFragment { private class DNSServerAdapter extends RecyclerView.Adapter { @Override public void onBindViewHolder(@NonNull ViewHolder holder, int position) { - CustomDNSServer server = Daedalus.configurations.getCustomDNSServers().get(position); + CustomDnsServer server = Daedalus.configurations.getCustomDNSServers().get(position); holder.setIndex(position); holder.textViewName.setText(server.getName()); holder.textViewAddress.setText(server.getRealName()); @@ -159,7 +159,7 @@ public class DNSServersFragment extends ToolbarFragment { @Override public void onClick(View v) { - if (!DNSServerHelper.isInUsing(Daedalus.configurations.getCustomDNSServers().get(index))) { + if (!DnsServerHelper.isInUsing(Daedalus.configurations.getCustomDNSServers().get(index))) { Daedalus.getInstance().startActivity(new Intent(Daedalus.getInstance(), ConfigActivity.class) .putExtra(ConfigActivity.LAUNCH_ACTION_ID, index) .putExtra(ConfigActivity.LAUNCH_ACTION_FRAGMENT, ConfigActivity.LAUNCH_FRAGMENT_DNS_SERVER) diff --git a/app/src/main/java/org/itxtech/daedalus/fragment/DNSTestFragment.java b/app/src/main/java/org/itxtech/daedalus/fragment/DnsTestFragment.java similarity index 91% rename from app/src/main/java/org/itxtech/daedalus/fragment/DNSTestFragment.java rename to app/src/main/java/org/itxtech/daedalus/fragment/DnsTestFragment.java index 3583274..893b3b6 100644 --- a/app/src/main/java/org/itxtech/daedalus/fragment/DNSTestFragment.java +++ b/app/src/main/java/org/itxtech/daedalus/fragment/DnsTestFragment.java @@ -12,8 +12,8 @@ import android.widget.*; import org.itxtech.daedalus.Daedalus; import org.itxtech.daedalus.R; import org.itxtech.daedalus.util.Logger; -import org.itxtech.daedalus.util.server.AbstractDNSServer; -import org.itxtech.daedalus.util.server.DNSServerHelper; +import org.itxtech.daedalus.server.AbstractDnsServer; +import org.itxtech.daedalus.server.DnsServerHelper; import org.minidns.dnsmessage.DnsMessage; import org.minidns.dnsmessage.Question; import org.minidns.record.Record; @@ -36,7 +36,7 @@ import java.util.Random; * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. */ -public class DNSTestFragment extends ToolbarFragment { +public class DnsTestFragment extends ToolbarFragment { private class Type { private Record.TYPE type; private String name; @@ -67,9 +67,9 @@ public class DNSTestFragment extends ToolbarFragment { final TextView textViewTestInfo = view.findViewById(R.id.textView_test_info); final Spinner spinnerServerChoice = view.findViewById(R.id.spinner_server_choice); - ArrayAdapter spinnerArrayAdapter = new ArrayAdapter<>(getActivity(), android.R.layout.simple_list_item_1, DNSServerHelper.getAllServers()); + ArrayAdapter spinnerArrayAdapter = new ArrayAdapter<>(getActivity(), android.R.layout.simple_list_item_1, DnsServerHelper.getAllServers()); spinnerServerChoice.setAdapter(spinnerArrayAdapter); - spinnerServerChoice.setSelection(DNSServerHelper.getPosition(DNSServerHelper.getPrimary())); + spinnerServerChoice.setSelection(DnsServerHelper.getPosition(DnsServerHelper.getPrimary())); ArrayList types = new ArrayList() {{ add(new Type("A", Record.TYPE.A)); @@ -110,38 +110,38 @@ public class DNSTestFragment extends ToolbarFragment { testDomain = Daedalus.DEFAULT_TEST_DOMAINS[0]; } StringBuilder testText = new StringBuilder(); - ArrayList dnsServers = new ArrayList() {{ - add(((AbstractDNSServer) spinnerServerChoice.getSelectedItem())); + ArrayList dnsServers = new ArrayList() {{ + add(((AbstractDnsServer) spinnerServerChoice.getSelectedItem())); String servers = Daedalus.getPrefs().getString("dns_test_servers", ""); if (!servers.equals("")) { for (String server : servers.split(",")) { if (server.contains(".") && server.contains(":")) {//IPv4 String[] pieces = servers.split(":"); - int port = AbstractDNSServer.DNS_SERVER_DEFAULT_PORT; + int port = AbstractDnsServer.DNS_SERVER_DEFAULT_PORT; try { port = Integer.parseInt(pieces[1]); } catch (Exception e) { Logger.logException(e); } - add(new AbstractDNSServer(pieces[0], port)); + add(new AbstractDnsServer(pieces[0], port)); } else if (!server.contains(".") && server.contains("|")) {//IPv6 String[] pieces = servers.split("\\|"); - int port = AbstractDNSServer.DNS_SERVER_DEFAULT_PORT; + int port = AbstractDnsServer.DNS_SERVER_DEFAULT_PORT; try { port = Integer.parseInt(pieces[1]); } catch (Exception e) { Logger.logException(e); } - add(new AbstractDNSServer(pieces[0], port)); + add(new AbstractDnsServer(pieces[0], port)); } else { - add(new AbstractDNSServer(server, AbstractDNSServer.DNS_SERVER_DEFAULT_PORT)); + add(new AbstractDnsServer(server, AbstractDnsServer.DNS_SERVER_DEFAULT_PORT)); } } } }}; DnsQuery dnsQuery = new DnsQuery(); Record.TYPE type = ((Type) spinnerType.getSelectedItem()).getType(); - for (AbstractDNSServer dnsServer : dnsServers) { + for (AbstractDnsServer dnsServer : dnsServers) { testText = testServer(dnsQuery, type, dnsServer, testDomain, testText); } mHandler.obtainMessage(DnsTestHandler.MSG_TEST_DONE).sendToTarget(); @@ -151,8 +151,7 @@ public class DNSTestFragment extends ToolbarFragment { } } - - private StringBuilder testServer(DnsQuery dnsQuery, Record.TYPE type, AbstractDNSServer server, String domain, StringBuilder testText) { + private StringBuilder testServer(DnsQuery dnsQuery, Record.TYPE type, AbstractDnsServer server, String domain, StringBuilder testText) { Logger.debug("Testing DNS server " + server.getRealName()); testText.append(getString(R.string.test_domain)).append(" ").append(domain).append("\n") .append(getString(R.string.test_dns_server)).append(" ").append(server.getRealName()); @@ -181,7 +180,7 @@ public class DNSTestFragment extends ToolbarFragment { } } testText.append("\n").append(getString(R.string.test_time_used)).append(" "). - append(String.valueOf(endTime - startTime)).append(" ms"); + append(endTime - startTime).append(" ms"); succ = true; } } catch (SocketTimeoutException ignored) { diff --git a/app/src/main/java/org/itxtech/daedalus/fragment/GlobalConfigFragment.java b/app/src/main/java/org/itxtech/daedalus/fragment/GlobalConfigFragment.java index 79353b9..56a9c19 100644 --- a/app/src/main/java/org/itxtech/daedalus/fragment/GlobalConfigFragment.java +++ b/app/src/main/java/org/itxtech/daedalus/fragment/GlobalConfigFragment.java @@ -2,12 +2,14 @@ package org.itxtech.daedalus.fragment; import android.content.Intent; import android.os.Bundle; -import android.preference.*; +import androidx.preference.*; import org.itxtech.daedalus.Daedalus; import org.itxtech.daedalus.R; import org.itxtech.daedalus.activity.AppFilterActivity; import org.itxtech.daedalus.activity.MainActivity; -import org.itxtech.daedalus.util.server.DNSServerHelper; +import org.itxtech.daedalus.server.DnsServerHelper; + +import java.util.ArrayList; /** * Daedalus Project @@ -20,52 +22,47 @@ import org.itxtech.daedalus.util.server.DNSServerHelper; * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. */ -public class GlobalConfigFragment extends PreferenceFragment { +public class GlobalConfigFragment extends PreferenceFragmentCompat { @Override - public void onCreate(Bundle savedInstanceState) { - super.onCreate(savedInstanceState); - + public void onCreatePreferences(Bundle savedInstanceState, String rootKey) { Daedalus.getPrefs().edit() - .putString("primary_server", DNSServerHelper.getPrimary()) - .putString("secondary_server", DNSServerHelper.getSecondary()) + .putString("primary_server", DnsServerHelper.getPrimary()) + .putString("secondary_server", DnsServerHelper.getSecondary()) .apply(); addPreferencesFromResource(R.xml.perf_settings); - ListPreference primaryServer = (ListPreference) findPreference("primary_server"); - primaryServer.setEntries(DNSServerHelper.getNames(Daedalus.getInstance())); - primaryServer.setEntryValues(DNSServerHelper.getIds()); - primaryServer.setSummary(DNSServerHelper.getDescription(primaryServer.getValue(), Daedalus.getInstance())); - primaryServer.setOnPreferenceChangeListener((preference, newValue) -> { - preference.setSummary(DNSServerHelper.getDescription((String) newValue, Daedalus.getInstance())); - return true; - }); + boolean visible = !Daedalus.getPrefs().getBoolean("settings_use_system_dns", false); + for (String k : new ArrayList() {{ + add("primary_server"); + add("secondary_server"); + }}) { + ListPreference listPref = findPreference(k); + listPref.setEntries(DnsServerHelper.getNames(Daedalus.getInstance())); + listPref.setEntryValues(DnsServerHelper.getIds()); + listPref.setSummary(DnsServerHelper.getDescription(listPref.getValue(), Daedalus.getInstance())); + listPref.setOnPreferenceChangeListener((preference, newValue) -> { + preference.setSummary(DnsServerHelper.getDescription((String) newValue, Daedalus.getInstance())); + return true; + }); + } - ListPreference secondaryServer = (ListPreference) findPreference("secondary_server"); - secondaryServer.setEntries(DNSServerHelper.getNames(Daedalus.getInstance())); - secondaryServer.setEntryValues(DNSServerHelper.getIds()); - secondaryServer.setSummary(DNSServerHelper.getDescription(secondaryServer.getValue(), Daedalus.getInstance())); - secondaryServer.setOnPreferenceChangeListener((preference, newValue) -> { - preference.setSummary(DNSServerHelper.getDescription((String) newValue, Daedalus.getInstance())); - return true; - }); - - EditTextPreference testDNSServers = (EditTextPreference) findPreference("dns_test_servers"); + EditTextPreference testDNSServers = findPreference("dns_test_servers"); testDNSServers.setSummary(testDNSServers.getText()); testDNSServers.setOnPreferenceChangeListener((preference, newValue) -> { preference.setSummary((String) newValue); return true; }); - EditTextPreference logSize = (EditTextPreference) findPreference("settings_log_size"); + EditTextPreference logSize = findPreference("settings_log_size"); logSize.setSummary(logSize.getText()); logSize.setOnPreferenceChangeListener((preference, newValue) -> { preference.setSummary((String) newValue); return true; }); - SwitchPreference darkTheme = (SwitchPreference) findPreference("settings_dark_theme"); + SwitchPreference darkTheme = findPreference("settings_dark_theme"); darkTheme.setOnPreferenceChangeListener((preference, o) -> { getActivity().startActivity(new Intent(Daedalus.getInstance(), MainActivity.class) .putExtra(MainActivity.LAUNCH_FRAGMENT, MainActivity.FRAGMENT_SETTINGS) @@ -73,13 +70,13 @@ public class GlobalConfigFragment extends PreferenceFragment { return true; }); - SwitchPreference advanced = (SwitchPreference) findPreference("settings_advanced_switch"); + SwitchPreference advanced = findPreference("settings_advanced_switch"); advanced.setOnPreferenceChangeListener((preference, newValue) -> { updateOptions((boolean) newValue, "settings_advanced"); return true; }); - SwitchPreference appFilter = (SwitchPreference) findPreference("settings_app_filter_switch"); + SwitchPreference appFilter = findPreference("settings_app_filter_switch"); appFilter.setOnPreferenceChangeListener((p, w) -> { updateOptions((boolean) w, "settings_app_filter"); return true; @@ -115,7 +112,7 @@ public class GlobalConfigFragment extends PreferenceFragment { } private void updateOptions(boolean checked, String pref) { - PreferenceCategory category = (PreferenceCategory) findPreference(pref); + PreferenceCategory category = findPreference(pref); for (int i = 1; i < category.getPreferenceCount(); i++) { Preference preference = category.getPreference(i); if (checked) { diff --git a/app/src/main/java/org/itxtech/daedalus/fragment/HomeFragment.java b/app/src/main/java/org/itxtech/daedalus/fragment/HomeFragment.java index 91803a8..0cc55ee 100644 --- a/app/src/main/java/org/itxtech/daedalus/fragment/HomeFragment.java +++ b/app/src/main/java/org/itxtech/daedalus/fragment/HomeFragment.java @@ -49,16 +49,7 @@ public class HomeFragment extends ToolbarFragment { updateUserInterface(); } - @Override - public void setUserVisibleHint(boolean isVisibleToUser) { - super.setUserVisibleHint(isVisibleToUser); - if (isVisibleToUser) { - updateUserInterface(); - } - } - private void updateUserInterface() { - Log.d("DMainFragment", "updateInterface"); Button but = getView().findViewById(R.id.button_activate); if (DaedalusVpnService.isActivated()) { but.setText(R.string.button_text_deactivate); diff --git a/app/src/main/java/org/itxtech/daedalus/fragment/LogFragment.java b/app/src/main/java/org/itxtech/daedalus/fragment/LogFragment.java index dc8880d..0a418b0 100644 --- a/app/src/main/java/org/itxtech/daedalus/fragment/LogFragment.java +++ b/app/src/main/java/org/itxtech/daedalus/fragment/LogFragment.java @@ -44,7 +44,7 @@ public class LogFragment extends ToolbarFragment implements Toolbar.OnMenuItemCl private void export() { try { - String file = Daedalus.logPath + String.valueOf(System.currentTimeMillis()) + ".log"; + String file = Daedalus.logPath + System.currentTimeMillis() + ".log"; FileWriter fileWriter = new FileWriter(file); fileWriter.write(Logger.getLog()); fileWriter.close(); diff --git a/app/src/main/java/org/itxtech/daedalus/fragment/RuleConfigFragment.java b/app/src/main/java/org/itxtech/daedalus/fragment/RuleConfigFragment.java index 860c83c..d02bddf 100644 --- a/app/src/main/java/org/itxtech/daedalus/fragment/RuleConfigFragment.java +++ b/app/src/main/java/org/itxtech/daedalus/fragment/RuleConfigFragment.java @@ -7,8 +7,8 @@ import android.net.Uri; import android.os.Bundle; import android.os.Handler; import android.os.Message; -import android.preference.EditTextPreference; -import android.preference.ListPreference; +import androidx.preference.EditTextPreference; +import androidx.preference.ListPreference; import android.view.LayoutInflater; import android.view.MenuItem; import android.view.View; @@ -72,10 +72,8 @@ public class RuleConfigFragment extends ConfigFragment { } } - @Override - public void onCreate(Bundle savedInstanceState) { - super.onCreate(savedInstanceState); + public void onCreatePreferences(Bundle savedInstanceState, String rootKey) { addPreferencesFromResource(R.xml.perf_rule); } @@ -85,13 +83,13 @@ public class RuleConfigFragment extends ConfigFragment { mHandler = new RuleConfigHandler().setView(view); - final EditTextPreference ruleName = (EditTextPreference) findPreference("ruleName"); + final EditTextPreference ruleName = findPreference("ruleName"); ruleName.setOnPreferenceChangeListener((preference, newValue) -> { preference.setSummary((String) newValue); return true; }); - final ListPreference ruleType = (ListPreference) findPreference("ruleType"); + final ListPreference ruleType = findPreference("ruleType"); final String[] entries = {"Hosts", "DNSMasq"}; String[] values = {"0", "1"}; ruleType.setEntries(entries); @@ -101,19 +99,19 @@ public class RuleConfigFragment extends ConfigFragment { return true; }); - final EditTextPreference ruleDownloadUrl = (EditTextPreference) findPreference("ruleDownloadUrl"); + final EditTextPreference ruleDownloadUrl = findPreference("ruleDownloadUrl"); ruleDownloadUrl.setOnPreferenceChangeListener((preference, newValue) -> { preference.setSummary((String) newValue); return true; }); - final EditTextPreference ruleFilename = (EditTextPreference) findPreference("ruleFilename"); + final EditTextPreference ruleFilename = findPreference("ruleFilename"); ruleFilename.setOnPreferenceChangeListener((preference, newValue) -> { preference.setSummary((String) newValue); return true; }); - ClickPreference ruleSync = (ClickPreference) findPreference("ruleSync"); + ClickPreference ruleSync = findPreference("ruleSync"); ruleSync.setOnPreferenceClickListener(preference -> { save(); if (mThread == null) { @@ -167,7 +165,7 @@ public class RuleConfigFragment extends ConfigFragment { return false; }); - ListPreference ruleImportBuildIn = (ListPreference) findPreference("ruleImportBuildIn"); + ListPreference ruleImportBuildIn = findPreference("ruleImportBuildIn"); ruleImportBuildIn.setEntries(Rule.getBuildInRuleNames()); ruleImportBuildIn.setEntryValues(Rule.getBuildInRuleEntries()); ruleImportBuildIn.setOnPreferenceChangeListener((preference, newValue) -> { @@ -183,7 +181,7 @@ public class RuleConfigFragment extends ConfigFragment { return true; }); - ClickPreference ruleImportExternal = (ClickPreference) findPreference("ruleImportExternal"); + ClickPreference ruleImportExternal = findPreference("ruleImportExternal"); ruleImportExternal.setOnPreferenceClickListener(preference -> { performFileSearch(); return false; diff --git a/app/src/main/java/org/itxtech/daedalus/fragment/SettingsFragment.java b/app/src/main/java/org/itxtech/daedalus/fragment/SettingsFragment.java index 41e1620..28419ac 100644 --- a/app/src/main/java/org/itxtech/daedalus/fragment/SettingsFragment.java +++ b/app/src/main/java/org/itxtech/daedalus/fragment/SettingsFragment.java @@ -1,7 +1,5 @@ package org.itxtech.daedalus.fragment; -import android.app.FragmentManager; -import android.os.Build; import android.os.Bundle; import android.view.LayoutInflater; import android.view.View; @@ -28,13 +26,7 @@ public class SettingsFragment extends ToolbarFragment { @Override public void onViewCreated(View view, Bundle savedInstanceState) { super.onViewCreated(view, savedInstanceState); - FragmentManager fm; - if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR1) { - fm = getChildFragmentManager(); - } else { - fm = getFragmentManager(); - } - fm.beginTransaction().replace(R.id.settings_content, new GlobalConfigFragment()).commit(); + getChildFragmentManager().beginTransaction().replace(R.id.settings_content, new GlobalConfigFragment()).commit(); } @Override diff --git a/app/src/main/java/org/itxtech/daedalus/fragment/ToolbarFragment.java b/app/src/main/java/org/itxtech/daedalus/fragment/ToolbarFragment.java index 7c8ff05..adfa8de 100644 --- a/app/src/main/java/org/itxtech/daedalus/fragment/ToolbarFragment.java +++ b/app/src/main/java/org/itxtech/daedalus/fragment/ToolbarFragment.java @@ -1,10 +1,10 @@ package org.itxtech.daedalus.fragment; -import android.app.Fragment; import android.os.Bundle; import android.view.Menu; import android.view.View; import androidx.appcompat.widget.Toolbar; +import androidx.fragment.app.Fragment; import com.google.android.material.navigation.NavigationView; import org.itxtech.daedalus.R; diff --git a/app/src/main/java/org/itxtech/daedalus/provider/HttpsProvider.java b/app/src/main/java/org/itxtech/daedalus/provider/HttpsProvider.java index 2acb812..b94256f 100644 --- a/app/src/main/java/org/itxtech/daedalus/provider/HttpsProvider.java +++ b/app/src/main/java/org/itxtech/daedalus/provider/HttpsProvider.java @@ -10,7 +10,7 @@ import okhttp3.OkHttpClient; import org.itxtech.daedalus.Daedalus; import org.itxtech.daedalus.service.DaedalusVpnService; import org.itxtech.daedalus.util.Logger; -import org.itxtech.daedalus.util.server.DNSServerHelper; +import org.itxtech.daedalus.server.DnsServerHelper; import org.minidns.dnsmessage.DnsMessage; import org.pcap4j.packet.IpPacket; import org.pcap4j.packet.IpSelector; @@ -58,8 +58,8 @@ abstract public class HttpsProvider extends Provider { .header("Accept", accept) .build())) .dns(hostname -> { - if (DNSServerHelper.domainCache.containsKey(hostname)) { - return DNSServerHelper.domainCache.get(hostname); + if (DnsServerHelper.domainCache.containsKey(hostname)) { + return DnsServerHelper.domainCache.get(hostname); } return Arrays.asList(InetAddress.getAllByName(hostname)); }) @@ -138,7 +138,7 @@ abstract public class HttpsProvider extends Provider { return; String uri; try { - uri = service.dnsServers.get(destAddr.getHostAddress());//https uri + uri = service.dnsServers.get(destAddr.getHostAddress()).getAddress();//https uri } catch (Exception e) { Logger.logException(e); return; @@ -161,7 +161,7 @@ abstract public class HttpsProvider extends Provider { return; } if (dnsMsg.getQuestion() == null) { - Log.i(TAG, "handleDnsRequest: Discarding DNS packet with no query " + dnsMsg); + Logger.debug("handleDnsRequest: Discarding DNS packet with no query " + dnsMsg); return; } diff --git a/app/src/main/java/org/itxtech/daedalus/provider/ProviderPicker.java b/app/src/main/java/org/itxtech/daedalus/provider/ProviderPicker.java index 7dcc492..b1d56eb 100644 --- a/app/src/main/java/org/itxtech/daedalus/provider/ProviderPicker.java +++ b/app/src/main/java/org/itxtech/daedalus/provider/ProviderPicker.java @@ -15,7 +15,7 @@ import org.itxtech.daedalus.service.DaedalusVpnService; * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. */ -public class ProviderPicker { +public abstract class ProviderPicker { public static final int DNS_QUERY_METHOD_UDP = 0; public static final int DNS_QUERY_METHOD_TCP = 1; public static final int DNS_QUERY_METHOD_TLS = 2; @@ -40,6 +40,6 @@ public class ProviderPicker { } public static int getDnsQueryMethod() { - return Integer.valueOf(Daedalus.getPrefs().getString("settings_dns_query_method", "0")); + return Integer.parseInt(Daedalus.getPrefs().getString("settings_dns_query_method", "0")); } } diff --git a/app/src/main/java/org/itxtech/daedalus/provider/TcpProvider.java b/app/src/main/java/org/itxtech/daedalus/provider/TcpProvider.java index 3768ea5..3a8fb34 100644 --- a/app/src/main/java/org/itxtech/daedalus/provider/TcpProvider.java +++ b/app/src/main/java/org/itxtech/daedalus/provider/TcpProvider.java @@ -9,7 +9,7 @@ import android.util.Log; import androidx.annotation.NonNull; import org.itxtech.daedalus.service.DaedalusVpnService; import org.itxtech.daedalus.util.Logger; -import org.itxtech.daedalus.util.server.DNSServerHelper; +import org.itxtech.daedalus.server.AbstractDnsServer; import org.pcap4j.packet.IpPacket; import java.io.*; @@ -123,7 +123,7 @@ public class TcpProvider extends UdpProvider { } @Override - protected void forwardPacket(DatagramPacket outPacket, IpPacket parsedPacket) throws DaedalusVpnService.VpnNetworkException { + protected void forwardPacket(DatagramPacket outPacket, IpPacket parsedPacket, AbstractDnsServer dnsServer) throws DaedalusVpnService.VpnNetworkException { Socket dnsSocket; try { // Packets to be sent to the real DNS server will need to be protected from the VPN @@ -131,7 +131,7 @@ public class TcpProvider extends UdpProvider { service.protect(dnsSocket); - SocketAddress address = new InetSocketAddress(outPacket.getAddress(), DNSServerHelper.getPortOrDefault(outPacket.getAddress(), outPacket.getPort())); + SocketAddress address = new InetSocketAddress(outPacket.getAddress(), dnsServer.getPort()); dnsSocket.connect(address, 5000); dnsSocket.setSoTimeout(5000); Logger.info("TcpProvider: Sending DNS query request"); @@ -161,7 +161,7 @@ public class TcpProvider extends UdpProvider { try { DataInputStream stream = new DataInputStream(dnsSocket.getInputStream()); int length = stream.readUnsignedShort(); - Log.d(TAG, "Reading length: " + String.valueOf(length)); + Log.d(TAG, "Reading length: " + length); byte[] data = new byte[length]; stream.read(data); dnsSocket.close(); diff --git a/app/src/main/java/org/itxtech/daedalus/provider/TlsProvider.java b/app/src/main/java/org/itxtech/daedalus/provider/TlsProvider.java index 6ca65c9..aeed205 100644 --- a/app/src/main/java/org/itxtech/daedalus/provider/TlsProvider.java +++ b/app/src/main/java/org/itxtech/daedalus/provider/TlsProvider.java @@ -3,7 +3,7 @@ package org.itxtech.daedalus.provider; import android.os.ParcelFileDescriptor; import org.itxtech.daedalus.service.DaedalusVpnService; import org.itxtech.daedalus.util.Logger; -import org.itxtech.daedalus.util.server.DNSServerHelper; +import org.itxtech.daedalus.server.AbstractDnsServer; import org.pcap4j.packet.IpPacket; import javax.net.ssl.SSLContext; @@ -28,13 +28,12 @@ public class TlsProvider extends TcpProvider{ } @Override - protected void forwardPacket(DatagramPacket outPacket, IpPacket parsedPacket) { + protected void forwardPacket(DatagramPacket outPacket, IpPacket parsedPacket, AbstractDnsServer dnsServer) { Socket dnsSocket; try { SSLContext context = SSLContext.getInstance("TLSv1.2"); context.init(null, null, null); - dnsSocket = context.getSocketFactory().createSocket(outPacket.getAddress(), - DNSServerHelper.getPortOrDefault(outPacket.getAddress(), outPacket.getPort())); + dnsSocket = context.getSocketFactory().createSocket(outPacket.getAddress(), dnsServer.getPort()); //Create TLS v1.2 socket //TODO: SNI diff --git a/app/src/main/java/org/itxtech/daedalus/provider/UdpProvider.java b/app/src/main/java/org/itxtech/daedalus/provider/UdpProvider.java index c51f5d3..59e35fc 100644 --- a/app/src/main/java/org/itxtech/daedalus/provider/UdpProvider.java +++ b/app/src/main/java/org/itxtech/daedalus/provider/UdpProvider.java @@ -9,7 +9,7 @@ import androidx.annotation.NonNull; import org.itxtech.daedalus.Daedalus; import org.itxtech.daedalus.service.DaedalusVpnService; import org.itxtech.daedalus.util.Logger; -import org.itxtech.daedalus.util.server.DNSServerHelper; +import org.itxtech.daedalus.server.AbstractDnsServer; import org.minidns.dnsmessage.DnsMessage; import org.pcap4j.packet.IpPacket; import org.pcap4j.packet.IpSelector; @@ -118,7 +118,7 @@ public class UdpProvider extends Provider { } } - protected void forwardPacket(DatagramPacket outPacket, IpPacket parsedPacket) throws DaedalusVpnService.VpnNetworkException { + protected void forwardPacket(DatagramPacket outPacket, IpPacket parsedPacket, AbstractDnsServer dnsServer) throws DaedalusVpnService.VpnNetworkException { DatagramSocket dnsSocket; try { // Packets to be sent to the real DNS server will need to be protected from the VPN @@ -158,7 +158,6 @@ public class UdpProvider extends Provider { */ @Override protected void handleDnsRequest(byte[] packetData) throws DaedalusVpnService.VpnNetworkException { - IpPacket parsedPacket; try { parsedPacket = (IpPacket) IpSelector.newPacket(packetData, 0, packetData.length); @@ -168,15 +167,21 @@ public class UdpProvider extends Provider { } if (!(parsedPacket.getPayload() instanceof UdpPacket)) { - Log.i(TAG, "handleDnsRequest: Discarding unknown packet type " + parsedPacket.getPayload()); + try { + Logger.debug("handleDnsRequest: Discarding unknown packet type " + parsedPacket.getPayload()); + } catch (Exception ignored) { + } return; } InetAddress destAddr = parsedPacket.getHeader().getDstAddr(); - if (destAddr == null) + if (destAddr == null) { return; + } + AbstractDnsServer dnsServer; try { - destAddr = InetAddress.getByName(service.dnsServers.get(destAddr.getHostAddress())); + dnsServer = service.dnsServers.get(destAddr.getHostAddress()); + destAddr = InetAddress.getByName(dnsServer.getHostAddress()); } catch (Exception e) { Logger.logException(e); Logger.error("handleDnsRequest: DNS server alias query failed for " + destAddr.getHostAddress()); @@ -191,9 +196,8 @@ public class UdpProvider extends Provider { // Let's be nice to Firefox. Firefox uses an empty UDP packet to // the gateway to reduce the RTT. For further details, please see // https://bugzilla.mozilla.org/show_bug.cgi?id=888268 - DatagramPacket outPacket = new DatagramPacket(new byte[0], 0, 0, destAddr, - DNSServerHelper.getPortOrDefault(destAddr, parsedUdp.getHeader().getDstPort().valueAsInt())); - forwardPacket(outPacket, null); + DatagramPacket outPacket = new DatagramPacket(new byte[0], 0, 0, destAddr, dnsServer.getPort()); + forwardPacket(outPacket, null, dnsServer); return; } @@ -209,14 +213,13 @@ public class UdpProvider extends Provider { return; } if (dnsMsg.getQuestion() == null) { - Log.i(TAG, "handleDnsRequest: Discarding DNS packet with no query " + dnsMsg); + Logger.debug("handleDnsRequest: Discarding DNS packet with no query " + dnsMsg); return; } if (!resolve(parsedPacket, dnsMsg)) { - DatagramPacket outPacket = new DatagramPacket(dnsRawData, 0, dnsRawData.length, destAddr, - DNSServerHelper.getPortOrDefault(destAddr, parsedUdp.getHeader().getDstPort().valueAsInt())); - forwardPacket(outPacket, parsedPacket); + DatagramPacket outPacket = new DatagramPacket(dnsRawData, 0, dnsRawData.length, destAddr, dnsServer.getPort()); + forwardPacket(outPacket, parsedPacket, dnsServer); } } diff --git a/app/src/main/java/org/itxtech/daedalus/receiver/BootBroadcastReceiver.java b/app/src/main/java/org/itxtech/daedalus/receiver/BootBroadcastReceiver.java index e7ac84e..63e65b1 100644 --- a/app/src/main/java/org/itxtech/daedalus/receiver/BootBroadcastReceiver.java +++ b/app/src/main/java/org/itxtech/daedalus/receiver/BootBroadcastReceiver.java @@ -21,7 +21,7 @@ public class BootBroadcastReceiver extends BroadcastReceiver { @Override public void onReceive(Context context, Intent intent) { if (Daedalus.getPrefs().getBoolean("settings_boot", false)) { - Daedalus.activateService(context); + Daedalus.activateService(context, true); Logger.info("Triggered boot receiver"); } } diff --git a/app/src/main/java/org/itxtech/daedalus/util/server/AbstractDNSServer.java b/app/src/main/java/org/itxtech/daedalus/server/AbstractDnsServer.java similarity index 65% rename from app/src/main/java/org/itxtech/daedalus/util/server/AbstractDNSServer.java rename to app/src/main/java/org/itxtech/daedalus/server/AbstractDnsServer.java index e1b6f39..d7760d5 100644 --- a/app/src/main/java/org/itxtech/daedalus/util/server/AbstractDNSServer.java +++ b/app/src/main/java/org/itxtech/daedalus/server/AbstractDnsServer.java @@ -1,4 +1,6 @@ -package org.itxtech.daedalus.util.server; +package org.itxtech.daedalus.server; + +import androidx.annotation.NonNull; /** * Daedalus Project @@ -11,17 +13,26 @@ package org.itxtech.daedalus.util.server; * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. */ -public class AbstractDNSServer { +public class AbstractDnsServer implements Cloneable { public static final int DNS_SERVER_DEFAULT_PORT = 53; protected String address; protected int port; + protected String hostAddress; - public AbstractDNSServer(String address, int port) { + public AbstractDnsServer(String address, int port) { this.address = address; this.port = port; } + public void setHostAddress(String hostAddress) { + this.hostAddress = hostAddress; + } + + public String getHostAddress() { + return hostAddress; + } + public void setAddress(String address) { this.address = address; } @@ -54,4 +65,14 @@ public class AbstractDNSServer { public boolean isHttpsServer() { return address.contains("/"); } + + @NonNull + @Override + public Object clone() { + try { + return super.clone(); + } catch (Exception ignored) { + } + return new AbstractDnsServer("", 0); + } } diff --git a/app/src/main/java/org/itxtech/daedalus/util/server/CustomDNSServer.java b/app/src/main/java/org/itxtech/daedalus/server/CustomDnsServer.java similarity index 83% rename from app/src/main/java/org/itxtech/daedalus/util/server/CustomDNSServer.java rename to app/src/main/java/org/itxtech/daedalus/server/CustomDnsServer.java index 56056ad..9aae884 100644 --- a/app/src/main/java/org/itxtech/daedalus/util/server/CustomDNSServer.java +++ b/app/src/main/java/org/itxtech/daedalus/server/CustomDnsServer.java @@ -1,4 +1,4 @@ -package org.itxtech.daedalus.util.server; +package org.itxtech.daedalus.server; import org.itxtech.daedalus.Daedalus; @@ -13,11 +13,11 @@ import org.itxtech.daedalus.Daedalus; * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. */ -public class CustomDNSServer extends AbstractDNSServer { +public class CustomDnsServer extends AbstractDnsServer { private String name; private String id; - public CustomDNSServer(String name, String address, int port) { + public CustomDnsServer(String name, String address, int port) { super(address, port); this.name = name; this.id = String.valueOf(Daedalus.configurations.getNextDnsId()); diff --git a/app/src/main/java/org/itxtech/daedalus/util/server/DNSServer.java b/app/src/main/java/org/itxtech/daedalus/server/DnsServer.java similarity index 75% rename from app/src/main/java/org/itxtech/daedalus/util/server/DNSServer.java rename to app/src/main/java/org/itxtech/daedalus/server/DnsServer.java index e6e8be9..74aa64d 100644 --- a/app/src/main/java/org/itxtech/daedalus/util/server/DNSServer.java +++ b/app/src/main/java/org/itxtech/daedalus/server/DnsServer.java @@ -1,4 +1,4 @@ -package org.itxtech.daedalus.util.server; +package org.itxtech.daedalus.server; import android.content.Context; import org.itxtech.daedalus.Daedalus; @@ -14,23 +14,27 @@ import org.itxtech.daedalus.Daedalus; * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. */ -public class DNSServer extends AbstractDNSServer { +public class DnsServer extends AbstractDnsServer { private static int totalId = 0; private String id; - private int description = 0; + private int description; - public DNSServer(String address, int description, int port) { + public DnsServer(String address, int description, int port) { super(address, port); this.id = String.valueOf(totalId++); this.description = description; } - public DNSServer(String address, int description) { + public DnsServer(String address, int description) { this(address, description, DNS_SERVER_DEFAULT_PORT); } + public DnsServer(String address) { + this(address, 0); + } + public String getId() { return id; } diff --git a/app/src/main/java/org/itxtech/daedalus/util/server/DNSServerHelper.java b/app/src/main/java/org/itxtech/daedalus/server/DnsServerHelper.java similarity index 68% rename from app/src/main/java/org/itxtech/daedalus/util/server/DNSServerHelper.java rename to app/src/main/java/org/itxtech/daedalus/server/DnsServerHelper.java index ce8b814..332e682 100644 --- a/app/src/main/java/org/itxtech/daedalus/util/server/DNSServerHelper.java +++ b/app/src/main/java/org/itxtech/daedalus/server/DnsServerHelper.java @@ -1,4 +1,4 @@ -package org.itxtech.daedalus.util.server; +package org.itxtech.daedalus.server; import android.content.Context; import android.net.Uri; @@ -25,31 +25,19 @@ import java.util.List; * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. */ -public class DNSServerHelper { - private static HashMap portCache = new HashMap<>(); +public class DnsServerHelper { public static HashMap> domainCache = new HashMap<>(); public static void clearCache() { - portCache = new HashMap<>(); domainCache = new HashMap<>(); } public static void buildCache() { domainCache = new HashMap<>(); - portCache = new HashMap<>(); - if (ProviderPicker.getDnsQueryMethod() >= ProviderPicker.DNS_QUERY_METHOD_HTTPS_IETF && - !Daedalus.getPrefs().getBoolean("settings_dont_build_doh_cache", false)) { - buildDomainCache(getAddressById(getPrimary())); - buildDomainCache(getAddressById(getSecondary())); - } - - for (DNSServer server : Daedalus.DNS_SERVERS) { - portCache.put(server.getAddress(), server.getPort()); - } - - for (CustomDNSServer server : Daedalus.configurations.getCustomDNSServers()) { - portCache.put(server.getAddress(), server.getPort()); + !Daedalus.getPrefs().getBoolean("settings_dont_build_cache", false)) { + buildDomainCache(getServerById(getPrimary()).getAddress()); + buildDomainCache(getServerById(getSecondary()).getAddress()); } } @@ -63,16 +51,6 @@ public class DNSServerHelper { } } - public static int getPortOrDefault(InetAddress address, int defaultPort) { - String hostAddress = address.getHostAddress(); - - if (portCache.containsKey(hostAddress)) { - return portCache.get(hostAddress); - } - - return defaultPort; - } - public static int getPosition(String id) { int intId = Integer.parseInt(id); if (intId < Daedalus.DNS_SERVERS.size()) { @@ -88,18 +66,18 @@ public class DNSServerHelper { } public static String getPrimary() { - return String.valueOf(DNSServerHelper.checkServerId(Integer.parseInt(Daedalus.getPrefs().getString("primary_server", "0")))); + return String.valueOf(DnsServerHelper.checkServerId(Integer.parseInt(Daedalus.getPrefs().getString("primary_server", "0")))); } public static String getSecondary() { - return String.valueOf(DNSServerHelper.checkServerId(Integer.parseInt(Daedalus.getPrefs().getString("secondary_server", "1")))); + return String.valueOf(DnsServerHelper.checkServerId(Integer.parseInt(Daedalus.getPrefs().getString("secondary_server", "1")))); } private static int checkServerId(int id) { if (id < Daedalus.DNS_SERVERS.size()) { return id; } - for (CustomDNSServer server : Daedalus.configurations.getCustomDNSServers()) { + for (CustomDnsServer server : Daedalus.configurations.getCustomDNSServers()) { if (server.getId().equals(String.valueOf(id))) { return id; } @@ -107,26 +85,26 @@ public class DNSServerHelper { return 0; } - public static String getAddressById(String id) { - for (DNSServer server : Daedalus.DNS_SERVERS) { + public static AbstractDnsServer getServerById(String id) { + for (DnsServer server : Daedalus.DNS_SERVERS) { if (server.getId().equals(id)) { - return server.getAddress(); + return server; } } - for (CustomDNSServer customDNSServer : Daedalus.configurations.getCustomDNSServers()) { + for (CustomDnsServer customDNSServer : Daedalus.configurations.getCustomDNSServers()) { if (customDNSServer.getId().equals(id)) { - return customDNSServer.getAddress(); + return customDNSServer; } } - return Daedalus.DNS_SERVERS.get(0).getAddress(); + return Daedalus.DNS_SERVERS.get(0); } public static String[] getIds() { ArrayList servers = new ArrayList<>(Daedalus.DNS_SERVERS.size()); - for (DNSServer server : Daedalus.DNS_SERVERS) { + for (DnsServer server : Daedalus.DNS_SERVERS) { servers.add(server.getId()); } - for (CustomDNSServer customDNSServer : Daedalus.configurations.getCustomDNSServers()) { + for (CustomDnsServer customDNSServer : Daedalus.configurations.getCustomDNSServers()) { servers.add(customDNSServer.getId()); } String[] stringServers = new String[Daedalus.DNS_SERVERS.size()]; @@ -135,30 +113,30 @@ public class DNSServerHelper { public static String[] getNames(Context context) { ArrayList servers = new ArrayList<>(Daedalus.DNS_SERVERS.size()); - for (DNSServer server : Daedalus.DNS_SERVERS) { + for (DnsServer server : Daedalus.DNS_SERVERS) { servers.add(server.getStringDescription(context)); } - for (CustomDNSServer customDNSServer : Daedalus.configurations.getCustomDNSServers()) { + for (CustomDnsServer customDNSServer : Daedalus.configurations.getCustomDNSServers()) { servers.add(customDNSServer.getName()); } String[] stringServers = new String[Daedalus.DNS_SERVERS.size()]; return servers.toArray(stringServers); } - public static ArrayList getAllServers() { - ArrayList servers = new ArrayList<>(Daedalus.DNS_SERVERS.size()); + public static ArrayList getAllServers() { + ArrayList servers = new ArrayList<>(Daedalus.DNS_SERVERS.size()); servers.addAll(Daedalus.DNS_SERVERS); servers.addAll(Daedalus.configurations.getCustomDNSServers()); return servers; } public static String getDescription(String id, Context context) { - for (DNSServer server : Daedalus.DNS_SERVERS) { + for (DnsServer server : Daedalus.DNS_SERVERS) { if (server.getId().equals(id)) { return server.getStringDescription(context); } } - for (CustomDNSServer customDNSServer : Daedalus.configurations.getCustomDNSServers()) { + for (CustomDnsServer customDNSServer : Daedalus.configurations.getCustomDNSServers()) { if (customDNSServer.getId().equals(id)) { return customDNSServer.getName(); } @@ -166,7 +144,7 @@ public class DNSServerHelper { return Daedalus.DNS_SERVERS.get(0).getStringDescription(context); } - public static boolean isInUsing(CustomDNSServer server) { + public static boolean isInUsing(CustomDnsServer server) { return DaedalusVpnService.isActivated() && (server.getId().equals(getPrimary()) || server.getId().equals(getSecondary())); } } diff --git a/app/src/main/java/org/itxtech/daedalus/service/DaedalusVpnService.java b/app/src/main/java/org/itxtech/daedalus/service/DaedalusVpnService.java index ccae93f..03ad1d8 100644 --- a/app/src/main/java/org/itxtech/daedalus/service/DaedalusVpnService.java +++ b/app/src/main/java/org/itxtech/daedalus/service/DaedalusVpnService.java @@ -4,14 +4,18 @@ import android.app.Notification; import android.app.NotificationChannel; import android.app.NotificationManager; import android.app.PendingIntent; +import android.content.BroadcastReceiver; import android.content.Context; import android.content.Intent; +import android.content.IntentFilter; import android.content.pm.PackageManager; +import android.net.ConnectivityManager; import android.net.VpnService; import android.os.Build; import android.os.ParcelFileDescriptor; import android.system.OsConstants; import android.util.Log; +import androidx.appcompat.app.AlertDialog; import androidx.core.app.NotificationCompat; import org.itxtech.daedalus.Daedalus; import org.itxtech.daedalus.R; @@ -19,9 +23,12 @@ import org.itxtech.daedalus.activity.MainActivity; import org.itxtech.daedalus.provider.Provider; import org.itxtech.daedalus.provider.ProviderPicker; import org.itxtech.daedalus.receiver.StatusBarBroadcastReceiver; +import org.itxtech.daedalus.server.AbstractDnsServer; +import org.itxtech.daedalus.server.DnsServer; +import org.itxtech.daedalus.server.DnsServerHelper; +import org.itxtech.daedalus.util.DnsServersDetector; import org.itxtech.daedalus.util.Logger; import org.itxtech.daedalus.util.RuleResolver; -import org.itxtech.daedalus.util.server.DNSServerHelper; import java.net.Inet4Address; import java.net.Inet6Address; @@ -51,22 +58,21 @@ public class DaedalusVpnService extends VpnService implements Runnable { private static final String CHANNEL_ID = "daedalus_channel_1"; private static final String CHANNEL_NAME = "daedalus_channel"; - public static String primaryServer; - public static String secondaryServer; + public static AbstractDnsServer primaryServer; + public static AbstractDnsServer secondaryServer; + private static InetAddress aliasPrimary; + private static InetAddress aliasSecondary; private NotificationCompat.Builder notification = null; - private boolean running = false; private long lastUpdate = 0; private boolean statisticQuery; private Provider provider; private ParcelFileDescriptor descriptor; - private Thread mThread = null; - - public HashMap dnsServers; - + public HashMap dnsServers; private static boolean activated = false; + private static BroadcastReceiver receiver; public static boolean isActivated() { return activated; @@ -75,6 +81,44 @@ public class DaedalusVpnService extends VpnService implements Runnable { @Override public void onCreate() { super.onCreate(); + if (Daedalus.getPrefs().getBoolean("settings_use_system_dns", false)) { + registerReceiver(receiver = new BroadcastReceiver() { + @Override + public void onReceive(Context context, Intent intent) { + updateUpstreamServers(context); + } + }, new IntentFilter(ConnectivityManager.CONNECTIVITY_ACTION)); + } + } + + private static void updateUpstreamServers(Context context) { + String[] servers = DnsServersDetector.getServers(context); + if (servers != null) { + if (servers.length >= 2 && (aliasPrimary == null || !aliasPrimary.getHostAddress().equals(servers[0])) && + (aliasSecondary == null || !aliasSecondary.getHostAddress().equals(servers[0])) && + (aliasPrimary == null || !aliasPrimary.getHostAddress().equals(servers[1])) && + (aliasSecondary == null || !aliasSecondary.getHostAddress().equals(servers[1]))) { + primaryServer.setAddress(servers[0]); + primaryServer.setPort(DnsServer.DNS_SERVER_DEFAULT_PORT); + secondaryServer.setAddress(servers[1]); + secondaryServer.setPort(DnsServer.DNS_SERVER_DEFAULT_PORT); + } else if ((aliasPrimary == null || !aliasPrimary.getHostAddress().equals(servers[0])) && + (aliasSecondary == null || !aliasSecondary.getHostAddress().equals(servers[0]))) { + primaryServer.setAddress(servers[0]); + primaryServer.setPort(DnsServer.DNS_SERVER_DEFAULT_PORT); + secondaryServer.setAddress(servers[0]); + secondaryServer.setPort(DnsServer.DNS_SERVER_DEFAULT_PORT); + } else { + StringBuilder buf = new StringBuilder(); + for (String server : servers) { + buf.append(server).append(" "); + } + Logger.error("Invalid upstream DNS " + buf); + } + Logger.info("Upstream DNS updated: " + primaryServer.getAddress() + " " + secondaryServer.getAddress()); + } else { + Logger.error("Cannot obtain upstream DNS server!"); + } } @Override @@ -84,7 +128,6 @@ public class DaedalusVpnService extends VpnService implements Runnable { case ACTION_ACTIVATE: activated = true; if (Daedalus.getPrefs().getBoolean("settings_notification", true)) { - NotificationManager manager = (NotificationManager) this.getSystemService(Context.NOTIFICATION_SERVICE); NotificationCompat.Builder builder; @@ -126,12 +169,7 @@ public class DaedalusVpnService extends VpnService implements Runnable { } Daedalus.initRuleResolver(); - - if (this.mThread == null) { - this.mThread = new Thread(this, "DaedalusVpn"); - this.running = true; - this.mThread.start(); - } + startThread(); Daedalus.updateShortcut(getApplicationContext()); if (MainActivity.getInstance() != null) { MainActivity.getInstance().startActivity(new Intent(getApplicationContext(), MainActivity.class) @@ -146,9 +184,21 @@ public class DaedalusVpnService extends VpnService implements Runnable { return START_NOT_STICKY; } + private void startThread() { + if (this.mThread == null) { + this.mThread = new Thread(this, "DaedalusVpn"); + this.running = true; + this.mThread.start(); + } + } + @Override public void onDestroy() { stopThread(); + if (receiver != null) { + unregisterReceiver(receiver); + receiver = null; + } } private void stopThread() { @@ -185,7 +235,7 @@ public class DaedalusVpnService extends VpnService implements Runnable { if (shouldRefresh) { RuleResolver.clear(); - DNSServerHelper.clearCache(); + DnsServerHelper.clearCache(); Logger.info("Daedalus VPN service has stopped"); } @@ -202,27 +252,30 @@ public class DaedalusVpnService extends VpnService implements Runnable { stopThread(); } - private InetAddress addDnsServer(Builder builder, String format, byte[] ipv6Template, String addr) throws UnknownHostException { + private InetAddress addDnsServer(Builder builder, String format, byte[] ipv6Template, AbstractDnsServer addr) + throws UnknownHostException { int size = dnsServers.size(); size++; - if (addr.contains("/")) {//https uri + if (addr.getAddress().contains("/")) {//https uri String alias = String.format(format, size + 1); dnsServers.put(alias, addr); builder.addRoute(alias, 32); return InetAddress.getByName(alias); } - InetAddress address = InetAddress.getByName(addr); + InetAddress address = InetAddress.getByName(addr.getAddress()); if (address instanceof Inet6Address && ipv6Template == null) { Log.i(TAG, "addDnsServer: Ignoring DNS server " + address); } else if (address instanceof Inet4Address) { String alias = String.format(format, size + 1); - dnsServers.put(alias, address.getHostAddress()); + addr.setHostAddress(address.getHostAddress()); + dnsServers.put(alias, addr); builder.addRoute(alias, 32); return InetAddress.getByName(alias); } else if (address instanceof Inet6Address) { ipv6Template[ipv6Template.length - 1] = (byte) (size + 1); InetAddress i6addr = Inet6Address.getByAddress(ipv6Template); - dnsServers.put(i6addr.getHostAddress(), address.getHostAddress()); + addr.setHostAddress(address.getHostAddress()); + dnsServers.put(i6addr.getHostAddress(), addr); return i6addr; } return null; @@ -231,14 +284,13 @@ public class DaedalusVpnService extends VpnService implements Runnable { @Override public void run() { try { - DNSServerHelper.buildCache(); + DnsServerHelper.buildCache(); Builder builder = new Builder() .setSession("Daedalus") .setConfigureIntent(PendingIntent.getActivity(this, 0, new Intent(this, MainActivity.class).putExtra(MainActivity.LAUNCH_FRAGMENT, MainActivity.FRAGMENT_SETTINGS), PendingIntent.FLAG_ONE_SHOT)); - //Set App Filter if (Daedalus.getPrefs().getBoolean("settings_app_filter_switch", false)) { ArrayList apps = Daedalus.configurations.getAppObjects(); if (apps.size() > 0) { @@ -275,36 +327,28 @@ public class DaedalusVpnService extends VpnService implements Runnable { statisticQuery = Daedalus.getPrefs().getBoolean("settings_count_query_times", false); byte[] ipv6Template = new byte[]{32, 1, 13, (byte) (184 & 0xFF), 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}; - if (primaryServer.contains(":") || secondaryServer.contains(":")) {//IPv6 - try { - InetAddress addr = Inet6Address.getByAddress(ipv6Template); - Log.d(TAG, "configure: Adding IPv6 address" + addr); - builder.addAddress(addr, 120); - } catch (Exception e) { - Logger.logException(e); + try { + InetAddress addr = Inet6Address.getByAddress(ipv6Template); + Log.d(TAG, "configure: Adding IPv6 address" + addr); + builder.addAddress(addr, 120); + } catch (Exception e) { + Logger.logException(e); - ipv6Template = null; - } - } else { ipv6Template = null; } - InetAddress aliasPrimary; - InetAddress aliasSecondary; if (advanced) { dnsServers = new HashMap<>(); aliasPrimary = addDnsServer(builder, format, ipv6Template, primaryServer); aliasSecondary = addDnsServer(builder, format, ipv6Template, secondaryServer); } else { - aliasPrimary = InetAddress.getByName(primaryServer); - aliasSecondary = InetAddress.getByName(secondaryServer); + aliasPrimary = InetAddress.getByName(primaryServer.getAddress()); + aliasSecondary = InetAddress.getByName(secondaryServer.getAddress()); } - InetAddress primaryDNSServer = aliasPrimary; - InetAddress secondaryDNSServer = aliasSecondary; - Logger.info("Daedalus VPN service is listening on " + primaryServer + " as " + primaryDNSServer.getHostAddress()); - Logger.info("Daedalus VPN service is listening on " + secondaryServer + " as " + secondaryDNSServer.getHostAddress()); - builder.addDnsServer(primaryDNSServer).addDnsServer(secondaryDNSServer); + Logger.info("Daedalus VPN service is listening on " + primaryServer.getAddress() + " as " + aliasPrimary.getHostAddress()); + Logger.info("Daedalus VPN service is listening on " + secondaryServer.getAddress() + " as " + aliasSecondary.getHostAddress()); + builder.addDnsServer(aliasPrimary).addDnsServer(aliasSecondary); if (advanced) { builder.setBlocking(true); @@ -324,13 +368,17 @@ public class DaedalusVpnService extends VpnService implements Runnable { Thread.sleep(1000); } } - } catch ( - InterruptedException ignored) { - } catch ( - Exception e) { + } catch (InterruptedException ignored) { + } catch (Exception e) { + MainActivity.getInstance().runOnUiThread(() -> + new AlertDialog.Builder(MainActivity.getInstance()) + .setTitle(R.string.error_occurred) + .setMessage(Logger.getExceptionMessage(e)) + .setPositiveButton(android.R.string.ok, (d, id) -> { + }) + .show()); Logger.logException(e); } finally { - Log.d(TAG, "quit"); stopThread(); } } @@ -346,14 +394,13 @@ public class DaedalusVpnService extends VpnService implements Runnable { if (time - lastUpdate >= 1000) { lastUpdate = time; if (notification != null) { - notification.setContentTitle(getResources().getString(R.string.notice_queries) + " " + String.valueOf(provider.getDnsQueryTimes())); + notification.setContentTitle(getResources().getString(R.string.notice_queries) + " " + provider.getDnsQueryTimes()); NotificationManager manager = (NotificationManager) this.getSystemService(Context.NOTIFICATION_SERVICE); manager.notify(NOTIFICATION_ACTIVATED, notification.build()); } } } - public static class VpnNetworkException extends Exception { public VpnNetworkException(String s) { super(s); @@ -362,7 +409,5 @@ public class DaedalusVpnService extends VpnService implements Runnable { public VpnNetworkException(String s, Throwable t) { super(s, t); } - } - } diff --git a/app/src/main/java/org/itxtech/daedalus/util/Configurations.java b/app/src/main/java/org/itxtech/daedalus/util/Configurations.java index 7de91c7..f970666 100644 --- a/app/src/main/java/org/itxtech/daedalus/util/Configurations.java +++ b/app/src/main/java/org/itxtech/daedalus/util/Configurations.java @@ -3,7 +3,7 @@ package org.itxtech.daedalus.util; import com.google.gson.Gson; import com.google.gson.stream.JsonReader; import org.itxtech.daedalus.Daedalus; -import org.itxtech.daedalus.util.server.CustomDNSServer; +import org.itxtech.daedalus.server.CustomDnsServer; import java.io.File; import java.io.FileReader; @@ -27,7 +27,7 @@ public class Configurations { private static File file; - private ArrayList customDNSServers; + private ArrayList customDNSServers; private ArrayList appObjects; private ArrayList hostsRules; @@ -60,7 +60,7 @@ public class Configurations { this.activateCounter = activateCounter; } - public ArrayList getCustomDNSServers() { + public ArrayList getCustomDNSServers() { if (customDNSServers == null) { customDNSServers = new ArrayList<>(); } diff --git a/app/src/main/java/org/itxtech/daedalus/util/DnsServersDetector.java b/app/src/main/java/org/itxtech/daedalus/util/DnsServersDetector.java new file mode 100644 index 0000000..1f24bef --- /dev/null +++ b/app/src/main/java/org/itxtech/daedalus/util/DnsServersDetector.java @@ -0,0 +1,166 @@ +package org.itxtech.daedalus.util; + +import android.content.Context; +import android.net.*; +import android.os.Build; + +import java.io.BufferedReader; +import java.io.InputStream; +import java.io.InputStreamReader; +import java.io.LineNumberReader; +import java.lang.reflect.Method; +import java.net.InetAddress; +import java.util.ArrayList; +import java.util.HashSet; +import java.util.List; +import java.util.Set; + +/** + * Daedalus Project + * + * @author iTX Technologies + * @link https://itxtech.org + *

+ * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + */ +public class DnsServersDetector { + //https://stackoverflow.com/a/48973823 + private static final String METHOD_EXEC_PROP_DELIM = "]: ["; + + public static String[] getServers(Context context) { + String[] result; + result = getServersMethodSystemProperties(); + if (result != null && result.length > 0) { + return result; + } + result = getServersMethodConnectivityManager(context); + if (result != null && result.length > 0) { + return result; + } + result = getServersMethodExec(); + if (result != null && result.length > 0) { + return result; + } + return null; + } + + private static String[] getServersMethodConnectivityManager(Context context) { + ArrayList priorityServersArrayList = new ArrayList<>(); + ArrayList serversArrayList = new ArrayList<>(); + ConnectivityManager connectivityManager = (ConnectivityManager) context.getSystemService(Context.CONNECTIVITY_SERVICE); + if (connectivityManager != null) { + for (Network network : connectivityManager.getAllNetworks()) { + NetworkInfo networkInfo = connectivityManager.getNetworkInfo(network); + if (networkInfo.isConnected()) { + LinkProperties linkProperties = connectivityManager.getLinkProperties(network); + List dnsServersList = linkProperties.getDnsServers(); + if (linkPropertiesHasDefaultRoute(linkProperties)) { + for (InetAddress element : dnsServersList) { + String dnsHost = element.getHostAddress(); + priorityServersArrayList.add(dnsHost); + } + } else { + for (InetAddress element : dnsServersList) { + String dnsHost = element.getHostAddress(); + serversArrayList.add(dnsHost); + } + } + } + } + } + if (priorityServersArrayList.isEmpty()) { + priorityServersArrayList.addAll(serversArrayList); + } + if (priorityServersArrayList.size() > 0) { + return priorityServersArrayList.toArray(new String[0]); + } + return null; + } + + private static String[] getServersMethodSystemProperties() { + if (Build.VERSION.SDK_INT < Build.VERSION_CODES.O) { + String re1 = "^\\d+(\\.\\d+){3}$"; + String re2 = "^[0-9a-f]+(:[0-9a-f]*)+:[0-9a-f]+$"; + ArrayList serversArrayList = new ArrayList<>(); + try { + Class SystemProperties = Class.forName("android.os.SystemProperties"); + Method method = SystemProperties.getMethod("get", new Class[]{String.class}); + String[] netdns = new String[]{"net.dns1", "net.dns2", "net.dns3", "net.dns4"}; + for (String dns : netdns) { + Object[] args = new Object[]{dns}; + String v = (String) method.invoke(null, args); + if (v != null && (v.matches(re1) || v.matches(re2)) && !serversArrayList.contains(v)) { + serversArrayList.add(v); + } + } + if (serversArrayList.size() > 0) { + return serversArrayList.toArray(new String[0]); + } + } catch (Exception ex) { + Logger.logException(ex); + } + } + return null; + } + + private static String[] getServersMethodExec() { + try { + Process process = Runtime.getRuntime().exec("getprop"); + InputStream inputStream = process.getInputStream(); + LineNumberReader lineNumberReader = new LineNumberReader(new InputStreamReader(inputStream)); + Set serversSet = methodExecParseProps(lineNumberReader); + if (serversSet.size() > 0) { + return serversSet.toArray(new String[0]); + } + } catch (Exception ex) { + Logger.logException(ex); + } + return null; + } + + private static Set methodExecParseProps(BufferedReader lineNumberReader) throws Exception { + String line; + HashSet serversSet = new HashSet<>(); + while ((line = lineNumberReader.readLine()) != null) { + int split = line.indexOf(METHOD_EXEC_PROP_DELIM); + if (split == -1) { + continue; + } + String property = line.substring(1, split); + int valueStart = split + METHOD_EXEC_PROP_DELIM.length(); + int valueEnd = line.length() - 1; + if (valueEnd < valueStart) { + continue; + } + String value = line.substring(valueStart, valueEnd); + if (value.isEmpty()) { + continue; + } + if (property.endsWith(".dns") || property.endsWith(".dns1") || property.endsWith(".dns2") || + property.endsWith(".dns3") || property.endsWith(".dns4")) { + InetAddress ip = InetAddress.getByName(value); + if (ip == null) { + continue; + } + value = ip.getHostAddress(); + if (value == null || value.length() == 0) { + continue; + } + serversSet.add(value); + } + } + return serversSet; + } + + private static boolean linkPropertiesHasDefaultRoute(LinkProperties linkProperties) { + for (RouteInfo route : linkProperties.getRoutes()) { + if (route.isDefaultRoute()) { + return true; + } + } + return false; + } +} diff --git a/app/src/main/java/org/itxtech/daedalus/widget/ClickPreference.java b/app/src/main/java/org/itxtech/daedalus/widget/ClickPreference.java index 432bc04..4640abf 100644 --- a/app/src/main/java/org/itxtech/daedalus/widget/ClickPreference.java +++ b/app/src/main/java/org/itxtech/daedalus/widget/ClickPreference.java @@ -1,7 +1,7 @@ package org.itxtech.daedalus.widget; import android.content.Context; -import android.preference.ListPreference; +import androidx.preference.ListPreference; import android.util.AttributeSet; /** diff --git a/app/src/main/res/layout/activity_app_filter.xml b/app/src/main/res/layout/activity_app_filter.xml index 0668267..a0e5c87 100644 --- a/app/src/main/res/layout/activity_app_filter.xml +++ b/app/src/main/res/layout/activity_app_filter.xml @@ -25,7 +25,6 @@ android:layout_height="match_parent" app:layout_behavior="@string/appbar_scrolling_view_behavior"> - - \ No newline at end of file + diff --git a/app/src/main/res/layout/card_appview.xml b/app/src/main/res/layout/card_appview.xml index a41bd15..97e14a3 100644 --- a/app/src/main/res/layout/card_appview.xml +++ b/app/src/main/res/layout/card_appview.xml @@ -1,32 +1,28 @@ + android:layout_width="match_parent" + android:layout_height="wrap_content" + android:gravity="center_vertical"> + android:id="@+id/app_icon" + android:layout_width="46dp" + android:layout_height="46dp" + android:paddingEnd="10dp" + android:paddingStart="14dp"/> + android:id="@+id/app_name" + android:layout_width="0dp" + android:layout_height="wrap_content" + android:layout_weight="1.0"/> + android:id="@+id/app_check" + android:layout_width="wrap_content" + android:layout_height="wrap_content" + android:clickable="false" + android:paddingEnd="6dp" + android:paddingStart="2dp"/> - \ No newline at end of file + diff --git a/app/src/main/res/layout/card_rule.xml b/app/src/main/res/layout/card_rule.xml index d448b35..d90ecad 100644 --- a/app/src/main/res/layout/card_rule.xml +++ b/app/src/main/res/layout/card_rule.xml @@ -14,47 +14,39 @@ app:cardPreventCornerOverlap="true" android:id="@+id/cardView_indicator"> - - + - - - - - - + android:padding="@dimen/margin_small" + android:id="@+id/textView_rule_name" + android:textAppearance="?android:attr/textAppearanceLarge" + android:layout_alignParentTop="true" + android:layout_alignParentStart="true"/> + + + - \ No newline at end of file + diff --git a/app/src/main/res/layout/card_server.xml b/app/src/main/res/layout/card_server.xml index 1a350a2..6191267 100644 --- a/app/src/main/res/layout/card_server.xml +++ b/app/src/main/res/layout/card_server.xml @@ -5,6 +5,7 @@ android:layout_height="wrap_content" android:layout_width="match_parent" android:clickable="true" + android:focusable="true" android:foreground="?attr/selectableItemBackground" app:cardCornerRadius="10dp" app:cardPreventCornerOverlap="true" @@ -23,7 +24,6 @@ android:id="@+id/textView_custom_dns_name" android:textAppearance="?android:attr/textAppearanceLarge" android:layout_alignParentTop="true" - android:layout_alignParentLeft="true" android:layout_alignParentStart="true"/> - \ No newline at end of file + diff --git a/app/src/main/res/layout/fragment_dns_servers.xml b/app/src/main/res/layout/fragment_dns_servers.xml index d012c3e..5021ef3 100644 --- a/app/src/main/res/layout/fragment_dns_servers.xml +++ b/app/src/main/res/layout/fragment_dns_servers.xml @@ -11,7 +11,6 @@ android:layout_height="match_parent" android:scrollbars="horizontal" android:layout_alignParentTop="true" - android:layout_alignParentLeft="true" android:layout_alignParentStart="true"/> - \ No newline at end of file + diff --git a/app/src/main/res/layout/fragment_dns_test.xml b/app/src/main/res/layout/fragment_dns_test.xml index 66d3cb2..eb1e1f9 100644 --- a/app/src/main/res/layout/fragment_dns_test.xml +++ b/app/src/main/res/layout/fragment_dns_test.xml @@ -41,18 +41,15 @@ android:layout_alignParentStart="true" android:layout_marginTop="10dp" android:id="@+id/button_start_test" - android:layout_alignParentEnd="true" - android:layout_alignParentRight="true" - android:layout_alignParentLeft="true"/> + android:layout_alignParentEnd="true"/> - \ No newline at end of file + diff --git a/app/src/main/res/layout/fragment_main.xml b/app/src/main/res/layout/fragment_main.xml index 9ada810..2924b70 100644 --- a/app/src/main/res/layout/fragment_main.xml +++ b/app/src/main/res/layout/fragment_main.xml @@ -13,7 +13,6 @@ app:layout_behavior="@string/appbar_scrolling_view_behavior" tools:context="org.itxtech.daedalus.fragment.HomeFragment"> -