Commits

Martin Eden  committed 89aacbe

Initial commit.

  • Participants

Comments (0)

Files changed (13)

+syntax: regexp
+/bin/
+/obj/
+.suo$

File LocalPolicy.sln

+
+Microsoft Visual Studio Solution File, Format Version 11.00
+# Visual Studio 2010
+Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "LocalPolicy", "LocalPolicy\LocalPolicy.csproj", "{52BD99E0-0865-4F2C-9A65-0D2F9D1A8982}"
+EndProject
+Global
+	GlobalSection(SolutionConfigurationPlatforms) = preSolution
+		Debug|x86 = Debug|x86
+		Release|x86 = Release|x86
+	EndGlobalSection
+	GlobalSection(ProjectConfigurationPlatforms) = postSolution
+		{52BD99E0-0865-4F2C-9A65-0D2F9D1A8982}.Debug|x86.ActiveCfg = Debug|x86
+		{52BD99E0-0865-4F2C-9A65-0D2F9D1A8982}.Debug|x86.Build.0 = Debug|x86
+		{52BD99E0-0865-4F2C-9A65-0D2F9D1A8982}.Release|x86.ActiveCfg = Release|x86
+		{52BD99E0-0865-4F2C-9A65-0D2F9D1A8982}.Release|x86.Build.0 = Release|x86
+	EndGlobalSection
+	GlobalSection(SolutionProperties) = preSolution
+		HideSolutionNode = FALSE
+	EndGlobalSection
+EndGlobal

File LocalPolicy/ActiveDirectoryGroupPolicyObject.cs

+using System;
+using System.Text;
+
+namespace LocalPolicy
+{
+    public class ActiveDirectoryGroupPolicyObject : GroupPolicyObject
+    {
+        /// <summary>
+        /// Opens the specified GPO as determined by the path
+        /// </summary>
+        /// <param name="activeDirectoryPath">
+        /// Specifies the Active Directory path of the object to open.
+        /// If the path specifies a domain controller, the GPO is created on that DC. 
+        /// Otherwise, the system will select a DC on the caller's behalf.
+        /// </param>
+        public ActiveDirectoryGroupPolicyObject(string activeDirectoryPath, GroupPolicyObjectSettings settings)
+        {
+            trycatch(() => instance.OpenDSGPO(activeDirectoryPath, settings.Flag),
+                "Unable to open GPO at ActiveDirectory path '{0}'", activeDirectoryPath);
+        }
+
+        public Guid GuidName
+        {
+            get
+            {
+                return new Guid(UniqueName);
+            }
+        }
+        /// <summary>
+        /// Retrieves the path to the root of the specified GPO section. 
+        /// The path is in ADSI format (LDAP://cn=user, ou=users, dc=coname, dc=com).
+        /// </summary>
+        public override string GetPathTo(GroupPolicySection section)
+        {
+            StringBuilder sb = new StringBuilder(maxLength);
+            trycatch(() => instance.GetDSPath((uint)section, sb, maxLength),
+                "Unable to retrieve path to section '{0}'",
+                Enum.GetName(typeof(GroupPolicySection), section));
+            return sb.ToString();
+        }
+    }
+}

File LocalPolicy/AssemblyInfoHelper.cs

+using System;
+using System.Linq;
+using System.Reflection;
+using System.Runtime.InteropServices;
+
+namespace LocalPolicy
+{
+    internal class AssemblyInfoHelper
+    {
+        internal static T GetAssemblyAttribute<T>()
+            where T : Attribute
+        {
+            var assembly = Assembly.GetExecutingAssembly();
+            return GetAssemblyAttribute<T>(assembly);            
+        }
+
+        internal static T GetAssemblyAttribute<T>(Assembly assembly)
+            where T : Attribute
+        {
+            object[] attributes = assembly.GetCustomAttributes(typeof(T), true);
+            if (attributes == null || attributes.Length == 0)
+                return null;
+
+            return (T)attributes.First();
+        }
+    }
+}

File LocalPolicy/ComputerGroupPolicyObject.cs

