For some unknown reason LSAN catches a SIGSEGV (rdo.c:45) when enabled,
but removing it also removes the supposed SIGSEGV it catches.
To repro, build the earlier build with LSAN, and enter a file that
doesnt exist.
As long as I don't know why LSAN thinks this simple error message causes
a segmentation fault, I will remove it.
Previously, we used a for loop to rearrange argv to omit the first
argument, the rdo call itself.
It's way smarter to just dereference the first argv argument, and use it
as an argv pointer, to achieve the same result.
This error occurs when the user we try to hash the password for doesn't
have a password, as seen in #8.
We now mention this, to avoid future confusion.
getpwnam() does not populate errno when the user simply doesn't exist,
making err() print "Success" as the error.
We now check for errno == 0, and print a different error message for it.
These changes make rdo build on my rpi, probably because this specific
GCC version requires arguments in the order we now supply.
We also disable ASAN in the debug build (for now), as it seems to cause
a segfault on my rpi.
Previously, the password would not be cleared after we hashed it with
crypt(), which lead to the password staying in memory for the duration
of program runtime.
This was only really an issue for incorrect passwords, as execve()
purges our memory anyway, but attackers could use an incorrect but
mostly correct password for privilege escalation.
Due to this being a security issue, this commit also introduces rdo
version 1.3.
Fixes#7
Before we made the ensuredir() function recurse on itself
if we couldn't open /run/rdo, after mkdir()'ing it,
to retry opening the directory.
Now we simplify and add a simple fd = open([...]) directly
after the mkdir(), to avoid the recursion.
If the second open fails, we error out.
In sessions.h, now line 95, we used sizeof(ts_str) to
determine how much to write, but as ts_str can be longer
than the actual string written, it wrote random data
after the actual timestamp.
This is by far the heaviest feature of rdo, justifying
its own file for its 140loc.
It creates sessions, inspired by the way doas does it.
We use the /run/rdo temporary folder to store files in the
format of /run/rdo/pid-ts, pid being the PID of the process
that executed rdo, and ts being the timestamp at which said
process started.
As no 2 processes can have the exact same PID and startup time
(startup time is measured in the milliseconds), this seems secure.
Closes#4.
We now have a normal and a debug build, both of which
have full RELRO, appropriate handling of warnings and
the default build has D_FORTIFY_SOURCE set to 2.