Network Configuration

Network configuration in OpenBSD is done with text files in /etc. Typically, these settings are initially configured during the installation process.

Identifying and Setting Up Your Network Interfaces

Interfaces are named by the type of card, not the type of connection. For example, here’s a dmesg(8) snippet for an Intel Fast Ethernet network card:

fxp0 at pci0 dev 10 function 0 "Intel 82557" rev 0x0c: irq 5, address 00:02:b3:2b:10:f7
inphy0 at fxp0 phy 1: i82555 10/100 media interface, rev. 4

This device uses the fxp(4) driver and is assigned the number 0 here.

You can find out what network interfaces have been identified by using the ifconfig(8) utility. The following command will show all network interfaces on a system.

$ ifconfig
lo0: flags=8049<UP,LOOPBACK,RUNNING,MULTICAST> mtu 33200
        index 3 priority 0 llprio 3
        groups: lo
        inet netmask 0xff000000
        lladdr 00:02:b3:2b:10:f7
        index 1 priority 0 llprio 3
        media: Ethernet autoselect (100baseTX full-duplex)
        status: active
        inet netmask 0xffffff00 broadcast
enc0: flags=0<>
        index 2 priority 0 llprio 3
        groups: enc
        status: active
pflog0: flags=141<UP,RUNNING,PROMISC> mtu 33200
        index 4 priority 0 llprio 3
        groups: pflog

This sample shows only one physical Ethernet interface: fxp0. An IP is configured on it, hence the values inet netmask 0xffffff00 broadcast The UP and RUNNING flags are also set on it.

The netstart(8) script configures network interfaces at boot time using hostname.if(5) files, where “if” is replaced by the full name of each interface. The example above would use the file /etc/hostname.fxp0, containing the following options:


This hostname.fxp0 file also has an interactive equivalent:

# ifconfig fxp0

Finally, you will notice several other interfaces come enabled by default. These are virtual interfaces that serve various functions. The following manual pages describe them: * enc - Encapsulating interface * lo - Loopback interface * pflog - Packet Filter logging interface

Other virtual interfaces can be added with ifconfig(8)’s create subcommand.

Default Hostname and Gateway

The /etc/myname and /etc/mygate files are read by the netstart(8) script. Both of these files consist of a single line, specifying the fully qualified domain name of the system and the address of the gateway host, respectively. The /etc/mygate file need not exist on all systems. See myname(5) for more details.

DNS Resolution

DNS resolution is controlled by resolv.conf(5).

$ cat /etc/resolv.conf
lookup file bind

Here, the default domain name will be, there will be two DNS resolvers, and, and the hosts(5) file will be consulted before the DNS resolvers are.

Activating the Changes

From here, you can either reboot or run the netstart(8) script:

# sh /etc/netstart

Note that a few warnings may be produced when running this script if you are reconfiguring interfaces that have already been configured. Use ifconfig(8) to make sure that your interfaces were set up correctly.

Even though you can completely reconfigure networking on a running OpenBSD system, a reboot is recommended after any significant reconfiguration.

Checking Routes

You can check your routes via netstat(1) or route(8).

$ netstat -rn
Routing tables

Destination        Gateway            Flags     Refs     Use    Mtu  Prio Interface
default             UGS         4       16      -    12 fxp0
224/4              URS         0        0  32768     8 lo0
127/8              UGRS        0        0  32768     8 lo0          UH          2       15  32768     1 lo0
10.0.0/24          link#1             UC          1        4      -     4 fxp0           aa:0:4:0:81:d      UHL         1       11      -     1 fxp0          UGHS        0        0      -     1 lo0

$ route show
Routing tables

Destination        Gateway            Flags     Refs     Use    Mtu  Prio Iface
default             UGS         4       16      -    12 fxp0
base-address.mcast localhost          URS         0        0  32768     8 lo0
loopback           localhost          UGRS        0        0  32768     8 lo0
localhost          localhost          UH          2       15  32768     1 lo0
10.0.0/24          link#1             UC          1        4      -     4 fxp0           aa:0:4:0:81:d      UHL         1       11      -     1 fxp0          localhost          UGHS        0        0      -     1 lo0

Setting Up Aliases on an Interface

To set up an IP alias on an interface, simply edit its hostname.if(5) file.

