Need to Get Process Name From Changing PID Using Batch File - batch-file

I am having random Applications Freeze up, while I can easily end unresponded tasks with the batch file, I am trying to diagnose which applications are causing the problems. But I cannot Reference a task that has already been killed by PID. I would like the code to show offending Applications before or after killing the process.
This is what I've been using up till now, it does work and does show the PID. But it does not show the application name.
#echo off
:Start
taskkill /f /fi "status eq not responding"
TIMEOUT /t 30 /nobreak
goto Start
**This is what i've been trying to use to get the offending application name**
:Start
Set %processPID% = taskkill.exe /fi "status eq not responding"
wmic process where "ProcessID=%processPID% get CommandLine, ExecutablePath
taskkill.exe /f /fi "status eq not responding"
TIMEOUT /t 5 /nobreak
goto Start
This is what I get when running the new code
It appears that the variable processPID is not being set.
C:\Users\razra\Desktop>Set = taskkill.exe /fi "status eq not responding"
The syntax of the command is incorrect.
C:\Users\razra\Desktop>wmic process where "ProcessID= get CommandLine, ExecutablePath
, - Invalid alias verb.

If you are willing to try PowerShell, you can achieve the same functionality.
Loop trough the processes having Responding property false.
Stops the process by ID.
Foreach($proc in Get-Process | Where-Object {$_.Responding -eq $false}){
Write-Host $proc.ID, $proc.Name
Stop-Process $proc.ID
}
Save the code with ps1 extension and run with PowerShell.exe -File <path>

Related

Batch Detecting Program Not Responding

I am trying to write a batch script that detects if an .exe is not responding, and if it isn't, it will run a piece of code that kills it and then does some other things as well. I know how I can kill the process and restart it if it is not responding in one line, but I am not sure how I can do more than just restart it by converting this into an if statement, or calling a goto.
taskkill /im "exeName.exe" /fi "STATUS eq NOT RESPONDING" /f >nul && start "" "pathToExe"
I have come across other Stack Overflow posts that are similar to this, however they only check the error level of the process and do not check if the program is not responding and how to perform code after that.
How would I go about this? Thanks in advance.
Assuming I am interpreting your question correctly and you want to test without killing a task, how about this:
tasklist /fi "status eq not responding" /nh | find "exeName.exe" >NUL
if %errorlevel% == 0 (
echo Oops, we've hung...
)
tasklist takes the same /fi status options as taskkill, even though the documentation states only RUNNING is allowed - taskkill /? on Windows 8 at least shows the full options. We then use find to check that the executable is in the list of not responding tasks.
BTW, if you want to use PowerShell instead:
$foo = get-process exeName
if (!$foo.Responding) {
echo "Oops, we've hung..."
}
Can be done more easily:
taskkill /FI "STATUS eq NOT RESPONDING" /IM "yourexe.exe" /F | findstr /c:"SUCCESS" >nul
if %errorlevel% EQU 0 (echo Successfully detected and terminated "yourexe.exe" which didn't respond) else (echo Ooops! We didn't find or could not terminate process "yourexe.exe")
If you want to just detect if process is not responding, then use tasklist:
tasklist /FI "STATUS eq NOT RESPONDING" | findstr /c:"yourexe.exe">nul
if %errorlevel% EQU 0 (echo We have detected that process with image name "yourexe.exe" is not responding.) else (echo We didn't found process with image name "yourexe.exe" because it doesn't exist.)
In both cases we use findstr command because even if process not found/terminated taskkill/tasklist will return errorlevel 0.

Batch script to find if program is not responding and then start another application else exit batch job

I want a batch script that checks if the program is in running or not responding state. If it is in running state exit the batch script, else kill the program start the other application.
I tried using the following code but it is executing opening application even though the program is in running state. Please help me in finding a solution
#echo off
TASKLIST/IM jusched.exe /FI "STATUS eq NOT RESPONDING">nul /T /F && start "" notepad.exe
You appear to be mixing up the TaskKill and TaskList syntax. (Enter TaskList/? and TaskKill/? at the command prompt for usage information). Also I think TaskList output is always successful so it would probably need to be checked using something which does register if unsuccessful, e.g. Find.exe.
Here is a basic step by step example for you.
#Echo Off
Rem Setting name of target process
Set "TP=jusched.exe"
Rem Setting name of new process
Set "NP=notepad.exe"
Rem Setting TaskList filters to reduce line length
Set "F1=ImageName eq %TP%"
Set "F2=Status eq Not Responding"
Rem Check target process status and exit if no match
TaskList /FI "%F1" /FI "%F2%" /NH|Find /I "%TP%">Nul||Exit/B
Rem Kill unresponsive process and wait a little
TaskKill /IM "%TP%" /T /F>Nul 2>&1&&Timeout 3 /NoBreak>Nul
Rem Open new process
Start "" "%NP%"

