Start concurrent batches with filename mask and wait for them to finish












0















I'm trying to start a fixed number of concurrent batch processes that have similar filenames, all in the same directory:



TestMe1.bat
TestMe2.bat
TestMe3.bat


All batches should start at the same time, and all should complete before the batch continues, e.g. a master.bat:



echo Starting batches

(
start "task1" cmd /C "TestMe1.bat"
start "task2" cmd /C "TestMe2.bat"
start "task3" cmd /C "TestMe3.bat"
) | pause

echo All batches have stopped and we can safely continue


I'm trying to find a way to start all batches in the directory that match TestMe*.bat, so that I don't have to craft a new master.bat file each time. Something like this, but, you know, working:



echo Starting batches

(
for /f "delims=" %%x in ('dir /b /a-d TestMe*.bat') do start "task" cmd /C "%%x"
) | pause

echo All batches have stopped and we can safely continue


Thanks to this and this for getting me this far.



Advice and ideas gratefully received!










share|improve this question



























    0















    I'm trying to start a fixed number of concurrent batch processes that have similar filenames, all in the same directory:



    TestMe1.bat
    TestMe2.bat
    TestMe3.bat


    All batches should start at the same time, and all should complete before the batch continues, e.g. a master.bat:



    echo Starting batches

    (
    start "task1" cmd /C "TestMe1.bat"
    start "task2" cmd /C "TestMe2.bat"
    start "task3" cmd /C "TestMe3.bat"
    ) | pause

    echo All batches have stopped and we can safely continue


    I'm trying to find a way to start all batches in the directory that match TestMe*.bat, so that I don't have to craft a new master.bat file each time. Something like this, but, you know, working:



    echo Starting batches

    (
    for /f "delims=" %%x in ('dir /b /a-d TestMe*.bat') do start "task" cmd /C "%%x"
    ) | pause

    echo All batches have stopped and we can safely continue


    Thanks to this and this for getting me this far.



    Advice and ideas gratefully received!










    share|improve this question

























      0












      0








      0








      I'm trying to start a fixed number of concurrent batch processes that have similar filenames, all in the same directory:



      TestMe1.bat
      TestMe2.bat
      TestMe3.bat


      All batches should start at the same time, and all should complete before the batch continues, e.g. a master.bat:



      echo Starting batches

      (
      start "task1" cmd /C "TestMe1.bat"
      start "task2" cmd /C "TestMe2.bat"
      start "task3" cmd /C "TestMe3.bat"
      ) | pause

      echo All batches have stopped and we can safely continue


      I'm trying to find a way to start all batches in the directory that match TestMe*.bat, so that I don't have to craft a new master.bat file each time. Something like this, but, you know, working:



      echo Starting batches

      (
      for /f "delims=" %%x in ('dir /b /a-d TestMe*.bat') do start "task" cmd /C "%%x"
      ) | pause

      echo All batches have stopped and we can safely continue


      Thanks to this and this for getting me this far.



      Advice and ideas gratefully received!










      share|improve this question














      I'm trying to start a fixed number of concurrent batch processes that have similar filenames, all in the same directory:



      TestMe1.bat
      TestMe2.bat
      TestMe3.bat


      All batches should start at the same time, and all should complete before the batch continues, e.g. a master.bat:



      echo Starting batches

      (
      start "task1" cmd /C "TestMe1.bat"
      start "task2" cmd /C "TestMe2.bat"
      start "task3" cmd /C "TestMe3.bat"
      ) | pause

      echo All batches have stopped and we can safely continue


      I'm trying to find a way to start all batches in the directory that match TestMe*.bat, so that I don't have to craft a new master.bat file each time. Something like this, but, you know, working:



      echo Starting batches

      (
      for /f "delims=" %%x in ('dir /b /a-d TestMe*.bat') do start "task" cmd /C "%%x"
      ) | pause

      echo All batches have stopped and we can safely continue


      Thanks to this and this for getting me this far.



      Advice and ideas gratefully received!







      batch-file concurrency wait






      share|improve this question













      share|improve this question











      share|improve this question




      share|improve this question










      asked Nov 23 '18 at 17:38









      DuodenalsalmonsDuodenalsalmons

      188139




      188139
























          2 Answers
          2






          active

          oldest

          votes


















          2














          First you have to understand how this special method of using pipe with the pause command works and why it can be used for waiting for multiple parallel processes.



          Taking your first working code sample as the starting point



          (
          start "task1" cmd /C "TestMe1.bat"
          start "task2" cmd /C "TestMe2.bat"
          start "task3" cmd /C "TestMe3.bat"
          ) | pause


          It works because each new instance of CMD which is invoked by the start command will be started in a new console with its stdout and stderr redirected to to that new console, so the outputs of the child CMDs will not be redirected to the pipe and so will not be consumed by the pause command which is waiting for input from the pipe.


          BUT,


          Still each of the processes have inherited the pipe handle, so the handle to the pipe will remain open as long as the child processes are alive.



          As a consequence the pause command in the right side of the pipe will remain active, waiting for input from the left side of the pipe until it receives input from the pipe(which will never happen) or all child processes have terminated and closed the handle to the pipe.



          So the main CMD instance which is executing your master batch file, is actually waiting for the pause command (right side of the pipe) to terminate which in turn is waiting for child processes (potential pipe writers) to terminate.



          Now it becomes clear why your second attempted code involving the FOR loop is not working.



          (
          for /f "delims=" %%x in ('dir /b /a-d TestMe*.bat') do start "task" cmd /C "%%x"
          ) | pause


          The FOR command inside the pipe is executed by the child CMD in command line mode, In this mode the command echoing in on by default, so every command inside the FOR body will be echoed to standard output(the pipe) before execution, which in turn feeds the pause command and terminate its process before even the first child process is created, Therefor the batch file execution continues without ever waiting for the child processes to finish.



          This can be easily resolved by putting the @ after do will turn the command echoing off inside the FOR body.



          (
          for /f "delims=" %%x in ('dir /b /a-d TestMe*.bat') do @start "task" cmd /C "%%x"
          ) | pause>nul


          You may also want to hide the output of pause command by redirecting it to nul






          share|improve this answer



















          • 1





            Great explanation, and a really simple fix too - thanks @sst

            – Duodenalsalmons
            Nov 26 '18 at 12:57






          • 1





            Thanks for the explanation, that's very interesting. I didn't really understand how it's supposed to work but now I do. So as far as I can tell, the trick is that ( ..... ) | command spawns processes with STDOUT redirected into STDIN pipe of the command. And although start directives all exit immidiately and cannot connect the pipe to another console, processes spawned that way still inherit its HANDLE. And until all of the HANDLEs to the input side of the pipe are closed the pipe cannot signal an EOF.

            – Jack White
            Nov 26 '18 at 22:48






          • 1





            @JackWhite, Yes that is correct, Theoretically even the processes that are spawned by start which creates a new console can write to the pipe if they could somehow be informed of the inherited pipe handle value and and were specifically designed to do so. For instance if you use start /b to create any process, its stdout will be set to the pipe handle so it automatically writes to the pipe. The pipe handle will be inherited and is usable by child processes regardless of their stdout being redirected or not.

            – sst
            Nov 27 '18 at 9:26



















          1














          EDIT: It seems I missed the point of this question. Despite that, I think I'll leave this here anyway for other people to find. Feel free to downvote though.





          Here are other suggestions on waiting for subordinate processes to complete.



          Your main process should periodically check if every subordinate processes is done. There is a multitude of ways of doing that. I'll name a few:



          Before that, please insert a delay between checks to not consume all CPU in a tight loop like this:



          timeout /t 1 /nobreak


          Marker files



          Make subordinate processes create or delete a file when they are about to finish



          You can create files like this:



          echo ANYTHING>FILENAME


          Main script should periodically check if those files exist like this:



          if exist FILENAME goto IT_EXISTS


          When all/none of the files exist your task is complete.



          To prevent clutter, create files in a %random% folder inside %temp% directory and pass its name to subordinates via arguments %1, %2 ...



          Check process existance by window title



          Run tasklist and parse its output to determine if your subordinate programs still run.



          Probably the easiest way is to use window name to filter out "your" processes.



          Start them like this:



          start "WINDOW_TITLE" "BATCH_FILE" ARGUMENTS


          then search for them like this:



          TASKLIST /fi "Windowtitle eq WINDOW_TITLE" | find ".exe"
          if "%errorlevel%" == "0" goto PROCESS_EXISTS


          if none are found your task is finished.



          Further information can be found at: A, B, C



          Check process existance by PID



          Instead of window title you can use processes' PID.



          To obtain it run your process with WMIC as described here



          External programs



          You can download or write an external program to facilitate inter-process communication. Examples include:




          • TCP server and clients with netcat

          • Use mkfifo from GnuWin32 coreutils to create a named pipe and use it

          • Windows semaphores and events via custom C/C#/AutoIT program

          • Utilities such as NirCmd and PsExec may simplify PID checking procedure


          ....and more



          If none of solutions work for you please edit the question to narrow down your query.






          share|improve this answer


























          • These are all good ideas, but the event-driven model works better for my purposes - thanks for your answer nonetheless

            – Duodenalsalmons
            Nov 26 '18 at 12:59











          Your Answer






          StackExchange.ifUsing("editor", function () {
          StackExchange.using("externalEditor", function () {
          StackExchange.using("snippets", function () {
          StackExchange.snippets.init();
          });
          });
          }, "code-snippets");

          StackExchange.ready(function() {
          var channelOptions = {
          tags: "".split(" "),
          id: "1"
          };
          initTagRenderer("".split(" "), "".split(" "), channelOptions);

          StackExchange.using("externalEditor", function() {
          // Have to fire editor after snippets, if snippets enabled
          if (StackExchange.settings.snippets.snippetsEnabled) {
          StackExchange.using("snippets", function() {
          createEditor();
          });
          }
          else {
          createEditor();
          }
          });

          function createEditor() {
          StackExchange.prepareEditor({
          heartbeatType: 'answer',
          autoActivateHeartbeat: false,
          convertImagesToLinks: true,
          noModals: true,
          showLowRepImageUploadWarning: true,
          reputationToPostImages: 10,
          bindNavPrevention: true,
          postfix: "",
          imageUploader: {
          brandingHtml: "Powered by u003ca class="icon-imgur-white" href="https://imgur.com/"u003eu003c/au003e",
          contentPolicyHtml: "User contributions licensed under u003ca href="https://creativecommons.org/licenses/by-sa/3.0/"u003ecc by-sa 3.0 with attribution requiredu003c/au003e u003ca href="https://stackoverflow.com/legal/content-policy"u003e(content policy)u003c/au003e",
          allowUrls: true
          },
          onDemand: true,
          discardSelector: ".discard-answer"
          ,immediatelyShowMarkdownHelp:true
          });


          }
          });














          draft saved

          draft discarded


















          StackExchange.ready(
          function () {
          StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53450963%2fstart-concurrent-batches-with-filename-mask-and-wait-for-them-to-finish%23new-answer', 'question_page');
          }
          );

          Post as a guest















          Required, but never shown

























          2 Answers
          2






          active

          oldest

          votes








          2 Answers
          2






          active

          oldest

          votes









          active

          oldest

          votes






          active

          oldest

          votes









          2














          First you have to understand how this special method of using pipe with the pause command works and why it can be used for waiting for multiple parallel processes.



          Taking your first working code sample as the starting point



          (
          start "task1" cmd /C "TestMe1.bat"
          start "task2" cmd /C "TestMe2.bat"
          start "task3" cmd /C "TestMe3.bat"
          ) | pause


          It works because each new instance of CMD which is invoked by the start command will be started in a new console with its stdout and stderr redirected to to that new console, so the outputs of the child CMDs will not be redirected to the pipe and so will not be consumed by the pause command which is waiting for input from the pipe.


          BUT,


          Still each of the processes have inherited the pipe handle, so the handle to the pipe will remain open as long as the child processes are alive.



          As a consequence the pause command in the right side of the pipe will remain active, waiting for input from the left side of the pipe until it receives input from the pipe(which will never happen) or all child processes have terminated and closed the handle to the pipe.



          So the main CMD instance which is executing your master batch file, is actually waiting for the pause command (right side of the pipe) to terminate which in turn is waiting for child processes (potential pipe writers) to terminate.



          Now it becomes clear why your second attempted code involving the FOR loop is not working.



          (
          for /f "delims=" %%x in ('dir /b /a-d TestMe*.bat') do start "task" cmd /C "%%x"
          ) | pause


          The FOR command inside the pipe is executed by the child CMD in command line mode, In this mode the command echoing in on by default, so every command inside the FOR body will be echoed to standard output(the pipe) before execution, which in turn feeds the pause command and terminate its process before even the first child process is created, Therefor the batch file execution continues without ever waiting for the child processes to finish.



          This can be easily resolved by putting the @ after do will turn the command echoing off inside the FOR body.



          (
          for /f "delims=" %%x in ('dir /b /a-d TestMe*.bat') do @start "task" cmd /C "%%x"
          ) | pause>nul


          You may also want to hide the output of pause command by redirecting it to nul






          share|improve this answer



















          • 1





            Great explanation, and a really simple fix too - thanks @sst

            – Duodenalsalmons
            Nov 26 '18 at 12:57






          • 1





            Thanks for the explanation, that's very interesting. I didn't really understand how it's supposed to work but now I do. So as far as I can tell, the trick is that ( ..... ) | command spawns processes with STDOUT redirected into STDIN pipe of the command. And although start directives all exit immidiately and cannot connect the pipe to another console, processes spawned that way still inherit its HANDLE. And until all of the HANDLEs to the input side of the pipe are closed the pipe cannot signal an EOF.

            – Jack White
            Nov 26 '18 at 22:48






          • 1





            @JackWhite, Yes that is correct, Theoretically even the processes that are spawned by start which creates a new console can write to the pipe if they could somehow be informed of the inherited pipe handle value and and were specifically designed to do so. For instance if you use start /b to create any process, its stdout will be set to the pipe handle so it automatically writes to the pipe. The pipe handle will be inherited and is usable by child processes regardless of their stdout being redirected or not.

            – sst
            Nov 27 '18 at 9:26
















          2














          First you have to understand how this special method of using pipe with the pause command works and why it can be used for waiting for multiple parallel processes.



          Taking your first working code sample as the starting point



          (
          start "task1" cmd /C "TestMe1.bat"
          start "task2" cmd /C "TestMe2.bat"
          start "task3" cmd /C "TestMe3.bat"
          ) | pause


          It works because each new instance of CMD which is invoked by the start command will be started in a new console with its stdout and stderr redirected to to that new console, so the outputs of the child CMDs will not be redirected to the pipe and so will not be consumed by the pause command which is waiting for input from the pipe.


          BUT,


          Still each of the processes have inherited the pipe handle, so the handle to the pipe will remain open as long as the child processes are alive.



          As a consequence the pause command in the right side of the pipe will remain active, waiting for input from the left side of the pipe until it receives input from the pipe(which will never happen) or all child processes have terminated and closed the handle to the pipe.



          So the main CMD instance which is executing your master batch file, is actually waiting for the pause command (right side of the pipe) to terminate which in turn is waiting for child processes (potential pipe writers) to terminate.



          Now it becomes clear why your second attempted code involving the FOR loop is not working.



          (
          for /f "delims=" %%x in ('dir /b /a-d TestMe*.bat') do start "task" cmd /C "%%x"
          ) | pause


          The FOR command inside the pipe is executed by the child CMD in command line mode, In this mode the command echoing in on by default, so every command inside the FOR body will be echoed to standard output(the pipe) before execution, which in turn feeds the pause command and terminate its process before even the first child process is created, Therefor the batch file execution continues without ever waiting for the child processes to finish.



          This can be easily resolved by putting the @ after do will turn the command echoing off inside the FOR body.



          (
          for /f "delims=" %%x in ('dir /b /a-d TestMe*.bat') do @start "task" cmd /C "%%x"
          ) | pause>nul


          You may also want to hide the output of pause command by redirecting it to nul






          share|improve this answer



















          • 1





            Great explanation, and a really simple fix too - thanks @sst

            – Duodenalsalmons
            Nov 26 '18 at 12:57






          • 1





            Thanks for the explanation, that's very interesting. I didn't really understand how it's supposed to work but now I do. So as far as I can tell, the trick is that ( ..... ) | command spawns processes with STDOUT redirected into STDIN pipe of the command. And although start directives all exit immidiately and cannot connect the pipe to another console, processes spawned that way still inherit its HANDLE. And until all of the HANDLEs to the input side of the pipe are closed the pipe cannot signal an EOF.

            – Jack White
            Nov 26 '18 at 22:48






          • 1





            @JackWhite, Yes that is correct, Theoretically even the processes that are spawned by start which creates a new console can write to the pipe if they could somehow be informed of the inherited pipe handle value and and were specifically designed to do so. For instance if you use start /b to create any process, its stdout will be set to the pipe handle so it automatically writes to the pipe. The pipe handle will be inherited and is usable by child processes regardless of their stdout being redirected or not.

            – sst
            Nov 27 '18 at 9:26














          2












          2








          2







          First you have to understand how this special method of using pipe with the pause command works and why it can be used for waiting for multiple parallel processes.



          Taking your first working code sample as the starting point



          (
          start "task1" cmd /C "TestMe1.bat"
          start "task2" cmd /C "TestMe2.bat"
          start "task3" cmd /C "TestMe3.bat"
          ) | pause


          It works because each new instance of CMD which is invoked by the start command will be started in a new console with its stdout and stderr redirected to to that new console, so the outputs of the child CMDs will not be redirected to the pipe and so will not be consumed by the pause command which is waiting for input from the pipe.


          BUT,


          Still each of the processes have inherited the pipe handle, so the handle to the pipe will remain open as long as the child processes are alive.



          As a consequence the pause command in the right side of the pipe will remain active, waiting for input from the left side of the pipe until it receives input from the pipe(which will never happen) or all child processes have terminated and closed the handle to the pipe.



          So the main CMD instance which is executing your master batch file, is actually waiting for the pause command (right side of the pipe) to terminate which in turn is waiting for child processes (potential pipe writers) to terminate.



          Now it becomes clear why your second attempted code involving the FOR loop is not working.



          (
          for /f "delims=" %%x in ('dir /b /a-d TestMe*.bat') do start "task" cmd /C "%%x"
          ) | pause


          The FOR command inside the pipe is executed by the child CMD in command line mode, In this mode the command echoing in on by default, so every command inside the FOR body will be echoed to standard output(the pipe) before execution, which in turn feeds the pause command and terminate its process before even the first child process is created, Therefor the batch file execution continues without ever waiting for the child processes to finish.



          This can be easily resolved by putting the @ after do will turn the command echoing off inside the FOR body.



          (
          for /f "delims=" %%x in ('dir /b /a-d TestMe*.bat') do @start "task" cmd /C "%%x"
          ) | pause>nul


          You may also want to hide the output of pause command by redirecting it to nul






          share|improve this answer













          First you have to understand how this special method of using pipe with the pause command works and why it can be used for waiting for multiple parallel processes.



          Taking your first working code sample as the starting point



          (
          start "task1" cmd /C "TestMe1.bat"
          start "task2" cmd /C "TestMe2.bat"
          start "task3" cmd /C "TestMe3.bat"
          ) | pause


          It works because each new instance of CMD which is invoked by the start command will be started in a new console with its stdout and stderr redirected to to that new console, so the outputs of the child CMDs will not be redirected to the pipe and so will not be consumed by the pause command which is waiting for input from the pipe.


          BUT,


          Still each of the processes have inherited the pipe handle, so the handle to the pipe will remain open as long as the child processes are alive.



          As a consequence the pause command in the right side of the pipe will remain active, waiting for input from the left side of the pipe until it receives input from the pipe(which will never happen) or all child processes have terminated and closed the handle to the pipe.



          So the main CMD instance which is executing your master batch file, is actually waiting for the pause command (right side of the pipe) to terminate which in turn is waiting for child processes (potential pipe writers) to terminate.



          Now it becomes clear why your second attempted code involving the FOR loop is not working.



          (
          for /f "delims=" %%x in ('dir /b /a-d TestMe*.bat') do start "task" cmd /C "%%x"
          ) | pause


          The FOR command inside the pipe is executed by the child CMD in command line mode, In this mode the command echoing in on by default, so every command inside the FOR body will be echoed to standard output(the pipe) before execution, which in turn feeds the pause command and terminate its process before even the first child process is created, Therefor the batch file execution continues without ever waiting for the child processes to finish.



          This can be easily resolved by putting the @ after do will turn the command echoing off inside the FOR body.



          (
          for /f "delims=" %%x in ('dir /b /a-d TestMe*.bat') do @start "task" cmd /C "%%x"
          ) | pause>nul


          You may also want to hide the output of pause command by redirecting it to nul







          share|improve this answer












          share|improve this answer



          share|improve this answer










          answered Nov 24 '18 at 5:58









          sstsst

          7821510




          7821510








          • 1





            Great explanation, and a really simple fix too - thanks @sst

            – Duodenalsalmons
            Nov 26 '18 at 12:57






          • 1





            Thanks for the explanation, that's very interesting. I didn't really understand how it's supposed to work but now I do. So as far as I can tell, the trick is that ( ..... ) | command spawns processes with STDOUT redirected into STDIN pipe of the command. And although start directives all exit immidiately and cannot connect the pipe to another console, processes spawned that way still inherit its HANDLE. And until all of the HANDLEs to the input side of the pipe are closed the pipe cannot signal an EOF.

            – Jack White
            Nov 26 '18 at 22:48






          • 1





            @JackWhite, Yes that is correct, Theoretically even the processes that are spawned by start which creates a new console can write to the pipe if they could somehow be informed of the inherited pipe handle value and and were specifically designed to do so. For instance if you use start /b to create any process, its stdout will be set to the pipe handle so it automatically writes to the pipe. The pipe handle will be inherited and is usable by child processes regardless of their stdout being redirected or not.

            – sst
            Nov 27 '18 at 9:26














          • 1





            Great explanation, and a really simple fix too - thanks @sst

            – Duodenalsalmons
            Nov 26 '18 at 12:57






          • 1





            Thanks for the explanation, that's very interesting. I didn't really understand how it's supposed to work but now I do. So as far as I can tell, the trick is that ( ..... ) | command spawns processes with STDOUT redirected into STDIN pipe of the command. And although start directives all exit immidiately and cannot connect the pipe to another console, processes spawned that way still inherit its HANDLE. And until all of the HANDLEs to the input side of the pipe are closed the pipe cannot signal an EOF.

            – Jack White
            Nov 26 '18 at 22:48






          • 1





            @JackWhite, Yes that is correct, Theoretically even the processes that are spawned by start which creates a new console can write to the pipe if they could somehow be informed of the inherited pipe handle value and and were specifically designed to do so. For instance if you use start /b to create any process, its stdout will be set to the pipe handle so it automatically writes to the pipe. The pipe handle will be inherited and is usable by child processes regardless of their stdout being redirected or not.

            – sst
            Nov 27 '18 at 9:26








          1




          1





          Great explanation, and a really simple fix too - thanks @sst

          – Duodenalsalmons
          Nov 26 '18 at 12:57





          Great explanation, and a really simple fix too - thanks @sst

          – Duodenalsalmons
          Nov 26 '18 at 12:57




          1




          1





          Thanks for the explanation, that's very interesting. I didn't really understand how it's supposed to work but now I do. So as far as I can tell, the trick is that ( ..... ) | command spawns processes with STDOUT redirected into STDIN pipe of the command. And although start directives all exit immidiately and cannot connect the pipe to another console, processes spawned that way still inherit its HANDLE. And until all of the HANDLEs to the input side of the pipe are closed the pipe cannot signal an EOF.

          – Jack White
          Nov 26 '18 at 22:48





          Thanks for the explanation, that's very interesting. I didn't really understand how it's supposed to work but now I do. So as far as I can tell, the trick is that ( ..... ) | command spawns processes with STDOUT redirected into STDIN pipe of the command. And although start directives all exit immidiately and cannot connect the pipe to another console, processes spawned that way still inherit its HANDLE. And until all of the HANDLEs to the input side of the pipe are closed the pipe cannot signal an EOF.

          – Jack White
          Nov 26 '18 at 22:48




          1




          1





          @JackWhite, Yes that is correct, Theoretically even the processes that are spawned by start which creates a new console can write to the pipe if they could somehow be informed of the inherited pipe handle value and and were specifically designed to do so. For instance if you use start /b to create any process, its stdout will be set to the pipe handle so it automatically writes to the pipe. The pipe handle will be inherited and is usable by child processes regardless of their stdout being redirected or not.

          – sst
          Nov 27 '18 at 9:26





          @JackWhite, Yes that is correct, Theoretically even the processes that are spawned by start which creates a new console can write to the pipe if they could somehow be informed of the inherited pipe handle value and and were specifically designed to do so. For instance if you use start /b to create any process, its stdout will be set to the pipe handle so it automatically writes to the pipe. The pipe handle will be inherited and is usable by child processes regardless of their stdout being redirected or not.

          – sst
          Nov 27 '18 at 9:26













          1














          EDIT: It seems I missed the point of this question. Despite that, I think I'll leave this here anyway for other people to find. Feel free to downvote though.





          Here are other suggestions on waiting for subordinate processes to complete.



          Your main process should periodically check if every subordinate processes is done. There is a multitude of ways of doing that. I'll name a few:



          Before that, please insert a delay between checks to not consume all CPU in a tight loop like this:



          timeout /t 1 /nobreak


          Marker files



          Make subordinate processes create or delete a file when they are about to finish



          You can create files like this:



          echo ANYTHING>FILENAME


          Main script should periodically check if those files exist like this:



          if exist FILENAME goto IT_EXISTS


          When all/none of the files exist your task is complete.



          To prevent clutter, create files in a %random% folder inside %temp% directory and pass its name to subordinates via arguments %1, %2 ...



          Check process existance by window title



          Run tasklist and parse its output to determine if your subordinate programs still run.



          Probably the easiest way is to use window name to filter out "your" processes.



          Start them like this:



          start "WINDOW_TITLE" "BATCH_FILE" ARGUMENTS


          then search for them like this:



          TASKLIST /fi "Windowtitle eq WINDOW_TITLE" | find ".exe"
          if "%errorlevel%" == "0" goto PROCESS_EXISTS


          if none are found your task is finished.



          Further information can be found at: A, B, C



          Check process existance by PID



          Instead of window title you can use processes' PID.



          To obtain it run your process with WMIC as described here



          External programs



          You can download or write an external program to facilitate inter-process communication. Examples include:




          • TCP server and clients with netcat

          • Use mkfifo from GnuWin32 coreutils to create a named pipe and use it

          • Windows semaphores and events via custom C/C#/AutoIT program

          • Utilities such as NirCmd and PsExec may simplify PID checking procedure


          ....and more



          If none of solutions work for you please edit the question to narrow down your query.






          share|improve this answer


























          • These are all good ideas, but the event-driven model works better for my purposes - thanks for your answer nonetheless

            – Duodenalsalmons
            Nov 26 '18 at 12:59
















          1














          EDIT: It seems I missed the point of this question. Despite that, I think I'll leave this here anyway for other people to find. Feel free to downvote though.





          Here are other suggestions on waiting for subordinate processes to complete.



          Your main process should periodically check if every subordinate processes is done. There is a multitude of ways of doing that. I'll name a few:



          Before that, please insert a delay between checks to not consume all CPU in a tight loop like this:



          timeout /t 1 /nobreak


          Marker files



          Make subordinate processes create or delete a file when they are about to finish



          You can create files like this:



          echo ANYTHING>FILENAME


          Main script should periodically check if those files exist like this:



          if exist FILENAME goto IT_EXISTS


          When all/none of the files exist your task is complete.



          To prevent clutter, create files in a %random% folder inside %temp% directory and pass its name to subordinates via arguments %1, %2 ...



          Check process existance by window title



          Run tasklist and parse its output to determine if your subordinate programs still run.



          Probably the easiest way is to use window name to filter out "your" processes.



          Start them like this:



          start "WINDOW_TITLE" "BATCH_FILE" ARGUMENTS


          then search for them like this:



          TASKLIST /fi "Windowtitle eq WINDOW_TITLE" | find ".exe"
          if "%errorlevel%" == "0" goto PROCESS_EXISTS


          if none are found your task is finished.



          Further information can be found at: A, B, C



          Check process existance by PID



          Instead of window title you can use processes' PID.



          To obtain it run your process with WMIC as described here



          External programs



          You can download or write an external program to facilitate inter-process communication. Examples include:




          • TCP server and clients with netcat

          • Use mkfifo from GnuWin32 coreutils to create a named pipe and use it

          • Windows semaphores and events via custom C/C#/AutoIT program

          • Utilities such as NirCmd and PsExec may simplify PID checking procedure


          ....and more



          If none of solutions work for you please edit the question to narrow down your query.






          share|improve this answer


























          • These are all good ideas, but the event-driven model works better for my purposes - thanks for your answer nonetheless

            – Duodenalsalmons
            Nov 26 '18 at 12:59














          1












          1








          1







          EDIT: It seems I missed the point of this question. Despite that, I think I'll leave this here anyway for other people to find. Feel free to downvote though.





          Here are other suggestions on waiting for subordinate processes to complete.



          Your main process should periodically check if every subordinate processes is done. There is a multitude of ways of doing that. I'll name a few:



          Before that, please insert a delay between checks to not consume all CPU in a tight loop like this:



          timeout /t 1 /nobreak


          Marker files



          Make subordinate processes create or delete a file when they are about to finish



          You can create files like this:



          echo ANYTHING>FILENAME


          Main script should periodically check if those files exist like this:



          if exist FILENAME goto IT_EXISTS


          When all/none of the files exist your task is complete.



          To prevent clutter, create files in a %random% folder inside %temp% directory and pass its name to subordinates via arguments %1, %2 ...



          Check process existance by window title



          Run tasklist and parse its output to determine if your subordinate programs still run.



          Probably the easiest way is to use window name to filter out "your" processes.



          Start them like this:



          start "WINDOW_TITLE" "BATCH_FILE" ARGUMENTS


          then search for them like this:



          TASKLIST /fi "Windowtitle eq WINDOW_TITLE" | find ".exe"
          if "%errorlevel%" == "0" goto PROCESS_EXISTS


          if none are found your task is finished.



          Further information can be found at: A, B, C



          Check process existance by PID



          Instead of window title you can use processes' PID.



          To obtain it run your process with WMIC as described here



          External programs



          You can download or write an external program to facilitate inter-process communication. Examples include:




          • TCP server and clients with netcat

          • Use mkfifo from GnuWin32 coreutils to create a named pipe and use it

          • Windows semaphores and events via custom C/C#/AutoIT program

          • Utilities such as NirCmd and PsExec may simplify PID checking procedure


          ....and more



          If none of solutions work for you please edit the question to narrow down your query.






          share|improve this answer















          EDIT: It seems I missed the point of this question. Despite that, I think I'll leave this here anyway for other people to find. Feel free to downvote though.





          Here are other suggestions on waiting for subordinate processes to complete.



          Your main process should periodically check if every subordinate processes is done. There is a multitude of ways of doing that. I'll name a few:



          Before that, please insert a delay between checks to not consume all CPU in a tight loop like this:



          timeout /t 1 /nobreak


          Marker files



          Make subordinate processes create or delete a file when they are about to finish



          You can create files like this:



          echo ANYTHING>FILENAME


          Main script should periodically check if those files exist like this:



          if exist FILENAME goto IT_EXISTS


          When all/none of the files exist your task is complete.



          To prevent clutter, create files in a %random% folder inside %temp% directory and pass its name to subordinates via arguments %1, %2 ...



          Check process existance by window title



          Run tasklist and parse its output to determine if your subordinate programs still run.



          Probably the easiest way is to use window name to filter out "your" processes.



          Start them like this:



          start "WINDOW_TITLE" "BATCH_FILE" ARGUMENTS


          then search for them like this:



          TASKLIST /fi "Windowtitle eq WINDOW_TITLE" | find ".exe"
          if "%errorlevel%" == "0" goto PROCESS_EXISTS


          if none are found your task is finished.



          Further information can be found at: A, B, C



          Check process existance by PID



          Instead of window title you can use processes' PID.



          To obtain it run your process with WMIC as described here



          External programs



          You can download or write an external program to facilitate inter-process communication. Examples include:




          • TCP server and clients with netcat

          • Use mkfifo from GnuWin32 coreutils to create a named pipe and use it

          • Windows semaphores and events via custom C/C#/AutoIT program

          • Utilities such as NirCmd and PsExec may simplify PID checking procedure


          ....and more



          If none of solutions work for you please edit the question to narrow down your query.







          share|improve this answer














          share|improve this answer



          share|improve this answer








          edited Nov 26 '18 at 22:57

























          answered Nov 23 '18 at 22:07









          Jack WhiteJack White

          33416




          33416













          • These are all good ideas, but the event-driven model works better for my purposes - thanks for your answer nonetheless

            – Duodenalsalmons
            Nov 26 '18 at 12:59



















          • These are all good ideas, but the event-driven model works better for my purposes - thanks for your answer nonetheless

            – Duodenalsalmons
            Nov 26 '18 at 12:59

















          These are all good ideas, but the event-driven model works better for my purposes - thanks for your answer nonetheless

          – Duodenalsalmons
          Nov 26 '18 at 12:59





          These are all good ideas, but the event-driven model works better for my purposes - thanks for your answer nonetheless

          – Duodenalsalmons
          Nov 26 '18 at 12:59


















          draft saved

          draft discarded




















































          Thanks for contributing an answer to Stack Overflow!


          • Please be sure to answer the question. Provide details and share your research!

          But avoid



          • Asking for help, clarification, or responding to other answers.

          • Making statements based on opinion; back them up with references or personal experience.


          To learn more, see our tips on writing great answers.




          draft saved


          draft discarded














          StackExchange.ready(
          function () {
          StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53450963%2fstart-concurrent-batches-with-filename-mask-and-wait-for-them-to-finish%23new-answer', 'question_page');
          }
          );

          Post as a guest















          Required, but never shown





















































          Required, but never shown














          Required, but never shown












          Required, but never shown







          Required, but never shown

































          Required, but never shown














          Required, but never shown












          Required, but never shown







          Required, but never shown







          Popular posts from this blog

          Wiesbaden

          Marschland

          Dieringhausen