PowerShell: Set-Acl Does Not Appear to Work

If you’ve ever dealt with NTFS permissions in VBScript, you will no doubt appreciate just how easy PowerShell now makes it to manage access control lists. Basic examples in PowerShell books and around the ‘net look something like this:

$directory = "Test"
$acl = Get-Acl $directory
$accessrule = New-Object system.security.AccessControl.FileSystemAccessRule("IUSR_CRACKLIN", "Modify", "Allow")
$acl.AddAccessRule($accessrule)
set-acl -aclobject $acl $directory

In the example above, user “IUSR_CRACKLIN” is given Modify access to the Test directory. Running the code above will not produce any errors but upon checking permission via the GUI, it seems as though the user was added, but no permissions were set.

I thought that perhaps this was an issue with Vista and I tried it on Windows Server 2003. And that’s when I noticed that the directory had been given “Special Permissions.” When I checked the Advanced permissions, I could see that Modify access had been assigned, but only to “This Folder.” Other folders that had the checkboxes checked listed “This Folder, subfolders and files”

Since I wanted the Test directory permissions to match the others, I searched the Google to see which flags would give me “This Folder, subfolders and files.” I found Damir Dobric’s blog post titled “Directory Security and Access Rules which sported a handy reference table flags that must be set to achieve various scenarios.

Subfolders and Files only InheritanceFlags.ContainerInherit, InheritanceFlags.ObjectInherit, PropagationFlags.InheritOnly
This Folder, Subfolders and Files    InheritanceFlags.ContainerInherit, InheritanceFlags.ObjectInherit, PropagationFlags.None
This Folder, Subfolders and Files InheritanceFlags.ContainerInherit, InheritanceFlags.ObjectInherit, PropagationFlags.NoPropagateInherit
This folder and subfolders InheritanceFlags.ContainerInherit, PropagationFlags.None
Subfolders only InheritanceFlags.ContainerInherit, PropagationFlags.InheritOnly
This folder and files InheritanceFlags.ObjectInherit, PropagationFlags.None
This folder and files InheritanceFlags.ObjectInherit, PropagationFlags.NoPropagateInherit

So it setting the following should give me what I need:
InheritanceFlags.ContainerInherit, InheritanceFlags.ObjectInherit and PropagationFlags.None
.

$directory = "Test"
$inherit = [system.security.accesscontrol.InheritanceFlags]"ContainerInherit, ObjectInherit"
$propagation = [system.security.accesscontrol.PropagationFlags]"None"
$acl = Get-Acl $directory
$accessrule = New-Object system.security.AccessControl.FileSystemAccessRule("IUSR_CRACKLIN", "Modify", $inherit, $propagation, "Allow")
$acl.AddAccessRule($accessrule)
set-acl -aclobject $acl $directory

I then checked the permissions and voila:

Imagine that.. PowerShell can set any number of permissions with about 6 lines of code while VBScript requires over 36 lines JUST to set the constants needed for managing permissions. I’m so excited thinking about the possibilities: PowerShell + Windows Core + SSH is going to be awesome.

