Keyboard shortcuts

Press or to navigate between chapters

Press S or / to search in the book

Press ? to show this help

Press Esc to hide this help

4.12 非对称算法实现:RSA与ECDSA的密码引擎

非对称算法家族

SoftHSM2支持的非对称算法:

非对称算法家族:

AsymmetricAlgorithm(抽象基类)
│
├── RSA
│   ├── BotanRSA  (Botan实现)
│   └── OSSLRSA   (OpenSSL实现)
│   └── 支持机制:PKCS, OAEP, PSS
│   └── 密钥长度:1024-4096位
│
├── DSA
│   ├── BotanDSA  (Botan实现)
│   └── OSSLDSA   (OpenSSL实现)
│   └── 支持机制:DSA签名
│   └── 密钥长度:1024-3072位
│
├── ECDSA
│   ├── BotanECDSA (Botan实现)
│   └── OSSLECDSA  (OpenSSL实现)
│   └── 支持曲线:P-256, P-384, P-521
│   └── 密钥长度:曲线决定
│
├── ECDH
│   ├── BotanECDH (Botan实现)
│   └── OSSLECDH  (OpenSSL实现)
│   └── 密钥派生:ECDH
│
├── EdDSA
│   ├── BotanEDDSA
│   └── OSSLEDDSA
│   └── 支持曲线:Ed25519, Ed448
│
└── DH
    ├── BotanDH
    └── OSSLDH
    └── 密钥长度:1024-8192位

AsymmetricAlgorithm抽象类

AsymmetricAlgorithm定义了非对称加密的通用接口:

struct AsymAlgo
{
    enum Type
    {
        Unknown,
        RSA,
        DSA,
        DH,
        ECDH,
        ECDSA,
        GOST,
        EDDSA,
        MLDSA
    };
};

struct AsymMech
{
    enum Type
    {
        Unknown,
        RSA,
        RSA_MD5_PKCS,
        RSA_PKCS,
        RSA_PKCS_OAEP,
        RSA_SHA1_PKCS,
        RSA_SHA224_PKCS,
        RSA_SHA256_PKCS,
        RSA_SHA384_PKCS,
        RSA_SHA512_PKCS,
        RSA_PKCS_PSS,
        RSA_SHA1_PKCS_PSS,
        RSA_SHA224_PKCS_PSS,
        RSA_SHA256_PKCS_PSS,
        RSA_SHA384_PKCS_PSS,
        RSA_SHA512_PKCS_PSS,
        RSA_SSL,
        DSA,
        DSA_SHA1,
        ECDSA,
        ECDSA_SHA1,
        ECDSA_SHA224,
        ECDSA_SHA256,
        ECDSA_SHA384,
        ECDSA_SHA512,
        EDDSA,
        MLDSA
    };
};

class AsymmetricAlgorithm
{
public:
    AsymmetricAlgorithm();
    virtual ~AsymmetricAlgorithm() { }
    
    // 签名函数
    virtual bool sign(PrivateKey* privateKey, 
                       const ByteString& dataToSign, 
                       ByteString& signature, 
                       const AsymMech::Type mechanism,
                       const void* param = NULL,
                       const size_t paramLen = 0);
    
    virtual bool signInit(PrivateKey* privateKey, 
                          const AsymMech::Type mechanism,
                          const void* param = NULL,
                          const size_t paramLen = 0);
    
    virtual bool signUpdate(const ByteString& dataToSign);
    virtual bool signFinal(ByteString& signature);
    
    // 验证函数
    virtual bool verify(PublicKey* publicKey, 
                        const ByteString& originalData, 
                        const ByteString& signature, 
                        const AsymMech::Type mechanism,
                        const void* param = NULL,
                        const size_t paramLen = 0);
    
    virtual bool verifyInit(PublicKey* publicKey, 
                            const AsymMech::Type mechanism,
                            const void* param = NULL,
                            const size_t paramLen = 0);
    
    virtual bool verifyUpdate(const ByteString& originalData);
    virtual bool verifyFinal(const ByteString& signature);
    
    // 加密函数
    virtual bool encrypt(PublicKey* publicKey, 
                         const ByteString& data, 
                         ByteString& encryptedData, 
                         const AsymMech::Type padding) = 0;
    
    // 解密函数
    virtual bool decrypt(PrivateKey* privateKey, 
                         const ByteString& encryptedData, 
                         ByteString& data, 
                         const AsymMech::Type padding) = 0;
    
    // 密钥生成
    virtual bool generateKeyPair(AsymmetricKeyPair** ppKeyPair, 
                                  AsymmetricParameters* parameters, 
                                  RNG* rng = NULL) = 0;
    
    // 密钥派生(ECDH)
    virtual bool deriveKey(SymmetricKey **ppSymmetricKey, 
                           PublicKey* publicKey, 
                           PrivateKey* privateKey);
    
    // 密钥重构
    virtual bool reconstructKeyPair(AsymmetricKeyPair** ppKeyPair, 
                                     ByteString& serialisedData) = 0;
    virtual bool reconstructPublicKey(PublicKey** ppPublicKey, 
                                      ByteString& serialisedData) = 0;
    virtual bool reconstructPrivateKey(PrivateKey** ppPrivateKey, 
                                       ByteString& serialisedData) = 0;
    
    // 密钥工厂
    virtual PublicKey* newPublicKey() = 0;
    virtual PrivateKey* newPrivateKey() = 0;
    
protected:
    PublicKey* currentPublicKey;
    PrivateKey* currentPrivateKey;
    AsymMech::Type currentMechanism;
};

RSA机制详解

RSA签名机制

RSA签名机制:

RSA_PKCS(裸RSA签名)
┌─────────────────────────────────────┐
│ PKCS#1 v1.5 签名                    │
│                                     │
│ 数据 → 填充 → RSA私钥运算 → 签名    │
│                                     │
│ 填充格式:                          │
│ 0x00 0x01 [0xFF...] 0x00 [数据]     │
└─────────────────────────────────────┘

RSA_SHA256_PKCS(带Hash的签名)
┌─────────────────────────────────────┐
│                                     │
│ 数据 → SHA256 Hash → PKCS#1 填充    │
│     → RSA私钥运算 → 签名           │
│                                     │
│ 签名格式:                          │
│ 0x00 0x01 [0xFF...] 0x00           │
│ [SHA256 AlgorithmID] [Hash值]       │
└─────────────────────────────────────┘

RSA_PKCS_PSS(PSS签名)
┌─────────────────────────────────────┐
│                                     │
│ 数据 → Hash → MGF1填充              │
│     → RSA私钥运算 → 签名           │
│                                     │
│ 需要参数:                          │
│ ├── hashAlg: Hash算法               │
│ ├── mgf: MGF函数                    │
│ └── sLen: Salt长度                  │
└─────────────────────────────────────┘

RSA加密机制

RSA加密机制:

