Under Linux file systems, files and directories have bits defining what can be done with them. Usually it looks quite obvious and no problem occurs and it is therefore not very interesting to learn how it behaves. But sometimes it is a pain and a hassle since those bits do not behave as expected and trying to modify them using the command line tools with not intuitive command line parameters of can end up in a worse situation.

ls -l

shows the permissions as a string of characters. Example:


The first character can be:

  1. - for regular file

  2. d for directory

  3. l for link to a file or directory

  4. p for named pipe (FIFO)

  5. s for socket

  6. c for character device (should exist just in /dev)

  7. b for block device (should exist just in /dev)

After the first character, three triples of the following characters or a - character is used as place holder are set in the following sequence:

  1. r the file can be read and the files in a directory can be listed

  2. w the file can be written and files in a directory can be added, modified and deleted access

  3. x the file can be executed and subdirectories in a directory can be opened


Note the difference between the bits for files and directories as described above.


The permission of a file or a directory can be set more restrictive by its parent directory. So the permission bits are evaluated by a top down approach, where a next level appears the permission used in the mount command of the file system. So if the drive is set to read-only, no files and directories can be modified regardless of their permission bits.

The first triple is the access right of the user, the second of the group (where the users and other users belong to) and the third of the world (all users). The user root has all the rights by default.

A file can have additional bits:

  1. setuid is used to run a program with user id of the file and not the user calling it

  2. setgid is used to run a program with other group id of the file and not the user calling it

  3. sticky restricts to delete this file just by the user

There is not enough space to show everything in the character string. So the characters s and t are used in the position where x is to indicate that those bits are set.

The character string of the access rights can also be present as a number as illustrated in the following example:

Table 8.1. Permissions

Example setuid setgid sticky Owner Group World
By characters - - - r w x r w x r w x
Weight 4 2 1 4 2 1 4 2 1 4 2 1
By number 0 0 0 0 0 0 0 2 0 0 2 0
Numerical value 0 0 0 0 2 2

Results in the numeric access right of 0022 or 022 or 22 since preceding zeros have no effect.

If you want to see what number corresponds to your files in a directory: stat -c "%a %n" *

Since it is so complicated there is a permission calculator

Example 8.1. Permission

chmod 400 <filename>

just read access to owner, rest forbidden

chmod -R 777 <directory>

Gives all the permissions to all files in the <directory> and its subdirectories.

chmod +x <file>

Gives executable permission to the file.

chmod ugo+x <file>

Gives x permission to user, group and others

umask shows default mask that user is using. It is defined in /etc/profile or /etc/login.defs. It can also be redefined on a user base by ~/.bashrc or ~/.bash_profile

To confuse the user, those bits are the inverse of the ones chmod uses. According the boolean algebra this is mathematically correct, since a logical zero deletes a logical one in a bitwise and function.


ls returns a string and chmod accepts a numeric value. ls is therefore not ideal to verify what chmod <n> <filename> did. The solution is stat -c %a <filename> that shows the numeric value.

Example 8.2. umask

Common command is chmod 0755 this corresponds to the umask 022

See the ownership section for owner and group assignment.


The permission of the drive set by the mount command or settings in /etc/fstab (or the defaults of the mount command) can make that those bits have no effect. Problems that can occur is no write and no execute permissions. Check this with cat /etc/mtab. For the execute permission /etc/fstab must contain the mount option exec!

chmod modifying access rights bits. The following command sets the access rights to all directories (but not files) in the home directory: chmod -R 755 /home/<username>

Problems with access rights and Microsoft file systems. Microsoft file systems do not support access rights as Linux uses it, so trying to modify the access rights will fail. Therefore mount and use them defaults values. As an option the parameter umask can be passed to the mount command to get the desired result.

Linurs startpage