OpenBSD

When I lived in student housing, I had a 486 as a firewall to my computers. The most stable operating system I found for it was OpenBSD. I actually had an uptime on one installation of it for something like 320 days before the power went out. As I played with versions from OpenBSD 2.9 to 3.4, I documented a lot of the stuff I learned and the configurations I made. When I worked at The University of Texas at Tyler, I was even able to setup an OpenBSD machine to firewall for one of the computer labs. The operating system was more dependable than the hardware it was installed on.

Auto-start MySQL in OpenBSD 3.2

Problem
I got MySQL to install from the pre-packaged .tgz files OpenBSD provides using pkg_add, but I couldn't figure out how to get it to automatically start.

Get MySQL
You'll want Mysql-server-**.tgz from a openbsd ftp server or your official CD.

    #: pkg_add Mysql*

Changing Files
Check /etc/rc.conf to make sure that the following line is at the bottom:

local_rcconf="/etc/rc.conf.local"

If it doesn't exist, create /etc/rc.conf.local and add:


mysql=YES

Then:

    #: chmod 755 /usr/local/share/mysql/mysql.server

Then add this to /etc/rc.local:

if [ X"${mysql}" == X"YES" -a -x /usr/local/bin/safe_mysqld ]; then
	echo -n " mysqld"; /usr/local/share/mysql/mysql.server start
fi

reboot

Cisco Aironet and OpenBSD 3.1

Objective
I decided to get a wireless network card for my OpenBSD machine instead of buying an access point. Having an access point just seems limiting to me. I decided to is get a wireless PCI card so I can just add it to the existing machine I have doing packet filtering with PF and NAT for my internal network on my cable modem. This would give me one hard-wire interface connected to my cable modem, one hard-wire interface to a hub, and one wireless card in the gateway machine.

The Part
Cisco Aironet 352 PCI adapter with the pcmcia card built in from ebay.

Kernel Configuration

I have a custom built kernel in OpenBSD 3.1, so I had to go back to my kernel configuration file, add the following line, and recompile:

    an*     at pci? dev ? function ?        # Aironet IEEE 802.11DS

If you have a laptop and just the pcmcia card, you should probably use:

    an*     at pcmcia? function ?           # Aironet IEEE 802.11DS

If you are running the kernel that came with the default installation of OpenBSD, you don't need to worry about adding an* because it is there already.

The Utility

OpenBSD already has the utilities to configure the computer, in this case, you need ancontrol. For wireless cards made by people other than Cisco, you'll probably need wicontrol and this page won't help you much because it uses different configuration options.

Setup

    Device txp0:

    • 3com 990 PCI with 3xp processor 10/100mbit
    • IP: 66.xx.xx.xx
    • Goes right to the cable modem

    Device ep1:

    • Old 3c509 ISA card 10mbit
    • IP: 192.168.0.1
    • Goes to hub

    Device an0:

    • Cisco 352 Aironet Wireless PCI
    • IP: 192.168.1.1
    • Acting as access point for my laptop

You'll need to add a file to /etc to give your wireless device an IP and subnet assignment:

    echo "inet 192.168.1.1 255.255.255.0 NONE" > /etc/hostname.an0

DHCPd
I also want to run DHCP on both devices ep1 and an0. That way when I take my laptop back and forth from home, I don't have to set a static IP. DHCP just makes things easier. I statically assign my IPs so when I need to ssh or scp into another machine, I don't have to hunt around.

In the case of the wireless device, I only want to assign a DHCP address for my laptop. I live in an apartment complex and don't want just anyone using my bandwidth. The other issue I have is that if I want to dish out IPs for two different devices, I have to have a special configuration in /etc/dhcpd.conf.

Edit /etc/dhcpd.interfaces so that it has both your hard-wire and wireless interfaces. Mine says:

ep1
an0

Edit /etc/dhcpd.conf to add another network. Mine says:


shared-network LOCAL-NET {
	option  domain-name "goodmeat.net";
	option  domain-name-servers 204.145.251.1, 205.128.118.1, 205.128.118.2, 4.2.2.2, 4.2.2.3, 128.83.185.40;

	# this is wireless
	subnet 192.168.1.0 netmask 255.255.255.0 {
		option routers 192.168.1.1;

		host laptop {
			hardware ethernet 00:14:3A:56:6A:D8;
			fixed-address 192.168.1.2;
			option host-name "laptop";
		}
	}
}

shared-network LOCAL-NET2 {
	option	domain-name "goodmeat.net";
	option	domain-name-servers 204.145.251.1, 4.2.2.2, 205.218.118.1, 208.180.0.2, 206.76.228.23, 128.83.185.40;	

	# this is hard-wired
	subnet 192.168.0.0 netmask 255.255.255.0 {
		option routers 192.168.0.1;

		range 192.168.0.100 192.168.0.155;

		host mariann {
			hardware ethernet 00:B0:F2:54:CA:D6;
			fixed-address 192.168.0.3;
			option host-name "mariann";
		}
		host oats {
			hardware ethernet 00:A3:D2:34:AC:E8;
			fixed-address 192.168.0.2;
			option host-name "oats";
		}
		host bogus {
			hardware ethernet 00:A0:F6:59:CD:D6;
			fixed-address 192.168.0.4;
			option host-name "bogus";
		}
	}
}


Notice the hard-wired network allows additional IPs to be assigned other than those which I have assigned statically. The wireless configuration only knows to allow one specific MAC to have an IP. This can easily be circumvented by having someone set their machine to 192.168.1.3 statically and use 192.168.1.1 as the gateway. The average person isn't smart enough to figure that out, so I'm not too worried about bandwidth leeches.

If you've been following along and haven't rebooted yet, now is probably a good time.

Using ancontrol
By default, your card will work in infrastructure mode. That's not what you want. You need ad-hoc, which means if it doesn't find an access point in the area, it declares itself to be an access point.

You will need the MAC address of your wireless card. Get it by doing:

    ancontrol -S

These options will give the most basic operation for your card to be an access point:

    ancontrol -n OpenBSD
    ancontrol -m (the MAC you got from -S here)
    ancontrol -l OpenBSD
    ancontrol -o 0

I am not going to explain what those do because now is a good time for you to read the ancontrol man page, just so you're clear about what's going on. It's wasteful of my time to rewrite the manual.

It might be a good idea to make a script out of it so you don't have to type it on every boot:

    #!/bin/sh

    ancontrol -n OpenBSD
    ancontrol -m xx:xx:xx:xx:xx:xx
    ancontrol -l OpenBSD
    ancontrol -o 0

That last line spoken is -lowercase oh space zero.

Wired Equivalent Privacy (WEP)
WEP isn't secure, but it's better than broadcasting all your traffic to the neighborhood in plaintext. From ancontrol(8):

WEP ("wired equivalent privacy") is based on the RC4 algorithm, using a
24 bit initialization vector.

RC4 is supposedly vulnerable to certain known plaintext attacks,
especially with 40 bit keys. So the security of WEP in part depends on how
much known plaintext is transmitted.

You should look for a IPSEC or SSH tunneling tutorial now if you want some proven security over wireless.

To get WEP enabled with ancontrol, you'll need three more commands. If you live in the US and have a nice encryption limit on your card (128 bit), then you'll want to use a long key, 26 hex characters (0-9, a-f, and A-F), otherwise you use 10 hex characters. Both are prefixed by a 0x (zero ex).

You can set up to 8 keys total, 4 temporary, 4 permanent. See ancontrol(8). The first example is 128 bit, but be smart and pick a more random combination of numbers and letters:


    ancontrol -v 0 -k 0x1234567890abcdefABCDEF1234
    ancontrol -e 0
    ancontrol -W 1

A 40 bit example would look something like:

    ancontrol -v 0 -k 0x1e3a5f7890
    ancontrol -e 0
    ancontrol -W 1

NAT
Now just make sure you have a line like this in your /etc/nat.conf:


    nat on txp0 from 192.168.0.0/16 from all -> txp0

That should cover both hard-wired and wireless subnets.

WEP on client WinXP laptop
Go to connection properties for the wireless adapter. Click the wireless networks tab. Click the OpenBSD connection. If it is configured in the bottom window already, click properties for that one. WinXP won't like if you try to configure the existing network from the top window. Click the "Data Encryption (WEP Enabled)" checkbox. Enter the key in the Network Key input field without the 0x prefix, for a total of 26 letters and numbers. Make sure Hexidecimal Digits is selected for key format. The key index, if you used this example is 0 (zero). Click OK to save the settings and then WinXP will reconnect to the gateway.

Additional Resources
Cisco - Configuring Wired Equivalent Privacy (WEP)

Create OpenBSD and Slackware ISOs

Some people try to hate Microsoft and pretend their operating systems and software don't exist. If you're like me, you've still got at least one machine with Windows still on it, whether you paid for Windows or pirated it from someone else.

Problem
I spend most of my time in Windows for work. I downloaded OpenBSD 3.2-beta, but I didn't want to make a boot floppy disk. I have plenty of CD-Rs and 3 burners, all attached to Windows machines. How am I going to make a bootable OpenBSD CD so I can have something to play with until I can order the official 3.2 release CD?

Solution
Believe it or not, making a bootable ISO in Windows is exactly the same as in Linux or BSD, thanks to official Windows ports of mkisofs. Just grab a copy of cdrtools from the official cdrecord website or the download directory on this server..

I extracted the cdrtools files to c:\cdrtools.

Then I moved the directories I wanted to burn to CD to c:\openbsd creating a structure like the following:

c:\openbsd
    3.2/
        ftplist
        ports.tar.gz
        I386/
            base32.tgz
            bsd
            bsd.rd
            cdrom32.fs
            CKSUM
            comp32.tgz
            etc32.tgz
            floppy32.fs
            ...

Then here's what you need to do to make the ISO file:

Start menu > Run...
(run `command` for Win95\98\ME or `cmd` for NT\2k\XP)

cd c:\
cd openbsd
c:\cdrtools\mkisofs
    -v
    -r
    -T
    -l
    -L
    -J
    -V "OpenBSD3.2-beta"
    -b 3.2/I386/cdrom32.fs
    -c boot.catalog
    -o c:/OpenBSD3.2-beta.iso
    -A "OpenBSD 3.2-beta Install"
    .

The period at the end is necessary.

When the ISO is done, I use Roxio Easy CD Creator 5 to burn it. If you don't have it, cdrecord is in the cdrtools distribution. I haven't tried it, but mkisofs works, so cdrecord probably does too.

Another Example

For linux, I like Slackware. The process is almost the same, except the boot image for slackware has special needs (see README in isolinux). I downloaded Slackware 9.0 beta from slackware-current and wanted a bootable CD. Here's my directory layout:

c:\slack
    bootdisks/
        adaptec.s
        bare.i
        ibmmca.s
        jfs.s
        ...
    BOOTING.TXT
    Changelog.txt
    CHECKSUMS
    CHECKSUMS.md5
    COPYING
    COPYRIGHT.TXT
    CRYPTO_NOTICE.TXT
    CURRENT.WARNING
    FAQ.TXT
    FILELIST.TXT
    isolinux/
        f2.txt
        f3.txt
        initrd.img
        iso.sort
        ...
    kernels/
        adaptec.s/
        bare.i/
        ibmmca.s/
        ...
    PACKAGES.TXT
    PRERELEASE_NOTES
    README81.TXT
    rootdisks/
        install.1
        install.2
        install.3
        ...
    slackware/
        a/
        ap/
        d/
        e/
        f/
        gnome/
        k/
        l/
        n/
        t/
        tcl/
        x/
        xap/
        y/
        CHECKSUMS
        CHECKSUMS.md5
        FILE_LIST
        MANIFEST.gz
        README.TXT
    Slackware-HOWTO
    SPEAK_INSTALL.TXT
    SPEAKUP_DOCS.TXT
    UPGRADE.TXT

I didn't list kde and kdei in the slackware directory on purpose. You can't fit all of Slackware on one CD, so I removed KDE since I prefer Gnome.

Start menu > Run...
(run `command` for Win95\98\ME or `cmd` for NT\2k\XP)

cd c:\
cd slack
c:\cdrtools\mkisofs
    -R
    -J
    -v
    -T
    -d
    -N
    -l
    -L
    -o c:/slackware9.0.iso
    -V "Slackware Install"
    -hide-rr-moved
    -no-emul-boot
    -boot-load-size 32
    -boot-info-table
    -sort isolinux/iso.sort
    -b isolinux/isolinux.bin
    -c isolinux.isolinux.boot
    -A "Slackware Install CD"
    .

or if you were to burn Harry Potter, you might do this:

K:\audio\audiobooks\J. K. Rowling - Harry Potter And The Half-Blood Prince>c:\cd
rtools\mkisofs -R -J -v -T -d -N -l -L -o c:/hphbp.iso -V "Half-Blood Prince" -h
ide-rr-moved -A "J. K. Rowling - Harry Potter And The Half-Blood Prince" .
Warning: creating filesystem that does not conform to ISO-9660.
mkisofs 1.15a12 (i586-pc-cygwin)
Scanning .
  1.96% done, estimate finish Fri Dec  2 21:45:58 2005
  3.91% done, estimate finish Fri Dec  2 21:45:32 2005
  5.87% done, estimate finish Fri Dec  2 21:45:41 2005
  7.83% done, estimate finish Fri Dec  2 21:45:45 2005
  9.78% done, estimate finish Fri Dec  2 21:45:47 2005
11.74% done, estimate finish Fri Dec  2 21:45:41 2005
13.69% done, estimate finish Fri Dec  2 21:45:43 2005
15.65% done, estimate finish Fri Dec  2 21:45:38 2005
17.61% done, estimate finish Fri Dec  2 21:45:41 2005
19.57% done, estimate finish Fri Dec  2 21:45:42 2005
21.52% done, estimate finish Fri Dec  2 21:45:39 2005
23.48% done, estimate finish Fri Dec  2 21:45:36 2005
25.43% done, estimate finish Fri Dec  2 21:45:38 2005
27.39% done, estimate finish Fri Dec  2 21:45:36 2005
29.35% done, estimate finish Fri Dec  2 21:45:37 2005
31.30% done, estimate finish Fri Dec  2 21:45:38 2005
33.26% done, estimate finish Fri Dec  2 21:45:40 2005
35.21% done, estimate finish Fri Dec  2 21:45:38 2005
37.17% done, estimate finish Fri Dec  2 21:45:36 2005
39.12% done, estimate finish Fri Dec  2 21:45:37 2005
41.08% done, estimate finish Fri Dec  2 21:45:36 2005
43.03% done, estimate finish Fri Dec  2 21:45:37 2005
44.99% done, estimate finish Fri Dec  2 21:45:35 2005
46.95% done, estimate finish Fri Dec  2 21:45:36 2005
48.90% done, estimate finish Fri Dec  2 21:45:35 2005
50.86% done, estimate finish Fri Dec  2 21:45:36 2005
52.81% done, estimate finish Fri Dec  2 21:45:35 2005
54.78% done, estimate finish Fri Dec  2 21:45:36 2005
56.73% done, estimate finish Fri Dec  2 21:45:35 2005
58.68% done, estimate finish Fri Dec  2 21:45:35 2005
60.64% done, estimate finish Fri Dec  2 21:45:35 2005
62.60% done, estimate finish Fri Dec  2 21:45:35 2005
64.55% done, estimate finish Fri Dec  2 21:45:34 2005
66.51% done, estimate finish Fri Dec  2 21:45:35 2005
68.47% done, estimate finish Fri Dec  2 21:45:34 2005
70.42% done, estimate finish Fri Dec  2 21:45:35 2005
72.38% done, estimate finish Fri Dec  2 21:45:34 2005
74.33% done, estimate finish Fri Dec  2 21:45:35 2005
76.29% done, estimate finish Fri Dec  2 21:45:34 2005
78.25% done, estimate finish Fri Dec  2 21:45:35 2005
80.20% done, estimate finish Fri Dec  2 21:45:35 2005
82.16% done, estimate finish Fri Dec  2 21:45:34 2005
84.11% done, estimate finish Fri Dec  2 21:45:35 2005
86.07% done, estimate finish Fri Dec  2 21:45:34 2005
88.03% done, estimate finish Fri Dec  2 21:45:35 2005
89.98% done, estimate finish Fri Dec  2 21:45:34 2005
91.94% done, estimate finish Fri Dec  2 21:45:34 2005
93.90% done, estimate finish Fri Dec  2 21:45:34 2005
95.85% done, estimate finish Fri Dec  2 21:45:35 2005
97.80% done, estimate finish Fri Dec  2 21:45:34 2005
99.76% done, estimate finish Fri Dec  2 21:45:35 2005
Total translation table size: 18022
Total rockridge attributes bytes: 24032
Total directory bytes: 38008
Path table size(bytes): 10
Max brk space used 2e000
255616 extents written (499 Mb)

DHCPd on OpenBSD 2.9

I wanted to set up a DHCP server for my network so that I didn't have to manually configure the IPs of each of my machines. Now if I want to change any of the IPs on my network I do it at the server and I can look it up in the configuration file to see if I forget what IP goes to what machine (but that hasn't happened yet).

Running a DHCP server with OpenBSD is really quite simple since it is installed already. All you have to do to turn it on is edit /etc/rc.conf and change dhcpd_flags to "-q" (then I rebooted since I was too lazy to look up the commandline needed to do it without rebooting).

You probably only want to answer to computers on your lan. Answering for your ISP might get you in some trouble. So edit your /etc/dhcpd.conf file. Below is mine with the MAC addresses xx'd out just in case. Note the internal IP address of the OpenBSD box is 192.168.0.1. It is giving specific "static" addresses to the machines where I have specified MAC addresses of NICs and for everything else, they get something between 192.168.0.100 and 192.168.0.155.

The domain-name-servers line has DNS servers for two different ISPs in Texas. You'll probably want to change those if you can find IP addresses of your own.

The DHCP server will assign names to the "static" machines which will probably be added to /etc/hosts and/or BIND later for internal resolution, but I havn't gotten around to doing that yet. You can see the MAC addresses for your NIC(s) in *nix by typing ifconfig or by going to start menu->run->winipcfg and selecting your NIC.

Be sure to edit your /etc/dhcpd.interfaces file so that you only serve IP addresses to the NIC on your LAN and another NIC (like the NIC for your cable modem). My file simply has x10 in it as the interface to my 3com905a NIC.

shared-network LOCAL-NET {
# option default-lease-time 3600;
# option max-lease-time 86400;
option  domain-name "goodmeat.net";
option  domain-name-servers 204.145.251.1, 205.128.118.1, 205.128.118.2;

subnet 192.168.0.0 netmask 255.255.255.0 {
option routers 192.168.0.1;

range 192.168.0.100 192.168.0.155;

host windows {
hardware ethernet 00:00:00:00:00:00;
fixed-address 192.168.0.4;
option host-name "windows";
}
host duron {
hardware ethernet 00:00:00:00:00:00;
fixed-address 192.168.0.2;
option host-name "duron";
}
host valinux {
hardware ethernet 00:00:00:00:00:00;
fixed-address 192.168.0.3;
option host-name "valinux";
}
host dell {
hardware ethernet 00:00:00:00:00:00;
fixed-address 192.168.0.6;
option host-name "dell";
}
}
}

Firewall with IDS in OpenBSD 3.2

Problem
Create an invisible firewall.

Solution
OpenBSD and its packet filter are free and have a good history of tight security.

Introduction

    Difference in OpenBSD releases

    PF in OpenBSD has gone through a history of changes. OpenBSD through version 2.9 had IPF, written by Darren Reed. One day Darren made some confusion on the OpenBSD mailing lists about the licensing of his IPF software in operating systems. The OpenBSD authors didn't like it and someone decided they would make their own packet filter, just for OpenBSD. The packet filter candidate from Daniel Hartmeier was released on http://www.benzedrine.cx/pf.html and was accepted by the core developers into the OpenBSD kernel. The official release of PF was in OpenBSD 3.0. Between the 3.0 release and 3.2, PF stayed relatively unchanged.

    The addition of PF made the rulesets from IPF incompatible with those from IPF. In other words, rules from OpenBSD 2.9 or before won't work with PF on a OpenBSD 3.0 or newer machine. Also note that PF started getting a large clump of changes in OpenBSD 3.3, where the kernel developers decided to merge ALTQ (traffic shaping) and PF so the packet filter could also do traffic shaping. I'd link to ALTQ docs, but by the time I wrote this, they had already started being merged in the snapshot sources of OpenBSD with the PF documentation.

Preparation

    Methods

    There are two ways you can get an install started, by CD or Floppy. I'll assume that since you're using OpenBSD, you want something free, so that rules out the possibility that you bought a OpenBSD release CD from the website, even though you should have.

    Floppy Method

    Download rawrite. The link, unless dead, should go to a rawrite for windows that has a GUI. All other versions you'll find on the internet work with a DOS prompt. Whether from a DOS window or a GUI, you'll need a copy of rawrite to write a copy of the boot image (OpenBSD 3.2 link) to a floppy disk. Open rawrite and write the floppy32.fs file to the floppy disk.

    Notice other releases will have floppy image filenames that match the version release. For example, OpenBSD 3.3 will have a floppy33.fs.

    The aforesaid will cover most hardware configurations. If you know you have some weird hardware in the machine you're going to be installing OpenBSD on, there are actually two other floppy images with different hardware support. From the documentation:

    • floppy32.fs (Desktop PC) supports many PCI and ISA NICs, IDE and simple SCSI adapters and some PCMCIA support.
    • floppyB32.fs (Servers) supports many RAID controllers, and some of the less common SCSI adapters. However, support for many standard SCSI adapters and many EISA and ISA NICS has been removed.
    • floppyC32.fs (Laptops) supports the Cardbus and PCMCIA devices found in many laptops.

    In almost all cases, you'll want the link above.

    CD-R(W) method

    This method will require you to download the install files before installation. Using Bulletproof FTP or CuteFTP might be a good idea here. What you will want is to create a directory called "3.2", or whatever version number you download and go to the version directory for that release of OpenBSD. For version 3.2, that would be ftp://ftp.openbsd.org/pub/OpenBSD/3.2/. Don't forget OpenBSD has many FTP mirrors such as ftp://ftp.usa.openbsd.org/pub/OpenBSD/3.2/

    Here is the directory structure of the files you need to download.
      c:\openbsd
        3.2/
        	ANNOUNCEMENT
            ftplist
            ports.tar.gz
            HARDWARE
            PACKAGES
            i386/
                base32.tgz
                bsd
                bsd.rd
                cdrom32.fs
                CKSUM
                comp32.tgz
                etc32.tgz
                floppy32.fs
                floppyB32.fs
                floppyC32.fs
                game32.tgz
                index.txt
                install.ata
                install.chs
                install.dbr
                install.i386
                install.linux
                install.mbr
                install.os2br
                install.pt
                man32.tgz
                MD5
                misc32.tgz
                xbase32.tgz
                xfont32.tgz
                xserv32.tgz
                xshare32.tgz
            PORTS
            README
            src.tar.gz
            srcsys.tar.gz
      
    Again, note that if you are installing OpenBSD 3.3 or newer, the filenames won't end with 32, but rather 33 or 34, and so on.

    The same tools that you can use on Linux or BSD are available in Windows to make ISO files. OpenBSD doesn't release ISO files to OpenBSD because they need CD sales to support the full time developers. Thanks to official Windows ports of
    mkisofs
    , just grab a copy of cdrtools from the official cdrecord website. Sometimes the windows binaries of cdrtools get moved on the ftp server, so you might have to hunt around.

    Extract the cdrtools files to
    c:\cdrtools
    .

    Then here's what you need to do to make the ISO file:
      Start menu > Run...
      (run `command` for Win95\98\ME or `cmd` for NT\2k\XP)
    
      cd c:\
      cd openbsd
      c:\cdrtools\mkisofs
        -v
        -r
        -T
        -l
        -L
        -J
        -V "OpenBSD3.2"
        -b 3.2/I386/cdrom32.fs
        -c boot.catalog
        -o c:/OpenBSD3.2.iso
        -A "OpenBSD 3.2 Install"
        .
      
    The period at the end is necessary.

    When the ISO is done, use Roxio Easy CD Creator 5 or your favorite burning program to burn it. If you don't have it, cdrecord is in the cdrtools distribution. I haven't tried it, but mkisofs works, so cdrecord probably does too. Documentation is all over the internet for cdrecord.

Install OpenBSD

    From here, it is only better to refer you to the official installation document. It is well written and should get you through the installation process, whether you bought a CD, created one, or made a floppy.

    Install Notes

    • If you did the floppy install, during the install, you'll have the option to get the installation files from FTP and that is what you will do.
    • To make an invisible firewall, you might ask yourself how it will be invisible if you have to configure a network device during the install. Don't worry about that now. Configure a device because we will need it both to grab operating system updates and to have an interface to use to get updates later if needed. You should have three interfaces in your machine for this document. Two will be invisible, and one will be for administration. Just configure one device during install, and leave the other two alone. If you want to configure all of them, you can do that too, because later, they will just be re-configured to be invisible.
    • However you partition your drive, it is a good idea to leave 2gb for the
      /usr
      partition.
    • When you're done with the install, type "reboot".
    • When the system comes back up to a login prompt, the administrator account is "root" and the password is whatever you set during the installation.
    • Configuring your machine with DHCP will be fine for the start. Later in this document will be instructions on how to set a static IP address. If you already know what static IP address you will use, go ahead and set it.
    • The network interface cards in the machine are numbered. For example, the a 3com NIC will use the
      xl
      kernel driver. The card furthest from the CPU is card 0, and each card closer increments by one, so if you have 4 NICs, the one closest to the CPU would be xl3.
    • This tutorial assumes you use 3com 905 NIC. Other network cards will have other kernel driver names in the kernel. When you start up your system, you can do
      
                # dmesg > dmesg
                # grep -e "..:..:..:..:.." dmesg
                # rm dmesg
               
      and the resulting lines should show the NICs, starting with the kernel driver and ending with the adapter MAC address.
    • If you're a Windows user and don't have much experience with BSD or Linux, creating a swap partition is mandatory. It is where all the extra memory processes go when you run out of RAM and is the equivalent of the Windows pagefile. Making it at least twice the size of the amount of space you have in RAM is good.

Update to -stable

    Why, why and where

    Although OpenBSD has a better than average record of remote and local security vulnerabilities, sometimes someone still discovers a flaw. The OpenBSD errata page is usually updated with patches for vulnerabilities or stability flaws. For purposes of explaining how to do an operating system upgrade, we'll skip the method that would use the src.tar.gz and srcsys.tar.gz files from the OpenBSD install tree. If you want to use the src.tar.gz and srcsys.tar.gz files, the patch branches page provides some information and links to get started in that direction.

    Method 1a: Installing kernel and system binary sources from CD

    If you have the official CD, you will only have one src.tar.gz file which contains srcsys.tar.gz.
       # mkdir /usr/src
       # mount /dev/cd0a /mnt
       # cd /mnt
       # cp src.tar.gz srcsys.tar.gz /usr/src
       # cd /usr/src
       # tar -xzf src.tar.gz
       # tar -xzf srcsys.tar.gz
    

    Method 2a: Installing kernel and system binary sources from FTP

    If you have src.tar.gz and srcsys.tar.gz
       # mkdir /usr/src
       # mount /dev/cd0a /mnt
       # cd /mnt
       # cp src.tar.gz srcsys.tar.gz /usr/src
       # cd /usr/src
       # tar -xzf src.tar.gz
       # tar -xzf srcsys.tar.gz
    

    Parts 1b and 2b: Updating kernel and system binary sources from CVS

    You must update your kernel and system sources if you installed them from the release tar files to patch security holes and fix reliability problems.
       # cd /usr
       # cvs -d anoncvs@anoncvs1.usa.openbsd.org:/cvs -q up -rOPENBSD_3_2 -Pd src
      
    During this process, it might look like your system stalled out downloading updates. Most likely it hasn't. The CVS process must still check each file in the source tree to make sure it matches the server. By doing the tar file first and then CVS, you save having to download each individual file and instead just check against a CVS version number. Files that have security updates will have a newer CVS version than the copy on your machine. When the cvs command sees the version difference, it will patch the file on your system to match the one on the server.

    Method 3: Downloading kernel and system binary sources from CVS

    Don't do this step if you already did the stuff above with the tar files. This method will download the contents of src.tar.gz and srcsys.tar.gz and put them in /usr/src for you complete with up-to-date patches.
       # cd /usr
       # cvs -d anoncvs@anoncvs1.usa.openbsd.org:/cvs -q get -rOPENBSD_3_2 -P src
      
    Say yes when it wants to confirm the SSH fingerprint. Note the OPENBSD_3_2 corresponds to the version number. OpenBSD 3.0 would have OPENBSD_3_0 for downloading the stable kernel source. Downloading with CVS will take a while, so while you wait, you can get started on downloading ports.

    Try hitting
    CTRL+ALT+F2
    . You didn't just log out, you switched to another console. Log in again on the second console. You can switch back to the original console by hitting
    CTRL+ALT+F1
    . You can use consoles with the F1, F2, F3, F4, and F6 keys. The other function keys are reserved by the operating system for other background tasks. Now you can multitask.

Install Ports

    What are they?

    Ports are specially packaged software editions for OpenBSD. They are maintained especially for OpenBSD and available from most OpenBSD regional mirrors. Often ports are created when software packages don't compile by default on OpenBSD. The port maintainers massage the source code of the software to make it work with OpenBSD. In some cases, they even make security audits to make the source more secure.

    Method 1: Downloading ports from CVS

    If you're already downloading the kernel and system sources, don't forget you can hit
    CTRL+ALT+F2
    and download ports in the second terminal.
    
       # cd /usr
       # setenv CVSROOT anoncvs@anoncvs1.usa.openbsd.org:/cvs
       # cvs -d $CVSROOT -q get -rOPENBSD_3_2 -P ports
    
    It is also possible to download ports that correspond to the major OpenBSD version release. In most cases, there is no reason to do so because the most recent imports to the CVS server will likely have security updates to software packages since the major release of OpenBSD, therefore the
    -rOPENBSD_3_2
    option was left off of the example.

    Even if you're on a T1, downloading sources and ports will take a while. Get up and strech. Get something to drink. Go to the bathroom. Make some phone calls. Check your email. You're cheering for src to finish first because that's what you'll need to work with first.

    Method 2: Install ports from CD

    This is often the choice if you already have ports.tar.gz downloaded and don't want to wait for it again. If you have the official CD from openbsd.org, ports.tar.gz is on the last CD. If you created your own cd, you know where it is.
    
       # mount /dev/cd0a /mnt
       # cd /mnt/3.2
       # cp ports.tar.gz /usr
       # cd /usr
       # tar -xzf ports.tar.gz
    

    Method 3: Ports from FTP

       # cd /usr
       # lynx ftp://ftp.openbsd.org/pub/OpenBSD/3.2/ports.tar.gz
       # tar -xzf ports.tar.gz
    
    lynx will ask you some questions. The sequence of answers is 'D' for download, '[enter]' to save to disk, '[enter]' again to accept the default filename, 'q' to quit, and 'y' to say you really want to quit.

    Updating packages

    No matter which method you used to istall, there are some packages you will probably want to update individually. Since the OpenBSD 3.2 release, MySQL has has some security patch releases and Snort has had a new release with a newer rule parsing method. If you already set the CVSROOT and haven't rebooted, you don't have to set it again until you reboot.
       # cd /usr
       # setenv CVSROOT anoncvs@anoncvs1.usa.openbsd.org:/cvs
       # cvs -d $CVSROOT -q up -Pd ports/net/snort
       # cvs -d $CVSROOT -q up -Pd ports/databases/mysql
    

Updating the system kernel, binaries, and libraries

    You need to update the system kernel. Don't skip this part. You need to compile your updated kernel source and compile your system binaries and libraries again before moving on. Don't skip steps. Why? Any programs from this point that you compile against security vulnerable kernel hooks or system libraries could have the vulnerabilities linger even after you compile a new kernel, binaries, and libraries. Compile the kernel, reboot, and recompile the system files.

    Compile a new kernel

       # cd /usr/src/sys/arch/i386/conf
       # config GENERIC
       # cd ../compile/GENERIC
       # make depend && make
          (this step will take a while)
       # cp /bsd /bsd.old
       # cp bsd /
    
    Then reboot. You must reboot before moving on to make use of the newly patched kernel.
       # shutdown -r now
    
    
    The -r is for reboot. If you want to shutdown a machine, use -h for halt.

    Compile new system files (binaries and libraries)

        # cd /usr/src
        # rm -r /usr/obj/*
        # make obj && make build
    
    You're recompiling everything installed on your system except your kernel, which you already did. This process will take a long time on an old machine. Rebooting when you're done isn't mandatory, but you should do it for good measure.

Download, compile, and install software from ports

The cool thing about using ports is that with one command, all the downloading, compiling, patching, installing, and cleanup is done with one command and is specifically tailored for OpenBSD. If you watch the installation, it also downloads all the libraries and dependencies that the programs you're installing might have.

    Installing text editor (nano)

    OpenBSD, and most other BSD and Linux operating systems come with VI as their default editor, however VI has a big learning curve. If you're feeling confident with your Google skills, learning VI will benefit you in the long run.

    Since VI has a big learning curve and you probably just want to get the system up, nano is a much simpler text editor which will give you the basic file editing funcitonality you'll need to get the job done.
       # cd /usr/ports/editors/nano
       # make install clean
    
    OpenBSD won't pick up the nano installation right away. It is not in the path. What that means is until you restart, you'll have to type the full path to the nano executable. You make the choice. Reboot or just type the full file path until the next reboot. You won't have to edit files for a bit, so it can wait.

    Compile and install Snort

    The snort intrusion detection system is available in ports. Here we will be adding a "FLAVOR" to the snort installation which changes the default install options. Normally snort writes all the intrusion hits to files, but we're going to want them stored in a MySQL database. If you're curious about the options available for snort install, you can do this:
       # cd /usr/ports/net/snort
       # make show VARNAME=FLAVORS
    
    
    The documentation for snort will explain better what each option does. This is merely an installation guide. For the purposes of this installation, do the following:
       # cd /usr/ports/net/snort
       # env FLAVOR="mysql flexresp" make install
    
    If you sit and watch the installation process, you will notice that MySQL will also automagicly download, get patched, configure, compile, and install. For your information, since the OpenBSD 3.2 release, MySQL has released new versions of MySQL that fix security vulnerabilties. This should not be a problem for an invisible firewall because nobody should have rights to either use the MySQL console client or connect to the MySQL socket. This will be discussed later in this paper.

    Install PHP

    If you are experienced with using the FLAVORS environment variable, you can alter the PHP install to cut install time. An example FLAVOR is shown. It excludes most of the extensions from the PHP install so you have a shorter install time and don't install a lot of software you won't use.
       # cd /usr/ports/graphics/jpeg
       # make install clean
       # cd /usr/ports/graphics/gd
       # make install clean
       # cd /usr/ports/www/php4/core
       # make install clean
       # /usr/local/sbin/phpxs -s
       # cp /usr/local/share/doc/php4/php.ini-recommended /var/www/conf/php.ini
       # cd ../extensions
       # env FLAVOR="no_x11 no_bz2 no_curl no_dba no_dbase no_domxml no_filepro \
        no_gmp no_imap no_ldap no_mcrypt no_mhash no_ncurses no_odbc no_pdf \
        no_pgsql no_shmop no_snmp no_sybase_ct no_xml no_xslt" make install clean
       # cd ../pear
       # make install clean
    
    As you can see, we're leaving out a lot of the functions of PHP, but we don't need them. All that should be left are the MySQL database and GD graphic library extensions. You still need to actually install them:
       # cd /usr/ports/packages/i386/www
       # pkg_add php4-mysql*
       # /usr/local/sbin/phpxs -a mysql
       # pkg_add php4-gd*
       # /usr/local/sbin/phpxs -a gd
    

Configure PHP

Now configure Apache to parse files ending with ".php" using the PHP extension.
   # cd /var/www/conf
   # /usr/local/bin/nano httpd.conf
If you have rebooted your machine since you installed nano, you can do this:
   # cd /var/www/conf
   # nano httpd.conf
Use the CTRL+W function to find "index.html". Add index.php and index.php3 to the DirectoryIndex line to make it look like:
  #
  # DirectoryIndex: Name of the file or files to use as a pre-written html
  # directory index. Separate multiple entries with spaces.
  #
  DirectoryIndex index.php index.html index.php3
Then use the CTRL+W function to find "x-httpd-php". You'll need to uncomment the two lines it finds and alter them. They should look like:
  # For example, the PHP3 module (not part of the Apache distribution)
  # will typically use:
  #
  AddType application/x-httpd-php .php .php3 .phtml
  AddType application/x-httpd-php-source .phps
If you can't find those lines in your httpd.conf file, look harder or just add the lines as you see them above. If there are other file extensions you want to be parsed by the PHP engine, you can add them to the first AddType line too if you want. Some people add .html to obscure the engines running their website. This can be inefficient if you also have a many regular html files that do not contain PHP which will require PHP to examine the files anyway.

Save your httpd.conf with CTRL+X and follow the prompts.

Now it might be nice to test your PHP installation. I delete all the default Apache documents in the web root directory. You can skip that if you want.

   # cd /var/www/htdocs
   # rm -fr *
   # /usr/local/bin/nano phpinfo.php
You're creating a file named phpinfo.php. In it, you want to put:
<?php phpinfo(); ?>
Save it and test it:
   # apachectl start
   # lynx localhost/phpinfo.php
If you see a page that has a bunch of information about PHP, all went well. If you see just phpinfo(); then you messed up somewhere. Go back and make sure you did everything. This won't prevent you from installing Snort, but it will definately keep ACID from working, which is one of the best Snort log HTTP-based viewers.

Setup Apache SSL

OpenBSD ships with an SSL-ready httpd and RSA libraries. For use with httpd(8), you must first have a certificate created. This will be kept in /etc/ssl/ with the corresponding key in /etc/ssl/private/. The steps shown here are taken in part from the ssl(8) man page. Refer to it for further information. This FAQ entry only outlines how to create an RSA certificate for web servers, not a DSA server certificate. To find out how to do so, please refer to the ssl(8) man page.

To start off, you need to create your server key and certificate using OpenSSL:
   # openssl genrsa -out /etc/ssl/private/server.key 1024
The next step is to generate a Certificate Signing Request which is used to get a Certifying Authority (CA) to sign your certificate. To do this use the command:


   # openssl req -new -key /etc/ssl/private/server.key -out /etc/ssl/private/server.csr
This server.csr file can then be given to Certifying Authority who will sign the key. One such CA is Thawte Certification which you can reach at http://www.thawte.com/. Thawte can currently sign RSA keys for you. A procedure is being worked out to allow for DSA keys.

If you cannot afford this, or just want to sign the certificate yourself, you can use the following.

   # openssl x509 -req -days 365 -in /etc/ssl/private/server.csr \
        -signkey /etc/ssl/private/server.key -out /etc/ssl/server.crt
With /etc/ssl/server.crt and /etc/ssl/private/server.key in place, you should be able to start httpd(8) with the -DSSL flag (see the section about rc(8) in this faq), enabling https transactions with your machine on port 443.

See 10.7

Start Apache on boot

   # cd /etc
   # /usr/local/bin/nano rc.conf
