It's both a historical and security restriction.
Historically, most drives weren't removable. So it made sense to restrict mounting to people who had legitimate physical access, and they would likely have access to the root account. The fstab entries allow administrators to delegate mounting to other users for removable drives.
From a security point of view, there are three major problems with allowing arbitrary users to mount arbitrary block devices or filesystem images at arbitrary locations.
- Mounting to a non-owned location shadows the files at that location. For example: mount a filesystem of your choice on
/etc
, with an /etc/shadow
containing a root password that you know. This is fixed by allowing a user to mount a filesystem only on a directory that he owns.
- Filesystem drivers have often not been tested as thoroughly with malformed filesystem. A buggy filesystem driver could allow a user supplying a malformed filesystem to inject code into the kernel.
- Mounting a filesystem can allow the mounter to cause some files to appear that he would not otherwise have permission to create. Setuid executable and device files are the most obvious examples, and they are fixed by the
nosuid
and nodev
options which are implied by having user
in /etc/fstab
.
So far enforcing user
when mount
is not called by root is enough. But more generally being able to create a file owned by another user is problematic: the content of that file risks being attributed by the purported owner instead of the mounter. A casual attribute-preserving copy by root to a different filesystem would produce a file owned by the declared-but-uninvolved owner. Some programs check that a request to use a file is legitimate by checking that the file is owned by a particular user, and this would no longer be safe (the program must also check that the directories on the access path are owned by that user; if arbitrary mounting was allowed, they would also have to check that none of these directories are a mount point where the mount was created neither by root nor by the desired user).
For practical purposes, it is possible nowadays to mount a filesystem without being root, through FUSE. FUSE drivers run as the mounting user so there is no risk of privilege escalation by exploiting a bug in kernel code. FUSE filesystems can only expose files that the user has the permission to create, which solves the last issue above.
This can be a bit of a confusing topic because there are different implementations of cron. Also there were several bugs that broke this feature, and there are also some use cases where it simply won't work, specifically if you do a shutdown/boot vs. a reboot.
Bugs
datapoint #1
One such bug in Debian is covered here, titled: cron: @reboot jobs are not run. This seems to have made it's way into Ubuntu as well, which I can't confirm directly.
datapoint #2
Evidence of the bug in Ubuntu would seem to be confirmed here in this SO Q&A titled: @reboot cronjob not executing.
excerpt
comment #1: .... 3) your version of crond may not support @reboot are you using vix's crond? ... show results of crontab -l -u user
comment #2: ... It might be a good idea to set it up as an init script instead of relying on a specific version of cron's @reboot.
comment #3: ... @MarkRoberts removed the reboot and modified the 1 * * * * , to */1 * * * * , problem is solved! Where do I send the rep pts Mark? Thank you!
The accepted answer in that Q&A also had this comment:
Seems to me Lubuntu doesn't support the @Reboot Cron syntax.
Additional evidence
datapoint #3
As additional evidence there was this thread that someone was attempting the very same thing and getting frustrated that it didn't work. It's titled: Thread: Cron - @reboot jobs not working.
excerpt
Re: Cron - @reboot jobs not working
Quote Originally Posted by ceallred View Post
This is killing me... Tried the wrapper script. Running manually generates the log file... rebooting and the job doesn't run or create log file.
Syslog shows that CRON ran the job... but again, no output and the process isn't running.
Jul 15 20:07:45 RavenWing cron[1026]: (CRON) INFO (Running @reboot jobs)
Jul 15 20:07:45 RavenWing CRON[1053]: (ceallred) CMD (/home/ceallred/Scripts/run_spideroak.sh > /home/ceallred/Scripts/SpiderOak.log 2>&1 &)
It's seems like cron doesn't like the @reboot command.... Any other ideas?
Okay... Partially solved. I'll mark this one as solved and start a new thread with the new issue.....
I think the answer was my encrypted home directory wasn't mounted when CRON was trying to run the script (stored in /home/username/scripts). Moved to /usr/scripts and the job runs as expected.
So now it appears to be a spideroak issue. Process starts, but by the time the boot process is finished, it's gone. I'm guessing a crash for some reason.... New thread to ask about that.
Thanks for all the help!
Once this above user figured out his issue he was able to get @reboot
working out of the crontab entry of a user.
I'm not entirely sure what version of cron is used on Ubuntu, but this would seem to indicate that user's can use @reboot
too, or that the bug was fixed at some point in subsequent versions of cron.
datapoint #4
I tested on CentOS 6 the following and it worked.
Example
$ crontab -l
@reboot echo "hi" > /home/sam/reboot.txt 2>&1
I then rebooted the system.
$ sudo reboot
After the reboot.
$ cat reboot.txt
hi
Take aways
- This feature does seem to be supported for both system and user crontab entries.
- You have to make sure that it's supported/working in your particular distro and/or version of the cron package.
For more on how the actual mechanism works for @reboot
I did come across this blog post which discusses the innards. It's titled: @reboot - explaining simple cron magic.
Debugging crond
You can turn up the verbosity of crond
by adding the following to this configuration file on RHEL/CentOS/Fedora based distros.
$ more crond
# Settings for the CRON daemon.
# CRONDARGS= : any extra command-line startup arguments for crond
CRONDARGS="-L 2"
The valid levels are 0, 1, or 2. To revert this file back to it's default logging level simply remove the "-L 2"
when you're done debugging the situation.
Best Answer
This is done via an authorization manager called
polkit
:With
systemd
andpolkit
users with non-remote session can issue power related commands. You can list allpolkit
registered actions and get details about any of them withpkaction
(invoked with no arguments it will list all action ids).In this particular case the action id is
org.freedesktop.login1.reboot
so if you run:the output should be something like:
Here,
active: yes
means the user in the active session is authorized to reboot the system (details about implicit authorizations onpolkit
page). You can check if your session is active with: