2009-06-18 6 views

답변

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

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

편집 : 프레드릭가 지적했듯이, 사용자 이름 속성이 GetProcesses 얻을 프로세스 설정되어 있지 않습니다. 여기 (GetProcessOwner 방법은 here을 발견) 사용자 이름을 사용하려면 WMI를 사용하는 수정 된 버전입니다 : 사용자 이름을 얻기 위하여

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”; 

} 
+1

음 ... 그 코드가 컴파일됩니까? Linq 쿼리에서 select가 누락 된 것처럼 보입니다. 참고 사항. 비슷한 접근 방식을 테스트했지만 StartInfo 개체의 UserName 속성은 모든 프로세스에 대한 빈 문자열입니다. –

+0

누락 된 '선택'을 추가했는데, 아마도 귀하가 귀하의 의견을 게시했을 때와 같을 것입니다.). 하지만 UserName에 대해 옳았습니다. 직접 만들지 않은 프로세스에 대해서는 설정되지 않았습니다. 다른 방법이 있어야합니다. –

+0

+1 : WMI 솔루션이 잘 작동합니다. –

0

, 당신이는 Win32 API에서 프로세스의 보안 컨텍스트를 잡아해야합니다.

이미 위 코드에서 .Net Process 클래스에있는 프로세스 핸들을 사용하여 P/Invoke를 통해 OpenProcessToken() 함수를 호출하십시오. 프로세스 소유자에 대한 SID를 포함하는 구조를 얻습니다. 액세스 거부와 같은 오류에 대비하십시오. 사용자가 아닌 프로세스와 같은 모든 프로세스에 대해이 정보를 얻을 수있는 액세스 권한이 없기 때문입니다. 거기에서 SID를 이름으로 변환해야합니다. 이 작업을 수행하는 데는 몇 가지 방법이 있지만 LookupAccountSid() 함수 (다시 P/Invoke를 통해)가 사용자 이름을 가져옵니다.

프레임 워크 2.0에서는 보안 설명 자 (System.Security.AccessControl 네임 스페이스)를 다루는 데 도움이되는 내용이 추가되었지만 P/Invoke의 복잡성을 처리하는 데 도움이되는 내용은 없습니다 그곳에.

C#의 Win32 API 사용에 대한 정보는 pinvoke.net을 참조하십시오.

관련 문제