Suppose you have a dc0 interface. You are on the network, the IP address for dc0 is and the netmask is

Assuming you are using multiple IP addresses which are in the same subnet with aliases, your netmask setting for each alias becomes They do not need to follow the netmask of the first IP bound to the interface. In this example, two aliases are added to the interface dc0, which was configured as with a netmask of

$ cat /etc/hostname.dc0
inet alias
inet alias

Once you’ve created this file, run netstart or reboot. To view all aliases, use ifconfig -A.

Dynamic Host Configuration Protocol

The Dynamic Host Configuration Protocol (DHCP) is a way to configure network interfaces automatically. OpenBSD can be a DHCP server that configures other machines, or a DHCP client that is configured by a DHCP server.

DHCP Client

To use dhclient(8), edit the hostname.if(5) file of your interface. The wireless networking section explains how to set up wireless interfaces. For ethernet interfaces, one line is enough:


OpenBSD will gather its IP address, default gateway and DNS servers from the DHCP server at startup time.

If you want to get an IP via DHCP from the command line, simply run:

# dhclient xl0

Replace xl0 with your interface name.

The resolv.conf file will be overwritten by dhclient(8) if the DHCP server provides the domain-name, domain-search or domain-name-servers options. Any of these can be ignored, overridden or modified with appropriate statements in dhclient.conf(5). For example, if you wanted to use the DNS server at rather than the one(s) the DHCP server provided, add the following:

supersede domain-name-servers;

Additionally, the file /etc/resolv.conf.tail can be used to append information if dhclient(8) does write resolv.conf.

DHCP Server

If you want to use OpenBSD as a DHCP server, enable the dhcpd(8) daemon at startup.

# rcctl enable dhcpd

On the next boot, dhcpd will run and attach to all NICs that have valid configurations in dhcpd.conf(5). You may specify individual interfaces instead by naming them explicitly.

# rcctl set dhcpd flags em1 em2

An example /etc/dhcpd.conf file might look like this:

