[tor-commits] [orbot/master] - Fixed .auth_privates being saved as .auth_private.txt

n8fr8 at torproject.org n8fr8 at torproject.org
Wed Dec 22 21:55:07 UTC 2021


commit 894c7ba11e1357833e4f40f2988ba856c96ae487
Author: bim <dsnake at protonmail.com>
Date:   Mon Mar 1 15:51:49 2021 -0500

    - Fixed .auth_privates being saved as .auth_private.txt
    - Better input validation on backing up client auth keys
    - Fixed minor bug where backup filename would clear on device rotation
---
 .../clientauth/ClientAuthActivity.java             | 20 +++++++--
 .../clientauth/ClientAuthBackupDialogFragment.java | 47 ++++++++++++++++++++--
 2 files changed, 60 insertions(+), 7 deletions(-)

diff --git a/app/src/main/java/org/torproject/android/ui/v3onionservice/clientauth/ClientAuthActivity.java b/app/src/main/java/org/torproject/android/ui/v3onionservice/clientauth/ClientAuthActivity.java
index e33ddf78..761ce171 100644
--- a/app/src/main/java/org/torproject/android/ui/v3onionservice/clientauth/ClientAuthActivity.java
+++ b/app/src/main/java/org/torproject/android/ui/v3onionservice/clientauth/ClientAuthActivity.java
@@ -8,6 +8,7 @@ import android.database.Cursor;
 import android.net.Uri;
 import android.os.Bundle;
 import android.os.Handler;
+import android.provider.OpenableColumns;
 import android.view.Menu;
 import android.view.MenuItem;
 import android.widget.ListView;
@@ -22,7 +23,6 @@ import org.torproject.android.R;
 import org.torproject.android.core.DiskUtils;
 import org.torproject.android.core.LocaleHelper;
 import org.torproject.android.ui.hiddenservices.backup.BackupUtils;
-import org.torproject.android.ui.hiddenservices.backup.ZipUtilities;
 
 import java.io.File;
 import java.util.List;
