- // If we did not get a record from the current keychain or the current
- // keychain did not exist skip to the next keychain in the list.
- if (!gotRecord)
- {
- ++mCurrent;
- mDbCursor = DbCursor();
- continue;
- }
+ // No more keychains to search so we are done.
+ return false;
+ }
+
+ try
+ {
+ // StLock<Mutex> _(gActivationMutex()); // force serialization of cursor creation
+ Keychain &kc = *mCurrent;
+ Mutex* mutex = kc->getKeychainMutex();
+ StLock<Mutex> _(*mutex);
+ (*mCurrent)->database()->activate();
+ mDbCursor = DbCursor((*mCurrent)->database(), *this);
+ }
+ catch(const CommonError &err)
+ {
+ ++mCurrent;
+ }
+ }
+
+ Keychain &kc = *mCurrent;
+ Mutex* mutex = kc->getKeychainMutex();
+ StLock<Mutex> _(*mutex);
+
+ bool gotRecord;
+ try
+ {
+ // Clear out existing attributes first!
+ // (the previous iteration may have left attributes from a different schema)
+ dbAttributes.clear();
+
+ gotRecord = mDbCursor->next(&dbAttributes, NULL, uniqueId);
+ mAllFailed = false;
+ }
+ catch(const CommonError &err)
+ {
+ // Catch the last error we get and move on to the next keychain
+ // This error will be returned when we reach the end of our keychain list
+ // iff all calls to KCCursorImpl::next failed
+ status = err.osStatus();
+ gotRecord = false;
+ dbAttributes.invalidate();
+ }
+ catch(...)
+ {
+ // Catch all other errors
+ status = errSecItemNotFound;
+ gotRecord = false;
+ }