2017-11-15 20 views
2

keyiv이 주어지면이 C 프로그램은 을 암호화하여 stdout으로 출력해야합니다.(LibreSSL) libcrypto를 사용하는 AES-256-GCM 암호화

EVP_CIPHER_CTX *ctx = EVP_CIPHER_CTX_new(); 
EVP_EncryptInit(ctx, EVP_aes_256_gcm(), key, iv); 

const size_t block_size = 128; 
unsigned char inbuf[block_size]; 
unsigned char outbuf[block_size + EVP_MAX_BLOCK_LENGTH]; 
int inlen, outlen; 
for (;;) 
{ 
     inlen = fread(inbuf, 1, block_size, stdin); 
     if (inlen <= 0) 
       break; 

     EVP_EncryptUpdate(ctx, outbuf, &outlen, inbuf, inlen) 
     fwrite(outbuf, 1, outlen, stdout); 
} 
EVP_EncryptFinal_ex(ctx, outbuf, &outlen) 
fwrite(outbuf, 1, outlen, stdout); 

암호문을 해독이 성공적으로 안정적으로

openssl aes-256-gcm -in ciphertext.txt -K <key> -iv <iv> -d

을 실행하여

이 코드의 출력을 확인하고을 (오류. 간결함을 제거 확인), 그러나 나쁜 를 기록 예를 들어을 해독합니다 (예 :

).
$ openssl aes-256-gcm ... 
Hello World. 
bad decrypt 

무엇을 잘못해서이 말을 할 수 있습니까?

답변

0

암호화 후 GCM 인증 태그를 얻지 못하고 암호 해독 중에이를 제공하지 못했습니다.

"잘못된 암호 해독"메시지가 잘못된 것입니다. 해독은 정상적으로 진행되었지만 인증을 제공하는 태그는 제공되지 않았습니다.

태그가

unsigned char *tag = malloc(TAGSIZE); 
EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_GCM_GET_TAG, TAGSIZE, tag); 

TAGSIZE으로 EVP_EncryptFinal_ex에 호출 후 에서 입수 가능하면, 태그의 크기 (바이트)이며, 다른 값의 개수 일 수있다. 이것은 다른 곳에서 Wikipedia에 대해 논의되었습니다.

0

여기서 문제는 PKCS # 7에서 요구하는대로 적절한 채우기를 구현하지 않는다는 것입니다. openssl은 디코딩 된 메시지에 올바른 패딩이 있어야합니다. 규칙은 다음과 같습니다 패딩의 항상 적어도 1 바이트이 있어야한다

  • 그것은 당신이이 AES-256으로 이제 암호

의 크기를 차단하는 패딩되어야한다

  • 블록 크기는 128 비트 (16 바이트)입니다. 즉, 1-16 개의 채우기 바이트를 추가해야합니다. 추가 할 패딩 바이트는 항상 패딩의 크기이므로 9 바이트의 패딩을 추가해야하는 경우 9 0x09 바이트를 추가합니다.

    이 패딩을 원래 일반 텍스트에 올바르게 추가하면 openssl이 해독시 불평하지 않아야합니다.

  • +0

    OP는 AES-256에 대해 묻습니다 - ** GCM **에는 제로 패딩이 포함되어 있으며 PKCS # 7 패딩은 GCM 모드에서 사용되지 않습니다. [GCM 패딩인지 여부] (https://crypto.stackexchange.com/questions/42412/gcm-padding-or-not) 및 [Galois/Counter Mode] (https://en.wikipedia.org/wiki)를 참조하십시오./Galois/Counter_Mode) – zaph

    +0

    오, 우리가 틀린 대답으로 붙어있는 것처럼 보입니다. **슬퍼!** – zaph