EldoS | Feel safer!

Software components for data protection, secure storage and transfer

MD5 Hash

Also by EldoS: Rethync
The cross-platform framework that simplifies synchronizing data between mobile and desktop applications and servers and cloud storages
#12542
Posted: 02/22/2010 15:38:36
by desslock (Basic support level)
Joined: 02/22/2010
Posts: 1

Hey guys,

I was wondering if I might be doing something wrong here. I'm getting inconsistent results when using the HashMD5() function within SBMD.pas. I'm trying to generate a hash of a file's contents. The file, itself, could be either text or binary. There are two other libraries available to us to accomplish this task: Indy and Delphi's own MessageDialog_5.pas that's included with D2009; however, we're trying to keep things standardized as much as possible. We're currently using version 7.2.169 of the SecureBlackbox library.

I set up a test application using the following calls and compared the MD5 hash results to those generated by Indy and Delphi. Whereas Indy's and Delphi's results matched each other, SecureBlackbox had some trouble.

Code
{:---------------------------------------------------------
@summary Calculates an MD5 hash using SecureBlackBox
@----------------------------------------------------------}
function TForm1.CalcMD5SBB: string;
var
  FStream: TBytesStream;
begin
  FStream := TBytesStream.Create;

  try
    { Load the file }
    FStream.LoadfromFile(edtFileName.Text);
    Result := DigestToStr(SBMD.HashMD5(ByteArray(FStream.Bytes)));
  finally
    FStream.Free;
  end;
end;

{:---------------------------------------------------------
@summary Calculates an MD5 hash using SecureBlackBox
@----------------------------------------------------------}
function TForm1.CalcMD5SBB2: string;
var
  FStream: TStringStream;
begin
  FStream := TStringStream.Create;

  try
    { Load the file }
    FStream.LoadfromFile(edtFileName.Text);
    Result := DigestToStr(SBMD.HashMD5(FStream.DataString));
  finally
    FStream.Free;
  end;
end;

What I noticed is that while the second call matched those returned by Indy's and Delphi's own MD5 Hash algorithm, the first call returned a completely different value. I could use the second call, but it would make more logical sense (from a coding and maintenance standpoint) to use the first, if possible.

Am I calling that method incorrectly?

Thanks for any help you can provide.

-John

P.S. Interestingly, there are a few binary files that I've tested that did return a matching hash using the first method call; however most times the results were different -- even when using a simple text file that contained the single word "Test".
#12550
Posted: 02/23/2010 00:26:03
by Eugene Mayevski (EldoS Corp.)

Use TElHashFunction to calculate hashes. Do the search in this forum for "TElHashFunction" to get code samples and comments regarding it's use.


Sincerely yours
Eugene Mayevski
#12551
Posted: 02/23/2010 00:34:10
by Ken Ivanov (EldoS Corp.)

Thank you for contacting us.

Please try to use the following approach (it seems that the compiler incorrectly calls the second overload of HashMD5() function that accepts AnsiString parameter, instead of calling the one that accepts byte array parameter; the input data gets corrupted this way):

Code
var
  Func : TElHashFunction;
  F : TFileStream;
  Dgst : BufferType;
begin
  F := TFileStream.Create(edFilename.Text, fmOpenRead or fmShareDenyWrite);
  try
    Func := TElHashFunction.Create(SB_ALGORITHM_DGST_MD5, nil);
    try
      Func.Update(F);
      Dgst := Func.Finish();
    finally
      FreeAndNil(Func);
    end;
    Result := BinaryToString(Dgst);
  finally
    FreeAndNil(F);
  end;
end;
#33015
Posted: 04/10/2015 08:09:30
by Paul Severini (Standard support level)
Joined: 08/12/2013
Posts: 5

I'll give it a try. Thanks.
#33988
Posted: 07/10/2015 17:28:01
by Walter Schrabmair (Priority Standard support level)
Joined: 05/03/2013
Posts: 150

I tried with the latest SBB 12 this:
But got a compiler error!
Can anyone help please?
Thanks


Code
function TForm1.ByteToString(const Value: ByteArray): String;
var    
   I: integer;    
   S : AnsiString;    
   Letra: char;

begin    
   S := '';    
   for I := Length(Value)-1 Downto 0 do
        begin
        letra := Chr(Value[I] + 48);
       S := letra + S;
       end;
     Result := S;
end;

function TFOrm1.GetMD5String (Str: String): String;
var
  Func : TElHashFunction;
  //F : TFileStream;
  F : TMemoryStream;
  Dgst : ByteArray;