# Home
subnet netmask {
	option domain-name-servers;
	option routers;

# Guests
subnet netmask {
	option domain-name-servers,;
	option routers;

There are two subnets in this example: a home network and a guest network. Clients will automatically be given an IP address and pointed to the gateway and DNS servers you specify. See dhcp-options(5) for more options.

PXE Booting (i386, amd64)

The Preboot Execution Environment (PXE) is a standard method of booting systems using only the network. A client’s PXE-capable NIC broadcasts a DHCP request at the start of the boot process and, rather than only receiving basic IP/DNS information, is also given a file to boot from. On OpenBSD, this file is known as pxeboot(8), and is typically served by tftpd(8).

Wireless Networking

OpenBSD has support for a number of wireless chipsets. Further supported devices can be found in usb(4) and pci(4). The precise extent of their support is described in the driver man pages. The following cards support Host-based Access Point (HostAP) mode, permitting them to be used as a wireless access point:

  • acx(4) TI ACX100/ACX111
  • ath(4) Atheros 802.11a/b/g
  • athn(4) Atheros 802.11/a/g/n devices
  • pgt(4) Conexant/Intersil Prism GT Full-MAC 802.11a/b/g
  • ral(4) and ural(4) Ralink Technology RT25x0 802.11a/b/g
  • rtw(4) Realtek 8180 802.11b
  • rum(4) Ralink Technology RT2501USB
  • wi(4) Prism2/2.53

The ifconfig(8) media subcommand shows media capabilities of network interfaces. For wireless devices, it displays supported 802.11a/b/g/n media modes and the supported operating modes (hostap, ibss, monitor). For example, to see media capabilities of interface ath0, type:

$ ifconfig ath0 media

In order to use some wireless cards, you will need to acquire firmware files with fw_update(1). Some manufacturers refuse to allow free distribution of their firmware, so it can’t be included with OpenBSD.

Another option to consider: use a conventional NIC and an external bridging wireless access point for your OpenBSD-based firewall. This has the added advantage of letting you easily position the antenna where it is most effective, which is often not directly on the back of your firewall.

Configuring Your Wireless Adapter

Adapters based on supported chips can be used like any other network interface. To connect an OpenBSD system to an existing wireless network, use the ifconfig(8) utility. An example of a hostname.if(5) file for a wireless client might be:

nwid puffyuberalles
wpakey passwordhere

Note that the dhcp keyword should be after the other configuration lines, as the network adapter will not be able to send a DHCP request until it is configured.

Trunking Your Wireless Adapter

Trunks are virtual interfaces consisting of one or more network interfaces. In this section, our example will be a laptop with a wired bge0 interface and a wireless iwn0 interface. We will build a trunk(4) interface using both of them.

To do this, we first activate the two physical ports, then assign them to trunk0.

# echo up > /etc/hostname.bge0

The wireless interface, however, needs a bit more configuration. It will need to attach to our wireless WPA-protected network:

$ cat /etc/hostname.iwn0
nwid puffynet
wpakey mysecretkey

Now, our trunk interface is defined like this:

$ cat /etc/hostname.trunk0
trunkproto failover trunkport bge0
trunkport iwn0

The trunk is set up in failover mode, so either interface can be used. If both are available, it will prefer the bge0 port, since that is the first one added to the trunk device.

Setting Up a Network Bridge

A bridge(4) is a link between two or more separate networks. Unlike a router, packets go through the bridge transparently: the two network segments appear as one to nodes on either side. Bridges will only forward packets that have to pass from one segment to the other and, as a result, an interface in a bridge may or may not have an IP address of its own. If it does, the interface has effectively two modes of operation: one as part of a bridge, the other as a stand-alone NIC. If neither interface has an IP address, the bridge will pass network data, but will not be externally maintainable (which can be a feature).

A Bridge Acting as a DHCP Server

Let’s say we have a system which has four vr(4) interfaces, vr0 through vr3. We want to bridge vr1, vr2 and vr3 together, leaving out vr0 for the uplink. We also want to serve IP addresses through DHCP over the bridged interfaces. Being a DHCP server and an uplink router, the box needs to have an IP address on the bridged network.

It is not possible to assign an IP address directly to a bridge interface. The IP address should be added to one of the member interfaces, but we cannot use a physical interface as the link might be down, in which case the address would not be reachable. Fortunately, there is the vether(4) (virtual Ethernet) driver that can be used for this purpose. We will add it to the bridge, assign the IP address to it and make dhcpd(8) listen there.

  • The DHCP server configuration is not described yet again in this section, but the addressing scheme used here is the same.
  • This will also be the uplink router for your bridged network, so we will use IP address to match the DHCP server configuration.
  • We will not cover the uplink, routing or firewalling configuration here.

First, mark the vr1, vr2 and vr3 interfaces as up:

# echo up > /etc/hostname.vr1
# echo up > /etc/hostname.vr2
# echo up > /etc/hostname.vr3

Then create the vether0 configuration:

# echo 'inet' > /etc/hostname.vether0

Configure the bridge interface to contain all the above interfaces:

$ cat /etc/hostname.bridge0
add vether0
add vr1
add vr2
add vr3

And finally we make the DHCP daemon listen on the vether0 interface:

# rcctl set dhcpd flags vether0

All that’s left now is to reboot!

Filtering on a Bridge

While there are certainly uses for a simple bridge like this, it is likely you might want to DO something with the packets as they go through your bridge. As you might expect, Packet Filter can be used to restrict what traffic goes through your bridge. Keep in mind, by the nature of a bridge, the same data flows through both interfaces, so you only need to filter on one interface.

Tips on Bridging

  • By using the blocknonip option of ifconfig(8) or in hostname.bridge0, you can prevent non-IP traffic (such as IPX or NETBEUI) from slipping around your filters. This may be important in some situations, but you should be aware that bridges work for all kinds of traffic, not just IP.
  • Bridging requires that the NICs be in a promiscuous mode. They listen to all network traffic, not just that directed at the interface. This will put a higher load on the processor and bus than one might expect.

Equal-cost Multipath Routing

Equal-cost multipath routing refers to having multiple routes in the routing table for the same network, such as the default route, When the kernel is doing a route lookup to determine where to send packets destined to that network, it can choose from any of the equal-cost routes. In most scenarios, multipath routing is used to provide redundant uplink connections, e.g., redundant connections to the internet.

The route(8) command is used to add/change/delete routes in the routing table. The -mpath argument is used when adding multipath routes.

# route add -mpath default
# route add -mpath default

Verify the routes:

# netstat -rnf inet | grep default
default      UGS       2      134      -     fxp1
default        UGS       0      172      -     fxp2

In this example we can see that one default route points to, which is accessible via the fxp1 interface, and the other points to, which is accessible via fxp2.

Since the mygate(5) file does not yet support multipath default routes, the above commands should be added to the bottom of the hostname.if(5) files for the fxp1 and fxp2 interfaces. The /etc/mygate file should then be deleted.

$ tail -1 /etc/hostname.fxp1
!route add -mpath default
$ tail -1 /etc/hostname.fxp2
!route add -mpath default

Lastly, don’t forget to activate the use of multipath routes by enabling the proper sysctl(8) variable.

# sysctl net.inet.ip.multipath=1
# sysctl net.inet6.ip6.multipath=1

Be sure to edit sysctl.conf(5) to make the changes permanent.

Now try a traceroute to different destinations. The kernel will load balance the traffic over each multipath route.

# traceroute -n
traceroute to (, 64 hops max, 60 byte packets
 1  19.337 ms  18.194 ms  18.849 ms
 2  17.642 ms  18.176 ms  17.731 ms
 3  110.486 ms  19.478 ms  100.949 ms
 4  32.772 ms  33.534 ms  32.835 ms

# traceroute -n
traceroute to (, 64 hops max, 60 byte packets
 1  14.175 ms  14.503 ms  14.58 ms
 2  13.664 ms  13.962 ms  13.445 ms
 3  13.964 ms  13.347 ms  13.788 ms
 4  30.177 ms  30.95 ms  30.593 ms

For more information about how the route is chosen, please refer to RFC2992, “Analysis of an Equal-Cost Multi-Path Algorithm”.

It’s worth noting that if an interface used by a multipath route goes down (i.e., loses carrier), the kernel will still try to forward packets using the route that points to that interface. This traffic will of course be blackholed and end up going nowhere. It’s highly recommended to use ifstated(8) to check for unavailable interfaces and adjust the routing table accordingly.

Networking vmm Guests

Network access to vmm(4) guests can be configured a number of different ways, four of which are detailed in this section.

In the examples below, various IPv4 address ranges will be mentioned for different use cases:

  • Private Addresses (RFC1918) are those reserved for private networks such as,, and are not globally routable.
  • Shared Addresses (RFC6598) are similar to private addresses in that they are not globally routable, but are intended to be used on equipment that can perform address translation. The address space is

Option 1 - VMs only need to talk to the host and each other

For this setup, vmm uses local interfaces: interfaces that use the shared address space defined above. Using vmctl(8)’s -L flag creates a local interface in the guest which will receive an address from vmm via DHCP. This essentially creates two interfaces: one for the host and the other for the VM.

Option 2 - NAT for the VMs

This setup builds upon the previous and allows VMs to connect outside the host. IP forwarding is required for it to work. The following line in /etc/pf.conf will enable Network Address Translation:

match out on egress from to any nat-to (egress) Reload the pf ruleset and the VM(s) can now connect to the internet.

Option 3 - Additional control over the VM network configuration

Sometimes you may want additional control over the virtual network for your VMs, such as being able to put certain ones on their own virtual switch. This can be done using a bridge(4) and a vether(4) interface.

Create a vether0 interface that will have a private IPv4 address as defined above. In this example, we’ll use the subnet.

# echo 'inet' > /etc/hostname.vether0
# sh /etc/netstart vether0

Create the bridge0 interface with the vether0 interface as a bridge port:

# echo 'add vether0' > /etc/hostname.bridge0
# sh /etc/netstart bridge0

Ensure that NAT is set up properly if the guests on the virtual network need access beyond the physical machine. An adjusted NAT line in /etc/pf.conf might look like this:

match out on egress from vether0:network to any nat-to (egress)

The following lines in vm.conf(5) can be used to ensure that a virtual switch is defined:

switch "my_switch" {
    interface bridge0

vm "my_vm" {
    interface { switch "my_switch" }

Inside the my_vm guest, it’s now possible to assign vio0 an address on the network and set the default route to

For convenience, you may wish to set up a DHCP server on vether0.

Option 4 - VMs as real hosts on the same network

In this scenario, the VM interface will be attached to the same network as the host so can it be configured as if it were physically connected to the host network. This option only works for Ethernet-based devices, as the IEEE 802.11 standard prevents wireless interfaces from participating in network bridges.

Create the vether0 interface:

# echo 'up' > /etc/hostname.vether0
# sh /etc/netstart vether0

The vether0 interface will be used as the local interface for the host that is managed via DHCP on the host network.

Create the bridge0 interface with the host network interface as a bridge port, along with the newly created vether0 interface. In this example, the host network interface is em0 - you should substitute the interface name that you wish to connect the VM to:

# echo 'add em0' > /etc/hostname.bridge0
# echo 'add vether0' >> /etc/hostname.bridge0
# sh /etc/netstart bridge0

As done in the previous example, create or modify the vm.conf(5) file to ensure that a virtual switch is defined:

switch "my_switch" {
    interface bridge0

vm "my_vm" {
    interface { switch "my_switch" }

The my_vm guest can now participate in the host network as if it were physically connected.

If the host interface (em0 in the above example) is also configured using DHCP, dhclient(8) running on that interface may block DHCP requests from reaching guest VMs. In this case, you should select a different host interface not using DHCP, or terminate any dhclient(8) processes assigned to that interface before starting VMs, or use static IP addresses for the VMs.

Using NFS

The Network File System, NFS, is used to share a filesystem over the network.

This section will go through the steps for a simple NFS setup. The example details a server on a LAN, with clients accessing NFS on the LAN. It does not cover securing NFS. We presume you have already set up packet filtering or other firewalling protection to prevent outside access.

Setting Up an NFS Server

First, enable the portmap(8), mountd(8) and nfsd(8) services on the server:

# rcctl enable portmap mountd nfsd

Then configure the list of filesystems that will be made available. In this example, we have a server with IP address This server will be serving NFS only to clients within its own subnet. This is configured in the following exports(5) file:

$ cat /etc/exports
/docs -alldirs -ro -network=10.0.0 -mask=

The local filesystem /docs will be made available via NFS. The -alldirs option specifies that clients will be able to mount at any point under /docs as well as /docs itself. The -ro option specifies that clients will only be granted read-only access. The last two arguments specify that only clients within the network using a netmask of will be authorized to mount this filesystem.

Now you can start the server services.

# rcctl start portmap mountd nfsd

If you make changes to /etc/exports while NFS is already running, you need to make mountd aware of this:

# rcctl reload mountd

Mounting NFS Filesystems

NFS filesystems should be mounted via mount(8), or more specifically, mount_nfs(8).

To mount the /docs filesystem on host to local filesystem /mnt, run:

# mount -t nfs /mnt

To have that filesystem mounted at boot, append a line to your fstab(5):

# echo ' /mnt nfs ro,nodev,nosuid 0 0' >> /etc/fstab

It is important that you use 0 0 at the end of this line so that your computer does not try to fsck(8) the NFS filesystem on boot.

When accessing an NFS mount as the root user, the server automatically maps root’s access to username nobody and group nobody. This is important to know when considering file permissions. For example, take a file with these permissions:

-rw-------    1 root     wheel           0 Dec 31 03:00 _daily.B20143

If this file was on an NFS share and the root user tried to access this file from the NFS client, access would be denied.

The user and group that root are mapped to are configurable via the exports(5) file on the NFS server.

Checking Stats on NFS

One thing to check to ensure NFS is operating properly is that all the daemons have properly registered with RPC. To do this, use rpcinfo(8).

$ rpcinfo -p
   program vers proto   port
    100000    2   tcp    111  portmapper
    100000    2   udp    111  portmapper
    100005    1   udp    633  mountd
    100005    3   udp    633  mountd
    100005    1   tcp    916  mountd
    100005    3   tcp    916  mountd
    100003    2   udp   2049  nfs
    100003    3   udp   2049  nfs
    100003    2   tcp   2049  nfs
    100003    3   tcp   2049  nfs

There are a few utilities that allow you to see what is happening with NFS. showmount(8) allows you to view what is currently mounted by whom. There is also nfsstat(1), which shows much more verbose statistics.