Date: 2025-07-14
In this article, we install PostmarketOS on a Minisforum S100 with the following high-level procedure:
These instructions should mostly work for any x86-64 target machine.
Just omit or customize the --sector-size=4096
flag when building a disk image.
The Minisforum S100 is a mini desktop computer with a quad-core Intel N100 processor 8 GB of RAM. At launch, many people tried to install their favorite flavors of Linux on the S100, but only a few distributions like Proxmox actually booted from internal storage. The issues revolve around 3 oddities of its internal storage:
dd
from a disk image will have a bad partition table.Due to reports of short lifespans of the internal storage, I’m also opting to format the root partition with the Flash-Friendly File System (F2FS). Granted, the main issue is that the S100 overheats when relying on Power over Ethernet rather than its USB-C adapter.
We’ll be cloning a fresh version of pmbootstrap
with git
, so we need to install dependencies manually.
See the full requirements list for details.
Chances are, you have most of them installed already.
I only needed multipath-tools
:
# For `kpartx`.
sudo apt install multipath-tools
If you have doas
installed, the pmbootstrap
command will use that to act as root
.
Rather than giving your normal user ambient root access, it’s easiest to do this whole process as a different user.
sudo sh
useradd --create-home -g users root-delegate || busybox adduser -D -G users root-delegate
echo "permit nopass root-delegate as root" >>/etc/doas.conf
su root-delegate
The instructions assume you’re running as the correct user and have the following environment variables set.
top_dir="${HOME}/Desktop/pmos"
pmbootstrap_device=generic-x86_64
alias pmbootstrap="${top_dir}/pmbootstrap/pmbootstrap.py --config '${top_dir}/pmbootstrap.cfg'"
# Put `losetup` in `${PATH}` if it isn't already.
export PATH="${PATH}:/usr/sbin"
mkdir -p "${top_dir}/work" "${top_dir}/export"
cd "${top_dir}"
git clone --single-branch https://gitlab.postmarketos.org/postmarketOS/pmbootstrap.git
cat >"${top_dir}/pmbootstrap.cfg" <<HEREDOC
[pmbootstrap]
work = ${top_dir}/work
aports = ${top_dir}/pmaports
boot_size = 512
device = ${pmbootstrap_device}
hostname = pmos
systemd = never
user = root-delegate
build_pkgs_on_install = False
HEREDOC
pmbootstrap init
The last command has some prompts. You can accept all the preselected values. Feel free to change the hostname and other values that we customized below it.
cat >>"${top_dir}/pmaports/device/community/device-${pmbootstrap_device}/modules-initfs" <<HEREDOC
f2fs
ufshcd
ufshcd_pci
HEREDOC
pmbootstrap checksum "device-${pmbootstrap_device}"
pmbootstrap build --force "device-${pmbootstrap_device}"
# Replace ${usb_devpath} with the device path of the flash drive that you want to overwrite (e.g., `/dev/sdb`).
# Remember, this erases the disk, so inspect the output of `lsblk` to verify your choice.
pmbootstrap install --filesystem=f2fs --disk "${usb_devpath}"
You’ll be prompted for a password for the new user.
When it’s done flashing, you can try booting to it.
# We have to build from scratch to apply the sector size change.
pmbootstrap zap
pmbootstrap install --filesystem=f2fs --sector-size=4096
You’ll be prompted for a password for the new user again.
pmbootstrap export "${top_dir}/export/"
pmbootstrap shutdown
Time to boot the LiveUSB! You’ll have to disable secure boot though.
Hopefully you can boot from the LiveUSB now. Remember to press F7 to select booting from the USB.
When it’s up, SSH in and give the root-delegate
user ambient root
access:
ssh root-delegate@pmos
# Type password.
doas -u root -- sh
# Type password.
echo "permit nopass root-delegate as root" >/etc/doas.d/root-delegate.conf
exit
exit
Finally, we flash it:
ssh root-delegate@pmos -- "doas -u root -- dd of=/dev/sda bs=4M conv=fsync" <"${top_dir}/export/${pmbootstrap_device}.img"
PostmarketOS should load from internal storage upon reboot:
ssh root-delegate@pmos -- "doas -u root -- reboot"