For an Android app managing cryptographic keys, I want to ensure that the device has had a screen lock set up continuously since the first time the app has been run.
Specifically, the app will only allow using the keys if the device has a secure look configured (which can be checked via KeyguardManager.isDeviceSecure()). But if the user disables their screen lock, someone else could potentially pick it up, re-enable the screen lock and continue to use the app pretending to be the original user. I want to prevent this, but still not require user authentication for every use of the keys (which rules out using Android KeyStore user authentication enforcement)
I currently see two ways to delete the data if the screen lock is disabled, both of which have downsides:
Set up a DeviceAdminReceiver and listen for screen lock changes with onPasswordChanged, invalidating keys if the screen lock is disabled. This is problematic since it requires USES_POLICY_LIMIT_PASSWORD, which will no longer be supported in API level 29.
Create a "canary" KeyStore key with user authentication enforcement and check whether it throws a KeyPermanentlyInvalidatedException when used. This solution feels very hacky, depends on implementation details (e.g. KeyPermanentlyInvalidatedException being thrown before UserNotAuthenticatedException) and is not event-based in the way solution 1 is, which means that the keys will not be deleted immediately after the screen lock is disabled.
Is there a better way to act upon the deactivation of the device screen lock?
Related
I have an app that currently requires a user to provide a PIN code upon opening, or to unlock the app using biometrics such as face recognition or fingerprint identification.
When the app receives a push notification on iOS, it seems quite redundant however to have the user unlock the phone with FaceId and then immediately require the user to do this again to enter the app and view the notification details.
The same would presumably hold true using TouchId or Android fingerprint identification.
Is there a reasonable way that I could detect that the device was biometrically unlocked, and thus skip the redundant pin/biometric check?
Reading through what you've written I had a thought in my mind: why exactly are you pivoting around biometric unlock? For your purposes, I guess, any kind of unlock will do. Give this thread a shot Android - detect phone unlock event, not screen on
Background
Smart Lock feature allows to fully unlock the device under certain conditions, such as GPS location, connected Bluetooth, etc...
The problem
I'd like to make an app that does that, with other special conditions.
Given user's approval, is it possible to completely unlock the lock screen, even if it has a password, so that the user will continue as if he unlocked the device by himself?
What I've found
I know it's probably possible using accessibility service, to mimic user actions of entering the code or drawing the pattern.
There is probably a way to temporarily disable the lock screen, by using keyguard API (written here for example), but as I've read, those are deprecated and might not work on some devices and Android versions. I guess it also requires to have a foreground service for it to continue staying on this state.
The questions
Is there a better way? Is there a way to unlock the device, just like Smart Lock feature?
If so, how?
Is it true the Keyguard API is not recommended? What is there to worry about when using it? Or maybe it's completely safe to use, and can be used to fully unlock?
For example, it's for promotions or events. Therefore I want users not able to leave our app. For iOS, i guess I can make a frame to physically block the main button. But for Android, i don't know how.
This is currently not possible. It is scheduled to be included in the upcoming L release. See Task locking.
"The L Developer Preview introduces a new task locking API that lets you temporarily restrict users from leaving your app or being interrupted by notifications. This could be used, for example, if you are developing an education app to support high stakes assessment requirements on Android. Once your app activates this mode, users will not be able to see notifications, access other apps, or return to the Home screen, until your app exits the mode."
Is there a way to programmatically change the phones screen lock method? For example, changing it to display a pattern, a pin, swipe unlock or none at all.
For example, think of a widget that lets the user toggle between swipe to unlock and pattern lock.
Cyanogenmod has something like this in their profiles, using PROFILE_SERVICE but that does not seem to be in the public API.
Not exactly. Through DevicePolicyManager, you can specify some minimum quality characteristics for a password, and force the user to reset their password to meet those characteristics. However:
The user can always choose something stronger than what you require
This requires that the user configure your app as a device admin
This requires additional permissions
The user is always involved in the password-reset process
I am developing an application where I have to change the screen lock password on a button click,can anybody tell me how can I do this.
If you are talking about the unlock pass word set in the device settings by the user then the answer is you can't.
If an application could change the unlock password/pattern without user interaction then these security features would be mostly useless. A rogue application could in theory lock the user out of their own device if this were possible.
Edit: if your aim is not to change this value without interaction but just to send them to the correct settings page. You might be able to do that some how. You'd want to look into what intents you can use to start the Settings Activities. But if you are developing this application for use by the general public I would strongly recommend you rethink having try to do anything with the users security settings. As a user if an application prompted and then sent me to the security settings page with the intention of having me change something in there I would immediately uninstall it.
Edit 2: I've never seen it until just now so I don't know for sure what they used to achieve that. Since it states that must be android 2.2+ though I would assume they are using the Device Administration APIs The docs seem to indicate that it can "Prompt user to set a new password." Which I would think means that it is just going to start the settings activity for them. It is not actually changing the password value by itself. This whole API is subject to user activation also. So even if you get installed on a device the user must explicitly "activate" your app before it is able to make use of any of the admin APIs
I am sure the only way this is possible is if you signed your APK with the device key. This way it could access API's that are limited to system applications. This isn't possible for a normal app, only one that is baked into a custom ROM or device manufacturer ROM when building Android from source.
I do not exactly understand what you are trying to do. If you wish to change the lock screen password programmatically, and your'e application is A device administration than you can call:
resetPassword method of DevicePolicyManager like this for example:
m_policyManager.resetPassword("bla bla", DevicePolicyManager.PASSWORD_QUALITY_SOMETHING);