50% OFF!!!

Showing posts with label program. Show all posts
Showing posts with label program. Show all posts

Wednesday, January 2, 2013

NSIS - Launch a program as user from UAC elevated installer

NSIS - Launch a program as user from UAC elevated installer
==========================================

I noticed that if a program is running as UAC elevated (admin or high user privileges), 
any opening process by this process will get the same privileges as the executing program,
which means, that any process opened by this UAC elevated program will be elevated also.

I found a solution for it, for opening the process UN-ELEVATED from ELEVATED running program.
I show this information as for NSIS installer, but can be used in ANY development environment (C#, NSIS, C++, JAVA, VB, and any).

The idea is to run the process in UN-ELEVATED mode, using windows's file explorer process `explorer.exe` (info).
Lets say the process that we want to launch is on `$TEMP\MyUnElevatedProcess.exe`.
So, for NSIS code, I will just write:

Exec '"$WINDIR\explorer.exe" "$TEMP\MyUnElevatedProcess.exe"'

And this will do the work...
The process `MyUnElevatedProcess.exe` will run with same ELEVATION that have your windows login, as have `$WINDIR\explorer.exe`.


Execute with parameters:
In addition, if the UN-ELEVATED process need to executed with parameters, you will need to create another file that executes the UN-ELEVATED process (for example a BATCH file which just run the process with the command line parameters).
a good example can be:
; assuming that the file `MyUnElevatedProcess.exe` exists on `$TEMP\`

; create shortcut with ARGUMENTS
CreateShortCut "$TEMP\Shortcut.lnk" "$TEMP\MyUnElevatedProcess.exe" "/arg1 /arg2 /arg3"

; execute the file NON elevated
Exec '"$WINDIR\explorer.exe" "$TEMP\Shortcut.lnk"'


Remember,
if your main program (the executing), is not ELEVATED, this logic is not relevant, because then you can just run `Exec` (open-process function in NSIS) which will have the same elevation as your process.

I hope it helps,
MDB-BLOG

Thursday, December 2, 2010

C# | check if program/application is installed on remote computer

As an advance to my previous post about checking if a program or an application is installed on my comptuer, I bringing a code for doing this validation on a remote computer.

The code is the same as checking for installed app in local comptuer (as described here) except that checking remote machine registry.
The remote machine registry checking is preformed using the static method OpenRemoteBaseKey of the class RegistryKey.

The code:
public static bool IsAppInstalled(string p_machineName, string p_name)
{
   string keyName;
 
   // search in: CurrentUser
   keyName = @"SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall";
   if (ExistsInRemoteSubKey(p_machineName, RegistryHive.CurrentUser, keyName, "DisplayName", p_name) == true)
   {
      return true;
   }
 
   // search in: LocalMachine_32
   keyName = @"SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall";
   if (ExistsInRemoteSubKey(p_machineName, RegistryHive.LocalMachine, keyName, "DisplayName", p_name) == true)
   {
      return true;
   }
 
   // search in: LocalMachine_64
   keyName = @"SOFTWARE\Wow6432Node\Microsoft\Windows\CurrentVersion\Uninstall";
   if (ExistsInRemoteSubKey(p_machineName, RegistryHive.LocalMachine, keyName, "DisplayName", p_name) == true)
   {
      return true;
   }
 
   return false;
}
private static bool ExistsInRemoteSubKey(string p_machineName, RegistryHive p_hive, string p_subKeyName, string p_attributeName, string p_name)
{
   RegistryKey subkey;
   string displayName;
 
   using (RegistryKey regHive = RegistryKey.OpenRemoteBaseKey(p_hive, p_machineName))
   {
      using (RegistryKey regKey = regHive.OpenSubKey(p_subKeyName))
      {
         if (regKey != null)
         {
            foreach (string kn in regKey.GetSubKeyNames())
            {
               using (subkey = regKey.OpenSubKey(kn))
               {
                  displayName = subkey.GetValue(p_attributeName) as string;
                  if (p_name.Equals(displayName, StringComparison.OrdinalIgnoreCase) == true) // key found!
                  {
                     return true;
                  }
               }
            }
         }
      }
   }
   return false;
}
    

How to use this code:
string MACHINE_NAME = "MY-PC-NAME";
string APPLICATION_NAME = "APP-NAME";
try
{
bool isAppInstalled = IsAppInstalled(MACHINE_NAME, APPLICATION_NAME);
  string msg = string.Format("Application '{0}' is {1} on the remote-machine '{2}'!",
APPLICATION_NAME,
isAppInstalled ? "installed" : "NOT installed",
MACHINE_NAME);
MessageBox.Show(msg);
}
catch (Exception ex)
{
MessageBox.Show(ex.Message);
}



Enjoy...
MDB-Blog

Wednesday, September 1, 2010

C# | check if program/application is installed

I searched for a code that getting the list of installed application/programs on my windows pc, but the result wat not satisfying.
I saw that the list of installed programs that i find is NOT like the "Add-Remove Programs" list!!!
The solution is to search for 3 places in registry:
1. SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall inside CurrentUser
2. SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall inside LocalMachine
3. SOFTWARE\Wow6432Node\Microsoft\Windows\CurrentVersion\Uninstall in LocalMachine
And this is my solution...

The Code:
public static bool IsApplictionInstalled(string p_name)
{
    string displayName;
    RegistryKey key;

    // search in: CurrentUser
    key = Registry.CurrentUser.OpenSubKey(@"SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall");
    foreach (String keyName in key.GetSubKeyNames())
    {
        RegistryKey subkey = key.OpenSubKey(keyName);
        displayName = subkey.GetValue("DisplayName") as string;
        if (p_name.Equals(displayName, StringComparison.OrdinalIgnoreCase) == true)
        {
            return true;
        }
    }

    // search in: LocalMachine_32
    key = Registry.LocalMachine.OpenSubKey(@"SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall");
    foreach (String keyName in key.GetSubKeyNames())
    {
        RegistryKey subkey = key.OpenSubKey(keyName);
        displayName = subkey.GetValue("DisplayName") as string;
        if (p_name.Equals(displayName, StringComparison.OrdinalIgnoreCase) == true)
        {
            return true;
        }
    }

    // search in: LocalMachine_64
    key = Registry.LocalMachine.OpenSubKey(@"SOFTWARE\Wow6432Node\Microsoft\Windows\CurrentVersion\Uninstall");
    foreach (String keyName in key.GetSubKeyNames())
    {
        RegistryKey subkey = key.OpenSubKey(keyName);
        displayName = subkey.GetValue("DisplayName") as string;
        if (p_name.Equals(displayName, StringComparison.OrdinalIgnoreCase) == true)
        {
            return true;
        }
    }

    // NOT FOUND
    return false;
}

This is great for searching for installed / uninstall programs.
I would like for some comments...