44import android .app .NotificationChannel ;
55import android .app .NotificationManager ;
66import android .app .PendingIntent ;
7+ import android .content .BroadcastReceiver ;
78import android .content .Context ;
89import android .content .Intent ;
10+ import android .content .IntentFilter ;
911import android .content .pm .PackageManager ;
12+ import android .net .ConnectivityManager ;
1013import android .net .VpnService ;
1114import android .os .Build ;
1215import android .os .ParcelFileDescriptor ;
1316import android .system .OsConstants ;
1417import android .util .Log ;
18+ import androidx .appcompat .app .AlertDialog ;
1519import androidx .core .app .NotificationCompat ;
1620import org .itxtech .daedalus .Daedalus ;
1721import org .itxtech .daedalus .R ;
1822import org .itxtech .daedalus .activity .MainActivity ;
1923import org .itxtech .daedalus .provider .Provider ;
2024import org .itxtech .daedalus .provider .ProviderPicker ;
2125import org .itxtech .daedalus .receiver .StatusBarBroadcastReceiver ;
22- import org .itxtech .daedalus .util .Logger ;
23- import org .itxtech .daedalus .util .RuleResolver ;
2426import org .itxtech .daedalus .server .AbstractDnsServer ;
27+ import org .itxtech .daedalus .server .DnsServer ;
2528import org .itxtech .daedalus .server .DnsServerHelper ;
29+ import org .itxtech .daedalus .util .DnsServersDetector ;
30+ import org .itxtech .daedalus .util .Logger ;
31+ import org .itxtech .daedalus .util .RuleResolver ;
2632
2733import java .net .Inet4Address ;
2834import java .net .Inet6Address ;
@@ -54,20 +60,19 @@ public class DaedalusVpnService extends VpnService implements Runnable {
5460
5561 public static AbstractDnsServer primaryServer ;
5662 public static AbstractDnsServer secondaryServer ;
63+ private static InetAddress aliasPrimary ;
64+ private static InetAddress aliasSecondary ;
5765
5866 private NotificationCompat .Builder notification = null ;
59-
6067 private boolean running = false ;
6168 private long lastUpdate = 0 ;
6269 private boolean statisticQuery ;
6370 private Provider provider ;
6471 private ParcelFileDescriptor descriptor ;
65-
6672 private Thread mThread = null ;
67-
6873 public HashMap <String , AbstractDnsServer > dnsServers ;
69-
7074 private static boolean activated = false ;
75+ private static BroadcastReceiver receiver ;
7176
7277 public static boolean isActivated () {
7378 return activated ;
@@ -76,6 +81,44 @@ public static boolean isActivated() {
7681 @ Override
7782 public void onCreate () {
7883 super .onCreate ();
84+ if (Daedalus .getPrefs ().getBoolean ("settings_use_system_dns" , false )) {
85+ registerReceiver (receiver = new BroadcastReceiver () {
86+ @ Override
87+ public void onReceive (Context context , Intent intent ) {
88+ updateUpstreamServers (context );
89+ }
90+ }, new IntentFilter (ConnectivityManager .CONNECTIVITY_ACTION ));
91+ }
92+ }
93+
94+ public static void updateUpstreamServers (Context context ) {
95+ String [] servers = DnsServersDetector .getServers (context );
96+ if (servers != null ) {
97+ if (servers .length >= 2 && (aliasPrimary == null || !aliasPrimary .getHostAddress ().equals (servers [0 ])) &&
98+ (aliasSecondary == null || !aliasSecondary .getHostAddress ().equals (servers [0 ])) &&
99+ (aliasPrimary == null || !aliasPrimary .getHostAddress ().equals (servers [1 ])) &&
100+ (aliasSecondary == null || !aliasSecondary .getHostAddress ().equals (servers [1 ]))) {
101+ primaryServer .setAddress (servers [0 ]);
102+ primaryServer .setPort (DnsServer .DNS_SERVER_DEFAULT_PORT );
103+ secondaryServer .setAddress (servers [1 ]);
104+ secondaryServer .setPort (DnsServer .DNS_SERVER_DEFAULT_PORT );
105+ } else if ((aliasPrimary == null || !aliasPrimary .getHostAddress ().equals (servers [0 ])) &&
106+ (aliasSecondary == null || !aliasSecondary .getHostAddress ().equals (servers [0 ]))) {
107+ primaryServer .setAddress (servers [0 ]);
108+ primaryServer .setPort (DnsServer .DNS_SERVER_DEFAULT_PORT );
109+ secondaryServer .setAddress (servers [0 ]);
110+ secondaryServer .setPort (DnsServer .DNS_SERVER_DEFAULT_PORT );
111+ } else {
112+ StringBuilder buf = new StringBuilder ();
113+ for (String server : servers ) {
114+ buf .append (server ).append (" " );
115+ }
116+ Logger .error ("Invalid upstream DNS " + buf );
117+ }
118+ Logger .info ("Upstream DNS updated: " + primaryServer .getAddress () + " " + secondaryServer .getAddress ());
119+ } else {
120+ Logger .error ("Cannot obtain upstream DNS server!" );
121+ }
79122 }
80123
81124 @ Override
@@ -85,7 +128,6 @@ public int onStartCommand(Intent intent, int flags, int startId) {
85128 case ACTION_ACTIVATE :
86129 activated = true ;
87130 if (Daedalus .getPrefs ().getBoolean ("settings_notification" , true )) {
88-
89131 NotificationManager manager = (NotificationManager ) this .getSystemService (Context .NOTIFICATION_SERVICE );
90132
91133 NotificationCompat .Builder builder ;
@@ -127,12 +169,7 @@ public int onStartCommand(Intent intent, int flags, int startId) {
127169 }
128170
129171 Daedalus .initRuleResolver ();
130-
131- if (this .mThread == null ) {
132- this .mThread = new Thread (this , "DaedalusVpn" );
133- this .running = true ;
134- this .mThread .start ();
135- }
172+ startThread ();
136173 Daedalus .updateShortcut (getApplicationContext ());
137174 if (MainActivity .getInstance () != null ) {
138175 MainActivity .getInstance ().startActivity (new Intent (getApplicationContext (), MainActivity .class )
@@ -147,9 +184,20 @@ public int onStartCommand(Intent intent, int flags, int startId) {
147184 return START_NOT_STICKY ;
148185 }
149186
187+ private void startThread () {
188+ if (this .mThread == null ) {
189+ this .mThread = new Thread (this , "DaedalusVpn" );
190+ this .running = true ;
191+ this .mThread .start ();
192+ }
193+ }
194+
150195 @ Override
151196 public void onDestroy () {
152197 stopThread ();
198+ if (receiver != null ) {
199+ unregisterReceiver (receiver );
200+ }
153201 }
154202
155203 private void stopThread () {
@@ -203,7 +251,8 @@ public void onRevoke() {
203251 stopThread ();
204252 }
205253
206- private InetAddress addDnsServer (Builder builder , String format , byte [] ipv6Template , AbstractDnsServer addr ) throws UnknownHostException {
254+ private InetAddress addDnsServer (Builder builder , String format , byte [] ipv6Template , AbstractDnsServer addr )
255+ throws UnknownHostException {
207256 int size = dnsServers .size ();
208257 size ++;
209258 if (addr .getAddress ().contains ("/" )) {//https uri
@@ -241,7 +290,6 @@ public void run() {
241290 new Intent (this , MainActivity .class ).putExtra (MainActivity .LAUNCH_FRAGMENT , MainActivity .FRAGMENT_SETTINGS ),
242291 PendingIntent .FLAG_ONE_SHOT ));
243292
244- //Set App Filter
245293 if (Daedalus .getPrefs ().getBoolean ("settings_app_filter_switch" , false )) {
246294 ArrayList <String > apps = Daedalus .configurations .getAppObjects ();
247295 if (apps .size () > 0 ) {
@@ -278,22 +326,16 @@ public void run() {
278326 statisticQuery = Daedalus .getPrefs ().getBoolean ("settings_count_query_times" , false );
279327 byte [] ipv6Template = new byte []{32 , 1 , 13 , (byte ) (184 & 0xFF ), 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 };
280328
281- if (primaryServer .getAddress ().contains (":" ) || secondaryServer .getAddress ().contains (":" )) {//IPv6
282- try {
283- InetAddress addr = Inet6Address .getByAddress (ipv6Template );
284- Log .d (TAG , "configure: Adding IPv6 address" + addr );
285- builder .addAddress (addr , 120 );
286- } catch (Exception e ) {
287- Logger .logException (e );
329+ try {
330+ InetAddress addr = Inet6Address .getByAddress (ipv6Template );
331+ Log .d (TAG , "configure: Adding IPv6 address" + addr );
332+ builder .addAddress (addr , 120 );
333+ } catch (Exception e ) {
334+ Logger .logException (e );
288335
289- ipv6Template = null ;
290- }
291- } else {
292336 ipv6Template = null ;
293337 }
294338
295- InetAddress aliasPrimary ;
296- InetAddress aliasSecondary ;
297339 if (advanced ) {
298340 dnsServers = new HashMap <>();
299341 aliasPrimary = addDnsServer (builder , format , ipv6Template , primaryServer );
@@ -303,8 +345,8 @@ public void run() {
303345 aliasSecondary = InetAddress .getByName (secondaryServer .getAddress ());
304346 }
305347
306- Logger .info ("Daedalus VPN service is listening on " + primaryServer + " as " + aliasPrimary .getHostAddress ());
307- Logger .info ("Daedalus VPN service is listening on " + secondaryServer + " as " + aliasSecondary .getHostAddress ());
348+ Logger .info ("Daedalus VPN service is listening on " + primaryServer . getAddress () + " as " + aliasPrimary .getHostAddress ());
349+ Logger .info ("Daedalus VPN service is listening on " + secondaryServer . getAddress () + " as " + aliasSecondary .getHostAddress ());
308350 builder .addDnsServer (aliasPrimary ).addDnsServer (aliasSecondary );
309351
310352 if (advanced ) {
@@ -325,13 +367,17 @@ public void run() {
325367 Thread .sleep (1000 );
326368 }
327369 }
328- } catch (
329- InterruptedException ignored ) {
330- } catch (
331- Exception e ) {
370+ } catch (InterruptedException ignored ) {
371+ } catch (Exception e ) {
372+ MainActivity .getInstance ().runOnUiThread (() ->
373+ new AlertDialog .Builder (MainActivity .getInstance ())
374+ .setTitle (R .string .error_occurred )
375+ .setMessage (Logger .getExceptionMessage (e ))
376+ .setPositiveButton (android .R .string .ok , (d , id ) -> {
377+ })
378+ .show ());
332379 Logger .logException (e );
333380 } finally {
334- Log .d (TAG , "quit" );
335381 stopThread ();
336382 }
337383 }
@@ -354,11 +400,11 @@ private void updateUserInterface() {
354400 }
355401 }
356402
357-
358403 public static class VpnNetworkException extends Exception {
359404 public VpnNetworkException (String s ) {
360405 super (s );
361406 }
407+
362408 public VpnNetworkException (String s , Throwable t ) {
363409 super (s , t );
364410 }
0 commit comments