Skip to main content

Enumerate all Users that are assigned User Rights with PowerShell

One of the security questions that came up in my last PowerShell class was who has the User Rights to shut down a server. I went with this and created a script that searches all the User Rights that have a user or group assigned to them.  It performs a recursive search through all groups and provides you with a list of users who have that certain right.  Below is a screen shot part of the output.

image

Here is the PowerShell script.

<#
===========================================================
Script Name:EnumerateUserRights.ps1
Author: Jason A. Yoder, MCT

Website: www.MCTExpert.com
Blog site: www.MCTExpert.Blogspot.com
-----------------------------------------------------------
Script Purpose:
Enumerates all the user accounts that are listed as having
a user right.  This script will do a recursive search
through all nested groups and will also report on user
accounts that have been directly assigned a User Right
outside of an Active Directory Group.

-----------------------------------------------------------
Requirements:
This script has been tested on a Domain Controller only.
The User rights were programed using the Default Domain
Controller Policy.

-----------------------------------------------------------
Revision History:
Version 2.0:
Now searches through all user rights.


Version 1.0:
Search only for Users who could shut down the
Server.

-----------------------------------------------------------
Known Issues:
None.

-----------------------------------------------------------

Variables:

$PolicyData : Holds the object of the user right for
               ShutDown server.

$UserList : Holds the names of all of the users found
            that have the User Right.
           
$UserObject : Holds the first name of the user. It is used
              to determine if a user account was directly
              assigned to the user right, as opposed to
              being assigned by a group.

$RightsAry : Holds the raw list of user rights extracted
           : from the server.


===========================================================
#>

# =========================================================
# Functions:

# =========================================================
# Function: Get_Rights_Name:
# ---------------------------------------------------------
# This function will create a User friendly version of
# the User Right name that was extracted with WMI.
Function Get_Rights_Names ($Name)
{

    # Only process the data if it is of string
    # data type.
    If($Name -is [String])
    {
        # Remove the surrounding double quotes and
        # the leading "Se".
        $Name = $Name.replace("`"Se","")
        $Name = $Name.replace("`"","")

        # Save an upper case version of the name in
        # $Data.
        $Data = $Name.ToUpper()

        # Make sure the variable $Final is empty.
        $Final = ""

        # Loop through the User Right name.
        # Identify the letters that are upper case
        # my using a case sensitive comparison
        # against both the original name, and
        # the upper case version.
        $i=0
        $i = While ($i -lt $Data.Length)
        {

            # When an upper case letter is found,
            # Place a space in front of it.
            If ($Data[$i] -ceq $Name[$i])
                {
                $Final += " "
                $Final += $Data[$i]

                }
           
            # Write all lower case letters without
            # making any changes.
            Else
                {
                    $Final += $Name[$i]
   
                }
   

            $i++
        }
    }
    # Trim any leading or trailing spaces from the
    # data.  Allow any errors here to pass without.
    # displaying error data.
    $ErrorActionPreference = 'SilentlyContinue'
    $Final = $Final.Trim()
    $ErrorActionPreference = 'Continue'

    # Write the header for the User Rights name.
    Write-Host "-- $Final ----------" `
        -ForegroundColor Yellow -BackgroundColor DarkGray

}



# =========================================================
# == Function: Enumerate_User_Rights                     ==
# ---------------------------------------------------------
# The below function will enumerate the User Rights that
# currently contain values.  It will return the values
# back to the script.

Function Enumerate_User_Rights
{
    # Get a string of all the __RELPATH properties that
    # contain the string "UserRight=".
    $RightsList = Get-WmiObject `
        -NameSpace Root\RSOP\Computer `
        -Class RSOP_PolicySetting | `
        Where {$_.PATH -match 'UserRight='}
   
    # Ensure this array has been cleared.
    $RightsArray = $NULL
   
    # Look through each object and select the string of
    # between the double quotes.  Add this data to
    # $RightsArray.  This process uses Regular
    # Expressions.  Type "Help About_Regular_Expressions"
    # for more information.
    foreach ($Rights in $RightsList)
    {
        $MatchString = "`"\w*`""
        $Rights.__RELPATH -match $MatchString
        $RightsArray += $Matches.Values
    }

    Return $RightsArray # Return the processed data.
}


# =========================================================
# Function: Enumerate_Users
# ---------------------------------------------------------
# Uses a WMI Query to list all the users and groups
# assigned to the User Right "Shutdown Server."
Function Enumerate_Users($RightsList)
{

# Feed the list of user rights.
ForEach ($RL in $RightsList)
{
    $UserList = $NULL
    If($RL -is [String])
    {
      Get_Rights_Names $RL
       
   
        # Use WMI to extract the object for the user right
        # of Shutdown Server.
        $PolicyData = Get-WmiObject `
            -NameSpace Root\RSOP\Computer `
            -Class RSOP_PolicySetting |
            Where-Object {$_.__RELPATH -like "*$RL*"}

   
        # Loop through each object in the "AccountList"
        # property and recursively get the members of that
        # group.
        For ($i = 0 
             $i -le $PolicyData.AccountList.count-1
             $i++)
             {

                # This first error handling will extract
                # the names of each User in each group
                # and nested group that have the right
                # to shutdown the server.
                Try {
                    $UserList += Get-ADGroupMember `
                        $PolicyData.AccountList[$i] `
                        -Recursive -ErrorAction Stop
       
                    }
                Catch{
                    # In the event that a user account is
                    # assigned directed to the user
                    # right as oppose through a group, this
                    # 'Catch' will allow the script to
                    # continue to the next 'Try'.
                    }



                # This error catch will extract a username
                # that was assigned directly to the User
                # Right.
                Try{
                    # $UserObject will use Regular
                    # Expressions to remove the Domain name
                    # and backslash and return the given 
                    # name of the user.
                    $UserObject = $PolicyData.AccountList[$i] `
                        -replace "\w*\W"
      
      
                    # Get the full user name and add it to
                    # the $userList array.
                    $UserList += Get-ADUser -filter `
                        'GivenName -like $UserObject'
                    }
                Catch{
                        # This will let the error handling
                        # continue if a group is passed to
                        # it instead of a user.
                }
            }
    }

    # Write the names of the users who have the User
    # Right that is being processed.
    $UserList | Sort-Object -Unique | format-Table Name
    }
}




# == End of Functions : ===================================

# =========================================================
# Main Code:

# Announce the start of the script.
Write-Host "Script EnumerateUserRights.ps1 has started" `
    -ForegroundColor Green -BackgroundColor DarkBlue

# Import the Active Director cmdlets needed
#  for this script.
Import-Module ActiveDirectory -Cmdlet Get-ADGroupMember,
Get-ADUser

Clear-Host  # Clear the display

# Enumerate the User Rights that have assigned users
# and groups.
$RightsAry = Enumerate_User_rights

# Get the list of users who are assigned User Rights.
Enumerate_Users $RightsAry


Try{
    # Clears the data from memory.
    Clear-Variable -name UserList -ErrorAction Stop  
   }
   
Catch{<# Do nothing, this is a none critical error.#>}
   
# Clears the data from memory.
Clear-Variable -name RightsAry
# Announce the end of the script.
Write-Host "Script EnumerateUserRights.ps1 has completed" `
    -ForegroundColor Green -BackgroundColor DarkBlue

# == End of Main Code =====================================

Comments

Popular posts from this blog

How to list all the AD LDS instances on a server

AD LDS allows you to provide directory services to applications that are free of the confines of Active Directory.  To list all the AD LDS instances on a server, follow this procedure: Log into the server in question Open a command prompt. Type dsdbutil and press Enter Type List Instances and press Enter . You will receive a list of the instance name, both the LDAP and SSL port numbers, the location of the database, and its status.

How to run GPResult on a remote client with PowerShell

In the past, to run the GPResult command, you would need to either physically visit this client, have the user do it, or use and RDP connection.  In all cases, this will disrupt the user.  First, you need PowerShell remoting enabled on the target machine.  You can do this via Group Policy . Open PowerShell and type this command. Invoke-Command –ScriptBlock {GPResult /r} –ComputerName <ComputerName> Replace <ComputerName> with the name of the target.  Remember, the target needs to be online and accessible to you.

Error icon when creating a GPO Preference drive map

You may not have an error at all.  Take a look at the drive mapping below. The red triangle is what threw us off.  It is not an error.  It is simply a color representation of the Replace option of the Action field in the properties of the drive mappings. Create action This give you a green triangle. The Create action creates a new mapped drive for users. Replace Action The Replace action gives you a red triangle.  This action will delete and recreate mapped drives for users. The net result of the Replace action is to overwrite all existing settings associated with the mapped drive. If the drive mapping does not exist, then the Replace action creates a new drive mapping. Update Action The Update action will have a yellow triangle. Update will modify settings of an existing mapped drive for users. This action differs from Replace in that it only updates settings defined within the preference item. All other settings remain as configured on the ma...