💾 Archived View for floppy.p1x.in › floppinux › article › floppinux-on-a-floppy.gmi captured on 2023-09-08 at 15:52:04. Gemini links have been rewritten to link to archived content
⬅️ Previous capture (2023-05-24)
-=-=-=-=-=-=-
Short story why I decided to make my own one floppy distribution. An extensive yet simple tutorial/workshop on how to make embedded Linux distribution under 1.44MB.
I use Linux for more than a 7 years as my main OS. I play with Linux since the first Fedora and Ubuntu came out. I still remember getting those free Live-CD from Canonical. I have now installed it on every computer I have including all Raspberry Pi's and smartphones. I administrate two IBM server that runs Linux. But even with all of that I did not know much of the underlying principles behind it. I decided to change that while also make something fun and useful.
I created an embedded Linux distribution from scratch. It fits on a single floppy diskette. At the time of writing it uses ~1MB of storage. This gives me ~400KB free space to use on any custom software.
This distribution can boot on 486DX PC with 24 MB of ram (did not boot with less using QEMU). On an emulator it boots almost instantly. On bare metal modern hardware the only thing that prevent those speeds is the actual speed of a floppy drive. The maximum raw speed is 125KB/s. In reality it is even slower.
I did not test on real 486 yet as I do not have one but I saw others done similar things and it took around 1 minute. To be fair most of that time was that data loading from the drive.
When I started this project I did a lot of research and to my surprise there was not a single good tutorial. Or I can not find it. There are a lot of instructions how to make some aspects but mostly redundant, old or oversimplified. And when I tried to combine this knowledge I hit many walls. This forced me to do even more research. In the end I learned a lot and manage to meed all my needs.
If your interested in making something similar I'm writing this article for you!
My first application I want to run will be Nomad Diskmag. An old-school magazine I'm creating. For a PC I made a nice Python GUI using PyGame. For this embedded project I will change the front-end to the bash script. Articles on both versions are plain .txt files. All I need is to present cover, table of content and then cat body of each file (using less for pages).
Before that I need the working distribution that will boot and run that script. Let's create one.
Compiling 32-bit code on 64-bit system is a little bit tricky. To make it easier I just make everything on my old notebook with 32-bit CPU.
You can use VirtualBox with 32bit system.
If you want to use 64-bit host OS open my article with needed changes and follow this tutorial.
This tutorial/workshop is available in many formats including EPUB. Put it on your favorite eBook reader for better reading experience.
https://archive.org/details/floppinux-manual/
Create directory where you will keep all the files.
mkdir ~/my-linux-distro/ BASE=~/my-linux-distro/ cd BASE
Install needed software/libs. In Ubuntu 21.04:
apt install git flex bison libncurses-dev qemu-system-x86 syslinux
I'm using the latest revision. It's a feat of it's own that connects old and new technologies together. At the moment it is Kernel 5.13.0-rc2.
Get the sources:
git clone --depth=1 https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git cd linux
Now that you have them in /linux/ directory lets configure and build our custom kernel. First create tiniest configuration:
make tinyconfig
Now you need to add additonal config settings on top of it:
make menuconfig
From menus choose those options:
Exit configuration (yes, save settings to .config). Now it's time for compiling!
make bzImage
This will take a while depending on the speed of your CPU. In the end the kernel will be created in arch/x86/boot/bzImage. Move it to our main directory.
mv arch/x86/boot/bzImage ../
Without tools kernel will just boot and you will not be able to do anything. One of the most popular lightweight tools are BusyBox. Those replaces (bigger) GNU tools with just enough functionality for embedded needs.
At the moment it is 1.33.1. Download this file, extract it and change directory:
wget https://busybox.net/downloads/busybox-1.33.1.tar.bz2 tar xjvf busybox-1.33.1.tar.bz2 cd busybox-1.33.1/
As with kernel you need to create starting configuration:
make allnoconfig
Now the fun part. You need to choose what tools you want. Each menu entry will show how much more KB will be taken if you choose it. So choose it wisely :)
make menuconfig
I chosed those:
Now exit with save config. Compile time.
make make install
This will create a filesystem with all the files at _install. Move it to our main directory. I like to rename it also.
mv _install ../filesystem
This will create a filesystem with all the files at _install. Move it to our main directory. I like to rename it also.
mv _install ../filesystem
You got kernel and basic tools but the system still needs some additional directory structure.
cd ../filesystem mkdir -pv {dev,proc,etc/init.d,sys,tmp} sudo mknod dev/console c 5 1 sudo mknod dev/null c 1 3
Now create few configuration files. First one is a welcome message that will be shown after booting:
cat >> welcome << EOF Some welcome text... EOF
Inittab file that handles starting, exiting and restarting:
cat >> etc/inittab << EOF ::sysinit:/etc/init.d/rc ::askfirst:/bin/sh ::restart:/sbin/init ::ctrlaltdel:/sbin/reboot ::shutdown:/bin/umount -a -r EOF
And the actual init script:
cat >> etc/init.d/rc << EOF #!/bin/sh mount -t proc none /proc mount -t sysfs none /sys clear cat welcome /bin/sh EOF
Make init executable and owner of all files to root:
chmod +x etc/init.d/rc sudo chown -R root:root .
Lastly compress this directory into one file:
find . | cpio -H newc -o | gzip -9 > ../rootfs.cpio.gz
You can test if everything goes as planned by runing QEMU from the base directory:
qemu-system-i386 -kernel bzImage -initrd rootfs.cpio.gz
Next step is to put this on a floppy!
Create this Syslinux boot file that will point to your newly created kernel and filesystem:
cat >> syslinux.cfg << EOF DEFAULT linux LABEL linux SAY [ BOOTING FLOPPINUX VERSION 0.1.0 ] KERNEL bzImage APPEND initrd=rootfs.cpio.gz EOF
chmod +x syslinux.cfg
Create empty floppy image:
dd if=/dev/zero of=floppinux.img bs=1k count=1440 mkdosfs floppinux.img syslinux --install floppinux.img
Mount it and copy syslinux, kernel and filesystem onto it:
sudo mount -o loop floppinux.img /mnt sudo cp bzImage /mnt sudo cp rootfs.cpio.gz /mnt sudo cp syslinux.cfg /mnt sudo umount /mnt
Done!
You have your own distribution image floppinux.img ready to burn onto a floppy and boot on real hardware!
If you have internal floppy drive:
sudo dd if=floppinux.img of=/dev/fd0
If you also have USB drive it will show as /dev/hd*. On my computer:
sudo dd if=floppinux.img of=/dev/sdb
It took less than 3 minutes.
1474560 bytes (1,5 MB, 1,4 MiB) copied, 164,476 s, 9,0 kB/s
Full size: 1440KiB / 1.44MiB Kernel size: 632KiB Tools: 552KiB Free space left (du -h): 272KiB
Now as we have our embedded distribution let's make some use of it. It boots very fast (after floppy loads) and can easily run any compiled application. But I want to have some fun with scripts. So I will put .sh scripts instead of compiled software. The process then is the same.