RSA_PKCS(PKCS#1 v1.5加密)
┌─────────────────────────────────────┐
│                                     │
│ 数据 → PKCS#1填充 → RSA公钥运算     │
│     → 密文                          │
│                                     │
│ 填充格式:                          │
│ 0x00 0x02 [随机字节...] 0x00 [数据] │
└─────────────────────────────────────┘

RSA_PKCS_OAEP(OAEP加密)
┌─────────────────────────────────────┐
│                                     │
│ 数据 → OAEP填充 → RSA公钥运算       │
│     → 密文                          │
│                                     │
│ OAEP填充:                          │
│ ├── MGF1掩码                        │
│ ├── Hash算法                        │
│ ├── 可选Label                       │
└─────────────────────────────────────┘

RSAPublicKey与RSAPrivateKey

RSA密钥的组成:

class RSAPublicKey : public PublicKey
{
public:
    static const char* type;
    
    virtual bool isOfType(const char* inType);
    virtual unsigned long getBitLength() const;
    virtual unsigned long getOutputLength() const;
    
    virtual void setN(const ByteString& inN);  // 模数
    virtual void setE(const ByteString& inE);  // 公钥指数
    
    virtual const ByteString& getN() const;
    virtual const ByteString& getE() const;
    
    virtual ByteString serialise() const;
    virtual bool deserialise(ByteString& serialised);

protected:
    ByteString n;  // 模数 N
    ByteString e;  // 公钥指数 E(通常为65537)
};

class RSAPrivateKey : public PrivateKey
{
public:
    static const char* type;
    
    virtual bool isOfType(const char* inType);
    virtual unsigned long getBitLength() const;
    virtual unsigned long getOutputLength() const;
    
    // CRT参数
    virtual void setP(const ByteString& inP);   // 素数P
    virtual void setQ(const ByteString& inQ);   // 素数Q
    virtual void setPQ(const ByteString& inPQ); // CRT系数 qInv = q⁻¹ mod p
    virtual void setDP1(const ByteString& inDP1); // D mod P-1
    virtual void setDQ1(const ByteString& inDQ1); // D mod Q-1
    
    // 基本参数
    virtual void setD(const ByteString& inD);   // 私钥指数D
    virtual void setN(const ByteString& inN);   // 模数N
    virtual void setE(const ByteString& inE);   // 公钥指数E
    
    virtual const ByteString& getP() const;
    virtual const ByteString& getQ() const;
    virtual const ByteString& getPQ() const;
    virtual const ByteString& getDP1() const;
    virtual const ByteString& getDQ1() const;
    virtual const ByteString& getD() const;
    virtual const ByteString& getN() const;
    virtual const ByteString& getE() const;
    
    virtual ByteString PKCS8Encode();
    virtual bool PKCS8Decode(const ByteString& ber);

protected:
    ByteString p, q, pq, dp1, dq1, d;  // 私钥组件
    ByteString n, e;                    // 公钥组件
};

RSA密钥结构

RSA密钥数学关系:

公钥:
├── N = P * Q(模数)
├── E = 公钥指数(通常65537)
│
私钥(基本形式):
├── D = E^(-1) mod (P-1)(Q-1)
│
私钥(CRT加速形式):
├── P, Q(素数)
├── dP = D mod (P-1)
├── dQ = D mod (Q-1)
├── qInv = Q^(-1) mod P
│
签名计算:
├── 基本形式:S = M^D mod N
├── CRT加速:
│   ├── S1 = M^dP mod P
│   ├── S2 = M^dQ mod Q
│   ├── S = S2 + qInv*(S1-S2) mod N

OSSLRSA实现

OSSLRSA使用OpenSSL EVP API:

class OSSLRSA : public AsymmetricAlgorithm
{
public:
    OSSLRSA();
    virtual ~OSSLRSA();
    
    virtual bool sign(PrivateKey* privateKey, 
                       const ByteString& dataToSign, 
                       ByteString& signature, 
                       const AsymMech::Type mechanism,
                       const void* param = NULL,
                       const size_t paramLen = 0);
    
    virtual bool encrypt(PublicKey* publicKey, 
                         const ByteString& data, 
                         ByteString& encryptedData, 
                         const AsymMech::Type padding);
    
    virtual bool decrypt(PrivateKey* privateKey, 
                         const ByteString& encryptedData, 
                         ByteString& data, 
                         const AsymMech::Type padding);
    
    virtual bool generateKeyPair(AsymmetricKeyPair** ppKeyPair, 
                                  AsymmetricParameters* parameters, 
                                  RNG* rng = NULL);
    
    virtual PublicKey* newPublicKey();
    virtual PrivateKey* newPrivateKey();

private:
    HashAlgorithm* pCurrentHash;
    HashAlgorithm* pSecondHash;
    size_t sLen;  // PSS Salt长度
};

bool OSSLRSA::sign(PrivateKey* privateKey, 
                    const ByteString& dataToSign, 
                    ByteString& signature, 
                    const AsymMech::Type mechanism,
                    const void* param,
                    const size_t paramLen)
{
    // 创建RSA密钥对象
    RSA* rsa = RSA_new();
    
    RSAPrivateKey* rsaKey = (RSAPrivateKey*)privateKey;
    
    // 设置密钥参数
    BIGNUM* n = BN_bin2bn(rsaKey->getN().byte_str(), rsaKey->getN().size(), NULL);
    BIGNUM* e = BN_bin2bn(rsaKey->getE().byte_str(), rsaKey->getE().size(), NULL);
    BIGNUM* d = BN_bin2bn(rsaKey->getD().byte_str(), rsaKey->getD().size(), NULL);
    
    RSA_set0_key(rsa, n, e, d);
    
    // 设置CRT参数(如果可用)
    if (rsaKey->getP().size() > 0) {
        BIGNUM* p = BN_bin2bn(rsaKey->getP().byte_str(), rsaKey->getP().size(), NULL);
        BIGNUM* q = BN_bin2bn(rsaKey->getQ().byte_str(), rsaKey->getQ().size(), NULL);
        RSA_set0_factors(rsa, p, q);
        
        BIGNUM* dp = BN_bin2bn(rsaKey->getDP1().byte_str(), rsaKey->getDP1().size(), NULL);
        BIGNUM* dq = BN_bin2bn(rsaKey->getDQ1().byte_str(), rsaKey->getDQ1().size(), NULL);
        BIGNUM* qInv = BN_bin2bn(rsaKey->getPQ().byte_str(), rsaKey->getPQ().size(), NULL);
        
        RSA_set0_crt_params(rsa, dp, dq, qInv);
    }
    
    // 根据机制选择签名方式
    switch (mechanism) {
        case AsymMech::RSA_PKCS:
        {
            int sigLen = RSA_size(rsa);
            unsigned char* sigBuf = new unsigned char[sigLen];
            int ret = RSA_private_encrypt(dataToSign.size(), dataToSign.byte_str(),
                                          sigBuf, rsa, RSA_PKCS1_PADDING);
            if (ret > 0) {
                signature = ByteString(sigBuf, ret);
            }
            delete[] sigBuf;
            RSA_free(rsa);
            return (ret > 0);
        }
            
        case AsymMech::RSA_SHA256_PKCS:
        {
            ByteString hash;
            computeHash(dataToSign, hash, EVP_sha256());
            int sigLen = RSA_size(rsa);
            unsigned char* sigBuf = new unsigned char[sigLen];
            int ret = RSA_sign(NID_sha256WithRSAEncryption,
                               hash.byte_str(), hash.size(),
                               sigBuf, &sigLen, rsa);
            if (ret == 1) {
                signature = ByteString(sigBuf, sigLen);
            }
            delete[] sigBuf;
            RSA_free(rsa);
            return (ret == 1);
        }
            
        case AsymMech::RSA_SHA256_PKCS_PSS:
        {
            int sigLen = RSA_size(rsa);
            unsigned char* sigBuf = new unsigned char[sigLen];
            ByteString hash;
            computeHash(dataToSign, hash, EVP_sha256());
            RSA_padding_add_PKCS1_PSS(rsa, sigBuf, hash.byte_str(), EVP_sha256(), -1);
            int ret = RSA_private_encrypt(RSA_size(rsa), sigBuf, sigBuf, rsa, RSA_NO_PADDING);
            if (ret > 0) {
                signature = ByteString(sigBuf, ret);
            }
            delete[] sigBuf;
            RSA_free(rsa);
            return (ret > 0);
        }
            
        default:
            RSA_free(rsa);
            return false;
    }

```cpp
bool OSSLRSA::generateKeyPair(AsymmetricKeyPair** ppKeyPair, 
                               AsymmetricParameters* parameters, 
                               RNG* rng)
{
    RSAParameters* rsaParams = (RSAParameters*)parameters;
    size_t bits = rsaParams->getBitLength();
    
    // 生成RSA密钥
    RSA* rsa = RSA_new();
    BIGNUM* e = BN_new();
    BN_set_word(e, RSA_F4);  // 65537
    
    int ret = RSA_generate_key_ex(rsa, bits, e, NULL);
    
    if (ret != 1) {
        RSA_free(rsa);
        BN_free(e);
        return false;
    }
    
    // 提取公钥参数
    const BIGNUM* n, *e_out;
    RSA_get0_key(rsa, &n, &e_out, NULL);
    
    RSAPublicKey* publicKey = new RSAPublicKey();
    ByteString nBytes(BN_num_bytes(n));
    BN_bn2bin(n, nBytes.byte_str());
    publicKey->setN(nBytes);
    
    ByteString eBytes(BN_num_bytes(e_out));
    BN_bn2bin(e_out, eBytes.byte_str());
    publicKey->setE(eBytes);
    
    // 提取私钥参数
    const BIGNUM* d, *p, *q, *dp, *dq, *pq;
    RSA_get0_key(rsa, NULL, NULL, &d);
    RSA_get0_crt_params(rsa, &dp, &dq, &pq);
    RSA_get0_factors(rsa, &p, &q);
    
    RSAPrivateKey* privateKey = new RSAPrivateKey();
    
    ByteString dBytes(BN_num_bytes(d));
    BN_bn2bin(d, dBytes.byte_str());
    privateKey->setD(dBytes);
    
    // ... 设置其他CRT参数
    
    privateKey->setN(nBytes);
    privateKey->setE(eBytes);
    
    // 创建密钥对
    *ppKeyPair = new RSAKeyPair(publicKey, privateKey);
    
    RSA_free(rsa);
    BN_free(e);
    
    return true;
}

ECDSA实现

ECDSA使用椭圆曲线签名:

class ECPublicKey : public PublicKey
{
public:
    virtual void setEC(const ByteString& inEC);   // 曲线参数
    virtual void setQ(const ByteString& inQ);     // 公钥点Q
    
    virtual const ByteString& getEC() const;
    virtual const ByteString& getQ() const;

protected:
    ByteString ec;  // 曲线OID或参数
    ByteString q;   // 公钥点(压缩或非压缩格式)
};

class ECPrivateKey : public PrivateKey
{
public:
    virtual void setEC(const ByteString& inEC);   // 曲线参数
    virtual void setD(const ByteString& inD);     // 私钥值d
    
    virtual const ByteString& getEC() const;
    virtual const ByteString& getD() const;

protected:
    ByteString ec;  // 曲线OID
    ByteString d;   // 私钥值(大整数)
};

ECDSA签名结构

ECDSA签名结构:

签名 (r, s):
├── r = x坐标 mod n
├── s = k^(-1)(z + r*d) mod n
│
其中:
├── k:随机数
├── z:消息Hash值
├── d:私钥
├── n:曲线阶数
│
签名格式(DER编码):
0x30 [长度]
  0x02 [长度] [r]
  0x02 [长度] [s]

BotanRSA实现

BotanRSA使用Botan C++ API:

class BotanRSA : public AsymmetricAlgorithm
{
public:
    virtual bool sign(PrivateKey* privateKey, 
                       const ByteString& dataToSign, 
                       ByteString& signature, 
                       const AsymMech::Type mechanism);
    
    virtual bool generateKeyPair(AsymmetricKeyPair** ppKeyPair, 
                                  AsymmetricParameters* parameters, 
                                  RNG* rng);
};

bool BotanRSA::sign(PrivateKey* privateKey, 
                     const ByteString& dataToSign, 
                     ByteString& signature, 
                     const AsymMech::Type mechanism)
{
    // 创建Botan RSA私钥
    RSAPrivateKey* rsaKey = (RSAPrivateKey*)privateKey;
    
    Botan::BigInt n(rsaKey->getN().byte_str(), rsaKey->getN().size());
    Botan::BigInt e(rsaKey->getE().byte_str(), rsaKey->getE().size());
    Botan::BigInt d(rsaKey->getD().byte_str(), rsaKey->getD().size());
    
    Botan::RSA_PrivateKey botanKey(n, e, d);
    
    // 根据机制选择签名方式
    std::string padding;
    
    switch (mechanism) {
        case AsymMech::RSA_SHA256_PKCS:
            padding = "PKCS1v15(SHA-256)";
            break;
            
        case AsymMech::RSA_SHA256_PKCS_PSS:
            padding = "PSSR(SHA-256,MGF1,32)";
            break;
            
        default:
            return false;
    }
    
    // 创建签名对象
    Botan::PK_Signer signer(botanKey, padding, Botan::IEEE_1363);
    
    // 执行签名
    Botan::SecureVector<Botan::byte> sig = signer.sign_message(
        dataToSign.byte_str(), 
        dataToSign.size(), 
        *rng);
    
    signature = ByteString(sig.begin(), sig.size());
    
    return true;
}

ECDH密钥派生

ECDH用于密钥协商:

bool BotanECDH::deriveKey(SymmetricKey** ppSymmetricKey, 
                           PublicKey* publicKey, 
                           PrivateKey* privateKey)
{
    ECPublicKey* ecPub = (ECPublicKey*)publicKey;
    ECPrivateKey* ecPriv = (ECPrivateKey*)privateKey;
    
    // 创建Botan ECDH密钥
    Botan::ECDH_PrivateKey privKey;
    // ... 从ecPriv初始化
    
    Botan::ECDH_PublicKey pubKey;
    // ... 从ecPub初始化
    
    // 执行密钥派生
    Botan::PK_Key_Agreement ka(privKey, "Raw");
    
    Botan::SecureVector<Botan::byte> sharedKey = ka.derive_key(
        32,  // 密钥长度
        pubKey.public_value());
    
    // 创建对称密钥
    SymmetricKey* symKey = new AESKey(256);
    symKey->setKeyBits(ByteString(sharedKey.begin(), sharedKey.size()));
    
    *ppSymmetricKey = symKey;
    
    return true;
}

ECDH密钥派生流程

ECDH密钥派生流程:

Alice                              Bob
│                                   │
│ 私钥 d_A                          │ 私钥 d_B
│ 公钥 Q_A = d_A * G                │ 公钥 Q_B = d_B * G
│                                   │
│ 发送 Q_A ────────────────────────→│
│                                   │
│←───────────────────────────────── Q_B
│                                   │
│ 计算:                            │ 计算:
│ K_A = d_A * Q_B                   │ K_B = d_B * Q_A
│   = d_A * d_B * G                 │   = d_B * d_A * G
│                                   │
│ K_A == K_B(共享密钥)
│
│ KDF(K_A) → AES密钥

非对称加密完整流程

非对称加密完整流程:

C_GenerateKeyPair
    │
    │ CryptoFactory::i()->getAsymmetricAlgorithm(AsymAlgo::RSA)
    │ algo->generateKeyPair(&keyPair, params, rng)
    ▼
密钥对创建(RSAKeyPair对象)
    │
    │ C_SignInit
    │ CryptoFactory::i()->getAsymmetricAlgorithm(AsymAlgo::RSA)
    │ algo->signInit(privateKey, mechanism)
    ▼
签名初始化
    │
    │ C_Sign
    │ algo->sign(privateKey, data, signature, mechanism)
    ▼
签名完成
    │
    │ CryptoFactory::i()->recycleAsymmetricAlgorithm(algo)
    ▼
回收算法实例

C_Encrypt
    │
    │ algo->encrypt(publicKey, data, encrypted, padding)
    ▼
加密完成

一个类比:保险箱的物理钥匙

保险箱物理钥匙类比:

RSA密钥(物理钥匙)
│
├── 公钥(锁的图纸)
│   ├── N:锁芯规格
│   ├── E:开锁规则
│   │
│   ├── 可公开分发
│   ├── 用于验证签名(检查锁)
│   └── 用于加密(设计新锁)
│
├── 私钥(物理钥匙)
│   ├── P, Q:钥匙齿形状
│   ├── D:钥匙转动角度
│   │
│   ├── 保密存储
│   ├── 用于签名(盖章)
│   └── 用于解密(开锁)
│
├── 签名机制(盖章方式)
│   │
│   ├── PKCS#1 v1.5(普通盖章)
│   │   ├── 盖章后附上数据
│   │   ├── 固定格式
│   │
│   ├── RSA-PSS(防伪盖章)
│   │   ├── 加随机Salt
│   │   ├── 防伪造攻击
│   │   ├── 更安全
│
└── 加密机制(锁设计)
    │
    ├── PKCS#1 v1.5(普通锁)
    │   ├── 随机填充
    │   ├── 可能被攻击
    │
    ├── RSA-OAEP(防破解锁)
    │   ├── MGF掩码
    │   ├── Hash校验
    │   ├── 更安全

本篇小结

今天我们分析了SoftHSM2的非对称算法实现。

AsymmetricAlgorithm抽象类

  • sign/verify:签名验证
  • encrypt/decrypt:加密解密
  • generateKeyPair:密钥生成
  • deriveKey:密钥派生

RSA机制

  • RSA_PKCS:裸RSA签名
  • RSA_SHA256_PKCS:带Hash签名
  • RSA_PKCS_PSS:PSS签名
  • RSA_PKCS_OAEP:OAEP加密

RSA密钥

  • 公钥:N(模数)、E(公钥指数)
  • 私钥:P、Q、D、CRT参数

ECDSA

  • 公钥:曲线EC、公钥点Q
  • 私钥:曲线EC、私钥值D
  • 签名:(r, s) DER编码

ECDH

  • 交换公钥
  • 计算共享密钥
  • KDF派生对称密钥

OpenSSL实现

  • RSA_sign/RSA_verify
  • EVP_PKEY API
  • BIGNUM处理大整数

Botan实现

  • PK_Signer/PK_Verifier
  • C++原生API
  • BigInt类

下一节,我们将分析哈希与MAC实现——SHA-256、HMAC如何工作。

【下集预告】

哈希算法如何实现?

SHA-256计算过程?

HMAC如何使用密钥?

CMAC如何工作?

下一节,哈希与MAC实现。