Linux & OS Advanced

WSL2 Ubuntu/Debian: Reclaiming Disk Space from Massive systemd Journald Logs

Is your WSL2 Ubuntu instance devouring disk space? Learn to efficiently manage and clean up oversized systemd journald log files to reclaim valuable storage.

👨‍💻
Senior Systems Architect • Verified in Staging Labs

Is your WSL2 Ubuntu instance devouring disk space? Learn to efficiently manage and clean up oversized systemd journald log files to reclaim valuable storage.

Introduction

As a seasoned Systems Administrator or DevOps Engineer working with Windows Subsystem for Linux 2 (WSL2), you've likely encountered the common headache of a rapidly growing virtual disk (ext4.vhdx) for your Ubuntu or Debian distribution. This often leads to critically low disk space warnings on your Windows host, sluggish WSL2 performance, and general frustration. A primary culprit behind this storage bloat is systemd-journald, which, by default, can accumulate vast amounts of log data, often without sensible limits configured for a development environment.

This highly technical guide will walk you through the process of diagnosing, cleaning up, and permanently configuring systemd-journald to prevent future log file proliferation, followed by compacting your WSL2 virtual disk to recover the freed space on your Windows system.

Symptom & Error Signature

The most prominent symptom is a decrease in available disk space on your Windows drive where your WSL2 distribution's virtual hard disk (.vhdx) resides. Inside the WSL2 environment, you'll observe significant disk usage attributed to /var/log/journal.

Here's how you'd typically identify the issue:

  1. Windows Disk Space Warning: Your C: or D: drive shows significantly less free space than expected.

  2. WSL2 Disk Usage Check:

    # Check overall disk usage in your WSL2 instance
    df -h
    

    Expected output (note the high usage, often 90%+):

    Filesystem      Size  Used Avail Use% Mounted on
    /dev/sda        250G  230G   10G  96% /
    # ... other mounts ...
    
  3. Identify Journald's Contribution:

    # Check the size of the /var/log/journal directory
    sudo du -sh /var/log/journal
    

    Expected output (showing multi-gigabyte usage):

    50G     /var/log/journal
    
  4. Direct Journald Disk Usage: The most accurate way to see what journald itself reports:

    # Query journald for its current disk usage
    journalctl --disk-usage
    

    Expected output:

    Journals take 48.7G on disk.
    

Root Cause Analysis

The underlying reason for this issue stems from the default configuration of systemd-journald on many Linux distributions, including Ubuntu and Debian.

  • Persistent Logging by Default: systemd-journald is configured to store logs persistently in /var/log/journal. These logs accumulate over time, and if no limits are set or the default limits are too generous, they can grow indefinitely.
  • Chatty Applications: In a development or hosting environment, applications (e.g., Nginx, Docker containers, custom services, cron jobs) can generate a massive volume of log entries, especially during debugging or if misconfigured.
  • WSL2 Disk Management: While WSL2's virtual disks (ext4.vhdx) dynamically expand as needed, they do not automatically shrink. Even if you delete files within the Linux distribution, the .vhdx file on the Windows host retains its peak size until explicitly compacted. This compaction requires sufficient free space within the Linux distro for the operation to be effective.

Essentially, logs fill up the virtual disk, journald keeps writing, and the .vhdx file on your Windows host balloons without an automatic mechanism to shrink it back down.

Step-by-Step Resolution

Follow these steps carefully to clean up existing logs, configure journald for better management, and reclaim the space on your Windows machine.

1. Confirm Journald Disk Usage

Before making changes, confirm the extent of the problem with journalctl.

# Check the current disk usage reported by journalctl
journalctl --disk-usage

Also, examine the largest files within the journal directory to understand if specific services are overly verbose.

# List journal files by size
sudo find /var/log/journal -type f -print0 | xargs -0 du -sh | sort -rh | head -n 10

2. Clean Up Existing Journal Logs

You have several options to clean up existing logs. Cleaning by size or age is generally preferred over manual deletion.

Option A: Clean by Size

This command will remove old archived journal files until the total disk space used by the journal is below the specified size.

# Example: Keep journal logs to a maximum of 500MB
sudo journalctl --vacuum-size=500M

Choose a size that makes sense for your debugging needs. For a WSL2 development environment, 200M-500M is often sufficient. For production systems, you might need more.

Option B: Clean by Age

This command will remove journal files older than the specified time.

# Example: Keep journal logs for only the last 7 days
sudo journalctl --vacuum-time=7d

Be cautious with --vacuum-time. Setting it too aggressively (e.g., 1d) might remove logs you need for recent troubleshooting.

Option C: Clean All (Use with Extreme Caution)

If you need to aggressively reclaim space immediately and have no need for historical logs, you can remove all existing journal files. This should be a last resort.

# Option 1: Using --vacuum-time=0 (removes all logs immediately)
sudo journalctl --vacuum-time=0

