#!/bin/sh # # dns-update -- update DNS A and AAAA records automatically # # Depends: perl, dnsutils # # Copyright 2004 by Nathaniel W. Turner # # This program is free software; you can redistribute it and/or modify it # under the terms of the GNU General Public License as published by the Free # Software Foundation; either version 2, or (at your option) any later # version. PATH=/usr/local/sbin:/usr/local/bin:/sbin:/bin:/usr/sbin:/usr/bin NAME=update-dns function usage { cat < {up|down} This program gets the primary IPv4 and IPv6 address for the specified network interface and updates the appropriate nameserver. OPTIONS: --hostname , -n register as the name of this host; if not specified, the output of \`hostname -f\` will be used --server , -s send nsupdate commands to server instead of the host registered as namserver for this hostname --key , -k use as the shared secret for TSIG request signing --verbose, -v explain what is being done --help, -h display this usage information EXAMPLES: $NAME eth0 up $NAME -n aardvarque.example.com -s 10.136.0.1 eth1 down $NAME -k Kmysecret.+157+38323.private eth0 up EOT } eval set -- `getopt -o 'n:s:t:k:vh' \ -l 'hostname:,server:,ttl:,key:,verbose,help' \ -n "$NAME" -- "$@"` hostname=`hostname -f` nameserver= ttl=600 key= verbose= help= while true; do case "$1" in -n|--hostname) hostname="$2"; shift 2;; -s|--server) nameserver="$2"; shift 2;; -t|--ttl) ttl="$2"; shift 2;; -k|--key) key="$2"; shift 2;; -v|--verbose) verbose=1; shift;; -h|--help) help=1; shift;; --) shift; break;; *) echo "Error: $1"; exit 1 esac done interface="$1"; shift; command="$1"; shift; if test "$help"; then usage exit 0 fi if test -z "$interface"; then usage 1>&2 exit 1 fi nsupdate_cmd="nsupdate" if test -n "$key"; then nsupdate_cmd="$nsupdate_cmd -k $key" fi case "$command" in up) myv4ip=`ip -4 addr show dev $interface primary 2>/dev/null \ | perl -ne 'print $1 if /^\ *inet (\d+(?:\.\d+){3})/'` myv6ip=`ip -6 addr show dev $interface primary 2>/dev/null \ | grep 'scope global' \ | perl -ne 'print $1 if /^\ *inet6 ([[:xdigit:]:]+)/'` if test "$verbose"; then echo "Updating DNS record(s) for $hostname" test "$nameserver" && echo "Using nameserver $nameserver" test "$myv4ip" && echo "Setting A record to $myv4ip" test "$myv6ip" && echo "Setting AAAA record to $myv6ip" test "$key" && echo "Using TSIG key $key" fi ( test "$nameserver" && echo server $nameserver echo update delete $hostname A test -n "$myv4ip" && echo update add $hostname $ttl A $myv4ip echo update delete $hostname AAAA test -n "$myv6ip" && echo update add $hostname $ttl AAAA $myv6ip echo send ) | $nsupdate_cmd rv=$? if test "$verbose" && test "$rv" = 0; then echo "DNS updated." fi ;; down) if test "$verbose"; then echo "Removing DNS record(s) for $hostname" test "$nameserver" && echo "Using nameserver $nameserver" test "$key" && echo "Using TSIG key $key" fi ( test "$nameserver" && echo server $nameserver echo update delete $hostname A echo update delete $hostname AAAA echo send ) | $nsupdate_cmd rv=$? if test "$verbose" && test "$rv" = 0; then echo "DNS updated." fi ;; *) echo "Invalid command $command" 1>&2 usage 1>&2 exit 1 ;; esac