准备工作

1、在项目名称上单机右键,点击属性。在“配置属性”中选择“VC++目录”,填写openssl中的头文件位置和库文件位置。

 

 2、在“连接器”选项中的“输入”中填写库的名称,libssl.lib和libcrypto.lib

 

 

3、将OpenSSL文件中bin目录下的libcrpto-1_1.dll和libssl-1_1.dll两个文件拷贝到当前项目的文件下

 

 使用OpenSSL进行单项散列函数计算,以MD5为例

#define _CRT_SECURE_NO_WARNINGS
#include<openssl/md5.h>
#include <stdio.h>
#include <string.h>
#include <stdlib.h>

void getMD5(const char* str, char* result)
{
    MD5_CTX ctx;

    MD5_Init(&ctx);

    MD5_Update(&ctx, str, strlen(str));

    unsigned char md[MD5_DIGEST_LENGTH] = { 0 };
    MD5_Final(md, &ctx);
    //转变为16进制
    for (int i = 0; i < MD5_DIGEST_LENGTH; ++i)
    {
        sprintf(&result[i * 2], "%02x", md[i]);
    }
}

int main()
{
    char result[33] = { 0 };
    getMD5("hello, md5", result);
    printf("md5 value: %s\n", result);
    system("pause");

    return 0;
}

使用OpenSSL完成消息认证码。消息认证码是为了保障信息没有被篡改,前提是双方要约定好相同的密钥和哈希算法。

以生成消息认证码为例

#define _CRT_SECURE_NO_WARNINGS
#include<openssl/hmac.h>
#include<openssl/sha.h>
#include<iostream>
using namespace std;
int main()
{
    /*unsigned char *HMAC(const EVP_MD *evp_md, const void *key, int key_len,
        const unsigned char *d, size_t n, unsigned char *md,
        unsigned int *md_len);*/
    //约定好的密钥
    char key[] = "ad12ni12";
    //原始数据
    char data[] = "hello world how are you";
    unsigned char md[SHA256_DIGEST_LENGTH] = { 0 };
    //存放16进制的消息认证码
    char mdbuf[2 * SHA256_DIGEST_LENGTH + 1] = { 0 };
    unsigned int len = 0;
    //参数1:约定好的算法;参数2:密钥;参数3:密钥长度;参数4:原始数据;参数5:原始数据的长度
    //参数6:传出的认证码,参数7:传出参数,认证码的长度
    HMAC(EVP_sha256(), key, strlen(key),(unsigned char *) data, strlen(data), md, &len);
    //将消息认证码转换成16进制
    for (int i = 0; i < SHA256_DIGEST_LENGTH; i++)
    {
        sprintf(&mdbuf[2 * i], "%02x", md[i]);
    }
    cout << "得到的散列值:" << mdbuf << endl;
    
}

使用OpenSSL完成对称加密。以AES算法CBC模式为例。CBC模式需要约定好初始化向量

#include<openssl/aes.h>
#include<iostream>
using namespace std;
//对称加密的密钥
const char* mykey = "0123456789abcdef";
//原始明文
const char *mystr = "hello world, how are you, i am fine, think you hahah";
void decrypto(const  char *ciphertext, const unsigned char *key, unsigned char *iv, unsigned char **outText)
{
    AES_KEY aes;
    AES_set_decrypt_key(key, 128, &aes);
    
    int datalen = strlen(mystr) + 1;
    
    unsigned char *decrypt = (unsigned char*)calloc(datalen, 1);
    AES_cbc_encrypt((unsigned char*)ciphertext, decrypt, datalen, &aes, iv, AES_DECRYPT);
    
    *outText = decrypt;
}
void encryptoText(const char *plainText,const unsigned char *key, unsigned char *iv,unsigned char **outText)
{
    AES_KEY aes;
    AES_set_encrypt_key(key, 128, &aes); //参数2为比特位

    //向上调整为16的倍数
    int datalen;
    if ((strlen(plainText) + 1) % 16 == 0)
    {
        datalen = strlen(plainText) + 1;
    }
    else
    {
        datalen = ((strlen(plainText) + 1) / 16 + 1) * 16;
    }
    unsigned char *cipherText = (unsigned char *)calloc(datalen, 1);
    
    AES_cbc_encrypt((unsigned char *)plainText, cipherText, datalen, &aes, iv, AES_ENCRYPT);
    
    *outText = cipherText;
    
}

int main()
{
    
    //初始化向量,长度和密钥一致
    unsigned char iv[16];
    memset(iv, 'a', sizeof(iv));
    unsigned char *cipher = NULL;
    //加密
    encryptoText(mystr, (unsigned char*)mykey, iv, &cipher);
    cout << "密文:" << cipher << endl;
    cout << "------------" << endl;
    //解密
    unsigned char *text = NULL;
    memset(iv, 'a', sizeof(iv));
    decrypto((char*)cipher, (unsigned char*)mykey, iv, &text);
    cout << "明文:" << text << endl;

    free(cipher);
    free(text);

}