tasign 0.2.0

TA ELF signing utilities with CMS/PKCS#7 support
//! SM2 PKCS#8 PEM 私钥解析(OpenSSL/GmSSL 生成的 `BEGIN PRIVATE KEY`)。

use num_bigint::BigUint;

pub use crate::crypto::pk::Pk;

use crate::error::Error;

fn map_crypto_err(e: crate::crypto::CryptoError) -> Error {
    Error::KeyParse(e.to_string())
}

/// 从 PEM 解析 SM2 私钥:支持明文 `PRIVATE KEY` 或 GmSSL 常用 `ENCRYPTED PRIVATE KEY`(需口令)。
pub fn sm2_secret_from_pkcs8_pem_with_pass(pem: &str, pass: &str) -> Result<BigUint, Error> {
    crate::crypto::key_parse::sm2_secret_from_pkcs8_pem_with_pass(pem, pass).map_err(map_crypto_err)
}

/// 从 PEM 文本解析 SM2 私钥标量(仅明文 `PRIVATE KEY`)。
pub fn sm2_secret_from_pkcs8_pem(pem: &str) -> Result<BigUint, Error> {
    for block in pem::parse_many(pem).map_err(|e| Error::KeyParse(e.to_string()))? {
        if block.tag() == "PRIVATE KEY" {
            let scalar = crate::crypto::key_parse::sm2_scalar_from_pkcs8_der(block.contents())
                .map_err(map_crypto_err)?;
            return Ok(BigUint::from_bytes_be(&scalar));
        }
    }
    Err(Error::KeyParse("no PRIVATE KEY block in PEM".into()))
}

/// PKCS#8 PEM(支持 GmSSL 加密格式)解析为 SM2 `Pk`,供 `sm2_sign`、CMS 等共用。
pub fn sm2_pk_from_pkcs8_pem_with_pass(pem: &str, pass: &str) -> Result<Pk, Error> {
    crate::crypto::key::sm2_pk_from_pkcs8_pem_with_pass(pem, pass).map_err(map_crypto_err)
}