Change httpd_flags from NO to "-u -DSSL". Add the quotes too. Be careful about the comment at the end of the line (# for normal use...) spilling over to the next line. That is bad. If it does, either get it all on one line again or delete the comment. Hit CTRL+X to save the file.

/var/www
. The -DSSL tells Apache to start up with SSL. A later section will discuss SSL. If you know you just want to run regular HTTP services through port 80 and don't want SSL through 443, you can leave off the -DSSL and skip the Apache SSL configuration.

Finishing MySQL Install

Check /etc/rc.conf to make sure that the following line is at the bottom:
local_rcconf="/etc/rc.conf.local"
   # cat /etc/rc.conf
The line should be there, but if for some reason it isn't, add it with nano.
/etc/rc.conf.local
should not exist. If it does or if it doesn't, do exit nano and do the following:

   # echo "mysql=YES" >> /etc/rc.conf.local
Using
echo
is just shorthand so you don't have to use an editor to edit a file. If the file doesn't exist, it will be created. If it does exist,
mysql=YES
will be appended to it. You can use
cat
to verify the contents of
/etc/rc.conf.local
.
cat
is a tool that can be used to output a file right to the screen.
   # cat /etc/rc.conf.local
MySQL isn't done installing. Go back to ports.
   # cd /usr/ports/databases/p5-DBD-Msql-Mysql
   # make install clean
   # cd /usr/ports/packages/i386/databases
   # pkg_add mysql-server*
Next you need to move the configuration file for MySQL to
/etc
. In
/usr/local/share/mysql
look at the files
my-small.cnf
,
my-medium.cnf
,
my-large.cnf
, and
my-huge.cnf
.
my-medium.cnf
is good for most server configurations.
   # cd /usr/local/share/mysql
   # cp my-medium.cnf /etc/my.cnf
   # /usr/local/bin/nano /etc/my.cnf
We're almost done with MySQL. Edit /etc/rc.conf and change
shlib_dirs= # extra directories for 
ldconfig
at the bottom of the file to read like this:

   # shlib_dirs="/usr/local/lib/mysql"
Or if you know you have multiple directories:
   # shlib_dirs="/usr/local/lib/{mysql,libmcrypt}"
Make sure the (# extra directories...) comment doesn't spill over to the next line. The following will add execute permissions to the file that starts mysql.
   # mkdir /var/run/mysql
   # chown mysql /var/run/mysql
   # chmod 755 /usr/local/share/mysql/mysql.server
If
/var/run/mysql
exists already, that's good. If it doesn't exist it'll be created. Either way, it should be there. Add this to the bottom of
/etc/rc.local
:

   if [ X"${mysql}" == X"YES" -a -x /usr/local/bin/safe_mysqld ]; then
	echo -n " mysqld"; /usr/local/share/mysql/mysql.server start
	/bin/sleep 1
   fi
This will start MySQL when you boot your server. Now might be a good time to reboot if you're curious to see if everything will crash and burn. If you don't want to reboot, you can do this:
   # /usr/local/share/mysql/mysql.server start
   # /usr/local/bin/mysql -u root
The second line will try to connect to MySQL. You can either connect or you can't. A connection is good. The password is blank if you did not set it before. Type
exit
to get out of mysql. When you reboot, you should see
mysqld
in the local daemons list just before logon. Now might be a good time to change the default root password to your MySQL server:
   # /usr/local/bin/mysqladmin -u root -p password 'new-password'
If it's a single user machine and you properly deny outside connections to MySQL, you might be fine leaving the root password blank. Later in this tutorial, we will configure the server to not accept connections on on the MySQL socket from anywhere other than localhost.

If you think you know what you're doing, now might be a good time to stop mysqld and move /var/mysql to another drive if you've got a multiple drive system. For example, you might have created a /misc partition during installation on a second hard drive. Then you could move /var/mysql to it and edit the datadir var in /usr/local/share/mysql/mysql.server and /etc/my.cnf to point to the new db storage directory.

Snort

Snort is a free intrusion detection system.

    Configure Snort

    Now you need to configure MySQL to have a user and table to store Snort alerts:
       # mysqladmin -u root -p create snort
       # mysqladmin -u root -p create snort_archive
       # mysql -u root -p
    
    If you didn't set a password before, when it asks for a password, hit enter. At the mysql prompt, type
       mysql> grant all on snort.* to snort@localhost identified by 'snort';
       mysql> grant all on snort_archive.* to snort@localhost identified by 'snort';
       mysql> exit
    
    
    snort
    will be the password in the quotes.
    snort.*
    says all tables in the snort database.
    snort@localhost
    says the snort user can only connect from localhost. Now add a system user for snort.
       # groupadd snort
       # adduser -batch snort snort -shell /bin/nologin -home /home
    
    Since this is the first time for you to create a user on the system, it will ask you for default values for accounts. Just hit enter to all of them to accept the set defaults in brackets.
       # mkdir /var/log/snort
       # chown snort /var/log/snort
    
    We will start Snort a lot like we started MySQL:
       # echo "snort=YES" >> /etc/rc.conf.local
       # /usr/local/bin/nano /etc/rc.local
    
    Now you will need to decide which interfaces in your machine will do what. Pick the one that will be on the inside of the firewall. In the example machine, we have one administration NIC with an IP address assigned, and two more, one for the outside of the firewall and one for the inside. For the sake of this example, xl1 will be the interface on the inside of the firewall. Add this to the bottom of your
    rc.local
    .
    
       if [ X"${snort}" == X"YES" -a -x /usr/local/bin/snort ]; then
    	echo -n " snort"; /usr/local/bin/snort -D -d -c /etc/snort/snort.conf -u snort -g snort -i xl1
       fi
    
    The
    echo
    line will be longer than the screen, so get it to fit on one line when it spills over to the next. If you are using VI, you don't have to worry about things like that, because when you edit a file with VI and a line spills over, it does a wordwrap instead of a line break like nano. Also note the
    -i xl1
    which corresponds to the interface on the inside of the firewall. Then we can import the Snort database information into MySQL:
       # cd /usr/ports/net/snort
       # mysql -u snort -p snort < /usr/ports/net/snort/w-snort-*/snort-*/contrib/create_mysql
       # make clean
    
    
    If you had done a
    make install clean
    or
    make clean
    for snort already, you can do a
    make extract
    to get the sources you'll need to import the tables you need into mysql. There are a lot of rules files in
    /usr/local/share/examples/snort
    . We should put them in a different directory.
       # mkdir /etc/snort
       # cd /usr/local/share/examples/snort
       # cp -r * /etc/snort
    
    
    Then go to the
    /etc/snort
    and edit snort.conf. The file will explain what variables do what. Defaults will probably work if you're scared to change the file. The only thing you absolutely have to change is find the mysql log line, uncomment it, and change the login information for each of the variables on the line, otherwise you won't be able to view the snort logs from ACID.

    To log to MySQL for ACID, you will need to find the database section, uncomment the line for MySQL in
    snort.conf
    , and change the connection details. Just make sure you read the whole configuration file.

    Update Snort rules

       # mkdir /usr/local/src
       # cd /usr/local/src
       # lynx http://www.snort.org/dl/rules/snortrules-stable.tar.gz
       # tar -xzvf snortrules-stable.tar.gz
       # cp -r rules /etc/snort
       # cd /etc/snort/rules
       # mv * ..
       # cd ..
       # mv *.rules rules
    
    Now you must go back to
    /etc/snort
    and edit snort.conf to add the additional rules files that aren't in the distribution and point the rules location to
    /etc/snort/rules

    Create firewall network

    If you want a NAT configuration, you'll need a LAN IP for an interface on the inside of the network. Choose a network device not in use. We'll assume that xl0 right now is configured with an external world address. Edit hostname.xl1. Nano and vi will create it if it's not there already. Put this line in it:
       inet 10.0.0.250 255.255.0.0 NONE
    
    To create IP aliases for the same network interface, the file would look like:
       inet 10.0.0.250 255.255.0.0 NONE
       inet alias 10.0.0.1 255.255.0.0 NONE
       inet alias 10.0.1.250 255.255.0.0 NONE
       inet alias 10.0.2.250 255.255.0.0 NONE
       inet alias 10.0.3.250 255.255.0.0 NONE
       inet alias 10.0.4.250 255.255.0.0 NONE
    
    If you don't want to reboot now, you can configure the network device with the
    ifconfig
    command.
    
       # ifconfig xl1 inet 10.0.0.250 netmask 255.255.0.0
       # ifconfig xl1 inet alias 10.0.0.1.250 netmask 255.255.0.0
    
    After you reboot, the hostname.xxx file will automaticly do ifconfig for you.

    The other choice is creating an invisible passthru firewall. Either way, if you want extra interfaces to go to the internal network interface and have them bridged together, you'll need to create invisible interface configurations for the other NICs.
       # ifconfig xl2 up
       # echo "up" > /etc/hostname.xl2
    
    Make sure you don't create a hostname file for the wrong interface. If you echo "up" to the interface hostname file you're using to get on the internet, you won't be able to get on the internet until you go back and replace up with the correct internet configuration. The interface you should have configured by default during the install was
    xl0


    While you're at it, now is a good time to add the second invisible interface for the firewall.
       # ifconfig xl3 up
       # echo "up" > /etc/hostname.xl3
    
    Now you can bridge them together. Your bridge configuration will list all the network interfaces for your internal network. For an invisible firewall, that should be two interfaces. For a NAT machine, the PCI slot number is the limit. Create /etc/bridgename.bridge0
       add xl1
       add xl2
       add xl3
       add xl4
       blocknonip xl1
       blocknonip xl2
       blocknonip xl3
       blocknonip xl4
       up
    
    Again, if you don't want to reboot right now, you can use the
    brconfig
    command to manually create the bridge:
       # brconfig bridge0 add xl1
       # brconfig bridge0 add xl2
       # brconfig bridge0 add xl3
       # brconfig bridge0 add xl4
       # brconfig bridge0 blocknonip xl1
       # brconfig bridge0 blocknonip xl2
       # brconfig bridge0 blocknonip xl3
       # brconfig bridge0 blocknonip xl4      
       # brconfig bridge0 up
    

    Start Snort

    You won't have to do this all the time because the editing you did to rc.local with a similar line should start Snort automagicly on boot. This will get snort running now just to make sure it runs.
       # /usr/local/bin/snort -D -d -c /etc/snort/snort.conf -u snort -g snort -i xl1
    
    
    You'll either get a "Snort running" message, or a "FATAL ERROR". The errors are quite informational and usually tell you, you have a file in the wrong place if you get one. Get
    /etc/snort/snort.conf
    to sync with where files are in the
    /etc/snort
    directory if you have an error. If it says it needs a file, but you don't know where to find it
       # find / -name "filename" -print
    
    should spit it out on the screen if it exists. It's a console Find File equivilent from Windows. You can add asterisks for wildcards if you feel the need.

    Install ADODB database abstraction

       # mkdir /usr/local/src
       # cd /usr/local/src
       # lynx http://php.weblogs.com/ADODB
       [ download file here and exit lynx ]
       # tar -xzf adodb*.tgz
    

    Install PHPlot graphing scripts

       # cd /usr/local/src
       # lynx http://www.phplot.com
       [ download file here and exit lynx ]
       # tar -xzf phplot-*.tar.gz
       # lynx http://www.aditus.nu/jpgraph/jpdownload.php
       [ download file here and exit lynx ]
       # tar -xzf jpgraph-*.tar.gz
    

    Install ACID

       # cd /usr/local/src
       # lynx http://www.andrew.cmu.edu/~rdanyliw/snort/snortacid.html
       [ download file here and exit lynx ]
       # tar -xzf acid*.tgz
       # mkdir /var/www/phplibs
       # mv adodb /var/www/phplibs
       # mv jpgraph-x.xx /var/www/phplibs/jpgraph
       # mv phplot-x.x.x /var/www/phplibs/phplot
       # mv acid /var/www/htdocs
       # cd /var/www/htdocs/acid
       # nano acid_conf.php
    
    Now edit acid_conf.php to point
    $DBlib_path
    to
    /var/www/phplibs/adodb
    , change the logon information for MySQL to use
    snort
    as the user and password with for the
    snort
    and
    snort_archive
    databases, and set
    $ChartLib_path
    to
    /var/www/phplibs/phplot
    .

    Now you'll probably want to put a password on the access to Apache. Edit /var/www/conf/httpd.conf, find the directory directive for /var/www/htdocs and change AllowOverride from None to All. This will allow us to use .htaccess files to change permissions of directories in the Apache web directory. An .htaccess file in a directory provides specific instructions for permissions to that specific directory. In this example, we will create an .htaccess file in the root directory, thereby blocking off all unauthorized access.

    
       # htpasswd -c /var/www/passwd administrator
    
    Then create the file /var/www/htdocs/.htaccess
       AuthUserFile /var/www/passwd
       AuthName "firewall"
       AuthType Basic
       
       
       require valid-user
       
    

Clear console on logout

Clearing the console isn't nessesary to get your firewall up and running, but it does add an extra layer of security to sensitive information you might enter in the console. When you log out, it will automaticly clear away for you. To do this you must add a line in
/etc/gettytab
. Change the current section:
   P|Pc|Pc console:\
        :np:sp#9600:
adding the line ":cl=\E[H\E[2J:" at the end, so that it ends up looking like this:
   P|Pc|Pc console:\
        :np:sp#9600:\
	:cl=\E[H\E[2J:
Changes will be immediate. Next time you log out, the console will clear. You can get the same result by typing
clear
at the prompt, but who wants to remember to do that every time.

Lockdown single user mode

One element of security often overlooked is physical security. The OpenBSD developers built a "feature" into OpenBSD called single user mode. Single user mode allows you, if you are at the keyboard, to boot into the system to do recovery or diagnostic work. Under normal circumstances, booting into single user mode gives you automatic root access, without asking for a password. Single user mode is also often used for password recovery when nobody can remember the root password. You can make single user mode ask for the root password.

Edit
/etc/ttys
to change the current line:
   console "/usr/libexec/getty Pc"     vt220   off secure
to insecure

   console "/usr/libexec/getty Pc"     vt220   off insecure

Deny remote root login

Root has the power to do anything to a system. Here we'll add a user that has very little power to change files on the system.
   # adduser
If you decided not to install Snort, the
adduser
command will ask for default user account values. Just hit enter to accept each of the default values in brackets. Then follow the prompts to create a user.

   Use option "-silent" if you don't want to see all warnings and questions.
   
   Reading /etc/shells
   Check /etc/master.passwd
   Check /etc/group
   
   Ok, let's go.
   Don't worry about mistakes. I will give you the chance later to correct any input.
   Enter username [a-z0-9_-]: administrator
   Enter full name []: administrator
   Enter shell csh ksh nologin sh [sh]: csh
   Uid [1002]: [ENTER]
   Login group administrator [administrator]: [ENTER]
   Login group is "administrator". Invite administrator into other groups: guest no [no]: wheel
   Enter password []: ********
   Enter password again []: ********
   
   Name:     administrator
   Password: ****
   Fullname: administrator
   Uid:      1002
   Gid:      1002
   Groups:   administrator wheel
   HOME:     /home/administrator
   Shell:    /bin/sh
   OK? (y/n) [y]: [ENTER]
   Added user "administrator
   Copy files from /etc/skel to /home/administrator
   Add another user? (y/n) [y]: n
   Goodbye!
   #
Don't make the administrator password the same as the root password. If someone compromised the system, was able to read /etc/passwd and noticed that the administrator password hash is the same as the root password, you're double login protection is wasted. If you're already familiar with a particular shell, you can pick something other than csh. Default is sh, but root's default is csh.

Edit
/etc/ssh/sshd_config
and change
   #PermitRootLogin yes
to

   PermitRootLogin no
Now that you can no longer log in as root remotely, when you log in as administrator over ssh, you'll have to use the
su
command to become a super user. It will ask you for a password. When it does, type in the root password and you will be root. This is only possible because when you created the administrator user, you added them to the wheel group, which is where super users go. Only users in the wheel group can become a super user from
su
. When you're done being a super user, type
exit
to become a regular user again. The
su
will make a log of when and where someone becomes a super user.

Configuring the firewall

Remember, this section was written for OpenBSD 3.3. These rules might work on other OpenBSD installations >=3.0, however that doesn't mean that they're right.

    Enable IP forwarding

    Edit
    /etc/sysctl.conf
    . Uncomment
    net.inet.ip.forwarding=1
    . While you're in there, you could uncomment
    vm.swapencrypt.enable=1
    .

    Create invisible interfaces

    For this example,
    xl0
    is our administration interface, which will have an IP assigned and firewall rules to allow only SSH and HTTPS connections. The invisible interfaces are
    xl1
    ,
    xl2
    , and
    xl3
    .

    There are some fine details of creating a bridge between network interfaces for a firewall.
    Rule 1: Always filter on one interface.
    Rule 2: Don't filter on the other interfaces.

    Remember, the computer doesn't know which interface leads to the internet and which goes to a crossover cable for a server. When you bridge interfaces, you are essentially creating one virtual interface.

    See the Create invisible interface section for the invisible device configuration.

    You also want to bridge those interfaces to make a connection between them. Create a file in
    /etc
    named
    bridgename.bridge0
    . Add the following to it and save.
       add xl1
       add xl2
       add xl3
       up
    
    You can lock things down even tighter. Type
    man brconfig
    at a prompt to get the manual for the bridge software. Some options might be to consider making the bridge
    
       add xl1
       add xl2
       add xl3
       blocknonip xl1
       blocknonip xl2
       blocknonip xl3
       rule pass in on xl3 dst 00:BB:A0:33:3A:D1
       rule pass out on xl3 src 00:BB:A0:33:3A:D1
       rule block in on xl3
       rule block out on xl3
       up
    
    What the rules have done is block all traffic that's not associated with the computer behind the firewall that has the MAC address of 00:BB:A0:33:3A:D1. If it either isn't headed to or from the machine with 00:BB:A0:33:3A:D1, it won't get passed. If you decide to use bridge rules with MAC addresses, you'll have to maintain a current ruleset of MACs, otherwise don't use bridge rules at all. Note:Experience has shown this author that MAC filtering in this style is not 100% good 100% of the time. If you decide you want MAC address filtering, make sure you test a lot. Merely adding the interfaces should be enough for most firewalling situations.

    Note that the packet filter reads traffic on the IP level. In other words, it won't filter traffic based on MACs, just source and destination IPs by port number and traffic type. The bridge is the only place to filter by MAC and the packet filter is the only place to filter by IP.

    Configure static network interface

    If you already configured the administration static IP you want during the OS install, you can skip this section.

    To switch from DHCP to static or to fix a mess-up if you echoed "up" into the wrong hostname file, you need to edit the hostname.if file for the interface you're using. In the example, the contents of
    /etc/hostname.xl0
    should be
       dhcp NONE NONE NONE
    
    for a DHCP environment. To change it to static, change it to match
       echo "inet 192.168.0.200 255.255.255.0 NONE" > /etc/hostname.xl0
    
    Note that the hostname.if file doesn't contain the gateway IP. That is stored in a different file.
       echo "192.168.0.1" > /etc/mygate
    
    To activate the gateway address, you'll have to restart. There are ways to activate it otherwise, but saying to restart is much simpler. You can do the research if you don't want to reboot.

    Setting up the packet filter (PF)

    First turn PF on. Edit
    /etc/rc.conf
    .
    
       PF=YES
    
    and then turn PF on without having to reboot.
       # pfctl -e
    
    You will not get enough information about packet filtering from this tutorial to be well versed. Minimally, you need to read these two documents and understand them or you're wasting your time with this firewall.


    You can type
       # man pfctl
    
    or
    
       # man pf.conf
    
    to get the manual for the packet filter right from your machine. To exit the man pages viewer, hit the "q" key or scroll all the way down to the end of the document. Page Down will get you there faster.

    Here is a ruleset you might use to start an invisible passthru firewall. It uses the slower bracketed blocks of IPs that expand into separate rules to check against incoming and outgoing traffic.
    #############################
    # /etc/pf.conf
    # David Norman, OpenBSD 3.2
    #############################
    
    #############################
    # Begin Ruleset
    #############################
    
    external="xl1"
    admin="xl0"
    
    # not routable
    # spaces before brackets required
    #
    spoofed="{ 10.0.0.0/8, 172.16.0.0/12, 192.168.0.0/16, \
                224.0.0.0/4, 240.0.0.0/5, 127.0.0.1/8 }"
    
    
    # IP blocks ripped from http://www.sentry.net/~obsid/
    #
    reserved="{ 0.0.0.0/8, 1.0.0.0/8, 2.0.0.0/8, 5.0.0.0/8, \
                 23.0.0.0/8, 27.0.0.0/8, 31.0.0.0/8, \
                 36.0.0.0/8, 37.0.0.0/8, 39.0.0.0/8, 41.0.0.0/8, \
                 42.0.0.0/8, 58.0.0.0/8, 59.0.0.0/8, \
                 60.0.0.0/8, 69.0.0.0/8, 70.0.0.0/8, \
                 71.0.0.0/8, 72.0.0.0/8, 73.0.0.0/8, 74.0.0.0/8, \
                 75.0.0.0/8, 76.0.0.0/8, 77.0.0.0/8, 78.0.0.0/8, \
                 79.0.0.0/8, 80.0.0.0/8, 81.0.0.0/8, 82.0.0.0/8, \
                 83.0.0.0/8, 84.0.0.0/8, 85.0.0.0/8, 86.0.0.0/8, \
                 87.0.0.0/8, 88.0.0.0/8, 89.0.0.0/8, 90.0.0.0/8, \
                 91.0.0.0/8, 92.0.0.0/8, 93.0.0.0/8, 94.0.0.0/8, \
                 95.0.0.0/8, 96.0.0.0/8, 97.0.0.0/8, 98.0.0.0/8, \
                 99.0.0.0/8, 100.0.0.0/8, 101.0.0.0/8, 102.0.0.0/8, \
                 103.0.0.0/8, 104.0.0.0/8, 105.0.0.0/8, 106.0.0.0/8, \
                 107.0.0.0/8, 108.0.0.0/8, 109.0.0.0/8, 110.0.0.0/8, \
                 111.0.0.0/8, 112.0.0.0/8, 113.0.0.0/8, 114.0.0.0/8, \
                 115.0.0.0/8, 116.0.0.0/8, 117.0.0.0/8, 118.0.0.0/8, \
                 119.0.0.0/8, 120.0.0.0/8, 121.0.0.0/8, 122.0.0.0/8, \
                 123.0.0.0/8, 124.0.0.0/8, 125.0.0.0/8, 126.0.0.0/8, \
                 127.0.0.0/8, 197.0.0.0/8, 201.0.0.0/8, 219.0.0.0/8, \
                 220.0.0.0/8, 221.0.0.0/8, 222.0.0.0/8, 223.0.0.0/8, \
                 240.0.0.0/8, 241.0.0.0/8, 242.0.0.0/8, 243.0.0.0/8, \
                 244.0.0.0/8, 245.0.0.0/8, 246.0.0.0/8, 247.0.0.0/8, \
                 248.0.0.0/8, 249.0.0.0/8, 250.0.0.0/8, 251.0.0.0/8, \
                 252.0.0.0/8, 253.0.0.0/8, 254.0.0.0/8, 255.0.0.0/8 }"
    
    uttnet="{ 198.213.56.0/24, 198.213.57.0/24, 198.213.58.0/24, \
                 198.213.59.0/24, 206.76.228.0/24, 206.76.229.0/24, \
                 204.158.4.0/24 }"
    
    scrub in on $external all
    
    # Loopback device rules
    pass out quick on lo0 all keep state
    pass in quick on lo0 all keep state
    
    block in on { $external, $admin } all
    
    ## Comment this out if you're using LAN IPs
    block in from no-route to any
    
    ## good rule but also dangerously strict and needs IP in place of ($external)
    # block out quick on $external ! from ($external) to any
    
    block in quick on { $external, $admin } inet from $spoofed to any
    block in quick on { $external, $admin } inet from $reserved to any
    
    pass in quick on $admin inet proto tcp from $uttnet to { 198.213.57.12/32 } port { 22, 443 } keep state
    
    pass out quick proto tcp all flags S/SA keep state
    pass out quick proto udp all keep state
    pass in quick on $external inet proto tcp from any to { 198.213.57.6/32, 206.76.228.42/32 } port 80
    pass in quick on $external inet proto icmp all icmp-type 8 code 0 keep state
    pass out quick on $external inet proto icmp all icmp-type 8 code 0 keep state
    
    Here is a newer ruleset that uses tables for blocks of IPs. PF takes as long to look up an address in a table with 5 addresses as it does with a table full of 100,000 addresses.
    #############################
    # /etc/pf.conf
    # Academic Computing Services
    # OpenBSD 3.3 PF ruleset
    #############################
    
    # reload rules with `pfctl -f /etc/pf.conf`
    # rc.conf should take over after you change it there and reboot
    
    ExtIF="xl3"
    IntIF="xl1"
    ExtIP="198.213.57.7"
    
    # not routable
    # spaces before brackets required
    #
    table <spoofed> const { 10/8, 172.16/12, 192.168/16, \
                224/4, 240/5, 127.0.0.1/8 }
    
    # IP blocks ripped from http://www.sentry.net/~obsid/
    #
    table <reserved> const { 0/8, 1/8, 2/8, 5/8, \
                 23/8, 27/8, 31/8, \
                 36/8, 37/8, 39/8, 41/8, \
                 42/8, 58/8, 59/8, \
                 60/8, 69/8, 70/8, \
                 71/8, 72/8, 73/8, 74/8, \
                 75/8, 76/8, 77/8, 78/8, \
                 79/8, 80/8, 81/8, 82/8, \
                 83/8, 84/8, 85/8, 86/8, \
                 87/8, 88/8, 89/8, 90/8, \
                 91/8, 92/8, 93/8, 94/8, \
                 95/8, 96/8, 97/8, 98/8, \
                 99/8, 100/8, 101/8, 102/8, \
                 103/8, 104/8, 105/8, 106/8, \
                 107/8, 108/8, 109/8, 110/8, \
                 111/8, 112/8, 113/8, 114/8, \
                 115/8, 116/8, 117/8, 118/8, \
                 119/8, 120/8, 121/8, 122/8, \
                 123/8, 124/8, 125/8, 126/8, \
                 127/8, 197/8, 201/8, 219/8, \
                 220/8, 221/8, 222/8, 223/8, \
                 240/8, 241/8, 242/8, 243/8, \
                 244/8, 245/8, 246/8, 247/8, \
                 248/8, 249/8, 250/8, 251/8, \
                 252/8, 253/8, 254/8, 255/8 }
    
    #set loginterface xl1
    set optimization conservative
    
    scrub in on $ExtIF all
    
    nat on $ExtIF from 10/8 to any -> $ExtIP
    
    # Loopback device rules
    pass out quick on lo0 all
    pass in quick on lo0 all
    
    # Default block everything
    block in on $ExtIF inet all
    block in on $IntIF inet from any to $IntIF 
    antispoof for lo0
    # Editor note: antispoof here on OBSD 3.2 kills talking btwn bridged interfaces
    #antispoof for { $ExtIF, $IntIF } inet
    # so I came up with a looser rule:
    block in on ! xl3 inet from 10.0.0.250/32 to any
    
    # silently drop UDP broadcasts
    #
    block in quick on $ExtIF inet proto udp from any to 255.255.255.255/32
    
    # Block any IP spoofing attempts. (Packets "from" our network
    # shouldn't be coming from the outside).
    #
    block in quick on $ExtIF inet from  to any
    
    # Block all reserved private IP addresses.
    #
    block in quick on $ExtIF inet from <reserved> to any
    
    # Outgoing Windows networking won't work stable over NAT
    #
    # rules not working?
    block out quick on $ExtIF inet proto tcp from any to any port { 135, 137 >< 139, 445 }
    block out quick on $ExtIF inet proto udp from any to any port { 135, 137 >< 139, 445 }
    
    ## start letting some stuff through
    #
    #  remote administration
    pass in quick on $ExtIF inet proto tcp from { 206.76.228.0/24, 198.213.57.0/24, 198.213.58.0/24, 205.165.41.0/24 } to $ExtIP/32 port { ssh, https } flags S/SA modulate state
    
    # pings
    pass in quick on { $ExtIF, $IntIF } inet proto icmp all icmp-type 8 code 0 keep state
    # dhcp and ntp
    pass in quick on $ExtIF inet proto udp from 10/8 to any port { 68, 123 } keep state
    
    # Let traffic in and out
    pass out quick on $ExtIF inet proto tcp all flags S/SA keep state
    pass out quick on $ExtIF inet proto udp all keep state
    
    ## Let pings out and back
    #
    pass in quick on { $ExtIF, $IntIF } inet proto icmp all icmp-type 8 code 0 keep state
    pass out quick on { $ExtIF, $IntIF } inet proto icmp all icmp-type 8 code 0 keep state
    
    

Transparent Squid

   # cd /usr/ports/www/squid
   # env FLAVOR="transparent" make install clean
   # /usr/local/sbin/squid -z
Before running
squid -z
, you might want to edit the default configuration in
/etc/squid
. The cache directories will be created with
squid -z
so if you want your cache in a different directory than
/var/squid/cache
or if you want to put your cache on a RAID striped device for extra speed, you'll want to edit some of the default options in
/etc/squid
.

Setting up BIND (or other DNS) is a good idea for local DNS resolution.

NTP (Network Time Protocol) daemon

Installing NTPd allows your machine to check with atomic clock servers for the correct time.
   # cd /usr/ports/net/ntp/stable
   # make install clean
   # echo "0" > /etc/ntp.drift
Then create
/etc/ntp.conf
with the following contents.
   server 139.78.100.163 prefer minpoll 9 maxpoll 13
   server 128.194.254.9
   server 129.7.1.66
   server 131.107.1.10
   
   driftfile /etc/ntp.drift
Optionally, you can add
restrict 10.0.0.0 mask 255.255.0.0 nomodify nopeer
to the bottom of the
ntp.conf
file. If you want to let NTP through the firewall, it is port 123/udp.

Symon

Symon is a system monitor that lets you view the status of the CPU, memory, PF, NICs, and misc services running on the system. It uses PHP and a combination of a server (symux) and monitor that reports to the server (symon). It stores the data in a special type of database for continuous data collection called rrdtool.
   # cd /usr/ports/sysutils/symon
Versions of Symon 2.60 and before have an installation bug that doesn't install all the PHP scripts that are needed for viewing services from Apache, so this will bypass some of the post-installation instructions to do some manual configuration. Symon 2.61 should have a fix to the installation bug.

Edit
/usr/ports/sysutils/symon/Makefile
. Since you have already custom installed PHP, you don't want the Symon install to do the generic one again. Change
   WEB_RUNDEPENDS=     rrd:rrdtool-*:net/rrdtool php:php4->=4.2.3:www/php4/core

to
   WEB_RUNDEPENDS=     rrd:rrdtool-*:net/rrdtool
And then also change
   RUN_DEPENDS=     rrd:rrdtool-*:net/rrdtool  php:php4->=4.2.3:www/php4/core
to
   RUN_DEPENDS=     rrd:rrdtool-*:net/rrdtool

Then you can do
   # make install
   # cd w-symon-2.60/symon/symon2web
   # rm Makefile
   # mkdir /var/www/htdocs/symon
   # chmod 444 /var/www/htdocs/symon/*
   # cd /usr/ports/sysutils/symon
   # make clean
   # cd /usr/ports/packages/i386/sysutils
   # pkg_add symon-2.60.tgz
   # cd /usr/local/share/symon
   # ./c_smrrds.sh cpu0
   # ./c_smrrds.sh pf
   # ./c_smrrds.sh mem
   # ./c_smrrds.sh bridge0
   # ./c_smrrds.sh lo0
   # ./c_smrrds.sh xl0
   # ./c_smrrds.sh xl1
   # ./c_smrrds.sh xl2
   # ./c_smrrds.sh xl3
   # ./c_smrrds.sh xl4
  do this if you have an ata drive # ./c_smrrds.sh wd0
  do this if you have a scsi drive # ./c_smrrds.sh sd0
   # ./c_smrrds.sh debug
   # ./c_smrrds.sh proc_httpd
   # ./c_smrrds.sh proc_snort
   # ./c_smrrds.sh proc_sshd
   # ./c_smrrds.sh proc_mysqld
   # mkdir /var/symon
   # mkdir /var/symon/localhost
   # mv *.rrd /var/symon/localhost
   # cd /var/www/htdocs/symon
Most installations will give you an error at the end of the make. Everything actually compiled correctly. Edit
/var/www/htdocs/symon/datasources.inc
and change the $symon2web variable to
/var/symon
.

Then there are a few finishing touches to configure and start the monitor. Create
/etc/symon.conf
. The contents should be similar to the following:
   monitor { cpu(0),  mem, pf,  if(xl0), if(xl1),
	  if(lo0), if(xl2), io(wd0), debug,
          if(bridge0), proc(httpd), proc(sshd),
	  proc(snort), proc(mysqld)}  
		stream to 127.0.0.1 2100
Then create a configuration for the monitor server as
/etc/symux.conf
:
   mux 127.0.0.1 2100

   source 127.0.0.1 {
	accept { cpu(0), mem, pf, if(xl0), if(xl1),
	         if(lo0), io(wd0), if(xl2),  debug,
                 if(bridge0), proc(httpd), proc(sshd),
		 proc(snort), proc(mysqld)}

	datadir "/var/symon/localhost"
   }
Then set some permissions on them. While not required, setting the permissions to 444 makes the file only have read permissions, no write or execute.

   # chmod 444 /etc/symon.conf
   # chmod 444 /etc/symux.conf
To start them, symux (the server) goes first so when the monitor (symon) starts, it has a server to send data to.
   # /usr/local/libexec/symux
   # /usr/local/libexec/symon
Edit
/etc/rc.local
and add this at the bottom:
   if [ -x /usr/local/libexec/symux ]; then
	echo -n ' symux';	/usr/local/libexec/symux
   fi

   if [ -x /usr/local/libexec/symon ]; then
	echo -n ' symon';	/usr/local/libexec/symon
   fi

Additional Notes

  • pftop
  • df -h
  • fewer httpd children
  • winscp

Fix /etc/fstab syntax error in OpenBSD 3.1

I messed up my copy of /etc/fstab and when I booted into obsd 3.1, it threw me into single user mode. /usr was not mounted with editors and /etc was mounted as read-only. Here's how I fixed it.

mount -w /dev/wd0a /
mount /dev/wd0g /usr
export TERM=vt220

vi /etc/fstab
hit x for the characters to delete
hit i to start inserting text
hit esc to escape from insert mode

type :wq to save and exit
reboot

Intrusion detection with OpenBSD 3.2

Problem
I want an intrusion detection system for free.

Solution
This is assuming you're starting from a fresh install of OpenBSD and that it is configured to connect and communicate on the internet.

Install Ports

    Ports from CVS

    Ports are specially packaged software editions for OpenBSD. They are maintained especially for OpenBSD and available from most OpenBSD regional mirrors.

       #:/> cd /usr
       #:/> setenv CVSROOT anoncvs@anoncvs.usa.openbsd.org:/cvs
       #:/> cvs -d $CVSROOT -q get -rOPENBSD_3_2 -P ports

    If this is your first time to connect to anoncvs.usa.openbsd.org, it will ask if you want to save a key.
    Say yes. Then go get something to drink because it will take a while to download everything.

    Ports from CD

    Alternatively, if you can use ports.tar.gz from the OpenBSD CD (if you have it).

       #:/> mount /dev/cd0a /mnt
       #:/> cd /mnt/3.2
       #:/> cp ports.tar.gz /usr
       #:/> cd /usr
       #:/> tar -xzf ports.tar.gz

    The location of ports.tar.gz on the CD will depend on whether you made the CD yourself or you purchased one from openbsd.org as you should have.

    Ports from FTP

       #:/> cd /usr
       #:/> lynx ftp://ftp.openbsd.org/pub/OpenBSD/3.2/ports.tar.gz
       #:/> tar -xzf ports.tar.gz

    lynx will ask you some questions. The sequence of answers is 'D' for download, '[enter]' to save to disk, '[enter]' again to accept the default filename, 'q' to quit, and 'y' to say you really want to quit.

Compile and Install Snort 1.8.6

By now, ports should be done downloading or un-taring. You'll need to compile and install it, which will involve both downloading and compiling, so figure out what you're going to do for a little while longer.

   #:/> cd /usr/ports/net/snort
   #:/> env FLAVOR="mysql flexresp" make install

The mysql flavor will also download and install mysql if it isn't already installed as well as support
for snort to record alerts to mysql. You do not want to run make clean on the snort port
because it will get rid of the database structure file you will need to import into MySQL later for Snort to record to MySQL for ACID.

Install PHP

If you want to use ACID to view alerts from Snort, you'll need to install php. Ports has PHP too. It will take longer to download, compile, and install than Snort. If you are experienced with using the FLAVORS environment variable, you can alter the PHP install to cut install time.

   #:/> cd /usr/ports/www/php4
   #:/> make
   #:/> cd core
   #:/> make install
   #:/> cd ../extensions
   #:/> make install
   #:/> cd ../pear
   #:/> make install
   #:/> cd ..
   #:/> make clean

You will probably get an error, but don't worry; we will work around it if you did.

   #:/> /usr/local/sbin/phpxs -s
   #:/> cp /usr/local/share/doc/php4/php.ini-recommended /var/www/conf/php.ini

You will probably need some PHP extensions too:

   #:/> cd /usr/ports/packages/i386/www
   #:/> pkg_add php4-mysql*
   #:/> /usr/local/sbin/phpxs -a mysql
   #:/> pkg_add php4-gd*
   #:/> /usr/local/sbin/phpxs -a gd

You can install and activate other extensions while you're in there if you want.

Install a text editor: Nano

If you are familiar with an editor installed by default in OpenBSD, such as vi, you can skip this step. This is merely to install an editor that will be easier to use for someone unfamiliar with vi.

vi is a commonly used editor in OpenBSD. If you want to learn how to use it quickly, there are pleny of hits on google if you search for "vi tutorial". Otherwise, nano is a simple editor found in ports that has a much lower learning curve for editing files since you will need to edit the Apache configuration file to get PHP to work and later Snort configuration files.

   #:/> cd /usr/ports/editors/nano
   #:/> make install clean

Now you can restart if you want so you can use nano without typing the full pathname to the binary. Otherwise the rest of this tutorial will use the full pathname to refer to the nano binary.

Configure PHP

There are a few remaining things to do to to get PHP to work in Apache.

   #:/> cd /usr/ports/editors/nano
   #:/> make install clean
   #:/> /usr/local/bin/nano /var/www/conf/httpd.conf

Use the CTRL+W function to find "index.html". Add index.php and index.php3 to the DirectoryIndex line to make it look like:

#
# DirectoryIndex: Name of the file or files to use as a pre-written HTML
# directory index. Separate multiple entries with spaces.
#
DirectoryIndex index.php index.html index.php3

Then use the CTRL+W function to find "x-httpd-php3". You'll need to uncomment the two lines it finds and alter them. They should look like:

# For example, the PHP3 module (not part of the Apache distribution)
# will typically use:
#
AddType application/x-httpd-php .php .php3 .phtml
AddType application/x-httpd-php-source .phps

If you can't find those lines in your httpd.conf file, that means you have a newer version of Apache for some reason. Just add the lines as you see them above. If there are other file extensions you want to be parsed by the PHP engine, you can add them to the first AddType line too if you want. Some people add .html to obscure the engines running their website. This can be inefficient if you also have a many regular HTML files that do not contain PHP which will require PHP to examine the files anyway.

Save your httpd.conf with CTRL+X and follow the prompts.

Now it might be nice to test your PHP installation. I delete all the default Apache documents in the web root directory. You can skip that if you want.

   #:/> cd /var/www/htdocs
   #:/> rm -fr *
   #:/> /usr/local/bin/nano phpversion.php

You're creating a file named phpversion.php. In it, you want to put:

<?php
echo phpversion();
?>

Save it and test it:

   #:/> apachectl start
   #:/> lynx localhost/phpversion.php

If you see a page that has "4.2.3", all went well. If you see phpversion(); then you messed up somewhere. Go back and make sure you did everything. This won't prevent you from installing Snort, but it will definately keep ACID from working.

Start Apache on boot

   #:/> cd /etc
   #:/> /usr/local/bin/nano rc.conf

Change httpd_flags from NO to YES. Be careful about the comment at the end of the line spilling over to the next line. That is bad. If it does, either get it all on one line again or delete something.

Finishing MySQL Install

For php/mysql applications, php will fail to find the mysql socket in

/var/run/mysql. This is because starting in OpenBSD 3.2, Apache is installed in a chroot, which means it can only see files in /var/www. The workaround is to create /var/www/var/run/mysql (owned by mysql) and start the mysql server using a socket located in /var/www/var/run/mysql/mysql.sock instead of the default location at /var/run/mysql/mysql.sock.

   #:/> mkdir /var/www/var
   #:/> mkdir /var/www/var/run
   #:/> mkdir /var/www/var/run/mysql
   #:/> chown mysql /var/www/var/run/mysql

Check /etc/rc.conf to make sure that the following line is at the bottom:

local_rcconf="/etc/rc.conf.local"

   #:/> /usr/local/bin/nano /etc/rc.conf

The line should be there, but if for some reason it isn't, add it.

/etc/rc.conf.local should not exist. If it does or if it doesn't, do exit nano and do the following:

   #:/> echo "mysql=YES" >> /etc/rc.conf.local

Using echo is just shorthand so you don't have to use an editor to edit a file. If the file doesn't exist, it will be created. If it does exist, mysql=YES will be appended to it. You can use cat to verify the contents of /etc/rc.conf.local. cat is a tool that can be used to output a file right to the screen.

   #:/> cat /etc/rc.conf.local

MySQL isn't done installing. Go back to ports.

   #:/> cd /usr/ports/databases/p5-DBD-Msql-Mysql
   #:/> make install
   #:/> cd /usr/ports/packages/i386/databases
   #:/> pkg_add mysql-server*

Now might be a good time to change the default root password to your MySQL server:

   #:/> /usr/local/bin/mysqladmin -u root -p password 'new-password'
   #:/> /usr/local/bin/mysqladmin -u root -h hostname -p password 'new-password'

That is an exact copy from what pkg_add should tell you. If it's a single user machine and you properly deny outside connections to MySQL, you might be fine leaving the root password blank. Later in this tutorial, we will remove the IP address from your network device(s), so it shouldn't be possible to make a connection from anywhere other than localhost.

Next you need to move the configuration file for MySQL to /etc. In /usr/local/share/mysql look at the files my-small.cnf, my-medium.cnf, my-large.cnf, and my-huge.cnf. my-medium.cnf is good for most server configurations.

   #:/> cd /usr/local/share/mysql
   #:/> cp my-medium.cnf /etc/my.cnf
   #:/> /usr/local/bin/nano /etc/my.cnf

In /etc/my.cnf, change the socket variable to equal what we said earlier. You will have to change it in two places:

socket = /var/www/var/run/mysql/mysql.sock

Save /etc/my.cnf. We're almost done with MySQL.

Edit /etc/rc.conf and change shlib_dirs=   # extra directories for ldconfig at the bottom of the file to read like this:

   #:/> shlib_dirs="/usr/local/lib/mysql"

Or if you have multiple directories:

   #:/> shlib_dirs="/usr/local/lib/{mysql,libmcrypt}"

The following like will add execute permissions to the file that starts mysql.

   #:/> mkdir /var/run/mysql
   #:/> chmod 755 /usr/local/share/mysql/mysql.server

If /var/run/mysql exists already, that's good. If it doesn't exist it'll be created. Either way, it should be there. Add this to the bottom of /etc/rc.local:

if [ X"${mysql}" == X"YES" -a -x /usr/local/bin/safe_mysqld ]; then
echo -n " mysqld"; /usr/local/share/mysql/mysql.server start
/bin/sleep 2
/bin/ln -s /var/www/var/run/mysql/mysql.sock /var/run/mysql/mysql.sock
fi

This will start MySQL when you boot your server. Now might be a good time to reboot if you're curious to see if everything will crash and burn. If you don't want to reboot, you can do this:

   #:/> /usr/local/share/mysql/mysql.server start
   #:/> /usr/local/bin/mysql -u root -p

The second line will try to connect to MySQL. You can either connect or you can't. A connection is good.
The password is blank if you did not set it before. Type exit to get out of mysql. When you
reboot, you should see mysqld in the local daemons list just before logon.

Configuring Snort

There are a lot of rules files in /usr/local/share/examples/snort. We should put them in a different directory.

   #:/> cd /usr/local/share/examples/snort
   #:/> mkdir /etc/snort
   #:/> cp * /etc/snort

Then go to the /etc/snort and edit snort.conf. To log to MySQL for ACID, you will need to find the database section, uncomment the line for MySQL, and change the connection details. I'm not going to step you through this just to make sure you read the whole configuration file.

If you want to add a MySQL user and database for Snort, do this:

   #:/> mysqladmin create snort
   #:/> mysql -u root -p

At the mysql prompt, type

   mysql> grant all on snort.* to snort@localhost identified by 'snort';
   mysql> exit

snort will be the password in the quotes. snort.* says all tables in the snort database. snort@localhost says the snort user can only connect from localhost.

Now add a system user for snort. Edit /etc/group

   #:/> groupadd snort
   #:/> adduser -batch snort snort -shell /bin/nologin -home /home
   #:/> mkdir /var/log/snort
   #:/> chown snort /var/log/snort

We will start Snort a lot like we started MySQL:

   #:/> echo "snort=YES" >> /etc/rc.conf.local
   #:/> /usr/local/bin/nano /etc/rc.local

Add this to the bottom of your rc.local:

if [ X"${snort}" == X"YES" -a -x /usr/local/bin/snort ]; then
echo -n " snort"; /usr/local/bin/snort -D -d -c /etc/snort/snort.conf -u snort -g snort
fi

Then we can import the Snort database information into MySQL:

   #:/> mysql -u snort -p snort < /usr/ports/net/snort/w-snort-1.8.6/snort-1.8.6/contrib/create_mysql

Install ADODB database abstraction

   #:/> mkdir /var/www/htdocs/acid
   #:/> cd /var/www/htdocs/acid
   #:/> lynx http://php.weblogs.com/ADODB
   [ download file here and exit lynx ]
   #:/> tar -xzf adodb*.tgz

Install PHPlot graphing scripts

   #:/> cd /var/www/htdocs/acid
   #:/> lynx http://www.phplot.com
   [ download file here and exit lynx ]
   #:/> tar -xzf phplot-*.tar.gz
   #:/> lynx http://www.aditus.nu/jpgraph/jpdownload.php
   [ download file here and exit lynx ]
   #:/> tar -xzf jpgraph-*.tar.gz

Install ACID

   #:/> mkdir /var/www/htdocs/acid
   #:/> cd /var/www/htdocs/acid
   #:/> lynx http://www.cert.org/kb/acid/
   [ download file here and exit lynx ]
   #:/> tar -xzf acid*.tgz
   #:/> cd acid

Configuring the packet filter

This section is completely optional. It is here for people who are running Snort on a machine that has an IP assigned to the network device. For improved security, you should not have an IP assigned to your intrusion detection system in case a remote vulnerability is found for OpenBSD.

It would not be good to have MySQL available to the world. You should use Packet Filter (PF) in OpenBSD to firewall port 3306 and drop all outside connections to MySQL.

Additional Notes

  • Starting in OpenBSD 3.2, Apache is in a strict chroot, which means it can't see the rest of the OpenBSD filesystem, just what's in the /var/www directory. When you're installing OpenBSD, you might consider giving more filesystem space to /var than you would normally have given in the past.
  • Move mysql database to /snort/mysql and chown, chgrp it to mysql and modify datadir in /usr/local/share/mysql/mysql.server to point to /snort/mysql. Then you have to copy /var/mysql to /snort/mysql

Mounting a floppy disk

I thought mounting a floppy drive in obsd would be the same as in linux, but it's not. Depending on the distro, in linux you could do:

    # mount /dev/fd0 /floppy

but not so in obsd.

I had a floppy I wanted to go from my win2k machine to my standalone obsd box, so it was msdos formatted. I went to /mnt and created a floppy dir

    # cd /mnt
    # mkdir floppy

Then you have to mount the floppy:

    # mount -t msdos /dev/fd0c /mnt/floppy

The -t msdos tells mount to use msdos instead of the default ffs filesystem. Then you put whatever you want in /mnt/floppy and it goes on the floppy. Works the same of course with deleting files.

I did more looking after that and found out how to format a floppy and mount it for the ffs filesystem.

First, as root, do a format. This will also verify that the floppy is OK. When you put in a bad disk like I did, it'll spit some garbage on the screen, but don't worry cause it'll keep going.

    # fdformat fd0

Next we need to partition the floppy. Use disklabel:

    # disklabel -E fd0

    Initial label editor (enter '?' for help at any prompt)
    > p

    device: /dev/rfd0c
    type: floppy
    disk: floppy disk
    label: fictitious
    bytes/sector: 512
    sectors/track: 18
    tracks/cylinder: 2
    sectors/cylinder: 36
    cylinders: 80

    total sectors: 2880
    free sectors: 2880
    rpm: 300

    16 partitions:
    #        size   offset    fstype   [fsize bsize   cpg]
      c:     2880        0    unused        0     0         # (Cyl.    0 - 79)
    > a a
    offset: [0]

    size: [2880]
    FS type: [4.2BSD]
    > w
    > q
    No label changes.
    #

Constructing the actual file system is next (if you skipped the disklabel part, use fd0c instead of fd0a). We'll use the command newfs for this:

    # newfs fd0a

...and mount your floppy:

    # mount -t ffs /dev/fd0a /mnt

As you can see, that's slightly different from the way we mounted the msdos disk. You can even leave off the -t ffs since that is the filesystem that mount will default to.

Nice

I was looking up stuff about cron and found nice. It is a way to run a program at a lower (or higher) priority than the rest of the things running on your box. I had noticed one of my old Mandrake installations ran a cron every night at 4 am and my desktop really took a performance hit, so this is something I needed. If you use the following command to build a program, it would run at a lower priority than other things on your machine:

nice +19 make

From man nice:

nice is built into csh(1)

with a slightly different syntax than described here. The form `nice +10' nices to positive nice, and
`nice -10' can be used by the superuser to give a process more of the processor.

So if I wanted to change my crons on my obsd box to run at low priority, I edit /var/cron/tabs/root:

# do daily/weekly/monthly maintainance
30 1 * * * root nice +19 /bin/csh /etc/daily 2>&1 | tee /var/log/daily.out | mail -s "`/bin/hostname` daily output" root
30 3 * * 6 root nice +19 /bin/csh /etc/weekly 2>&1 | tee /var/log/weekly.out | mail -s "`/bin/hostname` weekly output" root
30 5 1 * * root nice +19 /bin/csh /etc/monthly 2>&1 | tee /var/log/monthly.out | mail -s "`/bin/hostname` monthly output" root

I probably wouldn't really go as low as 19 because I run the distributed.net RC5 cracking client which is also low priority, so I would have to find a priority just above what it runs at for crons.

OpenBSD 3.4 email server

OpenBSD 3.4, Postfix, Procmail, Courier-Imap, Mutt, Pop/Imap before SMTP authentication

Introduction

    This document is written for configuring a OpenBSD 3.4-based mailserver, however it there is no reason it should not apply to versions as old as OpenBSD 3.0 or something newer.

    Install src

      untar src.tar.gz into /usr/src from the if you have an OpenBSD CD. If you're grabbing them from the ftp site then you want both src.tar.gz and srcsys.tar.gz.

    Upgrade to -stable

      Even OpenBSD can have security updates so be sure to update to the -stable branch of the release you're working with. To update OpenBSD 3.1 change the _3_4 to _3_1.

        # export CVSROOT=anoncvs@anoncvs1.usa.openbsd.org:/cvs
        # cd /usr
        # cvs -q up -rOPENBSD_3_4 -P src
      

      To update this tree later simply cd /usr/src; cvs -q up -rOPENBSD_3_4 -Pd

    Rebuild system from stable source

      Rebuild Kernel
        # cd /usr/src/sys/arch/i386/conf
        # /usr/sbin/config GENERIC
        # cd /usr/src/sys/arch/i386/compile/GENERIC
        # make clean && make depend && make
        # cd /usr/src/sys/arch/i386/compile/GENERIC
        # cp /bsd /bsd.old          (Save an old copy of your kernel)
        # cp bsd /bsd               (Copy the new kernel into place)
        # reboot
      
      
      Rebuild userland programs
        # cd /usr/src
        # rm -r /usr/obj/*
        # make obj && make build
      

    Reboot the machine, at this point it's safe to connect it to the internet

    Install ports tree, upgrade to stable

      # export CVSROOT=anoncvs@anoncvs1.usa.openbsd.org:/cvs
      # cd /usr
      # tar -xvzf /path/to/ports.tar.gz
      # cvs -q up -rOPENBSD_3_1 ports
    
    

Postfix Install

      # cd /usr/ports/mail/postfix
    

    Optionally, edit Makefile and uncomment out all the SUBDIR+= except for: SUBDIR+= stable,pcre,tls

      # make install
    

    edit /etc/rc.conf

      Comment out line:

        #sendmail_flags="-L sm-mta -C/etc/mail/localhost.cf -bd -q30m"
      

      and add:

        sendmail_flags="-bd -q30m"
      

    edit root crontab (# crontab -e )

      Comment out line:

        #*/30  *   *   *   *   /usr/sbin/sendmail -L sm-msp-queue -Ac -q
      

    edit /etc/postfix/main.cf

      Set the following fields:

        mydomain = your domain here
      
        myorigin = $mydomain
        mydestination = $myhostname, localhost.$mydomain, $mydomain
        home_mailbox = .maildir/    # NOTE: the trailing /  is important
        # mailbox_command = /usr/local/bin/procmail
      

      Leave mailbox_command commented out for now. After procmail is configured it will be uncommented.

    Run postfix

      # postfix check
      # postfix start
    

    At this point send a test message to a local user, his mail directory should be created $HOME/usrname/.maildir along with sub directories /new /cur /tmp with the new mail being in /new

Mutt Install

    This makes it easier for us to test the mailsystem while setting up the server

        # cd /usr/ports/mail/mutt
    

    edit Makefile

      comment out:

        #     SUBDIR += snapshot
        # make install
        cd /etc/Mutt
      
      

    edit Muttrc

      Set the following settings:

        set mbox_type=Maildir
        set folder=~/.maildir
        set spoolfile=~/.maildir/
      

      This allows Mutt to read Maildir format mailboxes

Procmail Install

    A small change need to be made to the authentice.c source file to make procmail work with the Maildir type mailboxes by default.

        # cd /usr/ports/mail/procmail
        # make fetch extract
        # cd /usr/ports/mail/procmail/w-procmail-3.22/procmail-3.22/src
    

    edit authenticate.c

      change line:

        #define MAILSPOOLDIR   "/var/spool/mail/"
      

      to:

        #define MAILSPOOLDIR   ""
      

      change line:

        #define MAILSPOOLHOME "/.mail"
      

      to:

        #define MAILSPOOLHOME "/.maildir"
      

    Compile install procmail:

      # make install
    

    edit /etc/procmailrc

    add line at top of file:

      DEFAULT=$HOME/.maildir/
    

    edit /etc/postfix/main.cf

      Uncomment the line:

        mailbox_command = /usr/local/bin/procmail  
      

    reload postfix

      # postfix reload
    

    Again you want to send another test message at this point to make sure that procmail is now delivering the mail correctly to the users .maildir mailbox

Courier-Imap Install

      # cd /usr/ports/mail/courier-imap
      # make install
      # cd /etc; mkdir courier-imap
      # cd courier-imap; cp /usr/local/share/examples/courier-imap/* .
    

    Edit imapd.cnf

    Configure the file for your server

      # mkimapdcert
    
    

    This reads imapd.cnf and creates an imap ssl certificate in /etc/ssl/private/imapd.pem

    Edit authdaemond.conf

    Set:

      AUTHDAEMOND="authdaemond.plain"
    

    Edit imapd

    Set at the end of the file:

      MAILDIR=.maildir
      IMAPDSTART=YES
    

    Startup Courier-IMAP:

      # /usr/local/libexec/authlib/authdaemond start
      # /usr/local/libexec/imapd.rc start
      # /usr/local/libexec/imapd-ssl.rc start
    

    You might want to put the above into a shell script you can call from /etc/rc.local for startup

    At this point you should be able to test out imap access with your favorite mail client.

Pop-before-smtp

    If this machine is going to allow remote users to connect and use the mail system, we dont want to have an open relay, so we'll setup pop/imap before smtp authentication to only allow those valid users who have an account and check their email to be able to send it.

    Grab pop-before-stmp from its website: http://popbsmtp.sourceforge.net/ and untar into a temp directory like /usr/local/src/pop-before-smtp

    edit pop-before-smtp-conf.pl

      uncomment the line under: # Override the DB hash file we will create/update (".db" gets appended).
        $dbfile = '/etc/postfix/pop-before-smtp';
    
      uncomment:
        $logto = '/var/log/pop-before-smtp';
    	  
      change the line under: # Set the log file we will watch for pop3d/imapd records. to read:
        $file_tail{'name'} = '/var/log/maillog';
    	  
      uncomment the line under:  # For Courier-POP3 and Courier-IMAP:
        $pat = '^(... .. ..:..:..) \S+ (?:courier)?(?:pop3|imap)(?:login|d|d-ssl): ' .
        'LOGIN, user=\S+, ip=\[[:f]*(\d+\.\d+\.\d+\.\d+)\]$';
    	     
      comment out the lines to tell it to use NDBM database:
        #=pod #------------------------ Postfix NDBM_File ---------------------START-
        #=cut #------------------------ Postfix NDBM_File -----------------------END-
    
      # cp pop-before-smtp-conf.pl /etc
      # cp pop-before-smtp.init /etc
      # cp pop-before-smtp /usr/sbin
    

    Start pop-before-smtp

    
      /etc/pop-before-smtp.init start
    

    You should see a list of ip addresses etc in /var/log/pop-before-smtp from your imap tests. You should also have a database file in /etc/postfix/pop-before-smtp.db

    Setup Postfix for pop-before-smtp authentication

      edit /etc/postfix/main.cf

      Add the following line:

        smtpd_recipient_restrictions = permit_mynetworks,reject_non_fqdn_recipient,check_client_access 
        hash:/etc/postfix/pop-before-smtp,check_relay_domains
      

      Reload postfix settings:

        # postfix reload
      

    You should be able to verify that postfix will now refuse to accept mail from remote (non local network) connections without logging in via imap or pop3 first.

Spamassassin

    Another great tool for configuring email is spamassassin, which is a perl script that can be used to identify and control incoming spam.
    Spamassassin website can be found at: http://spamassassin.sourceforge.net/

    Spamassassin requires HTML-Parser perl module as a prereq so we'll start there.

      # cd /usr/ports/www/p5-HTML-Parser
      # make install
    

    Now onto the spamassasin install

      # mkdir /usr/local/src
      # cd /usr/local/src
      # tar -xvzf /path/to/downloaded/Mail-SpamAssassin-2.41.tar.gz
      # perl Makefile.PL
      # make
      # make install
    

    Lets test the install:

      # spamassassin -t < sample-nonspam.txt > nonspam.out
      # spamassassin -t < sample-spam.txt > spam.out
    
    

    This runs spamassasin in test, by reading the spam.out file and nospam.out file you can see what it does to each mail message.

    At this point spamassassin is ready to be setup in procmail, you can either set it up system wide or in my case on a user by user basis.

    Setup spamassassin for your mail account:

      # cd ~
    

    create directory to store spam in

      
        # maildirmake -f Spam .maildir
      

      This creates a maildir folder inside your ~/.maildir called .Spam

    edit .procmailrc

      Add the following lines:

        :0fw
        | spamassassin -P
      
        :0:
        * ^X-Spam-Status: Yes
        $HOME/.maildir/.Spam/
      

    Now simply kick back and watch most if not all of your incoming spam get tagged and redirected into your new imap folder Spam.

Root partition on OpenBSD raidframe device

This document should show the long process for setting up a kernel-based software RAID system on OpenBSD 3.2 with the root partition / on a raid0a device, swap and /tmp on raid1b and raid1d, and /var and /usr on raid2e and raid2f. This project utilizes raidctl.

From the man raidctl(8):

raidctl is the user-land control program for raid(4), the RAIDframe disk device. raidctl is primarily used to dynamically configure and unconfigure RAIDframe disk devices. For more information about the RAIDframe disk device, see raid(4).

This document assumes the reader has at least rudimentary knowledge of RAID and RAID concepts.

The sample system has sd0(18gb), sd1(18gb), and sd2. I made a complete install of OpenBSD 3.2 on sd2. References:

raidctl(8)
installboot(8)
http://marc.theaimsgroup.com/?l=openbsd-misc&m=103635776223483&w=2
http://marc.theaimsgroup.com/?l=openbsd-misc&m=102839903925282&w=2
http://archives.neohapsis.com/archives/openbsd/2001-10/0142.html

http://www.blackant.net/other/docs/howto-full-system-mfs.php

-- modify the kernel:

# add
option		RAID_AUTOCONFIG
option		NMBCLUSTERS=8192
option		BUFCACHEPERCENT=15 # default is 5
option		DUMMY_NOPS	# speed hack; recommended
pseudo-device	raid		4	# RAIDframe disk driver

-- make partitions RAID

%disklabel -E sd0
# /dev/rsd0c:
type: SCSI
disk: SCSI disk
label: DK32DJ-18MC    
flags:
bytes/sector: 512
sectors/track: 447
tracks/cylinder: 3
sectors/cylinder: 1341
cylinders: 26866
total sectors: 36102720
rpm: 3600
interleave: 1
trackskew: 0
cylinderskew: 0
headswitch: 0		# microseconds
track-to-track seek: 0	# microseconds
drivedata: 0 

16 partitions:
#        size   offset    fstype   [fsize bsize   cpg]
  a:   307026       63    4.2BSD     1024  8192    16 	# (Cyl.    0*-
228)
  c: 36102720        0    unused        0     0       	# (Cyl.    0 -
26922*)
  d:   409005   307089      RAID                      	# (Cyl.  229 -
533)
  e:  5767641   716094      RAID                      	# (Cyl.  534 -
4834)
  f: 29614320  6483735      RAID                      	# (Cyl. 4835 -
26918*)

