openssl3.2 - exp - class warp for sha3-512

openssl3.2 - exp - class warp for sha3-512

概述

前面实验整了一个对buffer进行sha3-512算hash的函数。
实际用的时候,要对几个buffer连续做hash. 前面封装的统一做hash的函数不适用。
重新封装了一个类,只要在类的生命周期中,就可以随时对连续的buffer(可能不在一个函数中)做hash的update.

笔记

调用方代码

bool CPeFileCheck::calc_hash_SHA3_512()
{
    bool b_rc = false;
    CCipherSha3_512 hash;

    do {
        if (!hash.begin())
        {
            break;
        }

		// 如果buffer不在一个函数中,将hash的指针传给那些函数做hash.update
        if (!hash.update(this->m_pu8_map_file, this->m_u32_file_size))
        {
            break;
        }

        if (!hash.end())
        {
            break;
        }

        m_digest_length = hash.get_md_len();
        if (m_digest_length > sizeof(m_ary_digest_value))
        {
            break;
        }

        memcpy(m_ary_digest_value, hash.get_md(), hash.get_md_len());
        b_rc = true;
    } while (false);

    return b_rc;
}

子类 - cipher_sha3_512.h

//! \file cipher_sha3_512.h

#ifndef __CIPHER_SHA3_512_H__
#define __CIPHER_SHA3_512_H__

#include "cipher_md_base.h"


class CCipherSha3_512 : public CCipherMdBase
{
public:
	CCipherSha3_512();
	virtual ~CCipherSha3_512();
};

#endif // #ifndef __CIPHER_SHA3_512_H__

子类 - cipher_sha3_512.cpp

//! \file cipher_sha3_512.cpp

#include "pch.h"
#include "cipher_sha3_512.h"

CCipherSha3_512::CCipherSha3_512()
{
	setCiphherName("SHA3-512");
}

CCipherSha3_512::~CCipherSha3_512()
{
}


基类 - cipher_md_base.h

//! \file cipher_md_base.h

#ifndef __CIPHER_MD_BASE_H__
#define __CIPHER_MD_BASE_H__

#include <openssl/evp.h>
#include <string>

//! \ref https://blog.csdn.net/LostSpeed/article/details/135581192
class CCipherMdBase
{
public:
	CCipherMdBase();
	virtual ~CCipherMdBase();

	bool begin();
	bool update(uint8_t* pBuf, int lenBuf);
	bool end();

	unsigned int get_md_len() { return m_digest_length; }
	uint8_t* get_md() { return m_p_digest_value; }

	void setCiphherName(const char* pszNmae) { m_strCipherName = ((NULL != pszNmae) ? pszNmae : ""); }

private:
	void clear();

private:
	std::string m_strCipherName;

	OSSL_LIB_CTX* m_ossl_lib_ctx;
	EVP_MD* m_evp_md;
	EVP_MD_CTX* m_evp_md_ctx;

	unsigned int m_digest_length;
	uint8_t* m_p_digest_value;
};

#endif // #ifndef __CIPHER_MD_BASE_H__

基类 - cipher_md_base.cpp

//! \file cipher_md_base.cpp

#include "pch.h"
#include "cipher_md_base.h"

CCipherMdBase::CCipherMdBase()
	: m_ossl_lib_ctx(NULL),
	m_evp_md(NULL),
	m_evp_md_ctx(NULL),
	m_digest_length(0),
	m_p_digest_value(NULL)
{

}

CCipherMdBase::~CCipherMdBase()
{
    clear();
}

void CCipherMdBase::clear()
{
    if (NULL != m_evp_md_ctx)
    {
        EVP_MD_CTX_free(m_evp_md_ctx);
        m_evp_md_ctx = NULL;
    }

    m_digest_length = 0;
    if (NULL != m_p_digest_value)
    {
        OPENSSL_free(m_p_digest_value);
        m_p_digest_value = NULL;
    }

    if (NULL != m_evp_md)
    {
        EVP_MD_free(m_evp_md);
        m_evp_md = NULL;
    }

    if (NULL != m_ossl_lib_ctx)
    {
        OSSL_LIB_CTX_free(m_ossl_lib_ctx);
        m_ossl_lib_ctx = NULL;
    }
}

