We'll begin by getting the shell up and running so that we can start to put MSH through its paces. This section will focus on the time-honored task of inspecting the process list to see what's currently running on a system. There are some MSH features that may not be immediately familiar to those in other command shells—in particular, the strict command syntax—but we'll also look at a few of the obvious differences and see how they're really nothing to fear.
These basics show you how to start using the shell, and they provide the foundation for the rest of the examples we'll cover.
Most MSH commands are identified by a pair of words, one verb and one noun, separated by a hyphen. The verb describes the action (such as get or set) while the noun represents the target of the action in singular form (such as process or location). There is a standard list of verbs that covers the majority of tasks (including
remove). Although the number of these verbs may seem excessively large, consistent naming does make learning and using MSH easier in the long run.
Microsoft Command Shell Copyright (C) 2005 Microsoft Corporation. All rights reserved. MSH D:\MshScripts>
MSH is waiting for its first command. The MSH shell is in interactive mode with the current directory set to D:\MshScripts. We'll look at the different modes of operation in more detail later on. For now, the shell will execute commands line-by-line as they are entered.
get-processHandles NPM(K) PM(K) WS(K) VS(M) CPU(s) Id ProcessName ------- ------ ----- ----- ----- ------ -- ----------- 119 6 996 3336 31 0.22 1844 alg 602 12 10408 15816 64 18.96 1656 CcmExec 409 5 1648 3364 22 16.23 464 csrss 273 11 7376 12696 55 340.16 212 explorer 0 0 0 16 0 0 Idle 146 11 3532 7284 61 2.90 1264 InoRpc 110 5 11136 12404 60 9.33 1316 InoRT 107 5 2820 6244 53 4.22 1332 InoTask 405 10 4404 528 41 11.66 544 lsass 290 12 33948 32208 175 14.90 3088 msh ...
You can use a command line or argument to reduce the number of processes
get-process returns. Given something to match against,
get-process will compare the process name of each process, only allowing matching ones to be displayed. Let's take a look at all processes beginning with the letter "r" or "s":
get-process [rs]*Handles NPM(K) PM(K) WS(K) VS(M) CPU(s) Id ProcessName ------- ------ ----- ----- ----- ------ -- ----------- 96 4 1772 4972 43 54.60 1200 Realmon 260 6 1260 2840 24 13.38 532 services 21 1 168 368 4 0.57 308 smss 96 4 2428 3208 26 0.32 1088 spoolsv 207 6 2056 4312 35 4.41 940 svchost 251 13 1472 3968 34 8.20 756 svchost 1665 50 14648 22040 98 44.27 824 svchost 183 5 2280 4440 57 0.64 720 svchost 85 4 1036 2968 28 2.44 896 svchost 284 0 0 216 2 64.20 4 System
get-process will accept another parameter called
Exclude. This is used to filter certain processes from the results list. This time, we'll find all processes starting with the letter "w," except those that start with the three letters "win":
get-process w* -Exclude win*Handles NPM(K) PM(K) WS(K) VS(M) CPU(s) Id ProcessName ------- ------ ----- ----- ----- ------ -- ----------- 125 4 1300 3624 23 0.82 320 wmiprvse 137 4 3388 4156 25 1.36 1920 wmiprvse 221 7 6352 7868 65 2.60 1708 wuauclt
Cmdlets (pronounced "command-lets") are one of the fundamental parts of the functionality of MSH. Cmdlets range from the very simple to the very complex, but all are designed to do a single task and to do it well. MSH provides a framework within which these cmdlets can be run, effectively providing the plumbing for passing information between different pipeline elements. Cmdlets are not designed to be monolithic giants that completely solve any given problem; instead, their power derives from composition—their use in concert with other cmdlets. A well-designed cmdlet focuses on doing one job in a clear and predictable manner. We'll be talking a lot more about cmdlets and composition going forward.
A cmdlet is implemented as a managed class (built on the .NET Framework) that implements a well-defined set of methods to process data.
Although the verb-noun syntax may seem slightly foreign or even cumbersome, there are rewards in its consistency. Because we already know how to list active processes with the
get-process command, it's only a small jump to manipulate processes by using other verbs, for example
new-process. The symmetry in cmdlet naming helps to group commands based on either task or target, which makes it easy to use other related cmdlets by picking one of the set of common verbs. It's worth noting that the verb-noun requirement applies only to cmdlets; as we meet other MSH concepts such as functions, scripts, and aliases, we'll see that they are not subject to the same strict syntax.
If you're concerned that
get-process requires more keystrokes than
tasklist (its nearest cmd.exe equivalent), or that
get-childitem is significantly longer than
dir, rest assured that there are shortcuts in the form of command aliases
. We look into aliases in more detail in Chapter 2. For now, we'll continue to use the long form as it generally improves the readability of scripts.
In itself, generating a process list isn't rocket science.
tlist.exe, part of the Windows Resource Kit, has been offering this functionality for years. However, the MSH version is going to enable us to do a lot more. In the next few examples, we'll see how this cmdlet can be combined with others to offer some flexible process list reporting.
We'll look at wildcards
in Chapter 4, but it is worth mentioning now that the
win* style syntax used here isn't restricted to the
get-process cmdlet. In fact, it is actually MSH that interprets the command-line parameters (not the cmdlets), and the shell extends this kind of wildcard support and parsing consistency throughout.
get-help get-processNAME get-process SYNOPSIS Gets a list of processes on a machine. DETAILED DESCRIPTION The get-process Cmdlet gets a list of the process running on a machine and displays it to the console along with the process properties. This command also supports the ubiquitous parameters: -Debug (-db), -ErrorAction (-ea), -ErrorVariable (-ev) -OutBuffer (-ob), -OutVariable (-ov), and -Verbose (-vb) SYNTAX get-process [-ProcessName] [processName] [-Id processId] ...
get-help without any parameters generates an overview of the available help topics. Specific help information is available by supplying a topic or cmdlet name.
get-command cmdlet provides a mechanism for listing all cmdlets registered with the shell, including their signature, parameter list, and description.
Since we're on the quick tour, let's take a look at one of the new aspects of MSH: the ability to treat arbitrary data stores like regular filesystems by way of a provider model.