Jailing FreeBSD 4 on FreeBSD 10

We have an in-house application that was written for FreeBSD 4 and antediluvian versions of PHP, Perl, OpenSSL, and so forth. Most of the features have migrated into other applications, but a few critical functions remain.

An old operating system isn’t sufficiently bad, though. The hardware terrifies me. Not only is it over a decade old, it’s repurposed desktop hardware.

Virtualize it? Maybe. But device drivers have changed over the intervening decade, and a ten-year-old de(4) or fxp(4) driver works poorly on any of my virtualization systems. Virtio is right out.

Port it to a current OS, PHP, and perl? That would be a painful prospect if I knew what I was doing. I’m a sysadmin, not a programmer. I have no bloody clue what I’m doing.

But theoretically, FreeBSD 4 systems should run almost unchanged in a jail on FreeBSD 10. Can they? Let’s find out!

First I tarred up the entire 4.10 system, except for /proc. (Yes, FreeBSD 4.10 used /proc. Those were the days, eh?) I did no preparatory cleaning, and even included port work directories, /usr/obj, /var/tmp, and so on, as I have NO idea what I might need. Yes, I’m sure I can find a PHP 5.0.whatever tarball out on the Internet, but that would involve work.

Create my jail directory, and untar the copied server

# mkdir /var/jail/oldserver
# cd oldserver
# tar -xvpf $HOME/oldserver.tgz

Be sure to use the -p flag, to preserve permissions.

Now to edit some configuration files, to change this system from hardware to jail.

  • Check rc.conf. Remove functions handled by the host server: firewalls, timekeeping, SSH, and so on. This jailed host only needs the functions that directly support the application (the Apache web server and the associated MySQL database).
  • Check /etc/fstab for anything you need to retain, like NFS filesystems or /proc. Comment out everything else.
  • Remove the old /dev. You cannot use FreeBSD 4 device nodes on a FreeBSD 10 host. (I spent an hour repeatedly bashing my head on the brick wall intensively testing these two sentences, so you can rest assured that it’s true.)

    Now on to the jail server. FreeBSD 9 and above has a jail-specific configuration file, /etc/jail.conf. I define some basic characteristics here.

    While that’s running, do some basic jail setup. I would normally recommend ezjail, but this is a fairly special case: no ZFS, the server will never be upgraded, and I specifically want a very minimal system. Also, ezjail doesn’t seem to have been updated for the Jail New World Order. So I’ll configure this the hard way, which isn’t terribly hard.

    FreeBSD 9 and above has a jail-specific configuration file, /etc/jail.conf. Here’s a configuration for my old server.

    exec.start = "/bin/sh /etc/rc";
    exec.stop = "/bin/sh /etc/rc.shutdown";

    oldserver {
    path = /var/jail/oldserver;
    host.hostname = oldserver.mwlucas.org;
    ip4.addr = 10.0.16.31;
    interface = vtnet0;
    };

    Now for the real test:

    # service jail start oldserver
    Starting jails: oldserver
    #

    Is it that easy?

    Of course not. Several processes didn’t start. I had to edit some configuration files to account for the change of IP address. That’s pretty minor, though.

    To log into the jail, get the jail ID and run a shell prompt in that server.

    host# jls
    JID IP Address Hostname Path
    7 10.0.16.31 oldserver.mwlucas.org /var/toolkit
    host# jexec 7 /bin/tcsh
    oldserver#

    The advantage to hosting this ancient system as a jail is that I can use the host operating system to control access to the legacy application. I don’t have to use the ancient IPF included on FreeBSD 4.10; I protect this host with PF from FreeBSD 10. (Admittedly, there’s newer PF out there, but even the older version in FreeBSD 10 is better than IPF.) FreeBSD 4.10 includes OpenSSH 3.5, which has roughly the same security as Windows XP. To log into the old server now, you must authenticate to the up-to-date FreeBSD 10 system and get a jail command prompt.

    The disadvantage to this system is that you can’t run ps(1) inside the jail. The ps command reads kernel data structures. While the FreeBSD 10 kernel includes FreeBSD 4 compatibility, that compatibility doesn’t extend to ps(1) and similar commands. You must use ps(1) from the jail host.

    That’s an acceptable trade-off, if it means I don’t have to touch actual PHP code. That stuff has cooties.

  • 8 comments to Jailing FreeBSD 4 on FreeBSD 10