Jump to content

[SOLVED] HMAC SHA1


Recommended Posts

[solution SkinnyWhiteGuy]

Hi,

I have been trying to work with HMAC-SHA1 for oAuth, as it is the base requirement for generating the oAuth Signature.

According to the definition http://en.wikipedia.org/wiki/Hash-based_message_authentication_code

Definition (from RFC 2104)

HMAC (K,m) = H ((K ^ opad) || H ((K ^ ipad) || m))

where

H is a cryptographic hash function,

K is a secret key padded to the right with extra zeros to the input block size of the hash function, or the hash of the original key if it's longer than that block size,

m is the message to be authenticated,

|| denotes concatenation,

^ denotes exclusive or (XOR),

opad is the outer padding (0x5c5c5c…5c5c, one-block-long hexadecimal constant),

and ipad is the inner padding (0x363636…3636, one-block-long hexadecimal constant).

Since this is XOR of two strings I have used _StringEncrypt = RC4 = XOR two strings.

However, somewhere I am making a mistake and I getting a different result.

Need Help.

Regards

#include <Crypt.au3>
#include <String.au3>
$message = 'the'
$key = 'key'
$key = key_fill($key)
ConsoleWrite('Key        = ' & $key & @CRLF)
$opad = '0x'&_StringEncrypt(1, $key, padfill('5c', 64))
ConsoleWrite('Opad   = ' & $opad & @CRLF)
$ipad = '0x'&_StringEncrypt(1, $key, padfill('36', 64))
ConsoleWrite('Ipad   = ' & $ipad & @CRLF)
$val = _Crypt_HashData($opad & _Crypt_HashData($ipad & $message, $CALG_SHA1), $CALG_SHA1)
ConsoleWrite('OutPut Hash = ' & StringLower($val) & @CRLF)
ConsoleWrite(@CRLF & 'HMAC SHA1 from website http://caligatio.github.com/jsSHA/ ' & @CRLF _
& 'Input     = the ' & @CRLF _
& 'Key       = key ' & @CRLF _
& 'OutPut Hash = 0xe2bd5b5373d0602ec959cac3f83f5d1714744853' & @CRLF)
Func key_fill($keyfill)
If StringLen($keyfill) < 64 Then
While StringLen($keyfill) < 64
$keyfill &= 0
WEnd
Else
$keyfill = _Crypt_HashData($keyfill, $CALG_SHA1)
EndIf
Return $keyfill
EndFunc ;==>key_fill
Func padfill($pad, $blocksize)
Local $i = 1, $retpad
While $i <= 64
$retpad &= $pad
$i += 1
WEnd
ConsoleWrite($retpad &@CRLF)
Return $retpad
EndFunc ;==>padfill

The OutPut

Key      = key0000000000000000000000000000000000000000000000000000000000000
5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c5c
Opad     = 0x0B1BACB78CAE03D70B6993DC7F377E24B4C57CF4B51C5C2A875A71245C691C452FF81ED75B9AF81DB15C112E654AF8EA685F8B2F95CEA2B3D8FD6BE4680289B4DC589D2016184697A58E098608F80384BE7446FA95EE8B6AF7EEC332E051B021F10B49CF32110F3B9918FE704AA8C22A6C955F5A99370C184408185FD8982BAE
36363636363636363636363636363636363636363636363636363636363636363636363636363636363636363636363636363636363636363636363636363636
Ipad     = 0x159D405E7F0A5237C2810038FCBA216A4366FF99482CDD115D775BD0554F2A74457E227429511135CD511F6707A2BDD8C2FF3B2774FEAF59B1CB0258152204D66A475319B56793A82968090D19A0DE6FD9C2E7C52CBB759D7E6EC4231976A9363E99928F21EE2F8B31F101277CE935E7B0F62779126A528974208ABFF004060C
OutPut Hash = 0x8aa82e26740e55c7185f04432d82f064bf41e442
HMAC SHA1 from website http://caligatio.github.com/jsSHA/
Input    = the
Key      = key
OutPut Hash = 0xe2bd5b5373d0602ec959cac3f83f5d1714744853
Edited by DeltaRocked
Link to comment
Share on other sites

Some points for you to look at:

o) RC4 ≠ XOR

o) You seem to be confusing operation on strings and binary data. Look at you filled key: it should be a binary conatining the binary for 'key' appended with binary zeroes, not the character 0. Same for '5C' and '36'.

Once you change your code to perform on all binary data, I bet mud will clear a bit.

Edited by jchd

This wonderful site allows debugging and testing regular expressions (many flavors available). An absolute must have in your bookmarks.
Another excellent RegExp tutorial. Don't forget downloading your copy of up-to-date pcretest.exe and pcregrep.exe here
RegExp tutorial: enough to get started
PCRE v8.33 regexp documentation latest available release and currently implemented in AutoIt beta.

SQLitespeed is another feature-rich premier SQLite manager (includes import/export). Well worth a try.
SQLite Expert (freeware Personal Edition or payware Pro version) is a very useful SQLite database manager.
An excellent eBook covering almost every aspect of SQLite3: a must-read for anyone doing serious work.
SQL tutorial (covers "generic" SQL, but most of it applies to SQLite as well)
A work-in-progress SQLite3 tutorial. Don't miss other LxyzTHW pages!
SQLite official website with full documentation (may be newer than the SQLite library that comes standard with AutoIt)

Link to comment
Share on other sites

Some points for you to look at:

o) RC4 ≠ XOR

o) You seem to be confusing operation on strings and binary data. Look at you filled key: it should be a binary conatining the binary for 'key' appended with binary zeroes, not the character 0. Same for '5C' and '36'.

Once you change your code to perform on all binary data, I bet mud will clear a bit.

Hi jchd,

thanks for the inputs. will be back after sometime with whatever results I get.

btw any function available which will do XOR using a string?

[uPDATE]

XOR Function by piccaso being presently tested.

Regards

Edited by DeltaRocked
Link to comment
Share on other sites

Ok, here is the updated code , I guess I have ensured that everything is binary - atleast when the string is being processed.

but nowhere near the actual implementation of HMAC SHA1 :ranting:

#include <Crypt.au3>
#include <String.au3>
#include <Array.au3>
$message = 'the'
$key = 'key'
$key = key_fill($key)
ConsoleWrite('KeyLen = ' &StringLen($key)&@CRLF)
ConsoleWrite('Key = ' &StringToBinary($key)&@CRLF)
$opad = Encode( $key, '')
ConsoleWrite('Opad = ' & $opad & @CRLF)
$ipad = Encode($key,'6')
ConsoleWrite('Ipad = ' & $ipad & @CRLF)
$val = _Crypt_HashData($opad & _Crypt_HashData($ipad & $message, $CALG_SHA1), $CALG_SHA1)
ConsoleWrite('OutPut Hash = ' & StringLower($val) & @CRLF)
ConsoleWrite(@CRLF & 'HMAC SHA1 from website http://caligatio.github.com/jsSHA/ ' & @CRLF _
& 'Input     = the ' & @CRLF _
& 'Key   = key ' & @CRLF _
& 'OutPut Hash = 0xe2bd5b5373d0602ec959cac3f83f5d1714744853' & @CRLF)
Func key_fill($keyfill)
If StringLen($keyfill) < 64 Then
While StringLen($keyfill) < 64
$keyfill &= Chr(0)
WEnd
Else
$keyfill = _Crypt_HashData($keyfill, $CALG_SHA1)
EndIf
Return $keyfill
EndFunc ;==>key_fill
Func Encode($text, $xor)
Local $aASCII = StringToASCIIArray($text), $i
For $i = 0 To UBound($aASCII) - 1
$aASCII[$i] = Hex(BitXOR(Hex($aASCII[$i], 2), Hex(Asc($xor), 2)), 2)
Next
Return StringToBinary(_ArrayToString($aASCII, ""))
EndFunc ;==>Encode

The output.

KeyLen = 64
Key = 0x6B657900000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000
Opad = 0x3033343434413035303530353035303530353035303530353035303530353035303530353035303530353035303530353035303530353035303530353035303530353035303530353035303530353035303530353035303530353035303530353035303530353035303530353035303530353035303530353035303530353035
Ipad = 0x3232363536423234323432343234323432343234323432343234323432343234323432343234323432343234323432343234323432343234323432343234323432343234323432343234323432343234323432343234323432343234323432343234323432343234323432343234323432343234323432343234323432343234
OutPut Hash = 0xa07010179f9e4a18dd29e49d4d1536816e0105be
HMAC SHA1 from website http://caligatio.github.com/jsSHA/
Input    = the
Key  = key
OutPut Hash = 0xe2bd5b5373d0602ec959cac3f83f5d1714744853
Edited by DeltaRocked
Link to comment
Share on other sites

I was digging around some of my old code, and found this. Cleaned it up a little, and ensured it worked again.

I used Call on these, so with one HMAC function, you could use different hashing algorithms. Course, you'll have to modify the BlockSize for some hashing functions, but that's easily made an optional parameter and passed in for the larger block sizes of some hashing functions. It's also just as easy to remove the calls for the actual hash functions, if that's what you want.

#include <Crypt.au3>

Func sha1($message)
    Return _Crypt_HashData($message, $CALG_SHA1)
EndFunc

Func md5($message)
    Return _Crypt_HashData($message, $CALG_MD5)
EndFunc

Func hmac($key, $message, $hash="md5")
    Local $blocksize = 64
    Local $a_opad[$blocksize], $a_ipad[$blocksize]
    Local Const $oconst = 0x5C, $iconst = 0x36
    Local $opad = Binary(''), $ipad = Binary('')
    $key = Binary($key)
    If BinaryLen($key) > $blocksize Then $key = Call($hash, $key)
    For $i = 1 To BinaryLen($key)
        $a_ipad[$i-1] = Number(BinaryMid($key, $i, 1))
        $a_opad[$i-1] = Number(BinaryMid($key, $i, 1))
    Next
    For $i = 0 To $blocksize - 1
        $a_opad[$i] = BitXOR($a_opad[$i], $oconst)
        $a_ipad[$i] = BitXOR($a_ipad[$i], $iconst)
    Next
    For $i = 0 To $blocksize - 1
        $ipad &= Binary('0x' & Hex($a_ipad[$i],2))
        $opad &= Binary('0x' & Hex($a_opad[$i],2))
    Next
    Return Call($hash, $opad & Call($hash, $ipad & Binary($message)))
EndFunc

ConsoleWrite(hmac("key", "the", "sha1") & @CRLF)

Edit: Firefox ate my post, had to fix...

Edited by SkinnyWhiteGuy
Link to comment
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now
 Share

×
×
  • Create New...