As easy as Get-Service is to use in PowerShell, it has one limitation for IT Pros: it can't show you what account the service is running under. In old school terms, "What is the service account?" Fortunately you can get that information using WMI. Here's a query you can use that takes advantage of some slightly advanced WQL query syntax.
ManageEngine ADManager Plus - Download Free Trial
Exclusive offer on ADManager Plus for US and UK regions. Claim now!
Since Windows XP, WMI has supported the LIKE operator in a query. This makes it easier to do a wildcard search in WMI.
[cc lang="PowerShell"]
PS S:\> Get-WmiObject WIn32_process -filter "Name Like 'chr%'" | Select ProcessID,Name,WorkingSetSize,PageFaults,handles
ProcessID : 6912
Name : chrome.exe
WorkingSetSize : 140304384
PageFaults : 559235
Handles : 1436
ProcessID : 7352
Name : chrome.exe
WorkingSetSize : 61210624
PageFaults : 113482
Handles : 144
...
[/cc]
When using the LIKE operator, use the % as the wild card. But there are some advanced ways to use LIKE if you check out the MSDN documentation. The most useful information is how to achieve a "not like" filter. Ideally, I want a WMI query to filter out all the service accounts that start with NT Authority as well as LocalSystem. This should leave me with "regular" user accounts.So here's a simple one liner to do just that:
[cc lang="PowerShell"]
PS C:\> get-wmiobject win32_service -filter "(StartName Like '[^NT Authority]%') AND (StartName <> 'localsystem')" | Select name,Startname
name Startname
---- ---------
MSSQL$SQLEXPRESS .\sql
Veeam Backup and FastSCP Service .\Jeff
[/cc]
These accounts are local to the machine.
Remember that a WMI query uses legacy operators, not the PowerShell ones. And having WMI do the filtering is more efficient than bringing everything back to your computer and piping to Where-Object. You would really notice this when you start querying multiple remote machines. Use the SystemName property here to include the computer name.
But now you can run a simple expression to scan computers and find where non system accounts are being used. This will only work for computers running Windows XP and later.
Thanks again.
Hi Jeff, thank you for that information.
Using ! instead of ^ will get you the system account as below
get-wmiobject win32_service -filter “(StartName Like ‘[!NT Authority]%’) AND (StartName ‘localsystem’)” | Select name,Startname
Q. how could you search for more that one service account name at the same time? So if say you wanted to search for five service account names you wanted to chreck on multiple machines could this be done?
Get the command to work for one machine:
get-wmiobject win32_service -filter “Startname=’A’ OR Startname=’B’ OR Startame=’C'”
Of if you need to, use Like. Just add as many ORs as you need. If you can get by with wildcards, I’d go that route. Then you can run the query against multiple machines a number of ways. You could pipe a list of names to a foreach object and use the -computername parameter. You could use Invoke-Command and remoting. You could use Start-Job. Lots of options. Depends on the number of computers, potential error handling you might need, what you want to do with results. But all very doable without a lot of effort.
Thanks for that. I’ll try
$servers = get-content “c:\servers.txt”
foreach ($server in $servers)
{
Get-WMIObject -ComputerName $Server Win32_Service -filter “Startname
A=’123′ Or ‘Startname
B=456’ AND (StartName ‘localsystem’)” | Select name,Startname
}
Because you are querying remote computers, you might also want to select Systemname so you can see what service is on what server.