source: branches/eraser6/Eraser/Program.cs @ 752

Revision 752, 25.9 KB checked in by lowjoel, 6 years ago (diff)

Actually send the correct schedule, not just parse the command line correctly.

  • Property svn:keywords set to Id
RevLine 
[349]1/*
2 * $Id$
3 * Copyright 2008 The Eraser Project
4 * Original Author: Joel Low <lowjoel@users.sourceforge.net>
5 * Modified By:
6 *
7 * This file is part of Eraser.
8 *
9 * Eraser is free software: you can redistribute it and/or modify it under the
10 * terms of the GNU General Public License as published by the Free Software
11 * Foundation, either version 3 of the License, or (at your option) any later
12 * version.
13 *
14 * Eraser is distributed in the hope that it will be useful, but WITHOUT ANY
15 * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR
16 * A PARTICULAR PURPOSE. See the GNU General Public License for more details.
17 *
18 * A copy of the GNU General Public License can be found at
19 * <http://www.gnu.org/licenses/>.
20 */
21
22using System;
[78]23using System.Collections.Generic;
24using System.Windows.Forms;
25
[222]26using Eraser.Manager;
[314]27using Eraser.Util;
[234]28using Microsoft.Win32;
29using System.IO;
[303]30using System.Runtime.Serialization.Formatters.Binary;
[310]31using System.Globalization;
[612]32using System.Reflection;
[737]33using System.Diagnostics;
[222]34
[78]35namespace Eraser
36{
37    static class Program
38    {
39        /// <summary>
40        /// The main entry point for the application.
41        /// </summary>
42        [STAThread]
[608]43        static void Main(string[] commandLine)
[78]44        {
[612]45            //Trivial case: no command parameters
[608]46            if (commandLine.Length == 0)
47                GUIMain(false);
[612]48
49            //Determine if the sole parameter is --restart; if it is, start the GUI
50            //passing isRestart as true. Otherwise, we're a console application.
[608]51            else if (commandLine.Length == 1)
52            {
[612]53                if (commandLine[0] == "/restart" || commandLine[0] == "--restart")
[608]54                {
55                    GUIMain(true);
56                }
57                else
58                {
59                    CommandMain(commandLine);
60                }
61            }
[612]62
63            //The other trivial case: definitely a console application.
[608]64            else
65                CommandMain(commandLine);
66        }
67
[612]68        /// <summary>
69        /// Runs Eraser as a command-line application.
70        /// </summary>
71        /// <param name="commandLine">The command line parameters passed to Eraser.</param>
[608]72        private static void CommandMain(string[] commandLine)
73        {
[624]74            //True if the user specified a quiet command.
75            bool isQuiet = false;
[612]76
77            try
78            {
[624]79                CommandLineProgram program = new CommandLineProgram(commandLine);
80                isQuiet = program.Arguments.Quiet;
[631]81
82                using (ManagerLibrary library = new ManagerLibrary(new Settings()))
83                    program.Run();
[612]84            }
[616]85            catch (Exception e)
86            {
87                Console.WriteLine(e.Message);
88            }
[612]89            finally
90            {
[624]91                //Flush the buffered output to the console
[612]92                Console.Out.Flush();
93
[617]94                //Don't ask for a key to press if the user specified Quiet
[624]95                if (!isQuiet)
[617]96                {
97                    Console.Write("\nPress any key to continue . . . ");
98                    Console.Out.Flush();
99                    Console.ReadLine();
100                }
[631]101
102                KernelAPI.FreeConsole();
[624]103            }
104        }
[612]105
[624]106        /// <summary>
107        /// Runs Eraser as a GUI application.
108        /// </summary>
109        /// <param name="isRestart">True if the program was passed the --restart
110        /// switch.</param>
111        private static void GUIMain(bool isRestart)
112        {
113            Application.EnableVisualStyles();
114            Application.SetCompatibleTextRenderingDefault(false);
115            Application.SafeTopLevelCaptionFormat = S._("Eraser");
116
117            using (ManagerLibrary library = new ManagerLibrary(new Settings()))
[740]118            using (eraserClient = new RemoteExecutorServer())
[624]119            {
120                //Set our UI language
121                EraserSettings settings = new EraserSettings();
122                System.Threading.Thread.CurrentThread.CurrentUICulture =
123                    new CultureInfo(settings.Language);
124
125                //Load the task list
126                if (settings.TaskList != null)
127                    using (MemoryStream stream = new MemoryStream(settings.TaskList))
128                        try
129                        {
130                            eraserClient.LoadTaskList(stream);
131                        }
132                        catch (Exception)
133                        {
134                            settings.TaskList = null;
135                            MessageBox.Show(S._("Could not load task list. All task entries have " +
136                                "been lost."), S._("Eraser"), MessageBoxButtons.OK,
137                                MessageBoxIcon.Error);
138                        }
139
140                //Create the main form
141                MainForm form = new MainForm();
142
143                //Run tasks which are meant to be run on restart
144                if (isRestart)
145                {
146                    eraserClient.QueueRestartTasks();
147                }
148
149                //Run the program
150                eraserClient.Run();
151                Application.Run(form);
152
153                //Save the task list
154                using (MemoryStream stream = new MemoryStream())
155                {
156                    eraserClient.SaveTaskList(stream);
157                    settings.TaskList = stream.ToArray();
158                }
[612]159            }
[608]160        }
161
[612]162        /// <summary>
[624]163        /// The global Executor instance.
[616]164        /// </summary>
[624]165        public static Executor eraserClient;
166
167        /// <summary>
168        /// Handles commands passed to the program
169        /// </summary>
170        /// <param name="arguments">The arguments to the command</param>
171        private delegate void CommandHandler(Dictionary<string, string> arguments);
172    }
173
174    class CommandLineProgram
175    {
176        #region Command Line parsing classes
177        /// <summary>
178        /// Manages a command line.
179        /// </summary>
180        public class CommandLine
[616]181        {
[624]182            /// <summary>
183            /// Constructor.
184            /// </summary>
185            /// <param name="cmdParams">The raw arguments passed to the program.</param>
186            public CommandLine(string[] cmdParams)
187            {
188                //Get the action.
189                if (cmdParams.Length < 1)
190                    throw new ArgumentException("An action must be specified.");
191                Action = cmdParams[0];
192
193                //Iterate over each argument, resolving them ourselves and letting
194                //subclasses resolve them if we don't know how to.
195                for (int i = 1; i != cmdParams.Length; ++i)
196                {
197                    if (IsParam(cmdParams[i], "quiet", "q"))
198                        Quiet = true;
199                    else if (!ResolveParameter(cmdParams[i]))
200                        throw new ArgumentException("Unknown argument: " + cmdParams[i]);
201                }
202            }
203
204            /// <summary>
205            /// Called when a parameter is not used by the current CommandLine object
206            /// for subclasses to handle their parameters.
207            /// </summary>
208            /// <param name="param">The parameter to resolve.</param>
209            /// <returns>Return true if the parameter was resolved and accepted.</returns>
210            virtual protected bool ResolveParameter(string param)
211            {
212                return false;
213            }
214
215            /// <summary>
216            /// Checks if the given <paramref name="parameter"/> refers to the
217            /// <paramref name="expectedParameter"/>, regardless of whether it is specified
218            /// with -, --, or /
219            /// </summary>
220            /// <param name="parameter">The parameter on the command line.</param>
221            /// <param name="expectedParameter">The parameter the program is looking for, without
222            /// the - or / prefix.</param>
223            /// <param name="shortParameter">The short parameter when used with a single hyphen,
224            /// without the - or / prefix.</param>
225            /// <returns>True if the parameter references the given expected parameter.</returns>
226            protected static bool IsParam(string parameter, string expectedParameter,
227                string shortParameter)
228            {
229                //Trivial case
230                if (parameter.Length < 1)
231                    return false;
232
233                //Extract the bits before the equal sign.
234                {
235                    int equalPos = parameter.IndexOf('=');
236                    if (equalPos != -1)
237                        parameter = parameter.Substring(0, equalPos);
238                }
239
240                //Get the first letter.
241                switch (parameter[0])
242                {
243                    case '-':
244                        //Can be a - or a --. Check for the second parameter
245                        if (parameter.Length < 2)
246                            //Nothing specified at the end... it's invalid.
247                            return false;
248
249                        if (parameter[1] == '-')
250                            return parameter.Substring(2) == expectedParameter;
251                        else if (shortParameter == null || shortParameter == string.Empty)
252                            return parameter.Substring(1) == expectedParameter;
253                        else
254                            return parameter.Substring(1) == shortParameter;
255                       
256                    case '/':
257                        //The / can be used with both long and short parameters.
258                        parameter = parameter.Substring(1);
259                        return parameter == expectedParameter || (
260                            shortParameter != null && shortParameter != string.Empty &&
261                            parameter == shortParameter
262                        );
263
264                    default:
265                        return false;
266                }
267            }
268
269            /// <summary>
270            /// Gets the list of subparameters of the parameter. Subparameters are text
271            /// after the first =, separated by commas.
272            /// </summary>
273            /// <param name="param">The subparameter text to parse.</param>
274            /// <returns>The list of subparameters in the parameter.</returns>
275            protected static List<KeyValuePair<string, string>> GetSubParameters(string param)
276            {
277                List<KeyValuePair<string, string>> result =
278                    new List<KeyValuePair<string, string>>();
279                int lastPos = 0;
280                int commaPos = (param += ',').IndexOf(',');
281
282                while (commaPos != -1)
283                {
284                    //Extract the current subparameter, and dissect the subparameter at
285                    //the first =.
286                    string subParam = param.Substring(lastPos, commaPos - lastPos);
287                    int equalPos = subParam.IndexOf('=');
288                    if (equalPos == -1)
289                        result.Add(new KeyValuePair<string, string>(subParam, null));
290                    else
291                        result.Add(new KeyValuePair<string, string>(subParam.Substring(0, equalPos),
292                            subParam.Substring(equalPos + 1)));
293
294                    //Find the next ,
295                    lastPos = ++commaPos;
296                    commaPos = param.IndexOf(',', commaPos);
297                }
298
299                return result;
300            }
301
302            /// <summary>
303            /// The action that the command line specifies.
304            /// </summary>
305            public string Action
306            {
307                get
308                {
309                    return action;
310                }
311                private set
312                {
313                    action = value;
314                }
315            }
316
317            /// <summary>
318            /// True if no console window should be created.
319            /// </summary>
320            public bool Quiet
321            {
322                get
323                {
324                    return quiet;
325                }
326                private set
327                {
328                    quiet = value;
329                }
330            }
331
332            private string action;
333            private bool quiet;
[616]334        }
335
336        /// <summary>
[624]337        /// Manages a command line for adding tasks to the global DirectExecutor
[612]338        /// </summary>
[624]339        class AddTaskCommandLine : CommandLine
[612]340        {
[624]341            /// <summary>
342            /// Constructor.
343            /// </summary>
344            /// <param name="cmdParams">The raw command line arguments passed to the program.</param>
345            public AddTaskCommandLine(string[] cmdParams)
346                : base(cmdParams)
347            {
348            }
349
350            protected override bool ResolveParameter(string param)
351            {
352                int equalPos = param.IndexOf('=');
353                if (IsParam(param, "method", "m"))
354                {
355                    if (equalPos == -1)
356                        throw new ArgumentException("--method must be specified with an Erasure " +
357                            "method GUID.");
[751]358
359                    List<KeyValuePair<string, string>> subParams =
360                        GetSubParameters(param.Substring(equalPos + 1));
361                    ErasureMethod = new Guid(subParams[0].Key);
[624]362                }
[751]363                else if (IsParam(param, "schedule", "s"))
364                {
365                    if (equalPos == -1)
366                        throw new ArgumentException("--schedule must be specified with a Schedule " +
367                            "type.");
368
369                    List<KeyValuePair<string, string>> subParams =
370                        GetSubParameters(param.Substring(equalPos + 1));
371                    switch (subParams[0].Key)
372                    {
373                        case "now":
374                            Schedule = Schedule.RunNow;
375                            break;
376                        case "restart":
377                            schedule = Schedule.RunOnRestart;
378                            break;
379                        default:
380                            throw new ArgumentException("Unknown schedule type: " + subParams[0].Key);
381                    }
382                }
[624]383                else if (IsParam(param, "recycled", "r"))
384                {
385                    targets.Add(new Task.RecycleBin());
386                }
387                else if (IsParam(param, "unused", "u"))
388                {
389                    if (equalPos == -1)
390                        throw new ArgumentException("--unused must be specified with the Volume " +
391                            "to erase.");
392
393                    //Create the UnusedSpace target for inclusion into the task.
394                    Task.UnusedSpace target = new Task.UnusedSpace();
395
396                    //Determine if cluster tips should be erased.
397                    target.EraseClusterTips = false;
398                    List<KeyValuePair<string, string>> subParams =
399                        GetSubParameters(param.Substring(equalPos + 1));
400                    foreach (KeyValuePair<string, string> kvp in subParams)
401                        if (kvp.Value == null && target.Drive == null)
[747]402                            target.Drive = Path.GetFullPath(kvp.Key);
[624]403                        else if (kvp.Key == "clusterTips")
404                            target.EraseClusterTips = true;
405                        else
406                            throw new ArgumentException("Unknown subparameter: " + kvp.Key);
407                    targets.Add(target);
408                }
409                else if (IsParam(param, "dir", "d") || IsParam(param, "directory", null))
410                {
411                    if (equalPos == -1)
412                        throw new ArgumentException("--directory must be specified with the " +
413                            "directory to erase.");
414
415                    //Create the base target
416                    Task.Folder target = new Task.Folder();
417
418                    //Parse the subparameters.
419                    List<KeyValuePair<string, string>> subParams =
420                        GetSubParameters(param.Substring(equalPos + 1));
421                    foreach (KeyValuePair<string, string> kvp in subParams)
422                        if (kvp.Value == null && target.Path == null)
[747]423                            target.Path = Path.GetFullPath(kvp.Key);
[624]424                        else if (kvp.Key == "excludeMask")
425                        {
426                            if (kvp.Value == null)
427                                throw new ArgumentException("The exclude mask must be specified " +
428                                    "if the excludeMask subparameter is specified");
429                            target.ExcludeMask = kvp.Value;
430                        }
431                        else if (kvp.Key == "includeMask")
432                        {
433                            if (kvp.Value == null)
434                                throw new ArgumentException("The include mask must be specified " +
435                                    "if the includeMask subparameter is specified");
436                            target.IncludeMask = kvp.Value;
437                        }
438                        else if (kvp.Key == "delete")
439                            target.DeleteIfEmpty = true;
440                        else
441                            throw new ArgumentException("Unknown subparameter: " + kvp.Key);
442
443                    //Add the target to the list of targets
444                    targets.Add(target);
445                }
446                else
447                {
448                    //It's just a file!
449                    Task.File target = new Task.File();
[747]450                    target.Path = Path.GetFullPath(param);
[624]451                    targets.Add(target);
452                }
453
454                return true;
455            }
456
457            /// <summary>
458            /// The erasure method which the user specified on the command line.
459            /// </summary>
460            public Guid ErasureMethod
461            {
462                get
463                {
464                    return erasureMethod;
465                }
466                private set
467                {
468                    erasureMethod = value;
469                }
470            }
471
472            /// <summary>
[751]473            /// The schedule for the current set of targets.
474            /// </summary>
475            public Schedule Schedule
476            {
477                get
478                {
479                    return schedule;
480                }
481                set
482                {
483                    schedule = value;
484                }
485            }
486
487            /// <summary>
[624]488            /// The list of targets which was specified on the command line.
489            /// </summary>
490            public List<Task.ErasureTarget> Targets
491            {
492                get
493                {
494                    return new List<Task.ErasureTarget>(targets.ToArray());
495                }
496                set
497                {
498                    targets = value;
499                }
500            }
501
502            private Guid erasureMethod;
[751]503            private Schedule schedule = null;
[624]504            private List<Task.ErasureTarget> targets = new List<Task.ErasureTarget>();
[612]505        }
[624]506        #endregion
[612]507
508        /// <summary>
[624]509        /// Constructor.
[612]510        /// </summary>
[624]511        /// <param name="cmdParams">The raw command line arguments passed to the program.</param>
512        public CommandLineProgram(string[] cmdParams)
[612]513        {
[624]514            try
515            {
516                //Parse the command line arguments.
517                if (cmdParams.Length < 1)
518                    throw new ArgumentException("An action must be specified.");
[617]519
[624]520                switch (cmdParams[0])
521                {
522                    case "addtask":
523                        Arguments = new AddTaskCommandLine(cmdParams);
524                        break;
525                    case "querymethods":
526                    case "help":
527                    default:
528                        Arguments = new CommandLine(cmdParams);
529                        break;
530                }
531
532                //If the user did not specify the quiet command line, then create the console.
533                if (!Arguments.Quiet)
534                    CreateConsole();
535
536                //Map actions to their handlers
537                actionHandlers.Add("addtask", AddTask);
538                actionHandlers.Add("querymethods", QueryMethods);
539                actionHandlers.Add("help", Help);
540            }
541            finally
[617]542            {
[624]543                if (Arguments == null || !Arguments.Quiet)
544                    CreateConsole();
[617]545            }
[612]546        }
547
548        /// <summary>
[624]549        /// Runs the program, analogous to System.Windows.Forms.Application.Run.
[612]550        /// </summary>
[624]551        public void Run()
[612]552        {
[624]553            //Call the function handling the current command line.
[631]554            actionHandlers[Arguments.Action]();
[624]555        }
[612]556
[624]557        /// <summary>
558        /// Creates a console for our application, setting the input/output streams to the
559        /// defaults.
560        /// </summary>
561        private void CreateConsole()
562        {
563            if (KernelAPI.AllocConsole())
564            {
565                Console.SetOut(new StreamWriter(Console.OpenStandardOutput()));
566                Console.SetIn(new StreamReader(Console.OpenStandardInput()));
567            }
[612]568        }
569
570        /// <summary>
571        /// Prints the command line help for Eraser.
572        /// </summary>
573        private static void CommandUsage()
574        {
575            Console.WriteLine(@"usage: Eraser <action> <arguments>
576where action is
[750]577    help                    Show this help message.
[612]578    addtask                 Adds tasks to the current task list.
579    querymethods            Lists all registered Erasure methods.
580
[616]581global parameters:
[624]582    --quiet, -q             Do not create a Console window to display progress.
[616]583
[750]584parameters for help:
585    eraser help
586
587    no parameters to set.
588
[612]589parameters for addtask:
[750]590    eraser addtask [--method=<methodGUID>] [--schedule=(now|restart)] (--recycled " +
591@"| --unused=<volume> | --dir=<directory> | [file1 [file2 [...]]])
[612]592
593    --method, -m            The Erasure method to use.
[750]594    --schedule, -s          The schedule the task will follow. The value must
595                            be one of:
596            now             The task will be queued for immediate execution.
597            restart         The task will be queued for execution when the
598                            computer is next restarted.
[612]599    --recycled, -r          Erases files and folders in the recycle bin
600    --unused, -u            Erases unused space in the volume.
[624]601        optional arguments: --unused=<drive>[,clusterTips]
[750]602            clusterTips     If specified, the drive's files will have their
603                            cluster tips erased.
[612]604    --dir, --directory, -d  Erases files and folders in the directory
[624]605        optional arguments: --dir=<directory>[,e=excludeMask][,i=includeMask][,delete]
[750]606            excludeMask     A wildcard expression for files and folders to
607                            exclude.
608            includeMask     A wildcard expression for files and folders to
609                            include.
610                            The include mask is applied before the exclude
611                            mask.
612            delete          Deletes the folder at the end of the erasure if
613                            specified.
[612]614    file1 ... fileN         The list of files to erase.
615
616parameters for querymethods:
[624]617    eraser querymethods
618
619    no parameters to set.
620
621All arguments are case sensitive.");
[612]622            Console.Out.Flush();
623        }
624
[624]625        #region Action Handlers
[612]626        /// <summary>
[624]627        /// The command line arguments passed to the program.
[612]628        /// </summary>
[624]629        public CommandLine Arguments
[608]630        {
[624]631            get
[234]632            {
[624]633                return arguments;
634            }
635            private set
636            {
637                arguments = value;
638            }
639        }
[599]640
[624]641        /// <summary>
642        /// Prints the help text for Eraser (with copyright)
643        /// </summary>
644        private void Help()
645        {
646            Console.WriteLine(@"Eraser {0}
647(c) 2008 The Eraser Project
648Eraser is Open-Source Software: see http://eraser.heidi.ie/ for details.
649", Assembly.GetExecutingAssembly().GetName().Version);
[234]650
[624]651            Console.Out.Flush();
652            CommandUsage();
653        }
[238]654
[624]655        /// <summary>
656        /// Lists all registered erasure methods.
657        /// </summary>
658        /// <param name="commandLine">The command line parameters passed to the program.</param>
659        private void QueryMethods()
660        {
661            //Output the header
662            const string methodFormat = "{0,-2} {1,-39} {2}";
663            Console.WriteLine(methodFormat, "", "Method", "GUID");
664            Console.WriteLine(new string('-', 79));
[236]665
[624]666            //Refresh the list of erasure methods
667            Dictionary<Guid, ErasureMethod> methods = ErasureMethodManager.GetAll();
668            foreach (ErasureMethod method in methods.Values)
669            {
670                Console.WriteLine(methodFormat, (method is UnusedSpaceErasureMethod) ?
671                    "U" : "", method.Name, method.GUID.ToString());
672            }
673        }
[234]674
[624]675        /// <summary>
676        /// Parses the command line for tasks and adds them using the
677        /// <see cref="RemoteExecutor"/> class.
678        /// </summary>
679        /// <param name="commandLine">The command line parameters passed to the program.</param>
680        private void AddTask()
681        {
682            AddTaskCommandLine arguments = (AddTaskCommandLine)Arguments;
[737]683           
[624]684            //Create the task, and set the method to use.
685            Task task = new Task();
[737]686            ErasureMethod method = arguments.ErasureMethod == Guid.Empty ? 
687                ErasureMethodManager.Default :
688                ErasureMethodManager.GetInstance(arguments.ErasureMethod);
[624]689            foreach (Task.ErasureTarget target in arguments.Targets)
690            {
691                target.Method = method;
692                task.Targets.Add(target);
[234]693            }
[625]694
[751]695            //Check the number of tasks in the task.
696            if (task.Targets.Count == 0)
697                throw new ArgumentException("Tasks must contain at least one erasure target.");
698
[752]699            //Set the schedule for the task.
700            task.Schedule = arguments.Schedule;
701
[625]702            //Send the task out.
[750]703            using (Program.eraserClient = new RemoteExecutorClient())
704            {
705                if (!((RemoteExecutorClient)Program.eraserClient).Connect())
706                {
707                    //The client cannot connect to the server. This probably means
708                    //that the server process isn't running. Start an instance.
709                    Process eraserInstance = Process.Start(
710                        Assembly.GetExecutingAssembly().Location);
711                    eraserInstance.WaitForInputIdle();
712
713                    if (!((RemoteExecutorClient)Program.eraserClient).Connect())
714                        throw new Exception("Eraser cannot connect to the running " +
715                            "instance for erasures.");
716                }
717
718                Program.eraserClient.Run();
719                Program.eraserClient.AddTask(ref task);
720            }
[78]721        }
[624]722        #endregion
[222]723
[624]724        /// <see cref="Arguments"/>
725        private CommandLine arguments;
726
[607]727        /// <summary>
[624]728        /// The prototype of an action handler in the class which executes an
729        /// action as specified in the command line.
[607]730        /// </summary>
[624]731        private delegate void ActionHandler();
[612]732
733        /// <summary>
[624]734        /// Matches an action handler to a function in the class.
[612]735        /// </summary>
[624]736        private Dictionary<string, ActionHandler> actionHandlers =
737            new Dictionary<string, ActionHandler>();
[78]738    }
[238]739
[624]740    internal class Settings : Manager.SettingsManager
[238]741    {
[561]742        /// <summary>
743        /// Registry-based storage backing for the Settings class.
744        /// </summary>
745        private class RegistrySettings : Manager.Settings
[238]746        {
[561]747            /// <summary>
748            /// Constructor.
749            /// </summary>
750            /// <param name="key">The registry key to look for the settings in.</param>
751            public RegistrySettings(Guid pluginID, RegistryKey key)
[303]752            {
[561]753                this.key = key;
[303]754            }
[338]755
[561]756            public override object this[string setting]
757            {
758                get
[412]759                {
[561]760                    byte[] currentSetting = (byte[])key.GetValue(setting, null);
761                    if (currentSetting != null && currentSetting.Length != 0)
[412]762                        using (MemoryStream stream = new MemoryStream(currentSetting))
763                            try
764                            {
[561]765                                return new BinaryFormatter().Deserialize(stream);
[412]766                            }
767                            catch (Exception)
768                            {
[561]769                                key.DeleteValue(setting);
[581]770                                MessageBox.Show(S._("Could not load the setting {0} for plugin {1}. " +
771                                    "The setting has been lost.", key, pluginID.ToString()),
[412]772                                    S._("Eraser"), MessageBoxButtons.OK, MessageBoxIcon.Error);
773                            }
[561]774
775                    return null;
[412]776                }
[561]777                set
778                {
[597]779                    if (value == null)
[561]780                    {
[597]781                        key.DeleteValue(setting);
[561]782                    }
[597]783                    else
784                    {
785                        using (MemoryStream stream = new MemoryStream())
786                        {
787                            new BinaryFormatter().Serialize(stream, value);
788                            key.SetValue(setting, stream.ToArray(), RegistryValueKind.Binary);
789                        }
790                    }
[561]791                }
792            }
[412]793
[561]794            /// <summary>
795            /// The GUID of the plugin whose settings this object is storing.
796            /// </summary>
797            private Guid pluginID;
798
799            /// <summary>
800            /// The registry key where the data is stored.
801            /// </summary>
802            private RegistryKey key;
[412]803        }
804
[561]805        public override void Save()
[412]806        {
[561]807        }
808
809        protected override Manager.Settings GetSettings(Guid guid)
810        {
[412]811            //Open the registry key containing the settings
[573]812            const string eraserKeyPath = @"SOFTWARE\Eraser\Eraser 6";
813            RegistryKey eraserKey = Registry.CurrentUser.OpenSubKey(eraserKeyPath, true);
814            if (eraserKey == null)
815                eraserKey = Registry.CurrentUser.CreateSubKey(eraserKeyPath);
816
817            RegistryKey pluginsKey = eraserKey.OpenSubKey(guid.ToString(), true);
[561]818            if (pluginsKey == null)
[573]819                pluginsKey = eraserKey.CreateSubKey(guid.ToString());
[412]820
[561]821            //Return the Settings object.
822            return new RegistrySettings(guid, pluginsKey);
[238]823        }
824    }
[562]825
826    internal class EraserSettings
827    {
828        public EraserSettings()
829        {
830            settings = Manager.ManagerLibrary.Instance.SettingsManager.ModuleSettings;
831        }
832
833        /// <summary>
[594]834        /// Gets or sets the task list, serialised in binary form by the Manager assembly.
835        /// </summary>
836        public byte[] TaskList
837        {
838            get
839            {
840                return (byte[])settings["TaskList"];
841            }
842            set
843            {
844                settings["TaskList"] = value;
845            }
846        }
847
848        /// <summary>
[562]849        /// Gets or sets the LCID of the language which the UI should be displayed in.
850        /// </summary>
851        public string Language
852        {
853            get
854            {
855                return settings["Language"] == null ? 
856                    GetCurrentCulture().Name :
857                    (string)settings["Language"];
858            }
859            set
860            {
861                settings["Language"] = value;
862            }
863        }
864
865        /// <summary>
[742]866        /// Gets or sets whether the Shell Extension should be loaded into Explorer.
867        /// </summary>
868        public bool IntegrateWithShell
869        {
870            get
871            {
872                return settings["IntegrateWithShell"] == null ?
873                    true : (bool)settings["IntegrateWithShell"];
874            }
875            set
876            {
877                settings["IntegrateWithShell"] = value;
878            }
879        }
880
881        /// <summary>
[562]882        /// Gets or sets a value on whether the main frame should be minimised to the
883        /// system notification area.
884        /// </summary>
885        public bool HideWhenMinimised
886        {
887            get
888            {
889                return settings["HideWhenMinimised"] == null ?
890                    true : (bool)settings["HideWhenMinimised"];
891            }
892            set
893            {
894                settings["HideWhenMinimised"] = value;
895            }
896        }
897
898        /// <summary>
899        /// Gets the current UI culture, correct to the top-level culture (i.e., English
900        /// instead of English (United Kingdom))
901        /// </summary>
902        /// <returns>The CultureInfo of the current UI culture, correct to the top level.</returns>
903        private static CultureInfo GetCurrentCulture()
904        {
905            CultureInfo culture = CultureInfo.CurrentUICulture;
906            while (culture.Parent != CultureInfo.InvariantCulture)
907                culture = culture.Parent;
908
909            return culture;
910        }
911
912        private Manager.Settings settings;
913    }
[78]914}
Note: See TracBrowser for help on using the repository browser.