[Webinar] Learn how to a build a cloud-first strategyRegister Now

x
  • Status: Solved
  • Priority: Medium
  • Security: Public
  • Views: 3331
  • Last Modified:

isAdmin function and administrator rights in Windows 7

I have programmed a Delphi application (I am using Delphi 2006 ) that checks for icons associations at startup. For this reason I have been using the isAdmin function that I found on the web. I have attached a simplified piece of my code; in brief in the FormShow procedure I pass

      if isAdmin then GetAssociations;

and then in 'procedure GetAssociations' I open a Registry key and read and write to it.

In Windows Xp and Windows Vista the program faced no difficuties and, whenever the user had administrator rights, it associated the icons.

On the contrary, in Windows 7 when the user is an administrator the program moves to the GetAssociations procedure (i.e. isAdmin=true), and opens the registry key and reads successfully from it. However, it cannot write to the registry and when I try to WriteString to the Registry, it gives a glorious error message: Failed to set data for ''.
Note that when I right-click on the executable and I Run as Administrator the error does not occur.

Any ideas of how to solve this problem in Windows 7?

Thanks in advance,




procedure TMainForm.FormShow(Sender: TObject);
begin
    //associate the AppIcon to the input files
    if isAdmin then
        AssociateIcons;
end;

function IsAdmin: Boolean;
var 
  hAccessToken: THandle; 
  ptgGroups: PTokenGroups; 
  dwInfoBufferSize: DWORD; 
  psidAdministrators: PSID; 
  x: Integer; 
  bSuccess: BOOL; 
begin 
  Result := False;
  bSuccess := OpenThreadToken(GetCurrentThread, TOKEN_QUERY, 
                              True,hAccessToken); 
  if not bSuccess then 
  begin 
    if GetLastError = ERROR_NO_TOKEN then 
    bSuccess := OpenProcessToken(GetCurrentProcess, 
                          TOKEN_QUERY,hAccessToken); 
  end; 
  if bSuccess then 
  begin 
    GetMem(ptgGroups, 1024); 
    bSuccess := GetTokenInformation(hAccessToken,   
             TokenGroups,ptgGroups, 1024, dwInfoBufferSize); 
    CloseHandle(hAccessToken); 
    if bSuccess then 
    begin 
      AllocateAndInitializeSid(SECURITY_NT_AUTHORITY, 2, 
        SECURITY_BUILTIN_DOMAIN_RID, DOMAIN_ALIAS_RID_ADMINS, 
        0, 0, 0, 0, 0, 0, psidAdministrators); 
      {$R-} 
      for x := 0 to ptgGroups.GroupCount - 1 do 
        if EqualSid(psidAdministrators, 
                     ptgGroups.Groups[x].Sid) then 
        begin 
          Result := True; 
          Break; 
        end; 
      {$R+} 
      FreeSid(psidAdministrators); 
    end; 
    FreeMem(ptgGroups); 
  end; 
end;

procedure TMainForm.AssociateIcons;
var
  str : string;
  AskNow,AskNext : boolean;
  Assoc : boolean;
begin
    AskNow := RIniFile.ReadBool
                   ('Settings\General','AskAgainIcons',true);
    AskNext := AskNow;
    with TRegistry.Create do
    begin
        Assoc := true;
        RootKey := HKEY_CLASSES_ROOT;
        //first for project files
        OpenKey('\'+AppShortName+'.input',True);
        WriteString('',AppShortName+' Project File');
        //.................
        //...more code...
        //.................
        
        Destroy;
    end;

     RIniFile.WriteBool
            ('Settings\General','AskAgainIcons',AskNext);

end;

Open in new window

0
Stelios_Antoniou
Asked:
Stelios_Antoniou
  • 3
  • 2
1 Solution
 
ChristianWimmerCommented:
The code is just wrong! Once it was written to work with Windows 2000 and XP. Because these OS don't use restricted tokens the code works.
However, Vista introduced restricted tokens (people know it as UAC).

Instead use code that uses AccessCheck or CheckTokenMembership (http://msdn.microsoft.com/en-us/library/aa376389%28VS.85%29.aspx)
Here (http://www.delphipraxis.net/post730030.html#730030) source is available for you.
0
 
Stelios_AntoniouAuthor Commented:
To be honest, I was expecting that it was something so fundamentally wrong. Thanks for the prompt response.  However, I really did not understand which piece of code exactly to use (I do not know German) from the delphipraxis page

Moreover, do I have to distinguish in the code between the cases of Win2000/WinXP and WinVista/Win7 and use the relevant functions? Can you please write dome sample code?
0
 
Stelios_AntoniouAuthor Commented:
Finally, the compiler did not recognise the PSID, ULONG and BOOL words. A declaration that is missing possibly?
0
 
ChristianWimmerCommented:
The code for Win7/Vista is backwards compatible. No OS check is necessary. Just use the code, the german chat is unimportant :)

PSID, ULONG and BOOL should be defined in your Delphi unit Windows.pas.

 
0
 
Stelios_AntoniouAuthor Commented:
Thanks Christian!
0

Featured Post

Concerto's Cloud Advisory Services

Want to avoid the missteps to gaining all the benefits of the cloud? Learn more about the different assessment options from our Cloud Advisory team.

  • 3
  • 2
Tackle projects and never again get stuck behind a technical roadblock.
Join Now