tor-commits
Threads by month
- ----- 2025 -----
- June
- May
- April
- March
- February
- January
- ----- 2024 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2023 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2022 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2021 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2020 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2019 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2018 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2017 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2016 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2015 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2014 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2013 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2012 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2011 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
April 2020
- 25 participants
- 2156 discussions

[orbot/master] Added first stab at a MoatActivity. Doesn't change bridges automatically, yet. Also, Volley needs to be proxied.
by n8fr8@torproject.org 28 Apr '20
by n8fr8@torproject.org 28 Apr '20
28 Apr '20
commit e7cfe4651d6874f35579f724f22e83c78cec04af
Author: Benjamin Erhart <berhart(a)netzarchitekten.com>
Date: Fri Apr 17 13:43:05 2020 +0200
Added first stab at a MoatActivity. Doesn't change bridges automatically, yet. Also, Volley needs to be proxied.
---
app/build.gradle | 11 +-
app/src/main/AndroidManifest.xml | 139 ++++++------
.../ui/onboarding/BridgeWizardActivity.java | 48 +++--
.../android/ui/onboarding/MoatActivity.java | 233 +++++++++++++++++++++
app/src/main/res/layout/activity_moat.xml | 53 +++++
app/src/main/res/layout/content_bridge_wizard.xml | 9 +-
app/src/main/res/menu/moat.xml | 28 +++
app/src/main/res/values/strings.xml | 9 +-
8 files changed, 443 insertions(+), 87 deletions(-)
diff --git a/app/build.gradle b/app/build.gradle
index 20707251..e6cf6de7 100644
--- a/app/build.gradle
+++ b/app/build.gradle
@@ -24,7 +24,7 @@ def getVersionName = { ->
}
android {
- signingConfigs {
+ signingConfigs {
release {
if (keystorePropertiesFile.canRead()) {
keyAlias keystoreProperties['keyAlias']
@@ -118,15 +118,17 @@ android {
dependencies {
implementation project(':orbotservice')
- implementation 'com.google.android.material:material:1.0.0'
+ implementation 'com.google.android.material:material:1.1.0'
implementation 'pl.bclogic:pulsator4droid:1.0.3'
implementation 'com.github.apl-devs:appintro:v4.2.2'
- implementation 'com.github.javiersantos:AppUpdater:2.6.4'
+ implementation 'com.github.javiersantos:AppUpdater:2.7'
androidTestImplementation "tools.fastlane:screengrab:1.2.0"
+ implementation 'androidx.localbroadcastmanager:localbroadcastmanager:1.0.0'
+ implementation 'com.android.volley:volley:1.1.1'
}
// Map for the version code that gives each ABI a value.
-ext.abiCodes = ['armeabi-v7a':'1', 'arm64-v8a':'2', 'mips':'3', 'x86':'4', 'x86_64':'5']
+ext.abiCodes = ['armeabi-v7a': '1', 'arm64-v8a': '2', 'mips': '3', 'x86': '4', 'x86_64': '5']
import com.android.build.OutputFile
@@ -141,4 +143,3 @@ android.applicationVariants.all { variant ->
}
}
}
-
diff --git a/app/src/main/AndroidManifest.xml b/app/src/main/AndroidManifest.xml
index 1d7a9f16..011b78c7 100644
--- a/app/src/main/AndroidManifest.xml
+++ b/app/src/main/AndroidManifest.xml
@@ -4,6 +4,14 @@
package="org.torproject.android"
android:installLocation="internalOnly">
+ <!--
+ Some Chromebooks don't support touch. Although not essential,
+ it's a good idea to explicitly include this declaration.
+ -->
+ <uses-feature
+ android:name="android.hardware.touchscreen"
+ android:required="false" />
+
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.FOREGROUND_SERVICE" />
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
@@ -11,10 +19,6 @@
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.REQUEST_IGNORE_BATTERY_OPTIMIZATIONS" />
- <!-- Some Chromebooks don't support touch. Although not essential,
- it's a good idea to explicitly include this declaration. -->
- <uses-feature android:name="android.hardware.touchscreen"
- android:required="false" />
<application
android:name=".OrbotApp"
@@ -26,8 +30,8 @@
android:icon="@drawable/ic_launcher"
android:label="@string/app_name"
android:theme="@style/DefaultTheme"
- tools:replace="android:allowBackup"
- >
+ tools:replace="android:allowBackup">
+
<activity
android:name=".OrbotMainActivity"
android:excludeFromRecents="false"
@@ -46,18 +50,17 @@
<data android:scheme="bridge" />
</intent-filter>
<intent-filter>
- <category android:name="android.intent.category.DEFAULT" />
-
<action android:name="org.torproject.android.REQUEST_HS_PORT" />
+
+ <category android:name="android.intent.category.DEFAULT" />
</intent-filter>
<intent-filter>
- <category android:name="android.intent.category.DEFAULT" />
-
<action android:name="org.torproject.android.START_TOR" />
+
+ <category android:name="android.intent.category.DEFAULT" />
</intent-filter>
- </activity>
+ </activity> <!-- This is for ensuring the background service still runs when/if the app is swiped away -->
- <!-- This is for ensuring the background service still runs when/if the app is swiped away -->
<activity
android:name=".service.util.DummyActivity"
android:allowTaskReparenting="true"
@@ -69,39 +72,72 @@
android:noHistory="true"
android:stateNotNeeded="true"
android:theme="@android:style/Theme.Translucent" />
+
<activity
android:name=".ui.VPNEnableActivity"
android:exported="false"
android:label="@string/app_name" />
+
<activity
android:name=".settings.SettingsPreferences"
android:label="@string/app_name" />
+
<activity
android:name=".ui.AppManagerActivity"
android:label="@string/app_name"
android:theme="@style/Theme.AppCompat" />
- <service
- android:name=".service.OrbotService"
- android:enabled="true"
- android:permission="android.permission.BIND_VPN_SERVICE"
- android:stopWithTask="false"></service>
- <service
- android:name=".service.vpn.TorVpnService"
- android:enabled="true"
- android:permission="android.permission.BIND_VPN_SERVICE">
- <intent-filter>
- <action android:name="android.net.VpnService" />
- </intent-filter>
- </service>
+ <activity
+ android:name=".ui.hiddenservices.HiddenServicesActivity"
+ android:label="@string/title_activity_hidden_services"
+ android:theme="@style/DefaultTheme">
+ <meta-data
+ android:name="android.support.PARENT_ACTIVITY"
+ android:value=".OrbotMainActivity" />
+ </activity>
+
+ <activity
+ android:name=".ui.hiddenservices.ClientCookiesActivity"
+ android:label="@string/client_cookies"
+ android:theme="@style/DefaultTheme">
+ <meta-data
+ android:name="android.support.PARENT_ACTIVITY"
+ android:value=".OrbotMainActivity" />
+ </activity>
+
+ <activity android:name=".ui.onboarding.OnboardingActivity" />
+ <activity android:name=".ui.onboarding.BridgeWizardActivity" />
+ <activity android:name=".ui.onboarding.MoatActivity" />
+
+ <provider
+ android:name=".ui.hiddenservices.providers.HSContentProvider"
+ android:authorities="org.torproject.android.ui.hiddenservices.providers"
+ android:exported="false" />
+
+ <provider
+ android:name="androidx.core.content.FileProvider"
+ android:authorities="org.torproject.android.ui.hiddenservices.storage"
+ android:exported="false"
+ android:grantUriPermissions="true">
+ <meta-data
+ android:name="android.support.FILE_PROVIDER_PATHS"
+ android:resource="@xml/hidden_services_paths" />
+ </provider>
+
+ <provider
+ android:name=".ui.hiddenservices.providers.CookieContentProvider"
+ android:authorities="org.torproject.android.ui.hiddenservices.providers.cookie"
+ android:exported="false" />
<receiver
android:name=".service.StartTorReceiver"
- android:exported="true">
+ android:exported="true"
+ tools:ignore="ExportedReceiver">
<intent-filter>
<action android:name="org.torproject.android.intent.action.START" />
</intent-filter>
</receiver>
+
<receiver
android:name=".OnBootReceiver"
android:enabled="true"
@@ -123,45 +159,20 @@
</intent-filter>
</receiver>
- <activity
- android:name=".ui.hiddenservices.HiddenServicesActivity"
- android:label="@string/title_activity_hidden_services"
- android:theme="@style/DefaultTheme">
- <meta-data
- android:name="android.support.PARENT_ACTIVITY"
- android:value=".OrbotMainActivity" />
- </activity>
-
- <provider
- android:name=".ui.hiddenservices.providers.HSContentProvider"
- android:authorities="org.torproject.android.ui.hiddenservices.providers"
- android:exported="false" />
- <provider
- android:name="androidx.core.content.FileProvider"
- android:authorities="org.torproject.android.ui.hiddenservices.storage"
- android:exported="false"
- android:grantUriPermissions="true">
- <meta-data
- android:name="android.support.FILE_PROVIDER_PATHS"
- android:resource="@xml/hidden_services_paths" />
- </provider>
-
- <activity
- android:name=".ui.hiddenservices.ClientCookiesActivity"
- android:label="@string/client_cookies"
- android:theme="@style/DefaultTheme">
- <meta-data
- android:name="android.support.PARENT_ACTIVITY"
- android:value=".OrbotMainActivity" />
- </activity>
-
- <activity android:name=".ui.onboarding.OnboardingActivity"/>
- <activity android:name=".ui.onboarding.BridgeWizardActivity"/>
+ <service
+ android:name=".service.OrbotService"
+ android:enabled="true"
+ android:permission="android.permission.BIND_VPN_SERVICE"
+ android:stopWithTask="false" />
- <provider
- android:name=".ui.hiddenservices.providers.CookieContentProvider"
- android:authorities="org.torproject.android.ui.hiddenservices.providers.cookie"
- android:exported="false" />
+ <service
+ android:name=".service.vpn.TorVpnService"
+ android:enabled="true"
+ android:permission="android.permission.BIND_VPN_SERVICE">
+ <intent-filter>
+ <action android:name="android.net.VpnService" />
+ </intent-filter>
+ </service>
</application>
</manifest>
\ No newline at end of file
diff --git a/app/src/main/java/org/torproject/android/ui/onboarding/BridgeWizardActivity.java b/app/src/main/java/org/torproject/android/ui/onboarding/BridgeWizardActivity.java
index 6e54e103..5ffe79e5 100644
--- a/app/src/main/java/org/torproject/android/ui/onboarding/BridgeWizardActivity.java
+++ b/app/src/main/java/org/torproject/android/ui/onboarding/BridgeWizardActivity.java
@@ -8,13 +8,16 @@ import android.content.Intent;
import android.net.Uri;
import android.os.AsyncTask;
import android.os.Bundle;
-import androidx.appcompat.app.AppCompatActivity;
-import androidx.appcompat.widget.Toolbar;
import android.text.TextUtils;
import android.view.MenuItem;
import android.view.View;
import android.widget.RadioButton;
import android.widget.TextView;
+
+import androidx.appcompat.app.ActionBar;
+import androidx.appcompat.app.AppCompatActivity;
+import androidx.appcompat.widget.Toolbar;
+
import org.torproject.android.R;
import org.torproject.android.service.util.Prefs;
import org.torproject.android.settings.LocaleHelper;
@@ -36,7 +39,11 @@ public class BridgeWizardActivity extends AppCompatActivity {
setContentView(R.layout.activity_bridge_wizard);
Toolbar toolbar = findViewById(R.id.toolbar);
setSupportActionBar(toolbar);
- getSupportActionBar().setDisplayHomeAsUpEnabled(true);
+
+ ActionBar actionBar = getSupportActionBar();
+ if (actionBar != null) {
+ actionBar.setDisplayHomeAsUpEnabled(true);
+ }
tvStatus = findViewById(R.id.lbl_bridge_test_status);
tvStatus.setVisibility(View.GONE);
@@ -83,6 +90,14 @@ public class BridgeWizardActivity extends AppCompatActivity {
}
});
+ RadioButton btnMoat = findViewById(R.id.btnMoat);
+ btnMoat.setOnClickListener(new View.OnClickListener() {
+ @Override
+ public void onClick(View v) {
+ startActivity(new Intent(BridgeWizardActivity.this, MoatActivity.class));
+ }
+ });
+
if (!Prefs.bridgesEnabled())
btnDirect.setChecked(true);
else if (Prefs.getBridgesList().equals("meek"))
@@ -128,7 +143,7 @@ public class BridgeWizardActivity extends AppCompatActivity {
.setPositiveButton(R.string.get_bridges_web, new Dialog.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
- openBrowser(URL_TOR_BRIDGES, true);
+ openBrowser(URL_TOR_BRIDGES);
}
}).show();
}
@@ -146,7 +161,8 @@ public class BridgeWizardActivity extends AppCompatActivity {
/*
* Launch the system activity for Uri viewing with the provided url
*/
- private void openBrowser(final String browserLaunchUrl, boolean forceExternal) {
+ @SuppressWarnings("SameParameterValue")
+ private void openBrowser(final String browserLaunchUrl) {
startActivity(new Intent(Intent.ACTION_VIEW, Uri.parse(browserLaunchUrl)));
}
@@ -174,18 +190,17 @@ public class BridgeWizardActivity extends AppCompatActivity {
@Override
protected Boolean doInBackground(String... host) {
// Background Code
- boolean result = false;
-
for (int i = 0; i < host.length; i++) {
String testHost = host[i];
i++; //move to the port
int testPort = Integer.parseInt(host[i]);
- result = isHostReachable(testHost, testPort, 10000);
- if (result)
- return result;
+
+ if (isHostReachable(testHost, testPort, 10000)) {
+ return true;
+ }
}
- return result;
+ return false;
}
@Override
@@ -201,22 +216,23 @@ public class BridgeWizardActivity extends AppCompatActivity {
}
}
+ @SuppressWarnings("SameParameterValue")
private static boolean isHostReachable(String serverAddress, int serverTCPport, int timeoutMS) {
boolean connected = false;
- Socket socket;
+
try {
- socket = new Socket();
+ Socket socket = new Socket();
SocketAddress socketAddress = new InetSocketAddress(serverAddress, serverTCPport);
socket.connect(socketAddress, timeoutMS);
if (socket.isConnected()) {
connected = true;
socket.close();
}
- } catch (IOException e) {
+ }
+ catch (IOException e) {
e.printStackTrace();
- } finally {
- socket = null;
}
+
return connected;
}
}
diff --git a/app/src/main/java/org/torproject/android/ui/onboarding/MoatActivity.java b/app/src/main/java/org/torproject/android/ui/onboarding/MoatActivity.java
new file mode 100644
index 00000000..e5ea5459
--- /dev/null
+++ b/app/src/main/java/org/torproject/android/ui/onboarding/MoatActivity.java
@@ -0,0 +1,233 @@
+package org.torproject.android.ui.onboarding;
+
+import android.app.Dialog;
+import android.content.DialogInterface;
+import android.graphics.BitmapFactory;
+import android.os.Bundle;
+import android.util.Base64;
+import android.util.Log;
+import android.view.Menu;
+import android.view.MenuItem;
+import android.view.View;
+import android.widget.EditText;
+import android.widget.ImageView;
+
+import androidx.appcompat.app.ActionBar;
+import androidx.appcompat.app.AlertDialog;
+import androidx.appcompat.app.AppCompatActivity;
+import androidx.appcompat.widget.Toolbar;
+
+import com.android.volley.Request;
+import com.android.volley.RequestQueue;
+import com.android.volley.Response;
+import com.android.volley.VolleyError;
+import com.android.volley.toolbox.JsonObjectRequest;
+import com.android.volley.toolbox.Volley;
+
+import org.json.JSONArray;
+import org.json.JSONException;
+import org.json.JSONObject;
+import org.torproject.android.R;
+import org.torproject.android.service.util.Prefs;
+
+/**
+ Implements the MOAT protocol: Fetches OBFS4 bridges via Meek Azure.
+
+ The bare minimum of the communication is implemented. E.g. no check, if OBFS4 is possible or which
+ protocol version the server wants to speak. The first should be always good, as OBFS4 is the most widely
+ supported bridge type, the latter should be the same as we requested (0.1.0) anyway.
+
+ API description:
+ https://github.com/NullHypothesis/bridgedb#accessing-the-moat-interface
+ */
+public class MoatActivity extends AppCompatActivity implements View.OnClickListener {
+
+ private static String moatBaseUrl = "https://bridges.torproject.org/moat";
+
+ private ImageView mCaptchaIv;
+ private EditText mSolutionEt;
+
+ private String mChallenge;
+
+ private RequestQueue mQueue;
+
+
+ @Override
+ protected void onCreate(Bundle savedInstanceState) {
+ super.onCreate(savedInstanceState);
+ setContentView(R.layout.activity_moat);
+
+ Toolbar toolbar = findViewById(R.id.toolbar);
+ setSupportActionBar(toolbar);
+
+ ActionBar actionBar = getSupportActionBar();
+ if (actionBar != null) {
+ actionBar.setDisplayHomeAsUpEnabled(true);
+ }
+
+ setTitle(getString(R.string.request_bridges));
+
+ mCaptchaIv = findViewById(R.id.captchaIv);
+ mSolutionEt = findViewById(R.id.solutionEt);
+
+ findViewById(R.id.requestBt).setOnClickListener(this);
+
+ mQueue = Volley.newRequestQueue(this);
+ }
+
+ @Override
+ public boolean onCreateOptionsMenu(Menu menu) {
+ super.onCreateOptionsMenu(menu);
+
+ getMenuInflater().inflate(R.menu.moat, menu);
+
+ return true;
+ }
+
+ @Override
+ protected void onResume() {
+ super.onResume();
+
+ // Set to Meek bridge.
+ Prefs.setBridgesList("meek");
+ Prefs.putBridgesEnabled(true);
+
+ fetchCaptcha();
+ }
+
+ @Override
+ public void onClick(View view) {
+ Log.d(MoatActivity.class.toString(), "Request Bridge!");
+
+ requestBridges(mSolutionEt.getText().toString());
+ }
+
+ @Override
+ public boolean onOptionsItemSelected(MenuItem item) {
+ if (item.getItemId() == R.id.menu_refresh) {
+ fetchCaptcha();
+ }
+
+ return super.onOptionsItemSelected(item);
+ }
+
+ private void fetchCaptcha() {
+ JsonObjectRequest request = buildRequest("fetch",
+ "\"type\": \"client-transports\", \"supported\": [\"obfs4\"]",
+ new Response.Listener<JSONObject>() {
+ @Override
+ public void onResponse(JSONObject response) {
+ try {
+ JSONObject data = response.getJSONArray("data").getJSONObject(0);
+ mChallenge = data.getString("challenge");
+
+ byte[] image = Base64.decode(data.getString("image"), Base64.DEFAULT);
+ mCaptchaIv.setImageBitmap(BitmapFactory.decodeByteArray(image, 0, image.length));
+
+ } catch (JSONException e) {
+ Log.d(MoatActivity.class.toString(), "Error decoding answer.");
+
+ new AlertDialog.Builder(MoatActivity.this)
+ .setTitle(R.string.error)
+ .setMessage(e.getLocalizedMessage())
+ .setNegativeButton(R.string.btn_cancel, new Dialog.OnClickListener() {
+ @Override
+ public void onClick(DialogInterface dialog, int which) {
+ //Do nothing.
+ }
+ })
+ .show();
+ }
+ }
+ });
+
+ if (request != null) {
+ mQueue.add(request);
+ }
+ }
+
+ private void requestBridges(String solution) {
+ JsonObjectRequest request = buildRequest("check",
+ "\"id\": \"2\", \"type\": \"moat-solution\", \"transport\": \"obfs4\", \"challenge\": \""
+ + mChallenge + "\", \"solution\": \"" + solution + "\", \"qrcode\": \"false\"",
+ new Response.Listener<JSONObject>() {
+ @Override
+ public void onResponse(JSONObject response) {
+ try {
+ JSONArray bridges = response.getJSONArray("data").getJSONObject(0).getJSONArray("bridges");
+
+ Log.d(MoatActivity.class.toString(), "Bridges: " + bridges.toString());
+
+ StringBuilder sb = new StringBuilder();
+
+ for (int i = 0; i < bridges.length(); i++) {
+ sb.append(bridges.getString(i)).append("\n");
+ }
+
+ Prefs.setBridgesList(sb.toString());
+ Prefs.putBridgesEnabled(true);
+
+ MoatActivity.this.finish();
+
+ } catch (JSONException e) {
+ Log.d(MoatActivity.class.toString(), "Error decoding answer: " + response.toString());
+
+ new AlertDialog.Builder(MoatActivity.this)
+ .setTitle(R.string.error)
+ .setMessage(e.getLocalizedMessage())
+ .setNegativeButton(R.string.btn_cancel, new Dialog.OnClickListener() {
+ @Override
+ public void onClick(DialogInterface dialog, int which) {
+ //Do nothing.
+ }
+ })
+ .show();
+ }
+ }
+ });
+
+ if (request != null) {
+ mQueue.add(request);
+ }
+ }
+
+ private JsonObjectRequest buildRequest(String endpoint, String payload, Response.Listener<JSONObject> listener) {
+ JSONObject requestBody;
+
+ try {
+ requestBody = new JSONObject("{\"data\": [{\"version\": \"0.1.0\", " + payload + "}]}");
+ } catch (JSONException e) {
+ return null;
+ }
+
+ Log.d(MoatActivity.class.toString(), "Request: " + requestBody.toString());
+
+ return new JsonObjectRequest(
+ Request.Method.POST,
+ moatBaseUrl + "/" + endpoint,
+ requestBody,
+ listener,
+ new Response.ErrorListener() {
+ @Override
+ public void onErrorResponse(VolleyError error) {
+ Log.d(MoatActivity.class.toString(), "Error response.");
+
+ new AlertDialog.Builder(MoatActivity.this)
+ .setTitle(R.string.error)
+ .setMessage(error.getLocalizedMessage())
+ .setNegativeButton(R.string.btn_cancel, new Dialog.OnClickListener() {
+ @Override
+ public void onClick(DialogInterface dialog, int which) {
+ //Do nothing.
+ }
+ })
+ .show();
+ }
+ }
+ ) {
+ public String getBodyContentType() {
+ return "application/vnd.api+json";
+ }
+ };
+ }
+}
diff --git a/app/src/main/res/layout/activity_moat.xml b/app/src/main/res/layout/activity_moat.xml
new file mode 100644
index 00000000..fe01873c
--- /dev/null
+++ b/app/src/main/res/layout/activity_moat.xml
@@ -0,0 +1,53 @@
+<?xml version="1.0" encoding="utf-8"?>
+<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:app="http://schemas.android.com/apk/res-auto"
+ xmlns:tools="http://schemas.android.com/tools"
+ android:layout_width="match_parent"
+ android:layout_height="match_parent"
+ android:orientation="vertical"
+ android:background="@color/dark_purple"
+ tools:context=".ui.onboarding.MoatActivity">
+
+ <com.google.android.material.appbar.AppBarLayout
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:theme="@style/DefaultTheme.AppBarOverlay">
+
+ <androidx.appcompat.widget.Toolbar
+ android:id="@+id/toolbar"
+ android:layout_width="match_parent"
+ android:layout_height="?attr/actionBarSize"
+ android:background="?attr/colorPrimary"
+ app:popupTheme="@style/DefaultTheme.PopupOverlay" />
+
+ </com.google.android.material.appbar.AppBarLayout>
+
+ <TextView
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:layout_margin="12dp"
+ android:text="@string/solve_captcha_instruction" />
+
+ <ImageView
+ android:id="@+id/captchaIv"
+ android:layout_width="match_parent"
+ android:layout_height="240dp"
+ android:contentDescription="@string/captcha"
+ tools:srcCompat="@tools:sample/backgrounds/scenic" />
+
+ <EditText
+ android:id="@+id/solutionEt"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:autofillHints=""
+ android:hint="@string/enter_characters_from_image"
+ android:ems="10"
+ android:inputType="textShortMessage|text" />
+
+ <Button
+ android:id="@+id/requestBt"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:text="@string/request_bridges" />
+
+</LinearLayout>
diff --git a/app/src/main/res/layout/content_bridge_wizard.xml b/app/src/main/res/layout/content_bridge_wizard.xml
index a5b7995b..1a1e98e0 100644
--- a/app/src/main/res/layout/content_bridge_wizard.xml
+++ b/app/src/main/res/layout/content_bridge_wizard.xml
@@ -19,7 +19,7 @@
android:textSize="16sp"
android:textStyle="bold" />
- <RadioGroup xmlns:android="http://schemas.android.com/apk/res/android"
+ <RadioGroup
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:orientation="vertical">
@@ -52,6 +52,13 @@
android:layout_margin="12dp"
android:text="@string/bridges_get_new" />
+ <RadioButton
+ android:id="@+id/btnMoat"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:layout_margin="12dp"
+ android:text="@string/bridges_get_new"/>
+
</RadioGroup>
<TextView
diff --git a/app/src/main/res/menu/moat.xml b/app/src/main/res/menu/moat.xml
new file mode 100644
index 00000000..f32bbe11
--- /dev/null
+++ b/app/src/main/res/menu/moat.xml
@@ -0,0 +1,28 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+/*
+ * Copyright (C) 2008 Esmertec AG.
+ * Copyright (C) 2008 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+-->
+<menu xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:yourapp="http://schemas.android.com/apk/res-auto"
+ >
+ <item android:id="@+id/menu_refresh"
+ android:title="@string/refresh_captcha"
+ android:icon="@drawable/ic_refresh_white_24dp"
+ yourapp:showAsAction="always"
+ />
+</menu>
diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml
index bff412a2..cc60ddfd 100644
--- a/app/src/main/res/values/strings.xml
+++ b/app/src/main/res/values/strings.xml
@@ -124,7 +124,7 @@
<string name="newnym">You\'ve switched to a new Tor identity!</string>
<string name="pref_open_proxy_on_all_interfaces_title">Open Proxy on All Interfaces</string>
- <string name="pref_open_proxy_on_all_interfaces_summary">Allow Wi-Fi peers, tethered devices and anyone else who can connect to your IP, to access Tor</string>
+ <string name="pref_open_proxy_on_all_interfaces_summary">Allow Wi-Fi peers, tethered devices and anyone else who can connect to your IP, to access Tor</string>
<string name="no_network_connectivity_putting_tor_to_sleep_">No network connectivity. Putting Tor to sleep…</string>
<string name="network_connectivity_is_good_waking_tor_up_">Network connectivity is good. Waking Tor up…</string>
@@ -259,4 +259,11 @@
<string name="app_services">App services</string>
<string name="default_socks_http">SOCKS: - HTTP: -</string>
<string name="refresh_apps">Refresh Apps</string>
+
+ <!-- MoatActivity -->
+ <string name="request_bridges">Request Bridges</string>
+ <string name="refresh_captcha">Refresh CAPTCHA</string>
+ <string name="solve_captcha_instruction">Solve the CAPTCHA to request bridges.</string>
+ <string name="captcha">Captcha</string>
+ <string name="enter_characters_from_image">Enter characters from image</string>
</resources>
1
0

28 Apr '20
commit bfbb85bc69aaf277ad559e420c5f34d26c8460a7
Author: Hashik Donthineni <hashikdonthineni(a)gmail.com>
Date: Fri Mar 27 10:34:47 2020 +0530
Changed variable names for better understanding
---
.../android/ui/onboarding/CustomSlideBigText.java | 14 +++++++-------
1 file changed, 7 insertions(+), 7 deletions(-)
diff --git a/app/src/main/java/org/torproject/android/ui/onboarding/CustomSlideBigText.java b/app/src/main/java/org/torproject/android/ui/onboarding/CustomSlideBigText.java
index c1add577..ad4810b5 100644
--- a/app/src/main/java/org/torproject/android/ui/onboarding/CustomSlideBigText.java
+++ b/app/src/main/java/org/torproject/android/ui/onboarding/CustomSlideBigText.java
@@ -21,7 +21,7 @@ public class CustomSlideBigText extends Fragment {
private String mButtonText;
private String mSubTitle;
private View.OnClickListener mButtonListener;
- private TextView tv, title;
+ private TextView bigTextSub, title;
private Button button;
public static CustomSlideBigText newInstance(int layoutResId) {
@@ -63,11 +63,11 @@ public class CustomSlideBigText extends Fragment {
View view = inflater.inflate(layoutResId, container, false);
title = ((TextView) view.findViewById(R.id.custom_slide_big_text));
title.setText(mTitle);
- tv = (TextView) view.findViewById(R.id.custom_slide_big_text_sub);
+ bigTextSub = (TextView) view.findViewById(R.id.custom_slide_big_text_sub);
if (!TextUtils.isEmpty(mSubTitle)) {
- tv.setText(mSubTitle);
- tv.setVisibility(View.VISIBLE);
+ bigTextSub.setText(mSubTitle);
+ bigTextSub.setVisibility(View.VISIBLE);
}
if (mButtonText != null) {
@@ -85,8 +85,8 @@ public class CustomSlideBigText extends Fragment {
public void onActivityCreated(Bundle savedInstanceState) {
super.onActivityCreated(savedInstanceState);
if (savedInstanceState != null) {
- title.setText(savedInstanceState.getString(getResources().getString(R.string.Title)));
- tv.setText(savedInstanceState.getString(getResources().getString(R.string.SubTitle)));
+ title.setText(savedInstanceState.getString(getResources().getString(R.string.Pref_title)));
+ bigTextSub.setText(savedInstanceState.getString(getResources().getString(R.string.SubTitle)));
if (mButtonText != null) {
button.setText(savedInstanceState.getString(getResources().getString(R.string.ButtonText)));
}
@@ -98,7 +98,7 @@ public class CustomSlideBigText extends Fragment {
@Override
public void onSaveInstanceState(Bundle outState) {
super.onSaveInstanceState(outState);
- outState.putString(getResources().getString(R.string.Title), mTitle);
+ outState.putString(getResources().getString(R.string.Pref_title), mTitle);
outState.putString(getResources().getString(R.string.SubTitle), mSubTitle);
if (mButtonText != null) {
outState.putString(getResources().getString(R.string.ButtonText), mButtonText);
1
0

28 Apr '20
commit 446dfa6eb91c89e366740dba9c74887671f3968d
Author: bim <dsnake(a)protonmail.com>
Date: Wed Apr 8 20:41:53 2020 -0400
Fixes bugs in #289 pertaining to parsing bridges
---
.../torproject/android/service/OrbotService.java | 30 ++++++++--------------
1 file changed, 10 insertions(+), 20 deletions(-)
diff --git a/orbotservice/src/main/java/org/torproject/android/service/OrbotService.java b/orbotservice/src/main/java/org/torproject/android/service/OrbotService.java
index dbd36dbd..90d07456 100644
--- a/orbotservice/src/main/java/org/torproject/android/service/OrbotService.java
+++ b/orbotservice/src/main/java/org/torproject/android/service/OrbotService.java
@@ -25,8 +25,6 @@ import android.content.IntentFilter;
import android.content.SharedPreferences;
import android.content.pm.PackageManager;
import android.database.Cursor;
-import android.net.ConnectivityManager;
-import android.net.NetworkInfo;
import android.net.Uri;
import android.os.Build;
import android.os.IBinder;
@@ -37,14 +35,12 @@ import androidx.core.app.NotificationCompat;
import androidx.localbroadcastmanager.content.LocalBroadcastManager;
import android.text.TextUtils;
import android.util.Log;
-import android.widget.RemoteViews;
import com.jaredrummler.android.shell.CommandResult;
import net.freehaven.tor.control.ConfigEntry;
import net.freehaven.tor.control.TorControlConnection;
-import org.apache.commons.io.IOUtils;
import org.torproject.android.service.util.CustomShell;
import org.torproject.android.service.util.CustomTorResourceInstaller;
import org.torproject.android.service.util.DummyActivity;
@@ -70,7 +66,6 @@ import java.io.InputStreamReader;
import java.io.PrintStream;
import java.io.PrintWriter;
import java.net.Socket;
-import java.text.Normalizer;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collections;
@@ -78,7 +73,6 @@ import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Random;
-import java.util.Set;
import java.util.StringTokenizer;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
@@ -1628,10 +1622,8 @@ public class OrbotService extends Service implements TorServiceConstants, OrbotC
if (bridgeList != null && bridgeList.length() > 5) //longer then 1 = some real values here
{
- String[] bridgeListLines = bridgeList.trim().split("\\n");
-
-
- int bridgeIdx = (int)Math.round(Math.random()*((double)bridgeListLines.length));
+ String[] bridgeListLines = parseBridgesFromSettings(bridgeList);
+ int bridgeIdx = (int)Math.floor(Math.random()*((double)bridgeListLines.length));
String bridgeLine = bridgeListLines[bridgeIdx];
extraLines.append("Bridge ");
extraLines.append(bridgeLine);
@@ -1645,7 +1637,6 @@ public class OrbotService extends Service implements TorServiceConstants, OrbotC
}
}**/
-
} else {
String type = "obfs4";
@@ -1786,15 +1777,14 @@ public class OrbotService extends Service implements TorServiceConstants, OrbotC
return extraLines;
}
- public static String flattenToAscii(String string) {
- char[] out = new char[string.length()];
- string = Normalizer.normalize(string, Normalizer.Form.NFD);
- int j = 0;
- for (int i = 0, n = string.length(); i < n; ++i) {
- char c = string.charAt(i);
- if (c <= '\u007F') out[j++] = c;
- }
- return new String(out);
+ /**
+ * @param bridgeList bridges that were manually entered into Orbot settings
+ * @return Array with each bridge as an element, no whitespace entries see issue #289...
+ */
+ private static String[] parseBridgesFromSettings(String bridgeList) {
+ // this regex replaces lines that only contain whitespace with an empty String
+ bridgeList = bridgeList.trim().replaceAll("(?m)^[ \t]*\r?\n", "");
+ return bridgeList.split("\\n");
}
//using Google DNS for now as the public DNS server
1
0
commit 42832216bc0c0cbb7917a6eb0ccfd8bfbcd582e8
Author: Benjamin Erhart <berhart(a)netzarchitekten.com>
Date: Thu Apr 16 17:22:54 2020 +0200
Updated BUILD info.
---
BUILD | 3 +++
1 file changed, 3 insertions(+)
diff --git a/BUILD b/BUILD
index 8e9b9b33..285fdf1c 100644
--- a/BUILD
+++ b/BUILD
@@ -25,10 +25,13 @@ You then need to run "ndk-build" from:
ndk-build
mv libs/armeabi/pdnsd libs/armeabi/pdnsd.so
mv libs/armeabi-v7a/pdnsd libs/armeabi-v7a/pdnsd.so
+ mv libs/arm64-v8a/pdnsd libs/arm64-v8a/pdnsd.so
mv libs/x86/pdnsd libs/x86/pdnsd.so
+ mv libs/x86_64/pdnsd libs/x86_64/pdnsd.so
This isn't enough though and we'll now sew up the binary into a small package
that will handle basic Tor controlling features.
+(Doesn't work and should be unnecessary on Android Studio/Android SDK as of 2020!)
android update project --name Orbot --target android-15 --path .
1
0

[orbot/master] Fixed most warnings and errors in OrbotMainActivity.
by n8fr8@torproject.org 28 Apr '20
by n8fr8@torproject.org 28 Apr '20
28 Apr '20
commit 469d4cfaf2e645723e00347522b67047885e924e
Author: Benjamin Erhart <berhart(a)netzarchitekten.com>
Date: Thu Apr 16 17:34:59 2020 +0200
Fixed most warnings and errors in OrbotMainActivity.
---
.../org/torproject/android/OrbotMainActivity.java | 933 ++++++++++-----------
1 file changed, 444 insertions(+), 489 deletions(-)
diff --git a/app/src/main/java/org/torproject/android/OrbotMainActivity.java b/app/src/main/java/org/torproject/android/OrbotMainActivity.java
index 831f55f9..ff23beed 100644
--- a/app/src/main/java/org/torproject/android/OrbotMainActivity.java
+++ b/app/src/main/java/org/torproject/android/OrbotMainActivity.java
@@ -23,17 +23,16 @@ import android.net.Uri;
import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
-import android.os.RemoteException;
import android.text.Html;
import android.text.TextUtils;
import android.util.Log;
-import android.view.Gravity;
import android.view.LayoutInflater;
import android.view.Menu;
import android.view.MenuInflater;
import android.view.MenuItem;
import android.view.View;
import android.view.View.OnLongClickListener;
+import android.view.ViewGroup;
import android.view.animation.AccelerateInterpolator;
import android.widget.AdapterView;
import android.widget.AdapterView.OnItemSelectedListener;
@@ -45,13 +44,17 @@ import android.widget.LinearLayout;
import android.widget.Spinner;
import android.widget.TextView;
import android.widget.Toast;
+
import androidx.appcompat.app.AppCompatActivity;
import androidx.appcompat.widget.SwitchCompat;
import androidx.appcompat.widget.Toolbar;
+import androidx.core.view.GravityCompat;
import androidx.drawerlayout.widget.DrawerLayout;
import androidx.localbroadcastmanager.content.LocalBroadcastManager;
+
import com.google.zxing.integration.android.IntentIntegrator;
import com.google.zxing.integration.android.IntentResult;
+
import org.json.JSONArray;
import org.torproject.android.service.OrbotConstants;
import org.torproject.android.service.OrbotService;
@@ -73,7 +76,6 @@ import org.torproject.android.ui.hiddenservices.permissions.PermissionManager;
import org.torproject.android.ui.hiddenservices.providers.HSContentProvider;
import org.torproject.android.ui.onboarding.BridgeWizardActivity;
import org.torproject.android.ui.onboarding.OnboardingActivity;
-import pl.bclogic.pulsator4droid.library.PulsatorLayout;
import java.io.BufferedReader;
import java.io.File;
@@ -87,6 +89,8 @@ import java.util.ArrayList;
import java.util.Locale;
import java.util.StringTokenizer;
+import pl.bclogic.pulsator4droid.library.PulsatorLayout;
+
import static androidx.core.content.FileProvider.getUriForFile;
import static org.torproject.android.MainConstants.COUNTRY_CODES;
import static org.torproject.android.MainConstants.RESULT_CLOSE_ALL;
@@ -106,14 +110,14 @@ public class OrbotMainActivity extends AppCompatActivity
private TextView uploadText = null;
private TextView mTxtOrbotLog = null;
- private Button mBtnStart = null;
+ private Button mBtnStart = null;
- private SwitchCompat mBtnVPN = null;
+ private SwitchCompat mBtnVPN = null;
private SwitchCompat mBtnBridges = null;
-
+
private Spinner spnCountries = null;
- private DrawerLayout mDrawer;
+ private DrawerLayout mDrawer;
/* Some tracking bits */
private String torStatus = null; //latest status reported from the tor service
@@ -122,12 +126,12 @@ public class OrbotMainActivity extends AppCompatActivity
private SharedPreferences mPrefs = null;
private boolean autoStartFromIntent = false;
-
+
private final static int REQUEST_VPN = 8888;
private final static int REQUEST_SETTINGS = 0x9874;
private final static int REQUEST_VPN_APPS_SELECT = 8889;
- private final static int LOG_DRAWER_GRAVITY = Gravity.END;
+ private final static int LOG_DRAWER_GRAVITY = GravityCompat.END;
// message types for mStatusUpdateHandler
private final static int STATUS_UPDATE = 1;
@@ -136,7 +140,7 @@ public class OrbotMainActivity extends AppCompatActivity
public final static String INTENT_ACTION_REQUEST_HIDDEN_SERVICE = "org.torproject.android.REQUEST_HS_PORT";
- public final static String INTENT_ACTION_REQUEST_START_TOR = "org.torproject.android.START_TOR";
+ public final static String INTENT_ACTION_REQUEST_START_TOR = "org.torproject.android.START_TOR";
PulsatorLayout mPulsator;
@@ -157,7 +161,7 @@ public class OrbotMainActivity extends AppCompatActivity
Editor pEdit = mPrefs.edit();
pEdit.remove("pref_hs_ports");
- pEdit.commit();
+ pEdit.apply();
}
}
@@ -173,11 +177,11 @@ public class OrbotMainActivity extends AppCompatActivity
/* Create the widgets before registering for broadcasts to guarantee
* that the widgets exist when the status updates try to update them */
- doLayout();
+ doLayout();
- /* receive the internal status broadcasts, which are separate from the public
- * status broadcasts to prevent other apps from sending fake/wrong status
- * info to this app */
+ /* receive the internal status broadcasts, which are separate from the public
+ * status broadcasts to prevent other apps from sending fake/wrong status
+ * info to this app */
LocalBroadcastManager lbm = LocalBroadcastManager.getInstance(this);
lbm.registerReceiver(mLocalBroadcastReceiver,
new IntentFilter(TorServiceConstants.ACTION_STATUS));
@@ -189,32 +193,28 @@ public class OrbotMainActivity extends AppCompatActivity
new IntentFilter(TorServiceConstants.LOCAL_ACTION_PORTS));
-
boolean showFirstTime = mPrefs.getBoolean("connect_first_time", true);
- if (showFirstTime)
- {
+ if (showFirstTime) {
Editor pEdit = mPrefs.edit();
pEdit.putBoolean("connect_first_time", false);
- pEdit.commit();
- startActivity(new Intent(this,OnboardingActivity.class));
+ pEdit.apply();
+ startActivity(new Intent(this, OnboardingActivity.class));
}
- /**
- * Resets previous DNS Port to the default
- */
+ // Resets previous DNS Port to the default.
getSharedPrefs(getApplicationContext()).edit().putInt(VpnPrefs.PREFS_DNS_PORT,
VpnConstants.TOR_DNS_PORT_DEFAULT).apply();
}
- private void sendIntentToService(final String action) {
+ private void sendIntentToService(final String action) {
Intent intent = new Intent(OrbotMainActivity.this, OrbotService.class);
intent.setAction(action);
startService(intent);
- }
+ }
private void stopTor() {
@@ -239,61 +239,68 @@ public class OrbotMainActivity extends AppCompatActivity
if (action == null)
return;
- if (action.equals(TorServiceConstants.LOCAL_ACTION_LOG)) {
- Message msg = mStatusUpdateHandler.obtainMessage(STATUS_UPDATE);
- msg.obj = intent.getStringExtra(TorServiceConstants.LOCAL_EXTRA_LOG);
- msg.getData().putString("status", intent.getStringExtra(TorServiceConstants.EXTRA_STATUS));
- mStatusUpdateHandler.sendMessage(msg);
-
- } else if (action.equals(TorServiceConstants.LOCAL_ACTION_BANDWIDTH)) {
- long upload = intent.getLongExtra("up", 0);
- long download = intent.getLongExtra("down", 0);
- long written = intent.getLongExtra("written", 0);
- long read = intent.getLongExtra("read", 0);
-
- Message msg = mStatusUpdateHandler.obtainMessage(MESSAGE_TRAFFIC_COUNT);
- msg.getData().putLong("download", download);
- msg.getData().putLong("upload", upload);
- msg.getData().putLong("readTotal", read);
- msg.getData().putLong("writeTotal", written);
- msg.getData().putString("status", intent.getStringExtra(TorServiceConstants.EXTRA_STATUS));
-
- mStatusUpdateHandler.sendMessage(msg);
-
- } else if (action.equals(TorServiceConstants.ACTION_STATUS)) {
- lastStatusIntent = intent;
-
- Message msg = mStatusUpdateHandler.obtainMessage(STATUS_UPDATE);
- msg.getData().putString("status", intent.getStringExtra(TorServiceConstants.EXTRA_STATUS));
-
- mStatusUpdateHandler.sendMessage(msg);
- }
- else if (action.equals(TorServiceConstants.LOCAL_ACTION_PORTS)) {
+ switch (action) {
+ case TorServiceConstants.LOCAL_ACTION_LOG: {
+ Message msg = mStatusUpdateHandler.obtainMessage(STATUS_UPDATE);
+ msg.obj = intent.getStringExtra(TorServiceConstants.LOCAL_EXTRA_LOG);
+ msg.getData().putString("status", intent.getStringExtra(TorServiceConstants.EXTRA_STATUS));
+ mStatusUpdateHandler.sendMessage(msg);
+
+ break;
+ }
+ case TorServiceConstants.LOCAL_ACTION_BANDWIDTH: {
+ long upload = intent.getLongExtra("up", 0);
+ long download = intent.getLongExtra("down", 0);
+ long written = intent.getLongExtra("written", 0);
+ long read = intent.getLongExtra("read", 0);
+
+ Message msg = mStatusUpdateHandler.obtainMessage(MESSAGE_TRAFFIC_COUNT);
+ msg.getData().putLong("download", download);
+ msg.getData().putLong("upload", upload);
+ msg.getData().putLong("readTotal", read);
+ msg.getData().putLong("writeTotal", written);
+ msg.getData().putString("status", intent.getStringExtra(TorServiceConstants.EXTRA_STATUS));
+
+ mStatusUpdateHandler.sendMessage(msg);
+
+ break;
+ }
+ case TorServiceConstants.ACTION_STATUS: {
+ lastStatusIntent = intent;
+
+ Message msg = mStatusUpdateHandler.obtainMessage(STATUS_UPDATE);
+ msg.getData().putString("status", intent.getStringExtra(TorServiceConstants.EXTRA_STATUS));
+
+ mStatusUpdateHandler.sendMessage(msg);
+ break;
+ }
+ case TorServiceConstants.LOCAL_ACTION_PORTS: {
- Message msg = mStatusUpdateHandler.obtainMessage(MESSAGE_PORTS);
- msg.getData().putInt("socks",intent.getIntExtra(OrbotService.EXTRA_SOCKS_PROXY_PORT,-1));
- msg.getData().putInt("http",intent.getIntExtra(OrbotService.EXTRA_HTTP_PROXY_PORT,-1));
+ Message msg = mStatusUpdateHandler.obtainMessage(MESSAGE_PORTS);
+ msg.getData().putInt("socks", intent.getIntExtra(OrbotService.EXTRA_SOCKS_PROXY_PORT, -1));
+ msg.getData().putInt("http", intent.getIntExtra(OrbotService.EXTRA_HTTP_PROXY_PORT, -1));
- mStatusUpdateHandler.sendMessage(msg);
+ mStatusUpdateHandler.sendMessage(msg);
+ break;
+ }
}
}
};
-
- private void doLayout ()
- {
+
+ private void doLayout() {
setContentView(R.layout.layout_main);
-
+
setTitle(R.string.app_name);
- Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
+ Toolbar toolbar = findViewById(R.id.toolbar);
setSupportActionBar(toolbar);
-
- mDrawer = (DrawerLayout) findViewById(R.id.drawer_layout);
- mTxtOrbotLog = (TextView)findViewById(R.id.orbotLog);
-
- lblStatus = (TextView)findViewById(R.id.lblStatus);
+ mDrawer = findViewById(R.id.drawer_layout);
+
+ mTxtOrbotLog = findViewById(R.id.orbotLog);
+
+ lblStatus = findViewById(R.id.lblStatus);
lblStatus.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
@@ -303,39 +310,39 @@ public class OrbotMainActivity extends AppCompatActivity
lblPorts = findViewById(R.id.lblPorts);
- imgStatus = (ImageView)findViewById(R.id.imgStatus);
+ imgStatus = findViewById(R.id.imgStatus);
imgStatus.setOnLongClickListener(this);
- downloadText = (TextView)findViewById(R.id.trafficDown);
- uploadText = (TextView)findViewById(R.id.trafficUp);
-
- downloadText.setText(formatCount(0) + " / " + formatTotal(0));
- uploadText.setText(formatCount(0) + " / " + formatTotal(0));
-
- mBtnStart =(Button)findViewById(R.id.btnStart);
- mBtnStart.setOnClickListener(new View.OnClickListener()
- {
- @Override
- public void onClick(View v) {
-
- if (torStatus == TorServiceConstants.STATUS_OFF) {
- lblStatus.setText(getString(R.string.status_starting_up));
- startTor();
- } else {
- lblStatus.setText(getString(R.string.status_shutting_down));
- stopTor();
- }
- }
- });
-
- mBtnVPN = (SwitchCompat)findViewById(R.id.btnVPN);
-
+ downloadText = findViewById(R.id.trafficDown);
+ uploadText = findViewById(R.id.trafficUp);
+
+ String zero = String.format("%s / %s", formatCount(0), formatTotal(0));
+ downloadText.setText(zero);
+ uploadText.setText(zero);
+
+ mBtnStart = findViewById(R.id.btnStart);
+ mBtnStart.setOnClickListener(new View.OnClickListener() {
+ @Override
+ public void onClick(View v) {
+
+ if (torStatus.equals(TorServiceConstants.STATUS_OFF)) {
+ lblStatus.setText(getString(R.string.status_starting_up));
+ startTor();
+ } else {
+ lblStatus.setText(getString(R.string.status_shutting_down));
+ stopTor();
+ }
+ }
+ });
+
+ mBtnVPN = findViewById(R.id.btnVPN);
+
boolean useVPN = Prefs.useVpn();
mBtnVPN.setChecked(useVPN);
//auto start VPN if VPN is enabled
if (useVPN) {
- startActivity(new Intent(OrbotMainActivity.this,VPNEnableActivity.class));
+ startActivity(new Intent(OrbotMainActivity.this, VPNEnableActivity.class));
}
mBtnVPN.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {
@@ -346,43 +353,39 @@ public class OrbotMainActivity extends AppCompatActivity
});
- mBtnBridges = (SwitchCompat)findViewById(R.id.btnBridges);
- mBtnBridges.setChecked(Prefs.bridgesEnabled());
- mBtnBridges.setOnClickListener(new View.OnClickListener ()
- {
+ mBtnBridges = findViewById(R.id.btnBridges);
+ mBtnBridges.setChecked(Prefs.bridgesEnabled());
+ mBtnBridges.setOnClickListener(new View.OnClickListener() {
+
+ @Override
+ public void onClick(View v) {
+ promptSetupBridges(); //if ARM processor, show all bridge options
+ }
- @Override
- public void onClick(View v) {
- promptSetupBridges (); //if ARM processor, show all bridge options
- }
-
- });
+ });
- spnCountries = (Spinner)findViewById(R.id.spinnerCountry);
+ spnCountries = findViewById(R.id.spinnerCountry);
setCountrySpinner();
- mPulsator = (PulsatorLayout) findViewById(R.id.pulsator);
+ mPulsator = findViewById(R.id.pulsator);
}
- private void setCountrySpinner ()
- {
+ private void setCountrySpinner() {
String currentExit = Prefs.getExitNodes();
- if (currentExit.length() > 4)
- {
+ if (currentExit.length() > 4) {
//someone put a complex value in, so let's disable
- ArrayList<String> cList = new ArrayList<String>();
+ ArrayList<String> cList = new ArrayList<>();
cList.add(0, currentExit);
- ArrayAdapter<String> adapter = new ArrayAdapter<String>(this, android.R.layout.simple_spinner_item, cList);
+ ArrayAdapter<String> adapter = new ArrayAdapter<>(this, android.R.layout.simple_spinner_item, cList);
spnCountries.setAdapter(adapter);
spnCountries.setEnabled(false);
- }
- else {
+ } else {
int selIdx = -1;
- ArrayList<String> cList = new ArrayList<String>();
+ ArrayList<String> cList = new ArrayList<>();
cList.add(0, getString(R.string.vpn_default_world));
for (int i = 0; i < COUNTRY_CODES.length; i++) {
@@ -393,11 +396,11 @@ public class OrbotMainActivity extends AppCompatActivity
selIdx = i + 1;
}
- ArrayAdapter<String> adapter = new ArrayAdapter<String>(this, android.R.layout.simple_spinner_item, cList);
+ ArrayAdapter<String> adapter = new ArrayAdapter<>(this, android.R.layout.simple_spinner_item, cList);
spnCountries.setAdapter(adapter);
if (selIdx > 0)
- spnCountries.setSelection(selIdx,true);
+ spnCountries.setSelection(selIdx, true);
spnCountries.setOnItemSelectedListener(new OnItemSelectedListener() {
@@ -412,7 +415,7 @@ public class OrbotMainActivity extends AppCompatActivity
mOldPosition = position; //new position!
- String country = null;
+ String country;
if (position == 0)
country = "";
@@ -440,10 +443,10 @@ public class OrbotMainActivity extends AppCompatActivity
super.attachBaseContext(LocaleHelper.onAttach(base));
}
- /*
- * Create the UI Options Menu (non-Javadoc)
- * @see android.app.Activity#onCreateOptionsMenu(android.view.Menu)
- */
+ /*
+ * Create the UI Options Menu (non-Javadoc)
+ * @see android.app.Activity#onCreateOptionsMenu(android.view.Menu)
+ */
@Override
public boolean onCreateOptionsMenu(Menu menu) {
super.onCreateOptionsMenu(menu);
@@ -451,99 +454,85 @@ public class OrbotMainActivity extends AppCompatActivity
inflater.inflate(R.menu.orbot_main, menu);
return true;
}
-
-
+
@Override
- public boolean onOptionsItemSelected(MenuItem item) {
+ public boolean onOptionsItemSelected(MenuItem item) {
- if (item.getItemId() == R.id.menu_newnym)
- {
+ if (item.getItemId() == R.id.menu_newnym) {
requestNewTorIdentity();
- }
- else if (item.getItemId() == R.id.menu_settings)
- {
- Intent intent = new Intent(OrbotMainActivity.this, SettingsPreferences.class);
- startActivityForResult(intent, REQUEST_SETTINGS);
- }
- else if (item.getItemId() == R.id.menu_exit)
- {
- //exit app
- doExit();
-
- }
- else if (item.getItemId() == R.id.menu_about)
- {
- showAbout();
-
-
- }
- else if (item.getItemId() == R.id.menu_scan)
- {
- IntentIntegrator integrator = new IntentIntegrator(OrbotMainActivity.this);
- integrator.initiateScan();
- }
- else if (item.getItemId() == R.id.menu_share_bridge)
- {
-
- String bridges = Prefs.getBridgesList();
-
- if (bridges != null && bridges.length() > 0)
- {
- try {
- bridges = "bridge://" + URLEncoder.encode(bridges,"UTF-8");
-
- IntentIntegrator integrator = new IntentIntegrator(OrbotMainActivity.this);
- integrator.shareText(bridges);
-
- } catch (UnsupportedEncodingException e) {
- // TODO Auto-generated catch block
- e.printStackTrace();
- }
- }
-
- } else if (item.getItemId() == R.id.menu_hidden_services) {
- startActivity(new Intent(this, HiddenServicesActivity.class));
- } else if (item.getItemId() == R.id.menu_client_cookies) {
- startActivity(new Intent(this, ClientCookiesActivity.class));
- }
-
- return super.onOptionsItemSelected(item);
- }
-
- private void showAbout ()
- {
-
- LayoutInflater li = LayoutInflater.from(this);
- View view = li.inflate(R.layout.layout_about, null);
-
- String version = "";
-
- try {
- version = getPackageManager().getPackageInfo(getPackageName(), 0).versionName + " (Tor " + OrbotService.BINARY_TOR_VERSION + ")";
- } catch (NameNotFoundException e) {
- version = "Version Not Found";
- }
-
- TextView versionName = (TextView)view.findViewById(R.id.versionName);
- versionName.setText(version);
+ } else if (item.getItemId() == R.id.menu_settings) {
+ Intent intent = new Intent(OrbotMainActivity.this, SettingsPreferences.class);
+ startActivityForResult(intent, REQUEST_SETTINGS);
+ } else if (item.getItemId() == R.id.menu_exit) {
+ //exit app
+ doExit();
+
+ } else if (item.getItemId() == R.id.menu_about) {
+ showAbout();
+
- TextView aboutOther = (TextView)view.findViewById(R.id.aboutother);
+ } else if (item.getItemId() == R.id.menu_scan) {
+ IntentIntegrator integrator = new IntentIntegrator(OrbotMainActivity.this);
+ integrator.initiateScan();
+ } else if (item.getItemId() == R.id.menu_share_bridge) {
- try
- {
- String aboutText = readFromAssets(this,"LICENSE");
- aboutText = aboutText.replace("\n","<br/>");
- aboutOther.setText(Html.fromHtml(aboutText));
+ String bridges = Prefs.getBridgesList();
+
+ if (bridges != null && bridges.length() > 0) {
+ try {
+ bridges = "bridge://" + URLEncoder.encode(bridges, "UTF-8");
+
+ IntentIntegrator integrator = new IntentIntegrator(OrbotMainActivity.this);
+ integrator.shareText(bridges);
+
+ } catch (UnsupportedEncodingException e) {
+ e.printStackTrace();
+ }
}
- catch (Exception e){}
-
- new AlertDialog.Builder(this)
- .setTitle(getString(R.string.button_about))
- .setView(view)
- .show();
+
+ } else if (item.getItemId() == R.id.menu_hidden_services) {
+ startActivity(new Intent(this, HiddenServicesActivity.class));
+ } else if (item.getItemId() == R.id.menu_client_cookies) {
+ startActivity(new Intent(this, ClientCookiesActivity.class));
+ }
+
+ return super.onOptionsItemSelected(item);
+ }
+
+ private void showAbout() {
+
+ LayoutInflater li = LayoutInflater.from(this);
+ View view = li.inflate(R.layout.layout_about, (ViewGroup) lblStatus.getRootView());
+
+ String version;
+
+ try {
+ version = getPackageManager().getPackageInfo(getPackageName(), 0).versionName + " (Tor " + OrbotService.BINARY_TOR_VERSION + ")";
+ } catch (NameNotFoundException e) {
+ version = "Version Not Found";
}
+ TextView versionName = view.findViewById(R.id.versionName);
+ versionName.setText(version);
+
+ TextView aboutOther = view.findViewById(R.id.aboutother);
+
+ try {
+ String aboutText = readFromAssets(this, "LICENSE");
+ aboutText = aboutText.replace("\n", "<br/>");
+ aboutOther.setText(Html.fromHtml(aboutText));
+ } catch (Exception e) {
+ // This should not happen. Ignore.
+ }
+
+ new AlertDialog.Builder(this)
+ .setTitle(getString(R.string.button_about))
+ .setView(view)
+ .show();
+ }
+
+ @SuppressWarnings("SameParameterValue")
private static String readFromAssets(Context context, String filename) throws IOException {
BufferedReader reader = new BufferedReader(new InputStreamReader(context.getAssets().open(filename)));
@@ -551,7 +540,7 @@ public class OrbotMainActivity extends AppCompatActivity
StringBuilder sb = new StringBuilder();
String mLine = reader.readLine();
while (mLine != null) {
- sb.append(mLine + '\n'); // process line
+ sb.append(mLine).append('\n'); // process line
mLine = reader.readLine();
}
reader.close();
@@ -575,19 +564,16 @@ public class OrbotMainActivity extends AppCompatActivity
finish();
}
- protected void onPause() {
- try
- {
- super.onPause();
-
- if (aDialog != null)
- aDialog.dismiss();
- }
- catch (IllegalStateException ise)
- {
- //can happen on exit/shutdown
- }
- }
+ protected void onPause() {
+ try {
+ super.onPause();
+
+ if (aDialog != null)
+ aDialog.dismiss();
+ } catch (IllegalStateException ise) {
+ //can happen on exit/shutdown
+ }
+ }
@Override
@@ -595,20 +581,17 @@ public class OrbotMainActivity extends AppCompatActivity
// check to see if the log is open, if so close it
if (mDrawer.isDrawerOpen(LOG_DRAWER_GRAVITY)) {
mDrawer.closeDrawers();
- }
- else {
+ } else {
super.onBackPressed();
}
}
- private void refreshVPNApps ()
- {
+ private void refreshVPNApps() {
TorVpnService.stop(this);
startActivity(new Intent(OrbotMainActivity.this, VPNEnableActivity.class));
}
- private void enableVPN (boolean enable)
- {
+ private void enableVPN(boolean enable) {
Prefs.putUseVpn(enable);
if (enable) {
@@ -623,7 +606,7 @@ public class OrbotMainActivity extends AppCompatActivity
String hsName, final int hsPort, int hsRemotePort,
final String backupToPackage, final Uri hsKeyPath,
final Boolean authCookie
- ) throws RemoteException, InterruptedException {
+ ) {
String onionHostname = null;
@@ -682,7 +665,6 @@ public class OrbotMainActivity extends AppCompatActivity
try {
Thread.sleep(3000); //wait three seconds
} catch (Exception e) {
- // TODO Auto-generated catch block
e.printStackTrace();
}
@@ -698,7 +680,7 @@ public class OrbotMainActivity extends AppCompatActivity
onion.moveToNext();
hostname = onion.getString(onion.getColumnIndex(HSContentProvider.HiddenService.DOMAIN));
- if(hostname == null || hostname.length() < 1)
+ if (hostname == null || hostname.length() < 1)
continue;
nResult.putExtra("hs_host", hostname);
@@ -765,28 +747,17 @@ public class OrbotMainActivity extends AppCompatActivity
DialogInterface.OnClickListener dialogClickListener = new DialogInterface.OnClickListener() {
public void onClick(DialogInterface dialog, int which) {
- switch (which) {
- case DialogInterface.BUTTON_POSITIVE:
- try {
- enableHiddenServicePort(
- hiddenServiceName, hiddenServicePort,
- hiddenServiceRemotePort, backupToPackage,
- mKeyUri, authCookie
- );
- } catch (RemoteException e) {
- // TODO Auto-generated catch block
- e.printStackTrace();
- } catch (InterruptedException e) {
- // TODO Auto-generated catch block
- e.printStackTrace();
- }
-
- break;
+ if (which == DialogInterface.BUTTON_POSITIVE) {
+ enableHiddenServicePort(
+ hiddenServiceName, hiddenServicePort,
+ hiddenServiceRemotePort, backupToPackage,
+ mKeyUri, authCookie
+ );
}
}
};
- String requestMsg = getString(R.string.hidden_service_request, hiddenServicePort);
+ String requestMsg = getString(R.string.hidden_service_request, String.valueOf(hiddenServicePort));
AlertDialog.Builder builder = new AlertDialog.Builder(this);
builder.setMessage(requestMsg).setPositiveButton("Allow", dialogClickListener)
.setNegativeButton("Deny", dialogClickListener).show();
@@ -803,11 +774,13 @@ public class OrbotMainActivity extends AppCompatActivity
if (urlString != null) {
- if (urlString.toLowerCase().startsWith("bridge://"))
-
- {
+ if (urlString.toLowerCase().startsWith("bridge://")) {
String newBridgeValue = urlString.substring(9); //remove the bridge protocol piece
- newBridgeValue = URLDecoder.decode(newBridgeValue); //decode the value here
+ try {
+ newBridgeValue = URLDecoder.decode(newBridgeValue, "UTF-8"); //decode the value here
+ } catch (UnsupportedEncodingException e) {
+ // This cannot happen, UTF-8 is supported since Android 1.
+ }
showAlert(getString(R.string.bridges_updated), getString(R.string.restart_orbot_to_use_this_bridge_) + newBridgeValue, false);
@@ -835,58 +808,55 @@ public class OrbotMainActivity extends AppCompatActivity
enableBridges(true);
}
- /*
- * Launch the system activity for Uri viewing with the provided url
- */
- private void openBrowser(final String browserLaunchUrl,boolean forceExternal, String pkgId) {
- if (pkgId != null) {
- startIntent(pkgId,Intent.ACTION_VIEW,Uri.parse(browserLaunchUrl));
+ /*
+ * Launch the system activity for Uri viewing with the provided url
+ */
+ @SuppressWarnings("SameParameterValue")
+ private void openBrowser(final String browserLaunchUrl, boolean forceExternal, String pkgId) {
+ if (pkgId != null) {
+ startIntent(pkgId, Intent.ACTION_VIEW, Uri.parse(browserLaunchUrl));
+ } else if (mBtnVPN.isChecked() || forceExternal) {
+ //use the system browser since VPN is on
+ startIntent(null, Intent.ACTION_VIEW, Uri.parse(browserLaunchUrl));
}
- else if (mBtnVPN.isChecked()||forceExternal) {
- //use the system browser since VPN is on
- startIntent(null,Intent.ACTION_VIEW, Uri.parse(browserLaunchUrl));
- }
- }
-
- private void startIntent (String pkg, String action, Uri data)
- {
+ }
+
+ @SuppressWarnings("SameParameterValue")
+ private void startIntent(String pkg, String action, Uri data) {
Intent i;
- PackageManager pm = getPackageManager();
+ PackageManager pm = getPackageManager();
try {
- if (pkg != null) {
- i = pm.getLaunchIntentForPackage(pkg);
- if (i == null)
- throw new PackageManager.NameNotFoundException();
- }
- else
- {
- i = new Intent();
- }
+ if (pkg != null) {
+ i = pm.getLaunchIntentForPackage(pkg);
+ if (i == null)
+ throw new PackageManager.NameNotFoundException();
+ } else {
+ i = new Intent();
+ }
i.setAction(action);
i.setData(data);
- if (i.resolveActivity(pm)!=null)
- startActivity(i);
+ if (i.resolveActivity(pm) != null)
+ startActivity(i);
} catch (PackageManager.NameNotFoundException e) {
-
+ // Should not occur. Ignore.
}
}
-
+
@Override
protected void onActivityResult(int request, int response, Intent data) {
super.onActivityResult(request, response, data);
- if (request == REQUEST_SETTINGS && response == RESULT_OK)
- {
+ if (request == REQUEST_SETTINGS && response == RESULT_OK) {
if (data != null && (!TextUtils.isEmpty(data.getStringExtra("locale")))) {
String newLocale = data.getStringExtra("locale");
Prefs.setDefaultLocale(newLocale);
Languages.setLanguage(this, newLocale, true);
- // Language.setFromPreference(this, "pref_default_locale");
+ // Language.setFromPreference(this, "pref_default_locale");
finish();
@@ -895,106 +865,88 @@ public class OrbotMainActivity extends AppCompatActivity
@Override
public void run() {
//Do something after 100ms
- startActivity(new Intent(OrbotMainActivity.this,OrbotMainActivity.class));
+ startActivity(new Intent(OrbotMainActivity.this, OrbotMainActivity.class));
}
}, 1000);
}
- }
- else if (request == REQUEST_VPN)
- {
- if (response == RESULT_OK) {
+ } else if (request == REQUEST_VPN) {
+ if (response == RESULT_OK) {
TorVpnService.start(this);
+ } else if (response == VPNEnableActivity.ACTIVITY_RESULT_VPN_DENIED) {
+ mBtnVPN.setChecked(false);
+ Prefs.putUseVpn(false);
}
- else if (response == VPNEnableActivity.ACTIVITY_RESULT_VPN_DENIED)
- {
- mBtnVPN.setChecked(false);
- Prefs.putUseVpn(false);
- }
- }
- else if (request == REQUEST_VPN_APPS_SELECT)
- {
+ } else if (request == REQUEST_VPN_APPS_SELECT) {
if (response == RESULT_OK &&
- torStatus == TorServiceConstants.STATUS_ON)
+ torStatus.equals(TorServiceConstants.STATUS_ON))
refreshVPNApps();
}
-
+
IntentResult scanResult = IntentIntegrator.parseActivityResult(request, response, data);
if (scanResult != null) {
- // handle scan result
-
- String results = scanResult.getContents();
-
- if (results != null && results.length() > 0)
- {
- try {
-
- int urlIdx = results.indexOf("://");
-
- if (urlIdx!=-1)
- {
- results = URLDecoder.decode(results, "UTF-8");
- results = results.substring(urlIdx+3);
-
- showAlert(getString(R.string.bridges_updated),getString(R.string.restart_orbot_to_use_this_bridge_) + results,false);
-
- setNewBridges(results);
- }
- else
- {
- JSONArray bridgeJson = new JSONArray(results);
- StringBuffer bridgeLines = new StringBuffer();
-
- for (int i = 0; i < bridgeJson.length(); i++)
- {
- String bridgeLine = bridgeJson.getString(i);
- bridgeLines.append(bridgeLine).append("\n");
- }
-
- setNewBridges(bridgeLines.toString());
- }
-
-
- } catch (Exception e) {
- Log.e(TAG,"unsupported",e);
- }
- }
-
- }
-
+ // handle scan result
+
+ String results = scanResult.getContents();
+
+ if (results != null && results.length() > 0) {
+ try {
+
+ int urlIdx = results.indexOf("://");
+
+ if (urlIdx != -1) {
+ results = URLDecoder.decode(results, "UTF-8");
+ results = results.substring(urlIdx + 3);
+
+ showAlert(getString(R.string.bridges_updated), getString(R.string.restart_orbot_to_use_this_bridge_) + results, false);
+
+ setNewBridges(results);
+ } else {
+ JSONArray bridgeJson = new JSONArray(results);
+ StringBuilder bridgeLines = new StringBuilder();
+
+ for (int i = 0; i < bridgeJson.length(); i++) {
+ String bridgeLine = bridgeJson.getString(i);
+ bridgeLines.append(bridgeLine).append("\n");
+ }
+
+ setNewBridges(bridgeLines.toString());
+ }
+
+
+ } catch (Exception e) {
+ Log.e(TAG, "unsupported", e);
+ }
+ }
+
+ }
+
}
-
- public void promptSetupBridges ()
- {
- if (mBtnBridges.isChecked())
- {
+ public void promptSetupBridges() {
+
+ if (mBtnBridges.isChecked()) {
Prefs.putBridgesEnabled(true);
startActivity(new Intent(this, BridgeWizardActivity.class));
+ } else {
+ enableBridges(false);
}
- else
- {
- enableBridges(false);
- }
-
+
}
-
-
- private void enableBridges (boolean enable)
- {
- Prefs.putBridgesEnabled(enable);
-
- if (torStatus == TorServiceConstants.STATUS_ON)
- {
- String bridgeList = Prefs.getBridgesList();
- if (bridgeList != null && bridgeList.length() > 0)
- {
- requestTorRereadConfig ();
- }
- }
+
+
+ private void enableBridges(boolean enable) {
+ Prefs.putBridgesEnabled(enable);
+
+ if (torStatus.equals(TorServiceConstants.STATUS_ON)) {
+ String bridgeList = Prefs.getBridgesList();
+ if (bridgeList != null && bridgeList.length() > 0) {
+ requestTorRereadConfig();
+ }
+ }
}
private void requestTorRereadConfig() {
@@ -1010,54 +962,51 @@ public class OrbotMainActivity extends AppCompatActivity
setCountrySpinner();
- requestTorStatus();
+ requestTorStatus();
- if (torStatus == null)
- updateStatus("", TorServiceConstants.STATUS_STOPPING);
+ if (torStatus == null)
+ updateStatus("", TorServiceConstants.STATUS_STOPPING);
else
updateStatus(null, torStatus);
- addAppShortcuts();
+ addAppShortcuts();
- //now you can handle the intents properly
- handleIntents();
+ //now you can handle the intents properly
+ handleIntents();
- }
+ }
AlertDialog aDialog = null;
-
+
//general alert dialog for mostly Tor warning messages
//sometimes this can go haywire or crazy with too many error
//messages from Tor, and the user cannot stop or exit Orbot
//so need to ensure repeated error messages are not spamming this method
- private void showAlert(String title, String msg, boolean button)
- {
- try
- {
- if (aDialog != null && aDialog.isShowing())
- aDialog.dismiss();
- }
- catch (Exception e){} //swallow any errors
-
- if (button)
- {
- aDialog = new AlertDialog.Builder(OrbotMainActivity.this)
- .setIcon(R.drawable.onion32)
- .setTitle(title)
- .setMessage(msg)
- .setPositiveButton(R.string.btn_okay, null)
- .show();
- }
- else
- {
- aDialog = new AlertDialog.Builder(OrbotMainActivity.this)
- .setIcon(R.drawable.onion32)
- .setTitle(title)
- .setMessage(msg)
- .show();
- }
-
- aDialog.setCanceledOnTouchOutside(true);
+ @SuppressWarnings("SameParameterValue")
+ private void showAlert(String title, String msg, boolean button) {
+ try {
+ if (aDialog != null && aDialog.isShowing())
+ aDialog.dismiss();
+ } catch (Exception e) {
+ //swallow any errors
+ }
+
+ if (button) {
+ aDialog = new AlertDialog.Builder(OrbotMainActivity.this)
+ .setIcon(R.drawable.onion32)
+ .setTitle(title)
+ .setMessage(msg)
+ .setPositiveButton(R.string.btn_okay, null)
+ .show();
+ } else {
+ aDialog = new AlertDialog.Builder(OrbotMainActivity.this)
+ .setIcon(R.drawable.onion32)
+ .setTitle(title)
+ .setMessage(msg)
+ .show();
+ }
+
+ aDialog.setCanceledOnTouchOutside(true);
}
/**
@@ -1066,85 +1015,91 @@ public class OrbotMainActivity extends AppCompatActivity
*/
private synchronized void updateStatus(String torServiceMsg, String newTorStatus) {
- if (!TextUtils.isEmpty(torServiceMsg))
- {
+ if (!TextUtils.isEmpty(torServiceMsg)) {
if (torServiceMsg.contains(TorServiceConstants.LOG_NOTICE_HEADER)) {
lblStatus.setText(torServiceMsg);
}
mTxtOrbotLog.append(torServiceMsg + '\n');
-
}
if (torStatus == null || (newTorStatus != null && newTorStatus.equals(torStatus))) {
torStatus = newTorStatus;
return;
}
- else
- torStatus = newTorStatus;
+ else {
+ torStatus = newTorStatus;
+ }
- if (torStatus == TorServiceConstants.STATUS_ON) {
-
- imgStatus.setImageResource(R.drawable.toron);
+ if (torStatus == null) {
+ return;
+ }
- mBtnStart.setText(R.string.menu_stop);
- mPulsator.stop();
+ switch (torStatus) {
+ case TorServiceConstants.STATUS_ON:
- lblStatus.setText(getString(R.string.status_activated));
+ imgStatus.setImageResource(R.drawable.toron);
- if (autoStartFromIntent)
- {
- autoStartFromIntent = false;
- Intent resultIntent = lastStatusIntent;
+ mBtnStart.setText(R.string.menu_stop);
+ mPulsator.stop();
- if (resultIntent == null)
- resultIntent = new Intent(TorServiceConstants.ACTION_START);
+ lblStatus.setText(getString(R.string.status_activated));
- resultIntent.putExtra(
- TorServiceConstants.EXTRA_STATUS,
- torStatus == null?TorServiceConstants.STATUS_OFF:torStatus
- );
+ if (autoStartFromIntent) {
+ autoStartFromIntent = false;
+ Intent resultIntent = lastStatusIntent;
- setResult(RESULT_OK, resultIntent);
+ if (resultIntent == null)
+ resultIntent = new Intent(TorServiceConstants.ACTION_START);
- finish();
- Log.d(TAG, "autoStartFromIntent finish");
- }
-
-
+ resultIntent.putExtra(
+ TorServiceConstants.EXTRA_STATUS,
+ torStatus == null ? TorServiceConstants.STATUS_OFF : torStatus
+ );
- } else if (torStatus == TorServiceConstants.STATUS_STARTING) {
+ setResult(RESULT_OK, resultIntent);
- imgStatus.setImageResource(R.drawable.torstarting);
+ finish();
+ Log.d(TAG, "autoStartFromIntent finish");
+ }
- if (torServiceMsg != null)
- {
- if (torServiceMsg.contains(TorServiceConstants.LOG_NOTICE_BOOTSTRAPPED))
- lblStatus.setText(torServiceMsg);
- }
- else
- lblStatus.setText(getString(R.string.status_starting_up));
+ break;
- mBtnStart.setText("...");
+ case TorServiceConstants.STATUS_STARTING:
- } else if (torStatus == TorServiceConstants.STATUS_STOPPING) {
+ imgStatus.setImageResource(R.drawable.torstarting);
- if (torServiceMsg != null && torServiceMsg.contains(TorServiceConstants.LOG_NOTICE_HEADER))
- lblStatus.setText(torServiceMsg);
-
- imgStatus.setImageResource(R.drawable.torstarting);
- lblStatus.setText(torServiceMsg);
+ if (torServiceMsg != null) {
+ if (torServiceMsg.contains(TorServiceConstants.LOG_NOTICE_BOOTSTRAPPED))
+ lblStatus.setText(torServiceMsg);
+ }
+ else {
+ lblStatus.setText(getString(R.string.status_starting_up));
+ }
- } else if (torStatus == TorServiceConstants.STATUS_OFF) {
+ mBtnStart.setText("...");
- imgStatus.setImageResource(R.drawable.toroff);
- lblStatus.setText("Tor v" + OrbotService.BINARY_TOR_VERSION);
- mBtnStart.setText(R.string.menu_start);
- mPulsator.start();
+ break;
- }
+ case TorServiceConstants.STATUS_STOPPING:
+
+ if (torServiceMsg != null && torServiceMsg.contains(TorServiceConstants.LOG_NOTICE_HEADER))
+ lblStatus.setText(torServiceMsg);
+ imgStatus.setImageResource(R.drawable.torstarting);
+ lblStatus.setText(torServiceMsg);
+
+ break;
+ case TorServiceConstants.STATUS_OFF:
+
+ imgStatus.setImageResource(R.drawable.toroff);
+ lblStatus.setText(String.format("Tor v%s", OrbotService.BINARY_TOR_VERSION));
+ mBtnStart.setText(R.string.menu_start);
+ mPulsator.start();
+
+ break;
+ }
}
/**
@@ -1156,7 +1111,7 @@ public class OrbotMainActivity extends AppCompatActivity
sendIntentToService(TorServiceConstants.ACTION_START);
mTxtOrbotLog.setText("");
}
-
+
/**
* Request tor status without starting it
* {@link TorServiceConstants#ACTION_START} {@link Intent} to
@@ -1168,30 +1123,34 @@ public class OrbotMainActivity extends AppCompatActivity
private boolean isTorServiceRunning() {
ActivityManager manager = (ActivityManager) getSystemService(Context.ACTIVITY_SERVICE);
- for (RunningServiceInfo service : manager.getRunningServices(Integer.MAX_VALUE)) {
- if (OrbotService.class.getName().equals(service.service.getClassName())) {
- return true;
+
+ if (manager != null) {
+ for (RunningServiceInfo service : manager.getRunningServices(Integer.MAX_VALUE)) {
+ if (OrbotService.class.getName().equals(service.service.getClassName())) {
+ return true;
+ }
}
}
+
return false;
}
public boolean onLongClick(View view) {
- if (torStatus == TorServiceConstants.STATUS_OFF) {
+ if (torStatus.equals(TorServiceConstants.STATUS_OFF)) {
lblStatus.setText(getString(R.string.status_starting_up));
startTor();
} else {
- lblStatus.setText(getString(R.string.status_shutting_down));
-
+ lblStatus.setText(getString(R.string.status_shutting_down));
+
stopTor();
}
-
+
return true;
-
+
}
-// this is what takes messages or values from the callback threads or other non-mainUI threads
+ // this is what takes messages or values from the callback threads or other non-mainUI threads
//and passes them back into the main UI thread for display to the user
private Handler mStatusUpdateHandler = new Handler() {
@@ -1204,13 +1163,13 @@ public class OrbotMainActivity extends AppCompatActivity
switch (msg.what) {
case MESSAGE_TRAFFIC_COUNT:
- DataCount datacount = new DataCount(data.getLong("upload"),data.getLong("download"));
-
+ DataCount datacount = new DataCount(data.getLong("upload"), data.getLong("download"));
+
long totalRead = data.getLong("readTotal");
long totalWrite = data.getLong("writeTotal");
-
- downloadText.setText(formatCount(datacount.Download) + " / " + formatTotal(totalRead));
- uploadText.setText(formatCount(datacount.Upload) + " / " + formatTotal(totalWrite));
+
+ downloadText.setText(String.format("%s / %s", formatCount(datacount.Download), formatTotal(totalRead)));
+ uploadText.setText(String.format("%s / %s", formatCount(datacount.Upload), formatTotal(totalWrite)));
break;
case MESSAGE_PORTS:
@@ -1218,20 +1177,19 @@ public class OrbotMainActivity extends AppCompatActivity
int socksPort = data.getInt("socks");
int httpPort = data.getInt("http");
- lblPorts.setText("SOCKS: " + socksPort + " | HTTP: " + httpPort);
+ lblPorts.setText(String.format(Locale.getDefault(), "SOCKS: %d | HTTP: %d", socksPort, httpPort));
break;
default:
String newTorStatus = msg.getData().getString("status");
- String log = (String)msg.obj;
+ String log = (String) msg.obj;
if (torStatus == null && newTorStatus != null) //first time status
{
findViewById(R.id.frameMain).setVisibility(View.VISIBLE);
updateStatus(log, newTorStatus);
- }
- else
+ } else
updateStatus(log, newTorStatus);
super.handleMessage(msg);
break;
@@ -1242,22 +1200,22 @@ public class OrbotMainActivity extends AppCompatActivity
@Override
protected void onDestroy() {
super.onDestroy();
- LocalBroadcastManager.getInstance(this).unregisterReceiver(mLocalBroadcastReceiver);
+ LocalBroadcastManager.getInstance(this).unregisterReceiver(mLocalBroadcastReceiver);
+
+ }
+
+ public static class DataCount {
+ // data uploaded
+ long Upload;
+ // data downloaded
+ long Download;
+ DataCount(long Upload, long Download) {
+ this.Upload = Upload;
+ this.Download = Download;
+ }
}
- public class DataCount {
- // data uploaded
- public long Upload;
- // data downloaded
- public long Download;
-
- DataCount(long Upload, long Download){
- this.Upload = Upload;
- this.Download = Download;
- }
- }
-
private String formatCount(long count) {
NumberFormat numberFormat = NumberFormat.getInstance(Locale.getDefault());
// Converts the supplied argument into a string.
@@ -1287,16 +1245,15 @@ public class OrbotMainActivity extends AppCompatActivity
}
private static final float ROTATE_FROM = 0.0f;
- private static final float ROTATE_TO = 360.0f*4f;// 3.141592654f * 32.0f;
+ private static final float ROTATE_TO = 360.0f * 4f;// 3.141592654f * 32.0f;
- private void requestNewTorIdentity ()
- {
- sendIntentToService (TorServiceConstants.CMD_NEWNYM);
+ private void requestNewTorIdentity() {
+ sendIntentToService(TorServiceConstants.CMD_NEWNYM);
- Rotate3dAnimation rotation = new Rotate3dAnimation(ROTATE_FROM, ROTATE_TO, imgStatus.getWidth()/2f,imgStatus.getWidth()/2f,20f,false);
+ Rotate3dAnimation rotation = new Rotate3dAnimation(ROTATE_FROM, ROTATE_TO, imgStatus.getWidth() / 2f, imgStatus.getWidth() / 2f, 20f, false);
rotation.setFillAfter(true);
rotation.setInterpolator(new AccelerateInterpolator());
- rotation.setDuration((long) 2*1000);
+ rotation.setDuration((long) 2 * 1000);
rotation.setRepeatCount(0);
imgStatus.startAnimation(rotation);
lblStatus.setText(getString(R.string.newnym));
@@ -1353,9 +1310,7 @@ public class OrbotMainActivity extends AppCompatActivity
addFullDeviceVpnView(llBoxShortcuts);
}
}
- }
- else
- {
+ } else {
TextView tv = new TextView(this);
LinearLayout.LayoutParams params = new LinearLayout.LayoutParams(LinearLayout.LayoutParams.WRAP_CONTENT, LinearLayout.LayoutParams.WRAP_CONTENT);
params.setMargins(12, 3, 3, 3);
1
0
commit 3eb76e6f05edfbf0bf129616dfc55bf7c5af8c39
Author: Benjamin Erhart <berhart(a)netzarchitekten.com>
Date: Thu Apr 16 17:23:20 2020 +0200
Updated Gradle.
---
build.gradle | 2 +-
gradle/wrapper/gradle-wrapper.properties | 4 ++--
2 files changed, 3 insertions(+), 3 deletions(-)
diff --git a/build.gradle b/build.gradle
index c14d6885..fd955c96 100644
--- a/build.gradle
+++ b/build.gradle
@@ -5,7 +5,7 @@ buildscript {
google()
}
dependencies {
- classpath 'com.android.tools.build:gradle:3.5.3'
+ classpath 'com.android.tools.build:gradle:3.6.2'
}
}
diff --git a/gradle/wrapper/gradle-wrapper.properties b/gradle/wrapper/gradle-wrapper.properties
index 9dfc5f7e..8b62e5ba 100644
--- a/gradle/wrapper/gradle-wrapper.properties
+++ b/gradle/wrapper/gradle-wrapper.properties
@@ -1,6 +1,6 @@
-#Fri Mar 22 11:47:03 EDT 2019
+#Thu Apr 16 16:59:02 CEST 2020
distributionBase=GRADLE_USER_HOME
distributionPath=wrapper/dists
zipStoreBase=GRADLE_USER_HOME
zipStorePath=wrapper/dists
-distributionUrl=https\://services.gradle.org/distributions/gradle-5.5-all.zip
+distributionUrl=https\://services.gradle.org/distributions/gradle-5.6.4-all.zip
1
0
commit a46e463bcbfde1f6d3bbfc4bf8ec9c0ac0a8de2a
Author: Benjamin Erhart <berhart(a)netzarchitekten.com>
Date: Wed Apr 22 09:19:29 2020 +0200
Updated Gradle to latest version.
---
build.gradle | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/build.gradle b/build.gradle
index fd955c96..b8ebab92 100644
--- a/build.gradle
+++ b/build.gradle
@@ -5,7 +5,7 @@ buildscript {
google()
}
dependencies {
- classpath 'com.android.tools.build:gradle:3.6.2'
+ classpath 'com.android.tools.build:gradle:3.6.3'
}
}
1
0

28 Apr '20
commit 5c99859e0398830f9e8f28eda553d987e56d83ab
Author: Benjamin Erhart <berhart(a)netzarchitekten.com>
Date: Wed Apr 22 11:47:11 2020 +0200
Finish BridgeWizardActivity on successful MOAT.
---
.../android/ui/onboarding/BridgeWizardActivity.java | 18 ++++++++++++++++--
.../torproject/android/ui/onboarding/MoatActivity.java | 1 +
2 files changed, 17 insertions(+), 2 deletions(-)
diff --git a/app/src/main/java/org/torproject/android/ui/onboarding/BridgeWizardActivity.java b/app/src/main/java/org/torproject/android/ui/onboarding/BridgeWizardActivity.java
index 5ffe79e5..21b4f4e5 100644
--- a/app/src/main/java/org/torproject/android/ui/onboarding/BridgeWizardActivity.java
+++ b/app/src/main/java/org/torproject/android/ui/onboarding/BridgeWizardActivity.java
@@ -14,6 +14,7 @@ import android.view.View;
import android.widget.RadioButton;
import android.widget.TextView;
+import androidx.annotation.Nullable;
import androidx.appcompat.app.ActionBar;
import androidx.appcompat.app.AppCompatActivity;
import androidx.appcompat.widget.Toolbar;
@@ -31,6 +32,8 @@ import static org.torproject.android.MainConstants.URL_TOR_BRIDGES;
public class BridgeWizardActivity extends AppCompatActivity {
+ private static int MOAT_REQUEST_CODE = 666;
+
private TextView tvStatus;
@Override
@@ -94,7 +97,8 @@ public class BridgeWizardActivity extends AppCompatActivity {
btnMoat.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
- startActivity(new Intent(BridgeWizardActivity.this, MoatActivity.class));
+ startActivityForResult(new Intent(BridgeWizardActivity.this, MoatActivity.class),
+ MOAT_REQUEST_CODE);
}
});
@@ -104,7 +108,6 @@ public class BridgeWizardActivity extends AppCompatActivity {
btnMeek.setChecked(true);
else if (Prefs.getBridgesList().equals("obfs4"))
btnObfs4.setChecked(true);
-
}
@Override
@@ -122,6 +125,17 @@ public class BridgeWizardActivity extends AppCompatActivity {
return super.onOptionsItemSelected(item);
}
+ @Override
+ protected void onActivityResult(int requestCode, int resultCode, @Nullable Intent data) {
+ // If the MoatActivity could successfully gather OBFS4 bridges,
+ // the job is done and we can return immediately.
+ if (requestCode == MOAT_REQUEST_CODE && resultCode == RESULT_OK) {
+ finish();
+ }
+ else {
+ super.onActivityResult(requestCode, resultCode, data);
+ }
+ }
private void showGetBridgePrompt() {
new AlertDialog.Builder(this)
diff --git a/app/src/main/java/org/torproject/android/ui/onboarding/MoatActivity.java b/app/src/main/java/org/torproject/android/ui/onboarding/MoatActivity.java
index 0b99477f..464b3bd4 100644
--- a/app/src/main/java/org/torproject/android/ui/onboarding/MoatActivity.java
+++ b/app/src/main/java/org/torproject/android/ui/onboarding/MoatActivity.java
@@ -259,6 +259,7 @@ public class MoatActivity extends AppCompatActivity implements View.OnClickListe
mProgressBar.setVisibility(View.GONE);
+ MoatActivity.this.setResult(RESULT_OK);
MoatActivity.this.finish();
}
catch (JSONException e) {
1
0

[orbot/master] Fixed MoatActivity startup when Tor is not running. Reset old bridge configuration, when not completed.
by n8fr8@torproject.org 28 Apr '20
by n8fr8@torproject.org 28 Apr '20
28 Apr '20
commit 964c3115a9eeba7a9d26091ffb49441872b491eb
Author: Benjamin Erhart <berhart(a)netzarchitekten.com>
Date: Wed Apr 22 12:23:18 2020 +0200
Fixed MoatActivity startup when Tor is not running. Reset old bridge configuration, when not completed.
---
.../ui/onboarding/BridgeWizardActivity.java | 79 +++++++++++++++-------
.../android/ui/onboarding/MoatActivity.java | 42 ++++++++++--
2 files changed, 89 insertions(+), 32 deletions(-)
diff --git a/app/src/main/java/org/torproject/android/ui/onboarding/BridgeWizardActivity.java b/app/src/main/java/org/torproject/android/ui/onboarding/BridgeWizardActivity.java
index 21b4f4e5..6b439468 100644
--- a/app/src/main/java/org/torproject/android/ui/onboarding/BridgeWizardActivity.java
+++ b/app/src/main/java/org/torproject/android/ui/onboarding/BridgeWizardActivity.java
@@ -34,7 +34,13 @@ public class BridgeWizardActivity extends AppCompatActivity {
private static int MOAT_REQUEST_CODE = 666;
- private TextView tvStatus;
+ private TextView mTvStatus;
+ private RadioButton mBtDirect;
+ private RadioButton mBtObfs4;
+ private RadioButton mBtMeek;
+ private RadioButton mBtNew;
+ private RadioButton mBtMoat;
+
@Override
protected void onCreate(Bundle savedInstanceState) {
@@ -48,13 +54,13 @@ public class BridgeWizardActivity extends AppCompatActivity {
actionBar.setDisplayHomeAsUpEnabled(true);
}
- tvStatus = findViewById(R.id.lbl_bridge_test_status);
- tvStatus.setVisibility(View.GONE);
+ mTvStatus = findViewById(R.id.lbl_bridge_test_status);
+ mTvStatus.setVisibility(View.GONE);
setTitle(getString(R.string.bridges));
- RadioButton btnDirect = findViewById(R.id.btnBridgesDirect);
- btnDirect.setOnClickListener(new View.OnClickListener() {
+ mBtDirect = findViewById(R.id.btnBridgesDirect);
+ mBtDirect.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Prefs.setBridgesList("");
@@ -63,8 +69,8 @@ public class BridgeWizardActivity extends AppCompatActivity {
}
});
- RadioButton btnObfs4 = findViewById(R.id.btnBridgesObfs4);
- btnObfs4.setOnClickListener(new View.OnClickListener() {
+ mBtObfs4 = findViewById(R.id.btnBridgesObfs4);
+ mBtObfs4.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Prefs.setBridgesList("obfs4");
@@ -74,8 +80,8 @@ public class BridgeWizardActivity extends AppCompatActivity {
});
- RadioButton btnMeek = findViewById(R.id.btnBridgesMeek);
- btnMeek.setOnClickListener(new View.OnClickListener() {
+ mBtMeek = findViewById(R.id.btnBridgesMeek);
+ mBtMeek.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Prefs.setBridgesList("meek");
@@ -85,16 +91,16 @@ public class BridgeWizardActivity extends AppCompatActivity {
});
- RadioButton btnNew = findViewById(R.id.btnBridgesNew);
- btnNew.setOnClickListener(new View.OnClickListener() {
+ mBtNew = findViewById(R.id.btnBridgesNew);
+ mBtNew.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
showGetBridgePrompt();
}
});
- RadioButton btnMoat = findViewById(R.id.btnMoat);
- btnMoat.setOnClickListener(new View.OnClickListener() {
+ mBtMoat = findViewById(R.id.btnMoat);
+ mBtMoat.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
startActivityForResult(new Intent(BridgeWizardActivity.this, MoatActivity.class),
@@ -102,12 +108,7 @@ public class BridgeWizardActivity extends AppCompatActivity {
}
});
- if (!Prefs.bridgesEnabled())
- btnDirect.setChecked(true);
- else if (Prefs.getBridgesList().equals("meek"))
- btnMeek.setChecked(true);
- else if (Prefs.getBridgesList().equals("obfs4"))
- btnObfs4.setChecked(true);
+ evaluateBridgeListState();
}
@Override
@@ -129,8 +130,14 @@ public class BridgeWizardActivity extends AppCompatActivity {
protected void onActivityResult(int requestCode, int resultCode, @Nullable Intent data) {
// If the MoatActivity could successfully gather OBFS4 bridges,
// the job is done and we can return immediately.
- if (requestCode == MOAT_REQUEST_CODE && resultCode == RESULT_OK) {
- finish();
+ if (requestCode == MOAT_REQUEST_CODE) {
+ if (resultCode == RESULT_OK) {
+ finish();
+ }
+ // Reset selection to actual value.
+ else {
+ evaluateBridgeListState();
+ }
}
else {
super.onActivityResult(requestCode, resultCode, data);
@@ -189,7 +196,7 @@ public class BridgeWizardActivity extends AppCompatActivity {
} else if (Prefs.getBridgesList().equals("obfs4")) {
new HostTester().execute("85.17.30.79", "443", "154.35.22.9", "443", "192.99.11.54", "443");
} else {
- tvStatus.setText("");
+ mTvStatus.setText("");
}
}
@@ -197,8 +204,8 @@ public class BridgeWizardActivity extends AppCompatActivity {
@Override
protected void onPreExecute() {
// Pre Code
- tvStatus.setVisibility(View.VISIBLE);
- tvStatus.setText(R.string.testing_bridges);
+ mTvStatus.setVisibility(View.VISIBLE);
+ mTvStatus.setText(R.string.testing_bridges);
}
@Override
@@ -221,10 +228,10 @@ public class BridgeWizardActivity extends AppCompatActivity {
protected void onPostExecute(Boolean result) {
// Post Code
if (result) {
- tvStatus.setText(R.string.testing_bridges_success);
+ mTvStatus.setText(R.string.testing_bridges_success);
} else {
- tvStatus.setText(R.string.testing_bridges_fail);
+ mTvStatus.setText(R.string.testing_bridges_fail);
}
}
@@ -249,4 +256,24 @@ public class BridgeWizardActivity extends AppCompatActivity {
return connected;
}
+
+ private void evaluateBridgeListState() {
+ if (!Prefs.bridgesEnabled()) {
+ mBtDirect.setChecked(true);
+ }
+ else if (Prefs.getBridgesList().equals("meek")) {
+ mBtMeek.setChecked(true);
+ }
+ else if (Prefs.getBridgesList().equals("obfs4")) {
+ mBtObfs4.setChecked(true);
+ }
+ else {
+ mBtDirect.setChecked(false);
+ mBtMeek.setChecked(false);
+ mBtObfs4.setChecked(false);
+ }
+
+ mBtNew.setChecked(false);
+ mBtMoat.setChecked(false);
+ }
}
diff --git a/app/src/main/java/org/torproject/android/ui/onboarding/MoatActivity.java b/app/src/main/java/org/torproject/android/ui/onboarding/MoatActivity.java
index 464b3bd4..71d97715 100644
--- a/app/src/main/java/org/torproject/android/ui/onboarding/MoatActivity.java
+++ b/app/src/main/java/org/torproject/android/ui/onboarding/MoatActivity.java
@@ -30,6 +30,7 @@ import androidx.appcompat.app.AppCompatActivity;
import androidx.appcompat.widget.Toolbar;
import androidx.localbroadcastmanager.content.LocalBroadcastManager;
+import com.android.volley.DefaultRetryPolicy;
import com.android.volley.Request;
import com.android.volley.RequestQueue;
import com.android.volley.Response;
@@ -68,6 +69,11 @@ public class MoatActivity extends AppCompatActivity implements View.OnClickListe
private RequestQueue mQueue;
+ private String mOriginalBridges;
+ private boolean mOriginalBridgeStatus;
+
+ private boolean mSuccess;
+
private String mTorStatus;
private BroadcastReceiver mBroadcastReceiver = new BroadcastReceiver() {
@@ -144,6 +150,9 @@ public class MoatActivity extends AppCompatActivity implements View.OnClickListe
protected void onResume() {
super.onResume();
+ mOriginalBridges = Prefs.getBridgesList();
+ mOriginalBridgeStatus = Prefs.bridgesEnabled();
+
sendIntentToService(TorServiceConstants.ACTION_STATUS);
}
@@ -193,6 +202,19 @@ public class MoatActivity extends AppCompatActivity implements View.OnClickListe
}
@Override
+ protected void onPause() {
+ super.onPause();
+
+ if (mSuccess) {
+ setResult(RESULT_OK);
+ }
+ else {
+ Prefs.setBridgesList(mOriginalBridges);
+ Prefs.putBridgesEnabled(mOriginalBridgeStatus);
+ }
+ }
+
+ @Override
protected void onDestroy() {
super.onDestroy();
@@ -259,7 +281,8 @@ public class MoatActivity extends AppCompatActivity implements View.OnClickListe
mProgressBar.setVisibility(View.GONE);
- MoatActivity.this.setResult(RESULT_OK);
+ mSuccess = true;
+
MoatActivity.this.finish();
}
catch (JSONException e) {
@@ -286,7 +309,7 @@ public class MoatActivity extends AppCompatActivity implements View.OnClickListe
Log.d(MoatActivity.class.getSimpleName(), "Request: " + requestBody.toString());
- return new JsonObjectRequest(
+ JsonObjectRequest request = new JsonObjectRequest(
Request.Method.POST,
moatBaseUrl + "/" + endpoint,
requestBody,
@@ -304,6 +327,11 @@ public class MoatActivity extends AppCompatActivity implements View.OnClickListe
return "application/vnd.api+json";
}
};
+
+ request.setRetryPolicy(new DefaultRetryPolicy(30000,
+ 3, DefaultRetryPolicy.DEFAULT_BACKOFF_MULT));
+
+ return request;
}
private void sendIntentToService(final String action) {
@@ -320,12 +348,17 @@ public class MoatActivity extends AppCompatActivity implements View.OnClickListe
switch (status) {
case TorServiceConstants.STATUS_OFF:
+ // We need the Meek bridge.
+ Prefs.setBridgesList("meek");
+ Prefs.putBridgesEnabled(true);
+
sendIntentToService(TorServiceConstants.ACTION_START);
break;
case TorServiceConstants.STATUS_ON:
- Prefs.setBridgesList("moat");
+ // Switch to the Meek bridge, if not done, already.
+ Prefs.setBridgesList("meek");
Prefs.putBridgesEnabled(true);
Log.d(MoatActivity.class.getSimpleName(), "Set up Volley queue. host=" + host + ", port=" + port);
@@ -337,9 +370,6 @@ public class MoatActivity extends AppCompatActivity implements View.OnClickListe
fetchCaptcha();
break;
-
- default:
- sendIntentToService(TorServiceConstants.ACTION_STATUS);
}
}
1
0

[orbot/master] tweaks to app data storage and control port interaction
by n8fr8@torproject.org 28 Apr '20
by n8fr8@torproject.org 28 Apr '20
28 Apr '20
commit 410ae032564e0a57b3df20391b7023085087d628
Author: n8fr8 <nathan(a)guardianproject.info>
Date: Fri Apr 24 16:59:19 2020 -0400
tweaks to app data storage and control port interaction
- in some cases, Orbot connection to local control port can hang. Make changes to address that.
---
.../torproject/android/service/OrbotService.java | 63 +++++++++++-----------
.../android/service/TorEventHandler.java | 4 ++
2 files changed, 37 insertions(+), 30 deletions(-)
diff --git a/orbotservice/src/main/java/org/torproject/android/service/OrbotService.java b/orbotservice/src/main/java/org/torproject/android/service/OrbotService.java
index dbd36dbd..a5731fae 100644
--- a/orbotservice/src/main/java/org/torproject/android/service/OrbotService.java
+++ b/orbotservice/src/main/java/org/torproject/android/service/OrbotService.java
@@ -29,6 +29,7 @@ import android.net.ConnectivityManager;
import android.net.NetworkInfo;
import android.net.Uri;
import android.os.Build;
+import android.os.Debug;
import android.os.IBinder;
import android.os.RemoteException;
import android.provider.BaseColumns;
@@ -462,7 +463,7 @@ public class OrbotService extends Service implements TorServiceConstants, OrbotC
try {
logNotice("sending HALT signal to Tor process");
- conn.shutdownTor("HALT");
+ conn.shutdownTor("SHUTDOWN");
} catch (IOException e) {
Log.d(OrbotConstants.TAG, "error shutting down Tor via connection", e);
@@ -471,25 +472,6 @@ public class OrbotService extends Service implements TorServiceConstants, OrbotC
conn = null;
}
- /**
- if (mLastProcessId != -1)
- killProcess(mLastProcessId + "", "-9");
-
- if (filePid != null && filePid.exists())
- {
- List<String> lines = IOUtils.readLines(new FileReader(filePid));
- String torPid = lines.get(0);
- killProcess(torPid,"-9");
-
- }
-
-
- // if that fails, try again using native utils
- try {
- killProcess(fileTor, "-9"); // this is -HUP
- } catch (Exception e) {
- e.printStackTrace();
- }**/
}
@@ -532,7 +514,13 @@ public class OrbotService extends Service implements TorServiceConstants, OrbotC
if (!appBinHome.exists())
appBinHome.mkdirs();
- appCacheHome = getDir(DIRECTORY_TOR_DATA, Application.MODE_PRIVATE);
+ if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
+ appCacheHome = getDataDir();//getDir(DIRECTORY_TOR_DATA, Application.MODE_PRIVATE);
+ }
+ else {
+ appCacheHome = getDir(DIRECTORY_TOR_DATA, Application.MODE_PRIVATE);
+ }
+
if (!appCacheHome.exists())
appCacheHome.mkdirs();
@@ -664,8 +652,8 @@ public class OrbotService extends Service implements TorServiceConstants, OrbotC
extraLines.append("PidFile").append(' ').append(filePid.getCanonicalPath()).append('\n');
- // extraLines.append("RunAsDaemon 1").append('\n');
- // extraLines.append("AvoidDiskWrites 1").append('\n');
+ extraLines.append("RunAsDaemon 1").append('\n');
+ extraLines.append("AvoidDiskWrites 1").append('\n');
String socksPortPref = prefs.getString(OrbotConstants.PREF_SOCKS, (TorServiceConstants.SOCKS_PROXY_PORT_DEFAULT));
@@ -1064,11 +1052,7 @@ public class OrbotService extends Service implements TorServiceConstants, OrbotC
{
logNotice( "Connecting to control port: " + controlPort);
- Socket torConnSocket = new Socket(IP_LOCALHOST, controlPort);
- torConnSocket.setSoTimeout(CONTROL_SOCKET_TIMEOUT);
- conn = new TorControlConnection(torConnSocket);
- conn.launchThread(true);//is daemon
break;
}
@@ -1088,20 +1072,36 @@ public class OrbotService extends Service implements TorServiceConstants, OrbotC
catch (Exception e){}
}
+
+ if (controlPort != -1)
+ {
+ Socket torConnSocket = new Socket(IP_LOCALHOST, controlPort);
+ torConnSocket.setSoTimeout(CONTROL_SOCKET_TIMEOUT);
+
+ conn = new TorControlConnection(torConnSocket);
+
+ conn.launchThread(true);//is daemon
+
+ }
+
if (conn != null)
{
+
logNotice( "SUCCESS connected to Tor control port.");
File fileCookie = new File(appCacheHome, TOR_CONTROL_COOKIE);
if (fileCookie.exists())
{
+
byte[] cookie = new byte[(int)fileCookie.length()];
DataInputStream fis = new DataInputStream(new FileInputStream(fileCookie));
fis.read(cookie);
fis.close();
conn.authenticate(cookie);
+ addEventHandler();
+
logNotice( "SUCCESS - authenticated to control port.");
sendCallbackLogMessage(getString(R.string.tor_process_starting) + ' ' + getString(R.string.tor_process_complete));
@@ -1141,7 +1141,6 @@ public class OrbotService extends Service implements TorServiceConstants, OrbotC
sendCallbackPorts(mPortSOCKS, mPortHTTP, mPortDns, mPortTrans);
- addEventHandler();
return Integer.parseInt(torProcId);
@@ -1212,12 +1211,16 @@ public class OrbotService extends Service implements TorServiceConstants, OrbotC
// ...
logNotice( "adding control port event handler");
- conn.setEventHandler(mEventHandler);
conn.setEvents(Arrays.asList(new String[]{
- "ORCONN", "CIRC", "NOTICE", "WARN", "ERR","BW"}));
+ "CIRC","STREAM", "ORCONN" , "BW" , "INFO" ,"NOTICE" , "WARN" , "ERR" , "NEWDESC" , "ADDRMAP"}));
+
+ conn.setEventHandler(mEventHandler);
logNotice( "SUCCESS added control port event handler");
+
+ conn.setConf("DisableNetwork","0");
+
}
/**
diff --git a/orbotservice/src/main/java/org/torproject/android/service/TorEventHandler.java b/orbotservice/src/main/java/org/torproject/android/service/TorEventHandler.java
index e8de7024..d8f50d19 100644
--- a/orbotservice/src/main/java/org/torproject/android/service/TorEventHandler.java
+++ b/orbotservice/src/main/java/org/torproject/android/service/TorEventHandler.java
@@ -63,6 +63,10 @@ public class TorEventHandler implements EventHandler, TorServiceConstants {
@Override
public void newDescriptors(List<String> orList) {
+
+ for (String desc : orList)
+ mService.debug("descriptors: " + desc);
+
}
@Override
1
0