Solved

Binary values & strings

Posted on 1998-12-25
8
344 Views
Last Modified: 2010-04-04
Hi

I need to retrieve the Outlook default profile key from the Registry and then to access it.

If I get Profile UID from HKEY_CURRENT_USER\Software\Microsoft\Windows Messaging Subsystem\Profiles\Microsoft Outlook , I get a string value.

In the Registry it is a binary value.

I need to get the binary value as a string

For example, in Regedit I see the value as :
C0 B3 74 44 91 9A D2 11 A8 CE 00 40 95 A0 5F 99 09

This binary value means À³tD‘šÒ¨Î , if I have the string, how can I have the binary value as a string? (String:='C0 B3 74 44 91 9A D2 11 A8 CE 00 40 95 A0 5F 99 09')


I hope you'll understand me.

Saar


0
Comment
Question by:saar2
  • 4
  • 3
8 Comments
 
LVL 5

Expert Comment

by:heathprovost
ID: 1352922
I think I can answer this, but you need to clarify more - do you want to convert the value of one of the keys in a profile to a string representation of it?  for example:
key value = C0 B3 74 44 91 9A D2 11 A8 CE 00 40 95 A0 5F 99 09

you want to get a string that represents this like
 'C0 B3 74 44 91 9A D2 11 A8 CE 00 40 95 A0 5F 99 09'?

Is this what you are trying to do?
0
 
LVL 3

Expert Comment

by:williams2
ID: 1352923
This must be it then..

I must warn you, that the buffer length is just a fictive value.

Function ReadBinaryKey: String;
var
  i,Len: Integer;
  Buf: PByteArray;
  Registry: TRegistry;
Begin
  Registry:= TRegistry.Create;
  Registry.RootKey:= HKEY_CURRENT_USER;
  If Registry.OpenKey('Software\Microsoft\Windows Messaging Subsystem\Profiles\Microsoft Outlook',False) then
  Begin
    Buf:= AllocMem($FFFF);
    Len:= Registry.ReadBinaryData('Profile',Buf^,$FFFF);
    Result:= '';
    For i:= 0 to Len-1 do Result:= Result+IntToHex(Buf[i],2)+' ';
    If Len>0 then Delete(Result,Length(Result),1); //Delete last space
    FreeMem(Buf,$FFFF);
  End else
    ShowMessage('Didn''t find key!');
  Registry.free;
End;

procedure TForm1.Button1Click(Sender: TObject);
var
  S: String;
begin
  S:= ReadBinaryKey;
  If S<>'' then ShowMessage(S);
end;


Regards,
Williams
0
 
LVL 4

Author Comment

by:saar2
ID: 1352924
williams2, I forgot to say I use Delphi 1. There is no Tregistry component.

Saar
0
 
LVL 3

Accepted Solution

by:
williams2 earned 50 total points
ID: 1352925
You certainly did, Saar!

Use this instead then: make a button and a ButtonClick event procedure, then paste this to unit1

unit Unit1;

interface

uses
  Windows, Messages, SysUtils, Classes, Graphics, Controls, Forms, Dialogs,
  StdCtrls;

const
  HKEY_CLASSES_ROOT     = $80000000;
  HKEY_CURRENT_USER     = $80000001;
  HKEY_LOCAL_MACHINE    = $80000002;
  HKEY_USERS            = $80000003;
  HKEY_PERFORMANCE_DATA = $80000004;
  HKEY_CURRENT_CONFIG   = $80000005;
  HKEY_DYN_DATA         = $80000006;

type
  HKEY = Integer;

  TRegDataType = (rdUnknown, rdString, rdExpandString, rdInteger, rdBinary);

  TRegDataInfo = record
    RegData: TRegDataType;
    DataSize: Integer;
  end;

  TMyReg = class
  private
    CurrentKey: HKEY;
    function GetDataInfo(const ValueName: string; var Value: TRegDataInfo): Boolean;
  public
    CurrentPath: String;
    Root: HKEY;
    Constructor Create;
    Destructor Destroy; override;
    Function OpenKey(const Key: String): Boolean;
    function ReadBinaryData(const Name: string; var Buffer; BufSize: Integer): Integer;
    function GetData(const Name: string; Buffer: Pointer;
      BufSize: Integer; var RegData: TRegDataType): Integer;
    Procedure CloseKey;
  End;

  TForm1 = class(TForm)
    Button1: TButton;
    procedure Button1Click(Sender: TObject);
  private
    { Private declarations }
  public
    { Public declarations }
  end;

var
  Form1: TForm1;

implementation

{$R *.DFM}

Constructor TMyReg.Create;
Begin
  Root:= HKEY_CLASSES_ROOT;
End;

Function TMyReg.OpenKey(const Key: String): Boolean;
var
  TempKey: HKey;
begin
  TempKey := 0;
  Result := RegOpenKeyEx(Root, PChar(Key), 0, KEY_ALL_ACCESS, TempKey) = ERROR_SUCCESS;
  if Result then
  begin
    If CurrentKey<>0 then CloseKey;
    CurrentKey:= TempKey;
  end;
end;

function DataTypeToRegData(Value: Integer): TRegDataType;
begin
  if Value = REG_SZ then Result := rdString
  else if Value = REG_EXPAND_SZ then Result := rdExpandString
  else if Value = REG_DWORD then Result := rdInteger
  else if Value = REG_BINARY then Result := rdBinary
  else Result := rdUnknown;
end;

function TMyReg.GetDataInfo(const ValueName: string; var Value: TRegDataInfo): Boolean;
var
  DataType: Integer;
begin
  FillChar(Value, SizeOf(TRegDataInfo), 0);
  Result := RegQueryValueEx(CurrentKey, PChar(ValueName), nil, @DataType, nil,
    @Value.DataSize) = ERROR_SUCCESS;
  Value.RegData := DataTypeToRegData(DataType);
end;

function TMyReg.GetData(const Name: string; Buffer: Pointer;
  BufSize: Integer; var RegData: TRegDataType): Integer;
var
  DataType: Integer;
begin
  DataType := REG_NONE;
  if RegQueryValueEx(CurrentKey, PChar(Name), nil, @DataType, PByte(Buffer),
    @BufSize) <> ERROR_SUCCESS then
  Begin
    ShowMessage('Failed to get data');
    Application.Terminate;
  End;
  Result := BufSize;
  RegData := DataTypeToRegData(DataType);
end;

function TMyReg.ReadBinaryData(const Name: string; var Buffer; BufSize: Integer): Integer;
var
  RegData: TRegDataType;
  Info: TRegDataInfo;
begin
  if GetDataInfo(Name, Info) then
  begin
    Result := Info.DataSize;
    RegData := Info.RegData;
    if (RegData = rdBinary) and (Result <= BufSize) then
      GetData(Name, @Buffer, Result, RegData)
    else
    begin
      ShowMessage('Registry Error: '+Name);
      Application.Terminate;
    End;
  end else
    Result := 0;
end;

Procedure TMyReg.CloseKey;
Begin
  RegCloseKey(CurrentKey);
  CurrentKey:= 0;
End;

Destructor TMyReg.Destroy;
Begin
  If CurrentKey<>0 then RegCloseKey(CurrentKey);
  inherited Destroy;
End;

Function ReadBinaryKey: String;
var
  i,Len: Integer;
  Buf: PByteArray;
  MyReg: TMyReg;
Begin
  MyReg:= TMyReg.Create;
  MyReg.Root:= HKEY_CURRENT_USER;
  If MyReg.OpenKey('Software\Microsoft\Windows Messaging Subsystem\Profiles\Microsoft Outlook') then
  Begin
    Buf:= AllocMem($FFFF);
    Len:= MyReg.ReadBinaryData('Profile',Buf^,$FFFF);
    Result:= '';
    For i:= 0 to Len-1 do Result:= Result+IntToHex(Buf[i],2)+' ';
    If Len>0 then Delete(Result,Length(Result),1); //Delete last space
    FreeMem(Buf,$FFFF);
  End else
    ShowMessage('Didn''t find key!');
  MyReg.free;
End;

procedure TForm1.Button1Click(Sender: TObject);
var
  S: String;
begin
  S:= ReadBinaryKey;
  If S<>'' then ShowMessage(S);
end;

end.


If the API functions are unknown to you, I will provide the imports to you.

Regards,
Williams
0
Is Your Active Directory as Secure as You Think?

More than 75% of all records are compromised because of the loss or theft of a privileged credential. Experts have been exploring Active Directory infrastructure to identify key threats and establish best practices for keeping data safe. Attend this month’s webinar to learn more.

 
LVL 4

Author Comment

by:saar2
ID: 1352926
When I compile this Unit I get an error saying :
"Error in module Unit1: Call to RegisterClasses is missing or incorrect"

What does it mean?

Saar
0
 
LVL 3

Expert Comment

by:williams2
ID: 1352927
I'm not sure, but to replace the TMyReg class type:

  TMyReg = class(TPersistent)
  private
    CurrentKey: HKEY;
    function GetDataInfo(const ValueName: string; var Value: TRegDataInfo): Boolean;
  public
    CurrentPath: String;
    Root: HKEY;
    Constructor Create;
    Destructor Destroy; override;
    Function OpenKey(const Key: String): Boolean;
    function ReadBinaryData(const Name: string; var Buffer; BufSize: Integer): Integer;
    function GetData(const Name: string; Buffer: Pointer;
      BufSize: Integer; var RegData: TRegDataType): Integer;
    Procedure CloseKey;
  End;

and replace this too:

Constructor TMyReg.Create;
Begin
  inherited create;
  Root:= HKEY_CLASSES_ROOT;
End;

Another thing:

Try debug the code, and tell me EXACTLY at witch codeline the error is being raised!

BTW: Why don't you upgrade your Delphi to a newer version? There's too many things that is not registrated, even Delphi 2 can provide 5 times more tah version 1.

Regards,
Williams
0
 
LVL 4

Author Comment

by:saar2
ID: 1352928
My school decided to buy Delphi 4.0 .
I'll get it next week and try again.

Saar
0
 
LVL 3

Expert Comment

by:williams2
ID: 1352929
Good for you :-)
0

Featured Post

Is Your Active Directory as Secure as You Think?

More than 75% of all records are compromised because of the loss or theft of a privileged credential. Experts have been exploring Active Directory infrastructure to identify key threats and establish best practices for keeping data safe. Attend this month’s webinar to learn more.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

Suggested Solutions

Hello everybody This Article will show you how to validate number with TEdit control, What's the TEdit control? TEdit is a standard Windows edit control on a form, it allows to user to write, read and copy/paste single line of text. Usua…
Introduction Raise your hands if you were as upset with FireMonkey as I was when I discovered that there was no TListview.  I use TListView in almost all of my applications I've written, and I was not going to compromise by resorting to TStringGrid…
Get a first impression of how PRTG looks and learn how it works.   This video is a short introduction to PRTG, as an initial overview or as a quick start for new PRTG users.
Here's a very brief overview of the methods PRTG Network Monitor (https://www.paessler.com/prtg) offers for monitoring bandwidth, to help you decide which methods you´d like to investigate in more detail.  The methods are covered in more detail in o…

932 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question

Need Help in Real-Time?

Connect with top rated Experts

11 Experts available now in Live!

Get 1:1 Help Now