Team Ai
Datasetpublic

MegaBites-AI/Windows-powershell

sourceHugging Facemitupdated 6mo agoView on Hugging Face
0likes372downloads
AclCommands.cs1567 linesDownload Raw Back to security
1// Copyright (c) Microsoft Corporation.2// Licensed under the MIT License.3 4#pragma warning disable 1634, 16915#pragma warning disable 565066 7using System;8using System.Collections.Generic;9using System.Collections.ObjectModel;10using System.ComponentModel;11using System.Diagnostics.CodeAnalysis;12using System.Globalization;13using System.Management.Automation;14using System.Management.Automation.Security;15using System.Runtime.InteropServices;16using System.Security.AccessControl;17using System.Security.Principal;18 19using Dbg = System.Management.Automation;20 21namespace Microsoft.PowerShell.Commands22{23    /// <summary>24    /// Defines the base class from which all Security Descriptor commands25    /// are derived.26    /// </summary>27    public abstract class SecurityDescriptorCommandsBase : PSCmdlet28    {29        /// <summary>30        /// Gets or sets the filter property.  The filter31        /// property allows for provider-specific filtering of results.32        /// </summary>33        [Parameter]34        public string Filter35        {36            get37            {38                return _filter;39            }40 41            set42            {43                _filter = value;44            }45        }46 47        /// <summary>48        /// Gets or sets the include property.  The include property49        /// specifies the items on which the command will act.50        /// </summary>51        [Parameter]52        public string[] Include53        {54            get55            {56                return _include;57            }58 59            set60            {61                _include = value;62            }63        }64 65        /// <summary>66        /// Gets or sets the exclude property.  The exclude property67        /// specifies the items on which the command will not act.68        /// </summary>69        [Parameter]70        public string[] Exclude71        {72            get73            {74                return _exclude;75            }76 77            set78            {79                _exclude = value;80            }81        }82 83        /// <summary>84        /// The context for the command that is passed to the core command providers.85        /// </summary>86        internal CmdletProviderContext CmdletProviderContext87        {88            get89            {90                CmdletProviderContext coreCommandContext = new(this);91 92                Collection<string> includeFilter =93                    SessionStateUtilities.ConvertArrayToCollection<string>(Include);94 95                Collection<string> excludeFilter =96                    SessionStateUtilities.ConvertArrayToCollection<string>(Exclude);97 98                coreCommandContext.SetFilters(includeFilter,99                                              excludeFilter,100                                              Filter);101 102                return coreCommandContext;103            }104        }105 106        #region brokered properties107 108        /// <summary>109        /// Add brokered properties for easy access to important properties110        /// of security descriptor.111        /// </summary>112        internal static void AddBrokeredProperties(113            Collection<PSObject> results,114            bool audit,115            bool allCentralAccessPolicies)116        {117            foreach (PSObject result in results)118            {119                if (audit)120                {121                    // Audit122                    result.Properties.Add123                    (124                        new PSCodeProperty125                            (126                                "Audit",127                                typeof(SecurityDescriptorCommandsBase).GetMethod("GetAudit")128                            )129                    );130                }131                // CentralAccessPolicyId retrieval does not require elevation, so we always add this property.132                result.Properties.Add133                (134                    new PSCodeProperty135                        (136                            "CentralAccessPolicyId",137                            typeof(SecurityDescriptorCommandsBase).GetMethod("GetCentralAccessPolicyId")138                        )139                );140#if !CORECLR    // GetAllCentralAccessPolicies and GetCentralAccessPolicyName are not supported in OneCore powershell141                // because function 'LsaQueryCAPs' is not available in OneCoreUAP and NanoServer.142                if (allCentralAccessPolicies)143                {144                    // AllCentralAccessPolicies145                    result.Properties.Add146                    (147                        new PSCodeProperty148                            (149                                "AllCentralAccessPolicies",150                                typeof(SecurityDescriptorCommandsBase).GetMethod("GetAllCentralAccessPolicies")151                            )152                    );153                }154                // CentralAccessPolicyName retrieval does not require elevation, so we always add this property.155                result.Properties.Add156                (157                    new PSCodeProperty158                        (159                            "CentralAccessPolicyName",160                            typeof(SecurityDescriptorCommandsBase).GetMethod("GetCentralAccessPolicyName")161                        )162                );163#endif164            }165        }166 167        /// <summary>168        /// Gets the Path of the provided PSObject.169        /// </summary>170        /// <param name="instance">171        /// The PSObject for which to obtain the path.172        /// </param>173        /// <returns>174        /// The path of the provided PSObject.175        /// </returns>176        public static string GetPath(PSObject instance)177        {178            if (instance == null)179            {180                throw PSTraceSource.NewArgumentNullException(nameof(instance));181            }182            else183            {184                // These are guaranteed to not be null, but even checking185                // them for null causes a presharp warning186#pragma warning disable 56506187 188                // Get path189                return instance.Properties["PSPath"].Value.ToString();190#pragma warning restore 56506191            }192        }193 194        /// <summary>195        /// Gets the Owner of the provided PSObject.196        /// </summary>197        /// <param name="instance">198        /// The PSObject for which to obtain the Owner.199        /// </param>200        /// <returns>201        /// The Owner of the provided PSObject.202        /// </returns>203        public static string GetOwner(PSObject instance)204        {205            if (instance == null)206            {207                throw PSTraceSource.NewArgumentNullException(nameof(instance));208            }209 210            if (instance.BaseObject is not ObjectSecurity sd)211            {212                throw PSTraceSource.NewArgumentNullException(nameof(instance));213            }214 215            // Get owner216            try217            {218                IdentityReference ir = sd.GetOwner(typeof(NTAccount));219                return ir.ToString();220            }221            catch (IdentityNotMappedException)222            {223                // All Acl cmdlets returning SIDs will return a string224                // representation of the SID in all cases where the SID225                // cannot be mapped to a proper user or group name.226            }227 228            // We are here since we cannot get IdentityReference from sd..229            // So return sddl..230            return sd.GetSecurityDescriptorSddlForm(AccessControlSections.Owner);231        }232 233        /// <summary>234        /// Gets the Group of the provided PSObject.235        /// </summary>236        /// <param name="instance">237        /// The PSObject for which to obtain the Group.238        /// </param>239        /// <returns>240        /// The Group of the provided PSObject.241        /// </returns>242        public static string GetGroup(PSObject instance)243        {244            if (instance == null)245            {246                throw PSTraceSource.NewArgumentNullException(nameof(instance));247            }248 249            if (instance.BaseObject is not ObjectSecurity sd)250            {251                throw PSTraceSource.NewArgumentNullException(nameof(instance));252            }253 254            // Get Group255            try256            {257                IdentityReference ir = sd.GetGroup(typeof(NTAccount));258                return ir.ToString();259            }260            catch (IdentityNotMappedException)261            {262                // All Acl cmdlets returning SIDs will return a string263                // representation of the SID in all cases where the SID264                // cannot be mapped to a proper user or group name.265            }266 267            // We are here since we cannot get IdentityReference from sd..268            // So return sddl..269            return sd.GetSecurityDescriptorSddlForm(AccessControlSections.Group);270        }271        /// <summary>272        /// Gets the access rules of the provided PSObject.273        /// </summary>274        /// <param name="instance">275        /// The PSObject for which to obtain the access rules.276        /// </param>277        /// <returns>278        /// The access rules of the provided PSObject.279        /// </returns>280        public static AuthorizationRuleCollection GetAccess(PSObject instance)281        {282            if (instance == null)283            {284                throw PSTraceSource.NewArgumentNullException(nameof(instance));285            }286 287            ObjectSecurity sd = instance.BaseObject as ObjectSecurity;288            if (sd == null)289            {290                PSTraceSource.NewArgumentException(nameof(instance));291            }292 293            // Get DACL294            if (sd is CommonObjectSecurity cos)295            {296                return cos.GetAccessRules(true, true, typeof(NTAccount));297            }298            else299            {300                DirectoryObjectSecurity dos = sd as DirectoryObjectSecurity;301                Dbg.Diagnostics.Assert(dos != null, "Acl should be of type CommonObjectSecurity or DirectoryObjectSecurity");302                return dos.GetAccessRules(true, true, typeof(NTAccount));303            }304        }305 306        /// <summary>307        /// Gets the audit rules of the provided PSObject.308        /// </summary>309        /// <param name="instance">310        /// The PSObject for which to obtain the audit rules.311        /// </param>312        /// <returns>313        /// The audit rules of the provided PSObject.314        /// </returns>315        public static AuthorizationRuleCollection GetAudit(PSObject instance)316        {317            if (instance == null)318            {319                throw PSTraceSource.NewArgumentNullException(nameof(instance));320            }321 322            ObjectSecurity sd = instance.BaseObject as ObjectSecurity;323            if (sd == null)324            {325                PSTraceSource.NewArgumentException(nameof(instance));326            }327 328            if (sd is CommonObjectSecurity cos)329            {330                return cos.GetAuditRules(true, true, typeof(NTAccount));331            }332            else333            {334                DirectoryObjectSecurity dos = sd as DirectoryObjectSecurity;335                Dbg.Diagnostics.Assert(dos != null, "Acl should be of type CommonObjectSecurity or DirectoryObjectSecurity");336                return dos.GetAuditRules(true, true, typeof(NTAccount));337            }338        }339 340        /// <summary>341        /// Gets the central access policy ID of the provided PSObject.342        /// </summary>343        /// <param name="instance">344        /// The PSObject for which to obtain the central access policy ID.345        /// </param>346        /// <returns>347        /// The central access policy ID of the provided PSObject.348        /// </returns>349        public static SecurityIdentifier GetCentralAccessPolicyId(PSObject instance)350        {351            SessionState sessionState = new();352            string path = sessionState.Path.GetUnresolvedProviderPathFromPSPath(353                GetPath(instance));354            IntPtr pSd = IntPtr.Zero;355 356            try357            {358                // Get the file's SACL containing the CAPID ACE.359                uint rs = NativeMethods.GetNamedSecurityInfo(360                    path,361                    NativeMethods.SeObjectType.SE_FILE_OBJECT,362                    NativeMethods.SecurityInformation.SCOPE_SECURITY_INFORMATION,363                    out IntPtr pOwner,364                    out IntPtr pGroup,365                    out IntPtr pDacl,366                    out IntPtr pSacl,367                    out pSd);368                if (rs != NativeMethods.ERROR_SUCCESS)369                {370                    throw new Win32Exception((int)rs);371                }372 373                if (pSacl == IntPtr.Zero)374                {375                    return null;376                }377 378                NativeMethods.ACL sacl = Marshal.PtrToStructure<NativeMethods.ACL>(pSacl);379                if (sacl.AceCount == 0)380                {381                    return null;382                }383 384                // Extract the first CAPID from the SACL that does not have INHERIT_ONLY_ACE flag set.385                IntPtr pAce = pSacl + Marshal.SizeOf(new NativeMethods.ACL());386                for (ushort aceIdx = 0; aceIdx < sacl.AceCount; aceIdx++)387                {388                    NativeMethods.ACE_HEADER ace = Marshal.PtrToStructure<NativeMethods.ACE_HEADER>(pAce);389                    Dbg.Diagnostics.Assert(ace.AceType ==390                        NativeMethods.SYSTEM_SCOPED_POLICY_ID_ACE_TYPE,391                        "Unexpected ACE type: " + ace.AceType.ToString(CultureInfo.CurrentCulture));392                    if ((ace.AceFlags & NativeMethods.INHERIT_ONLY_ACE) == 0)393                    {394                        break;395                    }396 397                    pAce += ace.AceSize;398                }399 400                IntPtr pSid = pAce + Marshal.SizeOf(new NativeMethods.SYSTEM_AUDIT_ACE()) -401                    Marshal.SizeOf(new uint());402                bool ret = NativeMethods.IsValidSid(pSid);403                if (!ret)404                {405                    throw new Win32Exception(Marshal.GetLastWin32Error());406                }407 408                return new SecurityIdentifier(pSid);409            }410            finally411            {412                NativeMethods.LocalFree(pSd);413            }414        }415 416#if !CORECLR417        /// <summary>418        /// Gets the central access policy name of the provided PSObject.419        /// </summary>420        /// <remarks>421        /// Function 'LsaQueryCAPs' is not available in OneCoreUAP and NanoServer.422        /// </remarks>423        /// <param name="instance">424        /// The PSObject for which to obtain the central access policy name.425        /// </param>426        /// <returns>427        /// The central access policy name of the provided PSObject.428        /// </returns>429        public static string GetCentralAccessPolicyName(PSObject instance)430        {431            SecurityIdentifier capId = GetCentralAccessPolicyId(instance);432            if (capId == null)433            {434                return null; // file does not have the scope ace435            }436 437            int capIdSize = capId.BinaryLength;438            byte[] capIdArray = new byte[capIdSize];439            capId.GetBinaryForm(capIdArray, 0);440            IntPtr caps = IntPtr.Zero;441            IntPtr pCapId = Marshal.AllocHGlobal(capIdSize);442 443            try444            {445                // Retrieve the CAP by CAPID.446                Marshal.Copy(capIdArray, 0, pCapId, capIdSize);447                IntPtr[] ppCapId = new IntPtr[1];448                ppCapId[0] = pCapId;449                uint rs = NativeMethods.LsaQueryCAPs(450                    ppCapId,451                    1,452                    out caps,453                    out uint capCount);454                if (rs != NativeMethods.STATUS_SUCCESS)455                {456                    throw new Win32Exception((int)rs);457                }458 459                if (capCount == 0 || caps == IntPtr.Zero)460                {461                    return null;462                }463 464                // Get the CAP name.465                NativeMethods.CENTRAL_ACCESS_POLICY cap = Marshal.PtrToStructure<NativeMethods.CENTRAL_ACCESS_POLICY>(caps);466                // LSA_UNICODE_STRING is composed of WCHARs, but its length is given in bytes.467                return Marshal.PtrToStringUni(cap.Name.Buffer, cap.Name.Length / 2);468            }469            finally470            {471                Marshal.FreeHGlobal(pCapId);472                uint rs = NativeMethods.LsaFreeMemory(caps);473                Dbg.Diagnostics.Assert(rs == NativeMethods.STATUS_SUCCESS,474                    "LsaFreeMemory failed: " + rs.ToString(CultureInfo.CurrentCulture));475            }476        }477 478        /// <summary>479        /// Gets the names and IDs of all central access policies available on the machine.480        /// </summary>481        /// <remarks>482        /// Function 'LsaQueryCAPs' is not available in OneCoreUAP and NanoServer.483        /// </remarks>484        /// <param name="instance">485        /// The PSObject argument is ignored.486        /// </param>487        /// <returns>488        /// The names and IDs of all central access policies available on the machine.489        /// </returns>490        public static string[] GetAllCentralAccessPolicies(PSObject instance)491        {492            IntPtr caps = IntPtr.Zero;493 494            try495            {496                // Retrieve all CAPs.497                uint rs = NativeMethods.LsaQueryCAPs(498                    null,499                    0,500                    out caps,501                    out uint capCount);502                if (rs != NativeMethods.STATUS_SUCCESS)503                {504                    throw new Win32Exception((int)rs);505                }506 507                Dbg.Diagnostics.Assert(capCount < 0xFFFF,508                    "Too many central access policies");509                if (capCount == 0 || caps == IntPtr.Zero)510                {511                    return null;512                }513 514                // Add CAP names and IDs to a string array.515                string[] policies = new string[capCount];516                IntPtr capPtr = caps;517                for (uint capIdx = 0; capIdx < capCount; capIdx++)518                {519                    // Retrieve CAP name.520                    Dbg.Diagnostics.Assert(capPtr != IntPtr.Zero,521                        "Invalid central access policies array");522                    NativeMethods.CENTRAL_ACCESS_POLICY cap = Marshal.PtrToStructure<NativeMethods.CENTRAL_ACCESS_POLICY>(capPtr);523                    // LSA_UNICODE_STRING is composed of WCHARs, but its length is given in bytes.524                    policies[capIdx] = "\"" + Marshal.PtrToStringUni(525                        cap.Name.Buffer,526                        cap.Name.Length / 2) + "\"";527 528                    // Retrieve CAPID.529                    IntPtr pCapId = cap.CAPID;530                    Dbg.Diagnostics.Assert(pCapId != IntPtr.Zero,531                        "Invalid central access policies array");532                    bool ret = NativeMethods.IsValidSid(pCapId);533                    if (!ret)534                    {535                        throw new Win32Exception(Marshal.GetLastWin32Error());536                    }537 538                    SecurityIdentifier sid = new SecurityIdentifier(pCapId);539                    policies[capIdx] += " (" + sid.ToString() + ")";540 541                    capPtr += Marshal.SizeOf(cap);542                }543 544                return policies;545            }546            finally547            {548                uint rs = NativeMethods.LsaFreeMemory(caps);549                Dbg.Diagnostics.Assert(rs == NativeMethods.STATUS_SUCCESS,550                    "LsaFreeMemory failed: " + rs.ToString(CultureInfo.CurrentCulture));551            }552        }553#endif554 555        /// <summary>556        /// Gets the security descriptor (in SDDL form) of the557        /// provided PSObject.  SDDL form is the Security Descriptor558        /// Definition Language.559        /// </summary>560        /// <param name="instance">561        /// The PSObject for which to obtain the security descriptor.562        /// </param>563        /// <returns>564        /// The security descriptor of the provided PSObject, in SDDL form.565        /// </returns>566        public static string GetSddl(PSObject instance)567        {568            if (instance == null)569            {570                throw PSTraceSource.NewArgumentNullException(nameof(instance));571            }572 573            if (instance.BaseObject is not ObjectSecurity sd)574            {575                throw PSTraceSource.NewArgumentNullException(nameof(instance));576            }577 578            string sddl = sd.GetSecurityDescriptorSddlForm(AccessControlSections.All);579            return sddl;580        }581 582        #endregion brokered properties583 584        /// <summary>585        /// The filter to be used to when globbing to get the item.586        /// </summary>587        private string _filter;588 589        /// <summary>590        /// The glob string used to determine which items are included.591        /// </summary>592        private string[] _include = Array.Empty<string>();593 594        /// <summary>595        /// The glob string used to determine which items are excluded.596        /// </summary>597        private string[] _exclude = Array.Empty<string>();598    }599 600#if !UNIX601    /// <summary>602    /// Defines the implementation of the 'get-acl' cmdlet.603    /// This cmdlet gets the security descriptor of an item at the specified path.604    /// </summary>605    [Cmdlet(VerbsCommon.Get, "Acl", SupportsTransactions = true, DefaultParameterSetName = "ByPath", HelpUri = "https://go.microsoft.com/fwlink/?LinkID=2096593")]606    public sealed class GetAclCommand : SecurityDescriptorCommandsBase607    {608        /// <summary>609        /// Initializes a new instance of the GetAclCommand610        /// class.  Sets the default path to the current location.611        /// </summary>612        public GetAclCommand()613        {614            // Default for path is the current location615            _path = new string[] { "." };616        }617        #region parameters618 619        private string[] _path;620 621        /// <summary>622        /// Gets or sets the path of the item for which to obtain the623        /// security descriptor.  Default is the current location.624        /// </summary>625        [Parameter(Position = 0, ValueFromPipeline = true, ValueFromPipelineByPropertyName = true, ParameterSetName = "ByPath")]626        [ValidateNotNullOrEmpty]627        public string[] Path628        {629            get630            {631                return _path;632            }633 634            set635            {636                _path = value;637            }638        }639 640        private PSObject _inputObject;641 642        /// <summary>643        /// InputObject Parameter644        /// Gets or sets the inputObject for which to obtain the security descriptor.645        /// </summary>646        [Parameter(Mandatory = true, ParameterSetName = "ByInputObject")]647        public PSObject InputObject648        {649            get650            {651                return _inputObject;652            }653 654            set655            {656                _inputObject = value;657            }658        }659 660        /// <summary>661        /// Gets or sets the literal path of the item for which to obtain the662        /// security descriptor.  Default is the current location.663        /// </summary>664        [Parameter(ValueFromPipeline = true, ValueFromPipelineByPropertyName = true, ParameterSetName = "ByLiteralPath")]665        [Alias("PSPath", "LP")]666        [ValidateNotNullOrEmpty]667        [SuppressMessage("Microsoft.Performance", "CA1819:PropertiesShouldNotReturnArrays")]668        public string[] LiteralPath669        {670            get671            {672                return _path;673            }674 675            set676            {677                _path = value;678                _isLiteralPath = true;679            }680        }681 682        private bool _isLiteralPath;683 684        /// <summary>685        /// Gets or sets the audit flag of the command.  This flag686        /// determines if audit rules should also be retrieved.687        /// </summary>688        [Parameter]689        public SwitchParameter Audit690        {691            get692            {693                return _audit;694            }695 696            set697            {698                _audit = value;699            }700        }701 702        private SwitchParameter _audit;703 704#if CORECLR705        /// <summary>706        /// Parameter '-AllCentralAccessPolicies' is not supported in OneCore powershell,707        /// because function 'LsaQueryCAPs' is not available in OneCoreUAP and NanoServer.708        /// </summary>709        private SwitchParameter AllCentralAccessPolicies710        {711            get; set;712        }713#else714        /// <summary>715        /// Gets or sets the AllCentralAccessPolicies flag of the command. This flag716        /// determines whether the information about all central access policies717        /// available on the machine should be displayed.718        /// </summary>719        [Parameter]720        public SwitchParameter AllCentralAccessPolicies721        {722            get723            {724                return allCentralAccessPolicies;725            }726 727            set728            {729                allCentralAccessPolicies = value;730            }731        }732 733        private SwitchParameter allCentralAccessPolicies;734#endif735 736        #endregion737 738        /// <summary>739        /// Processes records from the input pipeline.740        /// For each input file, the command retrieves its741        /// corresponding security descriptor.742        /// </summary>743        protected override void ProcessRecord()744        {745            AccessControlSections sections =746                AccessControlSections.Owner |747                AccessControlSections.Group |748                AccessControlSections.Access;749            if (_audit)750            {751                sections |= AccessControlSections.Audit;752            }753 754            if (_inputObject != null)755            {756                PSMethodInfo methodInfo = _inputObject.Methods["GetSecurityDescriptor"];757 758                if (methodInfo != null)759                {760                    object customDescriptor = null;761 762                    try763                    {764                        customDescriptor = PSObject.Base(methodInfo.Invoke());765 766                        if (customDescriptor is not FileSystemSecurity)767                        {768                            customDescriptor = new CommonSecurityDescriptor(false, false, customDescriptor.ToString());769                        }770                    }771                    catch (Exception)772                    {773                        // Calling user code, Catch-all OK774                        ErrorRecord er =775                        SecurityUtils.CreateNotSupportedErrorRecord(776                            UtilsStrings.MethodInvokeFail,777                            "GetAcl_OperationNotSupported"778                            );779 780                        WriteError(er);781                        return;782                    }783 784                    WriteObject(customDescriptor, true);785                }786                else787                {788                    ErrorRecord er =789                        SecurityUtils.CreateNotSupportedErrorRecord(790                            UtilsStrings.GetMethodNotFound,791                            "GetAcl_OperationNotSupported"792                            );793 794                    WriteError(er);795                }796            }797            else798            {799                foreach (string p in Path)800                {801                    List<string> pathsToProcess = new();802 803                    string currentPath = null;804                    try805                    {806                        if (_isLiteralPath)807                        {808                            pathsToProcess.Add(p);809                        }810                        else811                        {812                            Collection<PathInfo> resolvedPaths =813                                SessionState.Path.GetResolvedPSPathFromPSPath(p, CmdletProviderContext);814                            foreach (PathInfo pi in resolvedPaths)815                            {816                                pathsToProcess.Add(pi.Path);817                            }818                        }819 820                        foreach (string rp in pathsToProcess)821                        {822                            currentPath = rp;823 824                            CmdletProviderContext context = new(this.Context);825                            context.SuppressWildcardExpansion = true;826 827                            if (!InvokeProvider.Item.Exists(rp, false, _isLiteralPath))828                            {829                                ErrorRecord er =830                                    SecurityUtils.CreatePathNotFoundErrorRecord(831                                               rp,832                                               "GetAcl_PathNotFound"833                                    );834 835                                WriteError(er);836                                continue;837                            }838 839                            InvokeProvider.SecurityDescriptor.Get(rp, sections, context);840 841                            Collection<PSObject> sd = context.GetAccumulatedObjects();842                            if (sd != null)843                            {844                                AddBrokeredProperties(845                                    sd,846                                    _audit,847                                    AllCentralAccessPolicies);848                                WriteObject(sd, true);849                            }850                        }851                    }852                    catch (NotSupportedException)853                    {854                        ErrorRecord er =855                            SecurityUtils.CreateNotSupportedErrorRecord(856                                UtilsStrings.OperationNotSupportedOnPath,857                                "GetAcl_OperationNotSupported",858                                currentPath859                            );860 861                        WriteError(er);862                    }863                    catch (ItemNotFoundException)864                    {865                        ErrorRecord er =866                            SecurityUtils.CreatePathNotFoundErrorRecord(867                                p,868                                "GetAcl_PathNotFound_Exception"869                            );870 871                        WriteError(er);872                        continue;873                    }874                }875            }876        }877    }878 879    /// <summary>880    /// Defines the implementation of the 'set-acl' cmdlet.881    /// This cmdlet sets the security descriptor of an item at the specified path.882    /// </summary>883    [Cmdlet(VerbsCommon.Set, "Acl", SupportsShouldProcess = true, SupportsTransactions = true, DefaultParameterSetName = "ByPath",884            HelpUri = "https://go.microsoft.com/fwlink/?LinkID=2096600")]885    public sealed class SetAclCommand : SecurityDescriptorCommandsBase886    {887        private string[] _path;888 889        /// <summary>890        /// Gets or sets the path of the item for which to set the891        /// security descriptor.892        /// </summary>893        [Parameter(Position = 0, Mandatory = true, ValueFromPipelineByPropertyName = true, ParameterSetName = "ByPath")]894        public string[] Path895        {896            get897            {898                return _path;899            }900 901            set902            {903                _path = value;904            }905        }906 907        private PSObject _inputObject;908 909        /// <summary>910        /// InputObject Parameter911        /// Gets or sets the inputObject for which to set the security descriptor.912        /// </summary>913        [Parameter(Position = 0, Mandatory = true, ValueFromPipelineByPropertyName = true, ParameterSetName = "ByInputObject")]914        public PSObject InputObject915        {916            get917            {918                return _inputObject;919            }920 921            set922            {923                _inputObject = value;924            }925        }926 927        /// <summary>928        /// Gets or sets the literal path of the item for which to set the929        /// security descriptor.930        /// </summary>931        [Parameter(Mandatory = true, ValueFromPipelineByPropertyName = true, ParameterSetName = "ByLiteralPath")]932        [Alias("PSPath", "LP")]933        [SuppressMessage("Microsoft.Performance", "CA1819:PropertiesShouldNotReturnArrays")]934        public string[] LiteralPath935        {936            get937            {938                return _path;939            }940 941            set942            {943                _path = value;944                _isLiteralPath = true;945            }946        }947 948        private bool _isLiteralPath;949 950        private object _securityDescriptor;951 952        /// <summary>953        /// Gets or sets the security descriptor object to be954        /// set on the target item(s).955        /// </summary>956        [Parameter(Position = 1, Mandatory = true, ValueFromPipeline = true, ParameterSetName = "ByPath")]957        [Parameter(Position = 1, Mandatory = true, ValueFromPipeline = true, ParameterSetName = "ByLiteralPath")]958        [Parameter(Position = 1, Mandatory = true, ValueFromPipeline = true, ParameterSetName = "ByInputObject")]959        public object AclObject960        {961            get962            {963                return _securityDescriptor;964            }965 966            set967            {968                _securityDescriptor = PSObject.Base(value);969            }970        }971 972#if CORECLR973        /// <summary>974        /// Parameter '-CentralAccessPolicy' is not supported in OneCore powershell,975        /// because function 'LsaQueryCAPs' is not available in OneCoreUAP and NanoServer.976        /// </summary>977        private string CentralAccessPolicy { get; }978#else979        private string centralAccessPolicy;980 981        /// <summary>982        /// Gets or sets the central access policy to be983        /// set on the target item(s).984        /// </summary>985        [Parameter(Position = 2, Mandatory = false, ValueFromPipelineByPropertyName = true, ParameterSetName = "ByPath")]986        [Parameter(Position = 2, Mandatory = false, ValueFromPipelineByPropertyName = true, ParameterSetName = "ByLiteralPath")]987        public string CentralAccessPolicy988        {989            get990            {991                return centralAccessPolicy;992            }993 994            set995            {996                centralAccessPolicy = value;997            }998        }999#endif1000 1001        private SwitchParameter _clearCentralAccessPolicy;1002 1003        /// <summary>1004        /// Clears the central access policy applied on the target item(s).1005        /// </summary>1006        [Parameter(Mandatory = false, ParameterSetName = "ByPath")]1007        [Parameter(Mandatory = false, ParameterSetName = "ByLiteralPath")]1008        public SwitchParameter ClearCentralAccessPolicy1009        {1010            get1011            {1012                return _clearCentralAccessPolicy;1013            }1014 1015            set1016            {1017                _clearCentralAccessPolicy = value;1018            }1019        }1020 1021        private SwitchParameter _passthru;1022 1023        /// <summary>1024        /// Gets or sets the Passthru flag for the operation.1025        /// If true, the security descriptor is also passed1026        /// down the output pipeline.1027        /// </summary>1028        [Parameter]1029        public SwitchParameter Passthru1030        {1031            get1032            {1033                return _passthru;1034            }1035 1036            set1037            {1038                _passthru = value;1039            }1040        }1041 1042        /// <summary>1043        /// Returns a newly allocated SACL with no ACEs in it.1044        /// Free the returned SACL by calling Marshal.FreeHGlobal.1045        /// </summary>1046        private static IntPtr GetEmptySacl()1047        {1048            IntPtr pSacl = IntPtr.Zero;1049            bool ret = true;1050 1051            try1052            {1053                // Calculate the size of the empty SACL, align to DWORD.1054                uint saclSize = (uint)(Marshal.SizeOf(new NativeMethods.ACL()) +1055                    Marshal.SizeOf(new uint()) - 1) & 0xFFFFFFFC;1056                Dbg.Diagnostics.Assert(saclSize < 0xFFFF,1057                    "Acl size must be less than max SD size of 0xFFFF");1058 1059                // Allocate and initialize the SACL.1060                pSacl = Marshal.AllocHGlobal((int)saclSize);1061                ret = NativeMethods.InitializeAcl(1062                    pSacl,1063                    saclSize,1064                    NativeMethods.ACL_REVISION);1065                if (!ret)1066                {1067                    throw new Win32Exception(Marshal.GetLastWin32Error());1068                }1069            }1070            finally1071            {1072                if (!ret)1073                {1074                    Marshal.FreeHGlobal(pSacl);1075                    pSacl = IntPtr.Zero;1076                }1077            }1078 1079            return pSacl;1080        }1081 1082        /// <summary>1083        /// Returns a newly allocated SACL with the supplied CAPID in it.1084        /// Free the returned SACL by calling Marshal.FreeHGlobal.1085        /// </summary>1086        /// <remarks>1087        /// Function 'LsaQueryCAPs' is not available in OneCoreUAP and NanoServer.1088        /// So the parameter "-CentralAccessPolicy" is not supported on OneCore powershell,1089        /// and thus this method won't be hit in OneCore powershell.1090        /// </remarks>1091        private IntPtr GetSaclWithCapId(string capStr)1092        {1093            IntPtr pCapId = IntPtr.Zero, pSacl = IntPtr.Zero;1094            IntPtr caps = IntPtr.Zero;1095            bool ret = true, freeCapId = true;1096            uint rs = NativeMethods.STATUS_SUCCESS;1097 1098            try1099            {1100                // Convert the supplied SID from string to binary form.1101                ret = NativeMethods.ConvertStringSidToSid(capStr, out pCapId);1102                if (!ret)1103                {1104                    // We may have got a CAP friendly name instead of CAPID.1105                    // Enumerate all CAPs on the system and try to find one with1106                    // a matching friendly name.1107                    // If we retrieve the CAPID from the LSA, the CAPID need not1108                    // be deallocated separately (but with the entire buffer1109                    // returned by LsaQueryCAPs).1110                    freeCapId = false;1111                    rs = NativeMethods.LsaQueryCAPs(1112                        null,1113                        0,1114                        out caps,1115                        out uint capCount);1116                    if (rs != NativeMethods.STATUS_SUCCESS)1117                    {1118                        throw new Win32Exception((int)rs);1119                    }1120 1121                    Dbg.Diagnostics.Assert(capCount < 0xFFFF,1122                        "Too many central access policies");1123                    if (capCount == 0 || caps == IntPtr.Zero)1124                    {1125                        return IntPtr.Zero;1126                    }1127 1128                    // Find the supplied string among available CAP names, use the corresponding CAPID.1129                    IntPtr capPtr = caps;1130                    for (uint capIdx = 0; capIdx < capCount; capIdx++)1131                    {1132                        Dbg.Diagnostics.Assert(capPtr != IntPtr.Zero,1133                            "Invalid central access policies array");1134                        NativeMethods.CENTRAL_ACCESS_POLICY cap = Marshal.PtrToStructure<NativeMethods.CENTRAL_ACCESS_POLICY>(capPtr);1135                        // LSA_UNICODE_STRING is composed of WCHARs, but its length is given in bytes.1136                        string capName = Marshal.PtrToStringUni(1137                            cap.Name.Buffer,1138                            cap.Name.Length / 2);1139                        if (capName.Equals(capStr, StringComparison.OrdinalIgnoreCase))1140                        {1141                            pCapId = cap.CAPID;1142                            break;1143                        }1144 1145                        capPtr += Marshal.SizeOf(cap);1146                    }1147                }1148 1149                if (pCapId == IntPtr.Zero)1150                {1151                    Exception e = new ArgumentException(UtilsStrings.InvalidCentralAccessPolicyIdentifier);1152                    WriteError(new ErrorRecord(1153                        e,1154                        "SetAcl_CentralAccessPolicy",1155                        ErrorCategory.InvalidArgument,1156                        AclObject));1157                    return IntPtr.Zero;1158                }1159 1160                ret = NativeMethods.IsValidSid(pCapId);1161                if (!ret)1162                {1163                    throw new Win32Exception(Marshal.GetLastWin32Error());1164                }1165 1166                uint sidSize = NativeMethods.GetLengthSid(pCapId);1167 1168                // Calculate the size of the SACL with one CAPID ACE, align to DWORD.1169                uint saclSize = (uint)(Marshal.SizeOf(new NativeMethods.ACL()) +1170                    Marshal.SizeOf(new NativeMethods.SYSTEM_AUDIT_ACE()) +1171                    sidSize - 1) & 0xFFFFFFFC;1172                Dbg.Diagnostics.Assert(saclSize < 0xFFFF,1173                    "Acl size must be less than max SD size of 0xFFFF");1174 1175                // Allocate and initialize the SACL.1176                pSacl = Marshal.AllocHGlobal((int)saclSize);1177                ret = NativeMethods.InitializeAcl(1178                    pSacl,1179                    saclSize,1180                    NativeMethods.ACL_REVISION);1181                if (!ret)1182                {1183                    throw new Win32Exception(Marshal.GetLastWin32Error());1184                }1185 1186                // Add CAPID to the SACL.1187                rs = NativeMethods.AddScopedPolicyIDAce(1188                    pSacl,1189                    NativeMethods.ACL_REVISION,1190                    NativeMethods.SUB_CONTAINERS_AND_OBJECTS_INHERIT,1191                    0,1192                    pCapId);1193                if (rs != NativeMethods.STATUS_SUCCESS)1194                {1195                    if (rs == NativeMethods.STATUS_INVALID_PARAMETER)1196                    {1197                        throw new ArgumentException(UtilsStrings.InvalidCentralAccessPolicyIdentifier);1198                    }1199                    else1200                    {

Showing the first 1,200 of 1567 lines. Download the file for the rest.