% disklabel -E sd1
# /dev/rsd1c:
type: SCSI
disk: SCSI disk
label: DK32DJ-18MC    
flags:
bytes/sector: 512
sectors/track: 447
tracks/cylinder: 3
sectors/cylinder: 1341
cylinders: 26866
total sectors: 36102720
rpm: 3600
interleave: 1
trackskew: 0
cylinderskew: 0
headswitch: 0		# microseconds
track-to-track seek: 0	# microseconds
drivedata: 0 

16 partitions:
#        size   offset    fstype   [fsize bsize   cpg]
  a:   307026       63    4.2BSD     1024  8192    16 	# (Cyl.    0*-
228)
  c: 36102720        0    unused        0     0       	# (Cyl.    0 -
26922*)
  d:   409005   307089      RAID                      	# (Cyl.  229 -
533)
  e:  5767641   716094      RAID                      	# (Cyl.  534 -
4834)
  f: 29614320  6483735      RAID                      	# (Cyl. 4835 -
26918*)

-- create /etc/raid0.conf:
START array
1 2 0
START disks
/dev/sd0d
/dev/sd1d
START layout
128 1 1 1
START queue
fifo 100

-- create /etc/raid1.conf:
START array
1 2 0
START disks
/dev/sd0e
/dev/sd1e
START layout
64 1 1 0
START queue
fifo 100

