On master: Current working dir changes

This commit is contained in:
AlexVallat 2013-07-25 13:47:05 +01:00
commit d678c711fa
30 changed files with 628 additions and 712 deletions

25
.gitignore vendored
View File

@ -1,3 +1,28 @@
PCtest
*.suo
*.userprefs
*.user
*.designer.cs
src/java/kp2akeytransform/kp2akeytransform.zip
src/Kp2aKeyboardBinding/bin
src/Kp2aKeyboardBinding/obj
src/kp2akeytransform/bin
src/kp2akeytransform/obj
src/Kp2aBusinessLogic/bin
src/Kp2aBusinessLogic/obj
src/Kp2aUnitTests/bin
src/Kp2aUnitTests/obj
src/monodroid-unittesting/MonoDroidUnitTesting/bin
src/monodroid-unittesting/MonoDroidUnitTesting/obj
/src/keepass2android/todos.cs /src/keepass2android/todos.cs
/src/keepass2android/obj /src/keepass2android/obj
/src/keepass2android/bin /src/keepass2android/bin

View File

@ -1,4 +1,5 @@
using System; using System;
using System.IO;
using Android.Content; using Android.Content;
using Android.OS; using Android.OS;
using KeePassLib.Serialization; using KeePassLib.Serialization;
@ -12,11 +13,15 @@ namespace keepass2android
/// This also contains methods which are UI specific and should be replacable for testing. /// This also contains methods which are UI specific and should be replacable for testing.
public interface IKp2aApp public interface IKp2aApp
{ {
/// <summary>
/// Locks the currently open database, quicklocking if available (unless false is passed for allowQuickUnlock)
/// </summary>
void LockDatabase(bool allowQuickUnlock = true);
/// <summary> /// <summary>
/// Set the flag that the database needs to be locked. /// Loads the specified data as the currently open database, as unlocked.
/// </summary> /// </summary>
void SetShutdown(); void LoadDatabase(IOConnectionInfo ioConnectionInfo, MemoryStream memoryStream, string s, string keyFile, ProgressDialogStatusLogger statusLogger);
/// <summary> /// <summary>
/// Returns the current database /// Returns the current database
@ -69,6 +74,5 @@ namespace keepass2android
IProgressDialog CreateProgressDialog(Context ctx); IProgressDialog CreateProgressDialog(Context ctx);
IFileStorage GetFileStorage(IOConnectionInfo iocInfo); IFileStorage GetFileStorage(IOConnectionInfo iocInfo);
} }
} }

View File

@ -88,7 +88,7 @@
<Name>KeePassLib2Android</Name> <Name>KeePassLib2Android</Name>
</ProjectReference> </ProjectReference>
</ItemGroup> </ItemGroup>
<Import Project="$(MSBuildExtensionsPath)\Xamarin\Android\Xamarin.Android.CSharp.targets" /> <Import Project="$(MSBuildExtensionsPath)\Novell\Novell.MonoDroid.CSharp.targets" />
<!-- To modify your build process, add your task inside one of the targets below and uncomment it. <!-- To modify your build process, add your task inside one of the targets below and uncomment it.
Other similar extension points exist, see Microsoft.Common.targets. Other similar extension points exist, see Microsoft.Common.targets.
<Target Name="BeforeBuild"> <Target Name="BeforeBuild">

View File

@ -72,25 +72,6 @@ namespace keepass2android
set { _loaded = value; } set { _loaded = value; }
} }
public bool Open
{
get { return Loaded && (!Locked); }
}
bool _locked;
public bool Locked
{
get
{
return _locked;
}
set
{
Kp2aLog.Log("Locked=" + _locked);
_locked = value;
}
}
public bool DidOpenFileChange() public bool DidOpenFileChange()
{ {
if (Loaded == false) if (Loaded == false)
@ -102,6 +83,9 @@ namespace keepass2android
} }
/// <summary>
/// Do not call this method directly. Call App.Kp2a.LoadDatabase instead.
/// </summary>
public void LoadData(IKp2aApp app, IOConnectionInfo iocInfo, MemoryStream databaseData, String password, String keyfile, ProgressDialogStatusLogger status) public void LoadData(IKp2aApp app, IOConnectionInfo iocInfo, MemoryStream databaseData, String password, String keyfile, ProgressDialogStatusLogger status)
{ {
PwDatabase pwDatabase = new PwDatabase(); PwDatabase pwDatabase = new PwDatabase();
@ -153,15 +137,6 @@ namespace keepass2android
SearchHelper = new SearchDbHelper(app); SearchHelper = new SearchDbHelper(app);
} }
public bool QuickUnlockEnabled { get; set; }
//KeyLength of QuickUnlock at time of loading the database.
//This is important to not allow an attacker to set the length to 1 when QuickUnlock is started already.
public int QuickUnlockKeyLength
{
get;
set;
}
public PwGroup SearchForText(String str) { public PwGroup SearchForText(String str) {
PwGroup group = SearchHelper.SearchForText(this, str); PwGroup group = SearchHelper.SearchForText(this, str);
@ -227,7 +202,6 @@ namespace keepass2android
Root = null; Root = null;
KpDatabase = null; KpDatabase = null;
_loaded = false; _loaded = false;
_locked = false;
_reloadRequested = false; _reloadRequested = false;
} }

View File

@ -79,7 +79,7 @@ namespace keepass2android
else else
{ {
// Let's not bother recovering from a failure to save a deleted entry. It is too much work. // Let's not bother recovering from a failure to save a deleted entry. It is too much work.
App.SetShutdown(); App.LockDatabase();
} }
}, OnFinishToRun); }, OnFinishToRun);
} }
@ -99,7 +99,7 @@ namespace keepass2android
Db.Dirty.Add(pgRecycleBin); Db.Dirty.Add(pgRecycleBin);
} else { } else {
// Let's not bother recovering from a failure to save a deleted entry. It is too much work. // Let's not bother recovering from a failure to save a deleted entry. It is too much work.
App.SetShutdown(); App.LockDatabase();
} }
}, OnFinishToRun); }, OnFinishToRun);

View File

@ -108,7 +108,7 @@ namespace keepass2android
Db.Dirty.Add(pgParent); Db.Dirty.Add(pgParent);
} else { } else {
// Let's not bother recovering from a failure to save a deleted group. It is too much work. // Let's not bother recovering from a failure to save a deleted group. It is too much work.
App.SetShutdown(); App.LockDatabase();
} }
}, OnFinishToRun); }, OnFinishToRun);
} }
@ -146,7 +146,7 @@ namespace keepass2android
} }
} else { } else {
// Let's not bother recovering from a failure to save a deleted group. It is too much work. // Let's not bother recovering from a failure to save a deleted group. It is too much work.
_app.SetShutdown(); _app.LockDatabase();
} }
base.Run(); base.Run();

View File

@ -47,7 +47,7 @@ namespace keepass2android
try try
{ {
StatusLogger.UpdateMessage(UiStringKey.loading_database); StatusLogger.UpdateMessage(UiStringKey.loading_database);
_app.GetDb().LoadData (_app, _ioc, _databaseData, _pass, _key, StatusLogger); _app.LoadDatabase(_ioc, _databaseData, _pass, _key, StatusLogger);
SaveFileData (_ioc, _key); SaveFileData (_ioc, _key);
} catch (KeyFileException) { } catch (KeyFileException) {

View File

@ -613,9 +613,7 @@ namespace keepass2android
} }
return true; return true;
case Resource.Id.menu_lock: case Resource.Id.menu_lock:
App.Kp2a.SetShutdown(); App.Kp2a.LockDatabase();
SetResult(KeePass.ExitLock);
Finish();
return true; return true;
case Resource.Id.menu_translate: case Resource.Id.menu_translate:
try { try {

View File

@ -92,8 +92,7 @@ namespace keepass2android
_closeForReload = false; _closeForReload = false;
// Likely the app has been killed exit the activity // Likely the app has been killed exit the activity
Database db = App.Kp2a.GetDb(); if (!App.Kp2a.DatabaseIsUnlocked)
if (! db.Open)
{ {
Finish(); Finish();
return; return;
@ -107,6 +106,8 @@ namespace keepass2android
} else } else
{ {
Database db = App.Kp2a.GetDb();
App.Kp2a.EntryEditActivityState = new EntryEditActivityState(); App.Kp2a.EntryEditActivityState = new EntryEditActivityState();
ISharedPreferences prefs = PreferenceManager.GetDefaultSharedPreferences(this); ISharedPreferences prefs = PreferenceManager.GetDefaultSharedPreferences(this);
State.ShowPassword = ! prefs.GetBoolean(GetString(Resource.String.maskpass_key), Resources.GetBoolean(Resource.Boolean.maskpass_default)); State.ShowPassword = ! prefs.GetBoolean(GetString(Resource.String.maskpass_key), Resources.GetBoolean(Resource.Boolean.maskpass_default));

View File

@ -240,9 +240,7 @@ namespace keepass2android
return true; return true;
case Resource.Id.menu_lock: case Resource.Id.menu_lock:
App.Kp2a.SetShutdown(); App.Kp2a.LockDatabase();
SetResult(KeePass.ExitLock);
Finish();
return true; return true;
case Resource.Id.menu_search: case Resource.Id.menu_search:
@ -353,8 +351,7 @@ namespace keepass2android
Toast.MakeText(_act, "Unrecoverable error: " + Message, ToastLength.Long).Show(); Toast.MakeText(_act, "Unrecoverable error: " + Message, ToastLength.Long).Show();
}); });
App.Kp2a.SetShutdown(); App.Kp2a.LockDatabase();
_act.Finish();
} }
} }

View File

@ -56,8 +56,7 @@ namespace keepass2android
} }
else else
{ {
Kp2aLog.Log(" Loaded=" + App.Kp2a.GetDb().Loaded + ", Locked=" + App.Kp2a.GetDb().Locked Kp2aLog.Log(" DatabaseIsUnlocked=" + App.Kp2a.DatabaseIsUnlocked);
+ ", shutdown=" + App.Kp2a.IsShutdown());
} }
} }

View File

@ -15,7 +15,10 @@ This file is part of Keepass2Android, Copyright 2013 Philipp Crocoll. This file
along with Keepass2Android. If not, see <http://www.gnu.org/licenses/>. along with Keepass2Android. If not, see <http://www.gnu.org/licenses/>.
*/ */
using System;
using Android.Content;
using Android.OS; using Android.OS;
using Android.App;
using KeePassLib.Serialization; using KeePassLib.Serialization;
namespace keepass2android namespace keepass2android
@ -26,12 +29,25 @@ namespace keepass2android
/// Checks in OnResume whether the timeout occured and the database must be locked/closed. /// Checks in OnResume whether the timeout occured and the database must be locked/closed.
public class LockCloseActivity : LockingActivity { public class LockCloseActivity : LockingActivity {
IOConnectionInfo _ioc; private IOConnectionInfo _ioc;
private BroadcastReceiver _intentReceiver;
protected override void OnCreate(Bundle savedInstanceState) protected override void OnCreate(Bundle savedInstanceState)
{ {
base.OnCreate(savedInstanceState); base.OnCreate(savedInstanceState);
_ioc = App.Kp2a.GetDb().Ioc; _ioc = App.Kp2a.GetDb().Ioc;
_intentReceiver = new LockCloseActivityBroadcastReceiver(this);
IntentFilter filter = new IntentFilter();
filter.AddAction(Intents.LockDatabase);
RegisterReceiver(_intentReceiver, filter);
}
protected override void OnDestroy()
{
UnregisterReceiver(_intentReceiver);
base.OnDestroy();
} }
@ -49,9 +65,32 @@ namespace keepass2android
App.Kp2a.CheckForOpenFileChanged(this); App.Kp2a.CheckForOpenFileChanged(this);
} }
private void OnLockDatabase()
{
Kp2aLog.Log("Finishing " + ComponentName.ClassName + " due to database lock");
SetResult(KeePass.ExitLock);
Finish();
}
private class LockCloseActivityBroadcastReceiver : BroadcastReceiver
{
readonly LockCloseActivity _service;
public LockCloseActivityBroadcastReceiver(LockCloseActivity service)
{
_service = service;
}
public override void OnReceive(Context context, Intent intent)
{
switch (intent.Action)
{
case Intents.LockDatabase:
_service.OnLockDatabase();
break;
}
}
}
} }
} }

View File

@ -16,6 +16,7 @@ This file is part of Keepass2Android, Copyright 2013 Philipp Crocoll. This file
*/ */
using System; using System;
using Android.Content;
using Android.OS; using Android.OS;
using Android.Runtime; using Android.Runtime;
using KeePassLib.Serialization; using KeePassLib.Serialization;
@ -33,11 +34,18 @@ namespace keepass2android
} }
IOConnectionInfo _ioc; IOConnectionInfo _ioc;
private BroadcastReceiver _intentReceiver;
protected override void OnCreate(Bundle savedInstanceState) protected override void OnCreate(Bundle savedInstanceState)
{ {
base.OnCreate(savedInstanceState); base.OnCreate(savedInstanceState);
_ioc = App.Kp2a.GetDb().Ioc; _ioc = App.Kp2a.GetDb().Ioc;
_intentReceiver = new LockCloseListActivityBroadcastReceiver(this);
IntentFilter filter = new IntentFilter();
filter.AddAction(Intents.LockDatabase);
RegisterReceiver(_intentReceiver, filter);
} }
public LockCloseListActivity (IntPtr javaReference, JniHandleOwnership transfer) public LockCloseListActivity (IntPtr javaReference, JniHandleOwnership transfer)
@ -57,6 +65,39 @@ namespace keepass2android
App.Kp2a.CheckForOpenFileChanged(this); App.Kp2a.CheckForOpenFileChanged(this);
} }
protected override void OnDestroy()
{
UnregisterReceiver(_intentReceiver);
base.OnDestroy();
}
private void OnLockDatabase()
{
Kp2aLog.Log("Finishing " + ComponentName.ClassName + " due to database lock");
SetResult(KeePass.ExitLock);
Finish();
}
private class LockCloseListActivityBroadcastReceiver : BroadcastReceiver
{
readonly LockCloseListActivity _service;
public LockCloseListActivityBroadcastReceiver(LockCloseListActivity service)
{
_service = service;
}
public override void OnReceive(Context context, Intent intent)
{
switch (intent.Action)
{
case Intents.LockDatabase:
_service.OnLockDatabase();
break;
}
}
}
} }
} }

View File

@ -15,6 +15,7 @@ This file is part of Keepass2Android, Copyright 2013 Philipp Crocoll. This file
along with Keepass2Android. If not, see <http://www.gnu.org/licenses/>. along with Keepass2Android. If not, see <http://www.gnu.org/licenses/>.
*/ */
using Android.Content;
using Android.OS; using Android.OS;
using KeePassLib.Serialization; using KeePassLib.Serialization;
@ -25,11 +26,18 @@ namespace keepass2android
IOConnectionInfo _ioc; IOConnectionInfo _ioc;
private BroadcastReceiver _intentReceiver;
protected override void OnCreate(Bundle savedInstanceState) protected override void OnCreate(Bundle savedInstanceState)
{ {
base.OnCreate(savedInstanceState); base.OnCreate(savedInstanceState);
_ioc = App.Kp2a.GetDb().Ioc; _ioc = App.Kp2a.GetDb().Ioc;
_intentReceiver = new LockingClosePreferenceActivityBroadcastReceiver(this);
IntentFilter filter = new IntentFilter();
filter.AddAction(Intents.LockDatabase);
RegisterReceiver(_intentReceiver, filter);
} }
protected override void OnResume() { protected override void OnResume() {
@ -37,6 +45,41 @@ namespace keepass2android
TimeoutHelper.CheckShutdown(this, _ioc); TimeoutHelper.CheckShutdown(this, _ioc);
} }
protected override void OnDestroy()
{
UnregisterReceiver(_intentReceiver);
base.OnDestroy();
}
private void OnLockDatabase()
{
Kp2aLog.Log("Finishing " + ComponentName.ClassName + " due to database lock");
SetResult(KeePass.ExitLock);
Finish();
}
private class LockingClosePreferenceActivityBroadcastReceiver : BroadcastReceiver
{
readonly LockingClosePreferenceActivity _service;
public LockingClosePreferenceActivityBroadcastReceiver(LockingClosePreferenceActivity service)
{
_service = service;
}
public override void OnReceive(Context context, Intent intent)
{
switch (intent.Action)
{
case Intents.LockDatabase:
_service.OnLockDatabase();
break;
}
}
}
} }
} }

View File

