base/workers: Assign worker process list len defensively

When we remove a worker, we know there are 'j' workers left in
the list, so in case we've managed to insert a worker twice in
the same list (unlikely but possible), and that worker later
disconnects, we would be left with a len mismatch and crash on
a segfault when attempting to access the now-empty worker slot.

Reported-by: Max Sikström <msikstrom@op5.com>
Signed-off-by: Andreas Ericsson <ae@op5.se>
base/workers: Fortify job-to-worker assignments

Previously, we could end up doing one of two unpleasant things when
assigning worker to a job and we had no general-purpose workers left
alive.

If we had special-purpose workers, we would end up leaking memory
when asked to run a job that wasn't connected to us.

If we didn't have special purpose workers, we would end up crashing
when asked to run any job at all.

Both scenarios required, as stated above, that all general-purpose
workers had died.

The memory leak was reported by Max Sikström <msikstrom@op5.com>
during code review. Many thanks.

Signed-off-by: Max Sikström <msikstrom@op5.com>
Signed-off-by: Andreas Ericsson <ae@op5.se>
lib/squeue: Protect against insane input

If a user would want to schedule things beyond the unix millenium,
which ends 2038-01-19 03:14:07 UTC (apparently a tuesday, according
to reliable sources), they would previously end up in one of two
unpleasant codepaths. If they were on 32-bit systems, the time would
silently wrap around into negative time, which would be interpreted
as "now" or pretty much anytime inside the 68 years that encompass
the unix millenium, depending on how much they wrapped around. Most
of the time it would be "now" though, since we discard times in the
past inside the squeue library.

If, however, they were on 64-bit systems, the situation could get a
bit more serious, since we would then try to cram 16 bytes of data
into 8 bytes. We would succeed (after a fashion), but we would lose
the top 32 bits of the seconds value for the purpose of priority
queue comparisons, but we would retain them for the sake of the
caller and use it when someone requested it from us (via
squeue_event_runtime()). Since the erroneous event went to the
head of the queue but was in reality scheduled to happen X thousand
years into the future, Nagios wouldn't run it, but would instead
go and sulk in a corner. Not very nice.

This patch fixes it, and as a nice bonus protects against broken
gettimeofday() implementations (are there any?), by masking off
the bottom 21 bits for the microsecond value and the 43 topmost
bits for the tv_sec value we actually store for the timeval
struct.

That means the Nagios millenium will end with the unix millenium
for 32 bit systems and sometime in the year 141166 for 64-bit
systems.

We don't support scheduling things beyond those years on the given
architectures. Doing so will cause undefined behaviour, and we
can't protect against it due to type restrictions enforced on us
by the compiler. Users who try will see their events being run
inappropriately early.

We will, however, not *stop* running events now, but merrily
carry on with our other scheduled tasks after we've run the
poorly scheduled event (at the wrong time).

Reported-by: Ton Voon <ton.voon@opsview.com>
Signed-off-by: Andreas Ericsson <ae@op5.se>
lib/tests: Janitor patch

Fix a bunch of compiler warnings.

Signed-off-by: Andreas Ericsson <ae@op5.se>
core: Avoid lock file removal race condition

The race condition happens when we receive a SIGHUP, break out
of the event execution loop, and receive any sort of signal
setting the 'sigshutdown' flag AFTER checking for the sigshutdown
state but BEFORE the do-while loop terminates. I.e, during
execution of cleanup() or close_debug_log() towards the end of
the loop.

It's a pretty narrow window, but the result is a segfault on
invalid memory access when we attempt to unlink() the lockfile.

Original-patch-by: Anton Löfgren <alofgren@op5.com>
Signed-off-by: Anton Löfgren <alofgren@op5.com>
Signed-off-by: Andreas Ericsson <ae@op5.se>