Setting Up ipfw on Mac OS X

Using multiple layers of security has long been recognized as a useful strategy in hardening your computers against attack or exploit. In this post, I want to explain how to set up and configure the BSD-level ipfw firewall that is present in Mac OS X. While ipfw is certainly not a security panacea, it can be a solid part of a broader security strategy.

Setting up ipfw on Mac OS X has three basic steps:

  1. Create a shell script that launches ipfw.
  2. Create a configuration file that the shell script from step 1 uses when launching ipfw.
  3. Create a LaunchDaemon in Mac OS X that calls the shell script from step 1 to start and configure ipfw every time your Mac boots.

Let’s take a deeper look at each of these steps.

Create a Startup Shell Script

This part is harder than it sounds. At its most basic level, the script only needs to call /sbin/ipfw and a configuration file, like this:

#!/bin/sh

/sbin/ipfw -q /etc/ipfw.conf

I did quite a bit of digging to see if something more than that was suggested, and finally came up with this startup shell script:

#!/bin/sh
# Startup script for ipfw on Mac OS X

# Flush existing rules
/sbin/ipfw -f -q flush

# Silently drop unsolicited connections
/usr/sbin/sysctl -w net.inet.tcp.blackhole=2
/usr/sbin/sysctl -w net.inet.udp.blackhole=1

# Load the firewall ruleset
/sbin/ipfw -q /etc/ipfw.conf

This startup shell script can generally be put anywhere; I chose to put it in /usr/local/bin (which may not exist by default on your system).

With the startup shell script in place, you’re now ready to proceed to the next step, which is perhaps the most involved and detailed step in the process.

Create the Configuration File

The configuration file contains all of the firewall rule definitions for ipfw and is therefore one of the most complicated steps. This complexity is not because the configuration file itself is difficult, but rather because the rules that should be included will vary greatly from user to user and network to network. I strongly encourage you to do your own research to understand what sort of firewall rules are most appropriate in your environment and for your setup.

You can (theoretically) place the configuration file anywhere; I chose to place the file in /etc as ipfw.conf (very original, I know). If you do use something other than /etc/ipfw.conf, then adjust the startup shell script accordingly.

Rather than provide any sort of suggested firewall ruleset here, let me suggest some other sites that provide excellent information on suggested rulesets for ipfw:

Use a custom firewall in 10.5 with ipfw (Mac OS X Hints)

Setting up firewall rules on Mac OS X

Configuring IPFW Firewalls on OS X

From those sites—and there are many others besides just those—you should be able to put together an ipfw ruleset that is right for your network and your environment. Once you have the configuration file created and in place, then you’re ready for the final step: ensuring that ipfw launches automatically when you boot your Mac.

Create a LaunchDaemon

The final step is ensuring that ipfw launches automatically every time your Mac boots. This is accomplished by creating a text file—known as a property list file, or a plist file—with very specific contents into the /Library/LaunchDaemons folder.

Here’s a screenshot of my plist file, named com.apple.ipfw.plist (you can use a different name, like your own domain name, in the filename):

Don’t just copy and paste this file “as is” into your system! You’ll need to customize it to fit your system. Specifically, under the ProgramArguments key, the path to and name of the startup shell script should be adjusted to match the shell script you created earlier. In my case, the script is named ipfwstartup.sh and is found in /usr/local/bin. This startup shell script should, in turn, refer to the ipfw configuration file you created.

I believe—but I could be mistaken—that you’ll need to set ownership of the LaunchDaemon plist file to root:wheel. You can do this using the chown command in Terminal.

Once the plist file is in place, reboot your Mac. Once your Mac boots up and you’ve logged in, fire up the Terminal and run this command (you will need to use sudo if your account has administrative privileges; if your account doesn’t have administrative privileges, you should log in as an account that does in order to test things):

sudo ipfw list

This command should return the list of firewall rules you embedded in the configuration file. If it doesn’t, then go back and double-check your setup. Be sure that the plist file has the correct reference to the startup shell script, and that the startup shell script has the correct reference to the configuration file. You should also check to ensure that you made the startup shell script executable (using the chmod command).

If the command does return your firewall ruleset, then you’re all set.

Note that using ipfw does not in any way prevent you from using other firewalls—such as the built-in application-level firewall in Mac OS X—to further secure your system.

Questions? Comments? Clarifications? Please feel free to speak up in the comments below to add your thoughts.

Tags: , , ,

  1. Ryan’s avatar

    For the more GUI oriented ipfw preferring folks, take a look at http://www.hanynet.com/waterroof/index.html . Keep in mind though, that ipfw is deprecated in favor of PF, and the same guy makes a GUI for that as well – http://www.hanynet.com/icefloor/index.html .

  2. phocean’s avatar

    Hi Scott,

    I am a very recent switcher (got a MacBook Pro a few days ago), so I am a complete noob on this system… so pardon my question, but what about the firewall provided with MacOS (at least on Lion) ?
    I quickly nmaped my laptop and it seems to do the job…

  3. slowe’s avatar

    PF is on Mac OS X Lion, but Snow Leopard and earlier versions use ipfw. Thanks!

  4. Rob Velarde’s avatar

    I enjoy reading the blog. Since you are playing with the Mac firewall, I use a program called WaterRoof from Haynet.com, its free and open source. It has a pretty good GUI for configuring the ipfw for your Mac and you can also use it deploy ipfw rules to other Macs in a enterprise. I thought you might want to give it a try.

  5. slowe’s avatar

    Phocean, the built-in firewall is good, but isn’t granular enough in my opinion. For example, you can allow iTunes to accept incoming connections, but you can’t specify from which networks. PF (on Lion) and ipfw (on earlier versions) gives you that level of granularity. I think you should use both.

  6. David Magda’s avatar

    While as you say that everyone’s situation is different, a good default working IPFW set of rules can be gleaned from FreeBSD:

    http://svnweb.freebsd.org/base/head/etc/rc.firewall

    Specifically they have following the pre-canned solutions:
    * open: will allow anyone in
    * client: will try to protect just this machine
    * simple: will try to protect a whole network
    * closed: totally disables IP services except via lo0 interface
    * workstation: will try to protect just this machine using stateful firewalling.

    “Client” and “workstation” would probably be the most useful, the main difference being is that the latter’s part of the script also has variables for services that you may want to allow to connect (e.g., SSH, HTTP, etc.).

    The script has lines for IPv6, multicast, ICMP, and other things that are easy to forget about (or not be aware of); again, under the “workstation” case.

  7. Frank’s avatar

    Righty, I do recognise the file from my original post (http://hints.macworld.com/dlfiles/custom_ipfw_105.txt) from 2005. Is it already that long ago???

    Anyway, this was working fine for a number of years but at some point the darn thing stopped logging into either ipfw.log or system.log. I think this stopped working with 10.6 and I have tried loads of things but no success.

    Does anybody know how I get my log entries back??

    Cheers!

  8. goarilla’s avatar

    Sorry for necroposting ? But the built-in firewall of Mac OS X isn’t that good.
    It returns a RST on tcp ports, marking the port as closed (the tcp stack responds) instead of denying/dropping it and making the attacker guess (proper firewall). Also it changes its mind when you scan too fast. It suddenly decides to rate limit you and deny instead of reject. Presenting you with open, closed and filtered ports and an insight in the rate limiting mechanism.

  9. Nad’s avatar

    Step 1. Create a startup script

    I’m stuck on step one. I don’t see what the script is to be called or where it is to be stored. The rest seems straightforward.

  10. slowe’s avatar

    Nad, the article provides a couple of sample scripts (they are embedded directly in the article) and tells you that the startup script can be placed just about anywhere on your system (although I placed mine in /usr/local/bin).

  11. expat42451’s avatar

    Scott-

    Many thanks for the excellent article and thread on ipfw config. I do have one question-

    I was under the impression that the GUI fronted for 10.9.4- and for everything for that matter since Lion- was simply a limited GUI control for pfctl. I have used ipfw in Unix, BSD and Linux but am not conversant with pfctl and the man pages are somewhat lacking in OSX. Reason I ask this is I have several friends who have reservations about using command line to configure the firewall and have been trying to help them out. I recommended Ice Floor. I also am curious thus the question.

    Thanks very much

    Expat

  12. Frank’s avatar

    Apparently ipfw is deprecated as of 10.7 and has been replaced with pf on OS X. So pf is relatively new on OS X as far as I know. So the GUI *could* be a front end for pfctl. However, previously (at least) the GUI was not a front end for ipfw. It was effectively a second firewall, higher on the stack than ipfw (if I’m not mistaken). Or rather the other way around, if you were using ipfw than that would be your second firewall, although I never used the GUI firewall, just ipfw.

    Still have to convert my ipfw setup to pf though …

  13. slowe’s avatar

    Expat42451, I know that in at least Mountain Lion (I haven’t migrated my systems to Mavericks yet), the pf configuration files are structured in such a way so that the GUI tools could manipulate them. However, I haven’t seen any indication that the GUI tools do actually manipulate pf. So, as far as I can tell, using pf (on later versions of OS X) or ipfw (on earlier versions of OS X) is in addition to the GUI firewall mechanisms.

Reply

Your email address will not be published. Required fields are marked *

You may use these HTML tags and attributes: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong>