diff cinst/nssstore_win.c @ 824:a511c1f45c70

(Issue47) Drop privileges before executing NSS process.
author Andre Heinecke <andre.heinecke@intevation.de>
date Mon, 21 Jul 2014 18:51:34 +0200
parents 85c5aa9aba2b
children 24e1e47e2d1a
line wrap: on
line diff
--- a/cinst/nssstore_win.c	Mon Jul 21 12:55:54 2014 +0200
+++ b/cinst/nssstore_win.c	Mon Jul 21 18:51:34 2014 +0200
@@ -39,6 +39,7 @@
 */
 
 #include <windows.h>
+#include <winsafer.h>
 #include <sddl.h>
 #include <stdio.h>
 #include <stdbool.h>
@@ -69,6 +70,35 @@
 /**@def The registry key to look for user profile directories */
 #define PROFILE_LIST L"Software\\Microsoft\\Windows NT\\CurrentVersion\\ProfileList"
 
+/** @brief get a restricted access token to execute nss process
+  *
+  * This function uses the Software Restriction API to obtain the
+  * access token for a process run als normal user.
+  *
+  * @returns A restricted handle or NULL on error.
+  */
+static HANDLE
+get_restricted_token()
+{
+  SAFER_LEVEL_HANDLE user_level = NULL;
+  HANDLE retval = NULL;
+  if (!SaferCreateLevel(SAFER_SCOPEID_USER,
+                        SAFER_LEVELID_NORMALUSER,
+                        SAFER_LEVEL_OPEN, &user_level, NULL))
+    {
+      PRINTLASTERROR ("Failed to create user level.\n");
+      return NULL;
+    }
+
+   if (!SaferComputeTokenFromLevel(user_level, NULL, &retval, 0, NULL))
+    {
+        SaferCloseLevel(user_level);
+        return NULL;
+    }
+
+   return retval;
+}
+
 /**@brief Write strv of instructions to a handle
 *
 * Writes the null terminated list of instructions to
@@ -652,14 +682,21 @@
   /* set up handles. stdin and stdout go to the same stdout*/
   siStartInfo.cb = sizeof (STARTUPINFO);
 
-  if(!OpenProcessToken(GetCurrentProcess(), TOKEN_ALL_ACCESS, &hToken))
+  if (is_elevated())
+    {
+      /* Start the child process as normal user */
+      hToken = get_restricted_token ();
+      if (hToken == NULL)
+        {
+          ERRORPRINTF ("Failed to get user level token.");
+          return false;
+        }
+    }
+  else if(!OpenProcessToken(GetCurrentProcess(), TOKEN_ALL_ACCESS, &hToken))
     {
       PRINTLASTERROR("Failed to get current handle.");
       return false;
     }
-  /* TODO! if (is_elevated())
-     restrict token -> hChildToken
-  */
 
   lpCommandLine = get_command_line (selection_file);
 

http://wald.intevation.org/projects/trustbridge/