Usually cron will run a job at the specified time, no matter what. FreeNAS cron as part of the tasks, looks like a web interface to a real crond. The documentation doesn't specify that this is in fact not a crond, but a part of middlewared and that this doesn't behave like crond. Cron doesn't wait on the job, it runs it and leaves it alone. This waits on the jobs and blocks (at least the particular job) until an invocation finishes.
Command:
sh -c ' echo "trying lock" >> /tmp/crontest.log; lockf -t 0 -k /tmp/testlock sh -c " echo got >> /tmp/crontest.log; while true;do sleep 1;done"'
Steps to reproduce:
1. Add "cron" job with the command above
2. Run now
3. Run now
3. Kill the command from the commandline
Expected:
/tmp/crontest:
trying lock
got
First run takes the lock and spins indefinitely . Second invocation runs, can' t acquire lock and fails.
Actual:
/tmp/crontest:
trying lock
got
trying lock
got
First run takes the lock and spins indefinitely . Second invocation is postponed until first command terminates, acquires lock and spins.
Its not a bug. All cron jobs will wait for the first instance to finish before it runs.
Moritz
May 27, 2020 at 7:28 PM
This bug can have big consequences. If you schedule your backups with it and the backup takes longer than expected, the next run will be directly after the first one finished. Usually one is expected to use lockf to limit the number of running instances. I currently use a workaround of using the daemon command.
Usually cron will run a job at the specified time, no matter what.
FreeNAS cron as part of the tasks, looks like a web interface to a real crond.
The documentation doesn't specify that this is in fact not a crond, but a part of middlewared and that this doesn't behave like crond.
Cron doesn't wait on the job, it runs it and leaves it alone. This waits on the jobs and blocks (at least the particular job) until an invocation finishes.
Command:
sh -c ' echo "trying lock" >> /tmp/crontest.log; lockf -t 0 -k /tmp/testlock sh -c " echo got >> /tmp/crontest.log; while true;do sleep 1;done"'
Steps to reproduce:
1. Add "cron" job with the command above
2. Run now
3. Run now
3. Kill the command from the commandline
Expected:
/tmp/crontest:
trying lock
got
First run takes the lock and spins indefinitely . Second invocation runs, can' t acquire lock and fails.
Actual:
/tmp/crontest:
trying lock
got
trying lock
got
First run takes the lock and spins indefinitely . Second invocation is postponed until first command terminates, acquires lock and spins.