--- dns/bind910/files/named.in.orig 2014-05-09 12:25:22.635423000 +0200 +++ dns/bind910/files/named.in 2015-01-05 19:10:08.536571346 +0100 @@ -21,21 +21,112 @@ start_postcmd=named_poststart reload_cmd=named_reload stop_cmd=named_stop +stop_postcmd=named_poststop named_enable=${named_enable:-"NO"} # Run named, the DNS server (or NO). named_program=${named_program:-"%%PREFIX%%/sbin/named"} # Path to named, if you want a different one. named_conf=${named_conf:-"%%ETCDIR%%/named.conf"} # Path to the configuration file named_flags=${named_flags:-""} # Use this for flags OTHER than -u and -c named_uid=${named_uid:-"bind"} # User to run named as +named_chrootdir=${named_chrootdir:-""} # Chroot directory, not enabled by default +named_chroot_autoupdate="YES" # Automatically install/update chrooted components +named_symlink_enable="YES" # Symlink the chrooted pid file named_wait=${named_wait:-"NO"} # Wait for working name service before exiting named_wait_host=${named_wait_host:-"localhost"} # Hostname to check if named_wait is enabled named_auto_forward=${named_auto_forward:-"NO"} # Set up forwarders from /etc/resolv.conf named_auto_forward_only=${named_auto_forward_only:-"NO"} # Do "forward only" instead of "forward first" %%NATIVE_PKCS11%%named_pkcs11_engine=${named_pkcs11_engine:-""} # Path to the PKCS#11 library to use. -named_confdir="${named_conf%/*}" # Not a configuration directive but makes rclint happy. +named_confdir="${named_conf%/*}" # Will be altered for chroot. + +# If running in a chroot cage, ensure that the appropriate files +# exist inside the cage, as well as helper symlinks into the cage +# from outside. +# +# As this is called after the is_running and required_dir checks +# are made in run_rc_command(), we can safely assume ${named_chrootdir} +# exists and named isn't running at this point (unless forcestart +# is used). +# +chroot_autoupdate() +{ + local file backupfiles + + # Create (or update) the chroot directory structure + # + if [ -r %%PREFIX%%/etc/mtree/BIND.chroot.dist ]; then + mtree -deU -f %%PREFIX%%/etc/mtree/BIND.chroot.dist \ + -p ${named_chrootdir} + else + warn "%%PREFIX%%/etc/mtree/BIND.chroot.dist missing," + warn "chroot directory structure not updated" + fi + + # Use named_confdir without local-prefix inside chrootdir (e.g. remove /usr/local) + named_confdir="${named_chrootdir}`echo ${named_conf%/*} | sed -e 's|%%PREFIX%%||'`" + + # Create (or update) the configuration directory symlink + # + if [ ! -L "${named_conf%/*}" ]; then + if [ -d "${named_conf%/*}" ]; then + sed -i "" -e '/^[[:blank:]]*directory/ s|%%PREFIX%%||;/[[:blank:]]file[[:blank:]]/ s|%%PREFIX%%||' ${named_conf} + backupfiles="`find ${named_confdir} -type f`" + if [ -n "${backupfiles}" ]; then + tar cPzf /var/backups/named-chroot-files.tgz "${backupfiles}" + warn "Saved files before overwriting into \"/var/backups/named-chroot-files.tgz\"!" + fi + rm -R ${named_confdir} + mv "${named_conf%/*}" "${named_confdir%/*}" + fi + fi + + # Make sure it points to the right place. + ln -shf ${named_confdir} ${named_conf%/*} + + # Adjust named_conf for chrootdir without local-prefix + named_conf="${named_confdir##${named_chrootdir}}/${named_conf##*/}" + + # Mount a devfs in the chroot directory if needed + # + if [ `${SYSCTL_N} security.jail.jailed` -eq 0 ]; then + umount ${named_chrootdir}/dev 2>/dev/null + devfs_domount ${named_chrootdir}/dev devfsrules_hide_all + devfs -m ${named_chrootdir}/dev rule apply path null unhide + devfs -m ${named_chrootdir}/dev rule apply path random unhide + else + if [ -c ${named_chrootdir}/dev/null -a \ + -c ${named_chrootdir}/dev/random ]; then + info "named chroot: using pre-mounted devfs." + else + err 1 "named chroot: devfs cannot be mounted from" \ + "within a jail. Thus a chrooted named cannot" \ + "be run from within a jail." \ + "To run named without chrooting it, set" \ + "named_chrootdir=\"\" in /etc/rc.conf." + fi + fi + + # Copy and/or update key files to the chroot /etc + # + for file in localtime protocols services; do + if [ -r /etc/$file ]; then + cmp -s /etc/$file "${named_chrootdir}/etc/$file" || + cp -p /etc/$file "${named_chrootdir}/etc/$file" + fi + done +} + +# Make symlinks to the correct pid file +# +make_symlinks() +{ + checkyesno named_symlink_enable && + ln -fs "${named_chrootdir}${pidfile}" ${pidfile} +} named_poststart() { + make_symlinks + if checkyesno named_wait; then until ${command%/sbin/named}/bin/host $named_wait_host >/dev/null 2>&1; do echo " Waiting for nameserver to resolve $named_wait_host" @@ -83,12 +174,26 @@ fi } +named_poststop() +{ + if [ -n "${named_chrootdir}" -a -c ${named_chrootdir}/dev/null ]; then + if [ `${SYSCTL_N} security.jail.jailed` -eq 0 ]; then + umount ${named_chrootdir}/dev 2>/dev/null || true + else + warn "named chroot:" \ + "cannot unmount devfs from inside jail!" + fi + fi +} + create_file() { if [ -e "$1" ]; then unlink $1 fi - install -o root -g wheel -m 0644 /dev/null $1 + > $1 + chown root:wheel $1 + chmod 644 $1 } named_prestart() @@ -101,11 +206,10 @@ piddir=`/usr/bin/dirname ${pidfile}` if [ ! -d ${piddir} ]; then - install -d -o ${named_uid} -g ${named_uid} ${piddir} + mkdir -m 0755 ${piddir} + chown ${named_uid}:${named_uid} ${piddir} fi - command_args="-u ${named_uid:=root} -c $named_conf $command_args" - %%NATIVE_PKCS11%% if [ -z "$named_pkcs11_engine"]; then %%NATIVE_PKCS11%% err 3 "named_pkcs11_engine has to be set to the PKCS#11 engine's library you want to use" %%NATIVE_PKCS11%% elif [ ! -f $named_pkcs11_engine ]; then @@ -116,6 +220,17 @@ %%NATIVE_PKCS11%% local line nsip firstns + # Is the user using a sandbox? + # + if [ -n "$named_chrootdir" ]; then + rc_flags="$rc_flags -t $named_chrootdir" + checkyesno named_chroot_autoupdate && chroot_autoupdate + else + named_symlink_enable=NO + fi + + command_args="-u ${named_uid:=root} -c $named_conf $command_args" + # Create an rndc.key file for the user if none exists # confgen_command="${command%/named}/rndc-confgen -a -b256 -u $named_uid \ @@ -135,6 +250,9 @@ local checkconf checkconf="${command%/named}/named-checkconf" + if ! checkyesno named_chroot_autoupdate && [ -n "$named_chrootdir" ]; then + checkconf="$checkconf -t $named_chrootdir" + fi # Create a forwarder configuration based on /etc/resolv.conf if checkyesno named_auto_forward; then @@ -210,4 +328,8 @@ $checkconf $named_conf || err 3 'named-checkconf for $named_conf failed' } +# Updating the following variables requires that rc.conf be loaded first +# +required_dirs="$named_chrootdir" # if it is set, it must exist + run_rc_command "$1"