Module: wine
Branch: master
Commit: 141e33b845bff271fd8aebdd8ec24b32a95be454
URL: http://source.winehq.org/git/wine.git/?a=commit;h=141e33b845bff271fd8aebdd8…
Author: Jason Edmeades <jason(a)edmeades.me.uk>
Date: Tue Sep 4 21:11:51 2012 +0100
cmd: More generic zero iteration for loop fix.
---
programs/cmd/builtins.c | 23 +++++++++++++++++------
programs/cmd/tests/test_builtins.cmd | 24 +++++++++++++++++++++---
programs/cmd/tests/test_builtins.cmd.exp | 9 ++++++---
3 files changed, 44 insertions(+), 12 deletions(-)
diff --git a/programs/cmd/builtins.c b/programs/cmd/builtins.c
index b2546d4..4ce78f7 100644
--- a/programs/cmd/builtins.c
+++ b/programs/cmd/builtins.c
@@ -1084,6 +1084,7 @@ void WCMD_for (WCHAR *p, CMD_LIST **cmdList) {
BOOL expandDirs = FALSE;
BOOL useNumbers = FALSE;
BOOL doFileset = FALSE;
+ BOOL doExecuted = FALSE; /* Has the 'do' part been executed */
LONG numbers[3] = {0,0,0}; /* Defaults to 0 in native */
int itemNum;
CMD_LIST *thisCmdStart;
@@ -1233,6 +1234,7 @@ void WCMD_for (WCHAR *p, CMD_LIST **cmdList) {
{
thisCmdStart = cmdStart;
WINE_TRACE("Processing FOR filename %s\n", wine_dbgstr_w(fd.cFileName));
+ doExecuted = TRUE;
WCMD_part_execute (&thisCmdStart, firstCmd, variable,
fd.cFileName, FALSE, TRUE);
}
@@ -1241,6 +1243,7 @@ void WCMD_for (WCHAR *p, CMD_LIST **cmdList) {
FindClose (hff);
}
} else {
+ doExecuted = TRUE;
WCMD_part_execute(&thisCmdStart, firstCmd, variable, item, FALSE, TRUE);
}
@@ -1310,6 +1313,7 @@ void WCMD_for (WCHAR *p, CMD_LIST **cmdList) {
/* FIXME: The following should be moved into its own routine and
reused for the string literal parsing below */
thisCmdStart = cmdStart;
+ doExecuted = TRUE;
WCMD_part_execute(&thisCmdStart, firstCmd, variable, parm, FALSE, TRUE);
cmdEnd = thisCmdStart;
}
@@ -1340,6 +1344,7 @@ void WCMD_for (WCHAR *p, CMD_LIST **cmdList) {
/* FIXME: The following should be moved into its own routine and
reused for the string literal parsing below */
thisCmdStart = cmdStart;
+ doExecuted = TRUE;
WCMD_part_execute(&thisCmdStart, firstCmd, variable, parm, FALSE, TRUE);
cmdEnd = thisCmdStart;
}
@@ -1369,17 +1374,23 @@ void WCMD_for (WCHAR *p, CMD_LIST **cmdList) {
WINE_TRACE("Processing FOR number %s\n", wine_dbgstr_w(thisNum));
thisCmdStart = cmdStart;
+ doExecuted = TRUE;
WCMD_part_execute(&thisCmdStart, firstCmd, variable, thisNum, FALSE, TRUE);
}
-
- /* Now skip over the subsequent commands if we did not perform the for loop */
- if (thisCmdStart == cmdStart) {
- WINE_TRACE("Skipping for loop commands due to no valid iterations\n");
- WCMD_part_execute(&thisCmdStart, firstCmd, variable, thisNum, FALSE, FALSE);
- }
cmdEnd = thisCmdStart;
}
+ /* Now skip over the do part if we did not perform the for loop so far.
+ We store in cmdEnd the next command after the do block, but we only
+ know this if something was run. If it has not been, we need to calculate
+ it. */
+ if (!doExecuted) {
+ thisCmdStart = cmdStart;
+ WINE_TRACE("Skipping for loop commands due to no valid iterations\n");
+ WCMD_part_execute(&thisCmdStart, firstCmd, NULL, NULL, FALSE, FALSE);
+ cmdEnd = thisCmdStart;
+ }
+
/* When the loop ends, either something like a GOTO or EXIT /b has terminated
all processing, OR it should be pointing to the end of && processing OR
it should be pointing at the NULL end of bracket for the DO. The return
diff --git a/programs/cmd/tests/test_builtins.cmd b/programs/cmd/tests/test_builtins.cmd
index 093cc23..77086ed 100644
--- a/programs/cmd/tests/test_builtins.cmd
+++ b/programs/cmd/tests/test_builtins.cmd
@@ -643,9 +643,27 @@ echo > bazbaz
echo --- basic wildcards
for %%i in (ba*) do echo %%i
echo --- for /d
-for /d %%i in (baz foo bar) do echo %%i
-rem FIXME for /d incorrectly parses when wildcards are used
-rem for /d %%i in (bazb*) do echo %%i
+for /d %%i in (baz foo bar) do echo %%i 2>&1
+rem Confirm we dont match files:
+for /d %%i in (bazb*) do echo %%i 2>&1
+for /d %%i in (bazb2*) do echo %%i 2>&1
+rem Show we pass through non wildcards
+for /d %%i in (PASSED) do echo %%i
+for /d %%i in (xxx) do (
+ echo %%i - Should be xxx
+ echo Expected second line
+)
+rem Show we issue no messages on failures
+for /d %%i in (FAILED?) do echo %%i 2>&1
+for /d %%i in (FAILED?) do (
+ echo %%i - Unexpected!
+ echo FAILED Unexpected second line
+)
+for /d %%i in (FAILED*) do echo %%i 2>&1
+for /d %%i in (FAILED*) do (
+ echo %%i - Unexpected!
+ echo FAILED Unexpected second line
+)
rem FIXME can't test wildcard expansion here since it's listed in directory
rem order, and not in alphabetic order.
rem Proper testing would need a currently missing "sort" program implementation.
diff --git a/programs/cmd/tests/test_builtins.cmd.exp b/programs/cmd/tests/test_builtins.cmd.exp
index 93b11e5..fe4c30c 100644
--- a/programs/cmd/tests/test_builtins.cmd.exp
+++ b/programs/cmd/tests/test_builtins.cmd.exp
@@ -455,9 +455,12 @@ C
--- basic wildcards
bazbaz
--- for /d
-baz
-foo
-bar
+baz@space@
+foo@space@
+bar@space@
+PASSED
+xxx - Should be xxx
+Expected second line
--- for /L
1
3