For loop for checking the 'state' of certain windows' services - batch-file

services.txt contains:-
Plugplay
spooler
dhcp
I want to check the status of some services that are specified in file services.txt. I am using for loop for this.
#echo off
for /f %%a IN ('type services.txt') do call :chkservice %%a
goto :eof
:chkservice
sc query %a%
Instead of getting the output for the three specified services, I am getting the output equivalent to three times the command sc query (I guess).
For debugging I tried checking if the variable a getting the values properly or not and tried this version of code:-
#echo off
for /f %%a IN ('type services.txt') do call :chkservice %%a
goto :eof
:chkservice
#echo on
echo %a%
This code display spooler and dhcp only. Why not plugplay? I Believe both the issues are related, but not sure how.
Any help on this would be highly appreciated.

If you call a function your parameters are in %1,%2,...%n not in %a%.
The parameters of a for-loop are nearly invisble outside of that loop.
So your code should looks like
#echo off
for /f %%a IN ('type services.txt') do call :chkservice %%a
goto :eof
:chkservice
echo %1
goto :eof

Related

Trying to understand this code (Batch, CMD)

#echo off
setlocal enabledelayedexpansion
::just a sample adapter here:
set "adapter=Ethernet adapter Local Area Connection"
set adapterfound=false
echo Network Connection Test
for /f "usebackq tokens=1-2 delims=:" %%f in (`ipconfig /all`) do
(
set "item=%%f"
if /i "!item!"=="!adapter!"
(
set adapterfound=true
)
else if not "!item!"=="!item:IP Address=!" if "!adapterfound!"=="true"
(
echo Your IP Address is: %%g
set adapterfound=false
)
)
VERY new to batch, can someone explain a few things here:
What does setlocal enabledelayedexpansion do in this particular instance?
What does usebackq do? (I've tried looking this up but didn't quite understand)
How did the variable %%g get initialized and is it global or local?
Thank you for your time!
Delayed Expansion will cause variables to be expanded at execution time rather than at parse time.
Code below would seem to echo second second, but it prints first second instead.
setlocal EnableDelayedExpansion
set var=first
set var=second & Echo %var% !var!
Source: SS64
usebackq forces for loops use backquotes (`dir`) to evaluate the commands inside it and use the output for the forloop, instead of open a file. This will list all elements of Documents predeced with an asterisk.
echo Documents:
for /f "usebackq" %%i in (`dir /b "C:\Users\%username%\Documents\"`) do (
echo * %%i
)
pause
They're local. Using the previous example, %%iis defined just in the for loop, no additional initialization needed.

Nested for loop - batch Script

Hello Batch File experts,
I wrote this piece of code which will print the Latest file version present in the folder in comparison to file name sent as argument, however these line seems to work accordingly when I remove the outer for loop, which I designed to loop as many time as CLI arguments.
FOR /f %%f IN ('DIR /b %%a.*.zip') DO #SET last=%%f
ECHO %last%
Full code :
cd C:\Users\batch\Desktop\test
chdir
set arg1=%1
set arg2=%2
set list=%arg1% %arg2%
(for %%a in (%list%) do (
FOR /f %%f IN ('DIR /b %%a.*.zip') DO #SET last=%%f
ECHO %last%
))
pause
what am I missing here because of which variable last is not set with value when outer loop is present which works perfectly without it.
Thanks,
Might I suggest you use SHIFT instead:
#Echo Off
SetLocal
If %1'==' Exit/B
If /I Not "%CD%"=="%USERPROFILE%\Desktop\test" (
PushD "%USERPROFILE%\Desktop\test" 2>Nul&&(Set _=PopD)||Exit/B)
:Loop
For %%A In ("%~1*.zip") Do Set "last=%%A"
Echo=%last%
Shift
If Not %1'==' GoTo Loop
%_%
EndLocal
Timeout -1
This of course means that you are free to use it with more than two arguments!
You need to use delayed expansion (about ten thousand SO items on this) or use a subroutine or
call echo %%last%%

Issues with batch file to search registry and edit

I'm not so new to batch scripting and have done a small amount of scripts for various other things but this script has stumped me.
I've actually pulled this idea from somewhere else as I'm not that deep into the for commands just yet.
What I'm trying to do with this script is search every subkey within the HKU rootkey for a specific subkey path. If that subkey path exists it'll modify a key value within that subkey path. But it seems to keep failing with no error.
This is what I have right now:
for /f %%a in ('reg query hku') do call :loop1 %%a
goto :end
:loop1
for /f %1 in (reg query %1\software\microsoft\dynamics) do call :loop2 %%b
goto :end
:loop2
if Errorlevel 1 goto :error
reg add %1\6.0\configuration /v configurationfile /t reg_sz /d \ /f
goto :end
:error
echo Error has occurrd.
goto :end
:end
Pause
When I run this batch I get the following.
c:\Users\-username-\Desktop\test>for /F %a in ('reg query hku') do call :loop1 %a
c:\Users\-username-\Desktop\test>call :loop1 HKEY_USERS\.DEFAULT
c:\Users\-username-\Desktop\test>for /f HKEY_USERS\.DEFAULT in (reg query HKEY_USER
S\.DEFAULT\software\microsoft\dynamics) do call :loop2 %b
c:\Users\-username-\Desktop\test>
It seems like it just stops running? when I check the errorlevel after it runs it returns "0" so I'd think I'd at least see the error message come up?
Am I missing something small I'm just looking over?
Run this to start with - see if what it returns is helpful to you:
This may need a later version of Windows - I'm not sure of the reg query options for earlier windows.
#echo off
for /f "delims=" %%a in ('reg query hku /s /f data /k ^| find /i "\software\microsoft\dynamics" ') do echo "%%a"
You need GOTO :eof to return from the subroutines.
for /f %%a in ('reg query hku') do call :loop1 "%%a"
pause
goto :eof
:loop1
for /f "%~1" in (reg query "%~1\software\microsoft\dynamics") do call :loop2 "%%b"
goto :eof
:loop2
if Errorlevel 1 echo Error has occurred. & pause & exit /B 1
reg add "%~1\6.0\configuration /v configurationfile" /t reg_sz /d \ /f
goto :eof
I found the bug(s). It was two places. RGuggiesberg, you are right. I needed the EOF in there. As foxidrive points out, the first line of "loop1" had some syntax issues. I was confusing myself.
Replaced:
for /f %1 in ('reg query %1\software\microsoft\dynamics') do call :loop2 %%b
with:
for /f %%b in ('reg query %1\software\microsoft\dynamics') do call :loop2 %%b
Now it's working fine. Thanks for the pointers!

Change letters alphabetically in a for loop to print all tokens

I have a file (MyFile.txt) with a string like this, for example:
var1,var2,asds,123,var6
This file is generated automatically, and I don't know how many words it will have.
I make a for to print all words, one in each line. And process them one by one
for /f "tokens=1-30 delims=," %%a in (MyFile.txt) do call Process.bat %%a
In Process.bat I have ping %1 for example.
This only processes the first token. My problem is, I need to process all tokens, but I need to do it automatically, is there a way to loop over all existing tokens?
In my example: var1,var2,asds,123,var6 it would be: do call Process.bat %%a, then %%b, then %%c, then %%d and %%e.
Thank you.
This will work even if you have various line in Myfile.txt
#echo off&cls
for /f "delims=" %%a in (MyFile.txt) do for %%b in (%%a) do call Process.bat %%b
What about this:
set /p var=<MyFile.txt
set var="%var%"
for %%a in ("%var:,=" "%) do call Process.bat %%a
That Should work.
Mona
you can combine for to read all your lines and call to parse the vars in the line
try this to get you started
#echo off
setlocal enabledelayedexpansion
for /f %%a in (file.txt) do (
set line=%%a
set line=!line:,= !
call :parms !line!
)
goto :eof
:parms
if "%1"=="" goto :eof
echo ping %1
shift
goto :parms
goto :eof

Parse filenames with Space and ( ) in DOS batch

How can I run this batch script on filenames with space and "(" ")"?
:Start
#Echo off
Set _SourcePath=C:\tifs\*.tif
Set _OutputPath=C:\txts\
Set _Tesseract="C:\Program Files\Tesseract-OCR\tesseract.exe"
:Convert
For /F "usebackq delims=" %%A in (%_SourcePath%) Do Echo Converting %%A...&%_Tesseract% %%A %_OutputPath%%%~nA
:End
Set "_SourcePath="
Set "_OutputPath="
Set "_Tesseract="
You have 2 problems:
1) You need some additional quotes.
2) You are using the wrong form of FOR. Your code is using the /F option with an unquoted IN() cluase. This attempts to read the contents of a file, which can't possibly work because your name includes a wildcard. I think you want a listing of .TIF files which is best done using the simple form of FOR (no /F option).
for %%A in (%_SourcePath%) do echo Converting "%%A"...&%_Tesseract% "%%A" "%_OutputPath%%%~nA"
I would change it to something like this:
:Start
#Echo off
SETLOCAL ENABLEEXTENSIONS
SETLOCAL ENABLEDELAYEDEXPANSION
Set _SourcePath=C:\tifs\*.tif
Set _OutputPath=C:\txts\
Set "_Tesseract=C:\Program Files\Tesseract-OCR\tesseract.exe"
:Convert
For /F "usebackq delims=" %%A in (%_SourcePath%) Do Echo Converting %%A...&%_Tesseract% "%%A" "%_OutputPath%%%~nA"
:End
Set "_SourcePath="
Set "_OutputPath="
Set "_Tesseract="
Now, my answer might not work but I think it might give you enough hints to figure it out.

Resources