How to connect a jail to the web ?

Oliver Fromme olli at
Thu Aug 12 08:40:15 UTC 2010

David Allen <the.real.david.allen at> wrote:
 > I've read comments in the past about setting up jails using local
 > loopback addresses, but I'm wondering if you wouldn't mind elaborating
 > on what the actual pf rules would look like.
 > Say you have 3 jails and more than one public IP address:
 >   ns   public_ip_1
 >   mail   public_ip_2
 >   www   public_ip_3
 > You want to pass port 25 traffic to/from the 'mail' jail.  But you also
 > need that jail to use the correct public_ip address.  Is that possible
 > without using, for example, pf's binat?

Just for completeness, this is a little "how-to" that
describes how you do it with IPFW.  You do not have to
configure NAT.  One single fwd rule is sufficient.
The following example works on FreeBSD 8.1.

In this example, I'll use port 42, the jail has address on lo0, and nc (netcat) is used in place of a
real daemon.  The real (external) address of the host
machine is

HOST# is the prompt of the server machine that hosts the
jail, JAIL# is the prompt within that host machine's
jail, and CLIENT$ is the prompt of a separate physical
machine on the same network which is used for testing

First add an alias IP to the lo0 (localnet) interface.

    HOST# ifconfig lo0 inet alias

In order to make that permament, you have to add an
alias line to /etc/rc.conf, of course:


Check the addresses:

    HOST# ifconfig lo0 | grep -w inet
            inet netmask 0xff000000 
            inet netmask 0xffffffff 

Install the IPFW fwd rule:

    HOST# ipfw add 1 fwd tcp from any to 42
    00001 fwd tcp from any to dst-port 42

To make that permanent, add these lines to /etc/rc.conf:


And create a file /etc/ipfw.conf containing these lines:

    -f flush
    add fwd tcp from any to 42

Ok, now start the jail.  For the sake of this example,
we simply re-use the host's installed base, i.e. the
jail's root path is "/".  For a real jail you would
use the jail's root directory, of course.

    HOST# jail / testjail /bin/sh -E

Finally start a netcat (nc) process in the jail.
In a real jail, this would be an apache process on
port 80, a mail transfer agent on port 25, whatever.

    JAIL# nc -ln 42

Now the netcat process is listening on port 42 inside
the jail on the localnet address  You can
verify that with sockstat(1) on the host:

    HOST# sockstat | grep -w 42
    root     nc         1953  3  tcp4          *:*

You can now connect to that "service" from a different
system on the network, using the external IP address
of the host.  The IPFW fwd rule reroutes the packets
destined for port 42 to the jail's localnet address.

    CLIENT$ echo Hello world | nc 42

As a result, netcat will echo the string "Hello world"
in the jail, and the nc process will terminate.

Note:  In order to be able to use IPFW fwd rules, you
should have these two lines in your kernel config:

    options    IPFIREWALL

If you don't intend to use IPFW for anything else than
fwd, you can also include the following line, so you
don't have to install any additional "allow" rules:


That's especially useful if you want to use IPFW for
forwarding only, and use another software for actual
packet filtering (i.e. pf or ipf).

Best regards

Oliver Fromme, secnetix GmbH & Co. KG, Marktplatz 29, 85567 Grafing b. M.
Handelsregister: Registergericht Muenchen, HRA 74606,  Geschäftsfuehrung:
secnetix Verwaltungsgesellsch. mbH, Handelsregister: Registergericht Mün-
chen, HRB 125758,  Geschäftsführer: Maik Bachmann, Olaf Erb, Ralf Gebhart

FreeBSD-Dienstleistungen, -Produkte und mehr:

"With sufficient thrust, pigs fly just fine.  However, this
is not necessarily a good idea.  It is hard to be sure where
they are going to land, and it could be dangerous sitting
under them as they fly overhead." -- RFC 1925

More information about the freebsd-questions mailing list