Batch that runs a timer in the background. How? - command-line

I was wondering if theres a way to make a batch file that uses a timer script (such as the TIMEOUT command) and while the timer is running, make the batch file do other processes. But when the timer runs out, then exit. (Or carry out another small process) I know this means that te batch file would have to run multiple processes at once, i just want to know if its possible somehow.
Any ideas?

You can use start /b cmd /c myTimeout.bat
This starts a new application in the same window (start /?)
With this mechanism you should be able do multiple jobs at the same time
EDIT
For a simple timeout this seems to be a bit oversized.
For a timeout of 6 seconds you can use something like
set startTime=%time%
call :timeToMs startMs startTime
set /a timeoutAt=startMs + 6000
:loop
... wait for something, like a file is created, or a CD is inserted
if job_is_ready goto :leaveTheLoop
REM Test if the timeout is reached
set currentTime=%time%
call :timeToMs nowMs currentTime
if nowMs GTR timeoutAt goto :leaveTheLoop
goto :loop
:leaveTheLoop
It fits better for real parallel jobs, like a display job and a key-input job for a game.

modified the code from jeb so that it works:
#echo off
set /A startMs=10*%time:~9,2%+1000*%time:~6,2%+60000*%time:~3,2%+3600000*%time:~0,2%
REM the 6000 in the next line is how many milliseconds of a delay you want
set /a timeoutAt=%startMs%+6000
:loop
REM 'passive' code here:
REM Test if the timeout is reached
2>NUL set /A nowMs=10*%time:~9,2%+1000*%time:~6,2%+60000*%time:~3,2%+3600000*%time:~0,2%
if /I %nowMs% GTR %timeoutAt% goto leaveTheLoop
goto loop
:leaveTheLoop
REM do the things you want to do when the timer ends

Related

Power shell script to clear RDP connection history from registry

I am new to Powershell but I have stuck in one place that is elaborate in the following details.
I want to perform a PowerShell script in which it will delete the RDP connection history from the registry (MRU number) but it will not delete all history, first, it will check one by one file and ask for approving whether to delete or not then deletion process will start. and after completion of the deletion process, it will restart the server again.
The following syntax will cycle through all 10 possible entries and ask you Y/N to delete them individually. Note that Windows only retains a max of 10 entries. Also note that Windows also retains similar data in "\documents\default.rdp", so this file should be deleted as part of your process.
#echo off
SET count=0
:AGAIN
reg query "HKEY_CURRENT_USER\Software\Microsoft\Terminal Server Client\Default" /s | findstr "MRU%count%"
if %errorlevel% EQU 0 (reg delete "HKEY_CURRENT_USER\Software\Microsoft\Terminal Server Client\Default" /v "MRU%count%") ELSE (goto ExitScript)
set /a count+=1
if %count% GEQ 10 GOTO ExitScript
GOTO AGAIN
:ExitScript

How to stop counting of timeout automatically if command finishes earlier?

In my script I'm using timeout to set a maximum timelimit for executing a command.
start 7z.exe t %%f
if errorlevel 2 (DEL %%f & echo File broken. Reload File!)
timeout /t 3600
If the execution lasts longer than an hour the timeout should break the execution. That's working without any problems.
But how can I ignore the timeout counting and proceed my script automatically if the command finishes before the timestamp?
As curretly written, start command without /W switch does not affect/change errorlevel! Proof:
==> hfhgf
'hfhgf' is not recognized as an internal or external command,
operable program or batch file.
==> echo %errorlevel%
9009
==> start "" ping.exe localhost
==> echo %errorlevel%
9009
==> start "" /W ping.exe localhost
==> echo %errorlevel%
0
Use /W or /WAIT switch (start application and wait for it to terminate) and remove all that timeout line as follows. I guess that your code snippet could be do part of a for loop:
for %%f in (*.zip) do (
(call )
start "" /W 7z.exe t "%%f"
if errorlevel 2 (
echo File broken. Reload File %%f
DEL "%%f"
)
)
On (call ) explanation, see Dave Benham's reply to setting ERRORLEVEL to 0 question:
If you want to force the errorlevel to 0, then you can use this
totally non-intuitive, but very effective syntax: (call ). The space
after call is critical. If you want to set the errorlevel to 1, you
can use (call). It is critical that there not be any space after
call.

Make batch file only work on a specific date

So I want to make a program which only works on the Christmas day.
If you try to open the file on Christmas day it would say: for example Merry christmas!
and if you are trying to open it on any other day, it would just say: Please come back later.
if it needs to be a batch, try this, I cannot test it. Don't have Windows. It would be much easier and infinitly prettier to do it in java or the like..
IMPORTANT: you might have to adjust the order of day and month, depends on the locale of your system! Maybe even the delims. There is a way to read that from the registry.
read here: http://www.robvanderwoude.com/datetimentparse.php
#ECHO OFF
FOR /F "tokens=*" %%A IN ('DATE/T') DO FOR %%B IN (%%A) DO SET Today=%%B
FOR /F "tokens=1-3 delims=/-" %%A IN ("%Today%") DO (
SET Day=%%A
SET Month=%%B
SET Year=%%C
)
if "%Day%;%Month%"=="24;12" GOTO :XMAS
echo Please come back later.
goto :eof
:XMAS
Merry christmas
You could just do this:
#echo off
set errorlevel=1
:: This is the base script for your example (only line that needs editing)
set /a day=25, month=12
if "%date:~4,2%:%date:~7,2%" EQU "%day%:%month%" GOTO :start
Echo Please Come Back Later
Exit/b 2
:: If Errorlevel=1 the program crashed, =2 its the wrong date, =0 The program ran fine
:start
:: Rest of Code
Echo MERRY CHRISTMAS
:EOF
Exit /b 0
And that should do what you want + more
Mona.
Like all the answers so far, this is dependent on the format of your %date% variable - you can modify the search term.
#echo off
echo %date%|find " 25/12/" >nul
if not errorlevel 1 (
echo Merry Christmas
) else (
echo Santa is asleep, try again tomorrow!
)

how to get an actively refreshing tasklist in command line (windows vista)

How do i get the tasklist command to refresh over a period of time? Is there any way to do so? Any advice would be greatly appreciated. BTW i would prefer not having to download any outside command line tools. :) Thank you in advance for your replies.
You may use anyone of the multiple methods previously posted here (search for "delay"). For example:
#ECHO OFF
:REFRESH
ECHO Put your Tasklist command here...
REM DELAY 20 seconds
REM GET ENDING SECOND
FOR /F "TOKENS=1-3 DELIMS=:." %%A IN ("%TIME%") DO SET /A H=%%A, M=1%%B%%100, S=1%%C%%100, ENDING=(H*60+M)*60+S+20
REM WAIT FOR SUCH A SECOND
:WAIT
FOR /F "TOKENS=1-3 DELIMS=:." %%A IN ("%TIME%") DO SET /A H=%%A, M=1%%B%%100, S=1%%C%%100, CURRENT=(H*60+M)*60+S
IF %CURRENT% LSS %ENDING% GOTO WAIT
GOTO REFRESH
Perhaps you may want to start this Batch file with low priority to not consume too much CPU time this way:
START "Tasklist Monitor" /LOW TheBatchFile

MS DOS edit a file

I am writing a batch script which I wish to open a file and then change the second line of it. I want to find the string "cat" and replace it with a value that I have SET i.e. %var% . I only want this to happen on the second line (or for the first 3 times). How would you go about doing this?
I just solve it myself. It will lookup var on line two only.
#echo OFF
SETLOCAL ENABLEEXTENSIONS ENABLEDELAYEDEXPANSION
SET filename=%1
set LINENO=0
for /F "delims=" %%l in (%filename%) do (
SET /A LINENO=!LINENO!+1
IF "!LINENO!"=="2" ( call echo %%l ) ELSE ( echo %%l )
)
But I prefer using cscript (vbscript or even jscript).
First of all, using a batch file to achieve this, is messy (IMHO). You will have to use an external tool anyway to do the string replacement. I'd use some scripting language instead.
If you really want to use a batch, this will get you started.
This would be ugly to do with native batch scripting. I would either
Do this in VBScript. If you really need this in a batch file, you can call the VBScript file from the batch script. You can even pass in %var% as an argument to the VBScript.
Use a sed script. There are windows ports of Unix commands like GnuWin32, GNU Utilities for Win32 (I use these), or Cygwin.
I would create a script that would:
scan the input file
write to a second output file
delete the input
rename the output
As far as the dos commands to parse, I did a Google Search and came up with a good starting point:
#echo off
setlocal enabledelayedexpansion
set file=c:\file.txt
set output=output.txt
set maxlines=5000
set count=0
for /F "tokens=* usebackq" %%G in ("%file%") do (
if !count!==%maxlines% goto :eof
set line=%%G
set line=!line:*000000000000=--FOUND--!
if "!line:~0,9!"=="--FOUND--" (
echo %%G>>"%output%"
set /a count+=1
)
)
(Stolen from teh Intarwebnet)