Skip to content

Instantly share code, notes, and snippets.

@tijme
Created May 26, 2021 20:12
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save tijme/123a403be78f08d7d6c40158d081d1c5 to your computer and use it in GitHub Desktop.
Save tijme/123a403be78f08d7d6c40158d081d1c5 to your computer and use it in GitHub Desktop.
Get the effective network share access for a specific domain user. Identify which ACL entry/rule matches for the given or current user.
Function Get-EffectiveNetworkShareAccess {
<#
.SYNOPSIS
This script will identify why a certain user has access to a network share.
.DESCRIPTION
This script will identify why a certain user has access to a network share.
.NOTES
Name: Get-EffectiveNetworkShareAccess
Author: Tijme Gommers
Version: 1.0
DateCreated: 05/26/2021
.PARAMETER Share
The UNC path to the network share
.PARAMETER Account
The Account to check the effective access for
.EXAMPLE
Get-EffectiveNetworkShareAccess \\contoso.com\SYSVOL
.EXAMPLE
Get-EffectiveNetworkShareAccess -Share \\contoso.com\SYSVOL -Account tijme
.LINK
https://twitter.com/tijme
#>
[CmdletBinding()]
Param(
[Parameter(
Mandatory = $True,
HelpMessage = "Specify the UNC path to the network share",
ValueFromPipeline = $True,
ValueFromPipelineByPropertyName = $True,
Position = 0
)] [ValidateNotNullOrEmpty()] [string] $Share,
[Parameter(
Mandatory = $False,
HelpMessage = "Specify the Account to check the access for",
Position = 1
)] [ValidateNotNullOrEmpty()] [string] $Account
)
Begin {
if ($PSBoundParameters.ContainsKey('Account') -eq $False) {
$AccountObject = Get-ADUser $env:UserName
$DomainObject = Get-ADDomain -Current LoggedOnUser
} else {
$AccountObject = Get-ADUser $Account
$DomainObject = Get-ADDomain -Current LoggedOnUser
}
$Account = $AccountObject.SamAccountName
$Domain = $DomainObject.Name
$ShareOwner = Get-ACL $Share | TG-GetUserFromOwner
$ShareACL = Get-ACL $Share | ForEach-Object { $_.Access }
Write-Host "[-] Checking effective ACL's for account '$Account' on share '$Share'."
}
Process {
foreach ($ShareAC in $ShareACL) {
if ($ShareAC.IdentityReference -like "NT AUTHORITY\SYSTEM") { continue }
if ($ShareAC.IdentityReference -like "BUILTIN\Administrators") { continue }
if ($ShareAC.IdentityReference -like "CREATOR OWNER") {
if ($ShareOwner -eq $Account) {
Write-Host -ForegroundColor Green "[+] The user '$Account' is the owner of the share."
Write-Host -ForegroundColor Green "[+] The owner has the ACL: $($ShareAC.FileSystemRights)"
}
continue
}
if ($ShareAC.IdentityReference -like "Everyone") {
Write-Host -ForegroundColor Green "[+] The user '$($Account)' is member of the group 'Everyone'."
Write-Host -ForegroundColor Green "[+] The group 'Everyone' has the ACL: $($ShareAC.FileSystemRights)."
continue
}
if ($ShareAC.IdentityReference -like "NT AUTHORITY\Authenticated Users") {
Write-Host -ForegroundColor Green "[+] The user '$($Account)' is member of the group 'NT AUTHORITY\Authenticated Users'."
Write-Host -ForegroundColor Green "[+] The group 'NT AUTHORITY\Authenticated Users' has the ACL: $($ShareAC.FileSystemRights)."
continue
}
if ($ShareAC.IdentityReference -like "BUILTIN\Users") {
Write-Host -ForegroundColor Green "[+] The user '$($Account)' is member of the group 'BUILTIN\Users'."
Write-Host -ForegroundColor Green "[+] The group 'BUILTIN\Users' has the ACL: $($ShareAC.FileSystemRights)."
continue
}
$ACAccountWithDomain = $ShareAC.IdentityReference.ToString().ToLower()
$ACAccountWithoutDomain = $ACAccountWithDomain.replace("$($DomainObject.Name.ToLower())\", "")
if ($ACAccountWithDomain.StartsWith($DomainObject.Name.ToLower())) {
if ($ACAccountWithoutDomain -like $AccountObject.SamAccountName) {
try {
$retrievedUser = Get-ADUser $ACAccountWithoutDomain
Write-Host -ForegroundColor Green "[+] $Account has an account specific ACL: $($ShareAC.FileSystemRights)"
} catch {
continue
}
}
try {
$retrievedGroup = Get-ADGroup $ACAccountWithoutDomain -Properties Members
TG-FindAccountInGroupRecursively -Account $AccountObject -Root $retrievedGroup -Level 0 -AC $ShareAC
} catch {
continue
}
}
}
}
End {
Write-Host "[-] Done!"
}
}
Function TG-GetUserFromOwner {
<#
.SYNOPSIS
This script tries to find an ADUser based on the Owner attribute of the given ACL.
.DESCRIPTION
This script tries to find an ADUser based on the Owner attribute of the given ACL.
.NOTES
Name: TG-GetUserFromOwner
Author: Tijme Gommers (@tijme)
Version: 1.0
DateCreated: 05/26/2021
.PARAMETER Owner
The Owner string of a Get-ACL (ACL) object
.EXAMPLE
TG-GetUserFromOwner contoso.com\tijme
.LINK
https://twitter.com/tijme
#>
[CmdletBinding()]
Param(
[Parameter(
Mandatory = $True,
HelpMessage = "Specify the Owner to get the ADUser object for",
ValueFromPipeline = $True,
ValueFromPipelineByPropertyName = $True,
Position = 0
)] [ValidateNotNullOrEmpty()] [string] $Owner
)
Process {
try {
$Owner = $Owner.Split("\")
$DomainName = $Owner[0]
$Account = $Owner[1]
} catch {
$DomainController = Get-ADDomainController -DomainName $DomainName -Discover -ErrorAction Stop
Get-ADUser -Identity $Account -Server $DomainController -ErrorAction Stop
}
}
}
Function TG-FindAccountInGroupRecursively {
<#
.SYNOPSIS
This script identifies if the given account is (recursively) part of the given group.
.DESCRIPTION
This script identifies if the given account is (recursively) part of the given group.
.NOTES
Name: TG-FindAccountInGroupRecursively
Author: Tijme Gommers (@tijme)
Version: 1.0
DateCreated: 05/26/2021
.PARAMETER Account
The ADUser to identify in the given group
.PARAMETER Root
The ADGroup to search in
.PARAMETER Level
The current level of recursion (root is 0)
.PARAMETER AC
The Access Control List configured on the root of the current group
.EXAMPLE
TG-FindAccountInGroupRecursively -Account $ADUser -Root $ADGroup -Level 0 -AC ACLObject
.LINK
https://twitter.com/tijme
#>
[CmdletBinding()]
Param(
[Parameter(
Mandatory = $True,
HelpMessage = "The ADUser to identify in the given group",
Position = 0
)] [ValidateNotNullOrEmpty()] $Account,
[Parameter(
Mandatory = $True,
HelpMessage = "The ADGroup to search in",
Position = 1
)] [ValidateNotNullOrEmpty()] $Root,
[Parameter(
Mandatory = $True,
HelpMessage = "The current level of recursion",
Position = 2
)] [ValidateNotNullOrEmpty()] [int] $Level,
[Parameter(
Mandatory = $True,
HelpMessage = "The Access Control List configured for the root of the current group",
Position = 3
)] [ValidateNotNullOrEmpty()] $AC
)
if ($Level -eq 0) {
$Indent = ""
Write-Host "[-] Parsing domain group '$($Root.Name)'..."
} else {
$Indent = " " * ($Level * 4)
Write-Host "[-] $Indent Parsing member/sub group '$($Root.Name)'..."
}
if ($Root.Name -like "Domain Users") {
Write-Host -ForegroundColor Green "[+] $Indent $Indent The user '$($Account.SamAccountName)' is member of the group '$($Root.Name)'."
Write-Host -ForegroundColor Green "[+] $Indent $Indent The group '$($Root.Name)' has the ACL: $($AC.FileSystemRights)."
return
}
$usersInGroup = Get-ADGroupMember $Root | select SamAccountName
foreach ($user in $usersInGroup) {
if ($user.SamAccountName -like $Account.Name.ToLower()) {
Write-Host -ForegroundColor Green "[+] $Indent $Indent The user '$($Account.SamAccountName)' is member of the group '$($Root.Name)'."
Write-Host -ForegroundColor Green "[+] $Indent $Indent The group '$($Root.Name)' has the ACL: $($AC.FileSystemRights)."
break
}
}
foreach ($member in $Root.Members) {
try {
$group = Get-ADGroup $member
TG-FindAccountInGroupRecursively -Account $Account -Root $group -Level $($Level+1) -AC $AC
} catch {
continue
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment