adds optional HiddenServiceAuthorizeClient option for each hidden service

This commit is contained in:
arrase 2016-12-04 21:10:44 +01:00
parent 07532bb04c
commit 4d0fe27ea3
11 changed files with 104 additions and 7 deletions

View File

@ -593,7 +593,8 @@ public class OrbotMainActivity extends AppCompatActivity
private void enableHiddenServicePort( private void enableHiddenServicePort(
String hsName, final int hsPort, int hsRemotePort, String hsName, final int hsPort, int hsRemotePort,
final String backupToPackage, final Uri hsKeyPath final String backupToPackage, final Uri hsKeyPath,
final Boolean authCookie
) throws RemoteException, InterruptedException { ) throws RemoteException, InterruptedException {
String onionHostname = null; String onionHostname = null;
@ -608,6 +609,7 @@ public class OrbotMainActivity extends AppCompatActivity
fields.put(HSContentProvider.HiddenService.NAME, hsName); fields.put(HSContentProvider.HiddenService.NAME, hsName);
fields.put(HSContentProvider.HiddenService.PORT, hsPort); fields.put(HSContentProvider.HiddenService.PORT, hsPort);
fields.put(HSContentProvider.HiddenService.ONION_PORT, hsRemotePort); fields.put(HSContentProvider.HiddenService.ONION_PORT, hsRemotePort);
fields.put(HSContentProvider.HiddenService.AUTH_COOKIE, authCookie);
ContentResolver cr = getContentResolver(); ContentResolver cr = getContentResolver();
@ -725,6 +727,7 @@ public class OrbotMainActivity extends AppCompatActivity
final int hiddenServiceRemotePort = intent.getIntExtra("hs_onion_port", -1); final int hiddenServiceRemotePort = intent.getIntExtra("hs_onion_port", -1);
final String hiddenServiceName = intent.getStringExtra("hs_name"); final String hiddenServiceName = intent.getStringExtra("hs_name");
final String backupToPackage = intent.getStringExtra("hs_backup_to_package"); final String backupToPackage = intent.getStringExtra("hs_backup_to_package");
final Boolean authCookie = intent.getBooleanExtra("hs_auth_cookie", false);
final Uri mKeyUri = intent.getData(); final Uri mKeyUri = intent.getData();
DialogInterface.OnClickListener dialogClickListener = new DialogInterface.OnClickListener() { DialogInterface.OnClickListener dialogClickListener = new DialogInterface.OnClickListener() {
@ -735,7 +738,8 @@ public class OrbotMainActivity extends AppCompatActivity
try { try {
enableHiddenServicePort( enableHiddenServicePort(
hiddenServiceName, hiddenServicePort, hiddenServiceName, hiddenServicePort,
hiddenServiceRemotePort, backupToPackage, mKeyUri hiddenServiceRemotePort, backupToPackage,
mKeyUri, authCookie
); );
} catch (RemoteException e) { } catch (RemoteException e) {
// TODO Auto-generated catch block // TODO Auto-generated catch block

View File

@ -90,6 +90,14 @@ public class HiddenServicesActivity extends AppCompatActivity {
"onion", item.getString(item.getColumnIndex(HSContentProvider.HiddenService.DOMAIN)) "onion", item.getString(item.getColumnIndex(HSContentProvider.HiddenService.DOMAIN))
); );
arguments.putInt(
"auth_cookie", item.getInt(item.getColumnIndex(HSContentProvider.HiddenService.AUTH_COOKIE))
);
arguments.putString(
"auth_cookie_value", item.getString(item.getColumnIndex(HSContentProvider.HiddenService.AUTH_COOKIE_VALUE))
);
HSActionsDialog dialog = new HSActionsDialog(); HSActionsDialog dialog = new HSActionsDialog();
dialog.setArguments(arguments); dialog.setArguments(arguments);
dialog.show(getSupportFragmentManager(), "HSActionsDialog"); dialog.show(getSupportFragmentManager(), "HSActionsDialog");

View File

@ -88,6 +88,16 @@ public class BackupUtils {
portData.getString(portData.getColumnIndex(HSContentProvider.HiddenService.DOMAIN)) portData.getString(portData.getColumnIndex(HSContentProvider.HiddenService.DOMAIN))
); );
config.put(
HSContentProvider.HiddenService.AUTH_COOKIE,
portData.getInt(portData.getColumnIndex(HSContentProvider.HiddenService.AUTH_COOKIE))
);
config.put(
HSContentProvider.HiddenService.AUTH_COOKIE_VALUE,
portData.getString(portData.getColumnIndex(HSContentProvider.HiddenService.AUTH_COOKIE_VALUE))
);
config.put( config.put(
HSContentProvider.HiddenService.CREATED_BY_USER, HSContentProvider.HiddenService.CREATED_BY_USER,
portData.getInt(portData.getColumnIndex(HSContentProvider.HiddenService.CREATED_BY_USER)) portData.getInt(portData.getColumnIndex(HSContentProvider.HiddenService.CREATED_BY_USER))
@ -173,6 +183,11 @@ public class BackupUtils {
savedValues.getString(HSContentProvider.HiddenService.DOMAIN) savedValues.getString(HSContentProvider.HiddenService.DOMAIN)
); );
fields.put(
HSContentProvider.HiddenService.AUTH_COOKIE,
savedValues.getInt(HSContentProvider.HiddenService.AUTH_COOKIE)
);
fields.put( fields.put(
HSContentProvider.HiddenService.CREATED_BY_USER, HSContentProvider.HiddenService.CREATED_BY_USER,
savedValues.getInt(HSContentProvider.HiddenService.CREATED_BY_USER) savedValues.getInt(HSContentProvider.HiddenService.CREATED_BY_USER)

View File

@ -16,6 +16,8 @@ public class HSDatabase extends SQLiteOpenHelper {
"name TEXT, " + "name TEXT, " +
"domain TEXT, " + "domain TEXT, " +
"onion_port INTEGER, " + "onion_port INTEGER, " +
"auth_cookie INTEGER DEFAULT 0, " +
"auth_cookie_value TEXT, " +
"created_by_user INTEGER DEFAULT 0, " + "created_by_user INTEGER DEFAULT 0, " +
"port INTEGER);"; "port INTEGER);";

View File

@ -83,6 +83,30 @@ public class HSActionsDialog extends DialogFragment {
} }
}); });
Button showAuth = (Button) dialog_view.findViewById(R.id.bt_hs_show_auth);
showAuth.setOnClickListener(new View.OnClickListener() {
public void onClick(View v) {
String auth_cookie_value = arguments.getString("auth_cookie_value");
if (arguments.getInt("auth_cookie") == 1) {
if (auth_cookie_value == null || auth_cookie_value.length() < 1) {
Toast.makeText(
v.getContext(), R.string.please_restart_Orbot_to_enable_the_changes, Toast.LENGTH_LONG
).show();
} else {
new AlertDialog.Builder(getActivity())
.setMessage(auth_cookie_value)
.show();
}
} else {
Toast.makeText(
v.getContext(), R.string.auth_cookie_was_not_configured, Toast.LENGTH_LONG
).show();
}
actionDialog.dismiss();
}
});
Button delete = (Button) dialog_view.findViewById(R.id.btn_hs_delete); Button delete = (Button) dialog_view.findViewById(R.id.btn_hs_delete);
delete.setOnClickListener(new View.OnClickListener() { delete.setOnClickListener(new View.OnClickListener() {
public void onClick(View v) { public void onClick(View v) {

View File

@ -10,6 +10,7 @@ import android.support.v4.app.DialogFragment;
import android.support.v7.app.AlertDialog; import android.support.v7.app.AlertDialog;
import android.view.View; import android.view.View;
import android.widget.Button; import android.widget.Button;
import android.widget.CheckBox;
import android.widget.EditText; import android.widget.EditText;
import android.widget.Toast; import android.widget.Toast;
@ -42,8 +43,10 @@ public class HSDataDialog extends DialogFragment {
((EditText) dialog_view.findViewById(R.id.hsOnionPort)).getText().toString() ((EditText) dialog_view.findViewById(R.id.hsOnionPort)).getText().toString()
); );
Boolean authCookie = ((CheckBox) dialog_view.findViewById(R.id.hsAuth)).isChecked();
if (checkInput(serverName, localPort, onionPort)) { if (checkInput(serverName, localPort, onionPort)) {
saveData(serverName, localPort, onionPort); saveData(serverName, localPort, onionPort, authCookie);
serviceDataDialog.dismiss(); serviceDataDialog.dismiss();
} }
} }
@ -80,11 +83,13 @@ public class HSDataDialog extends DialogFragment {
return is_ok; return is_ok;
} }
private void saveData(String name, Integer local, Integer remote) { private void saveData(String name, Integer local, Integer remote, Boolean authCookie) {
ContentValues fields = new ContentValues(); ContentValues fields = new ContentValues();
fields.put(HSContentProvider.HiddenService.NAME, name); fields.put(HSContentProvider.HiddenService.NAME, name);
fields.put(HSContentProvider.HiddenService.PORT, local); fields.put(HSContentProvider.HiddenService.PORT, local);
fields.put(HSContentProvider.HiddenService.ONION_PORT, remote); fields.put(HSContentProvider.HiddenService.ONION_PORT, remote);
fields.put(HSContentProvider.HiddenService.AUTH_COOKIE, authCookie);
fields.put(HSContentProvider.HiddenService.CREATED_BY_USER, 1); fields.put(HSContentProvider.HiddenService.CREATED_BY_USER, 1);
ContentResolver cr = getContext().getContentResolver(); ContentResolver cr = getContext().getContentResolver();

View File

@ -22,6 +22,8 @@ public class HSContentProvider extends ContentProvider {
HiddenService.PORT, HiddenService.PORT,
HiddenService.DOMAIN, HiddenService.DOMAIN,
HiddenService.ONION_PORT, HiddenService.ONION_PORT,
HiddenService.AUTH_COOKIE,
HiddenService.AUTH_COOKIE_VALUE,
HiddenService.CREATED_BY_USER HiddenService.CREATED_BY_USER
}; };
private static final String AUTH = "org.torproject.android.ui.hiddenservices.providers"; private static final String AUTH = "org.torproject.android.ui.hiddenservices.providers";
@ -130,6 +132,8 @@ public class HSContentProvider extends ContentProvider {
public static final String PORT = "port"; public static final String PORT = "port";
public static final String ONION_PORT = "onion_port"; public static final String ONION_PORT = "onion_port";
public static final String DOMAIN = "domain"; public static final String DOMAIN = "domain";
public static final String AUTH_COOKIE = "auth_cookie";
public static final String AUTH_COOKIE_VALUE = "auth_cookie_value";
public static final String CREATED_BY_USER = "created_by_user"; public static final String CREATED_BY_USER = "created_by_user";
private HiddenService() { private HiddenService() {

View File

@ -9,6 +9,12 @@
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:id="@+id/btn_hs_clipboard" /> android:id="@+id/btn_hs_clipboard" />
<Button
android:text="@string/show_auth_cookie"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:id="@+id/bt_hs_show_auth" />
<Button <Button
android:text="@string/backup_service" android:text="@string/backup_service"
android:layout_width="match_parent" android:layout_width="match_parent"

View File

@ -53,6 +53,14 @@
android:id="@+id/hsOnionPort" android:id="@+id/hsOnionPort"
android:inputType="number" /> android:inputType="number" />
<CheckBox
android:text="@string/auth_cookie"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:id="@+id/hsAuth"
android:paddingTop="5dp"
android:paddingBottom="10dp"/>
<LinearLayout <LinearLayout
android:orientation="horizontal" android:orientation="horizontal"
android:layout_width="match_parent" android:layout_width="match_parent"

View File

@ -347,6 +347,7 @@
<string name="done">Done!</string> <string name="done">Done!</string>
<string name="invalid_port">Invalid Port</string> <string name="invalid_port">Invalid Port</string>
<string name="copy_address_to_clipboard">Copy address to clipboard</string> <string name="copy_address_to_clipboard">Copy address to clipboard</string>
<string name="show_auth_cookie">Show auth cookie</string>
<string name="backup_service">Backup Service</string> <string name="backup_service">Backup Service</string>
<string name="delete_service">Delete Service</string> <string name="delete_service">Delete Service</string>
<string name="backup_saved_at_external_storage">Backup saved at external storage</string> <string name="backup_saved_at_external_storage">Backup saved at external storage</string>
@ -362,4 +363,7 @@
<string name="confirm_service_deletion">Confirm service deletion</string> <string name="confirm_service_deletion">Confirm service deletion</string>
<string name="click_again_for_backup">Click again for backup</string> <string name="click_again_for_backup">Click again for backup</string>
<string name="service_type">Service type</string> <string name="service_type">Service type</string>
<string name="auth_cookie">Auth cookie</string>
<string name="auth_cookie_was_not_configured">Auth cookie was not configured</string>
<string name="please_restart_Orbot_to_enable_the_changes">Please restart Orbot to enable the changes</string>
</resources> </resources>

View File

@ -139,6 +139,8 @@ public class TorService extends Service implements TorServiceConstants, OrbotCon
public static final String PORT = "port"; public static final String PORT = "port";
public static final String ONION_PORT = "onion_port"; public static final String ONION_PORT = "onion_port";
public static final String DOMAIN = "domain"; public static final String DOMAIN = "domain";
public static final String AUTH_COOKIE = "auth_cookie";
public static final String AUTH_COOKIE_VALUE = "auth_cookie_value";
public static final String CREATED_BY_USER = "created_by_user"; public static final String CREATED_BY_USER = "created_by_user";
private HiddenService() { private HiddenService() {
@ -147,8 +149,11 @@ public class TorService extends Service implements TorServiceConstants, OrbotCon
private String[] mProjection = new String[]{ private String[] mProjection = new String[]{
HiddenService._ID, HiddenService._ID,
HiddenService.NAME,
HiddenService.DOMAIN, HiddenService.DOMAIN,
HiddenService.PORT, HiddenService.PORT,
HiddenService.AUTH_COOKIE,
HiddenService.AUTH_COOKIE_VALUE,
HiddenService.ONION_PORT}; HiddenService.ONION_PORT};
public void debug(String msg) public void debug(String msg)
@ -777,9 +782,11 @@ public class TorService extends Service implements TorServiceConstants, OrbotCon
while (hidden_services.moveToNext()) { while (hidden_services.moveToNext()) {
String HSDomain = hidden_services.getString(hidden_services.getColumnIndex(HiddenService.DOMAIN)); String HSDomain = hidden_services.getString(hidden_services.getColumnIndex(HiddenService.DOMAIN));
Integer HSLocalPort = hidden_services.getInt(hidden_services.getColumnIndex(HiddenService.PORT)); Integer HSLocalPort = hidden_services.getInt(hidden_services.getColumnIndex(HiddenService.PORT));
Integer HSAuthCookie = hidden_services.getInt(hidden_services.getColumnIndex(HiddenService.AUTH_COOKIE));
String HSAuthCookieValue = hidden_services.getString(hidden_services.getColumnIndex(HiddenService.AUTH_COOKIE_VALUE));
// Update only new domains // Update only new domains or restored from backup with auth cookie
if(HSDomain == null || HSDomain.length() < 1) { if((HSDomain == null || HSDomain.length() < 1) || (HSAuthCookie == 1 && (HSAuthCookieValue == null || HSAuthCookieValue.length() < 1))) {
String hsDirPath = new File(mHSBasePath.getAbsolutePath(),"hs" + HSLocalPort).getCanonicalPath(); String hsDirPath = new File(mHSBasePath.getAbsolutePath(),"hs" + HSLocalPort).getCanonicalPath();
File file = new File(hsDirPath, "hostname"); File file = new File(hsDirPath, "hostname");
@ -789,7 +796,12 @@ public class TorService extends Service implements TorServiceConstants, OrbotCon
try { try {
String onionHostname = Utils.readString(new FileInputStream(file)).trim(); String onionHostname = Utils.readString(new FileInputStream(file)).trim();
fields.put("domain", onionHostname); if(HSAuthCookie == 1) {
String[] aux = onionHostname.split(" ");
onionHostname = aux[0];
fields.put(HiddenService.AUTH_COOKIE_VALUE, aux[1]);
}
fields.put(HiddenService.DOMAIN, onionHostname);
mCR.update(CONTENT_URI, fields, "port=" + HSLocalPort , null); mCR.update(CONTENT_URI, fields, "port=" + HSLocalPort , null);
} catch (FileNotFoundException e) { } catch (FileNotFoundException e) {
logException("unable to read onion hostname file",e); logException("unable to read onion hostname file",e);
@ -1784,14 +1796,19 @@ public class TorService extends Service implements TorServiceConstants, OrbotCon
if(hidden_services != null) { if(hidden_services != null) {
try { try {
while (hidden_services.moveToNext()) { while (hidden_services.moveToNext()) {
String HSname = hidden_services.getString(hidden_services.getColumnIndex(HiddenService.NAME));
Integer HSLocalPort = hidden_services.getInt(hidden_services.getColumnIndex(HiddenService.PORT)); Integer HSLocalPort = hidden_services.getInt(hidden_services.getColumnIndex(HiddenService.PORT));
Integer HSOnionPort = hidden_services.getInt(hidden_services.getColumnIndex(HiddenService.ONION_PORT)); Integer HSOnionPort = hidden_services.getInt(hidden_services.getColumnIndex(HiddenService.ONION_PORT));
Integer HSAuthCookie = hidden_services.getInt(hidden_services.getColumnIndex(HiddenService.AUTH_COOKIE));
String hsDirPath = new File(mHSBasePath.getAbsolutePath(),"hs" + HSLocalPort).getCanonicalPath(); String hsDirPath = new File(mHSBasePath.getAbsolutePath(),"hs" + HSLocalPort).getCanonicalPath();
debug("Adding hidden service on port: " + HSLocalPort); debug("Adding hidden service on port: " + HSLocalPort);
extraLines.append("HiddenServiceDir" + ' ' + hsDirPath).append('\n'); extraLines.append("HiddenServiceDir" + ' ' + hsDirPath).append('\n');
extraLines.append("HiddenServicePort" + ' ' + HSOnionPort + " 127.0.0.1:" + HSLocalPort).append('\n'); extraLines.append("HiddenServicePort" + ' ' + HSOnionPort + " 127.0.0.1:" + HSLocalPort).append('\n');
if(HSAuthCookie == 1)
extraLines.append("HiddenServiceAuthorizeClient stealth " + HSname).append('\n');
} }
} catch (NumberFormatException e) { } catch (NumberFormatException e) {
Log.e(OrbotConstants.TAG,"error parsing hsport",e); Log.e(OrbotConstants.TAG,"error parsing hsport",e);