@ -53,6 +53,7 @@ namespace keepass2android
private const String ViewIntent = "android.intent.action.VIEW"; private const String ViewIntent = "android.intent.action.VIEW";
private Task<MemoryStream> _loadDbTask;
private IOConnectionInfo _ioConnection; private IOConnectionInfo _ioConnection;
private String _keyFile; private String _keyFile;
private bool _rememberKeyfile; private bool _rememberKeyfile;
@ -130,58 +131,14 @@ namespace keepass2android
} }
void UnloadDatabase() void TryStartQuickUnlock()
{ {
App.Kp2a.GetDb().Clear(); if (App.Kp2a.QuickUnlockEnabled && App.Kp2a.QuickLocked)
StopService(new Intent(this, typeof(QuickUnlockForegroundService)));
}
void LockDatabase()
{
SetResult(KeePass.ExitLock);
SetEditText(Resource.Id.password, "");
if (App.Kp2a.GetDb().QuickUnlockEnabled)
App.Kp2a.GetDb().Locked = true;
else
{ {
UnloadDatabase(); Intent i = new Intent(this, typeof(QuickUnlock));
} PutIoConnectionToIntent(_ioConnection, i);
} Kp2aLog.Log("Starting QuickUnlock");
StartActivityForResult(i, 0);
void LockAndClose()
{
LockDatabase();
Finish();
}
bool TryStartQuickUnlock()
{
if (!App.Kp2a.GetDb().QuickUnlockEnabled)
return false;
if (App.Kp2a.GetDb().KpDatabase.MasterKey.ContainsType(typeof(KcpPassword)) == false)
return false;
KcpPassword kcpPassword = (KcpPassword)App.Kp2a.GetDb().KpDatabase.MasterKey.GetUserKey(typeof(KcpPassword));
String password = kcpPassword.Password.ReadString();
if (password.Length == 0)
return false;
App.Kp2a.GetDb().Locked = true;
Intent i = new Intent(this, typeof(QuickUnlock));
PutIoConnectionToIntent(_ioConnection, i);
Kp2aLog.Log("Starting QuickUnlock");
StartActivityForResult(i,0);
return true;
}
public void StartQuickUnlockForegroundService()
{
if (App.Kp2a.GetDb().QuickUnlockEnabled)
{
StartService(new Intent(this, typeof(QuickUnlockForegroundService)));
} }
} }
@ -194,45 +151,27 @@ namespace keepass2android
_startedWithActivityResult = true; _startedWithActivityResult = true;
Kp2aLog.Log("PasswordActivity.OnActivityResult "+resultCode+"/"+requestCode); Kp2aLog.Log("PasswordActivity.OnActivityResult "+resultCode+"/"+requestCode);
if (resultCode != KeePass.ExitCloseAfterTaskComplete)
{
//Stop service when app activity is left
StopService(new Intent(this, typeof(CopyToClipboardService)));
}
//NOTE: original code from k eepassdroid used switch ((Android.App.Result)requestCode) { (but doesn't work here, although k eepassdroid works) //NOTE: original code from k eepassdroid used switch ((Android.App.Result)requestCode) { (but doesn't work here, although k eepassdroid works)
switch(resultCode) { switch(resultCode) {
case KeePass.ExitNormal:
if (!TryStartQuickUnlock())
{
SetEditText(Resource.Id.password, "");
}
break;
case KeePass.ExitLock: case KeePass.ExitLock:
if (!TryStartQuickUnlock()) // The database has already been locked, just show the quick unlock screen if appropriate
{ TryStartQuickUnlock();
LockAndClose();
}
break; break;
case KeePass.ExitForceLock: case KeePass.ExitForceLock:
SetEditText(Resource.Id.password, ""); App.Kp2a.LockDatabase(false);
UnloadDatabase();
break; break;
case KeePass.ExitForceLockAndChangeDb: case KeePass.ExitForceLockAndChangeDb:
UnloadDatabase(); case KeePass.ExitChangeDb: // What's the difference between this and ExitForceLockAndChangeDb?
Finish(); case KeePass.ExitNormal: // Returned to this screen using the Back key, treat as exiting the database
break; App.Kp2a.LockDatabase(false, Finish);
case KeePass.ExitChangeDb:
LockAndClose();
break; break;
case KeePass.ExitCloseAfterTaskComplete: case KeePass.ExitCloseAfterTaskComplete:
SetResult(KeePass.ExitCloseAfterTaskComplete); SetResult(KeePass.ExitCloseAfterTaskComplete);
Finish(); Finish();
break; break;
case KeePass.ExitQuickUnlock: case KeePass.ExitQuickUnlock:
App.Kp2a.GetDb().Locked = false; App.Kp2a.UnlockDatabase();
LaunchNextActivity(); LaunchNextActivity();
break; break;
case KeePass.ExitReloadDb: case KeePass.ExitReloadDb:
@ -256,7 +195,6 @@ namespace keepass2android
SetEditText(Resource.Id.pass_keyfile, kcpKeyfile.Path); SetEditText(Resource.Id.pass_keyfile, kcpKeyfile.Path);
} }
} }
UnloadDatabase();
break; break;
case Result.Ok: case Result.Ok:
if (requestCode == Intents.RequestCodeFileBrowseForKeyfile) { if (requestCode == Intents.RequestCodeFileBrowseForKeyfile) {
@ -277,6 +215,17 @@ namespace keepass2android
} }
protected override void OnDestroy()
{
base.OnDestroy();
if (!App.Kp2a.QuickUnlockEnabled)
{
// We're exiting (probably task-killed), so stop the service, if it's still running - don't want it hanging around with an icon shown.
StopService(new Intent(this, typeof(Keepass2AndroidService)));
}
}
internal AppTask AppTask; internal AppTask AppTask;
protected override void OnCreate(Bundle savedInstanceState) protected override void OnCreate(Bundle savedInstanceState)
@ -335,9 +284,6 @@ namespace keepass2android
} }
} }
// Create task to kick off file loading while the user enters the password
var loadDbTask = new Task<MemoryStream>(LoadDbFile);
AppTask = AppTask.GetTaskInOnCreate(savedInstanceState, Intent); AppTask = AppTask.GetTaskInOnCreate(savedInstanceState, Intent);
SetContentView(Resource.Layout.password); SetContentView(Resource.Layout.password);
@ -360,18 +306,13 @@ namespace keepass2android
return; return;
} }
// Clear before we load
UnloadDatabase();
// Clear the shutdown flag
App.Kp2a.ClearShutdown();
CheckBox cbQuickUnlock = (CheckBox)FindViewById(Resource.Id.enable_quickunlock); CheckBox cbQuickUnlock = (CheckBox)FindViewById(Resource.Id.enable_quickunlock);
App.Kp2a.GetDb().QuickUnlockEnabled = cbQuickUnlock.Checked; App.Kp2a.SetQuickUnlockEnabled(cbQuickUnlock.Checked);
App.Kp2a.GetDb().QuickUnlockKeyLength = int.Parse(_prefs.GetString(GetString(Resource.String.QuickUnlockLength_key), GetString(Resource.String.QuickUnlockLength_default)));
Handler handler = new Handler(); Handler handler = new Handler();
LoadDb task = new LoadDb(App.Kp2a, _ioConnection, loadDbTask.Result, pass, key, new AfterLoad(handler, this)); var stream = _loadDbTask.Result;
_loadDbTask = null; // prevent accidental re-use
LoadDb task = new LoadDb(App.Kp2a, _ioConnection, stream, pass, key, new AfterLoad(handler, this));
ProgressTask pt = new ProgressTask(App.Kp2a, this, task); ProgressTask pt = new ProgressTask(App.Kp2a, this, task);
pt.Run(); pt.Run();
}; };
@ -445,13 +386,19 @@ namespace keepass2android
}; };
RetrieveSettings(); RetrieveSettings();
}
loadDbTask.Start(); protected override void OnStart()
{
base.OnStart();
// Create task to kick off file loading while the user enters the password
_loadDbTask = Task.Factory.StartNew<MemoryStream>(LoadDbFile);
} }
private MemoryStream LoadDbFile() private MemoryStream LoadDbFile()
{ {
System.Diagnostics.Debug.WriteLine("LoadDbFile Started"); Kp2aLog.Log("Pre-loading database file starting");
var fileStorage = App.Kp2a.GetFileStorage(_ioConnection); var fileStorage = App.Kp2a.GetFileStorage(_ioConnection);
var stream = fileStorage.OpenFileForRead(_ioConnection); var stream = fileStorage.OpenFileForRead(_ioConnection);
@ -463,7 +410,6 @@ namespace keepass2android
if (stream.CanSeek) if (stream.CanSeek)
{ {
capacity = (int)stream.Length; capacity = (int)stream.Length;
System.Diagnostics.Debug.WriteLine("LoadDbFile, data size: " + capacity);
} }
memoryStream = new MemoryStream(capacity); memoryStream = new MemoryStream(capacity);
MemUtil.CopyStream(stream, memoryStream); MemUtil.CopyStream(stream, memoryStream);
@ -471,7 +417,7 @@ namespace keepass2android
memoryStream.Seek(0, System.IO.SeekOrigin.Begin); memoryStream.Seek(0, System.IO.SeekOrigin.Begin);
} }
System.Diagnostics.Debug.WriteLine("LoadDbFile Done"); Kp2aLog.Log("Pre-loading database file completed");
return memoryStream; return memoryStream;
} }
@ -485,22 +431,13 @@ namespace keepass2android
protected override void OnResume() { protected override void OnResume() {
base.OnResume(); base.OnResume();
// If the application was shutdown make sure to clear the password field, if it
// was saved in the instance state
if (App.Kp2a.IsShutdown()) {
LockDatabase();
}
// Clear the shutdown flag
App.Kp2a.ClearShutdown();
if (_startedWithActivityResult) if (_startedWithActivityResult)
return; return;
if (App.Kp2a.GetDb().Loaded && (App.Kp2a.GetDb().Ioc != null) if (App.Kp2a.GetDb().Loaded && (App.Kp2a.GetDb().Ioc != null)
&& (_ioConnection != null) && (App.Kp2a.GetDb().Ioc.GetDisplayName() == _ioConnection.GetDisplayName())) && (_ioConnection != null) && (App.Kp2a.GetDb().Ioc.GetDisplayName() == _ioConnection.GetDisplayName()))
{ {
if (App.Kp2a.GetDb().Locked == false) if (App.Kp2a.QuickLocked == false)
{ {
LaunchNextActivity(); LaunchNextActivity();
} }
@ -596,7 +533,8 @@ namespace keepass2android
public override void Run() { public override void Run() {
if ( Success ) { if ( Success ) {
_act.StartQuickUnlockForegroundService(); _act.SetEditText(Resource.Id.password, "");
_act.LaunchNextActivity(); _act.LaunchNextActivity();
} else { } else {
DisplayMessage(_act); DisplayMessage(_act);

View File

@ -61,7 +61,7 @@ namespace keepass2android
TextView txtLabel = (TextView)FindViewById(Resource.Id.QuickUnlock_label); TextView txtLabel = (TextView)FindViewById(Resource.Id.QuickUnlock_label);
int quickUnlockLength = App.Kp2a.GetDb().QuickUnlockKeyLength; int quickUnlockLength = App.Kp2a.QuickUnlockKeyLength;
txtLabel.Text = GetString(Resource.String.QuickUnlock_label, new Java.Lang.Object[]{quickUnlockLength}); txtLabel.Text = GetString(Resource.String.QuickUnlock_label, new Java.Lang.Object[]{quickUnlockLength});

View File

@ -1,29 +1,24 @@
#pragma warning disable 1591 #pragma warning disable 1591
//------------------------------------------------------------------------------ //------------------------------------------------------------------------------
// <auto-generated> // <auto-generated>
// Dieser Code wurde von einem Tool generiert. // This code was generated by a tool.
// Laufzeitversion:4.0.30319.18051 // Runtime Version:4.0.30319.2012
// //
// Änderungen an dieser Datei können falsches Verhalten verursachen und gehen verloren, wenn // Changes to this file may cause incorrect behavior and will be lost if
// der Code erneut generiert wird. // the code is regenerated.
// </auto-generated> // </auto-generated>
//------------------------------------------------------------------------------ //------------------------------------------------------------------------------
[assembly: global::Android.Runtime.ResourceDesignerAttribute("keepass2android.Resource", IsApplication=true)] [assembly: Android.Runtime.ResourceDesignerAttribute("keepass2android.Resource", IsApplication=true)]
namespace keepass2android namespace keepass2android
{ {
[System.CodeDom.Compiler.GeneratedCodeAttribute("Xamarin.Android.Build.Tasks", "1.0.0.0")] [System.CodeDom.Compiler.GeneratedCodeAttribute("Novell.MonoDroid.Build.Tasks", "1.0.0.0")]
public partial class Resource public partial class Resource
{ {
static Resource()
{
global::Android.Runtime.ResourceIdManager.UpdateIdValues();
}
public static void UpdateIdValues() public static void UpdateIdValues()
{ {
KeePassLib2Android.Resource.String.library_name = keepass2android.Resource.String.library_name; KeePassLib2Android.Resource.String.library_name = keepass2android.Resource.String.library_name;
@ -44,11 +39,6 @@ namespace keepass2android
// aapt resource value: 0x7f040003 // aapt resource value: 0x7f040003
public const int anim_leave_back = 2130968579; public const int anim_leave_back = 2130968579;
static Animation()
{
global::Android.Runtime.ResourceIdManager.UpdateIdValues();
}
private Animation() private Animation()
{ {
} }
@ -72,11 +62,6 @@ namespace keepass2android
// aapt resource value: 0x7f0a0001 // aapt resource value: 0x7f0a0001
public const int list_size_values = 2131361793; public const int list_size_values = 2131361793;
static Array()
{
global::Android.Runtime.ResourceIdManager.UpdateIdValues();
}
private Array() private Array()
{ {
} }
@ -85,11 +70,6 @@ namespace keepass2android
public partial class Attribute public partial class Attribute
{ {
static Attribute()
{
global::Android.Runtime.ResourceIdManager.UpdateIdValues();
}
private Attribute() private Attribute()
{ {
} }
@ -104,6 +84,9 @@ namespace keepass2android
// aapt resource value: 0x7f090008 // aapt resource value: 0x7f090008
public const int OpenKp2aKeyboardAutomatically_default = 2131296264; public const int OpenKp2aKeyboardAutomatically_default = 2131296264;
// aapt resource value: 0x7f090009
public const int ShowUnlockedNotification_default = 2131296265;
// aapt resource value: 0x7f090005 // aapt resource value: 0x7f090005
public const int ShowUsernameInList_default = 2131296261; public const int ShowUsernameInList_default = 2131296261;
@ -125,11 +108,6 @@ namespace keepass2android
// aapt resource value: 0x7f090002 // aapt resource value: 0x7f090002
public const int sort_default = 2131296258; public const int sort_default = 2131296258;
static Boolean()
{
global::Android.Runtime.ResourceIdManager.UpdateIdValues();
}
private Boolean() private Boolean()
{ {
} }
@ -180,11 +158,6 @@ namespace keepass2android
// aapt resource value: 0x7f06000c // aapt resource value: 0x7f06000c
public const int light_gray = 2131099660; public const int light_gray = 2131099660;
static Color()
{
global::Android.Runtime.ResourceIdManager.UpdateIdValues();
}
private Color() private Color()
{ {
} }
@ -202,11 +175,6 @@ namespace keepass2android
// aapt resource value: 0x7f070000 // aapt resource value: 0x7f070000
public const int key_height = 2131165184; public const int key_height = 2131165184;
static Dimension()
{
global::Android.Runtime.ResourceIdManager.UpdateIdValues();
}
private Dimension() private Dimension()
{ {
} }
@ -480,75 +448,76 @@ namespace keepass2android
public const int ic_launcher_offline = 2130837591; public const int ic_launcher_offline = 2130837591;
// aapt resource value: 0x7f020058 // aapt resource value: 0x7f020058
public const int ic_menu_add_field_holo_light = 2130837592; public const int ic_launcher_red = 2130837592;
// aapt resource value: 0x7f020059 // aapt resource value: 0x7f020059
public const int ic_menu_remove_field_holo_light = 2130837593; public const int ic_menu_add_field_holo_light = 2130837593;
// aapt resource value: 0x7f02005a // aapt resource value: 0x7f02005a
public const int ic_menu_view = 2130837594; public const int ic_menu_remove_field_holo_light = 2130837594;
// aapt resource value: 0x7f02005b // aapt resource value: 0x7f02005b
public const int location_web_site = 2130837595; public const int ic_menu_view = 2130837595;
// aapt resource value: 0x7f02005c // aapt resource value: 0x7f02005c
public const int navigation_accept = 2130837596; public const int ic_unlocked_gray = 2130837596;
// aapt resource value: 0x7f02005d // aapt resource value: 0x7f02005d
public const int navigation_accept_dark = 2130837597; public const int location_web_site = 2130837597;
// aapt resource value: 0x7f02005e // aapt resource value: 0x7f02005e
public const int navigation_cancel = 2130837598; public const int navigation_accept = 2130837598;
// aapt resource value: 0x7f02005f // aapt resource value: 0x7f02005f
public const int navigation_previous_item = 2130837599; public const int navigation_accept_dark = 2130837599;
// aapt resource value: 0x7f020060 // aapt resource value: 0x7f020060
public const int navigation_previous_item_dark = 2130837600; public const int navigation_cancel = 2130837600;
// aapt resource value: 0x7f020061 // aapt resource value: 0x7f020061
public const int notify = 2130837601; public const int navigation_previous_item = 2130837601;
// aapt resource value: 0x7f020062 // aapt resource value: 0x7f020062
public const int notify_keyboard = 2130837602; public const int navigation_previous_item_dark = 2130837602;
// aapt resource value: 0x7f020063 // aapt resource value: 0x7f020063
public const int RedButton = 2130837603; public const int notify = 2130837603;
// aapt resource value: 0x7f020064 // aapt resource value: 0x7f020064
public const int section_header = 2130837604; public const int notify_keyboard = 2130837604;
// aapt resource value: 0x7f020065 // aapt resource value: 0x7f020065
public const int sym_keyboard = 2130837605; public const int RedButton = 2130837605;
// aapt resource value: 0x7f020066 // aapt resource value: 0x7f020066
public const int sym_keyboard_delete = 2130837606; public const int section_header = 2130837606;
// aapt resource value: 0x7f020067 // aapt resource value: 0x7f020067
public const int sym_keyboard_done = 2130837607; public const int sym_keyboard = 2130837607;
// aapt resource value: 0x7f020068 // aapt resource value: 0x7f020068
public const int sym_keyboard_kp2a = 2130837608; public const int sym_keyboard_delete = 2130837608;
// aapt resource value: 0x7f020069 // aapt resource value: 0x7f020069
public const int sym_keyboard_return = 2130837609; public const int sym_keyboard_done = 2130837609;
// aapt resource value: 0x7f02006a // aapt resource value: 0x7f02006a
public const int sym_keyboard_search = 2130837610; public const int sym_keyboard_kp2a = 2130837610;
// aapt resource value: 0x7f02006b // aapt resource value: 0x7f02006b
public const int sym_keyboard_shift = 2130837611; public const int sym_keyboard_return = 2130837611;
// aapt resource value: 0x7f02006c // aapt resource value: 0x7f02006c
public const int sym_keyboard_space = 2130837612; public const int sym_keyboard_search = 2130837612;
// aapt resource value: 0x7f02006d // aapt resource value: 0x7f02006d
public const int YellowButton = 2130837613; public const int sym_keyboard_shift = 2130837613;
static Drawable() // aapt resource value: 0x7f02006e
{ public const int sym_keyboard_space = 2130837614;
global::Android.Runtime.ResourceIdManager.UpdateIdValues();
} // aapt resource value: 0x7f02006f
public const int YellowButton = 2130837615;
private Drawable() private Drawable()
{ {
@ -1074,11 +1043,6 @@ namespace keepass2android
// aapt resource value: 0x7f0d0002 // aapt resource value: 0x7f0d0002
public const int version_title = 2131558402; public const int version_title = 2131558402;
static Id()
{
global::Android.Runtime.ResourceIdManager.UpdateIdValues();
}
private Id() private Id()
{ {
} }
@ -1201,11 +1165,6 @@ namespace keepass2android
// aapt resource value: 0x7f030025 // aapt resource value: 0x7f030025
public const int url_credentials = 2130903077; public const int url_credentials = 2130903077;
static Layout()
{
global::Android.Runtime.ResourceIdManager.UpdateIdValues();
}
private Layout() private Layout()
{ {
} }
@ -1229,11 +1188,6 @@ namespace keepass2android
// aapt resource value: 0x7f0c0004 // aapt resource value: 0x7f0c0004
public const int password = 2131492868; public const int password = 2131492868;
static Menu()
{
global::Android.Runtime.ResourceIdManager.UpdateIdValues();
}
private Menu() private Menu()
{ {
} }
@ -1245,53 +1199,53 @@ namespace keepass2android
// aapt resource value: 0x7f080034 // aapt resource value: 0x7f080034
public const int AboutText = 2131230772; public const int AboutText = 2131230772;
// aapt resource value: 0x7f080123
public const int AddingEntry = 2131231011;
// aapt resource value: 0x7f080124 // aapt resource value: 0x7f080124
public const int AddingGroup = 2131231012; public const int AddingEntry = 2131231012;
// aapt resource value: 0x7f080119 // aapt resource value: 0x7f080125
public const int AskDeletePermanentlyEntry = 2131231001; public const int AddingGroup = 2131231013;
// aapt resource value: 0x7f08011a // aapt resource value: 0x7f08011a
public const int AskDeletePermanentlyGroup = 2131231002; public const int AskDeletePermanentlyEntry = 2131231002;
// aapt resource value: 0x7f08011b // aapt resource value: 0x7f08011b
public const int AskDeletePermanently_title = 2131231003; public const int AskDeletePermanentlyGroup = 2131231003;
// aapt resource value: 0x7f08011e
public const int AskDiscardChanges = 2131231006;
// aapt resource value: 0x7f08011f
public const int AskDiscardChanges_title = 2131231007;
// aapt resource value: 0x7f080113
public const int AskOverwriteBinary = 2131230995;
// aapt resource value: 0x7f080116
public const int AskOverwriteBinary_no = 2131230998;
// aapt resource value: 0x7f080114
public const int AskOverwriteBinary_title = 2131230996;
// aapt resource value: 0x7f080115
public const int AskOverwriteBinary_yes = 2131230997;
// aapt resource value: 0x7f08011d
public const int AskReloadFile = 2131231005;
// aapt resource value: 0x7f08011c // aapt resource value: 0x7f08011c
public const int AskReloadFile_title = 2131231004; public const int AskDeletePermanently_title = 2131231004;
// aapt resource value: 0x7f08011f
public const int AskDiscardChanges = 2131231007;
// aapt resource value: 0x7f080120
public const int AskDiscardChanges_title = 2131231008;
// aapt resource value: 0x7f080114
public const int AskOverwriteBinary = 2131230996;
// aapt resource value: 0x7f080117 // aapt resource value: 0x7f080117
public const int AttachFailed = 2131230999; public const int AskOverwriteBinary_no = 2131230999;
// aapt resource value: 0x7f080022 // aapt resource value: 0x7f080115
public const int BinaryDirectory_default = 2131230754; public const int AskOverwriteBinary_title = 2131230997;
// aapt resource value: 0x7f080116
public const int AskOverwriteBinary_yes = 2131230998;
// aapt resource value: 0x7f08011e
public const int AskReloadFile = 2131231006;
// aapt resource value: 0x7f08011d
public const int AskReloadFile_title = 2131231005;
// aapt resource value: 0x7f080118
public const int AttachFailed = 2131231000;
// aapt resource value: 0x7f080021 // aapt resource value: 0x7f080021
public const int BinaryDirectory_key = 2131230753; public const int BinaryDirectory_default = 2131230753;
// aapt resource value: 0x7f080020
public const int BinaryDirectory_key = 2131230752;
// aapt resource value: 0x7f0800f8 // aapt resource value: 0x7f0800f8
public const int BinaryDirectory_summary = 2131230968; public const int BinaryDirectory_summary = 2131230968;
@ -1299,62 +1253,62 @@ namespace keepass2android
// aapt resource value: 0x7f0800f7 // aapt resource value: 0x7f0800f7
public const int BinaryDirectory_title = 2131230967; public const int BinaryDirectory_title = 2131230967;
// aapt resource value: 0x7f08013b
public const int ChangeLog = 2131231035;
// aapt resource value: 0x7f08013a // aapt resource value: 0x7f08013a
public const int ChangeLog = 2131231034; public const int ChangeLog_0_7 = 2131231034;
// aapt resource value: 0x7f080139
public const int ChangeLog_0_7 = 2131231033;
// aapt resource value: 0x7f080137
public const int ChangeLog_0_8 = 2131231031;
// aapt resource value: 0x7f080136
public const int ChangeLog_0_8_1 = 2131231030;
// aapt resource value: 0x7f080135
public const int ChangeLog_0_8_2 = 2131231029;
// aapt resource value: 0x7f080134
public const int ChangeLog_0_8_3 = 2131231028;
// aapt resource value: 0x7f080133
public const int ChangeLog_0_8_4 = 2131231027;
// aapt resource value: 0x7f080138 // aapt resource value: 0x7f080138
public const int ChangeLog_keptDonate = 2131231032; public const int ChangeLog_0_8 = 2131231032;
// aapt resource value: 0x7f080132 // aapt resource value: 0x7f080137
public const int ChangeLog_title = 2131231026; public const int ChangeLog_0_8_1 = 2131231031;
// aapt resource value: 0x7f080029 // aapt resource value: 0x7f080136
public const int CheckForFileChangesOnSave_key = 2131230761; public const int ChangeLog_0_8_2 = 2131231030;
// aapt resource value: 0x7f080135
public const int ChangeLog_0_8_3 = 2131231029;
// aapt resource value: 0x7f080134
public const int ChangeLog_0_8_4 = 2131231028;
// aapt resource value: 0x7f080139
public const int ChangeLog_keptDonate = 2131231033;
// aapt resource value: 0x7f080133
public const int ChangeLog_title = 2131231027;
// aapt resource value: 0x7f080028
public const int CheckForFileChangesOnSave_key = 2131230760;
// aapt resource value: 0x7f08010d
public const int CheckForFileChangesOnSave_summary = 2131230989;
// aapt resource value: 0x7f08010c // aapt resource value: 0x7f08010c
public const int CheckForFileChangesOnSave_summary = 2131230988; public const int CheckForFileChangesOnSave_title = 2131230988;
// aapt resource value: 0x7f08010b // aapt resource value: 0x7f08012d
public const int CheckForFileChangesOnSave_title = 2131230987; public const int CheckingTargetFileForChanges = 2131231021;
// aapt resource value: 0x7f08012c
public const int CheckingTargetFileForChanges = 2131231020;
// aapt resource value: 0x7f080049 // aapt resource value: 0x7f080049
public const int ClearClipboard = 2131230793; public const int ClearClipboard = 2131230793;
// aapt resource value: 0x7f08002d // aapt resource value: 0x7f08002c
public const int CopyToClipboardNotification_key = 2131230765; public const int CopyToClipboardNotification_key = 2131230764;
// aapt resource value: 0x7f080035 // aapt resource value: 0x7f080035
public const int CreditsText = 2131230773; public const int CreditsText = 2131230773;
// aapt resource value: 0x7f08012a // aapt resource value: 0x7f08012b
public const int DecodingDatabase = 2131231018; public const int DecodingDatabase = 2131231019;
// aapt resource value: 0x7f080125
public const int DeletingEntry = 2131231013;
// aapt resource value: 0x7f080126 // aapt resource value: 0x7f080126
public const int DeletingGroup = 2131231014; public const int DeletingEntry = 2131231014;
// aapt resource value: 0x7f080127
public const int DeletingGroup = 2131231015;
// aapt resource value: 0x7f080082 // aapt resource value: 0x7f080082
public const int FileNotFound = 2131230850; public const int FileNotFound = 2131230850;
@ -1362,35 +1316,35 @@ namespace keepass2android
// aapt resource value: 0x7f080095 // aapt resource value: 0x7f080095
public const int InvalidPassword = 2131230869; public const int InvalidPassword = 2131230869;
// aapt resource value: 0x7f080027 // aapt resource value: 0x7f080026
public const int LastInfoVersionCode_key = 2131230759; public const int LastInfoVersionCode_key = 2131230758;
// aapt resource value: 0x7f08002a // aapt resource value: 0x7f080029
public const int MarketURL = 2131230762; public const int MarketURL = 2131230761;
// aapt resource value: 0x7f08009f // aapt resource value: 0x7f08009f
public const int MaskedPassword = 2131230879; public const int MaskedPassword = 2131230879;
// aapt resource value: 0x7f08012e // aapt resource value: 0x7f08012f
public const int MessageSyncQuestion = 2131231022; public const int MessageSyncQuestion = 2131231023;
// aapt resource value: 0x7f080131 // aapt resource value: 0x7f080132
public const int NoOverwrite = 2131231025; public const int NoOverwrite = 2131231026;
// aapt resource value: 0x7f08002f // aapt resource value: 0x7f08002e
public const int OpenKp2aKeyboardAutomatically_key = 2131230767; public const int OpenKp2aKeyboardAutomatically_key = 2131230766;
// aapt resource value: 0x7f080113
public const int OpenKp2aKeyboardAutomatically_summary = 2131230995;
// aapt resource value: 0x7f080112 // aapt resource value: 0x7f080112
public const int OpenKp2aKeyboardAutomatically_summary = 2131230994; public const int OpenKp2aKeyboardAutomatically_title = 2131230994;
// aapt resource value: 0x7f080111 // aapt resource value: 0x7f08012c
public const int OpenKp2aKeyboardAutomatically_title = 2131230993; public const int ParsingDatabase = 2131231020;
// aapt resource value: 0x7f08012b // aapt resource value: 0x7f080022
public const int ParsingDatabase = 2131231019; public const int QuickUnlockDefaultEnabled_key = 2131230754;
// aapt resource value: 0x7f080023
public const int QuickUnlockDefaultEnabled_key = 2131230755;
// aapt resource value: 0x7f0800f3 // aapt resource value: 0x7f0800f3
public const int QuickUnlockDefaultEnabled_summary = 2131230963; public const int QuickUnlockDefaultEnabled_summary = 2131230963;
@ -1398,11 +1352,11 @@ namespace keepass2android
// aapt resource value: 0x7f0800f2 // aapt resource value: 0x7f0800f2
public const int QuickUnlockDefaultEnabled_title = 2131230962; public const int QuickUnlockDefaultEnabled_title = 2131230962;
// aapt resource value: 0x7f080025
public const int QuickUnlockLength_default = 2131230757;
// aapt resource value: 0x7f080024 // aapt resource value: 0x7f080024
public const int QuickUnlockLength_key = 2131230756; public const int QuickUnlockLength_default = 2131230756;
// aapt resource value: 0x7f080023
public const int QuickUnlockLength_key = 2131230755;
// aapt resource value: 0x7f0800f5 // aapt resource value: 0x7f0800f5
public const int QuickUnlockLength_summary = 2131230965; public const int QuickUnlockLength_summary = 2131230965;
@ -1422,8 +1376,8 @@ namespace keepass2android
// aapt resource value: 0x7f0800f1 // aapt resource value: 0x7f0800f1
public const int QuickUnlock_lockButton = 2131230961; public const int QuickUnlock_lockButton = 2131230961;
// aapt resource value: 0x7f080118 // aapt resource value: 0x7f080119
public const int RecycleBin = 2131231000; public const int RecycleBin = 2131231001;
// aapt resource value: 0x7f0800fc // aapt resource value: 0x7f0800fc
public const int SaveAttachmentDialog_open = 2131230972; public const int SaveAttachmentDialog_open = 2131230972;
@ -1443,23 +1397,26 @@ namespace keepass2android
// aapt resource value: 0x7f0800fd // aapt resource value: 0x7f0800fd
public const int SaveAttachment_doneMessage = 2131230973; public const int SaveAttachment_doneMessage = 2131230973;
// aapt resource value: 0x7f080127 // aapt resource value: 0x7f080128
public const int SettingPassword = 2131231015; public const int SettingPassword = 2131231016;
// aapt resource value: 0x7f08010e
public const int ShowCopyToClipboardNotification_summary = 2131230990;
// aapt resource value: 0x7f08010d
public const int ShowCopyToClipboardNotification_title = 2131230989;
// aapt resource value: 0x7f080110
public const int ShowKp2aKeyboardNotification_summary = 2131230992;
// aapt resource value: 0x7f08010f // aapt resource value: 0x7f08010f
public const int ShowKp2aKeyboardNotification_title = 2131230991; public const int ShowCopyToClipboardNotification_summary = 2131230991;
// aapt resource value: 0x7f08001e // aapt resource value: 0x7f08010e
public const int ShowUsernameInList_key = 2131230750; public const int ShowCopyToClipboardNotification_title = 2131230990;
// aapt resource value: 0x7f080111
public const int ShowKp2aKeyboardNotification_summary = 2131230993;
// aapt resource value: 0x7f080110
public const int ShowKp2aKeyboardNotification_title = 2131230992;
// aapt resource value: 0x7f080031
public const int ShowUnlockedNotification_key = 2131230769;
// aapt resource value: 0x7f08001d
public const int ShowUsernameInList_key = 2131230749;
// aapt resource value: 0x7f0800e3 // aapt resource value: 0x7f0800e3
public const int ShowUsernameInList_summary = 2131230947; public const int ShowUsernameInList_summary = 2131230947;
@ -1467,14 +1424,14 @@ namespace keepass2android
// aapt resource value: 0x7f0800e2 // aapt resource value: 0x7f0800e2
public const int ShowUsernameInList_title = 2131230946; public const int ShowUsernameInList_title = 2131230946;
// aapt resource value: 0x7f08002b // aapt resource value: 0x7f08002a
public const int SuggestionsURL = 2131230763; public const int SuggestionsURL = 2131230762;
// aapt resource value: 0x7f08012f // aapt resource value: 0x7f080130
public const int SynchronizingDatabase = 2131231023; public const int SynchronizingDatabase = 2131231024;
// aapt resource value: 0x7f08001d // aapt resource value: 0x7f08001c
public const int TanExpiresOnUse_key = 2131230749; public const int TanExpiresOnUse_key = 2131230748;
// aapt resource value: 0x7f0800e1 // aapt resource value: 0x7f0800e1
public const int TanExpiresOnUse_summary = 2131230945; public const int TanExpiresOnUse_summary = 2131230945;
@ -1482,35 +1439,35 @@ namespace keepass2android
// aapt resource value: 0x7f0800e0 // aapt resource value: 0x7f0800e0
public const int TanExpiresOnUse_title = 2131230944; public const int TanExpiresOnUse_title = 2131230944;
// aapt resource value: 0x7f08012d // aapt resource value: 0x7f08012e
public const int TitleSyncQuestion = 2131231021; public const int TitleSyncQuestion = 2131231022;
// aapt resource value: 0x7f08012a
public const int TransformingKey = 2131231018;
// aapt resource value: 0x7f08002b
public const int TranslationURL = 2131230763;
// aapt resource value: 0x7f080129 // aapt resource value: 0x7f080129
public const int TransformingKey = 2131231017; public const int UndoingChanges = 2131231017;
// aapt resource value: 0x7f08002c // aapt resource value: 0x7f080025
public const int TranslationURL = 2131230764; public const int UsageCount_key = 2131230757;
// aapt resource value: 0x7f080128 // aapt resource value: 0x7f080027
public const int UndoingChanges = 2131231016; public const int UseFileTransactions_key = 2131230759;
// aapt resource value: 0x7f080026 // aapt resource value: 0x7f08010b
public const int UsageCount_key = 2131230758; public const int UseFileTransactions_summary = 2131230987;
// aapt resource value: 0x7f080028
public const int UseFileTransactions_key = 2131230760;
// aapt resource value: 0x7f08010a // aapt resource value: 0x7f08010a
public const int UseFileTransactions_summary = 2131230986; public const int UseFileTransactions_title = 2131230986;
// aapt resource value: 0x7f080109 // aapt resource value: 0x7f08002d
public const int UseFileTransactions_title = 2131230985; public const int UseKp2aKeyboard_key = 2131230765;
// aapt resource value: 0x7f08002e // aapt resource value: 0x7f080131
public const int UseKp2aKeyboard_key = 2131230766; public const int YesSynchronize = 2131231025;
// aapt resource value: 0x7f080130
public const int YesSynchronize = 2131231024;
// aapt resource value: 0x7f080032 // aapt resource value: 0x7f080032
public const int about_feedback = 2131230770; public const int about_feedback = 2131230770;
@ -1596,8 +1553,8 @@ namespace keepass2android
// aapt resource value: 0x7f08004a // aapt resource value: 0x7f08004a
public const int clipboard_timeout = 2131230794; public const int clipboard_timeout = 2131230794;
// aapt resource value: 0x7f080030 // aapt resource value: 0x7f08002f
public const int clipboard_timeout_default = 2131230768; public const int clipboard_timeout_default = 2131230767;
// aapt resource value: 0x7f080014 // aapt resource value: 0x7f080014
public const int clipboard_timeout_key = 2131230740; public const int clipboard_timeout_key = 2131230740;
@ -1614,8 +1571,8 @@ namespace keepass2android
// aapt resource value: 0x7f080051 // aapt resource value: 0x7f080051
public const int creating_db_key = 2131230801; public const int creating_db_key = 2131230801;
// aapt resource value: 0x7f080108 // aapt resource value: 0x7f080109
public const int credentials_dialog_title = 2131230984; public const int credentials_dialog_title = 2131230985;
// aapt resource value: 0x7f080052 // aapt resource value: 0x7f080052
public const int current_group = 2131230802; public const int current_group = 2131230802;
@ -1629,11 +1586,14 @@ namespace keepass2android
// aapt resource value: 0x7f080107 // aapt resource value: 0x7f080107
public const int database_loaded_quickunlock_enabled = 2131230983; public const int database_loaded_quickunlock_enabled = 2131230983;
// aapt resource value: 0x7f080108
public const int database_loaded_unlocked = 2131230984;
// aapt resource value: 0x7f0800ca // aapt resource value: 0x7f0800ca
public const int database_name = 2131230922; public const int database_name = 2131230922;
// aapt resource value: 0x7f080020 // aapt resource value: 0x7f08001f
public const int database_name_key = 2131230752; public const int database_name_key = 2131230751;
// aapt resource value: 0x7f080015 // aapt resource value: 0x7f080015
public const int db_key = 2131230741; public const int db_key = 2131230741;
@ -1653,8 +1613,8 @@ namespace keepass2android
// aapt resource value: 0x7f0800cb // aapt resource value: 0x7f0800cb
public const int default_username = 2131230923; public const int default_username = 2131230923;
// aapt resource value: 0x7f08001f // aapt resource value: 0x7f08001e
public const int default_username_key = 2131230751; public const int default_username_key = 2131230750;
// aapt resource value: 0x7f080106 // aapt resource value: 0x7f080106
public const int delete_extra_string = 2131230982; public const int delete_extra_string = 2131230982;
@ -1914,8 +1874,8 @@ namespace keepass2android
// aapt resource value: 0x7f080009 // aapt resource value: 0x7f080009
public const int library_name = 2131230729; public const int library_name = 2131230729;
// aapt resource value: 0x7f080031 // aapt resource value: 0x7f080030
public const int list_size_default = 2131230769; public const int list_size_default = 2131230768;
// aapt resource value: 0x7f08001a // aapt resource value: 0x7f08001a
public const int list_size_key = 2131230746; public const int list_size_key = 2131230746;
@ -2058,8 +2018,8 @@ namespace keepass2android
// aapt resource value: 0x7f080103 // aapt resource value: 0x7f080103
public const int protection = 2131230979; public const int protection = 2131230979;
// aapt resource value: 0x7f080121 // aapt resource value: 0x7f080122
public const int rate_app = 2131231009; public const int rate_app = 2131231010;
// aapt resource value: 0x7f0800df // aapt resource value: 0x7f0800df
public const int regular_expression = 2131230943; public const int regular_expression = 2131230943;
@ -2151,14 +2111,11 @@ namespace keepass2android
// aapt resource value: 0x7f0800ea // aapt resource value: 0x7f0800ea
public const int start_open_url = 2131230954; public const int start_open_url = 2131230954;
// aapt resource value: 0x7f080120 // aapt resource value: 0x7f080121
public const int suggest_improvements = 2131231008; public const int suggest_improvements = 2131231009;
// aapt resource value: 0x7f08001c // aapt resource value: 0x7f080123
public const int timeout_key = 2131230748; public const int translate_app = 2131231011;
// aapt resource value: 0x7f080122
public const int translate_app = 2131231010;
// aapt resource value: 0x7f0800d8 // aapt resource value: 0x7f0800d8
public const int twofish = 2131230936; public const int twofish = 2131230936;
@ -2187,11 +2144,6 @@ namespace keepass2android
// aapt resource value: 0x7f0800b6 // aapt resource value: 0x7f0800b6
public const int yes = 2131230902; public const int yes = 2131230902;
static String()
{
global::Android.Runtime.ResourceIdManager.UpdateIdValues();
}
private String() private String()
{ {
} }
@ -2281,11 +2233,6 @@ namespace keepass2android
// aapt resource value: 0x7f0b000d // aapt resource value: 0x7f0b000d
public const int WhiteOnDarkSmall = 2131427341; public const int WhiteOnDarkSmall = 2131427341;
static Style()
{
global::Android.Runtime.ResourceIdManager.UpdateIdValues();
}
private Style() private Style()
{ {
} }
@ -2315,11 +2262,6 @@ namespace keepass2android
// aapt resource value: 0x7f050006 // aapt resource value: 0x7f050006
public const int symbols_shift = 2131034118; public const int symbols_shift = 2131034118;
static Xml()
{
global::Android.Runtime.ResourceIdManager.UpdateIdValues();
}
private Xml() private Xml()
{ {
} }

View File

@ -39,7 +39,6 @@
<string name="omitbackup_key">omitbackup</string> <string name="omitbackup_key">omitbackup</string>
<string name="list_size_key">list_size</string> <string name="list_size_key">list_size</string>
<string name="sort_key">sort_key</string> <string name="sort_key">sort_key</string>
<string name="timeout_key">timeout_key</string>
<string name="TanExpiresOnUse_key">TanExpiresOnUse_key</string> <string name="TanExpiresOnUse_key">TanExpiresOnUse_key</string>
<string name="ShowUsernameInList_key">ShowUsernameInList_key</string> <string name="ShowUsernameInList_key">ShowUsernameInList_key</string>
<string name="default_username_key">defaultUsername</string> <string name="default_username_key">defaultUsername</string>
@ -89,4 +88,8 @@
<item>20</item> <item>20</item>
<item>28</item> <item>28</item>
</string-array> </string-array>
<string name="ShowUnlockedNotification_key">ShowUnlockedNotification</string>
<bool name="ShowUnlockedNotification_default">true</bool>
</resources> </resources>

View File

@ -215,7 +215,8 @@
<string name="add_binary">Add file attachment...</string> <string name="add_binary">Add file attachment...</string>
<string name="add_extra_string">Add additional string</string> <string name="add_extra_string">Add additional string</string>
<string name="delete_extra_string">Delete additional string</string> <string name="delete_extra_string">Delete additional string</string>
<string name="database_loaded_quickunlock_enabled">Database loaded, QuickUnlock enabled.</string> <string name="database_loaded_quickunlock_enabled">%1$s: Locked. QuickUnlock enabled.</string>
<string name="database_loaded_unlocked">%1$s: Unlocked. Tap to lock.</string>
<string name="credentials_dialog_title">Enter server credentials</string> <string name="credentials_dialog_title">Enter server credentials</string>
<string name="UseFileTransactions_title">File transactions</string> <string name="UseFileTransactions_title">File transactions</string>
<string name="UseFileTransactions_summary">Use file transactions for writing databases</string> <string name="UseFileTransactions_summary">Use file transactions for writing databases</string>

View File

@ -71,7 +71,7 @@ namespace keepass2android
Finish(); Finish();
} }
else if (_db.Locked) else if (App.Kp2a.QuickLocked)
{ {
PasswordActivity.Launch(this,_db.Ioc, AppTask); PasswordActivity.Launch(this,_db.Ioc, AppTask);
Finish(); Finish();

View File

@ -16,10 +16,13 @@ This file is part of Keepass2Android, Copyright 2013 Philipp Crocoll. This file
*/ */
using System; using System;
using System.Collections.Generic;
using System.IO;
using Android.App; using Android.App;
using Android.Content; using Android.Content;
using Android.OS; using Android.OS;
using Android.Runtime; using Android.Runtime;
using KeePassLib.Keys;
using KeePassLib.Serialization; using KeePassLib.Serialization;
using Android.Preferences; using Android.Preferences;
using keepass2android.Io; using keepass2android.Io;
@ -58,26 +61,139 @@ namespace keepass2android
/// Main implementation of the IKp2aApp interface for usage in the real app. /// Main implementation of the IKp2aApp interface for usage in the real app.
/// </summary> /// </summary>
public class Kp2aApp: IKp2aApp public class Kp2aApp: IKp2aApp
{ {
public bool IsShutdown() public void LockDatabase(bool allowQuickUnlock = true)
{ {
return _shutdown; if (!allowQuickUnlock)
{
QuickUnlockEnabled = false;
}
Application.Context.SendBroadcast(new Intent(Intents.LockDatabase));
}
/// <summary>
/// Locks the database, then runs the specified action once the locking has completed.
/// </summary>
/// <param name="allowQuickUnlock"></param>
/// <param name="runAfterLocked"></param>
internal void LockDatabase(bool allowQuickUnlock, Action runAfterLocked)
{
_actionsToRunAfterLock.Enqueue(runAfterLocked);
LockDatabase(allowQuickUnlock);
}
private readonly Queue<Action> _actionsToRunAfterLock = new Queue<Action>();
/// <summary>
/// Do not call this directly, instead call LockDatabase
/// </summary>
internal void LockDatabaseInternal(Keepass2AndroidService service)
{
if (_db.Loaded)
{
if (QuickUnlockEnabled &&
_db.KpDatabase.MasterKey.ContainsType(typeof(KcpPassword)) &&
!((KcpPassword)App.Kp2a.GetDb().KpDatabase.MasterKey.GetUserKey(typeof(KcpPassword))).Password.IsEmpty)
{
if (!QuickLocked)
{
Kp2aLog.Log("QuickLocking database");
QuickLocked = true;
// Start the service to show the quicklock icon
var ctx = Application.Context;
ctx.StartService(new Intent(ctx, typeof(Keepass2AndroidService)));
}
else
{
Kp2aLog.Log("Database already QuickLocked");
}
}
else
{
Kp2aLog.Log("Locking database");
// Couldn't quick-lock, so unload database instead
_db.Clear();
QuickLocked = false;
}
}
else
{
Kp2aLog.Log("Database not loaded, couldn't lock");
}
while (_actionsToRunAfterLock.Count > 0)
{
var action = _actionsToRunAfterLock.Dequeue();
action();
}
} }
public void SetShutdown() public void LoadDatabase(IOConnectionInfo ioConnectionInfo, MemoryStream memoryStream, string password, string keyFile, ProgressDialogStatusLogger statusLogger)
{ {
Kp2aLog.Log("set shutdown"); _db.LoadData(this, ioConnectionInfo, memoryStream, password, keyFile, statusLogger);
_shutdown = true;
}
public void ClearShutdown() var ctx = Application.Context;
{ ctx.StartService(new Intent(ctx, typeof(Keepass2AndroidService)));
Kp2aLog.Log("clear shutdown"); }
_shutdown = false;
}
private Database _db; public void UnlockDatabase(Action runAfterUnlocked)
private bool _shutdown; {
_actionsToRunAfterUnlock.Enqueue(runAfterUnlocked);
Application.Context.SendBroadcast(new Intent(Intents.UnlockDatabase));
}
private readonly Queue<Action> _actionsToRunAfterUnlock = new Queue<Action>();
/// <summary>
/// Do not call this directly, instead call UnlockDatabase
/// </summary>
internal void UnlockDatabaseInternal(Keepass2AndroidService service)
{
QuickLocked = false;
while (_actionsToRunAfterUnlock.Count > 0)
{
var action = _actionsToRunAfterUnlock.Dequeue();
action();
}
}
public bool DatabaseIsUnlocked
{
get { return _db.Loaded && !QuickLocked; }
}
#region QuickUnlock
public void SetQuickUnlockEnabled(bool enabled)
{
if (enabled)
{
//Set KeyLength of QuickUnlock at time of enabling.
//This is important to not allow an attacker to set the length to 1 when QuickUnlock is started already.
var ctx = Application.Context;
var prefs = PreferenceManager.GetDefaultSharedPreferences(ctx);
QuickUnlockKeyLength = Math.Max(1, int.Parse(prefs.GetString(ctx.GetString(Resource.String.QuickUnlockLength_key), ctx.GetString(Resource.String.QuickUnlockLength_default))));
}
QuickUnlockEnabled = enabled;
}
public bool QuickUnlockEnabled { get; private set; }
public int QuickUnlockKeyLength { get; private set; }
/// <summary>
/// If true, the database must be regarded as locked and not exposed to the user.
/// </summary>
public bool QuickLocked { get; private set; }
#endregion
private Database _db;
/// <summary> /// <summary>
/// See comments to EntryEditActivityState. /// See comments to EntryEditActivityState.
@ -216,7 +332,7 @@ namespace keepass2android
public RealProgressDialog(Context ctx) public RealProgressDialog(Context ctx)
{ {
this._pd = new ProgressDialog(ctx); _pd = new ProgressDialog(ctx);
} }
public void SetTitle(string title) public void SetTitle(string title)

View File

@ -24,6 +24,8 @@ namespace keepass2android
/// </summary> /// </summary>
public class Intents { public class Intents {
public const String Timeout = "keepass2android.timeout"; public const String Timeout = "keepass2android.timeout";
public const String LockDatabase = "keepass2android.lock_database";
public const String UnlockDatabase = "keepass2android.unlock_database";
public const String CopyUsername = "keepass2android.copy_username"; public const String CopyUsername = "keepass2android.copy_username";
public const String CopyPassword = "keepass2android.copy_password"; public const String CopyPassword = "keepass2android.copy_password";

View File

@ -86,6 +86,7 @@
<Compile Include="fileselect\FileSelectActivity.cs" /> <Compile Include="fileselect\FileSelectActivity.cs" />
<Compile Include="fileselect\FileDbHelper.cs" /> <Compile Include="fileselect\FileDbHelper.cs" />
<Compile Include="search\SearchProvider.cs" /> <Compile Include="search\SearchProvider.cs" />
<Compile Include="services\Keepass2AndroidService.cs" />
<Compile Include="Utils\Util.cs" /> <Compile Include="Utils\Util.cs" />
<Compile Include="intents\Intents.cs" /> <Compile Include="intents\Intents.cs" />
<Compile Include="fileselect\BrowserDialog.cs" /> <Compile Include="fileselect\BrowserDialog.cs" />
@ -127,12 +128,10 @@
<Compile Include="compat\EditorCompat.cs" /> <Compile Include="compat\EditorCompat.cs" />
<Compile Include="compat\ActivityCompat.cs" /> <Compile Include="compat\ActivityCompat.cs" />
<Compile Include="ShareUrlResults.cs" /> <Compile Include="ShareUrlResults.cs" />
<Compile Include="services\TimeoutService.cs" />
<Compile Include="services\CopyToClipboardService.cs" /> <Compile Include="services\CopyToClipboardService.cs" />
<Compile Include="search\SearchActivity.cs" /> <Compile Include="search\SearchActivity.cs" />
<Compile Include="QuickUnlock.cs" /> <Compile Include="QuickUnlock.cs" />
<Compile Include="LifecycleDebugActivity.cs" /> <Compile Include="LifecycleDebugActivity.cs" />
<Compile Include="services\QuickUnlockForegroundService.cs" />
<Compile Include="AssemblyInfo.cs" /> <Compile Include="AssemblyInfo.cs" />
<Compile Include="views\FileSelectButtons.cs" /> <Compile Include="views\FileSelectButtons.cs" />
<Compile Include="EntryEditActivityState.cs" /> <Compile Include="EntryEditActivityState.cs" />
@ -703,4 +702,25 @@
<SubType>Designer</SubType> <SubType>Designer</SubType>
</AndroidResource> </AndroidResource>
</ItemGroup> </ItemGroup>
<ItemGroup>
<AndroidResource Include="Resources\drawable\ic_unlocked_gray.png" />
</ItemGroup>
<ItemGroup>
<AndroidResource Include="Resources\drawable-v11\ic_unlocked_gray.png" />
</ItemGroup>
<ItemGroup>
<AndroidResource Include="Resources\drawable-mdpi\ic_launcher_red.png" />
</ItemGroup>
<ItemGroup>
<AndroidResource Include="Resources\drawable-xhdpi\ic_launcher_red.png" />
</ItemGroup>
<ItemGroup>
<AndroidResource Include="Resources\drawable-xxhdpi\ic_launcher_red.png" />
</ItemGroup>
<ItemGroup>
<AndroidResource Include="Resources\drawable-hdpi\ic_launcher_red.png" />
</ItemGroup>
<ItemGroup>
<AndroidResource Include="Resources\drawable\ic_launcher_red.png" />
</ItemGroup>
</Project> </Project>

View File

@ -70,7 +70,7 @@ namespace keepass2android.search
public override Android.Database.ICursor Query(Android.Net.Uri uri, string[] projection, string selection, string[] selectionArgs, string sortOrder) public override Android.Database.ICursor Query(Android.Net.Uri uri, string[] projection, string selection, string[] selectionArgs, string sortOrder)
{ {
if (_db.Open) // Can't show suggestions if the database is locked! if (App.Kp2a.DatabaseIsUnlocked) // Can't show suggestions if the database is locked!
{ {
switch ((UriMatches)UriMatcher.Match(uri)) switch ((UriMatches)UriMatcher.Match(uri))
{ {

View File

@ -56,11 +56,9 @@ namespace keepass2android.search
private void ProcessIntent(Intent intent) private void ProcessIntent(Intent intent)
{ {
_db = App.Kp2a.GetDb();
// Likely the app has been killed exit the activity // Likely the app has been killed exit the activity
if ( ! _db.Open ) { if (!App.Kp2a.DatabaseIsUnlocked)
{
Finish(); Finish();
} }

View File

@ -57,7 +57,7 @@ namespace keepass2android
CopyToClipboardBroadcastReceiver _copyToClipBroadcastReceiver; CopyToClipboardBroadcastReceiver _copyToClipBroadcastReceiver;
NotificationDeletedBroadcastReceiver _notificationDeletedBroadcastReceiver; NotificationDeletedBroadcastReceiver _notificationDeletedBroadcastReceiver;
StopOnLockBroadcastReceiver _stopOnLockBroadcastReceiver;
public CopyToClipboardService() public CopyToClipboardService()
{ {
@ -74,6 +74,11 @@ namespace keepass2android
{ {
Kp2aLog.Log("Received intent to provide access to entry"); Kp2aLog.Log("Received intent to provide access to entry");
_stopOnLockBroadcastReceiver = new StopOnLockBroadcastReceiver(this);
IntentFilter filter = new IntentFilter();
filter.AddAction(Intents.LockDatabase);
RegisterReceiver(_stopOnLockBroadcastReceiver, filter);
String uuidBytes = intent.GetStringExtra(EntryActivity.KeyEntry); String uuidBytes = intent.GetStringExtra(EntryActivity.KeyEntry);
bool closeAfterCreate = intent.GetBooleanExtra(EntryActivity.KeyCloseAfterCreate, false); bool closeAfterCreate = intent.GetBooleanExtra(EntryActivity.KeyCloseAfterCreate, false);
@ -99,12 +104,23 @@ namespace keepass2android
return StartCommandResult.RedeliverIntent; return StartCommandResult.RedeliverIntent;
} }
private void OnLockDatabase()
{
Kp2aLog.Log("Stopping clipboard service due to database lock");
StopSelf();
}
private NotificationManager _notificationManager; private NotificationManager _notificationManager;
private int _numElementsToWaitFor; private int _numElementsToWaitFor;
public override void OnDestroy() public override void OnDestroy()
{ {
// These members might never get initialized if the app timed out // These members might never get initialized if the app timed out
if (_stopOnLockBroadcastReceiver != null)
{
UnregisterReceiver(_stopOnLockBroadcastReceiver);
}
if (_copyToClipBroadcastReceiver != null) if (_copyToClipBroadcastReceiver != null)
{ {
UnregisterReceiver(_copyToClipBroadcastReceiver); UnregisterReceiver(_copyToClipBroadcastReceiver);
@ -358,7 +374,24 @@ namespace keepass2android
return notify; return notify;
} }
private class StopOnLockBroadcastReceiver : BroadcastReceiver
{
readonly CopyToClipboardService _service;
public StopOnLockBroadcastReceiver(CopyToClipboardService service)
{
_service = service;
}
public override void OnReceive(Context context, Intent intent)
{
switch (intent.Action)
{
case Intents.LockDatabase:
_service.OnLockDatabase();
break;
}
}
}
class CopyToClipboardBroadcastReceiver: BroadcastReceiver class CopyToClipboardBroadcastReceiver: BroadcastReceiver
{ {
@ -429,7 +462,7 @@ namespace keepass2android
if (currentIme == kp2aIme) if (currentIme == kp2aIme)
{ {
imeManager.ToggleSoftInput(ShowFlags.Forced, HideSoftInputFlags.None); imeManager.ToggleSoftInput(ShowSoftInputFlags.Forced, HideSoftInputFlags.None);
} }
else else
{ {

View File

@ -1,79 +0,0 @@
/*
This file is part of Keepass2Android, Copyright 2013 Philipp Crocoll.
Keepass2Android is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 2 of the License, or
(at your option) any later version.
Keepass2Android is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with Keepass2Android. If not, see <http://www.gnu.org/licenses/>.
*/
using Android.App;
using Android.Content;
using Android.OS;
using Android.Support.V4.App;
using Android.Graphics;
namespace keepass2android
{
/// <summary>
/// This service is started as soon as a Database with QuickUnlock enabled is opened.
/// Its only purpose is to be a foreground service which prevents the App from being killed (in most situations)
/// </summary>
[Service]
public class QuickUnlockForegroundService : Service
{
public override IBinder OnBind(Intent intent)
{
return null;
}
const int QuickUnlockForegroundServiceId = 238787;
public override StartCommandResult OnStartCommand(Intent intent, StartCommandFlags flags, int startId)
{
Kp2aLog.Log("Starting QuickUnlockForegroundService");
//create notification item
NotificationCompat.Builder mBuilder =
new NotificationCompat.Builder(this)
.SetSmallIcon(Resource.Drawable.ic_launcher_gray)
.SetLargeIcon(BitmapFactory.DecodeResource(Resources, AppNames.LauncherIcon))
.SetContentTitle(GetText(Resource.String.app_name))
.SetContentText(GetText(Resource.String.database_loaded_quickunlock_enabled));
Intent startKp2aIntent = new Intent(this, typeof(KeePass));
startKp2aIntent.SetAction(Intent.ActionMain);
startKp2aIntent.AddCategory(Intent.CategoryLauncher);
PendingIntent startKp2APendingIntent =
PendingIntent.GetActivity(this, 0, startKp2aIntent, PendingIntentFlags.UpdateCurrent);
mBuilder.SetContentIntent(startKp2APendingIntent);
StartForeground(QuickUnlockForegroundServiceId , mBuilder.Build());
return StartCommandResult.NotSticky;
}
public override void OnCreate()
{
base.OnCreate();
Kp2aLog.Log("Creating QuickUnlockForegroundService");
}
public override void OnDestroy()
{
base.OnDestroy();
Kp2aLog.Log("Destroying QuickUnlockForegroundService");
}
}
}

View File

@ -1,129 +0,0 @@
/*
This file is part of Keepass2Android, Copyright 2013 Philipp Crocoll. This file is based on Keepassdroid, Copyright Brian Pellin.
Keepass2Android is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 2 of the License, or
(at your option) any later version.
Keepass2Android is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with Keepass2Android. If not, see <http://www.gnu.org/licenses/>.
*/
using System;
using Android.App;
using Android.Content;
using Android.OS;
using Android.Runtime;
using Android.Util;
namespace keepass2android
{
/// <summary>
/// Manages timeout to lock the database after some idle time
/// </summary>
[Service]
public class TimeoutService : Service {
private const String Tag = "KeePass2Android Timer";
private BroadcastReceiver _intentReceiver;
public TimeoutService (IntPtr javaReference, JniHandleOwnership transfer)
: base(javaReference, transfer)
{
_binder = new TimeoutBinder(this);
}
public TimeoutService()
{
_binder = new TimeoutBinder(this);
}
public override void OnCreate() {
base.OnCreate();
_intentReceiver = new MyBroadcastReceiver(this);
IntentFilter filter = new IntentFilter();
filter.AddAction(Intents.Timeout);
RegisterReceiver(_intentReceiver, filter);
}
public override void OnStart(Intent intent, int startId) {
base.OnStart(intent, startId);
Log.Debug(Tag, "Timeout service started");
}
private void Timeout() {
Log.Debug(Tag, "Timeout");
App.Kp2a.SetShutdown();
NotificationManager nm = (NotificationManager) GetSystemService(NotificationService);
nm.CancelAll();
StopService(new Intent(this, typeof(CopyToClipboardService)));
StopSelf();
}
public override void OnDestroy() {
base.OnDestroy();
Log.Debug(Tag, "Timeout service stopped");
UnregisterReceiver(_intentReceiver);
}
public class TimeoutBinder : Binder
{
readonly TimeoutService _service;
public TimeoutBinder(TimeoutService service)
{
_service = service;
}
public TimeoutService GetService() {
return _service;
}
}
private readonly IBinder _binder;
public override IBinder OnBind(Intent intent) {
return _binder;
}
[BroadcastReceiver]
public class MyBroadcastReceiver: BroadcastReceiver
{
public MyBroadcastReceiver()
{
//dummy constructor required for MonoForAndroid, not called.
throw new NotImplementedException();
}
readonly TimeoutService _timeoutService;
public MyBroadcastReceiver (TimeoutService timeoutService)
{
_timeoutService = timeoutService;
}
public override void OnReceive(Context context, Intent intent) {
String action = intent.Action;
if ( action.Equals(Intents.Timeout) ) {
_timeoutService.Timeout();
}
}
}
}
}

View File

@ -56,13 +56,12 @@ namespace keepass2android
} }
}; };
Database db = App.Kp2a.GetDb(); if (App.Kp2a.DatabaseIsUnlocked)
if ( db.Open ) { {
Database db = App.Kp2a.GetDb();
Preference rounds = FindPreference(GetString(Resource.String.rounds_key)); Preference rounds = FindPreference(GetString(Resource.String.rounds_key));
rounds.PreferenceChange += (sender, e) => rounds.PreferenceChange += (sender, e) => setRounds(db, e.Preference);
{
setRounds(App.Kp2a.GetDb(), e.Preference);
};
Preference defaultUser = FindPreference(GetString(Resource.String.default_username_key)); Preference defaultUser = FindPreference(GetString(Resource.String.default_username_key));
((EditTextPreference)defaultUser).EditText.Text = db.KpDatabase.DefaultUserName; ((EditTextPreference)defaultUser).EditText.Text = db.KpDatabase.DefaultUserName;

View File

@ -44,8 +44,6 @@ namespace keepass2android
public static void Start(Context ctx) public static void Start(Context ctx)
{ {
ISharedPreferences prefs = PreferenceManager.GetDefaultSharedPreferences(ctx); ISharedPreferences prefs = PreferenceManager.GetDefaultSharedPreferences(ctx);
String sTimeout = prefs.GetString(ctx.GetString(Resource.String.app_timeout_key), ctx.GetString(Resource.String.clipboard_timeout_default)); String sTimeout = prefs.GetString(ctx.GetString(Resource.String.app_timeout_key), ctx.GetString(Resource.String.clipboard_timeout_default));
@ -61,8 +59,6 @@ namespace keepass2android
return; return;
} }
ctx.StartService(new Intent(ctx, typeof(TimeoutService)));
long triggerTime = Java.Lang.JavaSystem.CurrentTimeMillis() + timeout; long triggerTime = Java.Lang.JavaSystem.CurrentTimeMillis() + timeout;
AlarmManager am = (AlarmManager)ctx.GetSystemService(Context.AlarmService); AlarmManager am = (AlarmManager)ctx.GetSystemService(Context.AlarmService);
@ -76,69 +72,25 @@ namespace keepass2android
Kp2aLog.Log("Timeout cancel"); Kp2aLog.Log("Timeout cancel");
am.Cancel(BuildIntent(ctx)); am.Cancel(BuildIntent(ctx));
ctx.StopService(new Intent(ctx, typeof(TimeoutService)));
} }
} }
public static void Pause(Activity act) { public static void Pause(Activity act)
// Record timeout time in case timeout service is killed {
long time = Java.Lang.JavaSystem.CurrentTimeMillis(); if ( App.Kp2a.DatabaseIsUnlocked )
{
ISharedPreferences prefs = PreferenceManager.GetDefaultSharedPreferences(act);
ISharedPreferencesEditor edit = prefs.Edit();
edit.PutLong(act.GetString(Resource.String.timeout_key), time);
Kp2aLog.Log("Pause: start at " + time);
EditorCompat.Apply(edit);
if ( App.Kp2a.GetDb().Open ) {
Timeout.Start(act); Timeout.Start(act);
} }
} }
public static void Resume(Activity act) { public static void Resume(Activity act)
if ( App.Kp2a.GetDb().Loaded ) { {
if ( App.Kp2a.GetDb().Loaded )
{
Timeout.Cancel(act); Timeout.Cancel(act);
} }
// Check whether the timeout has expired
long curTime = Java.Lang.JavaSystem.CurrentTimeMillis();
ISharedPreferences prefs = PreferenceManager.GetDefaultSharedPreferences(act);
long timeoutStart = prefs.GetLong(act.GetString(Resource.String.timeout_key), -1);
Kp2aLog.Log("timeoutStart=" + timeoutStart);
// The timeout never started
if (timeoutStart == -1) {
return;
}
String sTimeout = prefs.GetString(act.GetString(Resource.String.app_timeout_key), act.GetString(Resource.String.clipboard_timeout_default));
long timeout;
if (!long.TryParse(sTimeout, out timeout) || (timeout == -1))
{
Kp2aLog.Log("exit with timeout=" + timeout + "/"+sTimeout);
// We are set to never timeout
return;
}
long diff = curTime - timeoutStart;
if (diff >= timeout)
{
// We have timed out
Kp2aLog.Log("Shutdown due to " + diff + ">=" + timeout);
App.Kp2a.SetShutdown();
}
else
{
Kp2aLog.Log("No shutdown due to " + diff + "<" + timeout);
}
} }
static bool IocChanged(IOConnectionInfo ioc, IOConnectionInfo other) static bool IocChanged(IOConnectionInfo ioc, IOConnectionInfo other)
@ -148,11 +100,10 @@ namespace keepass2android
} }
public static bool CheckShutdown(Activity act, IOConnectionInfo ioc) { public static bool CheckShutdown(Activity act, IOConnectionInfo ioc) {
if (( App.Kp2a.GetDb().Loaded && (App.Kp2a.IsShutdown() || App.Kp2a.GetDb().Locked) ) if (( !App.Kp2a.DatabaseIsUnlocked )
|| (IocChanged(ioc, App.Kp2a.GetDb().Ioc))) //file was changed from ActionSend-Intent || (IocChanged(ioc, App.Kp2a.GetDb().Ioc))) //file was changed from ActionSend-Intent
{ {
act.SetResult(KeePass.ExitLock); App.Kp2a.LockDatabase();
act.Finish();
return true; return true;
} }
return false; return false;