+using System;
+using System.Text;
+
+namespace LocalPolicy
+{
+    public class ComputerGroupPolicyObject : GroupPolicyObject
+    {
+        /// <summary>
+        /// Opens the default GPO for the local computer 
+        /// </summary>
+        public ComputerGroupPolicyObject(GroupPolicyObjectSettings options = null)
+        {
+            options = options ?? new GroupPolicyObjectSettings();
+            trycatch(() => instance.OpenLocalMachineGPO(options.Flag),
+                "Unable to open local machine GPO");
+            IsLocal = true;
+        }
+        /// <summary>
+        /// Opens the default GPO for the specified remote computer
+        /// </summary>
+        /// <param name="computerName">Name of the remote computer in the format "\\ComputerName"</param>
+        public ComputerGroupPolicyObject(string computerName, GroupPolicyObjectSettings options = null)
+        {
+            options = options ?? new GroupPolicyObjectSettings();
+            trycatch(() => instance.OpenRemoteMachineGPO(computerName, options.Flag),
+                "Unable to open GPO on remote machine '{0}'", computerName);
+            IsLocal = false;
+        }
+
+        /// <summary>
+        /// Returns true if the object is on the local machine
+        /// </summary>
+        public readonly bool IsLocal;
+        /// <summary>
+        /// Returns true if the object is on a remote machine.
+        /// Use ComputerName to find out the name of that machine.
+        /// </summary>
+        public bool IsRemote
+        {
+            get { return !IsLocal; }
+        }
+        /// <summary>
+        /// Returns the name of the machine on which the GPO resides.
+        /// Returns "Local" if is on the local machine.
+        /// </summary>
+        public string ComputerName
+        {
+            get
+            {
+                return UniqueName;
+            }
+        }
+        /// <summary>
+        /// Retrieves the file system path to the root of the specified GPO section. 
+        /// The path is in UNC format.
+        /// </summary>
+        public override string GetPathTo(GroupPolicySection section)
+        {
+            StringBuilder sb = new StringBuilder(maxLength);
+            trycatch(() => instance.GetFileSysPath((uint)section, sb, maxLength),
+                "Unable to retrieve path to section '{0}'",
+                Enum.GetName(typeof(GroupPolicySection), section));
+            return sb.ToString();
+        }
+    }
+}

File LocalPolicy/GroupPolicyException.cs

+using System;
+
+namespace LocalPolicy
+{
+    public class GroupPolicyException : Exception
+    {
+        internal GroupPolicyException(string message)
+            : base(message) { }
+    }
+}

File LocalPolicy/GroupPolicyObject.cs

