- Introduction
- Linux Administration Series
- Linux Storage Stack Architecture
- Block Devices and Disk Architecture
- Disk Partitioning
- Filesystem Types
- Mounting Filesystems
- Logical Volume Manager (LVM)
- RAID Configuration
- Disk Encryption with LUKS
- Disk Quotas
- Storage Monitoring and Health
- Production Best Practices
- Troubleshooting Common Issues
- Frequently Asked Questions
- Conclusion
Introduction
Storage management is a fundamental aspect of Linux system administration. Proper storage configuration ensures data integrity, optimal performance, and efficient space utilization. This comprehensive guide covers disk partitioning, filesystem types, Logical Volume Manager (LVM), RAID configurations, encryption, and disk quotas.
We'll explore block device architecture, partitioning schemes (GPT vs MBR), filesystem selection (ext4, XFS, Btrfs), LVM for flexible storage management, software RAID for redundancy, LUKS encryption for security, and quota enforcement for multi-user systems. Each section includes practical examples and production scenarios.
Linux Administration Series
📚 View Complete Linux Administration Guide - Master all 7 parts with our comprehensive learning path.
This is Part VII of our comprehensive 7-part Linux administration guide:
- Part I: File System & Process Management
- Part II: User Authentication & LDAP
- Part III: UFW Firewall & Networking
- Part IV: systemd & SSH Hardening
- Part V: Postfix Email Server
- Part VI: QEMU KVM Virtualization
- Part VII: LVM & RAID Storage (Current Article)
Linux Storage Stack Architecture
Storage Layer Overview
Key Storage Components:
- Hardware Layer - Physical disks (HDD, SSD, NVMe)
- Block Devices - Kernel representation of storage devices
- Partitions - Logical divisions of physical disks
- Volume Management - LVM, RAID, encryption layer
- Filesystems - Data organization structure (ext4, XFS, Btrfs)
- Mount Points - Integration with directory tree
Block Devices and Disk Architecture
Understanding Block Devices
Block devices are storage devices that allow data access in fixed-size blocks. Linux represents them as files in /dev/:
Common device naming conventions:
| Device Type | Naming Pattern | Example |
|---|---|---|
| SATA/SCSI | /dev/sd[a-z] | /dev/sda, /dev/sdb |
| NVMe | /dev/nvme[0-9]n[0-9] | /dev/nvme0n1 |
| Virtual | /dev/vd[a-z] | /dev/vda (KVM/QEMU) |
| MMC/SD | /dev/mmcblk[0-9] | /dev/mmcblk0 |
| RAID | /dev/md[0-9] | /dev/md0 |
| LVM | /dev/mapper/* | /dev/mapper/vg0-lv0 |
Exploring block devices:
# List all block devices with hierarchy
lsblk
# Example output:
# NAME MAJ:MIN RM SIZE RO TYPE MOUNTPOINT
# sda 8:0 0 238.5G 0 disk
# ├─sda1 8:1 0 512M 0 part /boot/efi
# ├─sda2 8:2 0 230G 0 part
# │ └─vg0-root 254:0 0 230G 0 lvm /
# └─sda3 8:3 0 8G 0 part [SWAP]
# List with filesystem type and UUID
lsblk -f
# Show detailed block device information
sudo blkid
# Output:
# /dev/sda1: UUID="A1B2-C3D4" TYPE="vfat" PARTUUID="..."
# /dev/sda2: UUID="..." TYPE="LVM2_member" PARTUUID="..."
# Get device information
sudo fdisk -l /dev/sda
sudo parted /dev/sda print
# Check device capacity and usage
df -h # mounted filesystems
sudo df -h # include system mounts
lsblk -o NAME,SIZE,FSTYPE,MOUNTPOINT
# View I/O statistics
iostat
iostat -x 1 5 # extended stats, 1s interval, 5 iterations
# Check SMART health (for physical disks)
sudo apt install smartmontools
sudo smartctl -H /dev/sda # health status
sudo smartctl -a /dev/sda # all information
sudo smartctl -t short /dev/sda # run short test
Disk Partitioning
Partition Table Types
MBR vs GPT comparison:
| Feature | MBR | GPT |
|---|---|---|
| Max Disk Size | 2 TB | 9.4 ZB (zettabytes) |
| Max Partitions | 4 primary (+ extended) | 128 |
| Boot Mode | BIOS | UEFI (BIOS compatible) |
| Redundancy | No | Backup partition table |
| Data Protection | No CRC | CRC32 checksums |
| OS Support | All | Modern Linux, Windows 8+ |
Partitioning with fdisk (MBR)
# Launch fdisk for /dev/sdb
sudo fdisk /dev/sdb
# fdisk commands:
m # help menu
p # print partition table
n # create new partition
d # delete partition
t # change partition type
l # list partition types
w # write changes and exit
q # quit without saving
# Example workflow:
# 1. Create new partition
n
# Select: primary (p) or extended (e)
p
# Partition number: 1
# First sector: (press Enter for default)
# Last sector: +10G (10 GB partition)
# 2. Set partition type
t
# Partition number: 1
# Hex code: 83 (Linux), 82 (swap), 8e (LVM)
# 3. Review changes
p
# 4. Write changes
w
# Reload partition table
sudo partprobe /dev/sdb
# or
sudo partx -u /dev/sdb
Partitioning with parted (GPT)
# Launch parted
sudo parted /dev/sdb
# Parted commands:
print # show partition table
mklabel gpt # create GPT partition table
mklabel msdos # create MBR partition table
mkpart # create partition
rm 1 # remove partition 1
resizepart # resize partition
quit # exit
# Example: Create GPT disk with 3 partitions
sudo parted /dev/sdb mklabel gpt
sudo parted /dev/sdb mkpart primary ext4 1MiB 20GiB
sudo parted /dev/sdb mkpart primary ext4 20GiB 50GiB
sudo parted /dev/sdb mkpart primary ext4 50GiB 100%
# View result
sudo parted /dev/sdb print
# One-liner examples
sudo parted /dev/sdb mklabel gpt
sudo parted -a optimal /dev/sdb mkpart primary ext4 0% 100%
# Align partition optimally
sudo parted -a optimal /dev/sdb mkpart primary 1MiB 100%
Partition Type Codes
# Common partition types (fdisk hex codes)
83 # Linux filesystem
82 # Linux swap
8e # Linux LVM
fd # Linux RAID auto
ef # EFI System Partition
# GPT partition type GUIDs (parted)
# Linux filesystem: 0FC63DAF-8483-4772-8E79-3D69D8477DE4
# Linux swap: 0657FD6D-A4AB-43C4-84E5-0933C84B4F4F
# Linux LVM: E6D6D379-F507-44C2-A23C-238F2A3DF928
Filesystem Types
Filesystem Comparison
Detailed filesystem comparison:
| Feature | ext4 | XFS | Btrfs | FAT32 |
|---|---|---|---|---|
| Max File Size | 16 TB | 8 EB | 16 EB | 4 GB |
| Max Filesystem | 1 EB | 8 EB | 16 EB | 2 TB |
| Journaling | Yes | Yes | Yes | No |
| Snapshots | No | No | Yes | No |
| Compression | No | No | Yes | No |
| Online Resize | Grow only | Grow only | Grow/Shrink | No |
| Best For | General use | Large files, databases | Advanced features | USB drives |
| Maturity | Stable | Stable | Stable (caution) | Legacy |
Creating Filesystems
# Create ext4 filesystem (ext4 documentation: https://www.kernel.org/doc/html/latest/filesystems/ext4/index.html)
sudo mkfs.ext4 /dev/sdb1
sudo mkfs.ext4 -L mydata /dev/sdb1 # with label
sudo mkfs.ext4 -m 1 /dev/sdb1 # 1% reserved for root
sudo mkfs.ext4 -j /dev/sdb1 # with journal
# Create XFS filesystem (XFS documentation: https://xfs.wiki.kernel.org/)
sudo mkfs.xfs /dev/sdb2
sudo mkfs.xfs -L mydata /dev/sdb2 # with label
sudo mkfs.xfs -f /dev/sdb2 # force (if partition not empty)
# Create Btrfs filesystem
sudo mkfs.btrfs /dev/sdb3
sudo mkfs.btrfs -L mydata /dev/sdb3 # with label
sudo mkfs.btrfs -f /dev/sdb3 # force
# Create FAT32 (for USB/compatibility)
sudo mkfs.vfat -F 32 /dev/sdb4
sudo mkfs.vfat -F 32 -n MYUSB /dev/sdb4 # with label
# Create swap partition
sudo mkswap /dev/sdb5
sudo mkswap -L swap /dev/sdb5 # with label
sudo swapon /dev/sdb5 # activate swap
sudo swapon -s # show active swap
# Verify filesystem
sudo tune2fs -l /dev/sdb1 # ext4 info
sudo xfs_info /dev/sdb2 # XFS info
sudo btrfs filesystem show /dev/sdb3 # Btrfs info
Filesystem Labels and UUIDs
# Set/change filesystem label
sudo e2label /dev/sdb1 mydata # ext2/3/4
sudo xfs_admin -L mydata /dev/sdb2 # XFS
sudo btrfs filesystem label /dev/sdb3 mydata # Btrfs
sudo fatlabel /dev/sdb4 MYUSB # FAT32
# View label
sudo e2label /dev/sdb1
lsblk -o NAME,LABEL
# View UUID
sudo blkid /dev/sdb1
lsblk -o NAME,UUID
# Generate new UUID (ext4)
sudo tune2fs -U random /dev/sdb1
Mounting Filesystems
Mount Workflow
Manual Mounting
# Create mount point
sudo mkdir -p /mnt/data
# Mount filesystem
sudo mount /dev/sdb1 /mnt/data
sudo mount -t ext4 /dev/sdb1 /mnt/data # specify filesystem type
# Mount with options
sudo mount -o rw,noexec,nosuid /dev/sdb1 /mnt/data
# Common mount options:
# rw/ro - read-write / read-only
# noexec - prevent execution of binaries
# nosuid - ignore suid/sgid bits
# nodev - don't interpret device files
# user - allow regular users to mount
# auto/noauto - mount automatically with mount -a
# defaults - rw, suid, dev, exec, auto, nouser, async
# Mount by UUID
sudo mount UUID=a1b2c3d4-e5f6-... /mnt/data
# Mount by label
sudo mount LABEL=mydata /mnt/data
# Remount with different options (without unmounting)
sudo mount -o remount,ro /mnt/data
# Unmount
sudo umount /mnt/data
sudo umount /dev/sdb1
# Force unmount (if busy)
sudo umount -l /mnt/data # lazy unmount
sudo fuser -km /mnt/data # kill processes using mount
sudo umount -f /mnt/data # force unmount
# View mounted filesystems
mount | grep ^/dev
df -h
findmnt
Persistent Mounts with /etc/fstab
# Edit fstab
sudo vim /etc/fstab
# Format: <device> <mountpoint> <type> <options> <dump> <pass>
# Example entries:
# Mount by UUID (recommended)
UUID=a1b2c3d4-e5f6-1234-5678-abcdef123456 /mnt/data ext4 defaults 0 2
# Mount by device (not recommended - device names can change)
/dev/sdb1 /mnt/data ext4 defaults 0 2
# Mount by label
LABEL=mydata /mnt/data ext4 defaults 0 2
# Mount with specific options
UUID=... /mnt/storage ext4 rw,noexec,nosuid 0 2
# NFS mount
192.168.1.100:/export/share /mnt/nfs nfs defaults 0 0
# Swap partition
UUID=... none swap sw 0 0
# tmpfs (RAM filesystem)
tmpfs /tmp tmpfs defaults,size=4G 0 0
# Field explanations:
# <dump>: 0=don't backup, 1=backup with dump
# <pass>: 0=don't check, 1=root fs check first, 2=check after root
# Test fstab before reboot
sudo mount -a # mount all from fstab
sudo findmnt --verify # verify fstab syntax
# Get UUID for fstab
sudo blkid /dev/sdb1
Automount with autofs
# Install autofs
sudo apt install autofs
# Configure master map
sudo vim /etc/auto.master
# Add:
/mnt/auto /etc/auto.misc --timeout=60
# Configure mount map
sudo vim /etc/auto.misc
# Add:
data -fstype=ext4 :/dev/sdb1
usb -fstype=vfat,rw,uid=1000 :/dev/sdc1
# Restart autofs
sudo systemctl restart autofs
# Access (will auto-mount)
ls /mnt/auto/data
# Unmounts automatically after timeout
Logical Volume Manager (LVM)
LVM Architecture
LVM Benefits:
- Flexible resizing - Grow/shrink volumes online
- Snapshots - Point-in-time copies for backups
- Striping - Performance improvement across disks
- Mirroring - Data redundancy
- Easy management - Add/remove disks dynamically
Creating LVM Volumes
# Install LVM tools (LVM2 documentation: https://sourceware.org/lvm2/)
sudo apt install lvm2
# 1. Create Physical Volumes (PV)
sudo pvcreate /dev/sdb
sudo pvcreate /dev/sdc
sudo pvcreate /dev/sdd
# Or create PV on partition
sudo pvcreate /dev/sdb1
# Display PVs
sudo pvdisplay
sudo pvs # summary
# 2. Create Volume Group (VG)
sudo vgcreate vg0 /dev/sdb /dev/sdc
# vg0 is the volume group name
# Display VGs
sudo vgdisplay
sudo vgs # summary
# 3. Create Logical Volumes (LV)
sudo lvcreate -L 100G -n lv_root vg0 # 100GB volume
sudo lvcreate -L 500G -n lv_home vg0 # 500GB volume
sudo lvcreate -l 100%FREE -n lv_var vg0 # use remaining space
# Display LVs
sudo lvdisplay
sudo lvs # summary
# 4. Create filesystem on LV
sudo mkfs.ext4 /dev/vg0/lv_root
sudo mkfs.ext4 /dev/vg0/lv_home
sudo mkfs.xfs /dev/vg0/lv_var
# 5. Mount LV
sudo mkdir -p /mnt/root /mnt/home /mnt/var
sudo mount /dev/vg0/lv_root /mnt/root
sudo mount /dev/vg0/lv_home /mnt/home
sudo mount /dev/vg0/lv_var /mnt/var
# Add to /etc/fstab
/dev/vg0/lv_root /mnt/root ext4 defaults 0 2
/dev/vg0/lv_home /mnt/home ext4 defaults 0 2
/dev/vg0/lv_var /mnt/var xfs defaults 0 2
Extending LVM Volumes
# Extend Volume Group (add new disk)
sudo pvcreate /dev/sde
sudo vgextend vg0 /dev/sde
# Check VG free space
sudo vgs
sudo vgdisplay vg0 | grep Free
# Extend Logical Volume
sudo lvextend -L +50G /dev/vg0/lv_home # add 50GB
sudo lvextend -L 600G /dev/vg0/lv_home # resize to 600GB total
sudo lvextend -l +100%FREE /dev/vg0/lv_home # use all free space
# Resize filesystem (online, no unmount needed)
# For ext4:
sudo resize2fs /dev/vg0/lv_home
# For XFS:
sudo xfs_growfs /mnt/var
# One-liner: extend LV and resize filesystem
sudo lvextend -r -L +50G /dev/vg0/lv_home
# -r = resize filesystem automatically
Reducing LVM Volumes
# WARNING: Can cause data loss! Always backup first!
# 1. Unmount filesystem (required for shrinking)
sudo umount /mnt/home
# 2. Check filesystem
sudo e2fsck -f /dev/vg0/lv_home
# 3. Shrink filesystem first (ext4 only - XFS cannot shrink)
sudo resize2fs /dev/vg0/lv_home 400G
# 4. Reduce logical volume
sudo lvreduce -L 400G /dev/vg0/lv_home
# 5. Remount
sudo mount /dev/vg0/lv_home /mnt/home
# Note: XFS does not support shrinking!
# Only ext2/3/4 can be shrunk
LVM Snapshots
# Create snapshot (10GB snapshot space)
sudo lvcreate -L 10G -s -n lv_home_snap /dev/vg0/lv_home
# Mount snapshot (read-only backup)
sudo mkdir /mnt/home_snapshot
sudo mount -o ro /dev/vg0/lv_home_snap /mnt/home_snapshot
# Backup from snapshot
sudo tar czf /backup/home_backup.tar.gz -C /mnt/home_snapshot .
# Remove snapshot
sudo umount /mnt/home_snapshot
sudo lvremove /dev/vg0/lv_home_snap
# Restore from snapshot (reverts changes)
sudo lvconvert --merge /dev/vg0/lv_home_snap
# Reboot required for root volume merge
Removing LVM Components
# Remove Logical Volume
sudo umount /mnt/home
sudo lvremove /dev/vg0/lv_home
# Remove Volume Group
sudo vgremove vg0
# Remove Physical Volume
sudo pvremove /dev/sdb
RAID Configuration
RAID Levels Comparison
RAID Level Details:
| RAID | Min Disks | Capacity | Redundancy | Read Speed | Write Speed | Use Case |
|---|---|---|---|---|---|---|
| 0 | 2 | 100% | None | Excellent | Excellent | Performance (temp data) |
| 1 | 2 | 50% | 1 disk | Good | Fair | OS/boot drives |
| 5 | 3 | 67-94% | 1 disk | Good | Fair | General storage |
| 6 | 4 | 50-88% | 2 disks | Good | Poor | High reliability |
| 10 | 4 | 50% | 1 per pair | Excellent | Good | Databases, high I/O |
Creating Software RAID
# Install mdadm (Linux RAID documentation: https://raid.wiki.kernel.org/)
sudo apt install mdadm
# Create RAID 1 (mirroring with 2 disks)
sudo mdadm --create /dev/md0 \
--level=1 \
--raid-devices=2 \
/dev/sdb /dev/sdc
# Create RAID 5 (parity with 3+ disks)
sudo mdadm --create /dev/md0 \
--level=5 \
--raid-devices=3 \
/dev/sdb /dev/sdc /dev/sdd
# Create RAID 10 (mirror + stripe with 4+ disks)
sudo mdadm --create /dev/md0 \
--level=10 \
--raid-devices=4 \
/dev/sdb /dev/sdc /dev/sdd /dev/sde
# Create RAID 0 (striping - no redundancy)
sudo mdadm --create /dev/md0 \
--level=0 \
--raid-devices=2 \
/dev/sdb /dev/sdc
# Monitor array creation (takes time for large disks)
cat /proc/mdstat
watch cat /proc/mdstat
# View RAID details
sudo mdadm --detail /dev/md0
# Create filesystem on RAID
sudo mkfs.ext4 /dev/md0
# Mount RAID array
sudo mkdir /mnt/raid
sudo mount /dev/md0 /mnt/raid
# Save RAID configuration
sudo mdadm --detail --scan | sudo tee -a /etc/mdadm/mdadm.conf
# Update initramfs
sudo update-initramfs -u
# Add to fstab
/dev/md0 /mnt/raid ext4 defaults 0 2
RAID Management and Monitoring
# Check RAID status
cat /proc/mdstat
sudo mdadm --detail /dev/md0
# Monitor RAID (continuous updates)
watch -n 1 cat /proc/mdstat
# Mark disk as failed (simulate failure)
sudo mdadm --manage /dev/md0 --fail /dev/sdb
# Remove failed disk
sudo mdadm --manage /dev/md0 --remove /dev/sdb
# Add new disk to array
sudo mdadm --manage /dev/md0 --add /dev/sdf
# RAID will automatically rebuild
# Monitor rebuild progress:
cat /proc/mdstat
# Grow RAID array (add disk to RAID 5)
sudo mdadm --add /dev/md0 /dev/sdf
sudo mdadm --grow /dev/md0 --raid-devices=4
# Stop RAID array
sudo umount /mnt/raid
sudo mdadm --stop /dev/md0
# Start RAID array
sudo mdadm --assemble /dev/md0 /dev/sdb /dev/sdc /dev/sdd
# Remove RAID array completely
sudo mdadm --stop /dev/md0
sudo mdadm --remove /dev/md0
sudo mdadm --zero-superblock /dev/sdb /dev/sdc /dev/sdd
Disk Encryption with LUKS
LUKS Encryption Flow
Creating Encrypted Partitions
# Install cryptsetup (LUKS documentation: https://gitlab.com/cryptsetup/cryptsetup)
sudo apt install cryptsetup
# Create encrypted partition
sudo cryptsetup luksFormat /dev/sdb1
# WARNING: This will overwrite data on /dev/sdb1 irrevocably.
# Type 'YES' to confirm
# Enter passphrase: ********
# View LUKS header info
sudo cryptsetup luksDump /dev/sdb1
# Open (decrypt) encrypted partition
sudo cryptsetup open /dev/sdb1 secret
# Enter passphrase: ********
# This creates /dev/mapper/secret
# Create filesystem on decrypted device
sudo mkfs.ext4 /dev/mapper/secret
# Mount encrypted partition
sudo mkdir /mnt/secret
sudo mount /dev/mapper/secret /mnt/secret
# Use normally
echo "sensitive data" | sudo tee /mnt/secret/file.txt
# Unmount and close
sudo umount /mnt/secret
sudo cryptsetup close secret
Automatic Unlock at Boot
# Create key file (instead of passphrase)
sudo dd if=/dev/urandom of=/root/luks-key bs=512 count=1
sudo chmod 400 /root/luks-key
# Add key file to LUKS
sudo cryptsetup luksAddKey /dev/sdb1 /root/luks-key
# Enter existing passphrase: ********
# Configure crypttab
sudo vim /etc/crypttab
# Add entry:
secret /dev/sdb1 /root/luks-key luks
# Add to fstab
sudo vim /etc/fstab
# Add entry:
/dev/mapper/secret /mnt/secret ext4 defaults 0 2
# Update initramfs
sudo update-initramfs -u
# Test (will unlock at boot)
sudo reboot
Encrypting with LVM
# Encrypt partition first
sudo cryptsetup luksFormat /dev/sdb1
sudo cryptsetup open /dev/sdb1 crypt_sdb1
# Create LVM on encrypted device
sudo pvcreate /dev/mapper/crypt_sdb1
sudo vgcreate vg_secure /dev/mapper/crypt_sdb1
sudo lvcreate -L 100G -n lv_data vg_secure
# Create filesystem
sudo mkfs.ext4 /dev/vg_secure/lv_data
# Mount
sudo mount /dev/vg_secure/lv_data /mnt/secure
# This provides: encryption → LVM → filesystem
Managing LUKS Keys
# List key slots
sudo cryptsetup luksDump /dev/sdb1
# Add new passphrase/key
sudo cryptsetup luksAddKey /dev/sdb1
# Enter existing passphrase
# Enter new passphrase
# Remove key slot
sudo cryptsetup luksRemoveKey /dev/sdb1
# Enter passphrase to remove
# Change passphrase
sudo cryptsetup luksChangeKey /dev/sdb1
# Enter existing passphrase
# Enter new passphrase
# Backup LUKS header (critical!)
sudo cryptsetup luksHeaderBackup /dev/sdb1 --header-backup-file /root/luks-header-backup
# Restore LUKS header
sudo cryptsetup luksHeaderRestore /dev/sdb1 --header-backup-file /root/luks-header-backup
Disk Quotas
Quota Enforcement Architecture
Enabling Disk Quotas
# Install quota tools
sudo apt install quota
# Enable quota on filesystem (modify /etc/fstab)
sudo vim /etc/fstab
# Add usrquota and/or grpquota options:
# Before:
/dev/sdb1 /mnt/data ext4 defaults 0 2
# After:
/dev/sdb1 /mnt/data ext4 defaults,usrquota,grpquota 0 2
# Remount filesystem
sudo mount -o remount /mnt/data
# Create quota files
sudo quotacheck -cugm /mnt/data
# -c = create quota files
# -u = user quotas
# -g = group quotas
# -m = don't remount read-only
# This creates:
# /mnt/data/aquota.user
# /mnt/data/aquota.group
# Enable quotas
sudo quotaon /mnt/data
# Verify quota is enabled
sudo quotaon -p /mnt/data
Setting User Quotas
# Edit quota for user
sudo edquota -u username
# Opens editor with:
# Filesystem blocks soft hard inodes soft hard
# /dev/sdb1 1024 100000 110000 10 1000 1100
# Fields:
# blocks - current disk usage (KB)
# soft - soft limit for disk space (KB)
# hard - hard limit for disk space (KB)
# inodes - current file count
# soft - soft limit for file count
# hard - hard limit for file count
# Set quota directly
sudo setquota -u username 100000 110000 1000 1100 /mnt/data
# Format: setquota -u USER BLOCK_SOFT BLOCK_HARD INODE_SOFT INODE_HARD FILESYSTEM
# Example: 10GB soft, 12GB hard, 5000 files soft, 6000 hard
sudo setquota -u john 10485760 12582912 5000 6000 /mnt/data
# Copy quota from one user to another
sudo edquota -p john -u jane
# Set grace period
sudo edquota -t
# Example grace period:
# Block grace period: 7days
# Inode grace period: 7days
Setting Group Quotas
# Edit quota for group
sudo edquota -g developers
# Set quota directly
sudo setquota -g developers 524288000 629145600 50000 60000 /mnt/data
# 500GB soft, 600GB hard for group
# Copy quota from one group to another
sudo edquota -p developers -g designers
Monitoring Quotas
# View user quota
quota -u username
sudo quota -u username # as root
# View group quota
quota -g groupname
# View your own quota
quota
# Report all user quotas
sudo repquota -a # all filesystems
sudo repquota /mnt/data # specific filesystem
sudo repquota -aug # all users and groups
# Example output:
# *** Report for user quotas on device /dev/sdb1
# Block grace time: 7days; Inode grace time: 7days
# Block limits File limits
# User used soft hard grace used soft hard grace
# ----------------------------------------------------------------------
# john -- 102400 100000 110000 6days 850 1000 1100
# jane -- 45000 100000 110000 320 1000 1100
# Check quota status
sudo quotaon -p /mnt/data
Quota Warnings and Enforcement
# User exceeds soft limit:
$ dd if=/dev/zero of=/mnt/data/bigfile bs=1M count=200
sdb1: warning, user block quota exceeded.
# User exceeds hard limit:
$ dd if=/dev/zero of=/mnt/data/bigfile bs=1M count=250
sdb1: write failed, user block quota exceeded.
dd: error writing '/mnt/data/bigfile': Disk quota exceeded
# Check which users are over quota
sudo repquota -a | grep '++'
# ++ indicates over soft limit
# +- indicates over grace period
Disabling Quotas
# Disable quotas temporarily
sudo quotaoff /mnt/data
# Disable quotas permanently
# 1. Turn off quotas
sudo quotaoff /mnt/data
# 2. Edit /etc/fstab (remove usrquota,grpquota)
sudo vim /etc/fstab
# 3. Remount
sudo mount -o remount /mnt/data
# 4. Optional: remove quota files
sudo rm /mnt/data/aquota.*
Storage Monitoring and Health
Monitoring Disk Usage
# Disk space usage by filesystem
df -h # human-readable
df -i # inode usage
df -T # show filesystem type
# Disk usage by directory
du -sh /home/* # summary for each user
du -h --max-depth=1 /var # one level deep
du -h /var | sort -hr | head -20 # top 20 largest
# Find large files
find / -type f -size +1G # files over 1GB
find / -type f -size +100M -exec ls -lh {} \; | sort -k5 -hr
# Disk I/O statistics
iostat -x 1 5 # extended stats, 1s interval, 5 iterations
iostat -d 2 # device stats, 2s interval
# Per-process I/O
sudo iotop
sudo iotop -o # only show processes doing I/O
SMART Monitoring
# Install smartmontools
sudo apt install smartmontools
# Check if SMART is enabled
sudo smartctl -i /dev/sda
# Health status
sudo smartctl -H /dev/sda
# Output: PASSED or FAILED
# View all SMART attributes
sudo smartctl -A /dev/sda
# Key attributes to monitor:
# 5 Reallocated_Sector_Ct - Bad sectors remapped
# 10 Spin_Retry_Count - Spindle retry attempts
# 187 Reported_Uncorrect - Uncorrectable errors
# 188 Command_Timeout - Command timeouts
# 196 Reallocated_Event_Count - Reallocation events
# 197 Current_Pending_Sector - Sectors waiting remap
# 198 Offline_Uncorrectable - Uncorrectable offline
# Run short self-test
sudo smartctl -t short /dev/sda
# Run long self-test
sudo smartctl -t long /dev/sda
# View test results
sudo smartctl -l selftest /dev/sda
# View error log
sudo smartctl -l error /dev/sda
# Enable SMART monitoring daemon
sudo systemctl enable smartd
sudo systemctl start smartd
LVM Monitoring
# Physical volume health
sudo pvs
sudo pvdisplay
# Volume group status
sudo vgs
sudo vgdisplay
# Logical volume status
sudo lvs
sudo lvdisplay
# Check for errors
sudo dmesg | grep -i 'I/O error'
sudo dmesg | grep -i 'failed'
RAID Monitoring
# RAID status
cat /proc/mdstat
# Detailed RAID info
sudo mdadm --detail /dev/md0
# Check for disk failures
sudo mdadm --examine /dev/sdb
# Monitor RAID events
sudo tail -f /var/log/syslog | grep mdadm
# Email notifications on RAID events
sudo vim /etc/mdadm/mdadm.conf
# Add:
MAILADDR your-email@example.com
sudo systemctl restart mdadm
Production Best Practices
-
Partition and Filesystem Selection:
- Use GPT for modern systems (>2TB disks)
- Choose ext4 for general purpose, XFS for large files
- Separate partitions: /, /home, /var, /tmp
- Use LVM for flexibility in production
- Reserve 5-10% free space for optimal performance
-
LVM Strategy:
- Don't allocate all VG space immediately
- Leave 20% free for growth and snapshots
- Use descriptive VG/LV names (vg_data, lv_mysql)
- Create snapshots before major changes
- Monitor thin provisioning carefully
-
RAID Configuration:
- RAID 1 for OS/boot drives
- RAID 10 for databases and high I/O
- RAID 5/6 for bulk storage
- Use hardware RAID for best performance
- Regular scrubbing to detect silent corruption
- Hot spare disks for automatic rebuild
-
Encryption:
- Encrypt sensitive data partitions
- Backup LUKS headers to secure location
- Use key files for servers (with secure permissions)
- Test recovery procedures
- Document encryption keys securely
-
Disk Quotas:
- Implement quotas on multi-user systems
- Set soft limits at 90% of hard limits
- 7-day grace period is standard
- Monitor quota usage with alerts
- Document quota policies
-
Monitoring and Maintenance:
- Monitor disk space with alerts (80% threshold)
- Check SMART status weekly
- Test backups monthly
- RAID scrub monthly
- Review logs for I/O errors
- Capacity planning: forecast 6-12 months ahead
-
Backup Strategy:
- 3-2-1 rule: 3 copies, 2 media types, 1 offsite
- Use LVM snapshots for consistent backups
- Test restore procedures quarterly
- Document recovery procedures
- Automate backup verification
Troubleshooting Common Issues
Filesystem full but df shows space available:
# Check inode usage
df -i
# Find directories with many files
find / -xdev -type d -exec bash -c 'echo "{}: $(find "{}" -maxdepth 1 | wc -l)"' \; | sort -t: -k2 -nr | head
# Delete old files
find /var/log -type f -mtime +30 -delete
Cannot unmount busy filesystem:
# Find processes using filesystem
sudo lsof /mnt/data
sudo fuser -m /mnt/data
# Kill processes
sudo fuser -km /mnt/data
# Lazy unmount
sudo umount -l /mnt/data
LVM volume won't activate:
# Scan for volume groups
sudo vgscan
# Activate volume group
sudo vgchange -ay vg0
# Check logs
sudo dmesg | grep -i lvm
RAID degraded array:
# Check status
cat /proc/mdstat
sudo mdadm --detail /dev/md0
# Replace failed disk
sudo mdadm /dev/md0 --fail /dev/sdb
sudo mdadm /dev/md0 --remove /dev/sdb
# Physically replace disk
sudo mdadm /dev/md0 --add /dev/sdb
# Monitor rebuild
watch cat /proc/mdstat
LUKS partition won't unlock:
# Verify LUKS header
sudo cryptsetup luksDump /dev/sdb1
# Try different key slot
sudo cryptsetup open --key-slot 1 /dev/sdb1 secret
# Restore from header backup
sudo cryptsetup luksHeaderRestore /dev/sdb1 --header-backup-file /backup/luks-header
Disk I/O performance issues:
# Check I/O wait
top # look for high %wa (I/O wait)
# Identify I/O bottleneck
sudo iotop -o
# Check for disk errors
sudo dmesg | grep -i error
sudo smartctl -A /dev/sda
# Test disk performance
sudo hdparm -Tt /dev/sda
sudo dd if=/dev/zero of=/tmp/test bs=1M count=1024 oflag=direct
Frequently Asked Questions
Q: What is the difference between MBR and GPT partitioning?
MBR (Master Boot Record) supports up to 4 primary partitions and 2TB maximum disk size using 32-bit sector addressing. GPT (GUID Partition Table) supports unlimited partitions (128 default), disks larger than 2TB, and includes redundant partition tables for recovery. Use GPT for modern systems and large disks.
Q: What is LVM and why should I use it?
LVM (Logical Volume Manager) provides flexible storage management with volume groups and logical volumes. Benefits include online resizing, snapshots for backups, multiple physical disks combined into one volume, and easy migration. Create with pvcreate, vgcreate, lvcreate. Use LVM for production systems requiring storage flexibility without downtime.
Q: How does Linux software RAID work?
Linux software RAID uses mdadm to combine multiple disks for redundancy or performance. RAID 0 stripes for speed, RAID 1 mirrors for redundancy, RAID 5 uses parity with minimum 3 disks, RAID 10 combines mirroring and striping. Create with "mdadm --create", monitor with /proc/mdstat. Handles drive failures gracefully.
Q: What is LUKS encryption and how do I use it?
LUKS (Linux Unified Key Setup) provides full disk encryption for data at rest. Initialize with "cryptsetup luksFormat /dev/sdX", open with "cryptsetup open", then format and mount like normal partitions. Supports multiple key slots for different passwords. Essential for laptop security and compliance requirements.
Q: Which filesystem should I choose for Linux?
Ext4 is the default, mature, and reliable for most workloads. XFS excels with large files and parallel I/O for databases and video. Btrfs offers snapshots, compression, and self-healing but less mature. ZFS provides enterprise features but licensing complexity. Use ext4 for general purpose, XFS for databases, Btrfs for advanced features.
Q: How do disk quotas work in Linux?
Disk quotas limit storage usage per user or group preventing disk exhaustion. Configure with quota tools on ext4 or XFS filesystems. Set soft limits (warnings) and hard limits (enforcement). Enable with "quotaon", edit with "edquota". Essential for shared hosting environments and preventing single users from consuming all space.
Q: What is the difference between block size and inode?
Block size determines the minimum space allocation unit for files (typically 4KB). Smaller blocks reduce wasted space for small files but increase metadata overhead. Inodes store file metadata like permissions and timestamps. Each file requires one inode. Set at filesystem creation with mkfs -b for block size, -i for inode ratio.
Conclusion
Linux storage management encompasses partitioning, filesystems, LVM, RAID, encryption, and quotas. Understanding these technologies enables you to build robust, flexible, and secure storage systems.
Use GPT partitioning for modern systems, choose appropriate filesystems for your workload, leverage LVM for flexibility, implement RAID for redundancy, encrypt sensitive data with LUKS, and enforce quotas in multi-user environments. Regular monitoring, proactive maintenance, and tested backup procedures ensure data integrity and availability.
Master these storage fundamentals to build reliable infrastructure that scales with your needs while maintaining security and performance.