Strange value when parsing output in Windows batch script - windows

Trying to make a script to unlock all locked files inside a folder, by using Windows' handle.exe. But when I split the output the filename value is .... weird (all other values are Ok).
The sample output of the handle.exe is this:
REM perl.exe pid: 12532 type: File PCNAME\UserName 144: C:\dev\massunlocker\Eula.txt
REM a perl.exe
REM b pid:
REM c 12532
REM d type:
REM e File
REM f PCNAME\UserName
REM g 144:
REM h C:\dev\massunlocker\Eula.txt
So, from this I need c, g, and h.
#echo off
setlocal EnableDelayedExpansion
for /f "tokens=1,2,3,4,5,6,7,8 delims= " %%a in ( 'handle64.exe C:\dev\massunlocker\sample-dir -u -nobanner' ) do (
REM echo a = "%%a"
REM echo b = "%%b"
REM echo c = "%%c"
REM echo d = "%%d"
REM echo e = "%%e"
REM echo f = "%%f"
REM echo g = "%%g"
REM echo h = "%%h"
echo [%%h]
)
:end
setlocal DisableDelayedExpansion
First 2 are fine, but the %%h is hmm weird (edited)?
]C:\dev\massunlocker\sample-dir\ae\pdf
]C:\dev\massunlocker\sample-dir
]C:\dev\massunlocker\sample-dir\ae
Why its not this? :
[C:\dev\massunlocker\sample-dir\ae\pdf]
[C:\dev\massunlocker\sample-dir]
[C:\dev\massunlocker\sample-dir\ae]
And I can't test it for being dir or a file, it's always comes as true for not exist, for example.
Edit: here's an output example with lines uncommented:
a = "cmd.exe"
b = "pid:"
c = "1624"
d = "type:"
e = "File"
f = "PCNAME\UserName"
g = "1FC:"
" = "C:\dev\massunlocker\sample-dir
note the last line...
P.S. Handle tool

The output you're experiencing is the same as we get from the output of wmic.exe within a For loop. I'll assume therefore that handle64.exe also outputs an extra <CR>.
If that's the case, you should run the result through an additional For loop, in the same way as if it were WMIC. Take a look at some of the WMIC examples on this site for examples of it in use. Alternatively take a look at this topic over on dostips.com.
Here's an example of it in use:
For /F "Tokens=*" %%A In ('
handle64.exe C:\dev\massunlocker\sample-dir -u -nobanner
')Do For /F "Tokens=1-8" %%B In ("%%A")Do (Rem Echo B = "%%B"
Rem Echo C = "%%C"
Rem Echo D = "%%D"
Rem Echo E = "%%E"
Rem Echo F = "%%F"
Rem Echo G = "%%G"
Rem Echo H = "%%H"
Rem Echo I = "%%I"
Echo [%%I])
Pause

The following code snippet could help.
#ECHO OFF
SETLOCAL EnableExtensions EnableDelayedExpansion
for /f "tokens=1-7,* delims= " %%a in ('
handle64.exe C:\Windows\System32\en-US\Kernel -u -nobanner
' ) do (
REM echo a = "%%a"
REM echo b = "%%b"
REM echo c = "%%c"
REM echo d = "%%d"
REM echo e = "%%e"
REM echo f = "%%f"
REM echo g = "%%g"
REM echo h = "%%h"
for /F "tokens=*" %%H in ("%%~h") do echo h="%%H" a="%%a"
)
Here the for loops are
%%a to retrieve the handle64.exe output values;
%%H to remove the ending carriage return in the %%h value returned at a line end.
wmic (and handle64 as well) behaviour: each output line ends with 0x0D0D0A (<CR><CR><LF>) instead of common 0x0D0A (<CR><LF>).
See Dave Benham's WMIC and FOR /F: A fix for the trailing <CR> problem
Output (truncated):
==> D:\bat\SO\55065841.bat
h="C:\Windows\System32\en-US\KernelBase.dll.mui" a="GoldenDict.exe"
h="C:\Windows\System32\en-US\KernelBase.dll.mui" a="chrome.exe"
h="C:\Windows\System32\en-US\kernel32.dll.mui" a="chrome.exe"
h="C:\Windows\System32\en-US\KernelBase.dll.mui" a="AppleChromeDAV.exe"
==>

I don't mean this as an answer.. I just needed the formatted text.
As Compo points out.. there is indeed 0D 0D 0A at the end of the output but not in the middle where the parser should care about it.
Their parser should be better than that.
As a workaround (as Compo mentioned), take the output of the call and run it through another for loop, it works just fine. I did the one below with a function call.
#echo off
Set THE_DIR=%TEMP%
for /f "delims=" %%a in ( 'handle64.exe %THE_DIR% -u -nobanner' ) do call :Process_Line "%%a"
goto :EOF
:Process_Line
for /f "tokens=1,2,3,4,5,6,7,8 delims= " %%a in ( 'echo %*' ) do (
echo a = "%%a"
echo b = "%%b"
echo c = "%%c"
echo d = "%%d"
echo e = "%%e"
echo f = "%%f"
echo g = "%%g"
echo h = "%%h"
)
goto :EOF

Related

Lower and remove special character of file name

I want to create a script, which lower and remove special character multiple text files.
my files in folder like this:
- ⚡ Document.txt
- [Review] Test File.txt
i want remove special char of filename like this
- document.txt
- review test file.txt
i've tried like this, but only lower filename. how to remove special character?
#echo off
setlocal enableDelayedExpansion
pushd %currentfolder%
for %%f in (*) do (
set "filename=%%~f"
for %%A in (a b c d e f g h i j k l m n o p q r s t u w x y z) do (
set "filename=!filename:%%A=%%A!"
)
ren "%%f" "!filename!" >nul 2>&1
)
endlocal
Before
#ECHO OFF
SETLOCAL ENABLEDELAYEDEXPANSION
SET "sourcedir=u:\your files"
set "validchars=abcdefghijklmnopqrstuvwxyz1234567890. "
pushd "%sourcedir%"
FOR %%b IN (*) DO (
set "newname="
set "oldname=%%b"
call :validate
if /i "%%b" neq "!newname!" ren "%%~sb" "!newname!"
)
popd
GOTO :EOF
:validate
if not defined oldname goto :eof
set "c1=%oldname:~0,1%"
set "oldname=%oldname:~1%"
if "!validchars:%c1%=!" neq "%validchars%" set "newname=%newname%%c1%"
goto validate
Always verify against a test directory before applying to real data.
I predict it will have problems with some unicode characters and the usual suspects.
You could use pure powershell for this, or if you feel like continuing the use batch-file, just call powershell to assist:
#echo off
for %%i in (*) do for /f "delims=" %%a in ('powershell "$string='%%~ni';$String.tolower() -replace '[\W]', ''"') do echo ren "%%~i" "%%a%%~xi"
Note the echo at the end of the line, that is to test functionality by printing to screen before you do the actual renaming. Only remove echo when you're happy with the printed results.

Batch list folder contents, then echo results as options to be set as variables