+using System;
+using System.Runtime.InteropServices;
+using System.Text;
+using Microsoft.Win32;
+using Microsoft.Win32.SafeHandles;
+
+namespace LocalPolicy
+{
+    public abstract class GroupPolicyObject
+    {
+        private const uint S_OK = 0;
+        protected const int maxLength = 1024;
+
+        /// <summary>
+        /// The snap-in that processes .pol files
+        /// </summary>
+        private static readonly Guid RegistryExtension = new Guid(0x35378EAC, 0x683F, 0x11D2, 0xA8, 0x9A, 0x00, 0xC0, 0x4F, 0xBB, 0xCF, 0xA2);
+        /// <summary>
+        /// This application
+        /// </summary>
+        private static readonly Guid LocalGuid = new Guid(AssemblyInfoHelper.GetAssemblyAttribute<GuidAttribute>().Value);
+
+        protected LocalPolicy.COM.IGroupPolicyObject instance = null;
+
+        internal GroupPolicyObject()
+        {
+            this.instance = getInstance();
+        }
+
+        /// <summary>
+        /// Saves the specified registry policy settings to disk and updates the revision number of the GPO.
+        /// This saves both machine and user level settings.
+        /// </summary>
+        public void Save()
+        {
+            trycatch(() => instance.Save(true, true, RegistryExtension, LocalGuid),
+                "Error saving machine settings");
+            trycatch(() => instance.Save(false, true, RegistryExtension, LocalGuid),
+                "Error saving user settings");
+        }
+        /// <summary>
+        /// Deletes the GPO. You should not invoke any methods on this object after calling Delete. 
+        /// </summary>
+        public void Delete()
+        {
+            trycatch(() => instance.Delete(),
+                "Error deleting the GPO");
+            instance = null;
+        }
+
+        /// <summary>
+        /// The unique GPO name.
+        /// For a local GPO, this will be "Local".
+        /// For remote objects, this will be the computer name.
+        /// For Active Directory policy objects, this will be a GUID.
+        /// </summary>
+        public string UniqueName
+        {
+            get
+            {
+                return getString(instance.GetName, "Unable to retrieve name");
+            }
+        }
+        /// <summary>
+        /// The display name for the GPO.
+        /// </summary>
+        public string DisplayName
+        {
+            get
+            {
+                return getString(instance.GetDisplayName, "Unable to retrieve display name");
+            }
+            set
+            {
+                trycatch(() => instance.SetDisplayName(value),
+                    "Unable set display name to {0}", value);
+            }
+        }
+        /// <summary>
+        /// Retrieves the path to the GPO. 
+        /// If the GPO is an Active Directory object, the path is in ADSI name format. 
+        /// If the GPO is a computer object, this parameter receives a file system path.
+        /// </summary>
+        public string Path
+        {
+            get
+            {
+                return getString(instance.GetPath, "Unable to retrieve path");
+            }
+        }
+        
+        /// <summary>
+        /// Retrieves the root of the registry key for the specified GPO section
+        /// </summary>
+        public RegistryKey GetRootRegistryKey(GroupPolicySection section)
+        {
+            IntPtr key = default(IntPtr);
+            trycatch(() => instance.GetRegistryKey((uint)section, out key),
+                "Unable to get section '{0}'", Enum.GetName(typeof(GroupPolicySection), section));
+            var safeHandle = new SafeRegistryHandle(key, true);
+            return RegistryKey.FromHandle(safeHandle);
+        }
+        /// <summary>
+        /// Options that determine which parts of the GPO are enabled.
+        /// </summary>
+        public GroupPolicyObjectOptions Options
+        {
+            get
+            {
+                uint flag = default(uint);
+                trycatch(() => instance.GetOptions(out flag), 
+                    "Unable to retrieve options");
+                return new GroupPolicyObjectOptions(flag);
+            }
+            set
+            {
+                trycatch(() => instance.SetOptions(value.Flag, value.Mask),
+                    "Unable to set options");
+            }
+        }
+
+        public abstract string GetPathTo(GroupPolicySection section);
+
+        private LocalPolicy.COM.IGroupPolicyObject getInstance()
+        {
+            var concrete = new LocalPolicy.COM.GPClass();
+            return (LocalPolicy.COM.IGroupPolicyObject)concrete;
+        }
+        protected void trycatch(Func<uint> operation, string messageTemplate, params object[] messageArgs)
+        {
+            uint result = operation();
+            if (result != S_OK)
+            {
+                string message = string.Format(messageTemplate, messageArgs);
+                throw new GroupPolicyException(string.Format("{0}. Error code {1} (see WinError.h)", message, result));
+            }
+        }
+        protected string getString(Func<StringBuilder, int, uint> func, string errorMessage)
+        {
+            StringBuilder sb = new StringBuilder();
+            trycatch(() => func(sb, maxLength), errorMessage);
+            return sb.ToString();
+        }
+    }
+}

File LocalPolicy/GroupPolicyObjectOptions.cs

+
+namespace LocalPolicy
+{
+    public struct GroupPolicyObjectOptions
+    {
+        public readonly bool UserEnabled;
+        public readonly bool MachineEnabled;
+
+        public GroupPolicyObjectOptions(bool userEnabled = true, bool machineEnabled = true)
+        {
+            UserEnabled = userEnabled;
+            MachineEnabled = machineEnabled;
+        }
+        public GroupPolicyObjectOptions(uint flag)
+        {
+            UserEnabled = (flag & disableUserFlag) == 0;
+            MachineEnabled = (flag & disableMachineFlag) == 0;
+        }
+
+        private const uint disableUserFlag = 0x00000001;
+        private const uint disableMachineFlag = 0x00000002;
+
+        internal uint Flag
+        {
+            get
+            {
+                uint flag = 0x00000000;
+                if (!UserEnabled)
+                    flag |= disableUserFlag;
+                if (!MachineEnabled)
+                    flag |= disableMachineFlag;
+                return flag;
+            }
+        }
+
+        internal uint Mask
+        {
+            get
+            {
+                // We always change everything
+                return disableUserFlag 
+                    | disableMachineFlag;
+            }
+        }
+    }
+}

