Navigating the Filesystem

Summary: in this tutorial, you will learn learn the linux directory structure, essential navigation commands (pwd, cd, ls), and absolute vs relative paths.

Navigating the Filesystem

Everything in Linux is organized in a hierarchical tree-like filesystem. Before you can do anything useful—edit files, run programs, analyze logs—you need to know how to navigate this structure. Think of the filesystem as a building: directories (folders) are rooms, files are objects in those rooms, and paths are the directions to get there.

Why filesystem navigation matters:

  • Foundation of everything: Every command operates on files and directories
  • Context awareness: Understanding where you are prevents accidental file operations in the wrong location
  • Efficiency: Mastering navigation shortcuts saves hours of typing
  • Remote work: When SSH'd into a server, the GUI doesn't exist—navigation is everything

This tutorial teaches you the essential commands (pwd, cd, ls) and concepts (absolute vs relative paths, wildcards) that form the foundation of working with any Unix-like system.

The Linux Directory Structure

Linux follows the Filesystem Hierarchy Standard (FHS), a standard directory layout used by virtually all Unix-like systems. Understanding this structure helps you know where to find things and where to put things.

/                  ← Root (the top-level directory—everything starts here)
├── bin/           ← Essential user binaries (ls, cp, mv, bash)
├── boot/          ← Boot loader files (kernel, initrd)
├── dev/           ← Device files (hard drives, USB, terminals)
├── etc/           ← System configuration files
├── home/          ← User home directories
│   ├── alice/     ← Alice's personal files
│   └── bob/       ← Bob's personal files
├── lib/           ← Shared libraries (like Windows DLLs)
├── media/         ← Mount points for removable media (USB drives, CDs)
├── mnt/           ← Mount points for temporary filesystems
├── opt/           ← Optional/third-party software
├── proc/          ← Virtual filesystem for process info (not real files!)
├── root/          ← Root user's home directory (not /home/root!)
├── sbin/          ← System administration binaries (requires root)
├── srv/           ← Service data (web servers, FTP)
├── sys/           ← Virtual filesystem for system/hardware info
├── tmp/           ← Temporary files (cleared on reboot)
├── usr/           ← User programs and data (read-only)
│   ├── bin/       ← User binaries (most commands you use)
│   ├── lib/       ← Libraries for /usr/bin programs
│   ├── local/     ← Locally installed software (not from packages)
│   └── share/     ← Shared data (docs, icons, man pages)
└── var/           ← Variable data (changes during operation)
    ├── log/       ← Log files (application and system logs)
    ├── tmp/       ← Temporary files (preserved across reboots)
    └── www/       ← Web server files (on many systems)

Key Directory Purposes

DirectoryPurposeExamples
/binEssential commands needed in single-user models, cp, cat, bash
/etcSystem configuration filesnginx.conf, passwd, fstab
/homeUser home directories/home/alice, /home/bob
/tmpTemporary files (anyone can write)Session data, temp downloads
/usr/binMost user commandspython, git, vim, wget
/var/logLog filessyslog, auth.log, nginx/access.log
/optThird-party applications/opt/google/chrome
/devDevice files/dev/sda1 (hard drive), /dev/null

ℹ️ Everything is a file

In Linux, virtually everything is represented as a file—regular files, directories, hardware devices (/dev/sda1), processes (/proc/1234), and even network connections. This "everything is a file" philosophy is one of Unix/Linux's most powerful design decisions, enabling uniform access patterns across different resources.

Why this matters: When you see a command like sudo nano /etc/nginx/nginx.conf, you immediately know:

  • /etc = system configuration
  • nginx/ = nginx-specific config
  • Requires sudo because system configs aren't user-writable

Absolute vs Relative Paths

Understanding paths is absolutely fundamental. Every file and directory has a path—the "address" of where it lives.

Absolute Paths

An absolute path always starts from the root directory (/) and specifies the complete location.

/home/alice/Documents/report.txt
/etc/nginx/nginx.conf
/var/log/syslog
/usr/bin/python3
 

Characteristics:

  • Always starts with /
  • Works from anywhere (context-independent)
  • Unambiguous—only one meaning
  • Longer to type

When to use absolute paths:

  • Scripts (so they work regardless of where you run them)
  • Referring to system files (/etc, /var/log)
  • When you need certainty about the exact location

Relative Paths

A relative path starts from your current directory and doesn't begin with /.

# If you're in /home/alice:
Documents/report.txt              # Same as /home/alice/Documents/report.txt
../bob/file.txt                   # Go up to /home, then into bob/
../../etc/hostname                # Go up twice to /, then into etc/
 

Characteristics:

  • Does NOT start with /
  • Depends on current directory (context-dependent)
  • Shorter to type
  • Can break if you're not where you think you are

When to use relative paths:

  • Interactive work (faster typing)
  • Within a project directory structure
  • Temporary navigation

Special Path Symbols

These special symbols save massive amounts of typing:

SymbolMeaningExampleResult
/Root directorycd /Go to root
~Your home directorycd ~/DocumentsGo to your Documents folder
.Current directory./script.shRun script in current directory
..Parent directory (one level up)cd ..Go up one level
-Previous directorycd -Toggle to last location
~userAnother user's homecd ~bobGo to bob's home (if allowed)

Example workflow:

pwd                    # /home/alice
cd /var/log            # Absolute path to logs
pwd                    # /var/log
cd ~/Projects          # ~ expands to /home/alice
pwd                    # /home/alice/Projects
cd ..                  # Go up one level
pwd                    # /home/alice
cd -                   # Go back to previous directory
pwd                    # /home/alice/Projects
 

💡 The tilde (~) is your friend

~ always expands to your home directory, no matter where you are. This makes commands portable:

  • cd ~ always takes you home
  • cp file.txt ~/backup/ always copies to your backup folder
  • ~/.bashrc always refers to your personal config

Much better than typing /home/alice every time!

pwd — Where Am I?

The pwd command (Print Working Directory) shows your current location in the filesystem. This is your "GPS coordinates" in the terminal.

pwd
# Output: /home/alice
 
# After navigating somewhere
cd /var/log
pwd
# Output: /var/log
 
# The environment variable $PWD also contains this info
echo $PWD
# Output: /var/log
 

Why you need pwd:

  • Orientation: When you open a terminal, you might not know where you are
  • Confirmation: Before running dangerous commands (rm, mv), verify your location
  • Scripting: Capture the current directory to return to later
  • Debugging: When commands fail, check if you're in the right place
# Common pattern: save location, do work elsewhere, return
original_dir=$(pwd)
cd /tmp
# ... do some work ...
cd "$original_dir"  # Return to where you started
 

If you ever feel lost in the terminal, pwd is your GPS. Use it frequently when learning! Combine with ls to see what's around you: pwd; ls

cd — Moving Around

The cd command (Change Directory) is how you move through the filesystem. It's the most frequently used command you'll type.

Basic cd Usage

# Go to your home directory (all of these are equivalent)
cd
cd ~
cd $HOME
 
# Go to an absolute path
cd /var/log                      # System logs
cd /etc/nginx                    # Nginx configuration
cd /home/alice/Documents         # Specific directory
 
# Go to a relative path (from current location)
cd Documents                     # Move into Documents subdirectory
cd Documents/Projects            # Move into nested directory
cd Projects/my-app/src          # Multiple levels at once
 
# Go up one level (to parent directory)
cd ..
 
# Go up two levels
cd ../..
 
# Go up and into a sibling directory
cd ../other-directory
 
# Go to the previous directory (toggle between two locations)
cd -
 
# Go to another user's home (if you have permission)
cd ~bob
 

Advanced cd Patterns

# Start in home directory
cd ~
pwd                              # /home/alice
 
# Navigate to a deeply nested project
cd Documents/Projects/web-app/frontend/src/components
pwd                              # /home/alice/Documents/Projects/web-app/frontend/src/components
 
# Quick jump to parent directory
cd ..
pwd                              # /home/alice/Documents/Projects/web-app/frontend/src
 
# Jump multiple levels up
cd ../../..
pwd                              # /home/alice/Documents/Projects
 
# Toggle between two directories (very useful!)
cd /var/log
pwd                              # /var/log
cd /etc/nginx
pwd                              # /etc/nginx
cd -                             # Back to /var/log
pwd                              # /var/log
cd -                             # Back to /etc/nginx
pwd                              # /etc/nginx
 
# Go to root, then home
cd /
pwd                              # /
cd
pwd                              # /home/alice
 

Tab Completion: Your Superpower

Tab completion is the single most important keyboard shortcut for navigation. It:

  • Saves typing
  • Prevents typos
  • Shows you what's available
  • Works with commands, files, directories, and variables

How it works:

  1. Type the first few letters of a directory name
  2. Press Tab
  3. If there's one match, it auto-completes
  4. If there are multiple matches, press Tab twice to see all options
# Example: navigating to /etc/nginx/
cd /etc/ng<Tab>          # Completes to: cd /etc/nginx/
cd /etc/nginx/conf<Tab>  # Completes to: cd /etc/nginx/conf.d/
 
# Multiple matches: press Tab twice to see options
cd /etc/n<Tab><Tab>
# Shows: netconfig network/ NetworkManager/ nginx/
 
# You can then type more characters and Tab again
cd /etc/ng<Tab>          # Now completes uniquely to nginx/
 

💡 Use Tab completion religiously!

Never type full directory names manually. Always use Tab completion. It's faster, prevents errors, and shows you what exists. This habit alone will make you 10x faster in the terminal.

Common cd Mistakes and Solutions

Problem: cd to a directory with spaces

# Wrong (interprets as two arguments)
cd My Documents          # Error: bash: cd: My: No such file or directory
 
# Right (quote the path)
cd "My Documents"
cd 'My Documents'
cd My\ Documents         # Escape the space
 

Problem: Permission denied

cd /root                 # Error: Permission denied (unless you're root)
sudo cd /root            # Still doesn't work (cd is a shell builtin)
 
# Solution: Use sudo -i or su to become root first
sudo -i                  # Become root
cd /root                 # Now works
 

ls — Listing Contents

The ls command (List) shows the contents of a directory. It's how you see what files and directories exist.

Basic ls Usage

# List files in current directory
ls
 
# List files in a specific directory
ls /etc
 
# List with details (long format)
ls -l
 
# List all files (including hidden files starting with .)
ls -a
 
# Combine options: long format + all files
ls -la
 
# Human-readable file sizes (KB, MB, GB)
ls -lh
 

Understanding ls -l Output

The long format (ls -l) shows detailed information about each file:

ls -l
 

Output:


-rw-r--r--  1 alice  staff   4096 Jan 15 10:30 document.txt
drwxr-xr-x  3 alice  staff   4096 Jan 14 09:15 Projects
lrwxrwxrwx  1 alice  staff     15 Jan 13 08:00 link -> /tmp/file

Let's decode each column:


-rw-r--r--  1  alice  staff  4096  Jan 15 10:30  document.txt
│├─┤├─┤├─┤  │   │      │      │        │            │
│ │  │  │   │   │      │      │        │            └─ Filename
│ │  │  │   │   │      │      │        └─ Last modified date/time
│ │  │  │   │   │      │      └─ Size in bytes
│ │  │  │   │   │      └─ Group owner
│ │  │  │   │   └─ User owner
│ │  │  │   └─ Number of hard links
│ │  │  └─ Others permissions (read, no write, no execute)
│ │  └─ Group permissions (read, no write, no execute)
│ └─ Owner permissions (read, write, no execute)
└─ File type

File Types (First Character)

CharacterTypeExample
-Regular file-rw-r--r-- document.txt
dDirectorydrwxr-xr-x Projects/
lSymbolic linklrwxrwxrwx link -> target
cCharacter devicecrw-rw-rw- /dev/tty
bBlock devicebrw-rw---- /dev/sda1
pNamed pipe (FIFO)prw-r--r-- pipe
sSocketsrwxrwxrwx socket

Permission Characters

Permissions are shown as 9 characters in 3 groups of 3:


rwxr-xr-x
│││││││││
│││└┬┘└┬┘
│││ │  └─ Others: read + execute
│││ └─ Group: read + execute
│└┴─ Owner: read + write + execute

CharacterMeaningFor FilesFor Directories
rReadView file contentsList directory contents
wWriteModify fileCreate/delete files in directory
xExecuteRun as programEnter directory (cd)
-No permissionCannot perform actionCannot perform action

Essential ls Options

# Human-readable sizes (KB, MB, GB instead of bytes)
ls -lh
# Output: -rw-r--r--  1 alice  staff  4.0K Jan 15 10:30 document.txt
 
# Sort by modification time (newest first)
ls -lt
 
# Sort by modification time (oldest first)
ls -ltr
 
# Sort by size (largest first)
ls -lS
 
# Sort by size (smallest first)
ls -lSr
 
# Recursive (show contents of subdirectories)
ls -R
 
# Show only directories
ls -d */
 
# One file per line (useful for scripting)
ls -1
 
# Show file type indicators
ls -F
# / = directory, * = executable, @ = symlink, | = pipe
 
# All files, long format, human-readable, sorted by time
ls -alht
 
# List with full timestamps
ls -l --time-style=full-iso
 
# List inode numbers (useful for debugging hard links)
ls -li
 
# List with colors (usually aliased by default)
ls --color=auto
 

Practical ls Examples

# Find the largest files in a directory
ls -lhS /var/log | head -10
 
# Find recently modified files
ls -lt ~/Documents | head -10
 
# See hidden configuration files in your home directory
ls -la ~ | grep '^\.'
 
# Count files in a directory
ls -1 /etc | wc -l
 
# List only .txt files
ls -la *.txt
 
# List files matching a pattern
ls -la report_202*.pdf
 
# Show directory size summaries with du instead
ls -lh --block-size=M
du -sh */                         # Better for directory sizes
 
# List files modified in the last 24 hours
ls -lt | grep "$(date '+%b %e')"
 
# List files by extension, sorted
ls -la | grep '\.txt$' | sort
 
Was this page helpful?
SR

Written by the ShellRAG Team

The ShellRAG editorial team writes practical, beginner-friendly Bash Shell tutorials with tested code examples and real-world use cases. Every article is technically reviewed for accuracy and updated regularly.

Learn more about us →