3

I am trying to have this script go to the next part if the error level of a ping to a computer does not equal 0, but I cannot get it to work. The output says the syntax is not correct. Thank you.

@echo
setlocal EnableDelayedExpansion

for /f %%a in (main.txt)  do ( 
ping -n 1 %%a > NUL
IF %ERRORLEVEL%==0 (GOTO :COPY) ELSE GOTO :SKIP

:COPY
ROBOCOPY C:\Blah C:\Bloh
ECHO FILE COPIED

:SKIP
 ECHO FILE NOT COPIED
 )

2 Answers 2

3

You should try this:

@echo
setlocal EnableDelayedExpansion

for /f %%a in (main.txt) do ( 
  ping -n 1 %%a >NUL
  IF "!ERRORLEVEL!"=="0" (
    ROBOCOPY "C:\Blah" "C:\Bloh"
    ECHO FILE COPIED
  ) ELSE (
    ECHO FILE NOT COPIED
  )
)
PAUSE

There are a couple of things wrong with your code. First of all, you enable Delayed Expansion, but don't actually use it, only variables inside ! get expanded delayed. I also put quotes around your filepaths, to protect them against paths with spaces and stuff. Finally, goto and labels don't work inside for loops, so you need to replace them with if else logic

Sign up to request clarification or add additional context in comments.

1 Comment

Excellent, thank you very much, this works the way I needed it. You explained it very well and I learned something new.
0

goto :Label inside a parenthesised block of code like for loops breaks the block/loop context, so the code at the label is executed as if it were outside of the block/loop. Therefore you need to work around that.


Dennis van Gils points out a way how to do it -- using if/else logic (his method as well as the following slightly modified snippet (applying numeric comparison) both require delayed expansion):

setlocal EnableDelayedExpansion
for "usebackq" /F %%A in ("main.txt") do (
    > nul ping -n 1 %%A
    if !ErrorLevel! EQU 0 (
        robocopy "C:\Blah" "C:\Bloh"
        echo FILE COPIED
    ) else (
        echo FILE NOT COPIED
    )
)
endlocal

Or like this, avoiding the necessity of delayed expansion:

for "usebackq" /F %%A in ("main.txt") do (
    > nul ping -n 1 %%A
    if ErrorLevel 1 (
        echo FILE NOT COPIED
    ) else (
        robocopy "C:\Blah" "C:\Bloh"
        echo FILE COPIED
    )
)

To check the ErrorLevel against (non-)zero, you can also use the && and || operators:

for "usebackq" /F %%A in ("main.txt") do (
    > nul ping -n 1 %%A || (
        echo FILE NOT COPIED
    ) && (
        robocopy "C:\Blah" "C:\Bloh"
        echo FILE COPIED
    )
)

Finally, if you do want to keep the goto :Label structure, you need to use a sub-routine in order to move this part of the code outside of the () block (you also do not need delayed expansion here):

for "usebackq" /F %%A in ("main.txt") do (
    > nul ping -n 1 %%A
    call :SUB "C:\Blah" "C:\Bloh"
)
exit /B

:SUB
if %ErrorLevel% NEQ 0 goto :SKIP
robocopy "%~1" "%~2"
echo FILE COPIED
:SKIP
goto :EOF

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.