This little gem took me hours of searching to find the correct information and then the correct method to retrieve what IIS app pool is serviced by a specific w3wp.exe process. I looked through the code in the iisapp.vbs tool but it was not clear how the method worked that returned the command line data.

In the end I discovered that when a w3wp.exe process is started it is passed all the parameters it needs on the command line, the App Pool is designated with the -ap flag, the timeout with the -t flag etc. The trick is getting the command line was getting the correct command line back using the right system calls!

Initially I spent some time trying to use the following method and all possible properties and variants to no avail:

Process[] localAll = Process.GetProcesses();
ProcessStartInfo psinfo = ps.StartInfo;
Console.WriteLine("CMD Line :" + ps.StartInfo.Arguments);

The Missing Link

Finally after some experimentation I discovered that the C# ManagementClass object has all the data you need, so this example does the trick:

       public static string ListAllProcesses()
       {
            StringBuilder sb = new StringBuilder();
            // list out all processes and write them into a stringbuilder
            ManagementClass MgmtClass = new ManagementClass("Win32_Process");
            foreach (ManagementObject mo in MgmtClass.GetInstances())
            {
                if (mo["Name"].ToString() == "w3wp.exe")
                {
                    sb.Append("Name: " + mo["Name"] + "\n");
                    sb.Append("ID: " + mo["ProcessId"] + "\n");
                    sb.Append("CMDLine: " + mo["CommandLine"] + Environment.NewLine);
                 }
            }
            return sb.ToString();
        }

Sample Output

If there are indeed w3wp.exe processes running then you will get some output, if there are none running (typically when no requests have been made within the timeout period) then you will get no output.

Sample Output

Name: w3wp.exe
ID: 5952
CMDLine: c:\windows\system32\inetsrv\w3wp.exe -a \\.\pipe\iisipm71887c78-a556-472b-9508-ee722efe0a6f -t 20 -ap “TestAppPool”

Fully Working Example

The following code is a fully working example that outputs the list of Application Pools and then any w3wp.exe processes that are using them.

You will need to add a references to:

  • System.DirectoryServices
  • System.Management
using System;
using System.Text;
using System.DirectoryServices;
using System.Management;


namespace GetAppPool
{
    class Program
    {
        static void Main(string[] args)
        {
            Console.WriteLine("Application Pools");
            Console.WriteLine("=================");

            DirectoryEntry W3SVC = new DirectoryEntry("IIS://localhost/w3svc", "", "");
            foreach (DirectoryEntry Site in W3SVC.Children)
            {
                if (Site.SchemaClassName == "IIsApplicationPools")
                {
                    foreach (DirectoryEntry child in Site.Children)
                    {
                        Console.WriteLine(child.Name+" | "+child.Path);
                    }
                }
            }
            Console.WriteLine("\n\nProcesses\n=============\n");

            StringBuilder sb = new StringBuilder();
            // list out all processes and write them into a stringbuilder
            ManagementClass MgmtClass = new ManagementClass("Win32_Process");
            foreach (ManagementObject mo in MgmtClass.GetInstances())
            {
                if (mo["Name"].ToString() == "w3wp.exe")
                {
                    sb.Append("Name: " + mo["Name"] + "\n");
                    sb.Append("ID: " + mo["ProcessId"] + "\n");
                    sb.Append("CMDLine: " + mo["CommandLine"] + Environment.NewLine);
                    //                foreach (PropertyData prop in mo.Properties)
                    //              {
                    //                Console.WriteLine("{0}: {1}", prop.Name, prop.Value);
                    //          }
                }
            }
            Console.WriteLine(sb.ToString());
        }
    }
}

Enjoy!! 🙂

Advertisements