【问题标题】:Not the same hash value in c# and phpc#和php中的哈希值不一样
【发布时间】:2012-03-07 16:26:01
【问题描述】:

我有一个用 c# 开发的 Web 服务。 它使用 MD5 生成会话密钥。

c#:

public static string GetMD5(string pTxt)
{
    string sCTxt = "";
    byte[] aTxt;
    UnicodeEncoding oEnc = new UnicodeEncoding();
    aTxt = oEnc.GetBytes(pTxt);
    HashAlgorithm oHash = new MD5CryptoServiceProvider();
    byte[] aCTxt = oHash.ComputeHash(aTxt);
    foreach (byte b in aCTxt)
        sCTxt += String.Format("{0:X2}", b);
    return (sCTxt);
}

出于几个原因,我必须在 PHP 中创建相同的 GetMD5 方法。 当然,基本的 md5() 函数不会返回相同的哈希(因为 UNICODE)

我尝试在 PHP 中模拟代码但没有成功

php:

public function HexToBytes($s) {
    return join('', array_map('chr', array_map('hexdec', str_split($s, 2))));
}

public function GetMD5($pStr) {
    $data = mb_convert_encoding($pStr, 'UTF-16LE', 'ASCII');
    $h = $this->HexToBytes(hash_hmac('md5', $data, ''));
    return (base64_encode($h));
}

知道为什么结果不一样吗?

提前致谢


**

已修复!谢谢!

**

有兴趣的,这里是匹配c#的PHP方法

public function str2hex($string) {
   $hex = "";
   for ($i = 0; $i < strlen($string); $i++)
      $hex .= (strlen(dechex(ord($string[$i]))) < 2) ? "0" . dechex(ord($string[$i])) : dechex(ord($string[$i]));       
   return $hex;
}

public function GetMD5($pStr) {
   $data = mb_convert_encoding($pStr, 'UTF-16LE', 'UTF-8');
   $h = $this->str2hex(md5($data, true));
   return strtoupper($h);
}

【问题讨论】:

  • 看起来您的 C# 版本是十六进制编码结果,而 php 版本是 base64 编码结果。这肯定会产生不同的结果。
  • 加上 PHP 代码正在执行 HMAC 而不是直接哈希。

标签: c# php unicode md5


【解决方案1】:

我认为您只是过于复杂了您的方法。以下替代方案对我有用:

C#:

public static string GetMD5(string text)
{
    byte[] textBytes = Encoding.UTF8.GetBytes(text);
    byte[] hash = MD5.Create().ComputeHash(textBytes);

    return Convert.ToBase64String(hash);
}

PHP:

public function GetMD5($pStr) {
    return base64_encode(
              md5(mb_convert_encoding($pStr, "UTF8", "Unicode"), true));
}

【讨论】:

  • 感谢您的回复。如果 c# 散列是用 UTF-8 编码制作的,那就没问题了。但它是用 Unicode 编码制作的,我无法更改它...
  • 它在 Unicode 中的确切位置:C# 还是 PHP 端?您可以将其转换为 UTF8。 (请参阅更新的 PHP 代码。)
  • 我刚刚做了一些测试。在 c# 方法中将编码类型更改为 UTF-8 有效。但我想保留 UnicodeEncoding oEnc = new UnicodeEncoding();
  • 好的,我知道了!你很有帮助!这是所需的最终 PHP 代码: public function GetMD5($pStr) { $data = mb_convert_encoding($pStr, 'UTF-16LE', 'UTF-8'); $h = $this->str2hex(md5($data, true));返回 strtoupper($h); } 谢谢!
  • @Elian,当您使用md5 并将第二个参数设置为true 时,您可能不需要使用str2hex,因为它应该返回自身的二进制数据。
猜你喜欢
  • 1970-01-01
  • 2018-11-08
  • 2020-10-28
  • 2015-07-07
  • 2021-12-23
  • 1970-01-01
  • 1970-01-01
  • 2014-05-19
  • 2019-10-10
相关资源
最近更新 更多