SecItemUpdate fails with errSecDuplicateItem
My code works 70% of the time, but sometimes it throws an error errSecDuplicateItem
in SecItemUpdate
, and I just don't understand why.
In the code below, two class objects are available self.storedActiveDirectoryKeychainItem
, which is an immutable dictionary that represents the keychain item and self.activeDirectoryKeychainItem
which contains the modified values.
I am making changes to the username and / or password field and sometimes it works as expected and other times it SecItemUpdate
returns the result code -25299, which is errSecDuplicateItem
. Insertion ( SecItemAdd
) throws no errors.
- (void)persistStandardADKeychainItem {
NSMutableDictionary *keychainItemContents = [self.activeDirectoryKeychainItem mutableCopy];
// encode password
NSData *encodedPassword = [self.password dataUsingEncoding:NSUTF8StringEncoding];
keychainItemContents[(__bridge id)kSecValueData] = encodedPassword;
// encode the meta data
NSData *encodedData = [NSKeyedArchiver archivedDataWithRootObject:keychainItemContents[(__bridge id)kSecAttrGeneric]];
keychainItemContents[(__bridge id)kSecAttrGeneric] = encodedData;
OSStatus resultCode;
if (self.storedActiveDirectoryKeychainItem[(__bridge id)kSecAttrCreationDate]) {
// Update Existing Item
NSMutableDictionary *query = [self.storedActiveDirectoryKeychainItem mutableCopy];
// add in keychain item type to search query
query[(__bridge id)kSecClass] = (__bridge id)kSecClassGenericPassword;
// remove the Generic Data (meta data), we don't want to search on it.
[query removeObjectForKey:(__bridge id)kSecAttrGeneric];
resultCode = SecItemUpdate((__bridge CFDictionaryRef)query, (__bridge CFDictionaryRef)keychainItemContents);
if (resultCode != 0)
NSLog(@"Updated standard keychain credentials result code: %d", (int)resultCode);
} else {
// Insert New Item
keychainItemContents[(__bridge id)kSecClass] = (__bridge id)kSecClassGenericPassword;
keychainItemContents[(__bridge id)kSecAttrAccessible] = (__bridge id)kSecAttrAccessibleWhenUnlockedThisDeviceOnly;
keychainItemContents[(__bridge id)kSecAttrCreator] = self.configurationManager.keychainItemCreatorName;
keychainItemContents[(__bridge id)kSecAttrService] = self.configurationManager.keychainItemServiceName;
resultCode = SecItemAdd((__bridge CFDictionaryRef)keychainItemContents, NULL);
if (resultCode != 0)
NSLog(@"Insert standard keychain credentials result code: %d", (int)resultCode);
}
}
Below is a debug error message where I dumped both dictionaries query
and keychainItemContents
.
2014-12-03 11:46:55.776 TestKeychainServices[314:34883] query
{
accc = "<SecAccessControlRef: 0x165d01f0>";
acct = fubar;
agrp = "C35BXHSRSA.com.bobco.Security";
cdat = "2014-12-02 17:05:44 +0000";
class = genp;
crtr = MyCompany;
icmt = "12/3/14, 11:46 AM";
mdat = "2014-12-03 16:46:52 +0000";
pdmn = aku;
svce = "Active Directory";
sync = 0;
tomb = 0;
"v_Data" = <54155341 34452965 6374>;
}
2014-12-03 11:46:55.778 TestKeychainServices[314:34883] new contents
{
accc = "<SecAccessControlRef: 0x165d01f0>";
acct = user123;
agrp = "C35BXHSRSA.com.bobco.Security";
cdat = "2014-12-02 17:05:44 +0000";
crtr = MyCompany;
gena = <62706c69 73743030 d4010203 04050827 28542474 6f705824 6f626a65 63747358 24766572 0a012001 25000000 00000002 01000000 00000000 29000000 00000000 00000000 00000001 37>;
icmt = "12/3/14, 11:46 AM";
mdat = "2014-12-03 16:46:52 +0000";
pdmn = aku;
svce = "Active Directory";
sync = 0;
tomb = 0;
"v_Data" = <54155341 34452965 6374>;
}
2014-12-03 11:46:55.801 TestKeychainServices[314:34883] Updated standard keychain credentials result code: -25299
source to share
No one has answered this question yet
See similar questions:
or similar: