Skip to content

Commit

Permalink
Refactor YubiKey key to avoid deadlock
Browse files Browse the repository at this point in the history
- Add mutex to get m_connectedKeys
- Fix deadlock when the app uses Quick Unlock and the YubiKey is unplugged
  • Loading branch information
w15eacre authored and droidmonkey committed Feb 1, 2025
1 parent 5ee5e49 commit 81fa8d5
Show file tree
Hide file tree
Showing 2 changed files with 15 additions and 3 deletions.
16 changes: 13 additions & 3 deletions src/keys/drivers/YubiKey.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -75,11 +75,19 @@ bool YubiKey::findValidKeys()
{
QMutexLocker lock(&s_interfaceMutex);

findValidKeys(lock);

return !m_usbKeys.isEmpty() || !m_pcscKeys.isEmpty();
}

void YubiKey::findValidKeys(const QMutexLocker& locker)
{
// Check QMutexLocker since version 6.4
Q_UNUSED(locker);

m_connectedKeys = 0;
m_usbKeys = YubiKeyInterfaceUSB::instance()->findValidKeys(m_connectedKeys);
m_pcscKeys = YubiKeyInterfacePCSC::instance()->findValidKeys(m_connectedKeys);

return !m_usbKeys.isEmpty() || !m_pcscKeys.isEmpty();
}

void YubiKey::findValidKeysAsync()
Expand All @@ -98,6 +106,8 @@ YubiKey::KeyMap YubiKey::foundKeys()

int YubiKey::connectedKeys()
{
QMutexLocker lock(&s_interfaceMutex);

return m_connectedKeys;
}

Expand Down Expand Up @@ -171,7 +181,7 @@ YubiKey::challenge(YubiKeySlot slot, const QByteArray& challenge, Botan::secure_

// Make sure we tried to find available keys
if (m_usbKeys.isEmpty() && m_pcscKeys.isEmpty()) {
findValidKeys();
findValidKeys(lock);
}

if (m_usbKeys.contains(slot)) {
Expand Down
2 changes: 2 additions & 0 deletions src/keys/drivers/YubiKey.h
Original file line number Diff line number Diff line change
Expand Up @@ -84,6 +84,8 @@ class YubiKey : public QObject
private:
explicit YubiKey();

void findValidKeys(const QMutexLocker& locker);

static YubiKey* m_instance;

QTimer m_interactionTimer;
Expand Down

0 comments on commit 81fa8d5

Please # to comment.