Installing FreeBSD on a flash drive for a seedbox machine

    Many home seedboxes quite often put old hard drives, from the principle of "do not mind." All the same, important data is not written there, and when they die, nothing bad happens, except for problems with the OS rearrangement.
    To minimize the risk of OS death, you can take it to a separate physical medium. One option is for a small flash drive. We will go on to install and configure FreeBSD (7.0-8.0) on a USB flash drive.

    Flash drive size


    Based on my experiments, a completely working router with a dhcp / dns / vpn server easily gets into 200 megabytes (for a 256 megabyte flash drive). At the same time, all unnecessary drivers are thrown out of the kernel, as well as debugging and profiling options, and manes are removed from the world. Of course, the sources (/ usr / src) and ports (/ usr / ports) will not fit there, but they can be mounted from other media without any problems.

    For a router with seedbox functions, it is better to have a larger flash drive, since it will require apache, perl, and php. For this example, take a buggy flash drive for 4 gigabytes :).

    Reliability issues


    Since flash drives really do not like rewriting sectors, the guide recommends that the root be mounted only for reading, and all sections requiring write access should be put into memory. Thus, / var will be mounted as a disk in RAM and each reboot will delete all its contents.

    Partition Preparation


    The installation is most conveniently done from under FreeBSD (I did it with a virtual machine), in which the kernel and the world you need are already assembled.

    So, we insert the USB flash drive, we look how it was defined in dmesg (further da0). First you need to format the flash drive. Create flash_disk.proto:

    # slice type start length
    # создаем два слайса
    p 1 0xa5 63 1429722
    p 3 0xa5 2040255 6072570
    # делаем первый активным
    a 1


    Since my flash drive is buggy (trying to read data from a section between 700 and 1000 megabytes causes the controller to fall off), my space is split into two slices. With a normal flash drive, you can create one piece for the entire flash drive.

    Formatting:

    fdisk -f flash_disk.proto -i da0


    Create the bootloader:

    # создаем MBR
    boot0cfg -B da0
    # по-умолчанию грузимся с первого slice
    boot0cfg -s 1 da0
    # запрещаем загрузчику перезаписывать себя
    boot0cfg -o noupdate da0


    Now mark our slice. Create flash_labels.proto:

    # size offset fstype [fsize bsize bps/cpg]
    a: 1429722 0 4.2BSD 0 0 0
    c: * 0 unused 0 0 # "raw" part, don't edit


    We mark the disk and create the file system:

    # Размечаем в соответствии с созданным файлом
    bsdlabel -R da0s1 flash_labels.proto
    # Создаем файловую систему
    newfs -U da0s1a


    Mount our slice

    mount /dev/da0s1 /mnt/flash


    System and port installation


    To avoid specifying a path each time make install, temporarily set the DESTDIR flag in make.conf on the working system:

    DESTDIR=/mnt/flash


    Now install the kernel, world, system configs and scripts (etc) on the USB flash drive:

    cd /usr/src
    make installkernel
    make installworld
    cd /usr/src/etc
    make distrib-dirs
    make distribution


    In my make.conf, among other things, the info and man assembly is turned off (NO_INFO = YES NO_MAN = YES), therefore, for normal installation of ports on a USB flash drive, you will need to manually install texinfo, as described here .

    cd /usr/src/gnu/usr.bin/texinfo
    make install


    After that, edit fstab on the flash drive:

    # Device Mountpoint FStype Options Dump Pass#
    /dev/da0s1a / ufs ro 1 1
    md /tmp mfs rw,-s24M,noatime 0 0
    md /var mfs rw,-s128M,noatime` 0 0


    Since / var will be mounted in memory, it is necessary to transfer / var / db to a USB flash drive so that data on installed ports is not lost between restarts. To do this, create a link:

    mkdir /mnt/flash/etc/pkg
    ln -s ../../etc/pkg /mnt/flash/var/db/pkg


    Now you can configure the system on a USB flash drive, edit configs and install ports from the working system (you only need to register a dns server on the USB flash drive in resolv.conf).
    For instance:

    cd /usr/ports/net/isc-dhcp30-server
    make
    make install


    The DESTDIR flag in make.conf will tell make install to install the port on a USB flash drive.

    Problems with named dns server


    By default, named is started by the system in the sandbox (chroot) in the / var / named directory. You cannot put this directory on a USB flash drive, since named must be able to write to its small / var. The option I used is to add a named config to rc.local every time you start the system:

    # копируем конфиг named
    mkdir -p /var/named/etc
    cp -Rp /usr/local/etc/namedb /var/named/etc
    /etc/rc.d/named start


    In my opinion, this is somewhat clumsy and I would love to hear other solutions.

    Download installed system


    We connect the USB flash drive to the router and set the boot from it in the BIOS. On some motherboards, a bug is possible when the flash drive does not have time to determine by the time the bootloader begins to mount the root. The hack for this problem is described at the end of this article on Habré.
    After loading the system, you can continue to configure it. To do this, just remount the root to write:

    mount -uw /


    After making the necessary changes (setting ports / editing configs / adding users, etc.), you need to return the root to read-only access:

    mount -ur /


    useful links




    UPDATE: As noted in the comments, it makes no sense to manually mount / var and / tmp. If / var and / tmp are read-only during boot, /etc/rc.initdiskless will be automatically called, which, by default, will mount these partitions into RAM. Therefore, you can remove the lines about / var and / tmp from fstab, and add parameters to the rc.initdiskless script in /etc/rc.conf:

    tmpmfs=true
    tmpsize=24M
    varmfs=true
    varsize=128M



    Also popular now: