Advertisement
Guest User

Untitled

a guest
Mar 24th, 2013
52
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Pascal 2.33 KB | None | 0 0
  1. (*
  2.   HMAC plugin.
  3.   Copyright (C) 2012-2014 Silvio Clecio.
  4.  
  5.   Please see the LICENSE file.
  6. *)
  7.  
  8. unit HMAC;
  9.  
  10. {$mode objfpc}{$H+}
  11.  
  12. interface
  13.  
  14. uses
  15.   SysUtils, SHA1;
  16.  
  17. const
  18.   SHA1_BLOCK_SIZE = 64;
  19.   SHA1_BLOCK_COUNT = 20;
  20.   SHA1_HEX_TABLE: array[0..15] of Char = '0123456789abcdef';
  21.  
  22. function SHA1Raw(const ABuffer; const ABufferLength: PtrUInt): string;
  23. { TODO: function HMACMD5(const AKey, AMessage: string): string; }
  24. function HMACSHA1(const AKey, AMessage: string): string;
  25.  
  26. implementation
  27.  
  28. function SHA1Raw(const ABuffer; const ABufferLength: PtrUInt): string;
  29. var
  30.   I: Byte;
  31.   VDest: PChar;
  32.   VBytes : TBytes;
  33.   VDigest: TSHA1Digest;
  34.   VContext: TSHA1Context;
  35. begin
  36.   Result := '';
  37.   SHA1Init(VContext);
  38.   SHA1Update(VContext, ABuffer, ABufferLength);
  39.   SHA1Final(VContext, VDigest);
  40.   SetLength(VBytes, SHA1_BLOCK_COUNT);
  41.   Move(VDigest, VBytes[0], SHA1_BLOCK_COUNT);
  42.   SetLength(Result, SHA1_BLOCK_COUNT);
  43.   VDest := Pointer(Result);
  44.   for I := 0 to SHA1_BLOCK_COUNT - 1 do
  45.   begin
  46.     VDest^ := Char(VBytes[I]);
  47.     Inc(VDest);
  48.   end;
  49. end;
  50.  
  51. function HMACSHA1(const AKey, AMessage: string): string;
  52. var
  53.   I: Byte;
  54.   VDest: PChar;
  55.   VLenght: PtrUInt;
  56.   VDigest: TSHA1Digest;
  57.   VKey, VOPad, VIPad: string;
  58. begin
  59.   VLenght := Length(AKey);
  60.   if VLenght > SHA1_BLOCK_SIZE then
  61.   begin
  62.     SetLength(VKey, SHA1_BLOCK_SIZE);
  63.     FillChar(Pointer(VKey)^, SHA1_BLOCK_SIZE, #0);
  64.     VKey := SHA1Raw(Pointer(AKey)^, VLenght) + VKey;
  65.   end
  66.   else
  67.   begin
  68.     SetLength(VKey, SHA1_BLOCK_SIZE - VLenght);
  69.     FillChar(Pointer(VKey)^, SHA1_BLOCK_SIZE - VLenght, #0);
  70.     VKey := AKey + VKey;
  71.   end;
  72.   SetLength(VOPad, SHA1_BLOCK_SIZE);
  73.   FillChar(Pointer(VOPad)^, SHA1_BLOCK_SIZE, $5c);
  74.   SetLength(VIPad, SHA1_BLOCK_SIZE);
  75.   FillChar(Pointer(VIPad)^, SHA1_BLOCK_SIZE, $36);
  76.   for I := 1 to SHA1_BLOCK_SIZE do
  77.   begin
  78.     VOPad[I] := Char(Byte(VOPad[I]) xor Byte(VKey[I]));
  79.     VIPad[I] := Char(Byte(VIPad[I]) xor Byte(VKey[I]));
  80.   end;
  81.   VIPad := VIPad + AMessage;
  82.   VDigest := SHA1String(VOPad + SHA1Raw(Pointer(VIPad)^, Length(VIPad)));
  83.   SetLength(Result, SHA1_BLOCK_COUNT * 2);
  84.   VDest := Pointer(Result);
  85.   for I := 0 to SHA1_BLOCK_COUNT - 1 do
  86.   begin
  87.     VDest[0] := SHA1_HEX_TABLE[(VDigest[I] shr 4) and 15];
  88.     VDest[1] := SHA1_HEX_TABLE[VDigest[I] and 15];
  89.     Inc(VDest, 2);
  90.   end;
  91. end;
  92.  
  93. end.
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement