Linux permissions control who can read, write, and execute every file and directory. Once you understand the three-digit pattern, you can read ls -l output instantly and set the right permissions with a single command.
Quick reference
| Permission | Octal | Symbolic | Meaning |
|---|---|---|---|
rwxrwxrwx |
777 |
a+rwx |
Everyone can do everything |
rwxr-xr-x |
755 |
u=rwx,go=rx |
Owner full, others read+execute |
rwxr-x--- |
750 |
u=rwx,g=rx,o= |
Owner full, group read+execute, no others |
rw-r--r-- |
644 |
u=rw,go=r |
Owner read+write, others read-only |
rw-rw-r-- |
664 |
ug=rw,o=r |
Owner+group read+write, others read |
rw------- |
600 |
u=rw,go= |
Owner read+write only (private files) |
rwx------ |
700 |
u=rwx,go= |
Owner full, no others |
r--r--r-- |
444 |
a=r |
Read-only for everyone |
--------- |
000 |
a= |
No permissions |
Reading ls -l output
ls -l /etc/passwd
# -rw-r--r-- 1 root root 2345 Jul 14 09:00 /etc/passwd
The first 10 characters decode as:
- rw- r-- r--
│ │ │ └── others permissions
│ │ └─────── group permissions
│ └─────────── owner permissions
└───────────── file type: - file, d directory, l symlink, b block device
Each permission group is three bits — r (read), w (write), x (execute):
| Bit | File meaning | Directory meaning |
|---|---|---|
r (4) |
Read file contents | List directory (ls) |
w (2) |
Modify or delete file | Create/delete files inside |
x (1) |
Run as program | Enter directory (cd) |
chmod — change permissions
chmod accepts two styles: symbolic (letters) and octal (numbers).
Symbolic mode
chmod [who][operator][permissions] file
# who: u (owner/user), g (group), o (others), a (all)
# op: + add, - remove, = set exactly
# perms: r, w, x, s (setuid/setgid), t (sticky)
Common examples:
chmod +x script.sh # Add execute for everyone
chmod u+x script.sh # Add execute for owner only
chmod go-w file.txt # Remove write from group and others
chmod u=rw,go=r file.txt # Owner rw, everyone else r
chmod a-x file.txt # Remove execute from everyone
chmod -R 755 /var/www/html # Recursively set 755
Octal mode
Each digit is the sum of bits: r=4, w=2, x=1.
owner group others
7 5 5
r+w+x r+x r+x
Most common values:
chmod 755 script.sh # rwxr-xr-x — web server files, scripts
chmod 644 index.html # rw-r--r-- — web content, config files
chmod 600 ~/.ssh/id_rsa # rw------- — private keys
chmod 700 ~/.ssh # rwx------ — SSH directory
chmod 777 /tmp/shared # rwxrwxrwx — shared scratch (avoid on production)
chmod 664 shared-file.txt # rw-rw-r-- — team-writable file
chmod 440 /etc/sudoers # r--r----- — read-only critical configs
Recursive chmod
# Apply to directory and everything inside
chmod -R 755 /var/www/
# Directories 755, files 644 (common web server pattern)
find /var/www/ -type d -exec chmod 755 {} \;
find /var/www/ -type f -exec chmod 644 {} \;
chown — change owner and group
chown owner file # Change owner
chown owner:group file # Change owner and group
chown :group file # Change group only (same as chgrp)
chown -R user:group dir/ # Recursive
Examples:
chown alice report.txt # Give file to alice
chown alice:developers report.txt # alice owns it, developers group
chown -R www-data:www-data /var/www/html # Web server ownership
chown root:root /usr/local/bin/mytool # System binary
Check current owner:
ls -l file.txt
stat file.txt # More detail: inode, blocks, timestamps
Understanding groups
Every user belongs to a primary group and possibly supplementary groups.
id # Your user ID, group ID, and groups
id alice # Another user's info
groups # List your groups
groups alice # List groups for alice
cat /etc/group # All groups on system
# Add user to a group (takes effect on next login)
sudo usermod -aG developers alice
# Create a group
sudo groupadd developers
umask — default permissions
When you create a file or directory, the kernel subtracts the umask from the maximum permissions (666 for files, 777 for directories).
umask # Show current umask (e.g., 0022)
umask -S # Show in symbolic notation (e.g., u=rwx,g=rx,o=rx)
umask 0027 # Set umask for current session
How it works:
File defaults: 666 (rw-rw-rw-)
Subtract umask: - 022 (----w--w-)
Result: 644 (rw-r--r--)
Directory defaults: 777 (rwxrwxrwx)
Subtract umask: - 022 (----w--w-)
Result: 755 (rwxr-xr-x)
Common umask values:
| umask | Files created as | Dirs created as | Use case |
|---|---|---|---|
022 |
644 |
755 |
Standard (most distros) |
027 |
640 |
750 |
Group can read, no others |
077 |
600 |
700 |
Private — no group/others |
002 |
664 |
775 |
Collaborative (group can write) |
To make permanent, add to ~/.bashrc or ~/.profile:
echo "umask 027" >> ~/.bashrc
Special permission bits
Beyond the basic rwx, Linux has three special bits.
Setuid (SUID) — run as owner
When set on an executable, it runs with the file owner's permissions (not the caller's). Classic example: passwd runs as root so it can edit /etc/shadow.
# View: s appears in owner's execute position
ls -l /usr/bin/passwd
# -rwsr-xr-x 1 root root ...
# Set / remove
chmod u+s /usr/local/bin/myapp
chmod u-s /usr/local/bin/myapp
chmod 4755 /usr/local/bin/myapp # 4 = setuid in octal
Setgid (SGID) — run as group / inherit group
On executables: runs with file's group permissions.
On directories: new files created inside inherit the directory's group (useful for shared team directories).
# View: s in group's execute position
ls -ld /usr/bin/wall
# -rwxr-sr-x 1 root tty ...
# Set on directory so new files inherit group
chmod g+s /var/www/html
chmod 2755 /var/www/html # 2 = setgid in octal
ls -ld /var/www/html
# drwxr-sr-x 2 root www-data ...
Sticky bit — restrict deletion
On directories: users can only delete their own files, even if they have write permission on the directory. Used on /tmp.
# View: t in others' execute position
ls -ld /tmp
# drwxrwxrwt 10 root root ...
# Set
chmod +t /shared/uploads
chmod 1777 /shared/uploads # 1 = sticky in octal
All three special bits together
| Bit | Octal | On file | On directory |
|---|---|---|---|
| Setuid | 4 | Run as owner | Ignored (mostly) |
| Setgid | 2 | Run as group | New files inherit group |
| Sticky | 1 | Ignored (mostly) | Only owner can delete |
Practical patterns
Web server files
# Apache / Nginx — files owned by deploy user, served by www-data
sudo chown -R deploy:www-data /var/www/mysite
find /var/www/mysite -type d -exec chmod 750 {} \;
find /var/www/mysite -type f -exec chmod 640 {} \;
# Uploads directory — web server must write
chmod 770 /var/www/mysite/uploads
chown www-data:www-data /var/www/mysite/uploads
Shared team directory
# All files inherit the group; group can read+write
sudo groupadd devteam
sudo chown -R :devteam /home/shared
chmod 2775 /home/shared # setgid + rwxrwxr-x
SSH key permissions (required by sshd)
chmod 700 ~/.ssh
chmod 600 ~/.ssh/id_ed25519 # Private key
chmod 644 ~/.ssh/id_ed25519.pub # Public key
chmod 600 ~/.ssh/authorized_keys
chmod 600 ~/.ssh/config
Script deployment
chmod 755 deploy.sh # Owner execute, everyone read
chmod +x bin/* # Make all files in bin/ executable
Common mistakes
| Mistake | Problem | Fix |
|---|---|---|
chmod 777 on production |
Any user can write/execute | Use 755 (dirs) + 644 (files) |
| Forgetting execute on directory | cd: permission denied even with read |
Add x: chmod +x dir/ |
chown without -R on directory |
Children keep old owner | Use chown -R user:group dir/ |
| SUID on scripts | Ignored by most Linux kernels | SUID only works on compiled binaries |
Removing x from /tmp |
System breaks | Never chmod system directories |
644 on private key |
SSH refuses connection | Must be 600 or stricter |
| Wrong group in shared dir | New files not group-writable | Set setgid: chmod g+s dir/ |
Viewing permissions
ls -l file.txt # Standard view
ls -la # Include hidden files
ls -ld dir/ # Directory itself, not contents
stat file.txt # Full details: inode, permissions in octal, timestamps
getfacl file.txt # ACL details (if ACLs are enabled)
Permissions as octal:
stat -c "%a %n" file.txt # Print octal + name (e.g., 644 file.txt)
stat -c "%a %n" * # All files in current directory
FAQ
What does chmod 755 mean exactly?
7=rwx (owner), 5=r-x (group), 5=r-x (others). Owner can read, write, and execute. Group and others can read and execute but not write. Standard for web server directories and scripts.
What's the difference between chmod 644 and chmod 664?644 gives the group read-only (r--). 664 gives the group read+write (rw-). Use 664 in collaborative environments where the group needs to edit files.
Why can't I delete a file I own if the directory is owned by root?
Deletion is controlled by directory write permission, not the file's permissions. You need w on the parent directory to remove a file from it.
What's the sticky bit /tmp for?/tmp is world-writable (777) so anyone can create files. The sticky bit (t) prevents users from deleting each other's files — you can only delete files you own, even in a shared directory.
How do I find files with insecure permissions?
# World-writable files (excluding /proc and /sys)
find / -not \( -path /proc -prune -o -path /sys -prune \) -perm -o+w -type f
# SUID/SGID files (security audit)
find / -perm /6000 -type f 2>/dev/null
# Files readable only by root
find /etc -perm 600 -o -perm 400 2>/dev/null
Can I set permissions without knowing the current ones?
Yes — chmod u=rw,go=r file sets permissions exactly regardless of what they were before (unlike + or - which modify existing permissions).