File LocalPolicy/GroupPolicyObjectSettings.cs

+namespace LocalPolicy
+{
+    public class GroupPolicyObjectSettings
+    {
+        public readonly bool LoadRegistryInformation;
+        public readonly bool Readonly;
+
+        public GroupPolicyObjectSettings(bool loadRegistryInfo = true, bool readOnly = false)
+        {
+            LoadRegistryInformation = loadRegistryInfo;
+            Readonly = readOnly;
+        }
+
+        private const uint registryFlag = 0x00000001;
+        private const uint readonlyFlag = 0x00000002;
+
+        internal uint Flag
+        {
+            get               
+            {
+                uint flag = 0x00000000;
+                if (LoadRegistryInformation)
+                    flag |= registryFlag;
+                if (Readonly)
+                    flag |= readonlyFlag;
+                return flag;
+            }
+        }
+    }
+}

File LocalPolicy/GroupPolicySection.cs

+
+namespace LocalPolicy
+{
+    public enum GroupPolicySection
+    {
+        Root = 0,
+        User = 1,
+        Machine = 2,
+    }
+}

File LocalPolicy/IGroupPolicy.cs

+using System;
+using System.Runtime.InteropServices;
+using System.Text;
+
+namespace LocalPolicy.COM
+{
+    [ComImport, Guid("EA502722-A23D-11d1-A7D3-0000F87571E3")]
+    internal class GPClass
+    {
+    }
+
+    [ComImport, Guid("EA502723-A23D-11d1-A7D3-0000F87571E3"), InterfaceType(ComInterfaceType.InterfaceIsIUnknown)]
+    public interface IGroupPolicyObject
+    {
+        [System.Diagnostics.CodeAnalysis.SuppressMessage("Microsoft.Naming", "CA1716:IdentifiersShouldNotMatchKeywords")]
+        uint New(
+            [MarshalAs(UnmanagedType.LPWStr)] string domainName,
+            [MarshalAs(UnmanagedType.LPWStr)] string displayName,
+            uint flags);
+
+        [System.Diagnostics.CodeAnalysis.SuppressMessage("Microsoft.Naming", "CA1704:IdentifiersShouldBeSpelledCorrectly")]
+        uint OpenDSGPO(
+            [MarshalAs(UnmanagedType.LPWStr)] string path,
+            uint flags);
+
+        uint OpenLocalMachineGPO(
+            uint flags);
+
+        uint OpenRemoteMachineGPO(
+            [MarshalAs(UnmanagedType.LPWStr)] string computerName,
+            uint flags);
+
+        uint Save(
+            [MarshalAs(UnmanagedType.Bool)] bool machine,
+            [MarshalAs(UnmanagedType.Bool)] bool add,
+            [MarshalAs(UnmanagedType.LPStruct)] Guid extension,
+            [MarshalAs(UnmanagedType.LPStruct)] Guid app);
+
+        uint Delete();
+
+        uint GetName(
+            [MarshalAs(UnmanagedType.LPWStr)] StringBuilder name,
+            int maxLength);
+
+        uint GetDisplayName(
+            [MarshalAs(UnmanagedType.LPWStr)] StringBuilder name,
+            int maxLength);
+
+        uint SetDisplayName(
+            [MarshalAs(UnmanagedType.LPWStr)] string name);
+
+        uint GetPath(
+            [MarshalAs(UnmanagedType.LPWStr)] StringBuilder path,
+            int maxPath);
+
+        uint GetDSPath(
+            uint section,
+            [MarshalAs(UnmanagedType.LPWStr)] StringBuilder path,
+            int maxPath);
+
+        uint GetFileSysPath(
+            uint section,
+            [MarshalAs(UnmanagedType.LPWStr)] StringBuilder path,
+            int maxPath);
+
+        uint GetRegistryKey(
+            uint section,
+            out IntPtr key);
+
+        uint GetOptions(out uint options);
+
+        uint SetOptions(
+            uint options,
+            uint mask);
+
+        uint GetType(
+            out IntPtr gpoType
+        );
+
+        uint GetMachineName(
+            [MarshalAs(UnmanagedType.LPWStr)] StringBuilder name,
+            int maxLength);
+
+        uint GetPropertySheetPages(
+            out IntPtr pages);
+    }
+}

