|
|
@@ -0,0 +1,71 @@ |
|
|
using System; |
|
|
using System.Threading; |
|
|
using System.Windows; |
|
|
using System.Windows.Controls; |
|
|
using System.Runtime.InteropServices; |
|
|
using System.Windows.Threading; |
|
|
|
|
|
class Program |
|
|
{ |
|
|
// DESKTOP_ACCESS |
|
|
const UInt32 DESKTOP_NONE = 0x0000u; |
|
|
const UInt32 DESKTOP_READOBJECTS = 0x0001u; |
|
|
const UInt32 DESKTOP_CREATEWINDOW = 0x0002u; |
|
|
const UInt32 DESKTOP_CREATEMENU = 0x0004u; |
|
|
const UInt32 DESKTOP_HOOKCONTROL = 0x0008u; |
|
|
const UInt32 DESKTOP_JOURNALRECORD = 0x0010u; |
|
|
const UInt32 DESKTOP_JOURNALPLAYBACK = 0x0020u; |
|
|
const UInt32 DESKTOP_ENUMERATE = 0x0040u; |
|
|
const UInt32 DESKTOP_WRITEOBJECTS = 0x0080u; |
|
|
const UInt32 DESKTOP_SWITCHDESKTOP = 0x0100u; |
|
|
|
|
|
const UInt32 dwDesiredAccess = |
|
|
DESKTOP_READOBJECTS | |
|
|
DESKTOP_CREATEWINDOW | |
|
|
DESKTOP_CREATEMENU | |
|
|
DESKTOP_WRITEOBJECTS | |
|
|
DESKTOP_SWITCHDESKTOP; |
|
|
|
|
|
[DllImport("kernel32.dll")] static extern uint GetCurrentThreadId(); |
|
|
[DllImport("user32.dll")] static extern IntPtr GetThreadDesktop(uint dwThreadId); |
|
|
[DllImport("user32.dll")] static extern IntPtr CreateDesktop(string desktopName, IntPtr device, IntPtr deviceMode, uint flags, uint accessMask, IntPtr attributes); |
|
|
[DllImport("user32.dll")] static extern bool SetThreadDesktop(IntPtr hDesktop); |
|
|
[DllImport("user32.dll")] static extern bool CloseDesktop(IntPtr hDesktop); |
|
|
[DllImport("user32.dll")] static extern bool SwitchDesktop(IntPtr hDesktop); |
|
|
|
|
|
[STAThread] |
|
|
public static void Main() |
|
|
{ |
|
|
var btn = new Button() { Content = "Open secure desktop" }; |
|
|
btn.Click += (s, e) => SecureDialog(); |
|
|
var win = new Window() { Content = btn }; |
|
|
new Application().Run(win); |
|
|
} |
|
|
|
|
|
static void SecureDialog() |
|
|
{ |
|
|
var hOldDesktop = GetThreadDesktop(GetCurrentThreadId()); |
|
|
var hNewDesktop = CreateDesktop("My desktop", IntPtr.Zero, IntPtr.Zero, 0, dwDesiredAccess, IntPtr.Zero); |
|
|
SwitchDesktop(hNewDesktop); |
|
|
|
|
|
var thread = new Thread( () => SecureDesktopThread(hNewDesktop) ); |
|
|
thread.SetApartmentState(ApartmentState.STA); |
|
|
thread.Start(); |
|
|
thread.Join(); // Wait for thread to complete. |
|
|
|
|
|
SwitchDesktop(hOldDesktop); |
|
|
CloseDesktop(hNewDesktop); |
|
|
} |
|
|
|
|
|
static void SecureDesktopThread(IntPtr hNewDesktop) |
|
|
{ |
|
|
SetThreadDesktop(hNewDesktop); |
|
|
|
|
|
SynchronizationContext.SetSynchronizationContext( |
|
|
new DispatcherSynchronizationContext(Dispatcher.CurrentDispatcher)); |
|
|
|
|
|
var win = new Window() { Content = "Hello World!", FontSize=30 }; |
|
|
win.ShowDialog(); |
|
|
Dispatcher.CurrentDispatcher.InvokeShutdown(); |
|
|
} |
|
|
} |