1

ハイブリッド暗号システム(キー エンベロープにはRSA 、データ エンベロープには DES3 (2 キー オプション))を実装しようとしています。したがって、私は最初に Openssl のEVP機能を使用して DES3 を実装しようとしています。EVP を使用して RSA と DES3 暗号化を簡単に組み合わせることができるように思われるためです。

Openssl book からこのサンプル コード (gcc 警告を修正し、スニペットを 1 つのファイルに入れるためにデータ型を変更) を入手しました。

#include <stdio.h>
#include <openssl/ssl.h>
#include <openssl/evp.h>
#include <openssl/rand.h>

unsigned char *encrypt_example(EVP_CIPHER_CTX *ctx, unsigned char *data, int inl, int *rb);
unsigned char *decrypt_example(EVP_CIPHER_CTX *ctx, unsigned char *ct, int inl);
void select_random_key(unsigned char *key, int b);
void select_random_iv(unsigned char *iv, int b);
int seed_prng(int bytes);


int main(int argc, char *argv[])
{
    EVP_CIPHER_CTX ctx;
    EVP_CIPHER_CTX_init(&ctx);

    unsigned char key[EVP_MAX_KEY_LENGTH];
    unsigned char iv[EVP_MAX_IV_LENGTH];
    unsigned char *ct, *out;
    unsigned char final[EVP_MAX_BLOCK_LENGTH];
    unsigned char str[] = "123456789abcdef";
    int i = 0;

    if (!seed_prng(16))
    {
        printf("Fatal Error! Unable to seed the PRNG!\n");
        abort();
    }

    select_random_key(key, EVP_MAX_KEY_LENGTH);
    select_random_iv(iv, EVP_MAX_IV_LENGTH);


    /* EVP_des_ede3()       :three-key DES3 with ECB
     * EVP_des_ede()        :two-key DES3 with ECB
     * EVP_des_ede_cbc()    :two-key DES3 with CBC 
     * EVP_des_ede3_cbc()   :three-key DES3 with CBC */

    EVP_EncryptInit(&ctx, EVP_des_ede_cbc(), key, NULL);
    ct = encrypt_example(&ctx, str, strlen((const char*)str), &i);
    printf("Ciphertext is %d bytes.\n", i);

    EVP_DecryptInit(&ctx, EVP_des_ede_cbc(), key, NULL);
    out = decrypt_example(&ctx, ct, 8);
    printf("Decrypted: >>%s<<\n", out);
    out = decrypt_example(&ctx, ct + 8, 8);
    printf("Decrypted: >>%s<<\n", out);

    if (!EVP_DecryptFinal(&ctx, final, &i))
    {
        printf("Padding incorrect.\n");
        abort();
    }

    final[i] = 0;
    printf("Decrypted: >>%s<<\n", final);
    return 0;
}

int seed_prng(int bytes)
{
    if (!RAND_load_file("/dev/random", bytes))
        return 0;
    return 1;
}

void select_random_key(unsigned char *key, int b)
{
    int i;

    RAND_bytes(key, b);
    for (i = 0; i < b - 1; i++)
        printf("%02X:",key[i]);
    printf("%02X\n\n", key[b - 1]);
}

void select_random_iv (unsigned char *iv, int b)
{
    RAND_pseudo_bytes (iv, b);
}

unsigned char *encrypt_example(EVP_CIPHER_CTX *ctx, unsigned char *data, int inl, int *rb)
{
    unsigned char *ret = (unsigned char *)malloc(inl + EVP_CIPHER_CTX_block_size(ctx));
    int i, tmp, ol;

    ol = 0;
    for (i = 0; i < inl /100; i++)
    {
        EVP_EncryptUpdate(ctx, &ret[ol], &tmp, &data[ol], 100);
        ol += tmp;
    }

    if (inl % 100)
    {
        EVP_EncryptUpdate(ctx, &ret[ol], &tmp, &data[ol], inl%100);
        ol += tmp;
    }

    EVP_EncryptFinal(ctx, &ret[ol], &tmp);
    *rb = ol + tmp;
    return ret;
}