File LocalPolicy/LocalPolicy.csproj

+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <PropertyGroup>
+    <Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>
+    <Platform Condition=" '$(Platform)' == '' ">x86</Platform>
+    <ProductVersion>8.0.30703</ProductVersion>
+    <SchemaVersion>2.0</SchemaVersion>
+    <ProjectGuid>{52BD99E0-0865-4F2C-9A65-0D2F9D1A8982}</ProjectGuid>
+    <OutputType>Library</OutputType>
+    <AppDesignerFolder>Properties</AppDesignerFolder>
+    <RootNamespace>LocalPolicy</RootNamespace>
+    <AssemblyName>LocalPolicy</AssemblyName>
+    <TargetFrameworkVersion>v4.0</TargetFrameworkVersion>
+    <TargetFrameworkProfile>Client</TargetFrameworkProfile>
+    <FileAlignment>512</FileAlignment>
+  </PropertyGroup>
+  <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|x86' ">
+    <PlatformTarget>x86</PlatformTarget>
+    <DebugSymbols>true</DebugSymbols>
+    <DebugType>full</DebugType>
+    <Optimize>false</Optimize>
+    <OutputPath>bin\Debug\</OutputPath>
+    <DefineConstants>DEBUG;TRACE</DefineConstants>
+    <ErrorReport>prompt</ErrorReport>
+    <WarningLevel>4</WarningLevel>
+  </PropertyGroup>
+  <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|x86' ">
+    <PlatformTarget>x86</PlatformTarget>
+    <DebugType>pdbonly</DebugType>
+    <Optimize>true</Optimize>
+    <OutputPath>bin\Release\</OutputPath>
+    <DefineConstants>TRACE</DefineConstants>
+    <ErrorReport>prompt</ErrorReport>
+    <WarningLevel>4</WarningLevel>
+  </PropertyGroup>
+  <PropertyGroup>
+    <StartupObject />
+  </PropertyGroup>
+  <ItemGroup>
+    <Reference Include="System" />
+    <Reference Include="System.Core" />
+    <Reference Include="System.Xml.Linq" />
+    <Reference Include="System.Data.DataSetExtensions" />
+    <Reference Include="Microsoft.CSharp" />
+    <Reference Include="System.Data" />
+    <Reference Include="System.Xml" />
+  </ItemGroup>
+  <ItemGroup>
+    <Compile Include="ActiveDirectoryGroupPolicyObject.cs" />
+    <Compile Include="AssemblyInfoHelper.cs" />
+    <Compile Include="ComputerGroupPolicyObject.cs" />
+    <Compile Include="GroupPolicyException.cs" />
+    <Compile Include="GroupPolicyObject.cs" />
+    <Compile Include="GroupPolicyObjectOptions.cs" />
+    <Compile Include="GroupPolicyObjectSettings.cs" />
+    <Compile Include="GroupPolicySection.cs" />
+    <Compile Include="IGroupPolicy.cs" />
+    <Compile Include="Properties\AssemblyInfo.cs" />
+  </ItemGroup>
+  <Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
+  <!-- To modify your build process, add your task inside one of the targets below and uncomment it. 
+       Other similar extension points exist, see Microsoft.Common.targets.
+  <Target Name="BeforeBuild">
+  </Target>
+  <Target Name="AfterBuild">
+  </Target>
+  -->
+</Project>

File LocalPolicy/Properties/AssemblyInfo.cs

+using System.Reflection;
+using System.Runtime.InteropServices;
+
+[assembly: AssemblyTitle("LocalPolicy")]
+[assembly: AssemblyCompany("LShift")]
+[assembly: AssemblyProduct("LocalPolicy")]
+[assembly: AssemblyCopyright("Copyright LShift © 2013")]
+[assembly: ComVisible(false)]
+[assembly: Guid("871be5be-5b76-4ec1-800b-3d96758c2f18")]
+[assembly: AssemblyVersion("1.0.0.0")]
+[assembly: AssemblyFileVersion("1.0.0.0")]