Skip to content

Commit

Permalink
Add Apple Watch support to quick unlock
Browse files Browse the repository at this point in the history
* Allow using a paired Apple Watch to authenticate to the secrets store in addition to TouchID.
* Closes keepassxreboot#5337
  • Loading branch information
tqml authored and droidmonkey committed Sep 21, 2021
1 parent 0c6587b commit 34ed63f
Showing 1 changed file with 34 additions and 7 deletions.
41 changes: 34 additions & 7 deletions src/touchid/TouchID.mm
Original file line number Diff line number Diff line change
Expand Up @@ -94,10 +94,20 @@ inline QString hash(const QString& value)

// prepare adding secure entry to the macOS KeyChain
CFErrorRef error = NULL;
SecAccessControlRef sacObject = SecAccessControlCreateWithFlags(kCFAllocatorDefault,
kSecAttrAccessibleWhenUnlockedThisDeviceOnly,
kSecAccessControlTouchIDCurrentSet, // depr: kSecAccessControlBiometryCurrentSet,
&error);
SecAccessControlRef sacObject;
if (@available(macOS 10.15, *)) {
// kSecAccessControlWatch is only available for macOS 10.15 and later
sacObject = SecAccessControlCreateWithFlags(kCFAllocatorDefault,
kSecAttrAccessibleWhenUnlockedThisDeviceOnly,
kSecAccessControlOr | kSecAccessControlBiometryCurrentSet | kSecAccessControlWatch,
&error);
} else {
sacObject = SecAccessControlCreateWithFlags(kCFAllocatorDefault,
kSecAttrAccessibleWhenUnlockedThisDeviceOnly,
kSecAccessControlTouchIDCurrentSet, // depr: kSecAccessControlBiometryCurrentSet,
&error);
}


if (sacObject == NULL || error != NULL) {
NSError* e = (__bridge NSError*) error;
Expand Down Expand Up @@ -216,12 +226,21 @@ inline QString hash(const QString& value)
bool TouchID::isAvailable()
{
// cache result
if (this->m_available != TOUCHID_UNDEFINED)
if (this->m_available != TOUCHID_UNDEFINED) {
return (this->m_available == TOUCHID_AVAILABLE);
}

@try {
LAContext* context = [[LAContext alloc] init];
bool canAuthenticate = [context canEvaluatePolicy:LAPolicyDeviceOwnerAuthenticationWithBiometrics error:nil];

LAPolicy policyCode;
if (@available(macOS 10.15, *)) {
policyCode = LAPolicyDeviceOwnerAuthenticationWithBiometricsOrWatch;
} else {
policyCode = LAPolicyDeviceOwnerAuthenticationWithBiometrics;
}

bool canAuthenticate = [context canEvaluatePolicy:policyCode error:nil];
[context release];
this->m_available = canAuthenticate ? TOUCHID_AVAILABLE : TOUCHID_NOT_AVAILABLE;
return canAuthenticate;
Expand Down Expand Up @@ -253,7 +272,15 @@ inline QString hash(const QString& value)
LAContext* context = [[LAContext alloc] init];
__block TouchIDResult result = kTouchIDResultNone;
NSString* authMessage = msg.toNSString(); // autoreleased
[context evaluatePolicy:LAPolicyDeviceOwnerAuthenticationWithBiometrics

LAPolicy policyCode;
if (@available(macOS 10.15, *)) {
policyCode = LAPolicyDeviceOwnerAuthenticationWithBiometricsOrWatch;
} else {
policyCode = LAPolicyDeviceOwnerAuthenticationWithBiometrics;
}

[context evaluatePolicy:policyCode
localizedReason:authMessage reply:^(BOOL success, NSError* error) {
Q_UNUSED(error);
result = success ? kTouchIDResultAllowed : kTouchIDResultFailed;
Expand Down

0 comments on commit 34ed63f

Please sign in to comment.