I usually like to try to work these out myself, but at the moment I have to admit I don't know where to start with this one. Hoping someone could kindly steer me in the right direction at least.
I have a folder with a number of .txt files
Text1.txt
Text2.txt
Text3.txt
In my windows bat file I need to list the contents of said folder and set them as options to be set as variables.
example:
cls
echo[
echo[ Please select an option
echo[
echo (1) Text1
echo (2) Text2
echo (3) Text3
echo[
set /p option=Type your selection (1-3) and press ENTER=
if !option!==1 set var=Text1
if !option!==2 set var=Text2
if !option!==3 set var=Text3
Any advice is greatly appreciated, this forum has been great.
*Edit
here is something I tried
cls
echo[
echo[ Please select an option
echo[
dir /b "*.txt"
echo[
set /p option=Type your selection (1-3) and press ENTER=
if !option!==1 set var=text1
if !option!==2 set var=text2
if !option!==3 set var=text3
it works, but does not add the numbers (1) before the options, and it also has them aligned left not centred.
Please select an option
text1.txt
text2.txt
text3.txt
Type your selection (1-3) and press ENTER=
There are different solutions you can build, here are 2 examples.
If you have only a few files you can utilize choice:
#echo off
setlocal enabledelayedexpansion
for /F "tokens=1,*delims=[]" %%i in ('dir /b /a:-d *.txt ^| find /v /n ""') do (
echo %%i. %%j
set "cnt=!cnt!%%i"
set "fchoice%%i=%%~j"
)
choice /c %cnt% /m "Choose"
echo you chose !fchoice%errorlevel%!
if you have many files though, choice might not be a viable option, then revert to set /p:
#echo off
setlocal enabledelayedexpansion
for /F "tokens=1,*delims=[]" %%i in ('dir /b /a:-d *.txt ^| find /v /n ""') do (
echo %%i. %%j
set "cnt=!cnt!%%i"
set "fchoice%%i=%%~j"
set "fin=%%i"
)
set /p "chosen=Select a file by number: "
for /l %%i in (1,1,%fin%) do if "%chosen%" == "%%i" set "check=1"
if not defined check echo Incorrect choice selected & goto :EOF
echo you chose !fchoice%chosen%!
Well, if this were any other language what would you do? Probably populate an array with your directory listing, right? Then use that array to pair menu option with file choice? Well, don't let the fact that the Batch language doesn't have arrays stop you. They're easy enough to simulate.
#echo off & setlocal
rem // init array index
set file.length=0
rem // for each .txt file in the current directory
for %%I in (*.txt) do (
rem // It's good practice only to enable delayed expansion when needed, as
rem // otherwise it can mangle values containing exclamation marks
setlocal enabledelayedexpansion
rem // use a "for /f" command to endlocal while reading the value of
rem // !file.length!. This preserves exclamation marks in file names.
for /f %%# in ("!file.length!") do endlocal & set "file[%%~#]=%%~I"
rem // set /a doesn't require delayed expansion. It just works.
set /a file.ubound = file.length, file.length += 1
)
rem // Display the collection of variables named file...something.
set file
There you go. The last line should show you a list of all the variables beginning with file, including the simulated .length and .ubound properties. From there, just use a for /L %%I in (0, 1, %file.ubound%) to display your menu.
Here's a bit more. Firstly, I read your comment explaining that the number of txt files could exceed 50. By default, the Windows cmd console is 24 lines. Wouldn't it be nice to columnify the output so the user doesn't have to scroll? I wrote a utility script that will take a flat list and columnify it based on the number of rows in the current cmd console. Save this as...
columnify.bat:
#if (#CodeSection == #Batch) #then
#echo off & setlocal
if "%~1"=="test" (
rem // this errors if there's redirected input buffer waiting
timeout /t 0 /nobreak >NUL 2>NUL && (
echo Usage: command list output ^| %~nx0
echo or %~nx0 ^< txtfile containing a list
echo;
echo Hit Ctrl-C to exit.
)
exit
)
for /f "usebackq tokens=1,2 delims=," %%I in (
`powershell "(Get-Host).UI.RawUI.WindowSize.toString()"`
) do (
rem // detect whether input buffer has content waiting
start /b cmd /c "%~f0" test
cscript /nologo /e:JScript "%~f0" %%I %%J
)
goto :EOF
#end // end Batch / begin JScript hybrid code
var stdin = WSH.CreateObject('Scripting.FileSystemObject').GetStandardStream(0).ReadAll();
cols = WSH.Arguments(0) * 1 - 1,
rows = WSH.Arguments(1) * 1 - 4;
var out = stdin.split(/\r?\n/), buffer = [], maxlen, col = 0;
if (rows > out.length) { rows = out.length; }
while (out.length) {
buffer[col] = [];
maxlen = 0;
while (buffer[col].length < rows) {
val = out.length ? out.shift() : '';
buffer[col].push(val);
if (maxlen < val.length) maxlen = val.length;
}
for (var i = buffer[col].length; i--;) {
while (buffer[col][i].length < maxlen) { buffer[col][i] += ' '; }
}
col++;
}
for (var i=0; i < buffer[0].length; i++) {
var line = [];
for (var j=0; j < col; j++) {
line.push(buffer[j][i]);
}
WSH.Echo(line.join(' ').substr(0, cols));
}
Now your main script can make use of columnify.bat by piping output through it.
#echo off & setlocal
rem // All the same stuff as above, but without the comments.
set file.length=0
for %%I in (*.txt) do (
setlocal enabledelayedexpansion
for /f %%# in ("!file.length!") do endlocal & set "file[%%~#]=%%~I"
set /a file.ubound = file.length, file.length += 1
)
cls
:displaymenu
echo Always press your luck. Which file do you choose?
echo;
( for /L %%I in (0,1,%file.ubound%) do #(
call echo %%I: %%file[%%~I]%%
) ) | columnify
echo;
set /P "choice=Enter a number: "
if %choice% GEQ 0 if %choice% LEQ %file.ubound% (
setlocal enabledelayedexpansion
echo You chose !file[%choice%]!. Neat.
endlocal
) else (
cls
powershell "write-host -f red 'Invalid response. Enter a number between 0 and %file.ubound%.'"
goto displaymenu
)

find multiple files paths with single string

I tried to write a batch script that find all the paths of files that have the same name as the input string. right now it can find only the first file found, and i cant think of a way to make it list multiple files locations. I am not very experienced and I need some help.
this is part of the script code:
:start
cls
echo Enter file name with extension:
set /p filename=
echo Searching...
for %%a in (C D E F G H U W) do (
for /f "tokens=*" %%b in ('dir /s /b "%%a:\%filename%"') do (
set file=%%~nxb
set datapath=%%~dpb\
::the path of the file without the filename included "C:\folder\folder\"
set fullpath=%%b
::the path of the file with the filename included "C:\folder\folder\file"
goto break
)
)
:notfound
cls
echo Enter file name with extension:
echo %filename%
echo File Not Found!
ping localhost -n 4 >nul
goto start
:break
if "%datapath:~-1%"=="\" set datapath=%datapath:~,-1%
cls
echo 3 %filename% found
echo %fullpath1%
echo %fullpath2%
echo %fullpath3%
--- || ---
I want the script to search the computer and list every encountered files with the same name and I want to be able to put those files' paths into different variables.
For example, if readme.txt is the input, then I want the list of all the paths of all the files with that specific name (readme.txt) and I want to set variable for each path so I can use it after that.
input:
readme.txt
output:
3 files found
C:\folder\folder\readme.txt
C:\folder\folder\folder\readme.txt
D:\folder\readme.txt
#echo off
set filename=readme.txt
for %%a in (C D E F G H U W) do (
for /f "tokens=*" %%b in ('dir /s /b "%%a:\%filename%"') do (
echo you can do something here with %%~nxb in %%~dpb
echo full name: %%b
)
)
I see no need to set the filenames to variables, as you can process them inside your loop. But if you really need them (for some reason) in variables:
#echo off
setlocal enabledelayedexpansion
set filename=readme.txt
set count=0
for %%a in (C D E F G H U W) do (
for /f "tokens=*" %%b in ('dir /s /b "%%a:\%filename%" 2^>nul') do (
set /a count+=1
set _file[!count!]=%%b
)
)
set _file
You can try with this code :
#echo off
Title Searching for the path with the same file name
Mode con cols=80 lines=3 & Color 9E
SET /a Count=0
set /a cnt=1
set "FileName=Readme.txt"
set "Report=%~dp0Report.txt"
set "Folder2Copy=%~dp0Readme_Folder"
set "Result2Copy=%~dp0Result2Copy.txt
If exist %Folder2Copy% RD /S /Q %Folder2Copy%
If Exist %Report% Del %Report%
If Exist %Result2Copy% Del %Result2Copy%
echo(
Echo Searching for the path with the same file name
Rem Looking for fixed drives and store them into variables
SETLOCAL enabledelayedexpansion
For /f "skip=1" %%a IN ('wmic LOGICALDISK where driveType^=3 get deviceID') DO (
for /f "delims=" %%b in ("%%a") do (
SET /a "Count+=1"
set "Drive[!Count!]=%%b"
)
)
:Display
for /L %%i in (1,1,%Count%) do (
cls
Title Please wait a while ... Searching for "%FileName%" on "!Drive[%%i]!\"
echo(
echo Please wait a while ... Searching for "%FileName%" on "!Drive[%%i]!\"
Call :FindPathFile !Drive[%%i]!\ %FileName% >> %Report%
)
Start "" %Report%
Goto :AskQuestion
::***************************************************************************************
:FindPathFile <Location> <FileName>
Where.exe /r %1 %2
Goto :eof
::***************************************************************************************
:AskQuestion
cls & Mode con cols=100 lines=5
echo(
echo Did you want to make copy of all files found as name "%FileName%"
echo saved on "%Report%" ? (Y/N) ?
set /p "Input="
If /I "%INPUT%"=="Y" (
for /f "delims=" %%i in ('Type "%Report%"') do (
Call :MakeCopy "%%~i" "%Folder2Copy%\"
)
)
Call :Explorer "%Folder2Copy%\" & exit
If /I "%INPUT%"=="N" (
Exit
)
Goto :eof
::***************************************************************************************
:MakeCopy <Source> <Target>
If Not Exist "%~2\" MD "%~2\" (
if not exist "%2\%~n1" (
echo copying "%~1" to "%~2"
copy /N /B "%~1" "%~2" >>%Result2Copy% 2>&1
) else (
call :loop "%~1" "%~2"
)
)
::***************************************************************************************
:loop
set "fname=%2\%~n1(%cnt%)%~x1"
if exist "%fname%" set /a cnt+=1 && goto :loop
copy "%~1" "%fname%"
exit /b
::***************************************************************************************
:Explorer <file>
explorer.exe /e,/select,"%~1"
Goto :EOF
::***************************************************************************************

batch that copy list of filesnames from a .txt and generate another .txt

I start with this example: I have a file called concatlist.txt that contain a list of real .mxf files, for example
CONCATLIST.TXT
c:\myfolder\C0060.MXF
c:\myfolder\C0061.MXF
c:\myfolder\C0062.MXF
c:\myfolder\C0063.MXF
c:\myfolder\C0064.MXF
c:\myfolder\C0065.MXF
c:\myfolder\C0066.MXF
c:\myfolder\C0067.MXF
c:\myfolder\C0068.MXF
c:\myfolder\C0069.MXF
c:\myfolder\C0070.MXF
c:\myfolder\C0071.MXF
c:\myfolder\C0072.MXF
c:\myfolder\C0060.MXF
c:\myfolder\C0061.MXF
c:\myfolder\C0062.MXF
c:\myfolder\C0063.MXF
c:\myfolder\C0064.MXF
c:\myfolder\C0065.MXF
c:\myfolder\C0066.MXF
c:\myfolder\C0067.MXF
c:\myfolder\C0068.MXF
c:\myfolder\C0069.MXF
c:\myfolder\C0070.MXF
c:\myfolder\C0071.MXF
c:\myfolder\C0072.MXF
I would like create a batch script that from the concatlist.txt create a target.txt in wich each filename_and_pathfile is putted like this .txt file:
SetMemoryMax(16)
LoadPlugin("v:\automazioneclip\avisynth\plugins\LSMASHSource.dll")
videofile0 = LWLibavVideoSource("c:\myfolder\C0060.MXF")
audiofile0 = LWLibavAudioSource("c:\myfolder\C0060.MXF")
file0 = audiodub(videofile0,audiofile0)
videofile1 = LWLibavVideoSource("c:\myfolder\C0061.MXF")
audiofile1 = LWLibavAudioSource("c:\myfolder\C0061.MXF")
file1 = audiodub(videofile1,audiofile1)
videofile2 = LWLibavVideoSource("c:\myfolder\C0062.MXF")
audiofile2 = LWLibavAudioSource("c:\myfolder\C0062.MXF")
file2 = audiodub(videofile2,audiofile2)
videofile3 = LWLibavVideoSource("c:\myfolder\C0063.MXF")
audiofile3 = LWLibavAudioSource("c:\myfolder\C0063.MXF")
file3 = audiodub(videofile3,audiofile3)
videofile4 = LWLibavVideoSource("c:\myfolder\C0064.MXF")
audiofile4 = LWLibavAudioSource("c:\myfolder\C0064.MXF")
file4 = audiodub(videofile4,audiofile4)
videofile5 = LWLibavVideoSource("c:\myfolder\C0065.MXF")
audiofile5 = LWLibavAudioSource("c:\myfolder\C0065.MXF")
file5 = audiodub(videofile5,audiofile5)
videofile6 = LWLibavVideoSource("c:\myfolder\C0066.MXF")
audiofile6 = LWLibavAudioSource("c:\myfolder\C0066.MXF")
file6 = audiodub(videofile6,audiofile6)
videofile7 = LWLibavVideoSource("c:\myfolder\C0067.MXF")
audiofile7 = LWLibavAudioSource("c:\myfolder\C0067.MXF")
file7 = audiodub(videofile7,audiofile7)
videofile8 = LWLibavVideoSource("c:\myfolder\C0068.MXF")
audiofile8 = LWLibavAudioSource("c:\myfolder\C0068.MXF")
file8 = audiodub(videofile8,audiofile8)
videofile9 = LWLibavVideoSource("c:\myfolder\C0069.MXF")
audiofile9 = LWLibavAudioSource("c:\myfolder\C0069.MXF")
file9 = audiodub(videofile9,audiofile9)
videofile10 = LWLibavVideoSource("c:\myfolder\C0070.MXF")
audiofile10 = LWLibavAudioSource("c:\myfolder\C0070.MXF")
file10 = audiodub(videofile10,audiofile10)
videofile11 = LWLibavVideoSource("c:\myfolder\C0071.MXF")
audiofile11 = LWLibavAudioSource("c:\myfolder\C0071.MXF")
file11 = audiodub(videofile11,audiofile11)
videofile12 = LWLibavVideoSource("c:\myfolder\C0072.MXF")
audiofile12 = LWLibavAudioSource("c:\myfolder\C0072.MXF")
file12 = audiodub(videofile12,audiofile12)
file0++file1++file2++file3++file4++file5++file6++file7++file8++file9++file10++file11++file12
Another example:
assumed the concatList.txt is this
c:\cats\catsVideoA.MXF
c:\dogs\dogsVideoB.MXF
the batch should generate this target.txt:
SetMemoryMax(16)
LoadPlugin("v:\automazioneclip\avisynth\plugins\LSMASHSource.dll")
videofile0 = LWLibavVideoSource("c:\cats\catsVideoA.MXF")
audiofile0 = LWLibavAudioSource("c:\cats\catsVideoA.MXF")
file0 = audiodub(videofile0,audiofile0)
videofile1 = LWLibavVideoSource("c:\dogs\dogsVideoB.MXF")
audiofile1 = LWLibavAudioSource("c:\dogs\dogsVideoB.MXF")
file1 = audiodub(videofile1,audiofile1)
file0++file1
Test this code:
#echo off
setlocal enabledelayedexpansion
set num=0
(
echo SetMemoryMax(16^)
echo LoadPlugin("v:\automazioneclip\avisynth\plugins\LSMASHSource.dll"^)
for /f "usebackq delims=" %%a in ("CONCATLIST.TXT") do (
echo(
set line=!line!++file!num!
echo videofile!num! = LWLibavVideoSource("%%a"^)
echo audiofile!num! = LWLibavAudioSource("%%a"^)
echo file!num! = audiodub(videofile!num!,audiofile!num!^)
set /a num+=1
)
echo !line:~2!
)>"target.txt"
Here is a variant that can support an "unlimited" concatlist size. (not really unlimited, but a much bigger number than will ever be practical)
I also avoid delayed expansion so ! does not cause any problems in file paths.
#echo off
setlocal disableDelayedExpansion
call :createFile >target.txt
exit /b
:createFile
echo SetMemoryMax(16)
echo LoadPlugin("v:\automazioneclip\avisynth\plugins\LSMASHSource.dll")
for /f "tokens=1* delims=:" %%A in ('findstr /n "^" "concatlist.txt"') do (
echo(
echo videofile%%A = LWLibavVideoSource("%%B"^)
echo audiofile%%A = LWLibavAudioSource("%%B"^)
echo file%%A = audiodub(videofile%%A,audiofile%%A^)
set "cnt=%%A"
)
set /a cnt2=cnt-1
for /l %%N in (1 1 %cnt2%) do <nul set /p "=file%%N++"
echo file%cnt%
exit /b
EDIT
If you really insist that the numbering begin with 0 instead of 1, then it is best to revert back to using SET /A to keep track of the count.
#echo off
setlocal disableDelayedExpansion
call :createFile >target.txt
type target.txt
exit /b
:createFile
echo SetMemoryMax(16)
echo LoadPlugin("v:\automazioneclip\avisynth\plugins\LSMASHSource.dll")
set /a cnt=0
for /f "usebackq eol=: delims=" %%A in ("concatlist.txt") do (
echo(
setlocal enableDelayedExpansion
for %%N in (!cnt!) do (
endlocal
echo videofile%%N = LWLibavVideoSource("%%A"^)
echo audiofile%%N = LWLibavAudioSource("%%A"^)
echo file%%N = audiodub(videofile%%N,audiofile%%N^)
)
set /a cnt+=1
)
<nul set /p "=file0"
for /l %%N in (1 1 %cnt%) do <nul set /p "=++file%%N"
echo(
exit /b

Windows batch Nested for loop issue

I need to read a file in outer loop line by line, take this value and use it in inner loop. But currently I am able to read first line from this file and do some required processing in inner loop but outer loop runs only once.
Why does the outer loop run only once?
myfile.txt contains:
AWC00201
AWC00202
AWC00203
DDDD
#echo off
setlocal EnableDelayedExpansion
for /F %%D in (myfile.txt) do (
echo %D%
S:
cd \#vantage\AFG\AWC\AWCU\simulation\WRO_Regression_results\%%D
echo %%D
FOR /F %%i IN ('dir /b /ad-h /o-d') DO (
echo After Nested For
echo %%D
SET test=%%D
SET b=%%i
GOTO found
)
echo No subfolder found
goto done
:found
echo %D%
echo Most recent subfolder: %b%
cd %b%
echo %%D
find /c "O K" tooling.report
echo %D%
if %errorlevel% equ 1 goto notfound
echo found
goto done
:notfound
echo notfound
goto done
:done
echo %D%
echo now go up
echo !test!
echo %test%
)
pause
I am getting following output:
ECHO is off.
AWC00201
After Nested For
AWC00201
ECHO is off.
Most recent subfolder: 20141103_170658_wro_awc
%D
____________ TOOLING.REPORT: 0
ECHO is off.
notfound
ECHO is off.
now go up
AWC00201
AWC00201
Press any key to continue . . .
Your code has one big problem and one thing to change
The problem is that it is not possible to use goto while inside a for loop and keep the loop iterating. goto cancels the for looping.
The thing to change is your use of variables. You have the information you need inside the for replaceable parameters. Use them. Move the value to a variable when the replaceable parameters does not offer what you need, but this is not the case
#echo off
setlocal enableextensions disabledelayedexpansion
for /F "delims=" %%D in (myfile.txt) do (
cd /d "s:\#vantage\AFG\AWC\AWCU\simulation\WRO_Regression_results\%%D"
for /d %%a in (.) do echo Current folder is "%%~fa"
set "file="
FOR /F "delims=" %%i IN ('dir /b /ad-h /o-d 2 >nul ') DO if not defined file (
set "file=1"
echo subfolder found : %%i
find /c "O K" ".\%%i\tooling.report" >nul 2>nul
if errorlevel 1 (
echo O K found
) else (
echo O K not found or file does not exist
)
)
if not defined file (
echo subfolder not found
)
)
pause

Resources