Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to to terminate a windows batch file from within a 'call'ed routine?

I've got a windows batch file, with a few sub-routines in it something like this:

call :a
goto :eof

:a
call :b
goto :eof

:b
:: How do I directly exit here from here?
goto :eof

I'm running this in a cmd window on Vista.
If I detect an error somewhere in the batch file, I want it to exit with a non-zero errorlevel. Is there anything I can write in the routine :b that will cause the batch file to terminate like this.

  • I've tried 'exit', which closes the entire cmd window. That's not what I want.
  • I've tried 'exit /B 1'. That returns to the previous routine. To use this scheme after every 'call' I'd have to carefully write 'if errorlevel 1 exit /B 1' after every single 'call' to pass the error back up the call stack. I'd prefer not to have to write this line after every call.

This article was interesting, but non of the alternatives behave in the way I want. http://www.computerhope.com/exithlp.htm

Is there another way?

Thanks.

like image 795
Scott Langham Avatar asked Jun 01 '09 08:06

Scott Langham


People also ask

How do you terminate a batch file?

Ctrl+C. One of the most universal methods of aborting a batch file, command, or another program while it's running is to press and hold Ctrl + C .

How do I stop a Windows batch file from running?

You can insert the pause command before a section of the batch file that you might not want to process. When pause suspends processing of the batch program, you can press CTRL+C and then press Y to stop the batch program.

How do I stop a batch file from service?

In order to stop the service via batch script: Open cmd as administrator. Run this command: NET STOP <SERVICE_NAME>

What is @echo off in batch script?

When echo is turned off, the command prompt doesn't appear in the Command Prompt window. To display the command prompt again, type echo on. To prevent all commands in a batch file (including the echo off command) from displaying on the screen, on the first line of the batch file type: Copy. @echo off.


1 Answers

You can call your subroutines like so:

call :b||exit /b 1

which is equivalent to

call :b
if errorlevel 1 exit /b 1

It's slightly shorter and saves you one line, but it's still not ideal, I agree.

Other than that I don't see a way.

EDIT: Ok, I got a way, but it's Pure Evil™.

Misusing the maximum stack size, and therefore recursion limit, we create another subroutine which simply exhausts the stack by recursively calling itself:

@echo off
echo Calling a
call :a
echo Called a
goto :eof
:a
echo Calling b
call :b
echo Called b
goto :eof
:b
echo Trying to exit
call :exit
goto :eof
:exit
call :exit

This, however, will result in the nasty error message

******  B A T C H   R E C U R S I O N  exceeds STACK limits ******
Recursion Count=704, Stack Usage=90 percent
******       B A T C H   PROCESSING IS   A B O R T E D      ******

Also, it will take around 2 seconds on my machine.

You can suppress the error message by altering the call statement as follows:

call :exit >nul 2>&1

which will redirect everything it wants to output into a great void.

But considering the time it takes to fill the stack I think the first variant would be easier.

I was also contemplating using a second batch file, which, when run without call would essentially stop the first one. But somehow that doesn't play well with subroutines. Unrolling the call stack seemingly still takes place.

like image 57
Joey Avatar answered Oct 10 '22 14:10

Joey