Force autonomous .bat files to run sequentially - windows

I have a reasonably large number of .bat files that are launched by the Windows Task Scheduler. And, subsequently, or by an app that's called in the process. In the latter case, the app launches a .bat file to log that it has started and another .bat file to log that it has completed. They all trigger another single logging .bat file that writes to a log file. There a multiple situations that cause them to overlap:
all of the Task Scheduler tasks are manually Run at once
one of the app tasks is still running when another related Task
Scheduler runs on schedule.
So, we sometimes see:
the process cannot access the file because it is being used by another
process.
And, the result of this is that log entries are missed.
Just to be clear:
Task Scheduler tasks:
go1 >>> launches bat_name1.bat
go2 >>> launches bat_name2.bat
etc.
bat_name1.bat, bat_name2.bat,....
CALL log.bat %bat_nameN%
app.exe %bat_nameN%
EXIT
app.exe task:nameN
launches STARTnameN.bat
(runs the core of the app)
launches ENDnameN.bat
STARTnameN.bat and ENDnameN.bat
log.bat %nameN%
log.bat
#ECHO OFF
SET fileloc=C:\Users\Public\BackupLogs
echo %time% %date% %2 %3 %~1>%fileloc%\temp.txt
type %fileloc%\temp.txt>>%fileloc%\backuplog.txt
So the objective would be to allow all these programs to run autonomously but to sequentialize the result so the log files can be completely written without interference.
One thought would be to separate the temp.txt into tempN.txt,... and to append the result to the single backuplog.txt as a part of the ending process. That would likely make it better but doesn't appear to be a 100% solution as there could still be overlaps?

You could test if the append fails and retry via something like:
:try_append
copy /b %fileloc%\backuplog.txt+%fileloc%\temp.txt %fileloc%\backuplog.txt
if errorlevel 1 goto try_append
(copy must be used as internal commands such as echo and type won't set the error level.)
That would improve things, however you'd still have the problem of collision on the %fileloc%\temp.txt file. Perhaps you have a way to easily resolve this using unique temp names in your various .bat files.
If not, better random temp filenames can be created using %time::=% (millisecond randomness), but even that could conceivably collide.
When I want a truly random filename I involve the value of the RDTSC opcode which changes every processor clock cycle making collisions impossible. There are open source tools available to help with this, eg: capture RDTSC opcode. But perhaps that is a topic for another question.

Related

run sofware for a fixed time

I am creating a batch file which is calling other batch file. Sometimes the second batch file gives an error (because the license for the software I am running is not found). When the error hits, a window pop ups and I need to close manually (undesirable because it needs to run in a loop).
I would like to call the second batch file and if it didn't finish to run after 90seconds, kill it and go to the next line of my first batch file.
Is that possible?
Pause, sleep, timeout, and a few others can help you.
I would suggest timeout.
timeout /t 90
Here's some more info: http://www.wikihow.com/Delay-a-Batch-File
To do exactly what you want you'll have to work in some logic to decide what to do after the timeout, but you will likely use a loop after that. It depends on the structure of your code. Maybe toggle a boolean variable to determine if you want to go to the top of the script.

How do I make a task run on startup through raimeter?

I want a random number to be generated every time I start my computer so I can randomly choose a background on rainmeter. Every time I try to search for an answer I keep getting pages for how to make rainmeter run on startup.
You can use the RunCommand plugin to execute a command line input.
To make it run once when the skin is loaded, you just need to set option UpdateDivider=-1.
The following opens Notepad on startup, replace it in Parameter=Notepad with the command you wish to run.
[Rainmeter]
Update=1000
[MeasureRunCmd]
Measure=Plugin
Plugin=RunCommand
Parameter=Notepad
[MeterRunCmd]
UpdateDivider=-1
Meter=String
Text=None
OnUpdateAction=[!CommandMeasure MeasureRunCmd "Run"]
If you don't need the extra flexibility of that plugin you can just use the following
[Rainmeter]
Update=1000
[MeterRunCmd]
UpdateDivider=-1
Meter=String
Text=None
OnUpdateAction=["Notepad"]
I just became acquainted with Rainmeter about 3 hours ago. But here's a thought:
Any "app" (or even a shortcut to an app) that's in "C:\Users\\AppData\Roaming\Microsoft\Windows\Start Menu\Programs\Startup" will run at ... uhh? ... STARTUP! (that's it!). Now, since cmd.exe runs as conhost.exe before the startup folder is processed, that means we can use the "DOS" (I'm an old fart) %RANDOM% variable.
So, if Rainmeter can handle system variables in ".ini" files then you can use %Random% directly (Enter %RANDOM% at the command prompt and you'll see a different number returned everytime). Also, Google %RANDOM% (case, like size, does matter) to see the tweaks used to get any range of numbers you desire.
If Rainmeter can't handle system variables directly then write a 1 line ".bat" file that "set"s the random number to a string (or whatever you can use) and stick the batch file (or a shortcut to it) in the startup folder.
I can't think of a reason why this easy method (or your own enhanced version of it) won't work.
Good luck. Interesting idea. Let me know how you make out.

Batch file runs multiple processes simultaneously

I need to run similiar multiple mp3 converting processes at the same time with windows command prompt.
As far as I know, if I start one converting process using batch file, only 1 console window apears and only one process starts. After this process is finished (and if there is a command line for it) starts another process and so on.
As I just tested, if I start multiple batch files at the same time, I have more then 75% time economy!!!!! It's very important form me, because overall time processing counts in months (in my case)!
So, my problem is - how to force start all other multiple batch files at the same time and make the main batch file wait for finished executing all others batches. And only then continiue actions in main batch file.
THANK YOU!

A way to get just directories and PIDs using wmic?

I'm trying to write a script that handles application deployment, based off new builds. Unfortunately, our software (java/weblogic) doesn't have a very reliable "shutdown" command, so we're more or less forced to just kill the running processes before deploying the new code to the environment location.
What I would like to be able to do is write a script that can either (a) determine what PIDs exist for a specific directory, or (b) list all processes and parse the directories from that output.
So far, I've only made slight progress with (b), in that I can wmic process list and get everything in the world printed. Is there a way to narrow this list down? I searched but couldn't find flags that would allow me to request just the PIDs and directories they exist in. I could use the current output, since it looks like directories are printed everywhere, but this seems super inefficient.

Count number of executions of batch-script

This is my problem, I've got a batch-script that I can't modify (lets call it foo) and I would like to count how many times/day this script is executed - to keep track of that data.
Preferably, I would like to write the number of executions with date and exit-code to some kind of log file.
So my question is if this is possible and in that case - how? To create a batch-script/something that works in the background and writes every execution of foo to a log.
(I know this would be easy if I could modify foo but I can't. Also, everything is running on WinXP machines.)
You could write a wrapper script that does the logging and calls the existing script. Then use the wrapper in place of the original script
Consider writing a program that interrogates the Task Manager.
See http://www.netomatix.com/ProcDiagnostics.aspx
You could, for example, write a simple Console app which runs on a timer; every 5 seconds it checks that your foo application process exists. If it finds that it does, it assumes that find as the start time of the application; if it doesn't find it, it assumes the application has now closed and logs that information. It wouldn't be accurate to the second by any means, but would give you a rough approximation of when the thing is running and closing.
You might be able to configure Process Monitor
http://technet.microsoft.com/en-us/sysinternals/bb896645.aspx to capture the information you require

Resources