2011-12-04 16 views
2

DSA証明書を使用してデータに署名しようとしています。私は証明書をメモリに保存しています(これはopenssl gendsaコマンドで生成されたものです)。Openssl DSA sign

私の機能はこのように見え、問題はres = EVP_SignFinalです。関数は0を返し、signature_lenを0に設定します。

bool my_dsa_sign(const Certificate& certificate, const char* messageData, size_t messageLength, Signature &outSignature) { 
    bool resultOk = false; 
    BIO* bio = BIO_new_mem_buf((void*) certificate.getPEMData(), certificate.getSize()); 
    if(NULL != bio) { 
     EVP_PKEY *pkey = NULL; 
     if(NULL != (pkey = PEM_read_bio_PrivateKey(bio, NULL, NULL, NULL))) { 
      unsigned int signature_len; 
      EVP_MD_CTX ctx; 
      int res = EVP_SignInit(&ctx, EVP_sha512()); 
      if(1 == res) { 
       res = EVP_SignUpdate(&ctx, messageData, messageLength); 
       if(1 == res) { 
        unsigned char* s = (unsigned char*)malloc(EVP_PKEY_size(pkey)); 

        // problem here 
        res = EVP_SignFinal(&ctx, s, &signature_len, pkey); 
        if(1 == res) { 
         resultOk = true; 
         signature.setData(s, signature_len); 
        } 
       } 
      } 
      EVP_PKEY_free(pkey); 
      EVP_MD_CTX_cleanup(&ctx); 
     } 
     BIO_free(bio); 
    } 
    return resultOk; 
} 

何か問題が起こっている可能性はありますか? 私は、デバッガでチェックして、証明書の値は、フォームで、正しいされています。また、長さが正確である

-----BEGIN DSA PRIVATE KEY----- 
MIID.... 
....... 
-----END DSA PRIVATE KEY----- 

、ファイルのそれと一致しました。

+0

*証明書*は公開鍵を含むデータ(多かれ少なかれ一般的なもの)であり、一部はデータと署名(通常は他の誰かが記述する)を含み、秘密鍵はこれとは別です(証明書には含まれていません)。 –

+0

あなたは正しいです、私はそのクラスをリファクタリングする必要があります – Ha11owed

答えて

2

OpenSSLの多くを知らないので、あなたのコードでDSAを使用しているところはありません。

int res = EVP_SignInit(&ctx, EVP_sha512()); 

manual page to EVP_SignInitは言う:

EVP_SignInit()タイプダイジェストのデフォルトの実装を使用するために署名コンテキストCTXを初期化します。

manual page to EVP_sha512は言う:

[...]、EVP_sha512()、[...] [...]、SHA512は、[...]ダイジェストアルゴリズムに対してEVP_MD構造体を返すそれぞれ。 関連する署名アルゴリズムはいずれの場合もRSAです。

ハイライト DSAキーでRSA署名をしようとしているようですが、これは動作しません(またはナンセンスを吐き出す)。

ドキュメントを通していくつかのブラウジングの後、私はかなりのドキュメントは、今述べていても、しかし、DSAとSHA512一緒に使用する方法を見つけることができませんでした:

をダイジェストと署名アルゴリズムの間のリンクが修正されましたがOpenSSL 1.0以降ではEVP_sha1()を とRSAとDSAで使用できるため、EVP_dss1()を使用する必要はありません。

+1

あなたは正しいです、SHA512はDSAで使用することはできません、私はハッシュアルゴリズムが重要と思わなかった。 SHA1に変更して動作させています。 ありがとうございました、私は間違った方向に見て、ほぼ一日を過ごしました。 – Ha11owed

+0

また、DSAを使用するという事実は、EVP_KEYがDSAまたはRSA署名を行うかどうかを決定するので、EVP_SignUpdateを使用しているときの最後にのみ重要です。 PEM_read_bio_PrivateKeyメソッドは、すべての形式を透過的に処理します。 – Ha11owed