Linux Basics
Permissions
Permissions are one of the most common reasons things break on Linux servers. A script will not run. A service cannot read its config file. An application cannot write to its log directory. A cron job fails silently at 3 AM and nobody knows why. Nine times out of ten, the answer is permissions.
After this page, you should be able to:
- Read and interpret Linux permission strings like
-rwxr-xr-- - Use
chmodto change file permissions using both symbolic and numeric modes - Use
chownto change file and directory ownership - Apply the permission troubleshooting pattern to diagnose and fix access issues
- Recognize common permission requirements for real-world scenarios (SSH keys, web servers, scripts)
Why Permissions Matter
Every file and directory on a Linux system has permissions that control who can read it, who can modify it, and who can execute it. This is not academic — it is the security model that keeps a multi-user system from being chaos.
Here are real-world problems caused by incorrect permissions:
- Script will not execute — you wrote a bash script but forgot to add execute permission. You run it and get "Permission denied."
- Service cannot read its config — the config file is owned by your user account, but the service runs as a different user (like
www-dataornginx). It cannot read the file. - Application cannot write logs — the log directory exists, but the application user does not have write permission to it. Logs silently fail.
- Cron job fails silently — a scheduled task runs as root but tries to access files owned by another user, or vice versa.
- SSH refuses to connect — your private key file has permissions that are too open. SSH will not use a key that other users can read.
When something mysteriously does not work on Linux, checking permissions should be one of the first things you do. Understanding this system will save you hours of confused debugging.
Reading Permission Strings
When you run ls -la, you see something like this at the beginning of each line:
-rwxr-xr-- 1 jake staff 2048 Jan 15 10:30 script.sh drwxr-xr-x 3 jake staff 96 Jan 15 09:00 projects/ -rw-r--r-- 1 jake staff 512 Jan 15 08:45 config.txt
That first column is the permission string. It looks like gibberish until you know the pattern — then it becomes instantly readable.
Breaking It Down: Character by Character
A permission string is exactly 10 characters. Here is what each position means:
- rwx r-x r-- │ │││ │││ │││ │ │││ │││ └── Others (everyone else): read only │ │││ └── Group: read + execute │ └── Owner: read + write + execute └── File type: - = file, d = directory, l = symlink
The first character tells you what kind of thing it is:
-— regular filed— directoryl— symbolic link
The remaining 9 characters are three groups of three, each representing permissions for a different audience:
- Characters 2-4: Owner — the user who owns the file
- Characters 5-7: Group — members of the file's group
- Characters 8-10: Others — everyone else on the system
Within each group of three, the characters are always in the same order:
r— read (or-if not granted)w— write (or-if not granted)x— execute (or-if not granted)
Practice Reading Permissions
-rwxr-xr-- Owner: read, write, execute | Group: read, execute | Others: read -rw-r--r-- Owner: read, write | Group: read | Others: read -rwx------ Owner: read, write, execute | Group: nothing | Others: nothing drwxr-xr-x Directory | Owner: full | Group: read, execute | Others: read, execute
Run ls -la in your home directory and practice reading the permission strings on your own files. After a few minutes it becomes second nature.
chmod — Changing Permissions
chmod (change mode) modifies the permissions on a file or directory. There are two ways to use it: symbolic mode and numeric mode. Both do the same thing — you will use whichever feels more natural for the situation.
Symbolic Mode
Symbolic mode uses letters to add or remove specific permissions. It is intuitive for quick changes.
chmod +x script.sh # Add execute permission for everyone chmod -w file.txt # Remove write permission for everyone chmod u+x script.sh # Add execute for the owner (u = user/owner) chmod g+w file.txt # Add write for the group (g = group) chmod o-r secret.txt # Remove read for others (o = others) chmod u+rwx,g+rx,o+r file.txt # Set specific permissions for each
The letters: u = user/owner, g = group, o = others, a = all (everyone). + adds a permission, - removes it.
Numeric Mode
Numeric mode uses a three-digit number where each digit represents the permissions for owner, group, and others respectively. Each permission has a numeric value:
- Read (r) = 4
- Write (w) = 2
- Execute (x) = 1
You add the values together to get each digit:
7 = 4 + 2 + 1 = rwx (read + write + execute) 6 = 4 + 2 = rw- (read + write) 5 = 4 + 1 = r-x (read + execute) 4 = 4 = r-- (read only) 0 = = --- (no permissions)
Common Permission Sets
You do not need to memorize every combination. In practice, you will use the same handful of permission sets over and over:
chmod 755 script.sh # Owner: full | Others: read + execute
# Use for: executable scripts, directories
chmod 644 config.txt # Owner: read + write | Others: read only
# Use for: config files, HTML files, most regular files
chmod 600 id_rsa # Owner: read + write | Others: nothing
# Use for: SSH private keys, secrets, credentials
chmod 700 private/ # Owner: full | Others: nothing
# Use for: private scripts, personal directoriesMemorize 755, 644, and 600
These three cover the vast majority of real-world situations. 755 for things that need to be executable. 644 for files that should be readable but not executable. 600 for files that only the owner should see. If you know these three, you can handle most permission problems.
Recursive Permissions: chmod -R
Need to change permissions on a directory and everything inside it? Use the -R flag for recursive.
chmod -R 755 /var/www/html/
Be careful with recursive chmod — it applies to every file and subdirectory. Make sure you are targeting the right directory before running this.
chown — Changing Ownership
chown (change owner) changes who owns a file or directory. Every file on Linux has an owner (a user) and a group. Sometimes the permissions are fine but the wrong user owns the file, which means the right user cannot access it.
chown jake file.txt # Change owner to jake chown jake:staff file.txt # Change owner to jake and group to staff chown :staff file.txt # Change only the group to staff chown -R jake:staff /var/www/ # Recursive — change everything inside
When You Need chown
- Files created by the wrong user — you copied files as root, but the web server runs as
www-dataand cannot read them - Deployment scripts — your deployment process creates files as one user, but the application runs as another
- Service accounts — a service like Nginx or PostgreSQL needs to own its data and config directories
- After extracting archives — unpacking a
tarfile can preserve the original ownership, which might not match your system
Note: chown usually requires sudo because changing ownership of files is a privileged operation. Only root can give files to other users.
The Permission Troubleshooting Pattern
There is a consistent pattern you will follow every time something fails due to permissions. Internalize this workflow — you will use it constantly.
When something fails on Linux, check permissions FIRST
Before you start debugging code, checking network settings, or reinstalling packages — run ls -la on the file or directory in question. The answer is often right there in the permission string.
The pattern:
- Something fails — you get "Permission denied," a service will not start, or a script will not run
- Check the file — run
ls -laon the file or directory to see permissions and ownershipls -la /path/to/the/file
- Identify the problem — is the owner wrong? Is the execute bit missing? Does the group not have read access?
- Fix it — use
chmodto fix permissions orchownto fix ownershipchmod 755 script.sh # Fix permissions sudo chown appuser:appgroup config.txt # Fix ownership
- Verify — run
ls -laagain to confirm the change, then test if the original problem is resolved
Try It — Permission Debugging
Walk through this exercise step by step on your Linux VM. You are going to create a script, break it with permissions, and fix it — the exact workflow you will follow on the job.
- Create a bash script. Run these two commands to create a simple script file:
echo '#!/bin/bash' > test.sh echo 'echo "Hello from the script!"' >> test.sh
- Check the permissions. Run
ls -la test.shand read the permission string. Notice there is nox(execute) permission. - Try to run it. Run
./test.shand observe the "Permission denied" error. This is the exact error that trips up beginners. - Fix it. Run
chmod +x test.shto add execute permission. - Verify the fix. Run
ls -la test.shagain — you should now seexin the permission string. - Run it. Run
./test.sh— it works. That single missing permission was the entire problem. - Change ownership to root. Run
sudo chown root:root test.shto make root the owner. - See what changes. Run
ls -la test.shand notice the owner and group columns now sayroot. - Try to edit it. Run
nano test.shand try to save a change. Depending on the permissions, you may get a warning or be unable to save. This is ownership in action — even if the permissions say writable, the owner is now root, not you. - Try to delete it. Run
rm test.sh. Depending on your directory permissions, you might be able to delete it or you might get "Permission denied." Note that deletion depends on the directory permissions, not the file permissions. - Clean up. If
rmdid not work, usesudo rm test.shto remove the file. - Bonus: Try numeric permissions. Create the script again and experiment with different numeric modes:
echo '#!/bin/bash' > test2.sh echo 'echo "Testing permissions"' >> test2.sh chmod 644 test2.sh # Try to run it — fails (no execute) chmod 755 test2.sh # Try to run it — works chmod 000 test2.sh # Try to read it — fails (no permissions) chmod 644 test2.sh # Restore read/write rm test2.sh # Clean up
Common Permission Scenarios on the Job
Here are specific situations you will encounter in real IT work and the permissions that go with them. These are worth committing to memory.
SSH Key Permissions
SSH is extremely strict about key file permissions. If your private key is readable by anyone other than you, SSH will refuse to use it and print a warning about "unprotected private key file."
chmod 600 ~/.ssh/id_rsa # Private key: owner read/write only chmod 644 ~/.ssh/id_rsa.pub # Public key: readable by everyone chmod 700 ~/.ssh/ # .ssh directory: owner only
This is one of the most common "why can't I SSH in?" problems. If you copy your key to a new machine and SSH does not work, check the permissions first.
Web Server Files
A web server (like Nginx or Apache) needs to read your website files but should never need to write to them. The web server process typically runs as a user like www-data.
sudo chown -R www-data:www-data /var/www/html/
chmod -R 755 /var/www/html/ # Directories: read + execute
find /var/www/html -type f -exec chmod 644 {} \; # Files: read onlyLog Directories
Application log directories need to be writable by the service user. If an application cannot write to its log directory, it may fail silently or crash.
sudo mkdir -p /var/log/myapp sudo chown appuser:appuser /var/log/myapp chmod 755 /var/log/myapp
Executable Scripts
Any script you want to run directly (with ./script.sh) needs execute permission. This is the most common permission issue for people new to Linux.
chmod +x deploy.sh # Quick: add execute for everyone chmod 755 deploy.sh # Explicit: owner full, others read + execute
Sensitive Configuration Files
Files containing passwords, API keys, or database credentials should be locked down so only the owner (or service account) can read them.
chmod 600 /etc/myapp/secrets.conf sudo chown appuser:appuser /etc/myapp/secrets.conf
Never leave sensitive files world-readable (644). Anyone on the system could read them. Use 600 so only the owner has access.
Checkpoint
Before moving on, make sure you can do all of the following:
- Read a permission string like
-rwxr-xr--and explain what each part means - Identify the owner, group, and others sections in a permission string
- Explain the numeric values: what does
755mean? What about644? And600? - Use
chmod +xto make a script executable - Use
chmodwith a numeric mode to set specific permissions - Use
chownto change the owner of a file - Follow the troubleshooting pattern: something fails, check
ls -la, identify the problem, fix withchmodorchown, verify - Explain why SSH keys need
600permissions - Create a script, observe "Permission denied," and fix it
Permissions are one of those things that come up on every single Linux system you will ever touch. The concepts on this page will serve you for your entire career. If something does not work and you cannot figure out why — check the permissions.