Registry ReadString method is not working in Windows 7 in Delphi 7

前端 未结 6 485
感动是毒
感动是毒 2021-01-12 22:03

The following code sample used to return me windows id before, but now it doesn\'t work, and returns empty string, dunno why.

  function GetWindowsID: string         


        
6条回答
  •  不知归路
    2021-01-12 22:48

    There are usefull procedure to read Key Register in a 32 bit and 64 bit enviroment.First look what system you have

    Type TTypWin32Or64 = (Bit32,Bit64);
    var TypWin32Or64 :TTypWin32Or64;
    
     Procedure TypeOS(var TypWin32Or64:TTypWin32Or64 ) ;
       if DirectoryExists('c:\Windows\SysWOW64')
         then TypWin32Or64:=Bit64
         else TypWin32Or64:=Bit32;
    
      Procedure for looking Key or Create it in a Registry
       procedure TForm1.ReadKeyFromRegister(TypWin32Or64:TTypWin32Or64;
                           TypeKey:Longword; {at once symbol HKEY_LOCAL_MACHINE or HKEY_CURRENT_USER}
                           PathToKey:string;
                           TypeValueRead :Integer; //at once symbols as REG_SZ -- string key ,
                              //REG_DWORD A DWORD value, a 32-bit unsigned integer
                           NameValueToRead:string;
                           var ValueStrReaded:Ansistring; //is used if it is key string
                           var ValueByteReaded:Pchar; //is used if it is key Byte
                           ReadOnly:boolean);  
    var
      Reg       : TRegistry;
      S_TStr    : TStrings;
      VersBios  : string;
      Pos0      : integer;
      Key       : HKEY;
      Value     : Array of Byte;
      nValueLen :  Integer;
    const KEY_WOW64_64KEY = $0100 ;
     begin
      case TypWin32Or64 of
        Bit32: Reg := TRegistry.Create;
        Bit64:Reg := TRegistry.Create(KEY_WRITE OR KEY_WOW64_64KEY); 
        //use if if 64 bit enviroment Windows 
      end;
     try
      { open key }
       Reg.RootKey := TypeKey;
       if ReadOnly
         then Reg.OpenKeyReadOnly(PathToKey) 
            //not all key can be created or writed ie. ProductId(Serial Key)
            // name Windows - especially in a 64 bit Windows XP , Win 7  
         else Reg.OpenKey(PathToKey, false); 
            //CreateKey=True--> if this key is not present will be created
        case TypeValueRead of
         REG_SZ: ValueStrReaded:=Reg.ReadString(NameValueToRead);
         REG_BINARY : begin
                       nValueLen := Reg.GetDataSize(NameValueToRead);
                       ValueByteReaded:=Pchar(Reg.ReadBinaryData(NameValueToRead, PByte(Value), nValueLen));
                    end;
         REG_DWORD : begin
    
                     end;
         REG_MULTI_SZ: begin
                        S_TStr := ReadMultirowKey(Reg,NameValueToRead);
                           /in a enviroment 64 bit not good work - better use       
                           //procedure ReadREG_MULTI_SZ
                         VersBios:=S_TStr.Text;
                         Pos0:=Pos(#0,VersBios);
                         if Pos0 > 0  then
                           begin
                            delete(VersBios,Pos0,1);
                            insert(' ', VersBios,Pos0);
                           end;
                         VersBios := StringReplace(VersBios,#$D#$A, ' ' , [rfReplaceAll, rfIgnoreCase]);
                       ValueStrReaded:=VersBios;
                     end;
          end;  //case
          Reg.CloseKey;
       finally
        Reg.Free;
      end;
    end;
    {------------}
    
     Sample for reading system Key from Registry
       Reading UsedWindowsVersion_Full
         ReadKeyFromRegister(TypWin32Or64, {TypWin32Or64}
                      HKEY_LOCAL_MACHINE, {TypeKey:Longword;}
                      'SOFTWARE\Microsoft\Windows NT\CurrentVersion', {PathToKey:string;}
                              REG_SZ, {TypeValueRead :Integer; }
                              'BuildLabEx', {NameValueToRead:string;}
                              UsedWindowsVersion_Full, {ValueStrReaded:Ansistring;}
                              sPchar ,{ValueByteReaded:Pchar}
                              True {ReadOnly});
                {-----------------------}   
    
          For read ProductId(also called Product Key Windows)
               ReadKeyFromRegister( TypWin32Or64,
                       HKEY_LOCAL_MACHINE, {TypeKey:Longword;}
                      'SOFTWARE\Microsoft\Windows NT\CurrentVersion', {PathToKey:string;}
                              REG_SZ, {TypeValueRead :Integer; }
                              'ProductId', {NameValueToRead:string;}
                              SerialKey, {ValueStrReaded:Ansistring;}
                              sPchar, {ValueByteReaded:Pchar}
                              True {ReadOnly});
                 {------------------------}   
         For reading Product Name
             ReadKeyFromRegister(TypWin32Or64,
                      HKEY_LOCAL_MACHINE, {TypeKey:Longword;}
                      'SOFTWARE\Microsoft\Windows NT\CurrentVersion', {PathToKey:string;}
                              REG_SZ, {TypeValueRead :Integer; }
                              'ProductName', {NameValueToRead:string;}
                              UsedWindowsName, {ValueStrReaded:Ansistring;}
                              sPchar ,{ValueByteReaded:Pchar}
                              True {ReadOnly});   
               {-----------------------}
      Procedure for look miltiline key as i.e Version Bios - also 64 envir.
    
         procedure  TForm1.ReadREG_MULTI_SZ(const CurrentKey: HKey; const   
                                       Subkey, ValueName: string;
                                       Strings: TStrings; var ValueStrRead: String);
           var
             valueType: DWORD;
             valueLen: DWORD;
             p, buffer: PChar;
             key: HKEY;
            begin
             Strings.Clear;
               // open the specified key
           if RegOpenKeyEx(CurrentKey,
                  PChar(Subkey),
                  0, KEY_READ, key) = ERROR_SUCCESS then
              begin
                // retrieve the type and data for a specified value name
                SetLastError(RegQueryValueEx(key,
                 PChar(ValueName),
                 nil,
                 @valueType,
                 nil,
                 @valueLen));
                 if GetLastError = ERROR_SUCCESS then
                    if valueType = REG_MULTI_SZ then
                      begin
                       GetMem(buffer, valueLen);
                       try
                        // receive the value's data (in an array).
                        RegQueryValueEx(key,
                                        PChar(ValueName),
                                        nil,
                                        nil,
                                        PBYTE(buffer),
                                        @valueLen);
                         // Add values to stringlist
                         p := buffer;
                         while p^ <> #0 do
                            begin
                             Strings.Add(p);
                             Inc(p, lstrlen(p) + 1)
                            end
                        finally
                          ValueStrRead:=Strings.Text;
                          ValueStrRead:=StringReplace(ValueStrRead,#$D#$A, ' ' , [rfReplaceAll, rfIgnoreCase]);
                          FreeMem(buffer);
                         end
                       end
                    else
                     raise ERegistryException.Create('Stringlist expected')
                      else
                       raise ERegistryException.Create('Cannot Read MULTI_SZ    Value/');
               end;
            end;
          {-----------}     
    

提交回复
热议问题