/// <summary>
        /// Get a safer token.
        /// </summary>
        /// <param name="token">The base token.</param>
        /// <param name="level">The safer level to use.</param>
        /// <param name="make_inert">True to make the token inert.</param>
        /// <returns>The safer token.</returns>
        public static NtToken GetTokenFromSaferLevel(NtToken token, SaferLevel level, bool make_inert)
        {
            IntPtr level_handle;

            if (!Win32NativeMethods.SaferCreateLevel(SaferScope.User, level, Win32NativeMethods.SAFER_LEVEL_OPEN, out level_handle, IntPtr.Zero))
            {
                throw new SafeWin32Exception();
            }

            try
            {
                using (NtToken duptoken = token.Duplicate(TokenAccessRights.GenericRead | TokenAccessRights.GenericExecute))
                {
                    SafeKernelObjectHandle handle;
                    if (Win32NativeMethods.SaferComputeTokenFromLevel(level_handle,
                                                                      duptoken.Handle, out handle, make_inert ? SaferFlags.MakeInert : 0, IntPtr.Zero))
                    {
                        return(NtToken.FromHandle(handle));
                    }
                    else
                    {
                        throw new SafeWin32Exception();
                    }
                }
            }
            finally
            {
                Win32NativeMethods.SaferCloseLevel(level_handle);
            }
        }
Beispiel #2
0
 internal static extern bool SaferCreateLevel(SaferScope dwScopeId, SaferLevel dwLevelId, int OpenFlags, out IntPtr pLevelHandle, IntPtr lpReserved);
        public static NtToken GetTokenFromSaferLevel(NtToken token, SaferLevel level, bool make_inert)
        {
            IntPtr level_handle;

            if (!SaferCreateLevel(SaferScope.User, level, SAFER_LEVEL_OPEN, out level_handle, IntPtr.Zero))
            {
                throw new SafeWin32Exception();
            }

            try
            {
                using (NtToken duptoken = token.Duplicate(TokenAccessRights.GenericRead | TokenAccessRights.GenericExecute))
                {
                    SafeKernelObjectHandle handle;
                    if (SaferComputeTokenFromLevel(level_handle, duptoken.Handle, out handle, make_inert ? SaferFlags.MakeInert : 0, IntPtr.Zero))
                    {
                        return NtToken.FromHandle(handle);
                    }
                    else
                    {
                        throw new SafeWin32Exception();
                    }
                }
            }
            finally
            {
                SaferCloseLevel(level_handle);
            }
        }
 static extern bool SaferCreateLevel(SaferScope dwScopeId, SaferLevel dwLevelId, int OpenFlags, out IntPtr pLevelHandle, IntPtr lpReserved);
Beispiel #5
0
        public static Process CreateSaferProcess(String fileName, string arguments, SaferLevel saferLevel, IntegrityLevel integrityLevel, CreateProcessFlags flags = CreateProcessFlags.CREATE_NEW_CONSOLE)
        {
            IntPtr saferLevelHandle = IntPtr.Zero;

            //Create a SaferLevel handle to match what was requested
            if (!SaferCreateLevel(SaferLevelScope.User, saferLevel, SaferOpen.Open, out saferLevelHandle, IntPtr.Zero))
            {
                throw new Win32Exception(Marshal.GetLastWin32Error());
            }

            try
            {
                //Generate the access token to use, based on the safer level handle.
                IntPtr hToken = IntPtr.Zero;

                if (!SaferComputeTokenFromLevel(
                        saferLevelHandle,            // SAFER Level handle
                        IntPtr.Zero,                 // NULL is current thread token.
                        out hToken,                  // Target token
                        SaferTokenBehaviour.Default, // No flags
                        IntPtr.Zero))                // Reserved
                {
                    throw new Win32Exception(Marshal.GetLastWin32Error());
                }

                // Get the Integrity SID
                IntPtr pIntegritySid = GetIntegritySid(integrityLevel);

                // Construct a structure describing the token integrity level
                var TIL = new TOKEN_MANDATORY_LABEL();
                TIL.Label.Attributes = SE_GROUP_INTEGRITY;
                TIL.Label.Sid        = pIntegritySid;
                IntPtr pTIL = Marshal.AllocHGlobal(Marshal.SizeOf <TOKEN_MANDATORY_LABEL>());
                Marshal.StructureToPtr(TIL, pTIL, false);

                // Modify the token
                if (!SetTokenInformation(hToken, TOKEN_INFORMATION_CLASS.TokenIntegrityLevel, pTIL, (uint)Marshal.SizeOf <TOKEN_MANDATORY_LABEL>() + GetLengthSid(pIntegritySid)))
                {
                    throw new Win32Exception();
                }

                try
                {
                    //Now that we have a security token, we can lauch the process
                    //using the standard CreateProcessAsUser API
                    STARTUPINFO si = new STARTUPINFO();
                    si.cb        = Marshal.SizeOf(si);
                    si.lpDesktop = String.Empty;

                    var processAttributes = new SECURITY_ATTRIBUTES();
                    var threadAttributes  = new SECURITY_ATTRIBUTES();
                    // Spin up the new process
                    //bool result = CreateProcessAsUser(hToken, fileName, arguments,
                    bool result = CreateProcessAsUser(hToken, fileName, $"\"{fileName}\"{(arguments?.Length > 0 ? " " + arguments : "")}",
                                                      ref processAttributes,
                                                      ref threadAttributes,
                                                      false,                       //inherit handles
                                                      flags,
                                                      IntPtr.Zero,                 //environment
                                                      null,                        //current directory
                                                      ref si,                      //startup info
                                                      out PROCESS_INFORMATION pi); //process info

                    if (!result)
                    {
                        throw new Win32Exception(Marshal.GetLastWin32Error());
                    }

                    if (pi.hProcess != IntPtr.Zero)
                    {
                        CloseHandle(pi.hProcess);
                    }

                    if (pi.hThread != IntPtr.Zero)
                    {
                        CloseHandle(pi.hThread);
                    }

                    return(Process.GetProcessById(pi.dwProcessId));
                }
                finally
                {
                    if (hToken != IntPtr.Zero)
                    {
                        CloseHandle(hToken);
                    }
                }
            }
            finally
            {
                SaferCloseLevel(saferLevelHandle);
            }
        }
Beispiel #6
0
 public static extern bool SaferCreateLevel(SaferLevelScope scopeId, SaferLevel levelId, SaferOpen openFlags, out IntPtr levelHandle, IntPtr reserved);