Skip to content

Instantly share code, notes, and snippets.

Show Gist options
  • Save 43trh/231b9cfb64ea972de55636920a8bb88d to your computer and use it in GitHub Desktop.
Save 43trh/231b9cfb64ea972de55636920a8bb88d to your computer and use it in GitHub Desktop.
Install Alpine Linux Via Minirootfs Archive.

Install Alpine Linux on WSL via Minirootfs Archive

Prerequisites

  • Basic knowledge of PowerShell (pwsh) and *sh (Bash) in case of any unaccounted issues along the way.

Steps

(> is PowerShell, $ is *sh root, % is *sh user, # are comments)

  1. Setting up and downloading

    # Create directory to store the WSL files
    > Set-Location (New-Item  .\AlpineWSL -ItemType Directory).FullName
    
    # Download wsldl executable and the minirootfs
    > iwr 'https://github.com/yuk7/wsldl/releases/download/23051400/icons.zip' -OutFile 'icons.zip'
    > iwr 'https://dl-cdn.alpinelinux.org/alpine/v3.20/releases/x86_64/alpine-minirootfs-3.20.3-x86_64.tar.gz' -OutFile 'rootfs.tar.gz'
  2. Extract Alpine.exe from icons.zip

    # Initialize a `Shell.Application` COM object
    > $shell = New-Object -ComObject Shell.Application
    
    # Extract only Alpine.exe from all the files in icons.zip
    > $shell.NameSpace("$PWD").CopyHere($shell.NameSpace("$PWD\icons.zip").ParseName("Alpine.exe"))

    While these two commands may seem complex, they're not too hard to understand. I'll break them down step-by-step in the comments.

  3. Delete icons.zip and install Alpine Linux into WSL

    # Remove the icons.zip file
    > Remove-Item .\icons.zip
    
    # Install Alpine using the extracted Alpine.exe and the downloaded minirootfs
    > .\Alpine.exe install .\rootfs.tar.gz
    
    # Check if the installation worked
    > wsl -l
    Windows Subsystem for Linux Distributions:
    Ubuntu (Default)
    Alpine

    Great! Now we can open it up and make this minirootfs a bit less minimal.

Inside Alpine WSL

  1. Initial setup There are some things we need to set up. The setup scripts are unavailable by default in minirootfs, so we need to download them.

    # First, let's check who we are
    $ whoami
    root
    
    # Now, let's make sure we can connect to the internet
    $ ping -c 3 gnu.org
    PING gnu.org (209.51.188.116): 56 data bytes
    64 bytes from 209.51.188.116: seq=0 ttl=55 time=207.226 ms
    64 bytes from 209.51.188.116: seq=1 ttl=55 time=212.126 ms
    64 bytes from 209.51.188.116: seq=2 ttl=55 time=206.606 ms

    Good, we are currently root and connected to the internet. Now, let's install and run those scripts

    $ apk add alpine-conf

    Let's set up our repository mirrors too

    $ setup-apkrepos -f
  2. Install base packages

    Now we can install some base packages. While not all of them may be required in a WSL instance, it's better to be safe than sorry

    $ apk update && apk upgrade
    $ apk add linux-lts linux-firmware-none acpi mkinitfs acpid alpine-sdk 
    $ apk add busybox-openrc busybox-extras busybox-mdev-openrc openrc
    $ apk add llvm clang lld libc++ compiler-rt 
    $ apk add nano build-base coreutils zip unzip git curl wget ca-certificates 
  3. Set root password

    Don't forget to set a password for the root user:

    $ passwd
  4. Optional: Install zsh

    As an optional step, you can install zsh if you prefer it over ash:

    $ apk add zsh shadow
    $ chsh -s $(which zsh)
    
    # Now exit and re-enter AlpineWSL to see if it switched
    $ echo $SHELL
    /bin/zsh
  5. Set up Privilege elevation

    There are two main privilege elevation commands on Linux, and while sudo is the more common option, I'll be setting up doas as it's the default in Alpine Linux and what's downloaded in when running the setup-user script

  6. Setup user

    Setting up a user is super easy since we downloaded the setup scripts earlier:

    $ setup-user -a
    Setup a user? (enter a lower-case loginname, or 'no') [no] your_chosen_username
    Full name for user your_chosen_username [your_chosen_username] your_chosen_full_name
    New password:
    Retype new password:
    passwd: password updated successfully
    Enter ssh key or URL for gmifflen (or 'none') [none] none
    (1/1) Installing doas (6.8.2-r7)
    Executing busybox-1.36.1-r29.trigger
    OK: 767 MiB in 92 packages
    # Let's check if our user was correctly created
    $ cat /etc/passwd
    root:x:0:0:root:/root:/bin/zsh
    bin:x:1:1:bin:/bin:/sbin/nologin
    ...
    your_chosen_username:x:1000:1000:your_chosen_username:/home/your_chosen_username:/bin/zsh
    # perfect, our user is now setup!
    # one last thing we should do is to link doas to sudo so that any scripts that use sudo will work without us having to install it
    $ ln -s $(which doas) /usr/bin/sudo

    Now we just have to set our user as the default user in /etc/wsl.conf

    $ touch /etc/wsl.conf && nano /etc/wsl.conf
    # add this into the config
    [user]
    default = your_chosen_username

    Once again, let's exit and re-enter our Alpine WSL instance, and we should be logged into our newly created user, but this time we have to fully terminate the WSL instance before re-entering

    > wsl --terminate Alpine
    The operation completed successfully.

    Now we should check if we have been logged into or user

    % whoami
    your_chosen_username
    % pwd
    /home/your_chosen_username
    # lets check if our perms are set up correctly
    % doas apk update

    Awesome, now we have our Alpine Linux WSL instance setup with a user and Privilege elevation. This is where I'll stop for the main part of the guide, I might add an extras section in the future for other QOL things we can set up to help with using WSL, but for now here's a rapid-fire list of useful things to look into on your own time:

    • doas apk add git
    • git config --system core.autocrlf false: Disables Git’s automatic conversion between Windows-style line endings (\r\n) and Unix-style line endings (\n).
    • git config --system core.symlinks false: Disables Git’s handling of symbolic links.
    • git config --system rebase.autosquash true: Automatically squashes fixup commits during an interactive rebase.
    • git config --system lfs.activitytimeout 0: Sets the timeout for Git LFS (Large File Storage) operations to 0, meaning no timeout.
    • git config --system credential.helper 'cache --timeout 28800': Configures Git to cache credentials (e.g., passwords or tokens) for 28,800 seconds (about 8 hours or a full day of work).
    • git lfs install: an extension to Git that helps manage large binary files by storing them outside the main Git repository and only referencing them
    • setting perms in /etc/doas.d/doas.conf to permit nopass :wheel so you don't ever have to type your pass again (unsafe, but I don't personally care)
    • Updating to the latest wsl kernel https://github.com/microsoft/WSL2-Linux-Kernel
    • doas apk add wslu: some useful utilities for using linux in wsl

Thanks to:

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment