diff --git a/doc/man/Makefile.am b/doc/man/Makefile.am index a7dae80d9..c4747fa8f 100644 --- a/doc/man/Makefile.am +++ b/doc/man/Makefile.am @@ -1,162 +1,163 @@ # # doc: Linux-HA resource agents # # Copyright (C) 2009 Florian Haas # # 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 # of the License, or (at your option) any later version. # # This program is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU General Public License for more details. # # You should have received a copy of the GNU General Public License # along with this program; if not, write to the Free Software # Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. # MAINTAINERCLEANFILES = Makefile.in EXTRA_DIST = $(doc_DATA) $(REFENTRY_STYLESHEET) \ mkappendix.sh ralist.sh CLEANFILES = $(man_MANS) $(xmlfiles) metadata-*.xml STYLESHEET_PREFIX ?= http://docbook.sourceforge.net/release/xsl/current MANPAGES_STYLESHEET ?= $(STYLESHEET_PREFIX)/manpages/docbook.xsl HTML_STYLESHEET ?= $(STYLESHEET_PREFIX)/xhtml/docbook.xsl FO_STYLESHEET ?= $(STYLESHEET_PREFIX)/fo/docbook.xsl REFENTRY_STYLESHEET ?= ra2refentry.xsl XSLTPROC_OPTIONS ?= --xinclude XSLTPROC_MANPAGES_OPTIONS ?= $(XSLTPROC_OPTIONS) XSLTPROC_HTML_OPTIONS ?= $(XSLTPROC_OPTIONS) XSLTPROC_FO_OPTIONS ?= $(XSLTPROC_OPTIONS) radir = $(top_srcdir)/heartbeat # OCF_ROOT=. is necessary due to a sanity check in ocf-shellfuncs # (which tests whether $OCF_ROOT points to a directory metadata-%.xml: $(radir)/% OCF_ROOT=. OCF_FUNCTIONS_DIR=$(radir) $< meta-data > $@ metadata-IPv6addr.xml: ../../heartbeat/IPv6addr OCF_ROOT=. OCF_FUNCTIONS_DIR=$(radir) $< meta-data > $@ # Please note: we can't name the man pages # ocf:heartbeat:. Believe me, I've tried. It looks like it # works, but then it doesn't. While make can deal correctly with # colons in target names (when properly escaped), it royally messes up # when it is deals with _dependencies_ that contain colons. See Bug # 12126 on savannah.gnu.org. But, maybe it gets fixed soon, it was # first reported in 1995 and added to Savannah in in 2005... if BUILD_DOC man_MANS = ocf_heartbeat_AoEtarget.7 \ ocf_heartbeat_AudibleAlarm.7 \ ocf_heartbeat_ClusterMon.7 \ ocf_heartbeat_CTDB.7 \ ocf_heartbeat_Delay.7 \ ocf_heartbeat_Dummy.7 \ ocf_heartbeat_EvmsSCC.7 \ ocf_heartbeat_Evmsd.7 \ ocf_heartbeat_Filesystem.7 \ ocf_heartbeat_ICP.7 \ ocf_heartbeat_IPaddr.7 \ ocf_heartbeat_IPaddr2.7 \ ocf_heartbeat_IPsrcaddr.7 \ ocf_heartbeat_LVM.7 \ ocf_heartbeat_LinuxSCSI.7 \ ocf_heartbeat_MailTo.7 \ ocf_heartbeat_ManageRAID.7 \ ocf_heartbeat_ManageVE.7 \ ocf_heartbeat_Pure-FTPd.7 \ ocf_heartbeat_Raid1.7 \ ocf_heartbeat_Route.7 \ ocf_heartbeat_SAPDatabase.7 \ ocf_heartbeat_SAPInstance.7 \ ocf_heartbeat_SendArp.7 \ ocf_heartbeat_ServeRAID.7 \ ocf_heartbeat_SphinxSearchDaemon.7 \ ocf_heartbeat_Squid.7 \ ocf_heartbeat_Stateful.7 \ ocf_heartbeat_SysInfo.7 \ ocf_heartbeat_VIPArip.7 \ ocf_heartbeat_VirtualDomain.7 \ ocf_heartbeat_WAS.7 \ ocf_heartbeat_WAS6.7 \ ocf_heartbeat_WinPopup.7 \ ocf_heartbeat_Xen.7 \ ocf_heartbeat_Xinetd.7 \ ocf_heartbeat_anything.7 \ ocf_heartbeat_apache.7 \ ocf_heartbeat_asterisk.7 \ ocf_heartbeat_conntrackd.7 \ ocf_heartbeat_db2.7 \ + ocf_heartbeat_dhcpd.7 \ ocf_heartbeat_drbd.7 \ ocf_heartbeat_eDir88.7 \ ocf_heartbeat_ethmonitor.7 \ ocf_heartbeat_exportfs.7 \ ocf_heartbeat_fio.7 \ ocf_heartbeat_iSCSILogicalUnit.7 \ ocf_heartbeat_iSCSITarget.7 \ ocf_heartbeat_ids.7 \ ocf_heartbeat_iscsi.7 \ ocf_heartbeat_jboss.7 \ ocf_heartbeat_lxc.7 \ ocf_heartbeat_mysql.7 \ ocf_heartbeat_mysql-proxy.7 \ ocf_heartbeat_named.7 \ ocf_heartbeat_nfsserver.7 \ ocf_heartbeat_nginx.7 \ ocf_heartbeat_oracle.7 \ ocf_heartbeat_oralsnr.7 \ ocf_heartbeat_pgsql.7 \ ocf_heartbeat_pingd.7 \ ocf_heartbeat_portblock.7 \ ocf_heartbeat_postfix.7 \ ocf_heartbeat_pound.7 \ ocf_heartbeat_proftpd.7 \ ocf_heartbeat_rsyncd.7 \ ocf_heartbeat_rsyslog.7 \ ocf_heartbeat_scsi2reservation.7 \ ocf_heartbeat_sfex.7 \ ocf_heartbeat_slapd.7 \ ocf_heartbeat_symlink.7 \ ocf_heartbeat_syslog-ng.7 \ ocf_heartbeat_tomcat.7 \ ocf_heartbeat_varnish.7 \ ocf_heartbeat_vmware.7 if USE_IPV6ADDR man_MANS += ocf_heartbeat_IPv6addr.7 endif xmlfiles = $(man_MANS:.7=.xml) %.1 %.5 %.7 %.8: %.xml $(XSLTPROC) \ $(XSLTPROC_MANPAGES_OPTIONS) \ $(MANPAGES_STYLESHEET) $< ocf_heartbeat_%.xml: metadata-%.xml $(srcdir)/$(REFENTRY_STYLESHEET) $(XSLTPROC) --novalid \ --stringparam package $(PACKAGE_NAME) \ --stringparam version $(VERSION) \ --output $@ \ $(srcdir)/$(REFENTRY_STYLESHEET) $< ocf_resource_agents.xml: $(xmlfiles) mkappendix.sh ./mkappendix.sh $(xmlfiles) > $@ %.html: %.xml $(XSLTPROC) \ $(XSLTPROC_HTML_OPTIONS) \ --output $@ \ $(HTML_STYLESHEET) $< xml: ocf_resource_agents.xml endif diff --git a/heartbeat/Makefile.am b/heartbeat/Makefile.am index adfd97c68..2c0b3eedc 100644 --- a/heartbeat/Makefile.am +++ b/heartbeat/Makefile.am @@ -1,131 +1,132 @@ # Makefile.am for OCF RAs # # Author: Sun Jing Dong # Copyright (C) 2004 IBM # # 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 # of the License, or (at your option) any later version. # # This program is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU General Public License for more details. # # You should have received a copy of the GNU General Public License # along with this program; if not, write to the Free Software # Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. # MAINTAINERCLEANFILES = Makefile.in EXTRA_DIST = $(ocf_SCRIPTS) $(ocfcommon_DATA) \ $(common_DATA) $(hb_DATA) $(dtd_DATA) \ README INCLUDES = -I$(top_srcdir)/include -I$(top_srcdir)/linux-ha ocfdir = $(OCF_RA_DIR_PREFIX)/heartbeat dtddir = $(datadir)/$(PACKAGE_NAME) dtd_DATA = ra-api-1.dtd if USE_IPV6ADDR ocf_PROGRAMS = IPv6addr else ocf_PROGRAMS = endif IPv6addr_SOURCES = IPv6addr.c IPv6addr_LDADD = -lplumb $(LIBNETLIBS) ocf_SCRIPTS = ClusterMon \ CTDB \ Dummy \ IPaddr \ IPaddr2 \ drbd \ anything \ AoEtarget \ apache \ asterisk \ nginx \ AudibleAlarm \ conntrackd \ db2 \ + dhcpd \ Delay \ eDir88 \ EvmsSCC \ Evmsd \ ethmonitor \ exportfs \ Filesystem \ fio \ ids \ iscsi \ ICP \ IPsrcaddr \ iSCSITarget \ iSCSILogicalUnit \ jboss \ LinuxSCSI \ LVM \ lxc \ MailTo \ ManageRAID \ ManageVE \ mysql \ mysql-proxy \ named \ nfsserver \ oracle \ oralsnr \ pingd \ portblock \ postfix \ pound \ pgsql \ proftpd \ Pure-FTPd \ Raid1 \ Route \ rsyncd \ rsyslog \ SAPDatabase \ SAPInstance \ SendArp \ ServeRAID \ slapd \ SphinxSearchDaemon \ Squid \ Stateful \ SysInfo \ scsi2reservation \ sfex \ symlink \ syslog-ng \ tomcat \ VIPArip \ VirtualDomain \ varnish \ vmware \ WAS \ WAS6 \ WinPopup \ Xen \ Xinetd ocfcommondir = $(OCF_LIB_DIR_PREFIX)/heartbeat ocfcommon_DATA = ocf-shellfuncs \ ocf-binaries \ ocf-directories \ ocf-returncodes \ apache-conf.sh \ http-mon.sh \ sapdb-nosha.sh \ sapdb.sh # Legacy locations hbdir = $(sysconfdir)/ha.d hb_DATA = shellfuncs diff --git a/heartbeat/dhcpd b/heartbeat/dhcpd new file mode 100755 index 000000000..25e44e1e3 --- /dev/null +++ b/heartbeat/dhcpd @@ -0,0 +1,429 @@ +#!/bin/sh +# +# Resource Agent for managing dhcpd resources. +# +# License: GNU General Public License (GPL) +# (c) 2011-2012 Chris Bowlby, +# +# A fair amount of this script has been pulled from the official 0dhcpd +# init script. Those portions have been integrated into this script to +# ensure consistent behavior between the resource agent and the +# original script. The copyrights and original authors are credited +# as follows: +# +# Copyright (c) 1996, 1997, 1998 S.u.S.E. GmbH +# Copyright (c) 1998, 1999, 2000, 2001 SuSE GmbH +# Copyright (c) 2002, 2003 SuSE Linux AG +# Copyright (c) 2004-2008 SUSE LINUX Products GmbH, Nuernberg, Germany. +# +# Author(s) : Rolf Haberrecker , 1997-1999 +# Peter Poeml , 2000-2006 +# Marius Tomaschewski , 2006-2010 +# +# and Linux-HA contributors + +# Initialization: +: ${OCF_FUNCTIONS_DIR=${OCF_ROOT}/lib/heartbeat} +. ${OCF_FUNCTIONS_DIR}/ocf-shellfuncs + +# Defaults +OCF_RESKEY_binary_default="dhcpd" +OCF_RESKEY_pid_default="/var/run/dhcpd.pid" +OCF_RESKEY_user_default=dhcpd +OCF_RESKEY_group_default=nogroup +OCF_RESKEY_config_default="" +OCF_RESKEY_chrooted_path_default="/var/lib/dhcp" +OCF_RESKEY_leases_default="/db/dhcpd.leases" +OCF_RESKEY_interface_default="" +OCF_RESKEY_includes_default="" + +: ${OCF_RESKEY_binary=${OCF_RESKEY_binary_default}} +: ${OCF_RESKEY_pid=${OCF_RESKEY_pid_default}} +: ${OCF_RESKEY_user=${OCF_RESKEY_user_default}} +: ${OCF_RESKEY_group=${OCF_RESKEY_group_default}} +: ${OCF_RESKEY_chrooted_path=${OCF_RESKEY_chrooted_path_default}} +: ${OCF_RESKEY_config=${OCF_RESKEY_config_default}} +: ${OCF_RESKEY_leases=${OCF_RESKEY_leases_default}} +: ${OCF_RESKEY_interface=${OCF_RESKEY_interface_default}} +: ${OCF_RESKEY_includes=${OCF_RESKEY_includes_default}} + +# To enable support for different versions of dhcp, we need +# to know what version we are being run against. +DHCP_VERSION_MAJOR=`$OCF_RESKEY_binary --version 2>&1 | awk -F- '{print $3}' | awk -F. '{print $1}' | sed s/^[a-zA-Z]//g` + +# These files are always copied by default to ensure the chroot environment works. +DEFAULT_FILE_LIST="/etc/gai.conf /etc/nsswitch.conf /etc/resolv.conf /etc/host.conf /etc/hosts /etc/localtime /dev/urandom" + +usage() { + cat < + + + 0.1 + +Manage an ISC DHCP server service in a chroot environment. + + Chrooted ISC DHCP Server resource agent. + + + + The absolute path to the DHCP server configuration file. + + Configuration file + + + + + The absolute path of the chrooted DHCP environment. + + The chrooted path + + + + + The binary for the DHCP server process. An absolute path + definition is not required, but can be used to override + environment path. + + dhcpd binary + + + + + The system user the DHCP server process will run as when + it is chrooted. + + dhcpd owner + + + + + The system group the DHCP server process will run as when + it is chrooted. + + dhcpd group owner + + + + + The network interface(s) the DHCP server process will + bind to. A blank value will bind the process to all + interfaces. + + Network Interface + + + + + This parameter provides a means to copy include files + into the chrooted environment. If a dhcpd.conf file + contains a line similar to this: + + include "/etc/named.keys"; + + Then an admin also has to tell the dhcpd RA that this + file should be pulled into the chrooted environment. This + is a space delimited list. + + Include Files + + + + + The leases database file, relative to chrooted_path. + + Leases file + + + + + The path and filename of the PID file. It is relative + to chrooted_path. + + PID file + + + + + + + + + + + +EOF +} + +# Validate most critical parameters +dhcpd_validate_all() { + check_binary $OCF_RESKEY_binary + + + if ! ocf_is_probe; then + if ! test -e "$OCF_RESKEY_chrooted_path"; then + ocf_log err "Path $OCF_RESKEY_chrooted_path does not exist." + return $OCF_ERR_INSTALLED + fi + + if test -n "$OCF_RESKEY_chrooted_path/$OCF_RESKEY_config" -a ! -r "$OCF_RESKEY_chrooted_path/$OCF_RESKEY_config"; then + ocf_log err "Configuration file $OCF_RESKEY_chrooted_path/$OCF_RESKEY_config doesn't exist" + return $OCF_ERR_INSTALLED + fi + fi + + if ! getent passwd $OCF_RESKEY_user >/dev/null 2>&1; then + ocf_log err "User $OCF_RESKEY_user doesn't exist" + return $OCF_ERR_INSTALLED + fi + + return $OCF_SUCCESS +} + +# dhcpd_status. Simple check of the status of dhcpd process by pid. +dhcpd_status () { + ocf_pidfile_status $OCF_RESKEY_chrooted_path/$OCF_RESKEY_pid >/dev/null 2>&1 +} + +# dhcpd_monitor. Send a request to dhcpd and check response. +dhcpd_monitor() { + dhcpd_status || + return $OCF_NOT_RUNNING + + return $OCF_SUCCESS +} + +# Initialize Chroot +dhcpd_initialize_chroot() { + # If we are running the initialization for the first time, we need to make + # the new chrooted folder, in case we are not using the same default. + if ! [ -d $OCF_RESKEY_chrooted_path ] ; then + ocf_log info "Initializing $OCF_RESKEY_chrooted_path for use." + fi + + # Make sure all sub-paths are created if something went wrong during + # a partial run. + for i in db dev etc lib64 var/run; do + mkdir -p $OCF_RESKEY_chrooted_path/$i + done + + # If we are running version 4 of the dhcp server, we need to mount a proc partition. + if [ $DHCP_VERSION_MAJOR -ge 4 ] ; then + mkdir -p $OCF_RESKEY_chrooted_path/proc + + if ! [ -e $OCF_RESKEY_chrooted_path/proc/net/dev ] ; then + mount -t proc -o ro proc $OCF_RESKEY_chrooted_path/proc > /dev/null 2>&1 + fi + fi + + # Ensure all permissions are in place if the folder was re-created. + chown -R $OCF_RESKEY_user:$OCF_RESKEY_group $OCF_RESKEY_chrooted_path/`dirname $OCF_RESKEY_leases` + chown -R $OCF_RESKEY_user:$OCF_RESKEY_group $OCF_RESKEY_chrooted_path/`dirname $OCF_RESKEY_pid` + + ## If there is no conf file, we can't initialize the chrooted + ## environment, return with "program not configured" + if ! [ -f $OCF_RESKEY_config ] ; then + ocf_log err "dhcpd has not been configured." + return $OCF_ERR_CONFIGURED + fi + + # If the leases file does not exist, create it, as this is a fresh install. + if [ ! -e $OCF_RESKEY_chrooted_path/$OCF_RESKEY_leases ]; then + touch $OCF_RESKEY_chrooted_path/$OCF_RESKEY_leases + fi + + # Remove the random device. + test -e "$OCF_RESKEY_chrooted_path/dev/urandom" && + rm -f $OCF_RESKEY_chrooted_path/dev/urandom + + # Test for the existance of the defined include files, and append + # them to the list of files to be copied. + for i in $OCF_RESKEY_includes ; do + if [ -e $i ] ; then + DEFAULT_FILE_LIST="$DEFAULT_FILE_LIST $i" + else + ocf_log err "include file $i does not exist" + return $OCF_ERR_INSTALLED + fi + done + + # Ensure all "modified" non-chrooted configuration files are copied into the chrooted environment. + for i in $OCF_RESKEY_config $DEFAULT_FILE_LIST; do + # First, lets make sure the directory exists within the chrooted environment. + if test -d "$i" ; then + mkdir -p $OCF_RESKEY_chrooted_path/$i + elif test -e "$i" ; then + mkdir -p "`dirname $OCF_RESKEY_chrooted_path/$i`" + fi + + # Next, we copy the configuration file into place. + cp -aL "$i" "$OCF_RESKEY_chrooted_path/${i%/*}/" > /dev/null 2>&1 || + { ocf_log err "could not copy $i to chroot jail"; return $OCF_ERR_GENERIC; } + done + + libdir=$(basename $(echo /var/lib/dhcp/lib*)) + if test -x /usr/bin/ldd ; then + get_ldd_deps() + { + ldd_wl="\/$libdir\/lib" + ldd_bl="\/$libdir\/libc\." + /usr/bin/ldd "$1" | while read a b c d ; do + [ -n "$c" ] || continue + [[ $c =~ $ldd_wl ]] || continue + [[ $c =~ $ldd_bl ]] && continue + echo $c + done + } + else + get_ldd_deps() { :; } + fi + cplibs=`for i in /$libdir/libresolv.so.* /$libdir/libnss_*.so.* /$libdir/libpthread.so.0 /$libdir/libdl.so.2 + do + if [ -s "$i" ] ; then + echo "$i" + get_ldd_deps "$i" + fi + done | sort -u` + for i in $cplibs ; do + if [ -s "$i" ]; then + cp -pL "$i" "/var/lib/dhcp/$libdir/" || + { ocf_log err "could not copy $i to chroot jail"; return $OCF_ERR_GENERIC; } + fi + done + + return $OCF_SUCCESS +} + +# Start +dhcpd_start() { + # Lets make sure we are not already running. + if dhcpd_monitor; then + ocf_log info "dhcpd already running" + return $OCF_SUCCESS + fi + + dhcpd_initialize_chroot || + { ocf_log err "Could not fully initialize the chroot environment." ; return $OCF_ERR_INSTALLED; } + dhcpd_validate_all || exit + + ## If there is a pid file containing a pid, the machine might have crashed. pid files in + ## /var/run are always cleaned up at boot time, but this is not the case for the pid file in + ## the chroot jail. Therefore, an old pid file may exist. This is only a problem if it + ## incidentally contains the pid of a running process. If this process is not a 'dhcpd', + ## we remove the pid. (dhcpd itself only checks whether the pid is alive or not.) + + ocf_log info "Starting dhcpd [chroot] service." + test -e "$OCF_RESKEY_chrooted_path/$OCF_RESKEY_pid" && + rm -f $OCF_RESKEY_chrooted_path/$OCF_RESKEY_pid + + DHCPD_ARGS="-chroot $OCF_RESKEY_chrooted_path -lf $OCF_RESKEY_leases" + + if [ -n "$OCF_RESKEY_user" ]; then + DHCPD_ARGS="$DHCPD_ARGS -user $OCF_RESKEY_user" + fi + if [ -n "$OCF_RESKEY_group" ]; then + DHCPD_ARGS="$DHCPD_ARGS -group $OCF_RESKEY_group" + fi + + ocf_run $OCF_RESKEY_binary -cf $OCF_RESKEY_config $DHCPD_ARGS -pf $OCF_RESKEY_pid $OCF_RESKEY_interface || + return $OCF_ERR_INSTALLED + + while ! dhcpd_monitor; do + sleep .1 + ocf_log info "waiting for dhcpd to start" + return $OCF_SUCCESS + done + + ocf_log info "dhcpd [chrooted] has started." + + return $OCF_SUCCESS +} + +# Stop +dhcpd_stop () { + local timeout + local timewait + local rc + + dhcpd_monitor + rc=$? + + case "$rc" in + "$OCF_SUCCESS") + # Currently running, and is expected behaviour. + ;; + "$OCF_NOT_RUNNING") + # Currently not running, therefore nothing to do. + ocf_log info "dhcpd already stopped" + return $OCF_SUCCESS + ;; + esac + + kill `cat $OCF_RESKEY_chrooted_path/$OCF_RESKEY_pid` + + # Allow 2/3 of the action timeout for the orderly shutdown + # (The origin unit is ms, hence the conversion) + timewait=$((OCF_RESKEY_CRM_meta_timeout/1500)) + + sleep 0.1; timeout=0 # Sleep here for .1 sec to let dhcpd finish. + while dhcpd_monitor ; do + if [ $timeout -ge $timewait ]; then + break + else + sleep 1 + timeout=`expr $timeout + 1` + fi + done + + #If still up + if dhcpd_monitor 2>&1; then + ocf_log err "dhcpd is still up! Trying kill -s KILL" + kill -s SIGKILL `cat $OCF_RESKEY_chrooted_path/$OCF_RESKEY_pid` + fi + + # If we are running a dhcp server v4 or higher, unmount the proc partition. + if [ $DHCP_VERSION_MAJOR -ge 4 ] ; then + umount $OCF_RESKEY_chrooted_path/proc > /dev/null 2>&1 + fi + + rm -f $OCF_RESKEY_chrooted_path/$OCF_RESKEY_pid + ocf_log info "dhcpd stopped" + return $OCF_SUCCESS +} + +# Make sure meta-data and usage always succeed +case $__OCF_ACTION in +meta-data) dhcpd_meta_data + exit $OCF_SUCCESS + ;; +validate-all) dhcpd_validate_all + exit $OCF_SUCCESS + ;; +usage|help) dhcpd_usage + exit $OCF_SUCCESS + ;; +esac + +# Translate each action into the appropriate function call +case $__OCF_ACTION in +start) dhcpd_start;; +stop) dhcpd_stop;; +monitor) dhcpd_monitor;; +*) dhcpd_usage + exit $OCF_ERR_UNIMPLEMENTED + ;; +esac