begin
  //F := TFileStream.Create(edFilename.Text, fmOpenRead or fmShareDenyWrite);
  F := TMemoryStream.Create;
  F.WriteBuffer(Pointer(Str)^, Length(Str));
  F.Position := 0;
  try
    Func := TElHashFunction.Create(SB_ALGORITHM_DGST_MD5);  
    try
      Func.Update(F);
      Dgst := Func.Finish(); // WHere is ByteArray declared????
// see https://www.eldos.com/documentation/sbb/documentation/ref_cl_hashfunction_mtd_finish.html

// I got it : In SBTYPES; But if I add it in my use clause I get the error below:


    finally
      FreeAndNil(Func);
    end;
    Result := ByteToString(Dgst);
  finally
    FreeAndNil(F);
  end;
end;


Now after adding SBTypes to uses, I get an compiler error here

Code
function SetPrinterColorMode(InColor : Boolean) : Boolean;
var
  Device : array[0..MAX_PATH] of char;
  Driver : array[0..MAX_PATH] of char;
  Port   : array[0..MAX_PATH] of char;
  hDMode : THandle;
  PDMode : PDEVMODE;
begin
  result := FALSE;
  Printer.PrinterIndex := Printer.PrinterIndex;
  Printers.Printer.GetPrinter(Device, Driver, Port, hDMode); // HERE I get an error: The nuber of parameter must correlate. (translated)
  if hDMode <> 0 then begin
    pDMode := GlobalLock(hDMode);
    if pDMode <> nil then begin
      if (pDMode^.dmFields AND dm_Color) = dm_Color then begin
        if (InColor) then begin
          pDMode^.dmColor := DMCOLOR_COLOR;
        end else begin
          pDMode^.dmColor := DMCOLOR_MONOCHROME;
        end;
        result := TRUE;
      end;
      GlobalUnlock(hDMode);
      Printer.PrinterIndex := Printer.PrinterIndex;
    end;
  end;
end;


Any help or idears?

I think THandle is also in SBTypes, right? How can I use this with my printers?
Thanks
#33989
Posted: 07/10/2015 17:44:40
by Ken Ivanov (EldoS Corp.)

Hi Walter,

The ByteArray type if defined in SBTypes namespace.

As a side note, please note that the following line produces incorrect results with Unicode strings:

F.WriteBuffer(Pointer(Str)^, Length(Str));

Length(Str) call returns the number of characters in the string, while WriteBuffer() expects the size to be provided in bytes. Therefore the above code will only copy the first half of the string to the memory stream.

Ken
#33990
Posted: 07/10/2015 17:47:03
by Ken Ivanov (EldoS Corp.)

Quote
Printers.Printer.GetPrinter(Device, Driver, Port, hDMode); // HERE I get an error: The nuber of parameter must correlate. (translated)

Hmm, this looks pretty much like a compiler bug. Are there any further details or suggestions provided by the compiler about the error?
#33991
Posted: 07/11/2015 00:31:43
by Walter Schrabmair (Priority Standard support level)
Joined: 05/03/2013
Posts: 150

Quote
Length(Str) call returns the number of characters in the string, while WriteBuffer() expects the size to be provided in bytes. Therefore the above code will only copy the first half of the string to the memory stream.
Thanks a lot, Ken. So this will not work properly, then I have to use my own MD5 Routine. (I found one in the interen, where MD5PRINT() is following defined:
Code
// Create hex representation of given Digest
function MD5Print(D: MD5Digest): string;
var
   I: byte;
const
   Digits: array[0..15] of char =
      ('0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'a', 'b', 'c', 'd', 'e', 'f');
begin
   Result := '';
   for I := 0 to 15 do Result := Result + Digits[(D[I] shr 4) and $0f] + Digits[D[I] and $0f];
end;



See:
Quote
http://en.pudn.com/downloads139/sourcecode/delphi_control/detail598661_en.html
#33992
Posted: 07/11/2015 00:33:37
by Walter Schrabmair (Priority Standard support level)
Joined: 05/03/2013
Posts: 150

Quote
Hmm, this looks pretty much like a compiler bug. Are there any further details or suggestions provided by the compiler about the error?


But without SBTypes in the Uses it works fine. In Delphi 7 and in Delpphi XE6! It must ly on SBB.
COuld you reproduce it, Ken?
walter
Also by EldoS: Solid File System
A virtual file system that offers a feature-rich storage for application documents and data with built-in compression and encryption.

Reply

Statistics

Topic viewed 4120 times

Number of guests: 1, registered members: 0, in total hidden: 0




|

Back to top

As of July 15, 2016 EldoS Corporation will operate as a division of /n software inc. For more information, please read the announcement.

Got it!