I have Batch code like this
#echo off
:begin
SET d=netstat -an | find /c "0.0.0.0:80"
rem echo %d%
if %%d == "2" (
echo true
pause
rem exit
) else (
echo false
pause
rem GOTO begin
)
I want make netstat stetment output stored in variable d, and d became parameter from If cluse, What wrong with my file ?
You don't need to set a variable in your case.
This should work :
netstat -an | find /c "0.0.0.0:80" && echo true || echo False
But if you need to have this value in a variable you can do like this :
#echo off
for /f %%a in ('netstat -an ^| find /c "0.0.0.0:80"') do set D=%%a
if %D% equ 2 (
echo true
) else (
echo false)
Related
sometimes the ping fails and returns " " , i need to skip that empty line and if it's not empty print it
and count how many pings were successful
#echo off
for /l %%h in (1,1,10) do (
for /f "tokens=*" %%g in (' "ping -n 1 1.1.1.%%h | find /i "ttl" "') do (
if %%g ** *ITSNOTNULL *** (
set/a counter+=1
msg * %%g
)
)
)
pause>nul
exit
Something like this?
#echo off
SetLocal EnableDelayedExpansion
set counter=0
for /l %%h in (1,1,10) do (
for /f "tokens=*" %%g in (' "ping -n 1 1.1.1.%%h | find /i "ttl" "') do (
if not "%%g"=="" (
set /a counter=!counter!+1
echo * %%g )
)
)
echo %~NX0 complete.
echo Total IP addresses: %counter%
EndLocal
pause>nul
Instead of if %%g ** *ITSNOTNULL *** I used if not "%%g"==""
To use a variable within a for loop, if you want to maintain its state, you have to use "DelayedExpansion". This changes the syntax from %thingy% to !thingy!. The reasons for this can be found here
You also can use | findstr . with operator && and || to check any character in variable:
echo/ %%G or %Any_Variable% | findstr . >nul && (echo/Found something) || (echo/Nothing Found!!)
#echo off && SetLocal EnableDelayedExpansion
for /L %%L in (1 1 10)do for /f tokens^=* %%G in ('ping -n 1 1.1.1.%%L^|find "TTL"
')do echo/%%~G|findstr .>nul && (echo/ * %%G && set /a "_cnt+=1+0" ) || goto :next
:next
echo/ - %~NX0 complete^^! && echo/ - Total IP addresses: 0!_cnt! & timeout -1 >nul
endlocal & goto :EOF
I am trying to add a time out to Set /p Var1= So far I have only found this piece of code from here.
#echo off
setlocal EnableDelayedExpansion
if "%1" NEQ "" goto %1
del enter.tmp 2>nul >nul
start /b cmd /c %0 :secondThread
:FirstThread
set n=0
echo Enter Text (5 seconds timeout):
:loop
set /a n+=1
ping -n 2 localhost > nul
if !n! LSS 5 (
if not exist entER.tmp goto :loop
< Enter.tmp (
set /p input=
)
echo !input!
) ELSE (
echo Timeout for input
)
exit /b
:secondThread
set /p var=
> enter.tmp echo !var!
exit /b
This piece of code works great except it stops the count down only when the input is entered. I would like the count down to stop when any key is pressed. I don't know if this is possible. Thanks
I want to do a program for my friend and when i try to do more for /f commands it just dont work!
Code:
echo something1 > Settings.dll
echo something2 >> Settings.dll
echo something3 >> Settings.dll
for /f "skip=0" %%a in (Settings.dll) do set something1=%%a
for /f "skip=1" %%a in (Settings.dll) do set something2=%%a
for /f "skip=2" %%a in (Settings.dll) do set something3=%%a
echo %something1% %something2% %something3%
Pause>nul
But the output is : something1 something1 something1
If you only want to read some lines from a file it's easier to use redirection.
To save
(
echo John Smith
echo 22
echo 1
) > settings.txt
To load
(
set /p name=
set /p age=
set /p times=
) < settings.txt
…and using the For loop:
For /F "Delims=" %%I In (Settings.dll) Do (If Not Defined Line1 (Set Line1=%%I
) Else (If Not Defined Line2 (Set Line2=%%I) Else (
If Not Defined Line3 Set "Line3=%%I")))
Echo= %Line1% %Line2% %Line3%"
Pause>Nul
I have multiple string that come from a reg query inside a for loop.
I want to validate for each of them if it has certain words and do actions if it has.
My code is this:
for /l %%g in (0 1 3) do (
echo HOME%%g
for /f "tokens=1,2,3*" %%h in ('reg query \\%%c\HKLM\SOFTWARE\ORACLE\HOME%%g /v ORACLE_HOME') do (
echo HOME%%g
echo %%j
echo %%j | findstr /I /R /C:"806"
if %ERRORLEVEL% equ 0 (
echo YES
) else (
echo NO
)
echo %%j | findstr /C:".isuites."
if %ERRORLEVEL% equ 0 (
echo YES
) else (
echo NO
)
echo %%j | findstr /I ora90
if errorlevel 0 (
echo YES
) else (
echo NO
)
echo %%j | findstr /I forms10
if errorlevel 0 (
echo YES
) else (
echo NO
)
)
)
The problem is that is does not validates the string as seen in the output
HOME0
HOME0
ECHO is off.
YES
YES
YES
YES
HOME0
d:\oracle\806
d:\oracle\806
YES
YES
YES
YES
HOME1
HOME1
ECHO is off.
YES
YES
YES
YES
HOME1
d:\oracle\iSuites
YES
YES
YES
YES
HOME2
HOME2
ECHO is off.
YES
YES
YES
YES
HOME2
d:\oracle\ora90
YES
YES
d:\oracle\ora90
YES
YES
HOME3
HOME3
ECHO is off.
YES
YES
YES
YES
HOME3
D:\oracle\forms10g
YES
YES
YES
D:\oracle\forms10g
YES
Some corrections are needed in your code
Change for %%h into
for /f "tokens=1,2,*" %%h in ('reg query \\%%c\HKLM\SOFTWARE\ORACLE\HOME%%g /v ORACLE_HOME ^| find "REG_SZ" ') do (
That way, the ORACLE_HOME key name will be in %%h, the REG_SZ type in %%i and the folder in %%j (i supose this is what you intended)
With this done, the next problem is errorlevel checks
When a block of code (code inside parenthesis) is parsed, all variable reads are replaced with the value inside the variable before starting to execute the block. So, if you use %errorlevel% inside you block of code, as this variable read has been replaced with the value of the variable before starting to execute, you will not see the real value.
You can use delayed expansion (include setlocal enabledelayedexpansion at the start of batch file) and change the syntax from %errorlevel% to !errorlevel! to indicate to the parser that the variable read should be delayed until the moment the command is executed.
Or you can use the if errorlevel n ... syntax. In this case you should remember that the condition will be true for any errorlevel value greater or equal than the indicated value.
That is, if errorlevel is 1, both if errorlevel 1 and if errorlevel 0 will be true. For this reason, the proper way of checking error level is to check from greater values to lower values
echo %%j | findstr .....
if errorlevel 1 (
...
) else (
...
)
So, your code should be something like
....
....
for /l %%g in (0 1 3) do (
echo Testing HOME%%g
echo ---------------------------------
for /f "tokens=1,2,*" %%h in (
'reg query \\%%c\HKLM\SOFTWARE\ORACLE\HOME%%g /v ORACLE_HOME 2^>nul ^| find "REG_SZ" '
) do (
echo %%j | findstr /L /C:"806"
if errorlevel 1 (
echo NO
) else (
echo YES
)
echo %%j | findstr /C:".isuites."
if errorlevel 1 (
echo NO
) else (
echo YES
)
echo %%j | findstr /I /C:"ora90"
if errorlevel 1 (
echo NO
) else (
echo YES
)
echo %%j | findstr /I /C:"forms10"
if errorlevel 1 (
echo NO
) else (
echo YES
)
)
)
)
edited to adapt to comments
Some of the HOMEn will not be echoed if they does not exist in registry. To "solve" it, the error output from req query is included in the data to be parsed and it is tested if the string ERROR: is found.
for /l %%g in (0 1 3) do (
echo Testing HOME%%g
echo ---------------------------------
for /f "tokens=1,2,*" %%h in (
'reg query \\%%c\HKLM\SOFTWARE\ORACLE\HOME%%g /v ORACLE_HOME 2^>^&1 ^| findstr /L /C:"REG_SZ" /C:"REG_EXPAND_SZ" /C:"ERROR:" '
) do (
for %%z in ("806" ".isuites." "ora90" "forms10") do (
(if "%%h"=="ERROR:" (echo() else (echo %%j)) | findstr /i /c:"%%~z"
if errorlevel 1 (
echo NO
) else (
echo YES
)
)
)
)
)
Here is something I'm struggeling with:
Title Scanning online computers: && set /a title_count=0
call :next
:next
FOR /F "tokens=1" %%a IN (workstation.txt) do (
title Scanning for online computers: %title_count% / %workstation%
ping -n 1 %%a | find "bytes=" >nul
set /a title_count=title_count+=1
if NOT ERRORLEVEL 1 (
set color=%%a && call includes\what.bat %color_pass% && echo %%a >> logs\reachable.txt
) else (
set color=%%a && call includes\what.bat %color_fail% && echo %%a >> logs\unreachable.txt && echo %%a, offline, % date%, %time% >> logs\offline.txt
)
)
The problem I have here is that the function TITLE is not getting updated while the variable %count_title% is counting up through the script.
set /a title_count+=1
doesn't work either
It's displayed as:
Scanning for online computers 0 / 5
Can sombody tell me what I'm doing wrong here?
Thanks in advance.
Illusion
Hi,
I've tried it the way as suggested:
It finishes the rest of the script when using the last GOTO :EOF
IT doesn't make sense to me, if I remove the last GOTO :eof, only the first row in workstation.txt is getting processed/parsed.
Scanning online computers: && set /a title_count+=1`
call :next
::added as possibly missing
GOTO :EOF
:next
FOR /F "tokens=1" %%a IN (workstation.txt) DO CALL :pingstation %%a
GOTO :EOF
:pingstation
title Scanning for online computers: %title_count% / %workstation%
ping -n 1 %1 | find "bytes=" >nul
set /a title_count+=1
if NOT ERRORLEVEL 1 (
set color=%1 && call includes\what.bat %color_pass% && echo %1 >> logs\reachable.txt
) else (
set color=%1 && call includes\what.bat %color_fail% && echo %1 >> logs\unreachable.txt && echo %1, offline, %date%, %time% >> logs\offline.txt
)
goto :eof
)
Read this: Environment variable expansion occurs when the command is read.
Salient points:
Your variables are expanded right when for command (and its entire body enclosed in parentheses) is parsed.
Use !VARNAME! instead of %VARNAME% to avoid it.
For better portability across OS versions/setups, it's a good idea to stick a setlocal EnableExtensions EnableDelayedExpansion at the beginning of your batch file.
Also, make sure there is a goto (e.g., goto :EOF) after call :next, because the code as posted will run through next one extra time.
You can go with setlocal EnableDelayedExpansion and changing the % syntax to the ! one when addressing vars inside the loop that are initialised within that very loop, just as atzz has suggested.
But there's a different approach. You can simply move the body of the loop to a(nother) subroutine. That way the variables would expand as expected.
Title Scanning online computers: && set /a title_count=0
call :next
::added as possibly missing
GOTO :EOF
:next
FOR /F "tokens=1" %%a IN (workstation.txt) DO CALL :pingstation %%a
GOTO :EOF
:pingstation
title Scanning for online computers: %title_count% / %workstation%
ping -n 1 %1 | find "bytes=" >nul
set /a title_count+=1
if NOT ERRORLEVEL 1 (
set color=%1 && call includes\what.bat %color_pass% && echo %1 >> logs\reachable.txt
) else (
set color=%1 && call includes\what.bat %color_fail% && echo %1 >> logs\unreachable.txt && echo %1, offline, %date%, %time% >> logs\offline.txt
)