2
votes

In need to get the ACL object and replace an Access.IdentityReference.Value and keep the rest of the object intact so I can apply the Set-Acl to another system.

$acl = Get-Acl -Path "C:\Temp"
$h = New-Object -TypeName PSObject
ForEach-Object -InputObject $acl -Process {
    if ($_.Access.IdentityReference.Value -contains "BUILTIN\Users") {
        "found"
        $h += @($_.Access.IdentityReference.Value.Replace("BUILTIN\Users", "new\name"))
    } else {
        $h += @($_)
    }
}
$h.Access

I have so many ways to do this and the best I have been able to get is finding and replacing the target value but losing the rest of the original object.


Edit: when I try this code:

$acl = Get-Acl -Path 'C:\Temp'

$ace = $acl.Access | Where-Object { $_.IdentityReference -eq 'BUILTIN\Users' }
$newAce = New-Object System.Security.AccessControl.FileSystemAccessRule (
    'new\name',
    $ace.FileSystemRights,
    $ace.InheritanceFlags,
    $ace.PropagationFlags,
    $ace.AccessControlType
)
$acl.RemoveAccessRule($ace)
$acl.AddAccessRule($newAce)

Set-Acl -Path 'C:\Temp' -AclObject $acl

I'm getting the following error:

Exception calling "AddAccessRule" with "1" argument(s): "Some or all identity
references could not be translated."
At line:12 char:1
+ $acl.AddAccessRule($newAce)
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~
     + CategoryInfo          : NotSpecified: (:) [], MethodInvocationException
     + FullyQualifiedErrorId : IdentityNotMappedException

Edit2: New script, but not quite there yet:

$Ssid = "S-1-5-21-2214593661-3374179426-1523454523-1133"
$Tsid = "S-1-5-21-2227185791-3254421074-497073356-1005"
$Spath = "\\clw01\dept\CLW_Site"
$Tpath = "\\clw03\dept\CLW_Site"

$acl = Get-Acl -Path $Spath

$ace = $acl.Access | Where-Object { $_.IdentityReference -eq $Ssid }
$newAce = New-Object System.Security.AccessControl.FileSystemAccessRule (
    $Tsid,
    $ace.FileSystemRights,
    $ace.InheritanceFlags,
    $ace.PropagationFlags,
    $ace.AccessControlType
)
$acl.RemoveAccessRule($ace)
$acl.AddAccessRule($newAce)

Set-Acl -Path $Tpath -AclObject $acl

I'm getting the following error:

Exception calling "AddAccessRule" with "1" argument(s): "The trust relationship
between the primary domain and the trusted domain failed."
At line:9 char:1
+ $acl.AddAccessRule($newAce)
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~
    + CategoryInfo          : NotSpecified: (:) [], MethodInvocationException
    + FullyQualifiedErrorId : SystemException
1
Is new\name actually resolvable on the computer? Is new a different host? A trusted domain? External or in the same forest?Ansgar Wiechers
no, it is not resolvable on the computer it is running on, but it would be on the local computer that has the local group. Basically we have server1 (old server), server2(new server) and AdmWs1(workstation running the script). Server1 has many folders with local groups permissions to them, I need to copy the folders and local groups to server2, then copy the ACLsDavid C
It must be resolvable on the computer where you're running the code, otherwise it's not going to work. If you want to change a local group on a remote host you may want to run the code remotely, e.g. via Invoke-Command.Ansgar Wiechers
Or reference the local group by SID?David C
You can try, but I'm not sure it'll work.Ansgar Wiechers

1 Answers

1
votes

You can't replace the identity reference on an existing ACE, you need to replace the entire ACE with a new one.

$acl = Get-Acl -Path 'C:\Temp'

$ace = $acl.Access | Where-Object { $_.IdentityReference -eq 'BUILTIN\Users' }
$newAce = New-Object System.Security.AccessControl.FileSystemAccessRule (
    'new\name',
    $ace.FileSystemRights,
    $ace.InheritanceFlags,
    $ace.PropagationFlags,
    $ace.AccessControlType
)
$acl.RemoveAccessRule($ace)
$acl.AddAccessRule($newAce)

Set-Acl -Path 'C:\Temp' -AclObject $acl