@@ -36,6 +36,9 @@ public class ClientAuthActivity extends AppCompatActivity {
     private ContentResolver mResolver;
     private ClientAuthListAdapter mAdapter;
 
+    static final String CLIENT_AUTH_FILE_EXTENSION = ".auth_private",
+            CLIENT_AUTH_SAF_MIME_TYPE = "*/*";
+
     @Override
     protected void onCreate(@Nullable Bundle savedInstanceState) {
         super.onCreate(savedInstanceState);
@@ -69,14 +72,22 @@ public class ClientAuthActivity extends AppCompatActivity {
         if (requestCode == REQUEST_CODE_READ_ZIP_BACKUP && resultCode == RESULT_OK) {
             Uri uri = data.getData();
             if (uri != null) {
+                Cursor cursor = getContentResolver().query(uri, null, null, null, null);
+                int nameIndex = cursor.getColumnIndex(OpenableColumns.DISPLAY_NAME);
+                cursor.moveToFirst();
+                String filename = cursor.getString(nameIndex);
+                cursor.close();
+                if (!filename.endsWith(CLIENT_AUTH_FILE_EXTENSION)) {
+                    Toast.makeText(this, R.string.error, Toast.LENGTH_LONG).show();
+                    return;
+                }
                 String authText = DiskUtils.readFileFromInputStream(getContentResolver(), uri);
                 new BackupUtils(this).restoreClientAuthBackup(authText);
             }
         } else {
             super.onActivityResult(requestCode, resultCode, data);
             List<Fragment> frags = getSupportFragmentManager().getFragments();
-            if (frags != null)
-                for (Fragment f : frags) f.onActivityResult(requestCode, resultCode, data);
+            for (Fragment f : frags) f.onActivityResult(requestCode, resultCode, data);
         }
     }
 
@@ -103,7 +114,8 @@ public class ClientAuthActivity extends AppCompatActivity {
     public boolean onOptionsItemSelected(MenuItem item) {
         if (item.getItemId() == R.id.menu_import_auth_priv) {
             if (DiskUtils.supportsStorageAccessFramework()) {
-                Intent readFileIntent = DiskUtils.createReadFileIntent("text/*");
+                // unfortunately no good way to filter .auth_private files
+                Intent readFileIntent = DiskUtils.createReadFileIntent(CLIENT_AUTH_SAF_MIME_TYPE);
                 startActivityForResult(readFileIntent, REQUEST_CODE_READ_ZIP_BACKUP);
             } else { // APIs 16, 17, 18
                 doRestoreLegacy();
diff --git a/app/src/main/java/org/torproject/android/ui/v3onionservice/clientauth/ClientAuthBackupDialogFragment.java b/app/src/main/java/org/torproject/android/ui/v3onionservice/clientauth/ClientAuthBackupDialogFragment.java
index c924fe0e..b56bc337 100644
--- a/app/src/main/java/org/torproject/android/ui/v3onionservice/clientauth/ClientAuthBackupDialogFragment.java
+++ b/app/src/main/java/org/torproject/android/ui/v3onionservice/clientauth/ClientAuthBackupDialogFragment.java
@@ -3,9 +3,13 @@ package org.torproject.android.ui.v3onionservice.clientauth;
 import android.app.Activity;
 import android.app.AlertDialog;
 import android.app.Dialog;
+import android.content.DialogInterface;
 import android.content.Intent;
 import android.net.Uri;
 import android.os.Bundle;
+import android.text.Editable;
+import android.text.TextUtils;
+import android.text.TextWatcher;
 import android.view.ViewGroup;
 import android.widget.FrameLayout;
 import android.widget.Toast;
@@ -23,6 +27,9 @@ import java.io.File;
 public class ClientAuthBackupDialogFragment extends DialogFragment {
 
     private NoPersonalizedLearningEditText etFilename;
+    private TextWatcher fileNameTextWatcher;
+
+    private static final String BUNDLE_KEY_FILENAME = "filename";
 
     public ClientAuthBackupDialogFragment() {
     }
@@ -50,18 +57,52 @@ public class ClientAuthBackupDialogFragment extends DialogFragment {
         etFilename = new NoPersonalizedLearningEditText(ad.getContext(), null);
         etFilename.setSingleLine(true);
         etFilename.setHint(R.string.v3_backup_name_hint);
+        if (savedInstanceState != null)
+            etFilename.setText(savedInstanceState.getString(BUNDLE_KEY_FILENAME, ""));
+        fileNameTextWatcher = new TextWatcher() {
+            @Override
+            public void beforeTextChanged(CharSequence s, int start, int count, int after) {
+
+            }
+
+            @Override
+            public void onTextChanged(CharSequence s, int start, int before, int count) {
+
+            }
+
+            @Override
+            public void afterTextChanged(Editable s) {
+                ad.getButton(DialogInterface.BUTTON_POSITIVE).setEnabled(!TextUtils.isEmpty(s.toString().trim()));
+            }
+        };
+        etFilename.addTextChangedListener(fileNameTextWatcher);
         etFilename.setLayoutParams(params);
         container.addView(etFilename);
         ad.setView(container);
         return ad;
     }
 
+    @Override
+    public void onSaveInstanceState(Bundle outState) {
+        super.onSaveInstanceState(outState);
+        outState.putString(BUNDLE_KEY_FILENAME, etFilename.getText().toString());
+    }
+
+
+    @Override
+    public void onStart() {
+        super.onStart();
+        fileNameTextWatcher.afterTextChanged(etFilename.getEditableText());
+    }
+
+
+
     private void doBackup() {
         String filename = etFilename.getText().toString().trim();
-        if (filename.equals("")) filename = "filename";
-        filename += ".auth_private";
+        if (!filename.endsWith(ClientAuthActivity.CLIENT_AUTH_FILE_EXTENSION))
+            filename += ClientAuthActivity.CLIENT_AUTH_FILE_EXTENSION;
         if (DiskUtils.supportsStorageAccessFramework()) {
-            Intent createFileIntent = DiskUtils.createWriteFileIntent(filename, "text/*");
+            Intent createFileIntent = DiskUtils.createWriteFileIntent(filename, ClientAuthActivity.CLIENT_AUTH_SAF_MIME_TYPE);
             getActivity().startActivityForResult(createFileIntent, REQUEST_CODE_WRITE_FILE);
         } else { // APIs 16, 17, 18
             attemptToWriteBackup(Uri.fromFile(new File(DiskUtils.getOrCreateLegacyBackupDir("Orbot"), filename)));





More information about the tor-commits mailing list