Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
677 views
in Technique[技术] by (71.8m points)

hmac - C# equivalent to hash_hmac in PHP

using .NET and C# i need to provide an integrity string using HMAC SHA512 to a PHP server . Using in C# :

Encoding encoding = Encoding.UTF8;
byte[] keyByte = encoding.GetBytes(key);
HMACSHA512 hmacsha512 = new HMACSHA512(keyByte);
byte[] messageBytes = encoding.GetBytes(message);
byte[]  hashmessage = hmacsha512.ComputeHash(messageBytes);
return(ByteToString(hashmessage).toUpper());

But it doesn't match with PHP hash_hmac() PHP code :

$hmac = strtoupper(hash_hmac($pbx_hash, $msg, $binKey));

I try to change encoding in C# (utf8, ASCII,Unicode) Without success.

I've tried many solution found on the net but nothing give the same string :(

I can't change the PHP code, and doesn't see what's wrong in C#

Edit This is ByteToString (copied from the comment):

static string ByteToString(byte[] buff)
{
    string sbinary = "";
    for (int i = 0; i < buff.Length; i++)
    {
        sbinary += buff[i].ToString("X2"); /* hex format */
    }
    return (sbinary);
}    

After many tets, in found that i get the same results if PHP hash_hmac key is a string, not a byte Array . Seems that the problem is with the PHP convert function $binKey = pack("H*", $keyTest);

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

The problem must be the actual representation of the key/message data.

See the following tests:

PHP

#!/usr/bin/php
<?php
print strtoupper(hash_hmac("sha256", "message", "key"));
?>

Output (live via http://writecodeonline.com/php/):

6E9EF29B75FFFC5B7ABAE527D58FDADB2FE42E7219011976917343065F58ED4A

C#

using System;
using System.Text;
using System.Security.Cryptography;

public class Program
{
    private const string key = "key";
    private const string message = "message";
    private static readonly Encoding encoding = Encoding.UTF8; 

    static void Main(string[] args)
    {
        var keyByte = encoding.GetBytes(key);
        using (var hmacsha256 = new HMACSHA256(keyByte))
        {
            hmacsha256.ComputeHash(encoding.GetBytes(message));

            Console.WriteLine("Result: {0}", ByteToString(hmacsha256.Hash));
        }
    }
    static string ByteToString(byte[] buff)
    {
        string sbinary = "";
        for (int i = 0; i < buff.Length; i++)
            sbinary += buff[i].ToString("X2"); /* hex format */
        return sbinary;
    }    
}

Output (live via http://ideone.com/JdpeL):

Result: 6E9EF29B75FFFC5B7ABAE527D58FDADB2FE42E7219011976917343065F58ED4A

So, check the character set/encoding of the PHP input data. Also check the actual algorithm (in $pbx_hash).


与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...