3 of 3

Storage and LVMLesson 3 of 3

Growing volumes and adding swap

Extend a logical volume and its file system while it is mounted, add a disk to a group when it is full, and create swap that survives a reboot.

  • lvextend
  • lvextend -r
  • vgextend
  • xfs_growfs
  • resize2fs
  • mkswap
  • swapon
  • swapoff
  • swapon --show
  • free
  • blkid

50 min5 exercises

After this lesson you can

  • Extend a mounted logical volume and its file system in one step, to a target size or by an amount.
  • Add a physical volume to a full volume group, then extend.
  • Create swap on a partition, a logical volume and a file, activate it, and make it persistent using its UUID.

The idea

The reason to use LVM is this lesson: a volume can grow while it is in use. A logical volume is extended with lvextend; the file system on it then needs to learn about the extra space. The -r (--resizefs) option does both in one command and works for XFS and ext4:

sudo lvextend -r -L +100M /dev/vgdata/lvdata

Two ways to say the size, and they differ:

OptionMeaning
-L 500MMake the volume 500 MiB in total
-L +500MAdd 500 MiB to what it is now
-l +100%FREEAdd all the free extents in the group
-l 50Total of 50 extents (+50 adds 50)

If the volume group has no free extents, lvextend fails with Insufficient free space. First add a disk: pvcreate it, then vgextend VG DEVICE, and extend again.

Without -r, resize by hand: xfs_growfs /mount/point for XFS (the mount point, and the volume must be mounted) or resize2fs /dev/VG/LV for ext4.

Swap

Swap is disk space the kernel uses when RAM is short. It also holds hibernation data. A swap area can be a partition, a logical volume, or a file. Setting one up has four steps:

  1. Make the space (partition, LV or file; a file must have mode 600).
  2. mkswap DEVICE writes the swap signature and prints a UUID.
  3. swapon DEVICE activates it now.
  4. A line in /etc/fstab activates it at every boot.

The fstab line has no mount point, because swap is not mounted: UUID=... none swap defaults 0 0. Using the UUID avoids trouble when device names change between boots. swapon --show and free -h verify; swapoff DEVICE deactivates.

Try it

df -h /srv/data
sudo lvextend -r -L +100M /dev/vgdata/lvdata
df -h /srv/data
Filesystem                Size  Used Avail Use% Mounted on
/dev/mapper/vgdata-lvdata 195M  12M  184M   6% /srv/data
  Size of logical volume vgdata/lvdata changed from 200.00 MiB (25 extents) to 300.00 MiB (37 extents).
  Logical volume vgdata/lvdata successfully resized.
meta-data=/dev/mapper/vgdata-lvdata isize=512    agcount=4, agsize=12800 blks
data blocks changed from 51200 to 76800
Filesystem                Size  Used Avail Use% Mounted on
/dev/mapper/vgdata-lvdata 295M  12M  284M   4% /srv/data

No unmount, no downtime. The “meta-data” lines are xfs_growfs, run for you by -r.

The group is full

sudo lvextend -r -L +200M /dev/vgdata/lvdata
sudo pvcreate /dev/vdb3
sudo vgextend vgdata /dev/vdb3
sudo vgs vgdata
sudo lvextend -r -l +100%FREE /dev/vgdata/lvdata
  Insufficient free space: 25 extents needed, but only 0 available
  Physical volume "/dev/vdb3" successfully created.
  Volume group "vgdata" successfully extended
  VG     #PV #LV #SN Attr   VSize   VFree
  vgdata   2   1   0 wz--n- 488.00m 184.00m
  Size of logical volume vgdata/lvdata changed from 296.00 MiB (37 extents) to 480.00 MiB (60 extents).

Swap on a logical volume

sudo lvcreate -n lvswap -L 256M vgdata
sudo mkswap /dev/vgdata/lvswap
sudo swapon /dev/vgdata/lvswap
sudo blkid -s UUID -o value /dev/vgdata/lvswap
Setting up swapspace version 1, size = 256 MiB (268431360 bytes)
no label, UUID=cb829253-8500-472d-b602-17388fdaae9d
cb829253-8500-472d-b602-17388fdaae9d
echo 'UUID=cb829253-8500-472d-b602-17388fdaae9d none swap defaults 0 0' | sudo tee -a /etc/fstab
sudo systemctl daemon-reload
swapon --show
free -h | grep -i swap
NAME                  TYPE      SIZE USED PRIO
/dev/dm-1             partition   2G   0B   -2
/dev/dm-2             partition 256M   0B   -3
Swap:          2.2Gi          0B       2.2Gi

Swap devices are used in priority order; two areas of equal priority are used in parallel. You never need to reboot to add swap.

A swap file

sudo dd if=/dev/zero of=/swapfile bs=1M count=128 status=none
sudo chmod 600 /swapfile
sudo mkswap /swapfile
sudo swapon /swapfile
echo '/swapfile none swap defaults 0 0' | sudo tee -a /etc/fstab
Setting up swapspace version 1, size = 128 MiB (134213632 bytes)
no label, UUID=6a1c4f1d-9d1e-4a42-8f0b-2b0d1f0f8a55

If you forget chmod 600, swapon warns insecure permissions; fix the mode.

Going further

lvreduce exists for ext4 but needs the file system shrunk first (resize2fs) and unmounted; lvextend --resizefs is symmetrical only for growth. lvresize combines extend and reduce under one command. swapon -a activates everything in fstab, and vm.swappiness (sysctl vm.swappiness) tunes how eagerly the kernel swaps. When a disk’s size is increased in the hypervisor, pvresize /dev/vdb makes LVM see the extra space and you can extend into it. Thin provisioning and snapshots (lvcreate -s) are the next topics once plain volumes are routine.

Practice

0 of 5 done

Do these on your own system. They get harder. Check each result, then tick it off.

  1. Warm-up

    Make a volume bigger, online

    Set up first, if you don't have it: volume group vgdata on /dev/vdb2 (8 MiB extents), and in it lvdata of 200 MiB with XFS mounted on /srv/data (mkdir -p /srv/data, an fstab line, mount -a). Then grow the volume by 100 MiB and the file system with it, while it stays mounted. Show the size before and after.

    Check your result

    df -h /srv/data grows by about 100 MiB. lvs shows the larger size. The directory stayed mounted throughout.

    Hint

    lvextend -r -L +100M /dev/vgdata/lvdata. The -r option resizes the file system after extending the volume.

    Solution
    # setup (once)
    sudo pvcreate /dev/vdb2 && sudo vgcreate -s 8M vgdata /dev/vdb2
    sudo lvcreate -n lvdata -L 200M vgdata && sudo mkfs.xfs /dev/vgdata/lvdata
    sudo mkdir -p /srv/data
    echo '/dev/mapper/vgdata-lvdata /srv/data xfs defaults 0 0' | sudo tee -a /etc/fstab
    sudo systemctl daemon-reload && sudo mount -a
    # the task
    df -h /srv/data
    sudo lvextend -r -L +100M /dev/vgdata/lvdata
    df -h /srv/data
    sudo lvs vgdata
  2. Practice

    Make it exactly this size

    A task says: "Resize lvdata to approximately 500 MiB." Do this by giving the final size, not an increment, and check the result. Explain why -L 500M and -L +500M give very different results.

    Check your result

    lvs shows lvdata around 496m–504m, depending on extent size. With +500M the volume would be 500 MiB larger than it was.

    Hint

    lvextend -r -L 500M LV makes the volume 500 MiB in total. A plus sign means "add this much".

    Solution
    sudo lvextend -r -L 500M /dev/vgdata/lvdata
    sudo lvs vgdata
    df -h /srv/data
  3. Practice

    The group is full: add a disk, then grow

    vgdata has no free space left. Prepare /dev/vdb3 as a physical volume, add it to the group, confirm the new free space, and then extend lvdata by all of it, resizing the file system too.

    Check your result

    vgs vgdata shows #PV 2 and a larger VFree after vgextend. After the extend, VFree is 0 (or close to it) and df shows the extra space.

    Hint

    pvcreate /dev/vdb3, vgextend vgdata /dev/vdb3, lvextend -r -l +100%FREE /dev/vgdata/lvdata.

    Solution
    sudo pvcreate /dev/vdb3
    sudo vgextend vgdata /dev/vdb3
    sudo vgs vgdata
    sudo lvextend -r -l +100%FREE /dev/vgdata/lvdata
    sudo vgs vgdata
    df -h /srv/data
  4. Practice

    Add swap on a partition, persistently

    Use a new 256 MiB partition (or logical volume lvswap) as swap. Format it, activate it, and add it to /etc/fstab by UUID so it is active after a reboot. Show the total swap before and after.

    Check your result

    swapon --show lists the new device and free -h shows the larger swap. grep swap /etc/fstab shows a UUID=... line with type swap. After a reboot it is still active.

    Hint

    mkswap DEVICE, swapon DEVICE, then blkid DEVICE for the UUID. Line: UUID=... none swap defaults 0 0.

    Solution
    free -h | grep -i swap
    sudo lvcreate -n lvswap -L 256M vgdata
    sudo mkswap /dev/vgdata/lvswap
    sudo swapon /dev/vgdata/lvswap
    uuid=$(sudo blkid -s UUID -o value /dev/vgdata/lvswap)
    echo "UUID=$uuid none swap defaults 0 0" | sudo tee -a /etc/fstab
    sudo systemctl daemon-reload
    swapon --show
    free -h | grep -i swap
  5. Challenge

    A swap file and a clean removal

    Create a 128 MiB swap file /swapfile with safe permissions, activate it and make it persistent. Then remove it properly: deactivate, delete its fstab line and the file. State what happens if you delete the file first.

    Check your result

    swapon --show lists /swapfile as file. After removal it is gone from swapon --show and fstab. Deleting it while active leaves the kernel using a deleted file until swapoff or reboot.

    Hint

    Permissions must be 600 or swapon complains. Use dd if=/dev/zero of=/swapfile bs=1M count=128. fstab: /swapfile none swap defaults 0 0.

    Solution
    sudo dd if=/dev/zero of=/swapfile bs=1M count=128 status=none
    sudo chmod 600 /swapfile
    sudo mkswap /swapfile
    sudo swapon /swapfile
    echo '/swapfile none swap defaults 0 0' | sudo tee -a /etc/fstab
    swapon --show
    sudo swapoff /swapfile
    sudo sed -i '\#^/swapfile#d' /etc/fstab
    sudo rm /swapfile
    swapon --show