Mark
Mark

Reputation:

How to kill specific process running under specific user account

How to kill specific process running under specific user account. using C#?

Thanks,

Upvotes: 2

Views: 4153

Answers (2)

Bill
Bill

Reputation: 2451

In order to get the username, you have to grab the security context of the process from the Win32 API.

Call the OpenProcessToken() function via P/Invoke using the process handle found in the .Net Process class from the code you already have above. You will obtain a structure that contains a SID for the owner of the process. Be prepared for errors such as Access Denied, since you may not have access rights to obtain this information for all processes, such as those that are not yours. From there, you have to convert the SID to a name. There are a few ways to do this, but LookupAccountSid() function (again, via P/Invoke) will get the username for you.

In framework 2.0, a bunch of stuff was added to help with dealing with security descriptors (System.Security.AccessControl namespace), however, I don't see anything that will help you in dealing with the P/Invoke complexities there.

See pinvoke.net for information on using the Win32 API from C#.

Upvotes: 0

Thomas Levesque
Thomas Levesque

Reputation: 292345

var processes = from p in Process.GetProcessesByName(nameOfTheProcess)
                where p.StartInfo.UserName == nameOfTheUser
                select p;

foreach(Process p in processes) p.Kill();

EDIT: as Fredrik pointed out, the UserName property is not set for processes obtained by GetProcesses. Here's a modified version that uses WMI to get the username (GetProcessOwner method found here) :

static void KillProcessByNameAndUserName(string processName, string userName)
{
    var processes = from p in Process.GetProcessesByName(processName)
                    where GetProcessOwner(p.Id) == userName
                    select p;

    foreach(Process p in processes) p.Kill();
}

static string GetProcessOwner(int processId)
{

    string query = “Select * From Win32_Process Where ProcessID = “ + processId;
    ManagementObjectSearcher searcher = new ManagementObjectSearcher(query);
    ManagementObjectCollection processList = searcher.Get();

    foreach (ManagementObject obj in processList)
    {
        string[] argList = new string[] { string.Empty };
        int returnVal = Convert.ToInt32(obj.InvokeMethod(“GetOwner”, argList));
        if (returnVal == 0)
            return argList[0];
    }

    return “NO OWNER”;

}

Upvotes: 5

Related Questions