2010-05-25 Jb Evain <jbevain@novell.com>
[mcs.git] / tools / security / caspol.cs
blob537832921d6ff2eb50ffd54cf8cc7a00a7f6995c
1 //
2 // caspol.cs: Code Access Security Policy Tool
3 //
4 // Author:
5 // Sebastien Pouliot <sebastien@ximian.com>
6 //
7 // Copyright (C) 2004 Novell, Inc (http://www.novell.com)
8 //
10 using System;
11 using System.Collections;
12 using System.IO;
13 using System.Reflection;
14 using System.Security;
15 using System.Security.Cryptography;
16 using System.Security.Cryptography.X509Certificates;
17 using System.Security.Permissions;
18 using System.Security.Policy;
19 using System.Text;
21 using Mono.Security.Cryptography;
22 #if !NET_2_0
23 using Mono.Xml;
24 #endif
26 [assembly: AssemblyTitle ("Mono CasPol")]
27 [assembly: AssemblyDescription ("Command line tool to modify Code Access Security policies.")]
29 namespace Mono.Tools {
31 class CustomMembershipCondition : IMembershipCondition {
33 SecurityElement _se;
35 public CustomMembershipCondition (SecurityElement se)
37 _se = se;
40 public bool Check (Evidence evidence)
42 return true;
45 public IMembershipCondition Copy ()
47 return new CustomMembershipCondition (_se);
50 public void FromXml (SecurityElement e)
52 _se = e;
55 public SecurityElement ToXml ()
57 return _se;
60 public void FromXml (SecurityElement e, PolicyLevel level)
62 _se = e;
65 public SecurityElement ToXml (PolicyLevel level)
67 return _se;
71 class CasPol {
73 static ArrayList _levels;
75 static private void Help ()
77 Console.WriteLine ("Usage: caspol [options] [arguments] ...{0}", Environment.NewLine);
80 // (to be) Stored Options
81 static bool PolicyChangesConfirmation = true;
83 static bool forcePolicyChanges = false;
84 static bool policyLevelDefault = true;
86 static void PrintGlobalInfo ()
88 Console.WriteLine ("Security: {0}", SecurityManager.SecurityEnabled);
89 Console.WriteLine ("Execution check: {0}", SecurityManager.CheckExecutionRights);
90 Console.WriteLine ("Policy changes confirmation: {0}", PolicyChangesConfirmation);
93 static bool Confirm ()
95 if (PolicyChangesConfirmation) {
96 Console.WriteLine ("WARNING: This action will modify the specified security policy!");
97 Console.WriteLine ("Do you want to change the policy ?");
98 string answer = Console.ReadLine ();
99 switch (answer.ToUpper ()) {
100 case "YES":
101 case "Y":
102 return true;
103 default:
104 Console.WriteLine ("Change aborted!");
105 return false;
108 return true;
111 static string Policies (string prefix)
113 StringBuilder sb = new StringBuilder (prefix);
114 PolicyLevel pl = null;
115 for (int i = 0; i < Levels.Count - 1; i++) {
116 pl = (PolicyLevel)Levels [i];
117 sb.AppendFormat ("{0}, ", pl.Label);
119 pl = (PolicyLevel)Levels [Levels.Count - 1];
120 sb.Append (pl.Label);
122 sb.Append (" policy level");
123 if (Levels.Count > 1)
124 sb.Append ("s");
126 return sb.ToString ();
129 // In Fx 1.0/1.1 there is not direct way to load a XML file
130 // into a SecurityElement so we use SecurityParser from
131 // Mono.Security.dll.
132 static SecurityElement LoadXml (string filename)
134 if (!File.Exists (filename)) {
135 Console.WriteLine ("Couldn't not find '{0}'.", filename);
136 return null;
139 string xml = null;
140 using (StreamReader sr = new StreamReader (filename)) {
141 xml = sr.ReadToEnd ();
142 sr.Close ();
144 #if NET_2_0
145 // actually this use the SecurityParser (on the Mono
146 // runtime) in corlib do to the job - but it remove
147 // the dependency on Mono.Security.dll
148 SecurityElement se = SecurityElement.FromString (xml);
149 #else
150 SecurityParser sp = new SecurityParser ();
151 sp.LoadXml (xml);
152 SecurityElement se = sp.ToXml ();
153 #endif
154 return se;
157 static PermissionSet LoadPermissions (string filename)
159 SecurityElement se = LoadXml (filename);
160 if (se == null)
161 return null;
163 PermissionSet ps = new PermissionSet (PermissionState.None);
164 ps.FromXml (se);
165 if (se.Attribute ("class").IndexOf ("System.Security.NamedPermissionSet") == -1)
166 return ps;
167 // now we know it's a NamedPermissionSet
168 return (PermissionSet) new NamedPermissionSet (se.Attribute ("Name"), ps);
171 static StrongName GetStrongName (string filename)
173 try {
174 AssemblyName an = AssemblyName.GetAssemblyName (filename);
175 byte [] pk = an.GetPublicKey ();
176 return new StrongName (new StrongNamePublicKeyBlob (pk), an.Name, an.Version);
178 catch (FileNotFoundException) {
179 Console.WriteLine ("Couldn't find assembly '{0}'.", filename);
180 return null;
184 static Assembly GetAssembly (string filename)
186 try {
187 AssemblyName an = AssemblyName.GetAssemblyName (filename);
188 return Assembly.Load (an);
190 catch (FileNotFoundException) {
191 Console.WriteLine ("Couldn't find assembly '{0}'.", filename);
192 return null;
196 static Evidence GetAssemblyEvidences (string filename)
198 return GetAssembly (filename).Evidence;
201 static bool OnOff (string value, ref bool on)
203 switch (value.ToUpper ()) {
204 case "ON":
205 on = true;
206 break;
207 case "OFF":
208 on = false;
209 break;
210 default:
211 return false;
213 return true;
216 static bool SaveSettings ()
218 Console.WriteLine ("TODO - where to save those settings ?");
219 return false;
223 // Actions
225 static void ShowCodeGroup (CodeGroup cg, string prefix)
227 Console.WriteLine ("{0}. {1}: {2}", prefix, cg.MembershipCondition, cg.PermissionSetName);
228 for (int i=0; i < cg.Children.Count; i++) {
229 ShowCodeGroup ((CodeGroup)cg.Children [i], " " + prefix + "." + (i + 1));
233 // -lg
234 // -listgroups
235 static void ListCodeGroups ()
237 PrintGlobalInfo ();
239 foreach (PolicyLevel pl in Levels) {
240 Console.WriteLine ("{0}Level: {1}{0}", Environment.NewLine, pl.Label);
242 Console.WriteLine ("Code Groups:{0}", Environment.NewLine);
243 ShowCodeGroup (pl.RootCodeGroup, "1");
247 static void ShowDescription (CodeGroup cg, string prefix)
249 Console.WriteLine ("{0}. {1}: {2}", prefix, cg.Name, cg.Description);
250 for (int i = 0; i < cg.Children.Count; i++) {
251 ShowDescription ((CodeGroup)cg.Children [i], " " + prefix + "." + (i + 1));
255 // -ld
256 // -listdescription
257 static void ListDescriptions ()
259 PrintGlobalInfo ();
261 foreach (PolicyLevel pl in Levels) {
262 Console.WriteLine ("{0}Level: {1}{0}", Environment.NewLine, pl.Label);
264 Console.WriteLine ("Code Groups:{0}", Environment.NewLine);
265 ShowDescription (pl.RootCodeGroup, "1");
269 // -lp
270 // -listpset
271 static void ListPermissionSets ()
273 PrintGlobalInfo ();
275 foreach (PolicyLevel pl in Levels) {
276 Console.WriteLine ("{0}Level: {1}{0}", Environment.NewLine, pl.Label);
278 Console.WriteLine ("Named Permission Sets:{0}", Environment.NewLine);
279 int n=1;
280 foreach (NamedPermissionSet nps in pl.NamedPermissionSets) {
281 Console.WriteLine ("{0}. {1} ({2}) = {3}{4}",
282 n++, nps.Name, nps.Description, Environment.NewLine, nps);
287 // -lf
288 // -listfulltrust
289 static void ListFullTrust ()
291 PrintGlobalInfo ();
293 foreach (PolicyLevel pl in Levels) {
294 Console.WriteLine ("{0}Level: {1}{0}", Environment.NewLine, pl.Label);
296 Console.WriteLine ("Full Trust Assemblies:{0}", Environment.NewLine);
297 int n = 1;
298 foreach (StrongNameMembershipCondition snmc in pl.FullTrustAssemblies) {
299 Console.WriteLine ("{0}. {1} = {2}{3}",
300 n++, snmc.Name, Environment.NewLine, snmc);
305 static void ShowResolveGroup (PolicyLevel pl, Evidence e)
307 Console.WriteLine ("{0}Level: {1}{0}", Environment.NewLine, pl.Label);
308 CodeGroup cg = pl.ResolveMatchingCodeGroups (e);
309 Console.WriteLine ("Code Groups:{0}", Environment.NewLine);
310 ShowCodeGroup (cg, "1");
311 Console.WriteLine ();
314 // -rsg assemblyname
315 // -resolvegroup assemblyname
316 static bool ResolveGroup (string assemblyname)
318 Evidence ev = GetAssemblyEvidences (assemblyname);
319 if (ev == null)
320 return false;
322 if (policyLevelDefault) {
323 // different "default" here
324 IEnumerator e = SecurityManager.PolicyHierarchy ();
325 while (e.MoveNext ()) {
326 PolicyLevel pl = (PolicyLevel)e.Current;
327 ShowResolveGroup (pl, ev);
329 } else {
330 // use the user specified levels
331 foreach (PolicyLevel pl in Levels) {
332 ShowResolveGroup (pl, ev);
335 return true;
338 // -rsp assemblyname
339 // -resolveperm assemblyname
340 static bool ResolvePermissions (string assemblyname)
342 Evidence ev = GetAssemblyEvidences (assemblyname);
343 if (ev == null)
344 return false;
346 PermissionSet ps = null;
347 Console.WriteLine ();
348 if (policyLevelDefault) {
349 // different "default" here
350 IEnumerator e = SecurityManager.PolicyHierarchy ();
351 while (e.MoveNext ()) {
352 PolicyLevel pl = (PolicyLevel)e.Current;
353 Console.WriteLine ("Resolving {0} level", pl.Label);
354 if (ps == null)
355 ps = pl.Resolve (ev).PermissionSet;
356 else
357 ps = ps.Intersect (pl.Resolve (ev).PermissionSet);
359 } else {
360 // use the user specified levels
361 foreach (PolicyLevel pl in Levels) {
362 Console.WriteLine ("Resolving {0} level", pl.Label);
363 if (ps == null)
364 ps = pl.Resolve (ev).PermissionSet;
365 else
366 ps = ps.Intersect (pl.Resolve (ev).PermissionSet);
369 if (ps == null)
370 return false;
372 IEnumerator ee = ev.GetHostEnumerator ();
373 while (ee.MoveNext ()) {
374 IIdentityPermissionFactory ipf = (ee.Current as IIdentityPermissionFactory);
375 if (ipf != null) {
376 IPermission p = ipf.CreateIdentityPermission (ev);
377 ps.AddPermission (p);
381 Console.WriteLine ("{0}Grant:{0}{1}", Environment.NewLine, ps.ToXml ().ToString ());
382 return true;
385 // -ap namedxmlfile
386 // -addpset namedxmlfile
387 // -ap xmlfile name
388 // -addpset xmlfile name
389 static bool AddPermissionSet (string [] args, ref int i)
391 // two syntax - so we first load the XML file and
392 // if it's not a named XML file, then we use the next
393 // parameter as it's name
394 string xmlfile = args [++i];
395 PermissionSet ps = LoadPermissions (xmlfile);
396 if ((ps == null) || !Confirm ())
397 return false;
399 NamedPermissionSet nps = null;
400 if (ps is NamedPermissionSet) {
401 nps = (NamedPermissionSet)ps;
402 } else {
403 nps = new NamedPermissionSet (args [++i], ps);
406 foreach (PolicyLevel pl in Levels) {
407 pl.AddNamedPermissionSet (nps);
408 SecurityManager.SavePolicyLevel (pl);
410 return true;
413 // -cp xmlfile psetname
414 // -chgpset xmlfile psetname
415 static bool ChangePermissionSet (string[] args, ref int i)
417 string xmlfile = args [++i];
418 PermissionSet ps = LoadPermissions (xmlfile);
419 if (ps == null)
420 return false;
422 bool confirmed = false;
423 string psname = args [++i];
425 foreach (PolicyLevel pl in Levels) {
426 if (pl.GetNamedPermissionSet (psname) == null) {
427 Console.WriteLine ("Couldn't find '{0}' permission set in policy.", psname);
428 return false;
429 } else if (confirmed || Confirm ()) {
430 confirmed = true; // only ask once
431 pl.ChangeNamedPermissionSet (psname, ps);
432 SecurityManager.SavePolicyLevel (pl);
433 } else
434 return false;
436 return true;
439 // -rp psetname
440 // -rempset psetname
441 static bool RemovePermissionSet (string psname)
443 bool confirmed = false;
445 foreach (PolicyLevel pl in Levels) {
446 PermissionSet ps = pl.GetNamedPermissionSet (psname);
447 if (ps == null) {
448 Console.WriteLine ("Couldn't find '{0}' permission set in policy.", psname);
449 return false;
450 } else if (confirmed || Confirm ()) {
451 confirmed = true; // only ask once
452 pl.RemoveNamedPermissionSet (psname);
453 SecurityManager.SavePolicyLevel (pl);
454 Console.WriteLine ("Permission set '{0}' removed from policy.", psname);
455 } else
456 return false;
458 return true;
461 // -af assemblyname
462 // -addfulltrust assemblyname
463 static bool AddFullTrust (string aname)
465 StrongName sn = GetStrongName (aname);
466 if ((sn == null) || !Confirm ())
467 return false;
469 foreach (PolicyLevel pl in Levels) {
470 pl.AddFullTrustAssembly (sn);
472 return true;
475 // -rf assemblyname
476 // -remfulltrust assemblyname
477 static bool RemoveFullTrust (string aname)
479 StrongName sn = GetStrongName (aname);
480 if ((sn == null) || !Confirm ())
481 return false;
483 foreach (PolicyLevel pl in Levels) {
484 pl.RemoveFullTrustAssembly (sn);
486 return true;
490 static CodeGroup FindCodeGroupByName (string name, ref CodeGroup parent)
492 for (int i = 0; i < parent.Children.Count; i++) {
493 CodeGroup child = (CodeGroup)parent.Children [i];
494 if (child.Name == name) {
495 return child;
496 } else {
497 CodeGroup cg = FindCodeGroupByName (name, ref child);
498 if (cg != null)
499 return cg;
502 return null;
505 static CodeGroup FindCodeGroupByLabel (string label, string current, ref CodeGroup parent)
507 for (int i=0; i < parent.Children.Count; i++) {
508 CodeGroup child = (CodeGroup)parent.Children [i];
509 string temp = String.Concat (current, ".", (i + 1).ToString ());
510 if ((label == temp) || (label == temp + ".")) {
511 return child;
512 } else if (label.StartsWith (temp)) {
513 CodeGroup cg = FindCodeGroupByLabel (label, temp, ref child);
514 if (cg != null)
515 return cg;
518 return null;
521 static CodeGroup FindCodeGroup (string name, ref CodeGroup parent, ref PolicyLevel pl)
523 if (name.Length < 1)
524 return null;
526 // Notes:
527 // - labels starts with numbers (e.g. 1.2.1)
528 // - names cannot start with numbers (A-Z, 0-9 and _)
529 bool label = Char.IsDigit (name, 0);
531 // More notes
532 // - we can't remove the root code group
533 // - we remove only one group (e.g. name)
534 for (int i=0; i < Levels.Count; i++) {
535 pl = (PolicyLevel) Levels [i];
536 parent = pl.RootCodeGroup;
537 CodeGroup cg = null;
538 if (label)
539 cg = FindCodeGroupByLabel (name, "1", ref parent);
540 else
541 cg = FindCodeGroupByName (name, ref parent);
543 if (cg != null)
544 return cg;
546 Console.WriteLine ("CodeGroup with {0} '{1}' was not found!",
547 label ? "label" : "name", name);
548 return null;
551 // -custom xmlfile
552 static IMembershipCondition ProcessCustomMembership (string filename)
554 SecurityElement se = LoadXml (filename);
555 if (se == null)
556 return null;
557 return new CustomMembershipCondition (se);
560 // -hash algo -hex hash
561 // -hash algo -file assemblyname
562 static IMembershipCondition ProcessHashMembership (string[] args, ref int i)
564 HashAlgorithm ha = HashAlgorithm.Create (args [++i]);
565 byte [] value = null;
566 switch (args [++i]) {
567 case "-hex":
568 value = CryptoConvert.FromHex (args [++i]);
569 break;
570 case "-file":
571 Hash hash = new Hash (GetAssembly (args [++i]));
572 value = hash.GenerateHash (ha);
573 break;
574 default:
575 return null;
577 return new HashMembershipCondition (ha, value);
580 // -pub -cert certificate
581 // -pub -file signedfile
582 // -pub -hex rawdata
583 static IMembershipCondition ProcessPublisherMembership (string[] args, ref int i)
585 X509Certificate cert = null;
586 switch (args [++i]) {
587 case "-cert":
588 cert = X509Certificate.CreateFromCertFile (args [++i]);
589 break;
590 case "-file":
591 cert = X509Certificate.CreateFromSignedFile (args [++i]);
592 break;
593 case "-hex":
594 byte[] raw = CryptoConvert.FromHex (args [++i]);
595 cert = new X509Certificate (raw);
596 break;
597 default:
598 return null;
600 return new PublisherMembershipCondition (cert);
603 // -strong -file filename [name | -noname] [version | -noversion]
604 static IMembershipCondition ProcessStrongNameMembership (string[] args, ref int i)
606 if (args [++i] != "-file") {
607 Console.WriteLine ("Missing -file parameter.");
608 return null;
611 StrongName sn = GetStrongName (args [++i]);
613 string name = args [++i];
614 if (name == "-noname")
615 name = null;
617 Version v = null;
618 string version = args [++i];
619 if (version != "-noversion")
620 v = new Version (version);
622 return new StrongNameMembershipCondition (sn.PublicKey, name, v);
625 static bool ProcessCodeGroup (CodeGroup cg, string[] args, ref int i)
627 IMembershipCondition mship = null;
628 for (; i < args.Length; i++) {
629 switch (args [++i]) {
630 case "-all":
631 cg.MembershipCondition = new AllMembershipCondition ();
632 break;
633 case "-appdir":
634 cg.MembershipCondition = new ApplicationDirectoryMembershipCondition ();
635 break;
636 case "-custom":
637 mship = ProcessCustomMembership (args [++i]);
638 if (mship == null)
639 return false;
640 cg.MembershipCondition = mship;
641 break;
642 case "-hash":
643 mship = ProcessHashMembership (args, ref i);
644 if (mship == null)
645 return false;
646 cg.MembershipCondition = mship;
647 break;
648 case "-pub":
649 mship = ProcessPublisherMembership (args, ref i);
650 if (mship == null)
651 return false;
652 cg.MembershipCondition = mship;
653 break;
654 case "-site":
655 cg.MembershipCondition = new SiteMembershipCondition (args [++i]);
656 break;
657 case "-strong":
658 mship = ProcessStrongNameMembership (args, ref i);
659 if (mship == null)
660 return false;
661 cg.MembershipCondition = mship;
662 break;
663 case "-url":
664 cg.MembershipCondition = new UrlMembershipCondition (args [++i]);
665 break;
666 case "-zone":
667 SecurityZone zone = (SecurityZone) Enum.Parse (typeof (SecurityZone), args [++i]);
668 cg.MembershipCondition = new ZoneMembershipCondition (zone);
669 break;
671 case "-d":
672 case "-description":
673 cg.Description = args [++i];
674 break;
675 case "-exclusive":
676 bool exclusive = false;
677 if (OnOff (args [++i], ref exclusive)) {
678 if (exclusive)
679 cg.PolicyStatement.Attributes |= PolicyStatementAttribute.Exclusive;
681 else
682 return false;
683 break;
684 case "-levelfinal":
685 bool final = false;
686 if (OnOff (args [++i], ref final)) {
687 if (final)
688 cg.PolicyStatement.Attributes |= PolicyStatementAttribute.LevelFinal;
690 else
691 return false;
692 break;
693 case "-n":
694 case "-name":
695 cg.Name = args [++i];
696 break;
697 default:
698 i--;
699 break;
702 return true;
705 // -ag label|name membership psetname flag
706 // -addgroup label|name membership psetname flag
707 static bool AddCodeGroup (string[] args, ref int i)
709 string name = args [++i];
711 PolicyLevel pl = null;
712 CodeGroup parent = null;
713 CodeGroup cg = FindCodeGroup (name, ref parent, ref pl);
714 if ((pl == null) || (parent == null) || (cg == null))
715 return false;
717 UnionCodeGroup child = new UnionCodeGroup (
718 new AllMembershipCondition (),
719 new PolicyStatement (new PermissionSet (PermissionState.Unrestricted)));
720 if (!ProcessCodeGroup (child, args, ref i))
721 return false;
723 cg.AddChild (child);
724 SecurityManager.SavePolicyLevel (pl);
725 Console.WriteLine ("CodeGroup '{0}' added in {1} policy level.",
726 cg.Name, pl.Label);
727 return true;
730 // -cg label|name membership|psetname|flag
731 // -chggroup label|name membership|psetname|flag
732 static bool ChangeCodeGroup (string[] args, ref int i)
734 string name = args [++i];
736 PolicyLevel pl = null;
737 CodeGroup parent = null;
738 CodeGroup cg = FindCodeGroup (name, ref parent, ref pl);
739 if ((pl == null) || (parent == null) || (cg == null))
740 return false;
742 if (!ProcessCodeGroup (cg, args, ref i))
743 return false;
745 SecurityManager.SavePolicyLevel (pl);
746 Console.WriteLine ("CodeGroup '{0}' modified in {1} policy level.",
747 cg.Name, pl.Label);
748 return true;
751 // -rg label|name
752 // -remgroup label|name
753 static bool RemoveCodeGroup (string name)
755 PolicyLevel pl = null;
756 CodeGroup parent = null;
757 CodeGroup cg = FindCodeGroup (name, ref parent, ref pl);
758 if ((pl == null) || (parent == null) || (cg == null))
759 return false;
761 if (!Confirm ())
762 return false;
764 parent.RemoveChild (cg);
765 SecurityManager.SavePolicyLevel (pl);
766 Console.WriteLine ("CodeGroup '{0}' removed from {1} policy level.",
767 cg.Name, pl.Label);
768 return true;
771 // -r
772 // -recover
773 static void Recover ()
775 // no confirmation required to recover
776 foreach (PolicyLevel pl in Levels) {
777 pl.Recover ();
778 SecurityManager.SavePolicyLevel (pl);
782 // -rs
783 // -reset
784 static bool Reset ()
786 Console.WriteLine (Policies ("Resetting "));
787 if (Confirm ()) {
788 foreach (PolicyLevel pl in Levels) {
789 pl.Reset ();
790 SecurityManager.SavePolicyLevel (pl);
792 return true;
794 return false;
797 // -s on|off
798 // -security on|off
799 static bool Security (string value)
801 bool on = true;
802 if (!OnOff (value, ref on))
803 return false;
804 SecurityManager.SecurityEnabled = on;
805 return SaveSettings ();
808 // -e on|off
809 // -execution on|off
810 static bool Execution (string value)
812 bool on = true;
813 if (!OnOff (value, ref on))
814 return false;
815 SecurityManager.CheckExecutionRights = on;
816 return SaveSettings ();
819 // -b
820 // -buildcache
821 static bool BuildCache ()
823 // TODO
824 return false;
827 // -pp on|off
828 // -polchgprompt on|off
829 static bool PolicyChangePrompt (string value)
831 bool on = true;
832 if (!OnOff (value, ref on))
833 return false;
834 PolicyChangesConfirmation = on;
835 return SaveSettings ();
839 // Policy Levels Internal Management
841 static PolicyLevel levelEnterprise;
842 static PolicyLevel levelMachine;
843 static PolicyLevel levelUser;
845 static void BuildLevels ()
847 IEnumerator e = SecurityManager.PolicyHierarchy ();
848 if (e.MoveNext ())
849 levelEnterprise = (PolicyLevel) e.Current;
850 if (e.MoveNext ())
851 levelMachine = (PolicyLevel) e.Current;
852 if (e.MoveNext ())
853 levelUser = (PolicyLevel) e.Current;
856 static PolicyLevel Enterprise {
857 get {
858 if (levelEnterprise == null)
859 BuildLevels ();
860 return levelEnterprise;
864 static PolicyLevel Machine {
865 get {
866 if (levelMachine == null)
867 BuildLevels ();
868 return levelMachine;
872 static PolicyLevel User {
873 get {
874 if (levelUser == null)
875 BuildLevels ();
876 return levelUser;
880 static ArrayList Levels {
881 get {
882 if (_levels == null)
883 _levels = new ArrayList (3);
884 return _levels;
888 static bool ProcessInstruction (string[] args, ref int i)
890 for (; i < args.Length; i++) {
891 switch (args [i]) {
892 case "-q":
893 case "-quiet":
894 PolicyChangesConfirmation = false;
895 break;
896 case "-f":
897 case "-force":
898 forcePolicyChanges = true;
899 break;
900 case "-?":
901 case "/?":
902 case "-h":
903 case "-help":
904 Help ();
905 break;
907 case "-a":
908 case "-all":
909 policyLevelDefault = false;
910 Levels.Clear ();
911 Levels.Add (Enterprise);
912 Levels.Add (Machine);
913 Levels.Add (User);
914 break;
915 case "-ca":
916 case "-customall":
917 policyLevelDefault = false;
918 Levels.Clear ();
919 Levels.Add (Enterprise);
920 Levels.Add (Machine);
921 Levels.Add (SecurityManager.LoadPolicyLevelFromFile (args [++i], PolicyLevelType.User));
922 break;
923 case "-cu":
924 case "-customuser":
925 policyLevelDefault = false;
926 Levels.Clear ();
927 Levels.Add (SecurityManager.LoadPolicyLevelFromFile (args [++i], PolicyLevelType.User));
928 break;
929 case "-en":
930 case "-entreprise":
931 policyLevelDefault = false;
932 Levels.Clear ();
933 Levels.Add (Enterprise);
934 break;
935 case "-m":
936 case "-machine":
937 policyLevelDefault = false;
938 Levels.Clear ();
939 Levels.Add (Machine);
940 break;
941 case "-u":
942 case "-user":
943 policyLevelDefault = false;
944 Levels.Clear ();
945 Levels.Add (User);
946 break;
948 case "-lg":
949 case "-listgroups":
950 ListCodeGroups ();
951 break;
952 case "-ld":
953 case "-listdescription":
954 ListDescriptions ();
955 break;
956 case "-lp":
957 case "-listpset":
958 ListPermissionSets ();
959 break;
960 case "-lf":
961 case "-listfulltrust":
962 ListFullTrust ();
963 break;
964 case "-l":
965 case "-list":
966 ListCodeGroups ();
967 Console.WriteLine ();
968 ListPermissionSets ();
969 Console.WriteLine ();
970 ListFullTrust ();
971 break;
973 case "-rsg":
974 case "-resolvegroup":
975 if (!ResolveGroup (args [++i]))
976 return false;
977 break;
978 case "-rsp":
979 case "-resolveperm":
980 if (!ResolvePermissions (args [++i]))
981 return false;
982 break;
984 case "-ap":
985 case "-addpset":
986 if (!AddPermissionSet (args, ref i))
987 return false;
988 break;
989 case "-cp":
990 case "-chgpset":
991 if (!ChangePermissionSet (args, ref i))
992 return false;
993 break;
994 case "-rp":
995 case "-rempset":
996 if (!RemovePermissionSet (args [++i]))
997 return false;
998 break;
1000 case "-af":
1001 case "-addfulltrust":
1002 if (!AddFullTrust (args [++i]))
1003 return false;
1004 break;
1005 case "-rf":
1006 case "-remfulltrust":
1007 if (!RemoveFullTrust (args [++i]))
1008 return false;
1009 break;
1011 case "-ag":
1012 case "-addgroup":
1013 if (!AddCodeGroup (args, ref i))
1014 return false;
1015 break;
1016 case "-cg":
1017 case "-chggroup":
1018 if (!ChangeCodeGroup (args, ref i))
1019 return false;
1020 break;
1021 case "-rg":
1022 case "-remgroup":
1023 if (!RemoveCodeGroup (args [++i]))
1024 return false;
1025 break;
1027 case "-r":
1028 case "-recover":
1029 Recover ();
1030 break;
1031 case "-rs":
1032 case "-reset":
1033 if (!Reset ())
1034 return false;
1035 break;
1037 case "-s":
1038 case "-security":
1039 if (!Security (args [++i]))
1040 return false;
1041 break;
1042 case "-e":
1043 case "-execution":
1044 if (!Execution (args [++i]))
1045 return false;
1046 break;
1047 case "-b":
1048 case "-buildcache":
1049 if (!BuildCache ())
1050 return false;
1051 break;
1052 case "-pp":
1053 case "-polchgprompt":
1054 if (!PolicyChangePrompt (args [++i]))
1055 return false;
1056 break;
1058 default:
1059 Console.WriteLine ("*** unknown argument {0} ***", args [i]);
1060 return false;
1062 Console.WriteLine ();
1064 return true;
1067 static void SetDefaultPolicyLevel ()
1069 // default is User for normal users and Machine for
1070 // administrators. Here we define an administrator as
1071 // someone who can write to the Machine policy files
1072 try {
1073 using (FileStream fs = File.OpenWrite (Machine.StoreLocation)) {
1074 fs.Close ();
1076 Levels.Add (Machine);
1078 catch {
1079 Levels.Add (User);
1081 // some actions, like resolves, use a different default (all)
1082 policyLevelDefault = true;
1085 [STAThread]
1086 static int Main (string[] args)
1088 Console.WriteLine (new AssemblyInfo ().ToString ());
1089 if (args.Length == 0) {
1090 Help ();
1091 return 0;
1094 try {
1095 // set default level (when none is specified
1096 // by command line options)
1097 SetDefaultPolicyLevel ();
1099 // process instructions (i.e. multiple
1100 // instructions can be chained)
1101 for (int i=0; i < args.Length; i++) {
1102 if (!ProcessInstruction (args, ref i))
1103 return 1;
1106 catch (Exception e) {
1107 Console.WriteLine ("Error: " + e.ToString ());
1108 Help ();
1109 return 2;
1111 Console.WriteLine ("Success");
1112 return 0;