2011-06-23 11 views
6

Znalazłem funkcję EVP_PKEY_copy_parameters, która może skopiować EVP_PKEY. Jednak niektóre dokumenty na temat tej funkcji mówią, że mogą być używane tylko w algorytmach DSA/ECC. Oficjalna dokumentacja (od openssl.org) nie wspomina, czy funkcja może być używana dla RSA EVP_PKEY.Jak skopiować EVP_PKEY, który zawiera klucz RSA?

Kolejna realizacja dla EVP_PKEY (który zawiera klucz RSA) może być w ten sposób:

EVP_PKEY_assign_RSA(RSAPrivateKey_dup(EVP_PKEY_get1_RSA(pkey))); 

Czy macie jakieś sugestie?

Odpowiedz

6

Jeśli nie naprawdę potrzebę duplikat klucza, można po prostu zwiększyć swój licznik odniesień, tak:

CRYPTO_add(&your_evp_pkey->references, 1, CRYPTO_LOCK_EVP_PKEY); 

przeciwnym wypadku podobna (prawie identyczne) podejście do tego, co sugeruje byłby następujący:

int pkey_rsa_dup(EVP_PKEY *dst_pkey, EVP_PKEY *src_key) { 
    // Validate underlying key type - Only allow a RSA key 
    if (src_key->type != EVP_PKEY_RSA) 
     return -1; 

    RSA *rsa = EVP_PKEY_get1_RSA(src_key); // Get the underlying RSA key 
    RSA *dup_rsa = RSAPrivateKey_dup(rsa); // Duplicate the RSA key 
    RSA_free(rsa); // Decrement reference count 

    EVP_PKEY_set1_RSA(dst_pkey, dup_rsa); // Set the underlying RSA key in dst_pkey 
    // EVP_PKEY_set1_RSA also adjusts the other members in dst_pkey 

    return 0; 
} 

referencyjny: Re: How to duplicate an EVP_PKEY -> Jak @ X-Istence mówi poniżej, RSA_dup Metoda sugerowana w tym wątku referencyjnym nie istnieje w OpenSSL (przynajmniej do daty tej aktualizacji).

+0

RSA_dup nie istnieje nigdzie w kodzie źródłowym OpenSSL. Konkretnie w tym samym wątku e-mailowym kontynuacja tego samego plakatu mówi: http://www.mail-archive.com/[email protected]/msg17617.html –

+0

'dst_pkey' przecieki – Orient

+0

@Orient masz rację. Dzięki! Miałem fałszywą/niepotrzebną alokację dla 'dst_pkey'. Podany argument musi odnosić się do wcześniej przydzielonego pkeya. – jweyrich

2

W OpenSSL 1.0.0d, EVP_PKEY_copy_parameters powinien działać. Jednak, sądząc z realizacji, po prostu wydaje się, aby skopiować parametry publicznych:

static int pkey_rsa_copy(EVP_PKEY_CTX *dst, EVP_PKEY_CTX *src) { 
    RSA_PKEY_CTX *dctx, *sctx; 
    if (!pkey_rsa_init(dst)) 
     return 0; 
    sctx = src->data; 
    dctx = dst->data; 
    dctx->nbits = sctx->nbits; 
    if (sctx->pub_exp) { 
     dctx->pub_exp = BN_dup(sctx->pub_exp); 
     if (!dctx->pub_exp) 
      return 0; 
    } 
    dctx->pad_mode = sctx->pad_mode; 
    dctx->md = sctx->md; 
    return 1; 
} 

Oprócz rozwiązania jweyrich za kolejna prosta metoda to pierwszy i2d_RSAPrivateKey swój klucz RSA następnie d2i_RSAPrivateKey go ponownie - nie kopia :)

+0

+1 dla metody i2d/d2i. – jweyrich

+1

Zamiast metod i2d/d2i, które wymagają znajomości typu bazowego, należy zamiast tego użyć PEM_write_PrivateKey/PEM_read_PrivateKey. W ten sposób klucze prywatne RSA, DH, EC i DSA są kopiowane bez wyraźnego poznania rodzaju bazowego. –

+0

Użyję i2d/d2i do innego celu. Ta odpowiedź naprawdę zaoszczędziła mi dni i dni pracy ... Teraz będę pasować do jutrzejszego terminu ... Wielkie dzięki, stary –