2012-04-18 11 views
7

Stworzyłem parę kluczy za pomocą SecKeyGeneratePair. Chciałbym teraz przekazać klucz publiczny do serwera, ale nie jestem pewien, jak postępować.iPhone: Jak wyeksportować klucze publiczne SecKeyRef lub NSData zawierające klucze publiczne do formatu PEM?

Mam funkcję getPublicKeyBits (pobraną z Apple CryptoExercise), ale tak naprawdę nie wiem, co zrobić z surowym NSData. Oto funkcja:

- (NSData *)getPublicKeyBits { 
    OSStatus sanityCheck = noErr; 
    NSData* publicKeyBits = nil; 
    NSData* publicTag = [[NSData alloc] initWithBytes:publicKeyIdentifier length:sizeof(publicKeyIdentifier)]; 
    CFDataRef cfresult = NULL; 


    NSMutableDictionary * queryPublicKey = [[NSMutableDictionary alloc] init]; 

    // Set the public key query dictionary. 
    [queryPublicKey setObject:(__bridge id)kSecClassKey forKey:(__bridge id)kSecClass]; 
    [queryPublicKey setObject:publicTag forKey:(__bridge id)kSecAttrApplicationTag]; 
    [queryPublicKey setObject:(__bridge id)kSecAttrKeyTypeRSA forKey:(__bridge id)kSecAttrKeyType]; 
    [queryPublicKey setObject:[NSNumber numberWithBool:YES] forKey:(__bridge id)kSecReturnData]; 

    // Get the key bits. 
    sanityCheck = SecItemCopyMatching((__bridge CFDictionaryRef)queryPublicKey, (CFTypeRef*)&cfresult); 


    if (sanityCheck != noErr) 
    { 
     publicKeyBits = nil; 
    } 
    else 
    { 
     publicKeyBits = (__bridge_transfer NSData *)cfresult; 
    } 

    return publicKeyBits; 
} 

Jak mogę wziąć tego surowego bajt danych i przekształcić go w coś takiego PEM lub innego formatu, że biblioteka kryptograficzna rozumie? Czy powinienem ją kodować64? Czy są jeszcze inne rzeczy, które muszę zrobić?

Jeśli to pomaga, próbuję użyć klucza publicznego z biblioteką M2Crypto dostępną dla języka Python.

+0

Nie, to nie BASE64. Jest to pewna struktura ASN.1 zawierająca 'SEQUENCE' z dwoma elementami' INTEGER'. Podczas gdy drugi element wydaje się zawsze "65537", drugi element wydaje się mieć rozmiar klucza. Ale wciąż nie mam pojęcia, jak pobrać wykładnik i modulo, aby wyeksportować go do innego formatu. – miho

Odpowiedz

2

myślę, że będzie chciał patrzeć na http://www.openssl.org/docs/crypto/pem.html# Być może:

int PEM_write_PrivateKey(FILE *fp, EVP_PKEY *x, const EVP_CIPHER *enc, 
            unsigned char *kstr, int klen, 
            pem_password_cb *cb, void *u); 
+1

Oznaczałoby to włączenie OpenSSL do mojego projektu. Robiłem wszystko z wbudowaną biblioteką "CommonCrypto". W tych połączonych dokumentach jest napisane, że PEM to zasadniczo kodowanie base64 klucza, a następnie zawijanie go liniami nagłówka. Próbowałem tego, ale nie mogłem go uruchomić z 'M2Crypto'. Czy bajty generowane przez funkcję 'getPublicKeyBits' powyżej w poprawnym" formacie "są takie, że mogę je tylko kodować64? Przepraszam, nie wiem zbyt wiele o kryptografii i tych standardach i bibliotekach. –

+0

to jest baza64 wersji DER klucza ... http://www.itu.int/ITU-T/studygroups/com17/languages/X.690-0207.pdf –

+0

Ah, więc wygląda na to, ' getPublicKeyBits' zwraca bity "DER" zakodowane zgodnie z [this] (http://stackoverflow.com/questions/3840005/how-to-find-out-tod-modulus-and-exponent-of-rsa-public-key -on-iphone-cel-c). Więc jeśli zakodowuję base64 i zawijam ciąg znaków do linii nagłówka, powinien działać. Próbowałem tego, ale być może kod, którego użyłem do kodowania base64, było złe. Dzięki za pomoc! Zaznaczę tę odpowiedź jako poprawną, ponieważ była bardzo pomocna. –

1

Ta strona ma kilka cennych wskazówek i przykładowy kod do pakowania danych masz w formacie PEM, dzięki czemu można go wysłać do serwera :

http://blog.wingsofhermes.org/?p=42

nie trzeba całą bibliotekę openssl kompilowany ze źródeł i statycznie połączonego to zrobić. Używam właśnie tej techniki, owijając klucz podstawowy 64 w "----- BEGIN PUBLIC KEY -----" i może być odczytany i użyty przez aplikację Railsową przy użyciu standardowych klas ruby ​​openssl.

Powiązane problemy