# Option 2: Manually remove the directory contents (not recommended, but effective)
# This will stop journald, delete logs, then restart.
> [!WARNING]
> Manually deleting files without `journalctl --vacuum` can leave `journald` in an inconsistent state or cause issues with file rotation. Only use this if `journalctl --vacuum` is not working for some reason.
sudo systemctl stop systemd-journald.service
sudo rm -rf /var/log/journal/*
sudo systemctl start systemd-journald.service

After performing a cleanup, verify the disk usage again:

journalctl --disk-usage
sudo du -sh /var/log/journal

3. Configure Persistent Journald Log Limits

To prevent journald logs from growing out of control again, you need to configure persistent limits in its configuration file.

  1. Open the journald.conf file for editing:

    sudo nano /etc/systemd/journald.conf
    
  2. Locate and uncomment (remove #) the following lines, setting appropriate values:

    • SystemMaxUse: The maximum total disk space that the persistent journal files (in /var/log/journal) may occupy.
    • SystemKeepFree: The amount of disk space that shall be left free on the file system where the persistent journal is stored. This prevents journald from filling up the entire disk.
    • RuntimeMaxUse: The maximum total disk space that the volatile journal files (in /run/log/journal, i.e., in memory) may occupy. These are cleared on reboot.
    • RuntimeKeepFree: Similar to SystemKeepFree, but for volatile logs.

    Here's an example configuration suitable for a WSL2 development environment:

    # /etc/systemd/journald.conf
    
    [Journal]
    Storage=persistent      # Ensure logs are stored persistently if desired
    SystemMaxUse=200M       # Limit persistent logs to 200MB
    SystemKeepFree=1G       # Ensure at least 1GB of disk space is free
    RuntimeMaxUse=50M       # Limit volatile logs to 50MB (if Storage=auto/volatile)
    # ForwardToSyslog=yes   # Uncomment if you want logs forwarded to syslog too
    # MaxRetentionSec=30day # Alternative way to manage retention
    

    SystemMaxUse is typically the most crucial setting for this issue. SystemKeepFree acts as a safety net. The MaxRetentionSec option provides an alternative, time-based limit, similar to --vacuum-time.

  3. Save the changes (Ctrl+X, Y, Enter for Nano).

  4. Restart the systemd-journald service for the new configuration to take effect:

    sudo systemctl restart systemd-journald.service
    

    The journald service will now adhere to these new limits, automatically purging older logs as new ones come in, ensuring your /var/log/journal directory stays within bounds.

4. (Optional) Consider Non-Persistent Logging

If you truly do not need any log persistence between reboots in your WSL2 instance (e.g., it's purely for testing, and logs are forwarded elsewhere or only needed live), you can configure journald to store logs only in memory.

  1. Open journald.conf again:

    sudo nano /etc/systemd/journald.conf
    
  2. Change the Storage option:

    # /etc/systemd/journald.conf
    
    [Journal]
    Storage=volatile      # Logs stored in /run/log/journal, cleared on reboot
    # SystemMaxUse=...    # These will no longer apply if Storage=volatile
    # SystemKeepFree=...
    RuntimeMaxUse=50M     # Still useful to limit in-memory log size
    

    Setting Storage=volatile means all past logs will be irrevocably lost after a system restart. Only choose this if you are absolutely certain you do not require log persistence for troubleshooting in your WSL2 environment.

  3. Save the file and restart the systemd-journald service:

    sudo systemctl restart systemd-journald.service
    

    For Storage=volatile to fully take effect and clear out any remaining persistent logs, a full reboot of the WSL2 instance might be necessary.

5. Compact the WSL2 Virtual Disk

After cleaning up the logs within your WSL2 distribution, the actual size of the ext4.vhdx file on your Windows host won't immediately shrink. You need to perform a manual compaction operation.

  1. Shut down the specific WSL2 distribution (or all of them) from a PowerShell or Command Prompt (run as administrator is not strictly necessary for this part, but good practice).

    wsl --shutdown
    

    Ensure the WSL2 distribution is fully shut down (wsl --shutdown) before attempting to compact the VHDX file. Attempting to compact an in-use VHDX will fail.

  2. Locate your WSL2 VHDX file. The path is typically: C:Users<YourUser>AppDataLocalPackages<DistroName>LocalStateext4.vhdx Replace <YourUser> with your Windows username and <DistroName> with your specific distribution's package name (e.g., CanonicalGroupLimited.Ubuntu22.04LTS_79rhkp1fmygva). You can find the exact path by listing your distributions:

    wsl -l -v
    
  3. Run diskpart from an elevated PowerShell or Command Prompt.

    diskpart
    
  4. Perform the compaction within diskpart:

    # Select the virtual disk
    select vdisk file="C:Users<YourUser>AppDataLocalPackages<DistroName>LocalStateext4.vhdx"
    
    # Compact the virtual disk
    compact vdisk
    
    # Exit diskpart
    exit
    

    The compact vdisk command will analyze the virtual disk and reclaim unused blocks, shrinking the .vhdx file to its minimum possible size based on the actual data stored within it. This process can take several minutes depending on the size of the VHDX and the amount of free space being reclaimed.

  5. Restart your WSL2 instance:

    wsl
    

    Your WSL2 distribution will now start, and you should observe a significant reduction in the ext4.vhdx file size on your Windows drive.

By following these steps, you will not only reclaim critical disk space but also establish a robust log management strategy for your WSL2 environment, ensuring smooth operations for your development and hosting tasks.

👨‍💻

Johnathon Wheeler

Senior Systems Architect & DevOps Engineer • Austin, TX

Connect on LinkedIn →

Johnathon has over 16 years of hands-on experience designing, debugging, and scaling Linux web hosting stacks, container clusters, and high-availability database architectures. Every guide on ButItWorkedLocal is independently tested against Debian 12, Ubuntu 24.04/22.04 LTS, Rocky Linux, and Docker environments to guarantee reproducibility in production.

🛡️

Our Production Verification Guarantee

Encountering a bug not covered here or running a non-standard kernel configuration? Our solutions are continually refined against real production incidents. Submit an environment trace for our editorial team to replicate.