如何强制停止处于"停止挂起"状态的一个或多个服务



我想停止一个Windows服务,它被挂起或卡住状态为Stopping。我们使用的是混合操作系统,如Windows 2008/2012R2。

$ServerList = 'C:PowershellSCXAgentDSClist.txt'  
$SCXAgents = Get-Content -Path $ServerList  
foreach ($scxagent in $SCXAgents) {
  $Hostname = $scxagent
  Write-Host $Hostname
  #Ping host
  $IP = (Test-Connection $hostname -Count 1 -ErrorAction SilentlyContinue |
        Select-Object -ExpandProperty ProtocolAddress)
  if ($IP -eq $null) {
    continue
  }
  #Get state of service 
  $servicestate = Get-Service -ComputerName $Hostname service_name -ErrorAction SilentlyContinue
  #If service is stopped or does not exist, continue otherwise set to stopped and disabled
  if ($servicestate.status -eq 'Stopped' -or $servicestate.status -eq $null) {
    continue
  } else {
    (Get-Service -ComputerName $Hostname service_name).Stop()
    Set-Service -ComputerName $Hostname -Name service_name -StartupType Disabled
    Write-Host "stopped services" -BackgroundColor yellow
    $RPMLines = Get-Service -ComputerName $Hostname service_name
    if ($RPMLines.status -match "Stopped") {
      $ServiceStatus = "STOPPED"
    } else {
      $ServiceStatus = "RUNNING"
    }
    # Port testing (22 and 1270)
    try {
      if ((New-Object System.Net.Sockets.TcpClient("$scxagent", "1270")).Connected -eq $true) {
        $AgentPortStatus = "OK"
      } else {
        $AgentPortStatus = "NOT OK"
      }
    } catch {
      $AgentPortStatus = "NOT OK"
    }
    try {
      if ((New-Object System.Net.Sockets.TcpClient("$scxagent", "22")).Connected) {
        $sshstatus = "OK"
      } else {
        $sshstatus = "NOT OK"
      }
    } catch {
      $sshstatus = "NOT OK"
    }
    Write-Output "$scxagent | SSH : $sshstatus | AgentPort : $AgentPortStatus | AgentServStatus : $ServiceStatus"
  }
}

另外,在我的代码上面,我想把输出格式化成一行,我正确吗?例如:

scxagent sshstatus AgentPortStatus AgentServStatus服务器1 OK OK已停止服务器2不能正常运行等。之前去年更新:

if (-not ([Security.Principal.WindowsPrincipal][Security.Principal.WindowsIdentity]::GetCurrent()).IsInRole([Security.Principal.WindowsBuiltInRole]"Administrator")) {
  $arguments = "& '" + $myinvocation.mycommand.definition + "'"
  Start-Process powershell -Verb runAs -ArgumentList $arguments
  break
}
$ServerList = 'C:PowershellSCXAgentDSClist.txt'  
$SCXAgents = Get-Content -Path $ServerList  
foreach ($scxagent in $SCXAgents) {
  $Hostname = $scxagent
  Write-Host $Hostname
  #Ping host
  $IP = (Test-Connection $hostname -Count 1 -ErrorAction SilentlyContinue |
        Select-Object -ExpandProperty ProtocolAddress)
  if ($IP -eq $null) {
    continue
  }
  #Get state of service 
  $servicestate = Get-Service -ComputerName $Hostname service_name -ErrorAction SilentlyContinue
  #If service is stopped or does not exist, continue otherwise set to stopped and disabled
  if ($servicestate.Status -eq 'Stopped' -or $servicestate.Status -eq $null) {
    continue
  } else {
    $pid = Get-WmiObject -Computer $hostname -Class Win32_Service -Filter "Name='service_name'" |
           Select-Object -Expand ProcessID
    (Get-Process -Computer $hostname -PID $pid).Kill()
    (Get-Service -ComputerName $Hostname service_name).Stop()
    Set-Service -ComputerName $Hostname -Name service_name -StartupType Disabled
    Write-Host "stopped services" -BackgroundColor yellow
    $RPMLines = Get-Service -ComputerName $Hostname service_name
    if ($RPMLines.Status -match "Stopped") {
      $ServiceStatus = "stop"
    } else {
      $ServiceStatus = "start"
    }
    # Port testing (22 and 1270)
    try {
      if ((New-Object System.Net.Sockets.TcpClient("$scxagent", "1270")).Connected -eq $true ) {
        $AgentPortStatus = "OK"
      } else {
        $AgentPortStatus = "NOT OK"
      }
    } catch {
      $AgentPortStatus = "NOT OK"
    }
    try {
      if ((New-Object System.Net.Sockets.TcpClient("$scxagent", "22")).Connected) {
        $sshstatus = "OK"
      } else {
        $sshstatus = "NOT OK"
      }
    } catch {
      $sshstatus = "NOT OK"
    }
    Write-Output "$scxagent | SSH : $sshstatus | AgentPort : $AgentPortStatus | AgentServStatus : $ServiceStatus"
    Read-Host -Prompt "Press Enter to continue"
  }
}

错误信息:

ERROR:不能覆盖变量PID,因为它是只读或常量。getservice。ps1 (32): ERROR: At Line: 32 char: 3错误:+ $pid = Get-WmiObject -Computer $hostname -Class Win32_Service -Filter "Name='A…错误 : +    ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ERROR: + CategoryInfo: WriteError: (PID:String) [], SessionStateUnauthorizedAccessException错误:+ fulllyqualifiederrid: variablenotwwrititable 

如果一个服务在收到停止请求后挂起,"强制停止"的唯一方法就是杀死进程,正如@autsvet已经提到的。使用PID标识进程:

$processID = Get-WmiObject -Computer $hostname -Class Win32_Service -Filter "Name='service_name'" |
             Select-Object -Expand ProcessID
(Get-Process -Computer $hostname -PID $processID).Kill()

注意,一些服务被配置为不允许篡改它们的进程。在这种情况下,您可以尝试更改流程设置。如果这不起作用(或者由于某些原因不能这样做),您将不得不求助于重新启动系统。

相关内容

最新更新