-- create /etc/raid2.conf:
START array
1 2 0
START disks
/dev/sd0f
/dev/sd1f
START layout
128 1 1 1
START queue
fifo 100

-- configure raid arrays
raidctl -C /etc/raid0.conf raid0
raid -I 135790 raid0
raid -i raid0
disklabel -E raid0
# /dev/rraid0c:
type: RAID
disk: raid
label: fictitious
flags:
bytes/sector: 512
sectors/track: 128
tracks/cylinder: 8
sectors/cylinder: 1024
cylinders: 399
total sectors: 408832
rpm: 3600
interleave: 1
trackskew: 0
cylinderskew: 0
headswitch: 0		# microseconds
track-to-track seek: 0	# microseconds
drivedata: 0 

16 partitions:
#        size   offset    fstype   [fsize bsize   cpg]
  a:   408832        0    4.2BSD     8192 65536    32 	# (Cyl.    0 -
399*)
  c:   408832        0    unused        0     0       	# (Cyl.    0 -
399*)


newfs /dev/rraid0a
mkdir /mnt/kernel0
mkdir /mnt/kernel1
mount /dev/raid0a /mnt
mkdir /mnt/etc
mkdir /mnt/dev
mkdir /mnt/bin
mkdir /mnt/sbin
cd /etc
tar cXf - . | tar -xpf - -C /mnt/etc
cd /bin
tar cXf - . | tar -xpf - -C /mnt/bin
cd /sbin
tar cXf - . | tar -xpf - -C /mnt/sbin
cd /dev
tar cXf - . | tar -xpf - -C /mnt/dev
mkdir /mnt/tmp
mkdir /mnt/usr
mkdir /mnt/var
cp -r .cshrc .profile bsd bsd.old boot stand altroot root /mnt

newfs /dev/rsd0a
newfs /dev/rsd1a
mount /dev/sd0a /mnt/kernel0
mount /dev/sd1a /mnt/kernel1
cp /bsd /bsd.old /boot /mnt/kernel0
cp /bsd /bsd.old /boot /mnt/kernel1

raidctl -C /etc/raid1.conf raid1
raid -I 246810 raid1
raid -i raid1
disklabel -E raid1
# /dev/rraid1c:
type: RAID
disk: raid
label: fictitious
flags:
bytes/sector: 512
sectors/track: 128
tracks/cylinder: 8
sectors/cylinder: 1024
cylinders: 11264
total sectors: 11535104
rpm: 3600
interleave: 1
trackskew: 0
cylinderskew: 0
headswitch: 0		# microseconds
track-to-track seek: 0	# microseconds
drivedata: 0 

16 partitions:
#        size   offset    fstype   [fsize bsize   cpg]
  b:  8388608        0      swap                      	# (Cyl.    0 -
8191)
  c: 11535104        0    unused        0     0       	# (Cyl.    0 -
11264*)
  d:  3146496  8388608    4.2BSD     8192 65536    32 	# (Cyl. 8192 -
11264*)


newfs /dev/rraid1d

raidctl -C /etc/raid2.conf raid2
raid -I 123456 raid2
raid -i raid2
disklabel -E raid2
# /dev/rraid2c:
type: RAID
disk: raid
label: fictitious
flags:
bytes/sector: 512
sectors/track: 128
tracks/cylinder: 8
sectors/cylinder: 1024
cylinders: 28920
total sectors: 29614208
rpm: 3600
interleave: 1
trackskew: 0
cylinderskew: 0
headswitch: 0		# microseconds
track-to-track seek: 0	# microseconds
drivedata: 0 