Close a batch window only by typing "exit"?? disable the close "X" button on the top right of batch window

I run a batch file which carries out some task for hours. BY mistake users happen to close the terminal window in which the batch file is executing by pressing the top right "X" close button.
I want to disable it and want to close the batch file window only by typing "exit" inside the window..is this possible?
This can't be done using only one batch file. But there might be a really dirty way for this. You will need three batch files:
EDIT: Here is the solution. Put these three files into the same folder.
controller.bat:
#ECHO OFF
TITLE CONTROLLER
IF NOT EXIST hiddenrunner.vbs (
echo CreateObject^("WScript.Shell"^).Run Wscript.Arguments^(0^), 0, False>hiddenrunner.vbs
)
tasklist /V|findstr "MONITOR"
IF %ERRORLEVEL%==1 hiddenrunner.vbs monitor.bat
:INPUTLOOP
CLS
SET /P input=Type 'exit' to exit:
IF /i NOT %input%==exit GOTO INPUTLOOP
ECHO ok, exiting
taskkill /F /FI "WindowTitle eq Administrator: WORK" /T
taskkill /F /FI "WindowTitle eq Administrator: MONITOR" /T
ping localhost -n 2
del /Q hiddenrunner.vbs
monitor.bat:
#ECHO OFF
SETLOCAL EnableDelayedExpansion
TITLE MONITOR
hiddenrunner.vbs work.bat
:LOOP
tasklist /V|findstr "CONTROLLER"
IF !errorlevel!==1 START controller.bat
ping localhost -n 2
GOTO LOOP
work.bat:
#ECHO OFF
title WORK
ping -t localhost
In your case, the work-file will be your original batch you want to execute. You'll have to adjust the window titles (like TITLE CONTROLLER and WindowTitle eq Administrator: WORK) to fit your setup. However, this works for me. If the user closes the input console, it is being restarted after one second. All processes are being terminated after the user inputs exit in the input console.

start command in batch file

I am wanting to run a batch file which builds visual studio project in another window and then return to original window and execute later commands.
but following command immediately prints LetterTwo without waiting for complete solution building
echo LetterOne
start /WAIT msbuild sim.sln
echo LetterTwo
According to the comments to the question, it seems, msbuild doesn't behave, like one would guess. So your only way is to "wait manually":
start "MyUglyApplication" msbuild sim.sln
:loop
timeout 1 >nul
tasklist /v | find "MyUglyApplication" && goto :loop
echo finished.
Give the new window a unique name, test if the process is running and if yes, continue testing.
i have able to solve the problem by modifying #stephan code a little bit
#echo off
start msbuild <solution>
:loop
timeout 1 >nul
tasklist /FI "IMAGENAME eq msbuild.exe" 2>NUL | find /I /N "msbuild.exe">NUL
if "%ERRORLEVEL%"=="0" goto loop
echo finished.

Can you fork in Windows batch file?

I want to start two programs from the batch file, (also batch files) - they will execute few seconds. Then in the main batch file I want to wait while both are finished and then continue main execution. Is that possible at all?
You can, sort of:
#echo off
set Token=MAIN_%RANDOM%_%CD%
start "%Token%_1" cmd /c child1.cmd
start "%Token%_2" cmd /c child2.cmd
:loop
ping -n 2 localhost >nul 2>nul
tasklist /fi "WINDOWTITLE eq %Token%_1" | findstr "cmd" >nul 2>nul && set Child1=1 || set Child1=
tasklist /fi "WINDOWTITLE eq %Token%_2" | findstr "cmd" >nul 2>nul && set Child2=1 || set Child2=
if not defined Child1 if not defined Child2 goto endloop
goto loop
:endloop
echo Both children died.
child1 and child2 were just executing pause. This uses a more or less unique token to identify the child batch files. They are started in an own window with start and each one is given a specific window title. Using that window title we can find them again using tasklist and determine whether they are still running.
It gets a little tricky figuring out whether the batch files are still running. tasklist with the window title filter does what it's supposed to do, but it won't return a sensible errorlevel. That's why we have to pipe through findstr to pick up the process name (to avoid being language-sensitive by picking up the error message).

Resources