sl@92: /* sl@92: sl@92: This Source Code Form is subject to the terms of the Mozilla Public sl@92: License, v. 2.0. If a copy of the MPL was not distributed with this sl@92: file, You can obtain one at http://mozilla.org/MPL/2.0/. sl@92: sl@92: Copyright (C) 2009-2010 Michael Möller sl@92: sl@92: */ sl@92: sl@92: using Microsoft.Win32; sl@92: using SharpDisplayManager.TaskScheduler; sl@92: using System; sl@92: using System.IO; sl@92: using System.Runtime.InteropServices; sl@92: using System.Security; sl@92: using System.Security.Principal; sl@92: using System.Windows.Forms; sl@93: using System.Deployment.Application; sl@92: sl@92: namespace SharpDisplayManager sl@92: { sl@92: public class StartupManager sl@92: { sl@92: private TaskSchedulerClass scheduler; sl@92: private bool startup; sl@92: private bool isAvailable; sl@92: sl@92: private const string REGISTRY_RUN = sl@92: @"Software\Microsoft\Windows\CurrentVersion\Run"; sl@92: sl@92: private bool IsAdministrator() sl@92: { sl@92: try sl@92: { sl@92: WindowsIdentity identity = WindowsIdentity.GetCurrent(); sl@92: WindowsPrincipal principal = new WindowsPrincipal(identity); sl@92: return principal.IsInRole(WindowsBuiltInRole.Administrator); sl@92: } sl@92: catch sl@92: { sl@92: return false; sl@92: } sl@92: } sl@92: sl@92: public StartupManager() sl@92: { sl@92: int p = (int)System.Environment.OSVersion.Platform; sl@92: if ((p == 4) || (p == 128)) sl@92: { sl@92: scheduler = null; sl@92: isAvailable = false; sl@92: return; sl@92: } sl@92: sl@92: if (IsAdministrator()) sl@92: { sl@92: try sl@92: { sl@92: scheduler = new TaskSchedulerClass(); sl@92: scheduler.Connect(null, null, null, null); sl@92: } sl@92: catch sl@92: { sl@92: scheduler = null; sl@92: } sl@92: sl@92: if (scheduler != null) sl@92: { sl@92: try sl@92: { sl@92: // check if the task scheduler is running sl@92: IRunningTaskCollection collection = scheduler.GetRunningTasks(0); sl@92: sl@92: ITaskFolder folder = scheduler.GetFolder("\\Sharp Display Manager"); sl@92: IRegisteredTask task = folder.GetTask("Startup"); sl@92: startup = (task != null) && sl@92: (task.Definition.Triggers.Count > 0) && sl@92: (task.Definition.Triggers[1].Type == sl@92: TASK_TRIGGER_TYPE2.TASK_TRIGGER_LOGON) && sl@92: (task.Definition.Actions.Count > 0) && sl@92: (task.Definition.Actions[1].Type == sl@92: TASK_ACTION_TYPE.TASK_ACTION_EXEC) && sl@92: (task.Definition.Actions[1] as IExecAction != null) && sl@92: ((task.Definition.Actions[1] as IExecAction).Path == sl@92: Application.ExecutablePath); sl@92: } sl@92: catch (IOException) sl@92: { sl@92: startup = false; sl@92: } sl@92: catch (UnauthorizedAccessException) sl@92: { sl@92: scheduler = null; sl@92: } sl@92: catch (COMException) sl@92: { sl@92: scheduler = null; sl@92: } sl@92: } sl@92: } sl@92: else sl@92: { sl@92: scheduler = null; sl@92: } sl@92: sl@92: if (scheduler == null) sl@92: { sl@92: try sl@92: { sl@92: using (RegistryKey key = sl@92: Registry.CurrentUser.OpenSubKey(REGISTRY_RUN)) sl@92: { sl@92: startup = false; sl@92: if (key != null) sl@92: { sl@92: string value = (string)key.GetValue("SharpDisplayManager"); sl@92: if (value != null) sl@93: startup = value == LaunchCommand; sl@92: } sl@92: } sl@92: isAvailable = true; sl@92: } sl@92: catch (SecurityException) sl@92: { sl@92: isAvailable = false; sl@92: } sl@92: } sl@92: else sl@92: { sl@92: isAvailable = true; sl@92: } sl@92: } sl@92: sl@92: private void CreateSchedulerTask() sl@92: { sl@92: ITaskDefinition definition = scheduler.NewTask(0); sl@92: definition.RegistrationInfo.Description = sl@92: "This task starts the Sharp Display Manager on Windows startup."; sl@92: definition.Principal.RunLevel = sl@92: TASK_RUNLEVEL.TASK_RUNLEVEL_HIGHEST; sl@92: definition.Settings.DisallowStartIfOnBatteries = false; sl@92: definition.Settings.StopIfGoingOnBatteries = false; sl@92: definition.Settings.ExecutionTimeLimit = "PT0S"; sl@92: sl@92: ILogonTrigger trigger = (ILogonTrigger)definition.Triggers.Create( sl@92: TASK_TRIGGER_TYPE2.TASK_TRIGGER_LOGON); sl@92: sl@92: IExecAction action = (IExecAction)definition.Actions.Create( sl@92: TASK_ACTION_TYPE.TASK_ACTION_EXEC); sl@92: action.Path = Application.ExecutablePath; sl@92: action.WorkingDirectory = sl@92: Path.GetDirectoryName(Application.ExecutablePath); sl@92: sl@92: ITaskFolder root = scheduler.GetFolder("\\"); sl@92: ITaskFolder folder; sl@92: try sl@92: { sl@92: folder = root.GetFolder("Sharp Display Manager"); sl@92: } sl@92: catch (IOException) sl@92: { sl@92: folder = root.CreateFolder("Sharp Display Manager", ""); sl@92: } sl@92: folder.RegisterTaskDefinition("Startup", definition, sl@92: (int)TASK_CREATION.TASK_CREATE_OR_UPDATE, null, null, sl@92: TASK_LOGON_TYPE.TASK_LOGON_INTERACTIVE_TOKEN, ""); sl@92: } sl@92: sl@92: private void DeleteSchedulerTask() sl@92: { sl@92: ITaskFolder root = scheduler.GetFolder("\\"); sl@92: try sl@92: { sl@92: ITaskFolder folder = root.GetFolder("Sharp Display Manager"); sl@92: folder.DeleteTask("Startup", 0); sl@92: } sl@92: catch (IOException) { } sl@92: try sl@92: { sl@92: root.DeleteFolder("Sharp Display Manager", 0); sl@92: } sl@92: catch (IOException) { } sl@92: } sl@92: sl@93: string LaunchCommand sl@93: { sl@93: get sl@93: { sl@93: //Executable path won't launch ClickOnce Application with deployment enabled. sl@93: //return Application.ExecutablePath; sl@93: //Instead we need to launch the application using the .appref-ms shortcut. sl@93: //That shortcut is located at \\\.appref-ms sl@93: return string.Concat(Environment.GetFolderPath(Environment.SpecialFolder.Programs), "\\", "Slions", "\\", "Sharp Display Manager" , "\\" ,"Sharp Display Manager", ".appref-ms"); sl@93: } sl@93: } sl@93: sl@92: private void CreateRegistryRun() sl@92: { sl@92: RegistryKey key = Registry.CurrentUser.CreateSubKey(REGISTRY_RUN); sl@93: //Rather than the executable name we pass in the ClickOnce shortcut to make sure we launch with deployment support sl@93: key.SetValue("SharpDisplayManager", LaunchCommand); sl@92: } sl@92: sl@92: private void DeleteRegistryRun() sl@92: { sl@92: RegistryKey key = Registry.CurrentUser.CreateSubKey(REGISTRY_RUN); sl@92: key.DeleteValue("SharpDisplayManager"); sl@92: } sl@92: sl@92: public bool IsAvailable sl@92: { sl@92: get { return isAvailable; } sl@92: } sl@92: sl@92: public bool Startup sl@92: { sl@92: get sl@92: { sl@92: return startup; sl@92: } sl@92: set sl@92: { sl@92: if (startup != value) sl@92: { sl@92: if (isAvailable) sl@92: { sl@92: if (scheduler != null) sl@92: { sl@92: if (value) sl@92: CreateSchedulerTask(); sl@92: else sl@92: DeleteSchedulerTask(); sl@92: startup = value; sl@92: } sl@92: else sl@92: { sl@92: try sl@92: { sl@92: if (value) sl@92: CreateRegistryRun(); sl@92: else sl@92: DeleteRegistryRun(); sl@92: startup = value; sl@92: } sl@92: catch (UnauthorizedAccessException) sl@92: { sl@92: throw new InvalidOperationException(); sl@92: } sl@92: } sl@92: } sl@92: else sl@92: { sl@92: throw new InvalidOperationException(); sl@92: } sl@92: } sl@92: } sl@92: } sl@92: } sl@92: }