2009-07-27 15 views
5

Ich versuche, die Attribute eines Schlüsselbundelements zu erhalten. Dieser Code sollte alle verfügbaren Attribute nachschlagen und dann deren Tags und Inhalte ausdrucken.Attribute von Keychain-Elementen abrufen

Laut the docs sollte ich Tags wie 'cdat' sehen, aber sie sehen nur wie ein Index aus (d. H. Das erste Tag ist 0, das nächste ist 1). Das macht es ziemlich nutzlos, da ich nicht sagen kann, welches Attribut ich suche.

SecItemClass itemClass; 
    SecKeychainItemCopyAttributesAndData(itemRef, NULL, &itemClass, NULL, NULL, NULL); 

    SecKeychainRef keychainRef; 
    SecKeychainItemCopyKeychain(itemRef, &keychainRef); 

    SecKeychainAttributeInfo *attrInfo; 
    SecKeychainAttributeInfoForItemID(keychainRef, itemClass, &attrInfo); 

    SecKeychainAttributeList *attributes; 
    SecKeychainItemCopyAttributesAndData(itemRef, attrInfo, NULL, &attributes, 0, NULL); 

    for (int i = 0; i < attributes->count; i ++) 
    { 
     SecKeychainAttribute attr = attributes->attr[i]; 
     NSLog(@"%08x %@", attr.tag, [NSData dataWithBytes:attr.data length:attr.length]); 
    } 

    SecKeychainFreeAttributeInfo(attrInfo); 
    SecKeychainItemFreeAttributesAndData(attributes, NULL); 
    CFRelease(itemRef); 
    CFRelease(keychainRef); 

Antwort

1

Ich denke, die Dokumentation führt zu ein wenig Verwirrung. Die Zahlen, die ich sehe, scheinen keychain item attribute constants for keys zu sein.

SecKeychainItemCopyAttributesAndData gibt jedoch eine SecKeychainAttributeList-Struktur zurück, die ein Array von SecKeychainAttributes enthält. Von TFD:

Markierung Ein 4-Byte-Attribut-Tag. Siehe "Schlüsselbegriffsattributkonstanten" für gültige Attributtypen.

Die Attributkonstanten (der Nicht-Variante "for keys") sind die 4-char Werte, die ich erwartet habe.

3

Es gibt zwei Dinge, die Sie hier tun sollten. Zunächst müssen Sie „generischen“ itemClasses vor dem Aufruf von SecKeychainAttributeInfoForItemID ...

switch (itemClass) 
{ 
    case kSecInternetPasswordItemClass: 
     itemClass = CSSM_DL_DB_RECORD_INTERNET_PASSWORD; 
     break; 
    case kSecGenericPasswordItemClass: 
     itemClass = CSSM_DL_DB_RECORD_GENERIC_PASSWORD; 
     break; 
    case kSecAppleSharePasswordItemClass: 
     itemClass = CSSM_DL_DB_RECORD_APPLESHARE_PASSWORD; 
     break; 
    default: 
     // No action required 
} 

Zweiter zu handhaben, müssen Sie den attr.tag von einem FourCharCode in eine Zeichenfolge konvertieren, dh

NSLog(@"%c%c%c%c %@", 
    ((char *)&attr.tag)[3], 
    ((char *)&attr.tag)[2], 
    ((char *)&attr.tag)[1], 
    ((char *)&attr.tag)[0], 
    [[[NSString alloc] 
     initWithData:[NSData dataWithBytes:attr.data length:attr.length] 
     encoding:NSUTF8StringEncoding] 
    autorelease]]); 

Beachten Sie, dass ich die Daten auch als String ausgegeben habe - es handelt sich fast immer um UTF8-codierte Daten.

+0

Danke, dass Sie erklären, wie Sie mit den generischen Klassen umgehen können. Die Dokumentation für "SecKeychainAttributeInfoForItemID" lässt viel zu wünschen übrig. –

Verwandte Themen