standard file permissions
(Written by Paul Cobbaut, https://github.com/paulcobbaut/, with contributions by: Alex M. Schapelle, https://github.com/zero-pytagoras/, Bert Van Vreckem, https://github.com/bertvv/)
This chapter contains details about basic file security through file ownership and file permissions.
file ownership
user owner and group owner
The users and groups of a system can be locally managed in /etc/passwd
and /etc/group
, or they can be in a NIS, LDAP, or Samba domain. These users and groups can own files. Actually, every file has a user owner and a group owner, as can be seen in the following example.
student@linux:~/owners$ ls -lh
total 636K
-rw-r--r--. 1 student snooker 1.1K Apr 8 18:47 data.odt
-rw-r--r--. 1 student student 626K Apr 8 18:46 file1
-rw-r--r--. 1 student tennis 185 Apr 8 18:46 file2
-rw-rw-r--. 1 root root 0 Apr 8 18:47 stuff.txt
User student
owns three files: file1
has student
as user owner and has the group student
as group owner, data.odt
is group owned by the group snooker
, file2
by the group tennis
.
The last file is called stuff.txt
and is owned by the root
user and the root
group.
chgrp
You can change the group owner of a file using the chgrp
command. You must have root privileges to do this.
root@linux:/home/student/owners# ls -l file2
-rw-r--r--. 1 root tennis 185 Apr 8 18:46 file2
root@linux:/home/student/owners# chgrp snooker file2
root@linux:/home/student/owners# ls -l file2
-rw-r--r--. 1 root snooker 185 Apr 8 18:46 file2
root@linux:/home/student/owners#
chown
The user owner of a file can be changed with chown
command. You must have root privileges to do this. In the following example, the user owner of file2
is changed from root
to student
.
root@linux:/home/student# ls -l FileForStudent
-rw-r--r-- 1 root student 0 2008-08-06 14:11 FileForStudent
root@linux:/home/student# chown student FileForStudent
root@linux:/home/student# ls -l FileForStudent
-rw-r--r-- 1 student student 0 2008-08-06 14:11 FileForStudent
You can also use chown user:group
to change both the user owner and the group owner.
root@linux:/home/student# ls -l FileForStudent
-rw-r--r-- 1 student student 0 2008-08-06 14:11 FileForStudent
root@linux:/home/student# chown root:project42 FileForStudent
root@linux:/home/student# ls -l FileForStudent
-rw-r--r-- 1 root project42 0 2008-08-06 14:11 FileForStudent
list of special files
When you use ls -l
, for each file you can see ten characters before the user and group owner. The first character tells us the type of file. Regular files get a -
, directories get a d
, symbolic links are shown with an l
, pipes get a p
, character devices a c
, block devices a b
, and sockets an s
.
first character | file type |
---|---|
- |
normal file |
d |
directory |
l |
symbolic link |
p |
named pipe |
b |
block device |
c |
character device |
s |
socket |
Below an example of a character device (the console) and a block device (the hard disk).
student@linux:~$ ls -l /dev/console /dev/sda
crw--w---- 1 root tty 5, 1 Mar 8 08:32 /dev/console
brw-rw---- 1 root disk 8, 0 Mar 8 08:32 /dev/sda
And here you can see a directory, a regular file and a symbolic link.
student@linux:~$ ls -ld /etc /etc/hosts /etc/os-release
drwxr-xr-x 81 root root 4096 Mar 8 08:32 /etc
-rw-r--r-- 1 root root 186 Feb 26 14:58 /etc/hosts
lrwxrwxrwx 1 root root 21 Dec 9 21:08 /etc/os-release -> ../usr/lib/os-release
permissions
rwx
The nine characters following the file type denote the permissions in three triplets. A permission can be r
for read access, w
for write access, and x
for execute. You need the r
permission to list (ls) the contents of a directory. You need the x
permission to enter (cd) a directory. You need the w
permission to create files in or remove files from a directory.
permission | on a file | on a directory |
---|---|---|
read | read file contents (cat ) |
read directory contents (ls ) |
write | change file contents | create/delete files (touch ,rm ) |
execute | execute the file | enter the directory (cd ) |
three sets of rwx
We already know that the output of ls -l
starts with ten characters for each file. This example shows a regular file (because the first character is a - ).
Below is a table describing the function of all ten characters.
position | characters | function |
---|---|---|
1 | - |
file type |
2-4 | rwx |
permissions for the user owner |
5-7 | r-x |
permissions for the group owner |
8-10 | r-- |
permissions for others |
When you are the user owner of a file, then the user owner permissions apply to you. The rest of the permissions have no influence on your access to the file.
When you belong to the group that is the group owner of a file, then the group owner permissions apply to you. The rest of the permissions have no influence on your access to the file.
When you are not the user owner of a file and you do not belong to the group owner, then the others permissions apply to you. The rest of the permissions have no influence on your access to the file.
permission examples
Some example combinations on files and directories are seen in this example. The name of the file explains the permissions.
student@linux:~/perms$ ls -lh
total 12K
drwxr-xr-x 2 student student 4.0K 2007-02-07 22:26 AllEnter_UserCreateDelete
-rwxrwxrwx 1 student student 0 2007-02-07 22:21 EveryoneFullControl.txt
-r--r----- 1 student student 0 2007-02-07 22:21 OnlyOwnersRead.txt
-rwxrwx--- 1 student student 0 2007-02-07 22:21 OwnersAll_RestNothing.txt
dr-xr-x--- 2 student student 4.0K 2007-02-07 22:25 UserAndGroupEnter
dr-x------ 2 student student 4.0K 2007-02-07 22:25 OnlyUserEnter
To summarise, the first rwx
triplet represents the permissions for the user owner. The second triplet corresponds to the group owner; it specifies permissions for all members of that group. The third triplet defines permissions for all other users that are not the user owner and are not a member of the group owner. The root
user ignores all restrictions and can do anything with any file.
setting permissions with symbolic notation
Permissions can be changed with chmod MODE FILE...
. You need to be the owner of the file to do this. The first example gives (+
) the user owner (u
) execute (x
) permissions.
student@linux:~/perms$ ls -l permissions.txt
-rw-r--r-- 1 student student 0 2007-02-07 22:34 permissions.txt
student@linux:~/perms$ chmod u+x permissions.txt
student@linux:~/perms$ ls -l permissions.txt
-rwxr--r-- 1 student student 0 2007-02-07 22:34 permissions.txt
This example removes (-
) the group owner's (g
) read (r
) permission.
student@linux:~/perms$ chmod g-r permissions.txt
student@linux:~/perms$ ls -l permissions.txt
-rwx---r-- 1 student student 0 2007-02-07 22:34 permissions.txt
This example removes (-
) the other's (o
) read (r
) permission.
student@linux:~/perms$ chmod o-r permissions.txt
student@linux:~/perms$ ls -l permissions.txt
-rwx------ 1 student student 0 2007-02-07 22:34 permissions.txt
This example gives (+
) all (a
) of them the write (w
) permission.
student@linux:~/perms$ chmod a+w permissions.txt
student@linux:~/perms$ ls -l permissions.txt
-rwx-w--w- 1 student student 0 2007-02-07 22:34 permissions.txt
You don't even have to type the a
.
student@linux:~/perms$ chmod +x permissions.txt
student@linux:~/perms$ ls -l permissions.txt
-rwx-wx-wx 1 student student 0 2007-02-07 22:34 permissions.txt
You can also set explicit permissions with =
.
student@linux:~/perms$ chmod u=rw permissions.txt
student@linux:~/perms$ ls -l permissions.txt
-rw--wx-wx 1 student student 0 2007-02-07 22:34 permissions.txt
Feel free to make any kind of combination, separating them with a comma. Remark that spaces are not allowed!
student@linux:~/perms$ chmod u=rw,g=rw,o=r permissions.txt
student@linux:~/perms$ ls -l permissions.txt
-rw-rw-r-- 1 student student 0 2007-02-07 22:34 permissions.txt
Even fishy combinations are accepted by chmod
.
student@linux:~/perms$ chmod u=rwx,ug+rw,o=r permissions.txt
student@linux:~/perms$ ls -l permissions.txt
-rwxrw-r-- 1 student student 0 2007-02-07 22:34 permissions.txt
Summarized, in order to change permissions with chmod
using symbolic notation:
- first specify who the permissions are for:
u
for the user owner,g
for the group owner,o
for others, anda
for all.a
is the default and can be omitted. - then specify the operation:
+
to add permissions,-
to remove permissions, and=
to set permissions. - finally specify the permission(s):
r
for read,w
for write, andx
for execute. - multiple operations can be combined with a comma (no spaces!)
setting permissions with octal notation
Most Unix administrators will use the "old school" octal system to talk about and set permissions. Consider the triplet to be a binary number with 0 indicating the permission is not set and 1 indicating the permission is set. You then have \(2^3=8\) possible combinations, hence the name octal. You can then convert the binary number to an octal number, equating r
to 4, w
to 2, and x
to 1.
permission | binary | octal |
---|---|---|
--- |
000 | 0 |
--x |
001 | 1 |
-w- |
010 | 2 |
-wx |
011 | 3 |
r-- |
100 | 4 |
r-x |
101 | 5 |
rw- |
110 | 6 |
rwx |
111 | 7 |
Since we have three triplets, we can use three octal digits to represent the permissions. This makes 777 equal to rwxrwxrwx
and by the same logic, 654 mean rw-r-xr--
. The chmod
command will accept these numbers.
student@linux:~/perms$ chmod 777 permissions.txt
student@linux:~/perms$ ls -l permissions.txt
-rwxrwxrwx 1 student student 0 2007-02-07 22:34 permissions.txt
student@linux:~/perms$ chmod 664 permissions.txt
student@linux:~/perms$ ls -l permissions.txt
-rw-rw-r-- 1 student student 0 2007-02-07 22:34 permissions.txt
student@linux:~/perms$ chmod 750 permissions.txt
student@linux:~/perms$ ls -l permissions.txt
-rwxr-x--- 1 student student 0 2007-02-07 22:34 permissions.txt
Remark that in practice, some combinations will never occur:
- The permissions of a user will never be smaller than the permissions of the group owner or others. Consequently, the digits will always be in descending order.
- Setting the write or execute permission without read access is useless. Consequently, you will never use 1, 2, or 3 in an octal permission code
- A directory will always have the read and execute permission set or unset together. It is useless to allow a user to read the directory contents, but not let them
cd
into that directory. Allowingcd
without read access is also useless. The permission code for a directory will therefore always be odd.
Here's a little tip: you can print the permissions of a file in either octal or symbolic notation with the stat
command (check the man page of stat
to see how this works).
[student@linux ~]$ stat -c '%A %a' /etc/passwd
-rw-r--r-- 644
[student@linux ~]$ stat -c '%A %a' /etc/shadow
---------- 0
[student@linux ~]$ stat -c '%A %a' /bin/ls
-rwxr-xr-x 755
umask
When creating a file or directory, a set of default permissions are applied. These default permissions are determined by the umask
value. The umask
specifies permissions that you do not want set on by default. You can display the umask
with the umask
command.
[student@linux ~]$ umask
0002
[student@linux ~]$ touch test
[student@linux ~]$ ls -l test
-rw-rw-r-- 1 student student 0 Jul 24 06:03 test
[student@linux ~]$
As you can also see, the file is also not executable by default. This is a general security feature among Unixes; newly created files are never executable by default. You have to explicitly do a chmod +x
to make a file executable. This also means that the 1 bit in the umask
has no meaning. A umask
value of 0022 has the same effect as 0033.
In practice, you will only use umask values:
- 0: don't take away any permissions
- 2: take away write permissions
- 7: take away all permissions
You can set the umask
value to a new value with the umask
command. The umask
value is a four-digit octal number. The first digit is for special permissions (and is always zero), the second for the user permissions (is in practice always 0, since there is no use in taking away the user's permissions), the third for the group owner (sometimes 0, but usually 2 or 7), and the last for others (usually 2 or 7, 0 is very uncommon and can be considered to be a security risk).
The umask
value is subtracted from 777 to get the default permissions and in the case of a file, the execute bit is removed.
[student@linux ~]$ umask 0002
[student@linux ~]$ touch file0002
[student@linux ~]$ mkdir dir0002
[student@linux ~]$ ls -ld *0002
drwxrwxr-x. 2 student student 6 Mar 8 10:48 dir0002
-rw-rw-r--. 1 student student 0 Mar 8 10:47 file0002
[student@linux ~]$ umask 0027
[student@linux ~]$ touch file0027
[student@linux ~]$ mkdir dir0027
[student@linux ~]$ ls -ld *0027
drwxr-x---. 2 student student 6 Mar 8 10:48 dir0027
-rw-r-----. 1 student student 0 Mar 8 10:48 file0027
[student@linux ~]$ umask 0077
[student@linux ~]$ touch file0077
[student@linux ~]$ mkdir dir0077
[student@linux ~]$ ls -ld *0077
drwx------. 2 student student 6 Mar 8 10:51 dir0077
-rw-------. 1 student student 0 Mar 8 10:51 file0077
mkdir -m
When creating directories with mkdir
you can use the -m
option to set the mode
. This example explains.
student@linux~$ mkdir -m 700 MyDir
student@linux~$ mkdir -m 777 Public
student@linux~$ ls -dl MyDir/ Public/
drwx------ 2 student student 4096 2011-10-16 19:16 MyDir/
drwxrwxrwx 2 student student 4096 2011-10-16 19:16 Public/
cp -p
To preserve permissions and time stamps from source files, use cp -p
.
student@linux:~/perms$ cp file* cp
student@linux:~/perms$ cp -p file* cpp
student@linux:~/perms$ ll *
-rwx------ 1 student student 0 2008-08-25 13:26 file33
-rwxr-x--- 1 student student 0 2008-08-25 13:26 file42
cp:
total 0
-rwx------ 1 student student 0 2008-08-25 13:34 file33
-rwxr-x--- 1 student student 0 2008-08-25 13:34 file42
cpp:
total 0
-rwx------ 1 student student 0 2008-08-25 13:26 file33
-rwxr-x--- 1 student student 0 2008-08-25 13:26 file42
practice: standard file permissions
-
As normal user, create a directory
~/permissions
. Create a file owned by yourself in there. -
Copy a file owned by root from /etc/ to your permissions dir, who owns this file now ?
-
As root, create a file in the users
~/permissions
directory. -
As normal user, look at who owns this file created by root.
-
Change the ownership of all files in
~/permissions
to yourself. -
Delete the file created by root. Is this possible?
-
With chmod, is 770 the same as
rwxrwx---
? -
With chmod, is 664 the same as
r-xr-xr--
? -
With chmod, is 400 the same as
r--------
? -
With chmod, is 734 the same as
rwxr-xr--
? -
Display the umask value in octal and in symbolic form.
-
Set the umask to 0077, but use the symbolic format to set it. Verify that this works.
-
Create a file as root, give only read to others. Can a normal user read this file? Test writing to this file with
vi
ornano
. -
Create a file as a normal user, take away all permissions for the group owner and others. Can you still read the file? Can root read the file? Can root write to the file?
-
Create a directory that belongs to group
users
, where every member of that group can read and write to files, and create files. Make sure that people can only delete their own files.
solution: standard file permissions
-
As normal user, create a directory
~/permissions
. Create a file owned by yourself in there. -
Copy a file owned by root from /etc/ to your permissions dir, who owns this file now ?
[student@linux ~]$ ls -l /etc/hosts -rw-r--r--. 1 root root 174 Feb 26 15:05 /etc/hosts [student@linux ~]$ cp /etc/hosts ~/permissions/ [student@linux ~]$ ls -l permissions/hosts -rw-r--r--. 1 student student 174 Mar 8 11:00 permissions/hosts
The copy is owned by you.
-
As root, create a file in the users
~/permissions
directory. -
As normal user, look at who owns this file created by root.
[student@linux ~]$ ls -l permissions/*.txt -rw-r--r--. 1 student student 0 Mar 8 10:59 permissions/myfile.txt -rw-r--r--. 1 root root 0 Mar 8 11:02 permissions/rootfile.txt
The file created by root is owned by root.
-
Change the ownership of all files in \~/permissions to yourself.
[student@linux ~]$ chown student ~/permissions/* chown: changing ownership of '/home/student/permissions/rootfile.txt': Operation not permitted
You cannot become owner of the file that belongs to root. Root must change the ownership.
-
Delete the file created by root. Is this possible?
[student@linux ~]$ rm ~/permissions/rootfile.txt rm: remove write-protected regular empty file '/home/student/permissions/rootfile.txt'? y [student@linux ~]$ ls -l permissions/*.txt -rw-r--r--. 1 student student 0 Mar 8 10:59 permissions/myfile.txt
You can delete the file since you have write permission on the directory!
-
With chmod, is 770 the same as
rwxrwx---
?yes
-
With chmod, is 664 the same as
r-xr-xr--
?no,
rw-rw-r--
is 664 andrwxrwxr--
is 774 -
With chmod, is 400 the same as
r--------
?yes
-
With chmod, is 734 the same as
rwxr-xr--
?no,
rwxr-xr--
is 754 andrwx-wxr--
is 734 -
Display the umask in octal and in symbolic form.
umask
andumask -S
-
Set the umask to 0077, but use the symbolic format to set it. Verify that this works.
-
Create a file as root, give only read to others. Can a normal user read this file? Test writing to this file with
vi
ornano
.[student@linux ~]$ sudo vi permissions/rootfile.txt [student@linux ~]$ sudo chmod 644 permissions/rootfile.txt [student@linux ~]$ ls -l permissions/*.txt -rw-r--r--. 1 student student 0 Mar 8 10:59 permissions/myfile.txt -rw-r--r--. 1 root root 6 Mar 8 13:53 permissions/rootfile.txt [student@linux ~]$ cat permissions/rootfile.txt hello [student@linux ~]$ echo " world" >> permissions/rootfile.txt -bash: permissions/rootfile.txt: Permission denied
Yes, a normal user can read the file, but not write to it.
-
Create a file as a normal user, take away all permissions for the group and others. Can you still read the file? Can root read the file? Can root write to the file?
[student@linux ~]$ vi permissions/privatefile.txt ... (editing the file) ... [student@linux ~]$ cat permissions/privatefile.txt hello [student@linux ~]$ chmod 600 permissions/privatefile.txt [student@linux ~]$ ls -l permissions/privatefile.txt -rw-------. 1 student student 0 Mar 8 16:06 permissions/privatefile.txt [student@linux ~]$ cat permissions/privatefile.txt hello
Of course, the owner can still read (and write to) the file.
[student@linux ~]$ sudo vi permissions/privatefile.txt [sudo] password for student: ... (editing the file) ... [student@linux ~]$ cat permissions/privatefile.txt hello world
Root can read and write to the file. In fact, root ignores all file permissions and can do anything with any file.
-
Create a directory
shared/
that belongs to groupusers
, where every member of that group can read and write to files, and create files.