Get PowerShell Version with WMI

With the release of PowerShell 4.0, it is possible you might end up with a mix of systems in your environment. I know I do because I do a lot of writing, testing and development that requires multiple versions in my test network. Recently I was doing some Group Policy work when I thought about WMI filters. A WMI filter is a way to limit Group Policy to machines that meet certain criteria. I thought it would be useful to have a WMI filter that could determine if the computer was running PowerShell 3 or 4. Why? Well one reason would be so that v4 machines would update help from a local v4 source and likewise for v3. So I started looking a developing a WMI query.

That led to the development of this:

This function uses WMI to retrieve the instance of the CIM_DATAFILE class for PowerShell.exe. I have found when querying for this class to be as specific in your query as you can. This runs pretty quickly and returns some useful information. I can even run it for a group of computers.

Which gives me this:

The first two machines are running PowerShell 2.0, the next 2 v3 and the last 2 v4. Now that I know this works, I can create a WMI filter with a query like this:

This should filter only for computers running PowerShell 3.0.

I wrote this function thinking I would add support for alternate credentials. But if you don’t need it, you can also get the same information using the [WMI] type accelerator.

I needed to test and develop a SELECT query which is why I ended up with the function I did. The date information is extra and if you use Get-CIMInstance, the dates are converted for you.

Yes, I know you can get this information with Test-WSMan as well and that is certainly a much easier way. Although if by chance you still have PowerShell 1.0 in use, I don’t think that will work. Anyway, there you have it. A quick way using WMI to find out the PowerShell version and a query you can use to build a WMI filter for Group Policy.


UPDATE 11/14
I don’t know what I was thinking with my original query. It was much more complicated than it needed to be. I’ve updated my code samples with a better filter. Remember when using \ in any paths, it needs to be escaped which is why you see the name as you do.

Set GPO Status with PowerShell

talkbubbleLast week I dropped in on a class Jeremy Moskowitz was teaching on Group Policy to talk a little PowerShell. I was demonstrating the Get-GPO cmdlet and talking about the object you get back and how you can use it to filter and create reports. One of the attendees asked about changing the status.

What he was referring to was the status that indicates if all settings are disabled, or if the user/computer side of a GPO is disabled. Here’s an example of what you see using Get-GPO from the GroupPolicy module.

The setting in question is GpoStatus which as you can see here indicates that all settings are disabled on this particular GPO. In the graphical Group Policy Management console, you can manually adjust this setting. But in Group Policy there are no cmdlets for setting any values. I don’t know why I didn’t have an answer that night but it turns out to be surprisingly simple yet unexpected.

It turns out you can assign a new value directly on the object.

Valid values are AllSettingsEnabled, AllSettingsDisabled, UserSettingsDisabled and ComputerSettingsDisabled. The surprising part is that the change is immediate and written back to Active Directory. There’s no need to “set” or “put” anything. I can verify by retrieving the GPO again.

This makes for some convenient one-liners:

For quick and dirty work, that is pretty handy. But you know me, I like reusable tools. There are a few drawbacks to this. First, you have to remember the valid settings. There’s also no way to double-check you are changing the right GPO, ie no -WhatIf. So I put together a function called Set-GPOStatus.

The function takes either a GPO name or you can pipe a GPO into it. I then turned all of the settings into switches that are (I hope) a little more user-friendly. This command also supports ShouldProcess which gives me -WhatIf.

Now I can use the command like this.

The other key element in the function is the use of multiple parameter sets. I wanted each status option to be its own parameter set. Yet some parameters like GPO name, domain and server apply to all of them. In those situations all you need to do is specify all of the parameter sets you want a parameter to belong to. But I need to point out that in this particular function I’m bending the rules a little. Normally, if you don’t specify a parameter set then the parameter automatically belongs to all parameter sets. That generally works out because you can define a default parameter set name in the cmdletbinding tag. However I’m not doing that here because I didn’t want to make an assumption about what setting to use. So I explicitly define the parameter sets and have some error handling in a Switch statement to test the parameter set name and bail out if no setting switches were used. So don’t take this as a perfect example, but know that if you have a parameter that you want to belong to more than one parameter set, simply add the set name.

Even though it isn’t difficult in an interactive console to change the GPO status property, by creating a tool I’ve introduced some new functionality and now have something I can incorporate into any of my Group Policy management scripts.

Download Set-GPOStatus and let me know what you think.

TechEd 2012 Slides and Demos

At TechEd North America in Orlando, I presented a great session on Group Policy and Windows PowerShell. The session was entitled Group Policy Reporting and Analysis with Windows PowerShell. I co-presented with Group Policy MVP and guru Jeremy Moskowitz. Jeremy played the part of the “pointy-haired” boss, posing questions about Group Policy such as finding out what policies are being used, what policies have empty nodes and where are there empty registry settings?

Jeremy explained why this should matter to you, and then Prof. PowerShell, demonstrated how to solve the problem with Windows PowerShell and the Group Policy module.

It was a lot of fun and we received some excellent feedback. The session was even streamed live and recorded so if you missed it, you can still check it out.

Or visit if you want to download the video for later.

You can download a pdf of the slide deck. I also have a zip file with my PowerShell demo scripts. Some of these files are meant to be run one command at a time so look at the files before you do anything.

If you need some help with Group Policy, I encourage you to visit and have Jeremy help you out. And naturally, if you are looking for PowerShell help or training, I hope you’ll let me know.


Group Policy Analysis and Reporting with PowerShell

In a few weeks I’ll be presenting at TechEd North America. I hope you already made plans to go because it is sold-out. On Wednesday, June 13th at 8:30AM I’ll be talking about Group Policy and PowerShell; specifically Group Policy Analysis and Reporting with PowerShell. This should be a lot of fun. I’m doing the session with Group Policy MVP and propeller head Jeremy Moskowitz. We’re going to cover some common GPO challenges, such as finding unused policies. Jeremy will explain why this matters from a Group Policy perspective and then I’ll explain how to solve the problem with PowerShell. I think we’re going to have a lot of fun with this and I’ve been told it is going to be live streamed.

There will be plenty of demos, and most of them are only a few interactive commands so this isn’t necessarily rocket science. I hope you’ll find time to squeeze this into your TechEd schedule. After the session, you’ll also be able to find me at the ScriptingGuys booth.