16 partitions:
#        size   offset    fstype   [fsize bsize   cpg]
  c: 29614208        0    unused        0     0       	# (Cyl.    0 -
28920*)
  e: 25165824        0    4.2BSD     8192 65536    32 	# (Cyl.    0 -
24575)
  f:  4448384 25165824    4.2BSD     8192 65536    32 	# (Cyl. 24576 -
28920*)


newfs /dev/rraid2e
newfs /dev/rraid2f
mkdir /mnt2
mount /dev/raid2e /mnt2
mkdir /mnt2
cd /var
tar -cXf - . | tar -xpf - -C /mnt2
mkdir /mnt3
mount /dev/raid2f /mnt3
mkdir /mnt3
cd /usr
tar -cXf - . | tar -xpf - -C /mnt3

cd /usr/mdec
./installboot -v /mnt/kernel0/boot ./biosboot sd0
./installboot -v /mnt/kernel1/boot ./biosboot sd1

raidctl -A root raid0
raidctl -A yes raid1
raidctl -A yes raid2

-- modify /mnt/etc/fstab
/dev/raid0a / ffs rw 1 1
/dev/raid1b none swap sw 0 0
/dev/sd2h /home ffs rw,nodev,nosuid,softdep 1 2
/dev/raid1d /tmp ffs rw,nodev,nosuid,softdep 1 2
/dev/raid2f /usr ffs rw,nodev,softdep 1 2
/dev/raid2e /var ffs rw,nodev,nosuid,softdep 1 2

After you reboot, be sure to delete the raid config files from /etc because you'll get "Device already configured!" errors otherwise. The errors don't hurt anything, but they definately aren't needed. The raidctl -A yes raid1 lines eliminate the necessity of having the raid configuration files in /etc.

Unpacking src.tar.gz to /usr

Problem
I copied src.tar.gz to /usr, and