31

I am relatively new to the concepts mentioned in the question and reading about them from different sources only makes them more confusing. So this is what I understood so far:

When we are given permissions for a file, they look like this:

-rwsr-xr-- 1 user1 users 190 Oct 12 14:23 file.bin

We assume that a user user2 who is in the group users tries to execute file.bin. If the setuid bit were not set, this would mean that both the RUID and EUID of file.bin were equal to the UID of user2. But since the setuid bit is set, this means that the RUID is now equal to the UID of user2, while EUID is the UID of the owner of the file, user1.

My questions are:

  1. What is the difference between the owner of the file and root? Does root have the same permissions as the owner? Or would we need a separate entry in the permissions list for root?
  2. Difference between RUID and EUID?
    • As I understand it the RUID and EUID are applied only to processes. If that is the case, why do they have the value of user id's?
    • If RUID is the user who creates the process, and EUID is the user who is currently running the process, then the first sentence of the first answer in this question does not make any sense to me.
    • Did I understand correctly what the setuid bit does?

1 Answers1

46

Here are the answers:

  1. root has always full access to files and directories. The owner of the file usually has them too, but this is not always true. For example:

     -r-xr----- 1 user1 users 199 Oct 14 18:42 otherfile.bin
    

user1 is the owner; however they can only read and execute, but root still has full access (rwx) to the file.

  1. RUID is the Real User ID and it (almost) never changes. If user2 logs in to the system, the shell is then launched with its real ID set to user2. All processes they start from the shell will inherit the real ID user2 as their real ID.

EUID is the Effective User ID, it changes for processes (not for the user) that the user executes that have set the setuid bit.

If user2 executes file.bin, the RUID will be user2 and the EUID of the process started will be user1.

Let's use the case of passwd:

-rwsr-xr-x 1 root root 45396 may 25  2012 /usr/bin/passwd
  • When user2 wants to change their password, they execute /usr/bin/passwd.

  • The RUID will be user2 but the EUID of that process will be root.

  • user2 can use passwd to change only their own password because internally passwd checks the RUID and, if it is not root, its actions will be limited to real user's password.

  • It's neccesary that the EUID becomes root in the case of passwd because the process needs to write to /etc/passwd and/or /etc/shadow.

jcbermu
  • 4,736
  • 18
  • 26
  • Thank you! Now everyting is more clear. I do have one more question, though. The EUID only changes when a user executes a process which has the setuid bit set? Or can it change also in another situation? And if so, what is that situation? – user1956190 Mar 23 '15 at 14:18
  • 1
    I think there is not other way than executing processes which have the setuidbit set. – jcbermu Mar 23 '15 at 14:23
  • 3
    A process that is running from a “setuid” program (i.e., a process that has Effective UID ≠ Real UID) can set the EUID back to the RUID. In some cases, it can switch the EUID back and forth between its initial value (i.e., the owner of the program file) and the RUID. Also, it may be able to set its RUID equal to its EUID. … (Cont’d) – Scott - Слава Україні Mar 23 '15 at 19:54
  • 3
    (Cont’d) … Privileged processes (those with EUID = 0, a.k.a. root) can set EUID and RUID to arbitrary values (for example, the login, su, and sudo programs do that). Generally, once a privileged process changes its UIDs to non-zero values, it is no longer privileged and cannot become root again. See the man pages setuid(2), seteuid(2), and setreuid(2). – Scott - Слава Україні Mar 23 '15 at 19:55
  • @Scott there is also suid (saved), this allows you to copy real to effective, while leaving real alone, and be able to get back (because you earlier copied effective to saved). There is also a fuid (file), it is the effective ID used for file access. When you write to euid, it also writes to fuid (so you can ignore it, most of the time, unless you are writing some user-mode file-systems (nfs uses it)). – ctrl-alt-delor Sep 06 '18 at 18:32
  • @user1956190 you do not execute a process on Unix. You can create a process, with fork. This creates a new process, that is a clone of the original, but different PID, and the child returns 0 from fork (parent returns child's pid). Then there is exec this reads a program from disk and executes it. This is the sys-call that allows to gain a UID (or capability), as you describe. exec does not create a new process, it replaces the code of the existing process. – ctrl-alt-delor Sep 06 '18 at 18:38
  • @ctrl-alt-delor: (1) Well, yes; I said “In some cases, a process can switch the EUID back and forth between its initial value (i.e., the owner of the program file) and the RUID.” This was impossible before the invention of the saved UID. But the question was not “Tell me everything there is to know about UIDs”. The OP asked a follow-up question, “The EUID only changes when a user executes a process which has the setuid bit set? Or can it change also in another situation? And if so, what is that situation?” I was trying to answer that question without drowning them in information.  … (Cont’d) – Scott - Слава Україні Sep 06 '18 at 20:08
  • (Cont’d) …  (2) You say, “this allows you to copy real to effective, while leaving real alone.”  No, a simple euid = ruid assignment allows you to copy real to effective, while leaving real alone.  The saved UID lets a process copy the real UID to the effective UID (i.e., restore the effective UID to the ID of the user who is running the command) *and then* set the effective UID to the UID of the executable file again.  (3) That other UID that you mention is properly called file system user ID (fsuid);  … (Cont’d) – Scott - Слава Україні Sep 06 '18 at 20:08
  • (Cont’d) …  see also setfsuid(2).  I didn’t mention that, again, because it was out of the scope of the question.  (Perhaps you should be addressing @jcbermu, who said “Here are the answers” and yet didn’t dump the entire manual down the OP’s throat.)  Besides, as Wikipedia and the man page say, FSUID is borderline obsolete. … (Cont’d) – Scott - Слава Україні Sep 06 '18 at 20:08
  • 1
    (Cont’d) …  It was introduced as a hack to solve one problem, which has subsequently been solved in a broader way.  It might have been removed from Linux except for the fact that such a pruning would break the programs that use it.  Michael Kerrisk, author of The Linux Programming Interface, says, in his version of the setfsuid(2) man page, “setfsuid() is nowadays unneeded and should be avoided in new applications.” – Scott - Слава Україні Sep 06 '18 at 20:09