#!/bin/sh -e

##########################################################################
#   Script description:
#       Configure a basic firewall
#       
#   History:
#   Date        Name        Modification
#   2020-06-30  Jason Bacon Begin
##########################################################################

usage()
{
    printf "Usage: $0\n"
    exit 1
}


##########################################################################
#   Function description:
#       Pause until user presses return
##########################################################################

pause()
{
    local junk
    
    printf "Press return to continue..."
    read junk
}


##########################################################################
#   Main
##########################################################################

if [ $# != 0 ]; then
    usage
fi

auto-root-check $0

export AUTO_ASK_TAG_PREFIX=auto-firewall-setup

cat << EOM

********************************** WARNING **********************************

Changing your firewall settings is likely to terminate existing network
connections, such as ssh sessions, unless you really know what you're doing.

*****************************************************************************

EOM
printf "Are you sure you want to proceed? y/[n] "
read proceed
if [ 0$proceed != 0y ]; then
    exit
fi

firewall_script="/etc/ipfw.rules"

case $(auto-ostype) in
FreeBSD)
    firewall=0
    cat << EOM

Configuring a basic IPFW firewall.  See the FreeBSD Handbook for information
on customizing IPFW or using the PF or IPFILTER firewalls instead.

    https://www.freebsd.org/doc/handbook/firewalls.html

EOM
    pause

    while [ $firewall -lt 1 ] || [ $firewall -gt 6 ]; do
	cat << EOM

The "client" and "simple" rule sets can be customized in $firewall_script.
For example, to enable incoming SSH (TCP 22) connections, add the following:

    ${fwcmd} add pass tcp from any to me 22 setup

Replace "any" with an IP address specification to limit access.
Add similar rules for HTTP (80), HTTPS (443), 631 (IPP printing).  See
/etc/services for a list of common TCP service ports.

The "workstation" rule set is configured by setting variables such as
firewall_myservices in /etc/rc.conf.  See $firewall_script for details.

1.. Open (Allow all traffic for now, I'll add my own rules later)
2.. Client (Basic protection for this machine only)
3.. Simple (Protection for entire subnet)
4.. Closed (Block all traffic for now, I'll add my own rules later)
5.. Workstation (Protect this machine only using stateful rules)
6.. Use my custom IPFW rule set

EOM
	firewall=$(auto-ask firewall-type 'Firewall type?' 2)
    done
    sysrc firewall_enable="YES"
    case $firewall in
    1)
	sysrc firewall_type="open"
	sysrc firewall_script="$firewall_script"
	;;
    
    2)
	sysrc firewall_type="client"
	default_subnet="$(auto-get-network octet)/$(auto-get-netmask-bits)"
	printf "Local subnet? [$default_subnet] "
	read subnet
	if [ 0$subnet = 0 ]; then
	    subnet=$default_subnet
	fi
	sysrc firewall_client_net="$subnet"
	sysrc firewall_script="$firewall_script"
	;;
    
    3)
	sysrc firewall_type="simple"
	sysrc firewall_script="$firewall_script"
	;;
    
    4)
	sysrc firewall_type="closed"
	sysrc firewall_script="$firewall_script"
	;;
    
    5)
	sysrc firewall_type="workstation"
	sysrc firewall_script="$firewall_script"
	;;
    
    6)
	firewall_type=$(auto-ask custom-ipfw-script "Path to custom script?" $firewall_script)
	sysrc firewall_type="$firewall_script"
	firewall_script=$firewall_type
	printf "Install your rule set to $script now.\n"
	pause
	;;
    
    esac
    if [ ! -e $firewall_script ]; then
	cp /etc/rc.firewall $firewall_script
    fi
    cat << EOM

You MUST add rules to $firewall_script to allow traffic from
outside the local subnet, or all existing connections will be terminated.

Opening $EDITOR now...

EOM
    pause
    : ${EDITOR:=vi}
    $EDITOR $firewall_script
    service ipfw restart
    auto-set-sysctl net.inet.ip.fw.verbose_limit 5 $0
    ;;

*)
    auto-unsupported-os $0
    exit 1
    ;;

esac
