Guide

Shrink the WSL 2 and Docker Desktop virtual disk

You deleted gigabytes inside Linux and C: did not get any of it back. That is how WSL's virtual disks work, and this is how to fix it.

A WSL 2 distro or Docker Desktop stores its files in a virtual disk (ext4.vhdx, docker_data.vhdx). The file grows when Linux writes data, but it does not shrink when Linux deletes it. To get the space back, free the space inside first, then compact the virtual disk from Windows.

Why it never shrinks

Inside the distro, deleting a file only marks its blocks as free. The .vhdx file on C: keeps its size, because Windows does not know those blocks are now empty. Compacting tells the virtual disk to drop them.

Step 1: see the real numbers

Two numbers matter: the size of the .vhdx on Windows, and the space Linux actually uses inside.

  • In the distro, run df -h / for what Linux uses. For Docker, docker system df shows images, containers, volumes and the build cache.
  • The disks are usually here: %LOCALAPPDATA%\wsl\{GUID}\ext4.vhdx for distros installed from a recent WSL, or under %LOCALAPPDATA%\Packages\<distro package>\LocalState for older installs. Docker Desktop keeps docker_data.vhdx under %LOCALAPPDATA%\Docker\wsl.

If the file is much larger than what Linux uses, compacting will return the difference. Bytopsy's WSL & Docker view shows both figures side by side, without a scan.

Step 2: free space inside first

  • Delete what you do not need in the distro, such as old build outputs, package caches and logs.
  • For Docker, docker builder prune and docker image prune -a remove the build cache and the images no container uses. Stopped containers and unused volumes can hold data, so look before pruning them.
  • Run sudo fstrim -av in the distro so the freed blocks are reported as free.

Step 3: compact the disk

Back it up first if the distro holds anything you cannot recreate: wsl --export <distro> backup.tar.

Microsoft's documented method uses diskpart, in an administrator terminal:

wsl --shutdown
diskpart
select vdisk file="C:\Users\<you>\AppData\Local\wsl\{GUID}\ext4.vhdx"
attach vdisk readonly
compact vdisk
detach vdisk
exit

On Windows editions with the Hyper-V PowerShell module, Optimize-VHD -Path <file> -Mode Full does the same after wsl --shutdown. For Docker Desktop, quit it first.

Newer WSL versions also have a sparse virtual disk option that shrinks automatically. It has been marked experimental, so read Microsoft's current WSL documentation before enabling it on a disk that holds work you care about.

The one-click version

Bytopsy's WSL & Docker view automates exactly the steps above. It reads each disk's usage (asking running distros, and reading the ext4 superblock from the file for stopped ones, which are never started), trims free space, stops Docker Desktop and starts it again afterwards, shuts WSL down, and runs diskpart to compact each disk. Windows asks for administrator permission once. It never prunes containers or volumes for you.

Related: find out what else fills your C: drive.