unsigned char *decrypt_example(EVP_CIPHER_CTX *ctx, unsigned char *ct, int inl)
{

    /* We're going to null-terminate the plaintext under the assumption it's
     * non-null terminated ASCII text. The null can be ignored otherwise.
     */
    unsigned char *pt = (unsigned char *)malloc(inl + EVP_CIPHER_CTX_block_size(ctx) + 1);
    int ol;

    EVP_DecryptUpdate(ctx, pt, &ol, ct, inl);
    if (!ol) /* there's no block to decrypt */
    {
        free(pt);
        return NULL;
    }

    pt[ol] = 0;
    return pt;
}

私はこれでそれをコンパイルしています

gcc -g -O0 -Wall evp_encrypt_decrypt.c  -o evp_encrypt_decrypt -lssl -lcrypto

これを実行すると、次の出力が得られます。

13:98:EB:64:D5:8B:1E:0A:70:1D:28:9D:25:3A:13:40:FE:C1:81:3C:C5:8F:4B:F6:66:1A:07:F8:17:D6:10:B6:4E:BC:45:96:00:A1:9F:59:44:A0:43:D9:9D:DD:C8:A9:0B:22:EC:7B:F2:5F:78:01:D1:58:6D:0B:B4:CB:5F:CD 

Ciphertext is 16 bytes.
Decrypted: >>(null)<<
Decrypted: >>12345678<<
Decrypted: >>9abcdef<<

ここでは、チップテキストが 16 バイトであることが示されています (これで問題ありません)。しかし、キー自体 (上記の 16 進コード) の長さは64 バイトです!

ただし、2 キー オプションを使用する DES3 では、キーの長さを 128 ビット (パリティ ビットを含む) にする必要があります。ただし、EVP_MAX_KEY_LENGTHの定義はデフォルトで64です。keyまた、以下に示すように、チッパー キーの長さ、変数のサイズ、および ctx キーのサイズを出力しようとしました。

printf("Key length DES3: %d\n", EVP_CIPHER_key_length(EVP_des_ede3_cbc()));
printf("Key size: %d\n", sizeof(key));
printf("Cipher CTX key length: %d\n\n", EVP_CIPHER_CTX_key_length(&ctx));

これは出力されます:

Key length DES3: 24
Key size: 64
Cipher CTX key length: 16

ここで少し混乱しています。DES3(ツーキー)のキーサイズは128ビットじゃないの?DES3 キーの長さが 24 と表示されるのはなぜですか (これはビット、バイトなどですか?) これらのキーの長さとサイズがすべて異なるのはなぜですか?

4

1 に答える 1

0

ただし、2 キー オプションを使用する DES3 では、128 ビット (パリティ ビットを含む) のキー長が必要です。

はい。2 キー 3DES のキー サイズは 64x2 = 128 ビットです。3キー3DESのキーサイズは64x3 = 192ビットです(Greg Sが述べたように)。

ただし、EVP_MAX_KEY_LENGTH の定義はデフォルトで 64 です。

これは、DES/3DES/AES などだけでなく、(すべての EVP 対称暗号に対して) 可能な最大値です。この値は、将来変更される可能性さえあります。

DES3 (2 キー) のキー サイズは 128 ビットであるべきではありませんか?

はい。

DES3 キーの長さが 24 と表示されるのはなぜですか (これはビット、バイトなどですか?)

誰が知っている....しかし、それはビットではなくバイトです。

これらのキーの長さとサイズがすべて異なるのはなぜですか?

サイズは、アルゴリズムまたは暗号システムに基づいています。

2-key 3DES は Encrypt-Decrypt-Encrypt を実行し、2 つのキーを使用します。したがって、キーの 1 つが 2 回使用されます。3-key 3DES は Encrypt-Decrypt-Encrypt を実行し、3 つの独立したキーを使用します。それが彼らが設計された方法です。

于 2014-04-20T12:12:50.110 に答える