2017-04-21 126 views
0

我需要一些幫助來解密C++中使用AES解密和Open SSL庫中的字符數組。我已經完成加密模式並且工作正常,但解密不起作用。在C++中解密AES示例

這是加密功能:

string Encrypt(char *Key, char *Msg, int size) 
{ 
    static char* Res; 
    static const char* const lut = "ABCDEF"; 
    string output; 
    AES_KEY enc_key; 

    Res = (char *)malloc(size); 

    AES_set_encrypt_key((unsigned char *)Key, 128, &enc_key); 

    for(int vuelta = 0; vuelta <= size; vuelta += 16) 
    { 
     AES_ecb_encrypt((unsigned char *)Msg + vuelta, (unsigned char *)Res + vuelta, &enc_key, AES_ENCRYPT); 
    }   

    output.reserve(2 * size); 

    for (size_t i = 0; i < size; ++i) 
    { 
     const unsigned char c = Res[i]; 
     output.push_back(lut[c >> 4]); 
     output.push_back(lut[c & 15]); 
    } 

    free(Res); 

    return output; 
} 

這是解密函數(不工作):

char * Decrypt(char *Key, char *Msg, int size) 
{ 
    static char* Res; 
    AES_KEY dec_key; 

    Res = (char *) malloc(size); 

    AES_set_decrypt_key((unsigned char *) Key, 128, &dec_key); 

    for(int vuelta= 0; vuelta<=size; vuelta+=16) 
    { 
     AES_ecb_encrypt((unsigned char *) Msg+vuelta, (unsigned char *) Res+vuelta, &dec_key, AES_DECRYPT); 
    } 

    return (Res); 
} 

這是調用的方法的主要功能的一個實施例,這個問題是thar no mather如何在Decrypt函數中打印「Res」變量,它總是顯示隨機ASCII值,並且我喜歡在加密函數中顯示字符串結果:

#include <stdlib.h> 
#include <stdio.h> 
#include <unistd.h> 
#include <string.h> 

#include "openSSL/aes.h" 

using namespace std; 

int main(int argc, char const *argv[]) 
{ 
    char key[16]; 
    char message[128]; 
    char enc_message[128]; 

    string s_key = "THIS_IS_THE_KEY_"; 
    string s_message = "Hello World !!!"; 

    memset(key, 0, sizeof(key)); 
    strcpy(key, s_key.c_str()); 

    memset(message, 0, sizeof(message)); 
    strcpy(message, s_message.c_str()); 

    string response = Encrypt(key, message, sizeof(message)); 

    cout<<"This is the Encrypted Message: "<<response<<endl; 

    memset(enc_message, 0, sizeof(enc_message)); 
    strcpy(enc_message, response.c_str()); 

    Decrypt(key, enc_message, sizeof(enc_message)); 

    return 0; 
} 

這種方法有什麼改進?

+0

感謝您的回答,我上傳了一個主函數調用函數的例子。我有probelmas顯示解密響應作爲一個字符串。 –

+1

'Decrypt(key,enc_message,sizeof(enc_message));'可能是錯誤的。密文的大小應該由你的'Encrypt'函數返回。根據你的消息,它應該是16或32個字節(並且只能看代碼)。也許你應該看看[EVP對稱加密和解密| C++程序](https://wiki.openssl.org/index.php/EVP_Symmetric_Encryption_and_Decryption#C.2B.2B_Programs)。還有C++庫可用,如[Botan](https://github.com/randombit/botan)和[Crypto ++](https://github.com/weidai11/cryptopp)。 – jww

+1

你應該*不*使用'AES_encrypt'和朋友。這是一個純軟件實現,所以你不會喜歡硬件支持,比如AES-NI。您應該使用'EVP_ *'功能。請參閱OpenSSL wiki上的[EVP Symmetric Encryption and Decryption](http://wiki.openssl.org/index.php/EVP_Symmetric_Encryption_and_Decryption)。事實上,您應該使用經過身份驗證的加密,因爲它提供了*機密性和真實性。請參閱OpenSSL wiki上的[EVP Authenticated Encryption and Decryption](http://wiki.openssl.org/index.php/EVP_Authenticated_Encryption_and_Decryption)。 – jww

回答

1

我想把答案放在我如何解決它的問題上:我的例子的問題是我試圖使用HEXADECIMAL STRING的解密函數,它應該使用ASCII字符串完成,值爲由加密功能提供。

也就是說,與其試圖解密這樣的字符串:461D019896EFA3

它必須與這樣的字符串進行解密:@(%_#$

之後,解密將在ASCII值傳遞它們必須被傳遞到十六進制,最後以一個字符串

這裏是爲我工作的例子:。

string Decrypt_string(char *Key, string HEX_Message, int size) 
{ 
    int i = 0; 
    char* Res; 
    AES_KEY dec_key; 
    string auxString, output, newString; 

    for(i = 0; i < size; i += 2) 
    { 
     string byte = HEX_Message.substr(i, 2); 
     char chr = (char) (int)strtol(byte.c_str(), NULL, 16); 
     auxString.push_back(chr); 
    } 

    const char *Msg = auxString.c_str(); 
    Res = (char *)malloc(size); 

    AES_set_decrypt_key((unsigned char *)Key, 128, &dec_key); 

    for(i = 0; i <= size; i += 16) 
    { 
     AES_ecb_encrypt((unsigned char *)Msg + i, (unsigned char *)Res + i, &dec_key, AES_DECRYPT); 
    } 

    output.reserve(2 * size); 

    for (size_t i = 0; i < size; ++i) 
    { 
     const unsigned char c = Res[i]; 
     output.push_back(lut[c >> 4]); 
     output.push_back(lut[c & 15]); 
    } 

    int len = output.length(); 

    for(int i = 0; i < len; i += 2) 
    { 
     string byte = output.substr(i, 2); 
     char chr = (char) (int)strtol(byte.c_str(), NULL, 16); 
     newString.push_back(chr); 
    } 

    free(Res); 

    return newString; 
}