bool CCipherMdBase::begin()
{
    bool b_rc = false;
    const char* _psz_option_properties = NULL;

    do {
        clear();

        m_ossl_lib_ctx = OSSL_LIB_CTX_new();
        if (NULL == m_ossl_lib_ctx) {
            // fprintf(stderr, "OSSL_LIB_CTX_new() returned NULL\n");
            break;
        }

        /*
         * Fetch a message digest by name
         * The algorithm name is case insensitive.
         * See providers(7) for details about algorithm fetching
         */

        if (m_strCipherName.empty())
        {
            break;
        }

        m_evp_md = EVP_MD_fetch(m_ossl_lib_ctx, m_strCipherName.data(), _psz_option_properties);
        if (NULL == m_evp_md) {
            // fprintf(stderr, "EVP_MD_fetch could not find SHA3-512.");
            break;
        }

        /*
         * Make a message digest context to hold temporary state
         * during digest creation
         */
        m_evp_md_ctx = EVP_MD_CTX_new();
        if (NULL == m_evp_md_ctx) {
            // fprintf(stderr, "EVP_MD_CTX_new failed.\n");
            break;
        }

        /*
         * Initialize the message digest context to use the fetched
         * digest provider
         */
        if (EVP_DigestInit(m_evp_md_ctx, m_evp_md) != 1) {
            // fprintf(stderr, "EVP_DigestInit failed.\n");
            break;
        }

        b_rc = true;
    } while (false);

    return b_rc;
}

bool CCipherMdBase::update(uint8_t* pBuf, int lenBuf)
{
    bool b_rc = false;

    do {
        if (EVP_DigestUpdate(m_evp_md_ctx, pBuf, lenBuf) != 1) {
            // fprintf(stderr, "EVP_DigestUpdate(hamlet_1) failed.\n");
            break;
        }

        b_rc = true;
    } while (false);

    return b_rc;

}

bool CCipherMdBase::end()
{
    bool b_rc = false;
    int digest_length = 0;

    do {

        /* Determine the length of the fetched digest type */
        m_digest_length = EVP_MD_get_size(m_evp_md);
        if (m_digest_length <= 0) {
            // fprintf(stderr, "EVP_MD_get_size returned invalid size.\n");
            break;
        }

        m_p_digest_value = (uint8_t*)OPENSSL_malloc(m_digest_length);
        if (NULL == m_p_digest_value) {
            // fprintf(stderr, "No memory.\n");
            break;
        }

        if (EVP_DigestFinal(m_evp_md_ctx, m_p_digest_value, &m_digest_length) != 1) {
            // fprintf(stderr, "EVP_DigestFinal() failed.\n");
            break;
        }

        b_rc = true;
    } while (false);

    return b_rc;
}

备注

这个封装类用的很舒服。
如果要做其他种类的hash, 只需要继承一个子类,给定新的hash算法名称就行。

END

相关推荐

  1. openssl3.2 - exp - class warp for sha3-512

    2024-04-12 06:34:03       16 阅读
  2. openssl3.2 - exp - RAND_bytes_ex

    2024-04-12 06:34:03       28 阅读
  3. openssl3.2 - exp - PEM <==> DER

    2024-04-12 06:34:03       26 阅读
  4. openssl3.2 - exp - AES-256-GCM

    2024-04-12 06:34:03       16 阅读
  5. openssl3.2 - exp - generate prime

    2024-04-12 06:34:03       20 阅读
  6. openssl3.2 - exp - aes-128-cbc

    2024-04-12 06:34:03       16 阅读
  7. openssl3.2 - exp - get openssl version info

    2024-04-12 06:34:03       9 阅读

最近更新

  1. TCP协议是安全的吗?

    2024-04-12 06:34:03       18 阅读
  2. 阿里云服务器执行yum,一直下载docker-ce-stable失败

    2024-04-12 06:34:03       19 阅读
  3. 【Python教程】压缩PDF文件大小

    2024-04-12 06:34:03       19 阅读
  4. 通过文章id递归查询所有评论(xml)

    2024-04-12 06:34:03       20 阅读

热门阅读

  1. Gson

    2024-04-12 06:34:03       13 阅读
  2. docker+jekins+gitlab cicd

    2024-04-12 06:34:03       14 阅读
  3. android引用aar资源

    2024-04-12 06:34:03       18 阅读
  4. 负载均衡原理和负载均衡算法代码案例

    2024-04-12 06:34:03       13 阅读
  5. macad.occt解析extentions,tkernel

    2024-04-12 06:34:03       12 阅读
  6. 基于单链表的通讯录C语言实现

    2024-04-12 06:34:03       16 阅读
  7. http与https的区别?

    2024-04-12 06:34:03       16 阅读