Posted in PowerShell, Security
20 comments on “PowerShell: Set-Acl Does Not Appear to Work
  1. ghjconan says:

    Thank you :)

    I’m writing a ps script about batch creating floders with certain ACL.

  2. Colin Bowern says:

    Thanks for the post! That saved a whole bunch of time (and like your experience, cut down my VBScript)

  3. Michael says:

    Another option use xcacls or cacls… You can do this at the command line of your shell and pass it parameters in 1 line of code. This is what I have done in the past with automating our file server, works, it’s slow but it works.

  4. Kunal says:

    Hello,

    I am using BlogEngin.NET open source application. Afer transfering to New Hosting Provider. I getting error of access denied. Which is basically the problem of permission of “App_Data” Folder.

    I told to my hosting provider. They told me that we have set the permission. After that I will getting this error ocasionally means some times. I will refersh the page again and again then sudenly error comes. If you go through all page one by one then suddenly error appears.

    If you want to check my website is http://elevatesoftsolutions.in/default.aspx

    Please let me any other way to set the permission to existing folder.

    Thanks
    Kunal Mehta

    http://360by2.blogspot.com/

  5. Sean Kearney says:

    Hey Thanks for that! I’ve been using a script in Powershell that sets up all my users for me daily in including home folder and permissions. the only stumbling block was I had to keep going in and resetting the subfolder permissions after.

    THIS NAILED IT!

    Sean
    the Energized Tech

  6. Sam Prince says:

    Thanks for the post. I’m trying to use Powershell to tell me (amongst other things) if an ACE within an ACL was set explicitly or inherited. In GUI terms this means: are the tickboxes for the relevant ACE enabled or greyed out?

    I thought that info would be stored in PropagationFlags or InheritanceFlags, but sadly my two test folders report identical settings for those despite one have explicit perms set and the other being inherited.

    Any insights?!

    • Sam Prince says:

      UPDATE: As is always the case, I found the answer immediately after posting! There is another property of the ACE called “IsInherited” which evaluates to either true or false and is exactly what I was after!

  7. Ian Manning says:

    Really useful post – save me loads of time :)

  8. Ian Manning says:

    Any get this error intermitently when running the New-Object part of the script above?

    “New-Object : Cannot find an overload for “FileSystemAccessRule” and the argument count: “5″.”

    I can’t pin down what is changing when I do and don’t get this.

  9. Ian manning says:

    I eventually “solved this” myself, but I don’t understand how/why it works:

    If you do :

    $accessrule = New-Object system.security.AccessControl.FileSystemAccessRule($UserObject, “Modify”, “3″, “None”, “Allow”)

    ie pass the arguments direct, it works. There is probably something obvious going on here, but I don’t have time to work out what at the moment.

  10. Liberty says:

    Great post!

    Another way to pass the arguments directly:

    $accessrule = New-Object system.security.AccessControl.FileSystemAccessRule(“IUSR_CRACKLIN”, “Modify”, “ContainerInherit,ObjectInherit”, “None”, “Allow”)

  11. Noba Dee says:

    … and it could be done in ONE line at the "shell" command prompt, on VMS forty years ago. (The whole concept, most of the syntax, and the interactions among, ownership, protections, and ACLs, was lifted almost in one piece from VMS by the Windows NT system architect, Dave Cutler. Then Microsoft mixed in its own peculiar brand of f'd-uppedness, and now we have the PowerShell way of doing it. Yay.)

  12. Pete says:

    If you want "files only" use InheritanceFlags.ObjectInherit and PropagationFlags.InheritOnly

  13. Martin says:

    Great post! It finaly helped me a lot, finishing my script! Thanks!

  14. robertpearman says:

    Just what i needed!

  15. Praveen says:

    I have 500 users list to create TS profiles and I need a script to create
    1, 500 folders with respective user name
    2, Respective folder needs full permission to respective users
    3, path needs to be updated in the respective users TS profile

    • Chrissy LeMaire says:

      Alright, 200 euros an hour. Estimated 30 hours of work. All paid upfront :) No guarantees, no warranties.

  16. Noel says:

    Same thing for me!

    Thanks!!

3 Pings/Trackbacks for "PowerShell: Set-Acl Does Not Appear to Work"
  1. [...] 这里插入一段题外话。对很多ITpro而言,.net是开发人员用的,因此也不会把太多时间花在这上。但是我们在实际工作中时不时会遇到需要写一段脚本来解决的问题。很多人的办法就是通过访问脚本中心或者搜索来解决问题。那么对于.net而言,其实我们也可以通过搜索解决问题,在不知道具体.net方法的情况下。昨天我在思考“批量创建带有特定ACL的文件夹”这个问题时,我也是通过搜索知道如何利用.net配合PowerShell来设置ACL。昨天我的搜索关键词是“PowerShell Set-ACL”,搜索结果的第四个正是我需要的内容。在该页面提供的脚本基础之上,我完成了以下代码。 [...]

Leave a Reply

Your email address will not be published. Required fields are marked *

*

You may use these HTML tags and attributes: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code class="" title="" data-url=""> <del datetime=""> <em> <i> <q cite=""> <strike> <strong> <pre class="" title="" data-url=""> <span class="" title="" data-url="">