You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

PHP替代C#客户端实现PDF签名:哈希签名一致性问题排查

解决PHP生成与C#一致的RSA SHA1签名问题

现有一套C#实现的PDF签名系统:

  • 服务端预处理PDF待签名区域,生成SHA1哈希并Base64编码后传给客户端
  • C#客户端通过RSACryptoServiceProvider.SignHash方法完成签名,与服务端交互正常
  • 改用PHP实现客户端签名逻辑时,使用openssl_sign生成的签名与C#结果不一致,导致后续PDF签名失败

相关代码

C#服务端代码

Stream data = appearance.GetRangeStream();
byte[] hashByte = DigestAlgorithms.Digest(data, "SHA1");
string hash = Convert.ToBase64String(hashByte);

C#客户端签名代码

public static string SignHash(string hash, X509Certificate2 cert)
{            
    RSACryptoServiceProvider rsaCert = cert.PrivateKey as RSACryptoServiceProvider;
    byte[] hashSigned = rsaCert.SignHash(Convert.FromBase64String(hash), CryptoConfig.MapNameToOID("SHA1"));               
    return Convert.ToBase64String(hashSigned);
}

当前PHP签名代码

openssl_sign(base64_decode($hash), $sign, $private_key(), OPENSSL_ALGO_SHA1);

问题原因

C#的RSACryptoServiceProvider.SignHash方法并非直接对传入的哈希字节签名,而是遵循PKCS#1 v1.5标准,先将哈希值封装为ASN.1格式的DigestInfo结构,再进行RSA签名。而PHP的openssl_sign在传入原始哈希字节并指定OPENSSL_ALGO_SHA1时,会错误地将传入的字节视为原始数据,重新计算SHA1哈希后再签名,这就导致了签名结果的差异。

SHA1对应的DigestInfo结构DER编码前缀为固定字节:3021300906052b0e03021a05000414,拼接上20字节的SHA1哈希值后,才是C#实际签名的字节流。

解决方案

修改PHP代码,手动构造符合要求的DigestInfo字节流,再进行签名:

// 1. 解码服务端传来的Base64哈希字符串,得到原始SHA1哈希字节
$hashBytes = base64_decode($hash);

// 2. 构造SHA1的DigestInfo结构(固定前缀 + 哈希字节)
$digestInfoPrefix = hex2bin('3021300906052b0e03021a05000414');
$dataToSign = $digestInfoPrefix . $hashBytes;

// 3. 加载私钥(替换为你的私钥路径或内容)
$privateKey = openssl_pkey_get_private(file_get_contents('your_private_key.pem'));

// 4. 执行RSA PKCS#1 v1.5签名
openssl_sign($dataToSign, $sign, $privateKey, OPENSSL_ALGO_SHA1);

// 5. 将签名结果Base64编码,与C#返回格式一致
$signedHash = base64_encode($sign);

额外注意事项

  • 确保PHP加载的私钥与C#客户端使用的证书私钥完全一致,私钥需为PEM格式(可从PFX证书中提取)
  • 若C#中使用了非默认的签名填充方式(如OAEP),需调整PHP的签名参数(对应改为OPENSSL_ALGO_RSA_SHA1_OAEP等),默认情况下RSACryptoServiceProvider使用PKCS#1 v1.5填充
  • 服务端验证签名时,需使用对应公钥验证PHP生成的签名,逻辑与验证C#签名一致

内容的提问来源于stack exchange,提问作者Elvis Reis

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.20 11:57:42