OpenSSL 是一種開源的加密庫,提供了一組用於加密和解密資料、驗證數位憑證以及實現各種安全協定的函數和工具。它可以用於建立和管理公鑰和私鑰、數位憑證和其他安全憑據,還支援SSL/TLS
、SSH
、S/MIME
、PKCS
等常見的加密協定和標準。
OpenSSL 的功能非常強大,可以用於構建安全的網路通訊、加密檔案和資料傳輸,還可以用於建立和驗證數位簽章、生成亂數等安全應用。它被廣泛用於Web伺服器、作業系統、網路應用程式和其他需要安全保護的系統中。
如上所示的連結則是該庫的官方網站,讀者可自行下載對應版本的OpenSSL
庫,並執行安裝程式,該庫預設會被安裝在根目錄下,通過點選下一步即可很容易的完成安裝設定。
該庫安裝成功後我們可以開啟OpenSSL-Win32
根目錄,在目錄中bin
目錄是可執行檔案,OpenSSL的執行需要依賴於這些動態連結庫,在使用時需要自行將本目錄設定到環境變數內,其次include
標頭檔案lib
靜態庫檔案,在使用時讀者需要自行設定到開發專案中,如下圖所示;
OpenSSL庫其本身就是一種加密與解密演演算法庫,運用該庫我們可以實現各類資料的加解密功能,首先我們以簡單的Base64演演算法為例對該庫進行使用。
Base64演演算法是一種用於將二進位制資料編碼為ASCII
字元的演演算法。該演演算法將三個位元組的二進位制資料轉換成四個字元的ASCII
字串,使得資料在傳輸時能夠避免出現非法字元、特殊字元等問題,同時也可以將二進位制資料轉換為文字形式,方便在文字協定中傳輸,但讀者需要注意Base64
編碼雖然可以作為一種簡單的加密方式,但是它並不是一種真正的加密演演算法,因為它只是將資料轉換為另一種形式,而沒有對資料進行加密處理。
在OpenSSL中,使用Base64
加密可以呼叫BIO_f_base64
函數實現,該函數是一種BIO
過濾器,用於將資料進行Base64
編碼和解碼,如下程式碼中筆者分別封裝實現了這兩種加解密方法,其中base64Encode
接收一個字串並將該字串壓縮為編碼字串儲存,與之相反base64Decode
則用於將壓縮後的字串恢復。
#include <openssl/err.h>
#include <openssl/pem.h>
#include <openssl/crypto.h>
#pragma comment(lib,"libssl.lib")
#pragma comment(lib,"libcrypto.lib")
// base64 編碼
char* base64Encode(const char* buffer, int length, bool newLine)
{
BIO* bmem = NULL;
BIO* b64 = NULL;
BUF_MEM* bptr;
b64 = BIO_new(BIO_f_base64());
if (!newLine)
{
BIO_set_flags(b64, BIO_FLAGS_BASE64_NO_NL);
}
bmem = BIO_new(BIO_s_mem());
b64 = BIO_push(b64, bmem);
BIO_write(b64, buffer, length);
BIO_flush(b64);
BIO_get_mem_ptr(b64, &bptr);
BIO_set_close(b64, BIO_NOCLOSE);
char* buff = (char*)malloc(bptr->length + 1);
memcpy(buff, bptr->data, bptr->length);
buff[bptr->length] = 0;
BIO_free_all(b64);
return buff;
}
// base64 解碼
char* base64Decode(char* input, int length, bool newLine)
{
BIO* b64 = NULL;
BIO* bmem = NULL;
char* buffer = (char*)malloc(length);
memset(buffer, 0, length);
b64 = BIO_new(BIO_f_base64());
if (!newLine)
{
BIO_set_flags(b64, BIO_FLAGS_BASE64_NO_NL);
}
bmem = BIO_new_mem_buf(input, length);
bmem = BIO_push(b64, bmem);
BIO_read(bmem, buffer, length);
BIO_free_all(bmem);
return buffer;
}
上述程式碼的使用也非常簡單,如下所示我們通過傳入一個input
字串,並將該字串壓縮後輸出,接著再把該字串解密後輸出。
int main(int argc, char* argv[])
{
// flag == false 將編碼資料壓縮為一行,否則原格式輸出
bool flag = false;
std::string input = "Hello lyshark!";
// 輸出編碼內容
char* encode = base64Encode(input.c_str(), input.length(), flag);
std::cout << "Base64 編碼後: " << encode << std::endl;
// 輸出解碼內容
char* decode = base64Decode(encode, strlen(encode), flag);
std::cout << "Base64 解碼後: " << decode << std::endl;
system("pause");
return 0;
}
執行上述程式碼,讀者可看到如下圖所示的輸出效果;