[Pkg-samba-maint] [SCM] CTDB branch, upstream-sid, updated. upstream/2.1-1-geee2fde

Mathieu Parent math.parent at gmail.com
Thu Jun 6 20:20:00 UTC 2013


The following commit has been merged in the upstream-sid branch:
commit eee2fdef6a3aa1cd43f0f6f9680f352f1c12a1e9
Author: Mathieu Parent <math.parent at gmail.com>
Date:   Thu Jun 6 21:06:15 2013 +0200

    Imported Upstream version 2.2+debian0

diff --git a/.gitignore b/.gitignore
index 6a71e4d..a76dc38 100644
--- a/.gitignore
+++ b/.gitignore
@@ -28,4 +28,5 @@ tests/takeover/ctdb_takeover.pyc
 tests/eventscripts/var
 tests/eventscripts/etc/iproute2
 tests/eventscripts/etc-ctdb/policy_routing
-include/version.h
+include/ctdb_version.h
+packaging/RPM/ctdb.spec
diff --git a/Makefile.in b/Makefile.in
index fef2e45..bfeccf8 100755
--- a/Makefile.in
+++ b/Makefile.in
@@ -42,19 +42,25 @@ TDB_LIBS = @TDB_LIBS@
 TDB_CFLAGS = @TDB_CFLAGS@
 TDB_OBJ = @TDB_OBJ@
 
+REPLACE_OBJ = @LIBREPLACEOBJ@
+
 SOCKET_WRAPPER_OBJ = @SOCKET_WRAPPER_OBJS@
 
 PMDA_LIBS = -lpcp -lpcp_pmda
 PMDA_INSTALL = @CTDB_PMDA_INSTALL@
-PMDA_DEST_DIR = /var/lib/pcp/pmdas
+PMDA_DEST_DIR = /var/lib/pcp/pmdas/ctdb
+
+ifeq ($(CC),gcc)
+EXTRA_CFLAGS=-Wno-format-zero-length -fPIC
+endif
 
 CFLAGS=@CPPFLAGS@ -g -I$(srcdir)/include -Iinclude -Ilib -Ilib/util -I$(srcdir) \
        $(TALLOC_CFLAGS) $(TEVENT_CFLAGS) $(TDB_CFLAGS) -I at libreplacedir@ \
 	-DVARDIR=\"$(localstatedir)\" -DETCDIR=\"$(etcdir)\" \
-	-DLOGDIR=\"$(logdir)\" \
+	-DLOGDIR=\"$(logdir)\" -DBINDIR=\"$(bindir)\" \
 	-DSOCKPATH=\"$(sockpath)\" \
-	-DUSE_MMAP=1 -DTEVENT_DEPRECATED_QUIET=1 @CFLAGS@ -Wno-format-zero-length $(POPT_CFLAGS) \
-	-fPIC
+	-DUSE_MMAP=1 -DTEVENT_DEPRECATED_QUIET=1 @CFLAGS@ $(POPT_CFLAGS) \
+	$(EXTRA_CFLAGS)
 
 LDSHFLAGS=-fPIC -shared
 #LDSHFLAGS=-fPIC -shared -Wl,-Bsymbolic -Wl,-z,relo -Wl,-Bsymbolic-funtions -Wl,--as-needed -Wl,-z,defs
@@ -63,7 +69,7 @@ SHLD=${CC} ${CFLAGS} ${LDSHFLAGS} -o $@
 LIB_FLAGS=@LDFLAGS@ -Llib @LIBS@ $(POPT_LIBS) $(TALLOC_LIBS) $(TEVENT_LIBS) $(TDB_LIBS) \
 		  @INFINIBAND_LIBS@ @CTDB_PCAP_LDFLAGS@
 
-CTDB_VERSION_H = include/version.h
+CTDB_VERSION_H = include/ctdb_version.h
 
 UTIL_OBJ = lib/util/idtree.o lib/util/db_wrap.o lib/util/strlist.o lib/util/util.o \
 	lib/util/util_time.o lib/util/util_file.o lib/util/fault.o lib/util/substitute.o \
@@ -72,7 +78,7 @@ UTIL_OBJ = lib/util/idtree.o lib/util/db_wrap.o lib/util/strlist.o lib/util/util
 CTDB_COMMON_OBJ =  common/ctdb_io.o common/ctdb_util.o \
 	common/ctdb_ltdb.o common/ctdb_message.o common/cmdline.o  \
 	lib/util/debug.o common/rb_tree.o @CTDB_SYSTEM_OBJ@ common/system_common.o \
-	common/ctdb_logging.c common/ctdb_fork.o
+	common/ctdb_logging.o common/ctdb_fork.o
 
 CTDB_LIB_OBJ = libctdb/ctdb.o libctdb/io_elem.o libctdb/local_tdb.o \
 	libctdb/messages.o libctdb/sync.o libctdb/control.o \
@@ -80,9 +86,11 @@ CTDB_LIB_OBJ = libctdb/ctdb.o libctdb/io_elem.o libctdb/local_tdb.o \
 
 CTDB_TCP_OBJ = tcp/tcp_connect.o tcp/tcp_io.o tcp/tcp_init.o
 
+CTDB_EXTERNAL_OBJ = $(POPT_OBJ) $(TALLOC_OBJ) $(TDB_OBJ) \
+	$(REPLACE_OBJ) $(EXTRA_OBJ) $(TEVENT_OBJ) $(SOCKET_WRAPPER_OBJ)
+
 CTDB_CLIENT_OBJ = client/ctdb_client.o \
-	$(CTDB_COMMON_OBJ) $(POPT_OBJ) $(UTIL_OBJ) $(TALLOC_OBJ) $(TDB_OBJ) \
-	@LIBREPLACEOBJ@ $(EXTRA_OBJ) $(TEVENT_OBJ) $(SOCKET_WRAPPER_OBJ)
+	$(CTDB_COMMON_OBJ) $(UTIL_OBJ) $(CTDB_EXTERNAL_OBJ)
 
 CTDB_SERVER_OBJ = server/ctdbd.o server/ctdb_daemon.o \
 	server/ctdb_recoverd.o server/ctdb_recover.o server/ctdb_freeze.o \
@@ -104,9 +112,11 @@ TEST_BINS=tests/bin/ctdb_bench tests/bin/ctdb_fetch tests/bin/ctdb_fetch_one \
 	tests/bin/ctdb_takeover_tests tests/bin/ctdb_update_record \
 	tests/bin/ctdb_update_record_persistent \
 	tests/bin/ctdb_tool_libctdb tests/bin/ctdb_tool_stubby \
+	tests/bin/ctdb_porting_tests \
 	@INFINIBAND_BINS@
 
-BINS = bin/ctdb @CTDB_SCSI_IO@ bin/smnotify bin/ping_pong bin/ltdbtool @CTDB_PMDA@
+BINS = bin/ctdb @CTDB_SCSI_IO@ bin/smnotify bin/ping_pong bin/ltdbtool \
+       bin/ctdb_lock_helper @CTDB_PMDA@
 
 SBINS = bin/ctdbd
 
@@ -173,7 +183,11 @@ bin/ctdb: $(CTDB_CLIENT_OBJ) tools/ctdb.o tools/ctdb_vacuum.o libctdb/libctdb.a
 
 bin/ltdbtool: tools/ltdbtool.o $(TDB_OBJ)
 	@echo Linking $@
-	@$(CC) $(CFLAGS) -o $@ $+ $(TDB_LIBS)
+	@$(CC) $(CFLAGS) -o $@ $+ $(TDB_LIBS) $(LIB_FLAGS)
+
+bin/ctdb_lock_helper: server/ctdb_lock_helper.o lib/util/util_file.o $(CTDB_EXTERNAL_OBJ)
+	@echo Linking $@
+	@$(CC) $(CFLAGS) -o $@ server/ctdb_lock_helper.o lib/util/util_file.o $(CTDB_EXTERNAL_OBJ) $(TDB_LIBS) $(LIB_FLAGS)
 
 bin/smnotify: utils/smnotify/gen_xdr.o utils/smnotify/gen_smnotify.o utils/smnotify/smnotify.o $(POPT_OBJ)
 	@echo Linking $@
@@ -195,7 +209,7 @@ utils/smnotify/gen_smnotify.c: utils/smnotify/smnotify.x utils/smnotify/smnotify
 
 bin/ping_pong: utils/ping_pong/ping_pong.o
 	@echo Linking $@
-	@$(CC) $(CFLAGS) -o $@ utils/ping_pong/ping_pong.o
+	@$(CC) $(CFLAGS) -o $@ utils/ping_pong/ping_pong.o $(LIB_FLAGS)
 
 bin/pmdactdb: $(CTDB_CLIENT_OBJ) utils/pmda/pmda_ctdb.o
 	@echo Linking $@
@@ -217,13 +231,13 @@ tests/bin/ctdb_fetch_one: $(CTDB_CLIENT_OBJ) tests/src/ctdb_fetch_one.o
 	@echo Linking $@
 	@$(CC) $(CFLAGS) -o $@ tests/src/ctdb_fetch_one.o $(CTDB_CLIENT_OBJ) $(LIB_FLAGS)
 
-tests/bin/ctdb_fetch_lock_once: libctdb/libctdb.a tests/src/ctdb_fetch_lock_once.o 
+tests/bin/ctdb_fetch_lock_once: libctdb/libctdb.a tests/src/ctdb_fetch_lock_once.o $(CTDB_EXTERNAL_OBJ)
 	@echo Linking $@
-	@$(CC) $(CFLAGS) -o $@ tests/src/ctdb_fetch_lock_once.o $(TDB_OBJ) $(POPT_OBJ) libctdb/libctdb.a $(LIB_FLAGS)
+	@$(CC) $(CFLAGS) -o $@ tests/src/ctdb_fetch_lock_once.o $(CTDB_EXTERNAL_OBJ) libctdb/libctdb.a $(LIB_FLAGS)
 
-tests/bin/ctdb_fetch_readonly_once: libctdb/libctdb.a tests/src/ctdb_fetch_readonly_once.o
+tests/bin/ctdb_fetch_readonly_once: libctdb/libctdb.a tests/src/ctdb_fetch_readonly_once.o $(CTDB_EXTERNAL_OBJ)
 	@echo Linking $@
-	@$(CC) $(CFLAGS) -o $@ tests/src/ctdb_fetch_readonly_once.o $(TDB_OBJ) $(POPT_OBJ) libctdb/libctdb.a $(LIB_FLAGS)
+	@$(CC) $(CFLAGS) -o $@ tests/src/ctdb_fetch_readonly_once.o $(CTDB_EXTERNAL_OBJ) libctdb/libctdb.a $(LIB_FLAGS)
 
 tests/bin/ctdb_fetch_readonly_loop: $(CTDB_CLIENT_OBJ) tests/src/ctdb_fetch_readonly_loop.o
 	@echo Linking $@
@@ -233,31 +247,35 @@ tests/bin/ctdb_trackingdb_test: $(CTDB_CLIENT_OBJ) tests/src/ctdb_trackingdb_tes
 	@echo Linking $@
 	@$(CC) $(CFLAGS) -o $@ tests/src/ctdb_trackingdb_test.o $(CTDB_CLIENT_OBJ) $(LIB_FLAGS)
 
-tests/bin/ctdb_update_record: $(CTDB_CLIENT_OBJ) tests/src/ctdb_update_record.o 
+tests/bin/ctdb_update_record: $(CTDB_CLIENT_OBJ) tests/src/ctdb_update_record.o
 	@echo Linking $@
 	@$(CC) $(CFLAGS) -o $@ tests/src/ctdb_update_record.o $(CTDB_CLIENT_OBJ) $(LIB_FLAGS)
 
-tests/bin/ctdb_update_record_persistent: $(CTDB_CLIENT_OBJ) tests/src/ctdb_update_record_persistent.o 
+tests/bin/ctdb_update_record_persistent: $(CTDB_CLIENT_OBJ) tests/src/ctdb_update_record_persistent.o
 	@echo Linking $@
 	@$(CC) $(CFLAGS) -o $@ tests/src/ctdb_update_record_persistent.o $(CTDB_CLIENT_OBJ) $(LIB_FLAGS)
 
-tests/bin/ctdb_store: $(CTDB_CLIENT_OBJ) tests/src/ctdb_store.o 
+tests/bin/ctdb_store: $(CTDB_CLIENT_OBJ) tests/src/ctdb_store.o
 	@echo Linking $@
 	@$(CC) $(CFLAGS) -o $@ tests/src/ctdb_store.o $(CTDB_CLIENT_OBJ) $(LIB_FLAGS)
 
-tests/bin/ctdb_traverse: $(CTDB_CLIENT_OBJ) tests/src/ctdb_traverse.o 
+tests/bin/ctdb_traverse: $(CTDB_CLIENT_OBJ) tests/src/ctdb_traverse.o
 	@echo Linking $@
 	@$(CC) $(CFLAGS) -o $@ tests/src/ctdb_traverse.o $(CTDB_CLIENT_OBJ) $(LIB_FLAGS)
 
-tests/bin/ctdb_randrec: $(CTDB_CLIENT_OBJ) tests/src/ctdb_randrec.o 
+tests/bin/ctdb_randrec: $(CTDB_CLIENT_OBJ) tests/src/ctdb_randrec.o
 	@echo Linking $@
 	@$(CC) $(CFLAGS) -o $@ tests/src/ctdb_randrec.o $(CTDB_CLIENT_OBJ) $(LIB_FLAGS)
 
-tests/bin/ctdb_persistent: $(CTDB_CLIENT_OBJ) tests/src/ctdb_persistent.o 
+tests/bin/ctdb_persistent: $(CTDB_CLIENT_OBJ) tests/src/ctdb_persistent.o
 	@echo Linking $@
 	@$(CC) $(CFLAGS) -o $@ tests/src/ctdb_persistent.o $(CTDB_CLIENT_OBJ) $(LIB_FLAGS)
 
-tests/bin/ctdb_transaction: $(CTDB_CLIENT_OBJ) tests/src/ctdb_transaction.o 
+tests/bin/ctdb_porting_tests: $(CTDB_CLIENT_OBJ) tests/src/ctdb_porting_tests.o
+	@echo Linking $@
+	@$(CC) $(CFLAGS) -o $@ tests/src/ctdb_porting_tests.o $(CTDB_CLIENT_OBJ) $(LIB_FLAGS)
+
+tests/bin/ctdb_transaction: $(CTDB_CLIENT_OBJ) tests/src/ctdb_transaction.o
 	@echo Linking $@
 	@$(CC) $(CFLAGS) -o $@ tests/src/ctdb_transaction.o $(CTDB_CLIENT_OBJ) $(LIB_FLAGS)
 
@@ -267,7 +285,7 @@ CTDBD_TEST_C = $(CTDB_SERVER_MOST_OBJ:.o=.c) tests/src/ctdbd_test.c
 CTDB_TEST_C = $(CTDB_CLIENT_OBJ:.o=.c) tools/ctdb.c tools/ctdb_vacuum.c  tests/src/ctdb_test.c
 
 CTDB_TEST_OBJ =  $(TALLOC_OBJ) $(TDB_OBJ) \
-	@CTDB_SYSTEM_OBJ@ @LIBREPLACEOBJ@ $(EXTRA_OBJ) $(TEVENT_OBJ) $(SOCKET_WRAPPER_OBJ)
+	@CTDB_SYSTEM_OBJ@ $(REPLACE_OBJ) $(EXTRA_OBJ) $(TEVENT_OBJ) $(SOCKET_WRAPPER_OBJ)
 
 tests/src/ctdb_takeover_tests.o: tests/src/ctdb_takeover_tests.c $(CTDBD_TEST_C)
 
@@ -312,6 +330,9 @@ install: all manpages $(PMDA_INSTALL)
 	mkdir -p $(DESTDIR)$(includedir)
 	mkdir -p $(DESTDIR)$(etcdir)/ctdb
 	mkdir -p $(DESTDIR)$(etcdir)/ctdb/events.d
+	mkdir -p $(DESTDIR)$(etcdir)/ctdb/nfs-rpc-checks.d
+	mkdir -p $(DESTDIR)$(etcdir)/sudoers.d/
+	mkdir -p $(DESTDIR)$(etcdir)/ctdb/notify.d
 	mkdir -p $(DESTDIR)$(docdir)/ctdb
 	${INSTALLCMD} -m 644 ctdb.pc $(DESTDIR)$(libdir)/pkgconfig
 	${INSTALLCMD} -m 755 bin/ctdb $(DESTDIR)$(bindir)
@@ -319,12 +340,14 @@ install: all manpages $(PMDA_INSTALL)
 	${INSTALLCMD} -m 755 bin/smnotify $(DESTDIR)$(bindir)
 	$(INSTALLCMD) -m 755 bin/ping_pong $(DESTDIR)$(bindir)
 	$(INSTALLCMD) -m 755 bin/ltdbtool $(DESTDIR)$(bindir)
+	$(INSTALLCMD) -m 755 bin/ctdb_lock_helper $(DESTDIR)$(bindir)
 	$(INSTALLCMD) -m 755 libctdb/libctdb.a $(DESTDIR)$(libdir)
 	${INSTALLCMD} -m 644 include/ctdb.h $(DESTDIR)$(includedir)
 	${INSTALLCMD} -m 644 include/ctdb_client.h $(DESTDIR)$(includedir)
 	${INSTALLCMD} -m 644 include/ctdb_protocol.h $(DESTDIR)$(includedir)
 	${INSTALLCMD} -m 644 include/ctdb_private.h $(DESTDIR)$(includedir) # for samba3
 	${INSTALLCMD} -m 644 include/ctdb_typesafe_cb.h $(DESTDIR)$(includedir)
+	${INSTALLCMD} -m 440 config/ctdb.sudoers $(DESTDIR)$(etcdir)/sudoers.d/ctdb
 	${INSTALLCMD} -m 644 config/functions $(DESTDIR)$(etcdir)/ctdb
 	${INSTALLCMD} -m 755 config/statd-callout $(DESTDIR)$(etcdir)/ctdb
 	${INSTALLCMD} -m 644 README $(DESTDIR)$(docdir)/ctdb/README
@@ -349,6 +372,11 @@ install: all manpages $(PMDA_INSTALL)
 	${INSTALLCMD} -m 755 config/events.d/62.cnfs $(DESTDIR)$(etcdir)/ctdb/events.d
 	${INSTALLCMD} -m 755 config/events.d/70.iscsi $(DESTDIR)$(etcdir)/ctdb/events.d
 	${INSTALLCMD} -m 755 config/events.d/91.lvs $(DESTDIR)$(etcdir)/ctdb/events.d
+	${INSTALLCMD} -m 644 config/nfs-rpc-checks.d/10.statd.check $(DESTDIR)$(etcdir)/ctdb/nfs-rpc-checks.d/
+	${INSTALLCMD} -m 644 config/nfs-rpc-checks.d/20.nfsd.check $(DESTDIR)$(etcdir)/ctdb/nfs-rpc-checks.d/
+	${INSTALLCMD} -m 644 config/nfs-rpc-checks.d/30.lockd.check $(DESTDIR)$(etcdir)/ctdb/nfs-rpc-checks.d/
+	${INSTALLCMD} -m 644 config/nfs-rpc-checks.d/40.mountd.check $(DESTDIR)$(etcdir)/ctdb/nfs-rpc-checks.d/
+	${INSTALLCMD} -m 644 config/nfs-rpc-checks.d/50.rquotad.check $(DESTDIR)$(etcdir)/ctdb/nfs-rpc-checks.d/
 	${INSTALLCMD} -m 755 tools/ctdb_diagnostics $(DESTDIR)$(bindir)
 	${INSTALLCMD} -m 755 tools/onnode $(DESTDIR)$(bindir)
 	if [ -f doc/ctdb.1 ];then ${INSTALLCMD} -d $(DESTDIR)$(mandir)/man1; fi
@@ -363,15 +391,16 @@ install: all manpages $(PMDA_INSTALL)
 	if [ -f doc/ltdbtool.1.html ];then ${INSTALLCMD} -m 644 doc/ltdbtool.1.html $(DESTDIR)$(docdir)/ctdb; fi
 	if [ -f doc/ping_pong.1.html ];then ${INSTALLCMD} -m 644 doc/ping_pong.1.html $(DESTDIR)$(docdir)/ctdb; fi
 	if [ ! -f $(DESTDIR)$(etcdir)/ctdb/notify.sh ];then ${INSTALLCMD} -m 755 config/notify.sh $(DESTDIR)$(etcdir)/ctdb; fi
+	if [ ! -f $(DESTDIR)$(etcdir)/ctdb/notify.d/README ];then ${INSTALLCMD} -m 755 config/notify.d.README $(DESTDIR)$(etcdir)/ctdb/notify.d/README ; fi
 	${INSTALLCMD} -m 755 config/debug-hung-script.sh $(DESTDIR)$(etcdir)/ctdb
 	if [ ! -f $(DESTDIR)$(etcdir)/ctdb/ctdb-crash-cleanup.sh ];then ${INSTALLCMD} -m 755 config/ctdb-crash-cleanup.sh $(DESTDIR)$(etcdir)/ctdb; fi
 	if [ ! -f $(DESTDIR)$(etcdir)/ctdb/gcore_trace.sh ];then ${INSTALLCMD} -m 755 config/gcore_trace.sh $(DESTDIR)$(etcdir)/ctdb; fi
 
 install_pmda:
-	$(INSTALLCMD) -m 755 -d $(PMDA_DEST_DIR)
-	$(INSTALLCMD) -m 755 pmda/Install pmda/Remove $(PMDA_DEST_DIR)
-	$(INSTALLCMD) -m 644 pmda/pmns pmda/domain.h pmda/help pmda/README $(PMDA_DEST_DIR)
-	$(INSTALLCMD) -m 755 bin/pmdactdb $(PMDA_DEST_DIR)
+	$(INSTALLCMD) -m 755 -d $(DESTDIR)$(PMDA_DEST_DIR)
+	$(INSTALLCMD) -m 755 utils/pmda/Install utils/pmda/Remove $(DESTDIR)$(PMDA_DEST_DIR)
+	$(INSTALLCMD) -m 644 utils/pmda/pmns utils/pmda/domain.h utils/pmda/help utils/pmda/README $(DESTDIR)$(PMDA_DEST_DIR)
+	$(INSTALLCMD) -m 755 bin/pmdactdb $(DESTDIR)$(PMDA_DEST_DIR)
 
 # Should use $(datarootdir) but older autoconfs don't do this.  :-(
 install_tests: all
diff --git a/NEWS b/NEWS
new file mode 100644
index 0000000..b4a6169
--- /dev/null
+++ b/NEWS
@@ -0,0 +1,65 @@
+Changes in CTDB 2.2
+===================
+
+User-visible changes
+--------------------
+
+* The "stopped" event has been removed.
+
+  The "ipreallocated" event is now run when a node is stopped.  Use
+  this instead of "stopped".
+
+* New --pidfile option for ctdbd, used by initscript
+
+* The 60.nfs eventscript now uses configuration files in
+  /etc/ctdb/nfs-rpc-checks.d/ for timeouts and actions instead of
+  hardcoding them into the script.
+
+* Notification handler scripts can now be dropped into /etc/ctdb/notify.d/.
+
+* The NoIPTakeoverOnDisabled tunable has been renamed to
+  NoIPHostOnAllDisabled and now works properly when set on individual
+  nodes.
+
+* New ctdb subcommand "runstate" prints the current internal runstate.
+  Runstates are used for serialising startup.
+
+Important bug fixes
+-------------------
+
+* The Unix domain socket is now set to non-blocking after the
+  connection succeeds.  This avoids connections failing with EAGAIN
+  and not being retried.
+
+* Fetching from the log ringbuffer now succeeds if the buffer is full.
+
+* Fix a severe recovery bug that can lead to data corruption for SMB clients.
+
+* The statd-callout script now runs as root via sudo.
+
+* "ctdb delip" no longer fails if it is unable to move the IP.
+
+* A race in the ctdb tool's ipreallocate code was fixed.  This fixes
+  potential bugs in the "disable", "enable", "stop", "continue",
+  "ban", "unban", "ipreallocate" and "sync" commands.
+
+* The monitor cancellation code could sometimes hang indefinitely.
+  This could cause "ctdb stop" and "ctdb shutdown" to fail.
+
+Important internal changes
+--------------------------
+
+* The socket I/O handling has been optimised to improve performance.
+
+* IPs will not be assigned to nodes during CTDB initialisation.  They
+  will only be assigned to nodes that are in the "running" runstate.
+
+* Improved database locking code.  One improvement is to use a
+  standalone locking helper executable - the avoids creating many
+  forked copies of ctdbd and potentially running a node out of memory.
+
+* New control CTDB_CONTROL_IPREALLOCATED is now used to generate
+  "ipreallocated" events.
+
+* Message handlers are now indexed, providing a significant
+  performance improvement.
diff --git a/client/ctdb_client.c b/client/ctdb_client.c
index d7c3031..334d830 100644
--- a/client/ctdb_client.c
+++ b/client/ctdb_client.c
@@ -253,57 +253,32 @@ done:
 }
 
 /*
-  connect with exponential backoff, thanks Stevens
+  connect to a unix domain socket
 */
-#define CONNECT_MAXSLEEP 64
-static int ctdb_connect_retry(struct ctdb_context *ctdb)
+int ctdb_socket_connect(struct ctdb_context *ctdb)
 {
 	struct sockaddr_un addr;
-	int secs;
-	int ret = 0;
 
 	memset(&addr, 0, sizeof(addr));
 	addr.sun_family = AF_UNIX;
 	strncpy(addr.sun_path, ctdb->daemon.name, sizeof(addr.sun_path));
 
-	for (secs = 1; secs <= CONNECT_MAXSLEEP; secs *= 2) {
-		ret = connect(ctdb->daemon.sd, (struct sockaddr *)&addr,
-			      sizeof(addr));
-		if ((ret == 0) || (errno != EAGAIN)) {
-			break;
-		}
-
-		if (secs <= (CONNECT_MAXSLEEP / 2)) {
-			DEBUG(DEBUG_ERR,("connect failed: %s, retry in %d second(s)\n",
-					 strerror(errno), secs));
-			sleep(secs);
-		}
-	}
-
-	return ret;
-}
-
-/*
-  connect to a unix domain socket
-*/
-int ctdb_socket_connect(struct ctdb_context *ctdb)
-{
 	ctdb->daemon.sd = socket(AF_UNIX, SOCK_STREAM, 0);
 	if (ctdb->daemon.sd == -1) {
 		DEBUG(DEBUG_ERR,(__location__ " Failed to open client socket. Errno:%s(%d)\n", strerror(errno), errno));
 		return -1;
 	}
 
-	set_nonblocking(ctdb->daemon.sd);
-	set_close_on_exec(ctdb->daemon.sd);
-
-	if (ctdb_connect_retry(ctdb) == -1) {
-		DEBUG(DEBUG_ERR,(__location__ " Failed to connect client socket to daemon. Errno:%s(%d)\n", strerror(errno), errno));
+	if (connect(ctdb->daemon.sd, (struct sockaddr *)&addr, sizeof(addr)) == -1) {
 		close(ctdb->daemon.sd);
 		ctdb->daemon.sd = -1;
+		DEBUG(DEBUG_ERR,(__location__ " Failed to connect client socket to daemon. Errno:%s(%d)\n", strerror(errno), errno));
 		return -1;
 	}
 
+	set_nonblocking(ctdb->daemon.sd);
+	set_close_on_exec(ctdb->daemon.sd);
+	
 	ctdb->daemon.queue = ctdb_queue_setup(ctdb, ctdb, ctdb->daemon.sd, 
 					      CTDB_DS_ALIGNMENT, 
 					      ctdb_client_read_cb, ctdb, "to-ctdbd");
@@ -1165,6 +1140,17 @@ int ctdb_control(struct ctdb_context *ctdb, uint32_t destnode, uint64_t srvid,
 	state = ctdb_control_send(ctdb, destnode, srvid, opcode, 
 			flags, data, mem_ctx,
 			timeout, errormsg);
+
+	/* FIXME: Error conditions in ctdb_control_send return NULL without
+	 * setting errormsg.  So, there is no way to distinguish between sucess
+	 * and failure when CTDB_CTRL_FLAG_NOREPLY is set */
+	if (flags & CTDB_CTRL_FLAG_NOREPLY) {
+		if (status != NULL) {
+			*status = 0;
+		}
+		return 0;
+	}
+
 	return ctdb_control_recv(ctdb, state, mem_ctx, outdata, status, 
 			errormsg);
 }
@@ -1668,6 +1654,36 @@ int ctdb_ctrl_ping(struct ctdb_context *ctdb, uint32_t destnode)
 	return res;
 }
 
+int ctdb_ctrl_get_runstate(struct ctdb_context *ctdb, 
+			   struct timeval timeout, 
+			   uint32_t destnode,
+			   uint32_t *runstate)
+{
+	TDB_DATA outdata;
+	int32_t res;
+	int ret;
+
+	ret = ctdb_control(ctdb, destnode, 0, CTDB_CONTROL_GET_RUNSTATE, 0,
+			   tdb_null, ctdb, &outdata, &res, &timeout, NULL);
+	if (ret != 0 || res != 0) {
+		DEBUG(DEBUG_ERR,("ctdb_control for get_runstate failed\n"));
+		return ret != 0 ? ret : res;
+	}
+
+	if (outdata.dsize != sizeof(uint32_t)) {
+		DEBUG(DEBUG_ERR,("Invalid return data in get_runstate\n"));
+		talloc_free(outdata.dptr);
+		return -1;
+	}
+
+	if (runstate != NULL) {
+		*runstate = *(uint32_t *)outdata.dptr;
+	}
+	talloc_free(outdata.dptr);
+
+	return 0;
+}
+
 /*
   find the real path to a ltdb 
  */
@@ -2486,7 +2502,7 @@ int ctdb_ctrl_get_tunable(struct ctdb_context *ctdb,
 	talloc_free(data.dptr);
 	if (ret != 0 || res != 0) {
 		DEBUG(DEBUG_ERR,(__location__ " ctdb_control for get_tunable failed\n"));
-		return -1;
+		return ret != 0 ? ret : res;
 	}
 
 	if (outdata.dsize != sizeof(uint32_t)) {
@@ -3313,6 +3329,11 @@ static void async_callback(struct ctdb_client_control_state *state)
 			DEBUG(DEBUG_ERR,("Async operation failed with state %d, opcode:%u\n", state->state, data->opcode));
 		}
 		data->fail_count++;
+		if (state->state == CTDB_CONTROL_TIMEOUT) {
+			res = -ETIME;
+		} else {
+			res = -1;
+		}
 		if (data->fail_callback) {
 			data->fail_callback(ctdb, destnode, res, outdata,
 					data->callback_data);
@@ -3451,19 +3472,23 @@ uint32_t *list_of_vnnmap_nodes(struct ctdb_context *ctdb,
 	return nodes;
 }
 
-uint32_t *list_of_active_nodes(struct ctdb_context *ctdb,
-				struct ctdb_node_map *node_map,
-				TALLOC_CTX *mem_ctx,
-				bool include_self)
+/* Get list of nodes not including those with flags specified by mask.
+ * If exclude_pnn is not -1 then exclude that pnn from the list.
+ */
+uint32_t *list_of_nodes(struct ctdb_context *ctdb,
+			struct ctdb_node_map *node_map,
+			TALLOC_CTX *mem_ctx,
+			uint32_t mask,
+			int exclude_pnn)
 {
 	int i, j, num_nodes;
 	uint32_t *nodes;
 
 	for (i=num_nodes=0;i<node_map->num;i++) {
-		if (node_map->nodes[i].flags & NODE_FLAGS_INACTIVE) {
+		if (node_map->nodes[i].flags & mask) {
 			continue;
 		}
-		if (node_map->nodes[i].pnn == ctdb->pnn && !include_self) {
+		if (node_map->nodes[i].pnn == exclude_pnn) {
 			continue;
 		}
 		num_nodes++;
@@ -3473,10 +3498,10 @@ uint32_t *list_of_active_nodes(struct ctdb_context *ctdb,
 	CTDB_NO_MEMORY_FATAL(ctdb, nodes);
 
 	for (i=j=0;i<node_map->num;i++) {
-		if (node_map->nodes[i].flags & NODE_FLAGS_INACTIVE) {
+		if (node_map->nodes[i].flags & mask) {
 			continue;
 		}
-		if (node_map->nodes[i].pnn == ctdb->pnn && !include_self) {
+		if (node_map->nodes[i].pnn == exclude_pnn) {
 			continue;
 		}
 		nodes[j++] = node_map->nodes[i].pnn;
@@ -3485,38 +3510,21 @@ uint32_t *list_of_active_nodes(struct ctdb_context *ctdb,
 	return nodes;
 }
 
+uint32_t *list_of_active_nodes(struct ctdb_context *ctdb,
+				struct ctdb_node_map *node_map,
+				TALLOC_CTX *mem_ctx,
+				bool include_self)
+{
+	return list_of_nodes(ctdb, node_map, mem_ctx, NODE_FLAGS_INACTIVE,
+			     include_self ? -1 : ctdb->pnn);
+}
+
 uint32_t *list_of_active_nodes_except_pnn(struct ctdb_context *ctdb,
 				struct ctdb_node_map *node_map,
 				TALLOC_CTX *mem_ctx,
 				uint32_t pnn)
 {
-	int i, j, num_nodes;
-	uint32_t *nodes;
-
-	for (i=num_nodes=0;i<node_map->num;i++) {
-		if (node_map->nodes[i].flags & NODE_FLAGS_INACTIVE) {
-			continue;
-		}
-		if (node_map->nodes[i].pnn == pnn) {
-			continue;
-		}
-		num_nodes++;
-	} 
-
-	nodes = talloc_array(mem_ctx, uint32_t, num_nodes);
-	CTDB_NO_MEMORY_FATAL(ctdb, nodes);
-
-	for (i=j=0;i<node_map->num;i++) {
-		if (node_map->nodes[i].flags & NODE_FLAGS_INACTIVE) {
-			continue;
-		}
-		if (node_map->nodes[i].pnn == pnn) {
-			continue;
-		}
-		nodes[j++] = node_map->nodes[i].pnn;
-	} 
-
-	return nodes;
+	return list_of_nodes(ctdb, node_map, mem_ctx, NODE_FLAGS_INACTIVE, pnn);
 }
 
 uint32_t *list_of_connected_nodes(struct ctdb_context *ctdb,
@@ -3524,33 +3532,8 @@ uint32_t *list_of_connected_nodes(struct ctdb_context *ctdb,
 				TALLOC_CTX *mem_ctx,
 				bool include_self)
 {
-	int i, j, num_nodes;
-	uint32_t *nodes;
-
-	for (i=num_nodes=0;i<node_map->num;i++) {
-		if (node_map->nodes[i].flags & NODE_FLAGS_DISCONNECTED) {
-			continue;
-		}
-		if (node_map->nodes[i].pnn == ctdb->pnn && !include_self) {
-			continue;
-		}
-		num_nodes++;
-	} 
-
-	nodes = talloc_array(mem_ctx, uint32_t, num_nodes);
-	CTDB_NO_MEMORY_FATAL(ctdb, nodes);
-
-	for (i=j=0;i<node_map->num;i++) {
-		if (node_map->nodes[i].flags & NODE_FLAGS_DISCONNECTED) {
-			continue;
-		}
-		if (node_map->nodes[i].pnn == ctdb->pnn && !include_self) {
-			continue;
-		}
-		nodes[j++] = node_map->nodes[i].pnn;
-	} 
-
-	return nodes;
+	return list_of_nodes(ctdb, node_map, mem_ctx, NODE_FLAGS_DISCONNECTED,
+			     include_self ? -1 : ctdb->pnn);
 }
 
 /* 
diff --git a/common/ctdb_fork.c b/common/ctdb_fork.c
index 24534e6..d372ae0 100644
--- a/common/ctdb_fork.c
+++ b/common/ctdb_fork.c
@@ -23,11 +23,33 @@
 #include "../include/ctdb_private.h"
 #include "../common/rb_tree.h"
 
+static bool is_child = false;
+
+void ctdb_set_child_info(TALLOC_CTX *mem_ctx, const char *child_name_fmt, ...)
+{
+	is_child = true;
+	if (child_name_fmt != NULL) {
+		va_list ap;
+		char *t;
+
+		va_start(ap, child_name_fmt);
+		t = talloc_vasprintf(mem_ctx, child_name_fmt, ap);
+		debug_extra = talloc_asprintf(mem_ctx, "%s:", t);
+		talloc_free(t);
+		va_end(ap);
+	}
+}
+
+bool ctdb_is_child_process(void)
+{
+	return is_child;
+}
+
 /*
  * This function forks a child process and drops the realtime 
  * scheduler for the child process.
  */
-pid_t ctdb_fork(struct ctdb_context *ctdb)
+pid_t ctdb_fork_no_free_ringbuffer(struct ctdb_context *ctdb)
 {
 	pid_t pid;
 	char *process;
@@ -37,6 +59,8 @@ pid_t ctdb_fork(struct ctdb_context *ctdb)
 		return -1;
 	}
 	if (pid == 0) {
+		ctdb_set_child_info(ctdb, NULL);
+
 		/* Close the Unix Domain socket and the TCP socket.
 		 * This ensures that none of the child processes will
 		 * look like the main daemon when it is not running.
@@ -59,6 +83,7 @@ pid_t ctdb_fork(struct ctdb_context *ctdb)
 			ctdb_restore_scheduler(ctdb);
 		}
 		ctdb->can_send_controls = false;
+
 		return 0;
 	}
 
@@ -72,6 +97,17 @@ pid_t ctdb_fork(struct ctdb_context *ctdb)
 	return pid;
 }
 
+pid_t ctdb_fork(struct ctdb_context *ctdb)
+{
+	pid_t pid;
+
+	pid = ctdb_fork_no_free_ringbuffer(ctdb);
+	if (pid == 0) {
+		ctdb_log_ringbuffer_free();
+	}
+
+	return pid;
+}
 
 
 static void ctdb_sigchld_handler(struct tevent_context *ev,
diff --git a/common/ctdb_io.c b/common/ctdb_io.c
index 3ac1b63..4e592b9 100644
--- a/common/ctdb_io.c
+++ b/common/ctdb_io.c
@@ -30,9 +30,10 @@
 #include <stdarg.h>
 
 /* structures for packet queueing - see common/ctdb_io.c */
-struct ctdb_partial {
+struct ctdb_buffer {
 	uint8_t *data;
 	uint32_t length;
+	uint32_t size;
 };
 
 struct ctdb_queue_pkt {
@@ -44,7 +45,8 @@ struct ctdb_queue_pkt {
 
 struct ctdb_queue {
 	struct ctdb_context *ctdb;
-	struct ctdb_partial partial; /* partial input packet */
+	struct tevent_immediate *im;
+	struct ctdb_buffer buffer; /* input buffer */
 	struct ctdb_queue_pkt *out_queue, *out_queue_tail;
 	uint32_t out_queue_length;
 	struct fd_event *fde;
@@ -63,6 +65,75 @@ int ctdb_queue_length(struct ctdb_queue *queue)
 	return queue->out_queue_length;
 }
 
+static void queue_process(struct ctdb_queue *queue);
+
+static void queue_process_event(struct tevent_context *ev, struct tevent_immediate *im,
+				void *private_data)
+{
+	struct ctdb_queue *queue = talloc_get_type(private_data, struct ctdb_queue);
+
+	queue_process(queue);
+}
+
+/*
+ * This function is used to process data in queue buffer.
+ *
+ * Queue callback function can end up freeing the queue, there should not be a
+ * loop processing packets from queue buffer.  Instead set up a timed event for
+ * immediate run to process remaining packets from buffer.
+ */
+static void queue_process(struct ctdb_queue *queue)
+{
+	uint32_t pkt_size;
+	uint8_t *data;
+
+	if (queue->buffer.length < sizeof(pkt_size)) {
+		return;
+	}
+
+	pkt_size = *(uint32_t *)queue->buffer.data;
+	if (pkt_size == 0) {
+		DEBUG(DEBUG_CRIT, ("Invalid packet of length 0\n"));
+		goto failed;
+	}
+
+	if (queue->buffer.length < pkt_size) {
+		DEBUG(DEBUG_DEBUG, ("Partial packet data read\n"));
+		return;
+	}
+
+	/* Extract complete packet */
+	data = talloc_size(queue, pkt_size);
+	if (data == NULL) {
+		DEBUG(DEBUG_ERR, ("read error alloc failed for %u\n", pkt_size));
+		return;
+	}
+	memcpy(data, queue->buffer.data, pkt_size);
+
+	/* Shift packet out from buffer */
+	if (queue->buffer.length > pkt_size) {
+		memmove(queue->buffer.data,
+			queue->buffer.data + pkt_size,
+			queue->buffer.length - pkt_size);
+	}
+	queue->buffer.length -= pkt_size;
+
+	if (queue->buffer.length > 0) {
+		/* There is more data to be processed, schedule an event */
+		tevent_schedule_immediate(queue->im, queue->ctdb->ev,
+					  queue_process_event, queue);
+	}
+
+	/* It is the responsibility of the callback to free 'data' */
+	queue->callback(data, pkt_size, queue->private_data);
+	return;
+
+failed:
+	queue->callback(NULL, 0, queue->private_data);
+
+}
+
+
 /*
   called when an incoming connection is readable
   This function MUST be safe for reentry via the queue callback!
@@ -70,10 +141,6 @@ int ctdb_queue_length(struct ctdb_queue *queue)
 static void queue_io_read(struct ctdb_queue *queue)
 {
 	int num_ready = 0;
-	uint32_t sz_bytes_req;
-	uint32_t pkt_size;
-	uint32_t pkt_bytes_remaining;
-	uint32_t to_read;
 	ssize_t nread;
 	uint8_t *data;
 
@@ -91,77 +158,33 @@ static void queue_io_read(struct ctdb_queue *queue)
 		goto failed;
 	}
 
-	if (queue->partial.data == NULL) {
-		/* starting fresh, allocate buf for size bytes */
-		sz_bytes_req = sizeof(pkt_size);
-		queue->partial.data = talloc_size(queue, sz_bytes_req);
-		if (queue->partial.data == NULL) {
-			DEBUG(DEBUG_ERR,("read error alloc failed for %u\n",
-					 sz_bytes_req));
+	if (queue->buffer.data == NULL) {
+		/* starting fresh, allocate buf to read data */
+		queue->buffer.data = talloc_size(queue, num_ready);
+		if (queue->buffer.data == NULL) {
+			DEBUG(DEBUG_ERR, ("read error alloc failed for %u\n", num_ready));
 			goto failed;
 		}
-	} else if (queue->partial.length < sizeof(pkt_size)) {
-		/* yet to find out the packet length */
-		sz_bytes_req = sizeof(pkt_size) - queue->partial.length;
-	} else {
-		/* partial packet, length known, full buf allocated */
-		sz_bytes_req = 0;
-	}
-	data = queue->partial.data;
-
-	if (sz_bytes_req > 0) {
-		to_read = MIN(sz_bytes_req, num_ready);
-		nread = read(queue->fd, data + queue->partial.length,
-			     to_read);
-		if (nread <= 0) {
-			DEBUG(DEBUG_ERR,("read error nread=%d\n", (int)nread));
+		queue->buffer.size = num_ready;
+	} else if (queue->buffer.length + num_ready > queue->buffer.size) {
+		/* extending buffer */
+		data = talloc_realloc_size(queue, queue->buffer.data, queue->buffer.length + num_ready);
+		if (data == NULL) {
+			DEBUG(DEBUG_ERR, ("read error realloc failed for %u\n", queue->buffer.length + num_ready));
 			goto failed;
 		}
-		queue->partial.length += nread;
-
-		if (nread < sz_bytes_req) {
-			/* not enough to know the length */
-			DEBUG(DEBUG_DEBUG,("Partial packet length read\n"));
-			return;
-		}
-		/* size now known, allocate buffer for the full packet */
-		queue->partial.data = talloc_realloc_size(queue, data,
-							  *(uint32_t *)data);
-		if (queue->partial.data == NULL) {
-			DEBUG(DEBUG_ERR,("read error alloc failed for %u\n",
-					 *(uint32_t *)data));
-			goto failed;
-		}
-		data = queue->partial.data;
-		num_ready -= nread;
+		queue->buffer.data = data;
+		queue->buffer.size = queue->buffer.length + num_ready;
 	}
 
-	pkt_size = *(uint32_t *)data;
-	if (pkt_size == 0) {
-		DEBUG(DEBUG_CRIT,("Invalid packet of length 0\n"));
-		goto failed;
-	}
-
-	pkt_bytes_remaining = pkt_size - queue->partial.length;
-	to_read = MIN(pkt_bytes_remaining, num_ready);
-	nread = read(queue->fd, data + queue->partial.length,
-		     to_read);
+	nread = read(queue->fd, queue->buffer.data + queue->buffer.length, num_ready);
 	if (nread <= 0) {
-		DEBUG(DEBUG_ERR,("read error nread=%d\n",
-				 (int)nread));
+		DEBUG(DEBUG_ERR, ("read error nread=%d\n", (int)nread));
 		goto failed;
 	}
-	queue->partial.length += nread;
-
-	if (queue->partial.length < pkt_size) {
-		DEBUG(DEBUG_DEBUG,("Partial packet data read\n"));
-		return;
-	}
+	queue->buffer.length += nread;
 
-	queue->partial.data = NULL;
-	queue->partial.length = 0;
-	/* it is the responsibility of the callback to free 'data' */
-	queue->callback(data, pkt_size, queue->private_data);
+	queue_process(queue);
 	return;
 
 failed:
@@ -170,8 +193,8 @@ failed:
 
 
 /* used when an event triggers a dead queue */
-static void queue_dead(struct event_context *ev, struct timed_event *te, 
-		       struct timeval t, void *private_data)
+static void queue_dead(struct event_context *ev, struct tevent_immediate *im,
+		       void *private_data)
 {
 	struct ctdb_queue *queue = talloc_get_type(private_data, struct ctdb_queue);
 	queue->callback(NULL, 0, queue->private_data);
@@ -202,8 +225,8 @@ static void queue_io_write(struct ctdb_queue *queue)
 			talloc_free(queue->fde);
 			queue->fde = NULL;
 			queue->fd = -1;
-			event_add_timed(queue->ctdb->ev, queue, timeval_zero(), 
-					queue_dead, queue);
+			tevent_schedule_immediate(queue->im, queue->ctdb->ev,
+						  queue_dead, queue);
 			return;
 		}
 		if (n <= 0) return;
@@ -269,8 +292,8 @@ int ctdb_queue_send(struct ctdb_queue *queue, uint8_t *data, uint32_t length)
 			talloc_free(queue->fde);
 			queue->fde = NULL;
 			queue->fd = -1;
-			event_add_timed(queue->ctdb->ev, queue, timeval_zero(), 
-					queue_dead, queue);
+			tevent_schedule_immediate(queue->im, queue->ctdb->ev,
+						  queue_dead, queue);
 			/* yes, we report success, as the dead node is 
 			   handled via a separate event */
 			return 0;
@@ -354,6 +377,9 @@ int ctdb_queue_set_fd(struct ctdb_queue *queue, int fd)
 /* If someone sets up this pointer, they want to know if the queue is freed */
 static int queue_destructor(struct ctdb_queue *queue)
 {
+	TALLOC_FREE(queue->buffer.data);
+	queue->buffer.length = 0;
+	queue->buffer.size = 0;
 	if (queue->destroyed != NULL)
 		*queue->destroyed = true;
 	return 0;
@@ -364,7 +390,6 @@ static int queue_destructor(struct ctdb_queue *queue)
  */
 struct ctdb_queue *ctdb_queue_setup(struct ctdb_context *ctdb,
 				    TALLOC_CTX *mem_ctx, int fd, int alignment,
-				    
 				    ctdb_queue_cb_fn_t callback,
 				    void *private_data, const char *fmt, ...)
 {
@@ -378,6 +403,9 @@ struct ctdb_queue *ctdb_queue_setup(struct ctdb_context *ctdb,
 	va_end(ap);
 	CTDB_NO_MEMORY_NULL(ctdb, queue->name);
 
+	queue->im= tevent_create_immediate(queue);
+	CTDB_NO_MEMORY_NULL(ctdb, queue->im);
+
 	queue->ctdb = ctdb;
 	queue->fd = fd;
 	queue->alignment = alignment;
diff --git a/common/ctdb_logging.c b/common/ctdb_logging.c
index 09b1df2..408fda8 100644
--- a/common/ctdb_logging.c
+++ b/common/ctdb_logging.c
@@ -27,8 +27,8 @@ int log_ringbuf_size;
 
 #define MAX_LOG_SIZE 128
 
-static int first_entry;
-static int last_entry;
+static int first_entry = 0;
+static int ringbuf_count = 0;
 
 struct ctdb_log_entry {
 	int32_t level;
@@ -45,6 +45,7 @@ static struct ctdb_log_entry *log_entries;
 static void log_ringbuffer_v(const char *format, va_list ap)
 {
 	int ret;
+	int next_entry;
 
 	if (log_entries == NULL && log_ringbuf_size != 0) {
 		/* Hope this works. We cant log anything if it doesnt anyway */
@@ -54,25 +55,30 @@ static void log_ringbuffer_v(const char *format, va_list ap)
 		return;
 	}
 
-	log_entries[last_entry].message[0] = '\0';
+	next_entry = (first_entry + ringbuf_count) % log_ringbuf_size;
 
-	ret = vsnprintf(&log_entries[last_entry].message[0], MAX_LOG_SIZE, format, ap);
-	if (ret == -1) {
-		return;
+	if (ringbuf_count > 0 && first_entry == next_entry) {
+		first_entry = (first_entry + 1) % log_ringbuf_size;
 	}
 
-	log_entries[last_entry].level = this_log_level;
-	log_entries[last_entry].t = timeval_current();
+	log_entries[next_entry].message[0] = '\0';
 
-	last_entry++;
-	if (last_entry >= log_ringbuf_size) {
-		last_entry = 0;
+	ret = vsnprintf(&log_entries[next_entry].message[0], MAX_LOG_SIZE, format, ap);
+	if (ret == -1) {
+		return;
 	}
-	if (first_entry == last_entry) {
-		first_entry++;
+	/* Log messages longer than MAX_LOG_SIZE are truncated to MAX_LOG_SIZE-1
+	 * bytes.  In that case, add a newline.
+	 */
+	if (ret >= MAX_LOG_SIZE) {
+		log_entries[next_entry].message[MAX_LOG_SIZE-2] = '\n';
 	}
-	if (first_entry >= log_ringbuf_size) {
-		first_entry = 0;
+
+	log_entries[next_entry].level = this_log_level;
+	log_entries[next_entry].t = timeval_current();
+
+	if (ringbuf_count < log_ringbuf_size) {
+		ringbuf_count++;
 	}
 }
 
@@ -85,7 +91,14 @@ void log_ringbuffer(const char *format, ...)
 	va_end(ap);
 }
 
-
+void ctdb_log_ringbuffer_free(void)
+{
+	if (log_entries != NULL) {
+		free(log_entries);
+		log_entries = NULL;
+	}
+	log_ringbuf_size = 0;
+}
 
 void ctdb_collect_log(struct ctdb_context *ctdb, struct ctdb_get_log_addr *log_addr)
 {
@@ -93,8 +106,11 @@ void ctdb_collect_log(struct ctdb_context *ctdb, struct ctdb_get_log_addr *log_a
 	FILE *f;
 	long fsize;
 	int tmp_entry;
-	int count = 0;
-	DEBUG(DEBUG_ERR,("Marshalling log entries  first:%d last:%d\n", first_entry, last_entry));
+	struct tm *tm;
+	char tbuf[100];
+	int i;
+
+	DEBUG(DEBUG_ERR,("Marshalling %d log entries\n", ringbuf_count));
 
 	/* dump to a file, then send the file as a blob */
 	f = tmpfile();
@@ -103,20 +119,10 @@ void ctdb_collect_log(struct ctdb_context *ctdb, struct ctdb_get_log_addr *log_a
 		return;
 	}
 
-	tmp_entry = first_entry;
-	while (tmp_entry != last_entry) {
-		struct tm *tm;
-		char tbuf[100];
-
-		if (log_entries == NULL) {
-			break;
-		}
+	for (i=0; i<ringbuf_count; i++) {
+		tmp_entry = (first_entry + i) % log_ringbuf_size;
 
 		if (log_entries[tmp_entry].level > log_addr->level) {
-			tmp_entry++;
-			if (tmp_entry >= log_ringbuf_size) {
-				tmp_entry = 0;
-			}
 		 	continue;
 		}
 
@@ -124,12 +130,9 @@ void ctdb_collect_log(struct ctdb_context *ctdb, struct ctdb_get_log_addr *log_a
 		strftime(tbuf, sizeof(tbuf)-1,"%Y/%m/%d %H:%M:%S", tm);
 
 		if (log_entries[tmp_entry].message) {
-			count += fprintf(f, "%s:%s %s", tbuf, get_debug_by_level(log_entries[tmp_entry].level), log_entries[tmp_entry].message);
-		}
-
-		tmp_entry++;
-		if (tmp_entry >= log_ringbuf_size) {
-			tmp_entry = 0;
+			fprintf(f, "%s:%s %s", tbuf,
+				get_debug_by_level(log_entries[tmp_entry].level),
+				log_entries[tmp_entry].message);
 		}
 	}
 
@@ -156,7 +159,7 @@ int32_t ctdb_control_get_log(struct ctdb_context *ctdb, TDB_DATA addr)
 	/* spawn a child process to marshall the huge log blob and send it back
 	   to the ctdb tool using a MESSAGE
 	*/
-	child = ctdb_fork(ctdb);
+	child = ctdb_fork_no_free_ringbuffer(ctdb);
 	if (child == (pid_t)-1) {
 		DEBUG(DEBUG_ERR,("Failed to fork a log collector child\n"));
 		return -1;
@@ -177,7 +180,7 @@ int32_t ctdb_control_get_log(struct ctdb_context *ctdb, TDB_DATA addr)
 void ctdb_clear_log(struct ctdb_context *ctdb)
 {
 	first_entry = 0;
-	last_entry  = 0;
+	ringbuf_count  = 0;
 }
 
 int32_t ctdb_control_clear_log(struct ctdb_context *ctdb)
diff --git a/common/ctdb_message.c b/common/ctdb_message.c
index 5fc7b22..b0d2ea0 100644
--- a/common/ctdb_message.c
+++ b/common/ctdb_message.c
@@ -2,6 +2,7 @@
    ctdb_message protocol code
 
    Copyright (C) Andrew Tridgell  2007
+   Copyright (C) Amitay Isaacs  2013
 
    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
@@ -27,16 +28,123 @@
 #include "../include/ctdb_private.h"
 #include "lib/util/dlinklist.h"
 
+static int message_list_db_init(struct ctdb_context *ctdb)
+{
+	ctdb->message_list_indexdb = tdb_open("messagedb", 8192,
+					      TDB_INTERNAL|
+					      TDB_INCOMPATIBLE_HASH|
+					      TDB_DISALLOW_NESTING,
+					      O_RDWR|O_CREAT, 0);
+	if (ctdb->message_list_indexdb == NULL) {
+		DEBUG(DEBUG_ERR, ("Failed to create message list indexdb\n"));
+		return -1;
+	}
+
+	return 0;
+}
+
+static int message_list_db_add(struct ctdb_context *ctdb, uint64_t srvid,
+			       struct ctdb_message_list_header *h)
+{
+	int ret;
+	TDB_DATA key, data;
+
+	if (ctdb->message_list_indexdb == NULL) {
+		ret = message_list_db_init(ctdb);
+		if (ret < 0) {
+			return -1;
+		}
+	}
+
+	key.dptr = (uint8_t *)&srvid;
+	key.dsize = sizeof(uint64_t);
+
+	data.dptr = (uint8_t *)&h;
+	data.dsize = sizeof(struct ctdb_message_list_header *);
+
+	ret = tdb_store(ctdb->message_list_indexdb, key, data, TDB_INSERT);
+	if (ret < 0) {
+		DEBUG(DEBUG_ERR, ("Failed to add message list handler (%s)\n",
+				  tdb_errorstr(ctdb->message_list_indexdb)));
+		return -1;
+	}
+
+	return 0;
+}
+
+static int message_list_db_delete(struct ctdb_context *ctdb, uint64_t srvid)
+{
+	int ret;
+	TDB_DATA key;
+
+	if (ctdb->message_list_indexdb == NULL) {
+		return -1;
+	}
+
+	key.dptr = (uint8_t *)&srvid;
+	key.dsize = sizeof(uint64_t);
+
+	ret = tdb_delete(ctdb->message_list_indexdb, key);
+	if (ret < 0) {
+		DEBUG(DEBUG_ERR, ("Failed to delete message list handler (%s)\n",
+				  tdb_errorstr(ctdb->message_list_indexdb)));
+		return -1;
+	}
+
+	return 0;
+}
+
+static int message_list_db_fetch_parser(TDB_DATA key, TDB_DATA data,
+					void *private_data)
+{
+	struct ctdb_message_list_header **h =
+		(struct ctdb_message_list_header **)private_data;
+
+	if (data.dsize != sizeof(struct ctdb_message_list_header *)) {
+		return -1;
+	}
+
+	*h = *(struct ctdb_message_list_header **)data.dptr;
+	return 0;
+}
+
+static int message_list_db_fetch(struct ctdb_context *ctdb, uint64_t srvid,
+				 struct ctdb_message_list_header **h)
+{
+	TDB_DATA key;
+
+	if (ctdb->message_list_indexdb == NULL) {
+		return -1;
+	}
+
+	key.dptr = (uint8_t *)&srvid;
+	key.dsize = sizeof(uint64_t);
+
+	return tdb_parse_record(ctdb->message_list_indexdb, key,
+				message_list_db_fetch_parser, h);
+}
+
 /*
   this dispatches the messages to the registered ctdb message handler
 */
 int ctdb_dispatch_message(struct ctdb_context *ctdb, uint64_t srvid, TDB_DATA data)
 {
-	struct ctdb_message_list *ml;
+	struct ctdb_message_list_header *h;
+	struct ctdb_message_list *m;
+	uint64_t srvid_all = CTDB_SRVID_ALL;
+	int ret;
+
+	ret = message_list_db_fetch(ctdb, srvid, &h);
+	if (ret == 0) {
+		for (m=h->m; m; m=m->next) {
+			m->message_handler(ctdb, srvid, data, m->message_private);
+		}
+	}
 
-	for (ml=ctdb->message_list;ml;ml=ml->next) {
-		if (ml->srvid == srvid || ml->srvid == CTDB_SRVID_ALL) {
-			ml->message_handler(ctdb, srvid, data, ml->message_private);
+	ret = message_list_db_fetch(ctdb, srvid_all, &h);
+	if (ret == 0) {
+		for(m=h->m; m; m=m->next) {
+			m->message_handler(ctdb, srvid, data, m->message_private);
 		}
 	}
 
@@ -57,13 +165,36 @@ void ctdb_request_message(struct ctdb_context *ctdb, struct ctdb_req_header *hdr
 	ctdb_dispatch_message(ctdb, c->srvid, data);
 }
 
+/*
+ * When header is freed, remove all the srvid handlers
+ */
+static int message_header_destructor(struct ctdb_message_list_header *h)
+{
+	struct ctdb_message_list *m;
+
+	while (h->m != NULL) {
+		m = h->m;
+		DLIST_REMOVE(h->m, m);
+		TALLOC_FREE(m);
+	}
+
+	message_list_db_delete(h->ctdb, h->srvid);
+	DLIST_REMOVE(h->ctdb->message_list_header, h);
+
+	return 0;
+}
 
 /*
   when a client goes away, we need to remove its srvid handler from the list
  */
 static int message_handler_destructor(struct ctdb_message_list *m)
 {
-	DLIST_REMOVE(m->ctdb->message_list, m);
+	struct ctdb_message_list_header *h = m->h;
+
+	DLIST_REMOVE(h->m, m);
+	if (h->m == NULL) {
+		talloc_free(h);
+	}
 	return 0;
 }
 
@@ -76,20 +207,39 @@ int ctdb_register_message_handler(struct ctdb_context *ctdb,
 				  ctdb_msg_fn_t handler,
 				  void *private_data)
 {
+	struct ctdb_message_list_header *h;
 	struct ctdb_message_list *m;
+	int ret;
 
-	m = talloc(mem_ctx, struct ctdb_message_list);
+	m = talloc_zero(mem_ctx, struct ctdb_message_list);
 	CTDB_NO_MEMORY(ctdb, m);
 
-	m->ctdb            = ctdb;
-	m->srvid           = srvid;
 	m->message_handler = handler;
 	m->message_private = private_data;
-	
-	DLIST_ADD(ctdb->message_list, m);
 
-	talloc_set_destructor(m, message_handler_destructor);
+	ret = message_list_db_fetch(ctdb, srvid, &h);
+	if (ret != 0) {
+		/* srvid not registered yet */
+		h = talloc_zero(ctdb, struct ctdb_message_list_header);
+		CTDB_NO_MEMORY(ctdb, h);
 
+		h->ctdb = ctdb;
+		h->srvid = srvid;
+
+		ret = message_list_db_add(ctdb, srvid, h);
+		if (ret < 0) {
+			talloc_free(m);
+			talloc_free(h);
+			return -1;
+		}
+
+		DLIST_ADD(ctdb->message_list_header, h);
+		talloc_set_destructor(h, message_header_destructor);
+	}
+
+	m->h = h;
+	DLIST_ADD(h->m, m);
+	talloc_set_destructor(m, message_handler_destructor);
 	return 0;
 }
 
@@ -99,13 +249,38 @@ int ctdb_register_message_handler(struct ctdb_context *ctdb,
 */
 int ctdb_deregister_message_handler(struct ctdb_context *ctdb, uint64_t srvid, void *private_data)
 {
+	struct ctdb_message_list_header *h;
 	struct ctdb_message_list *m;
+	int ret;
 
-	for (m=ctdb->message_list;m;m=m->next) {
-		if (m->srvid == srvid && m->message_private == private_data) {
+	ret = message_list_db_fetch(ctdb, srvid, &h);
+	if (ret != 0) {
+		return -1;
+	}
+
+	for (m=h->m; m; m=m->next) {
+		if (m->message_private == private_data) {
 			talloc_free(m);
 			return 0;
 		}
 	}
+
 	return -1;
 }
+
+
+/*
+ * check if the given srvid exists
+ */
+bool ctdb_check_message_handler(struct ctdb_context *ctdb, uint64_t srvid)
+{
+	struct ctdb_message_list_header *h;
+	int ret;
+
+	ret = message_list_db_fetch(ctdb, srvid, &h);
+	if (ret != 0 || h->m == NULL) {
+		return false;
+	}
+
+	return true;
+}
diff --git a/common/ctdb_util.c b/common/ctdb_util.c
index 71dee2b..a910a0c 100644
--- a/common/ctdb_util.c
+++ b/common/ctdb_util.c
@@ -702,3 +702,53 @@ const char *ctdb_eventscript_call_names[] = {
 	"updateip",
 	"ipreallocated"
 };
+
+/* Runstate handling */
+static struct {
+	enum ctdb_runstate runstate;
+	const char * label;
+} runstate_map[] = {
+	{ CTDB_RUNSTATE_UNKNOWN, "UNKNOWN" },
+	{ CTDB_RUNSTATE_INIT, "INIT" },
+	{ CTDB_RUNSTATE_SETUP, "SETUP" },
+	{ CTDB_RUNSTATE_FIRST_RECOVERY, "FIRST_RECOVERY" },
+	{ CTDB_RUNSTATE_STARTUP, "STARTUP" },
+	{ CTDB_RUNSTATE_RUNNING, "RUNNING" },
+	{ CTDB_RUNSTATE_SHUTDOWN, "SHUTDOWN" },
+	{ -1, NULL },
+};
+
+const char *runstate_to_string(enum ctdb_runstate runstate)
+{
+	int i;
+	for (i=0; runstate_map[i].label != NULL ; i++) {
+		if (runstate_map[i].runstate == runstate) {
+			return runstate_map[i].label;
+		}
+	}
+
+	return runstate_map[0].label;
+}
+
+enum ctdb_runstate runstate_from_string(const char *label)
+{
+	int i;
+	for (i=0; runstate_map[i].label != NULL; i++) {
+		if (strcasecmp(runstate_map[i].label, label) == 0) {
+			return runstate_map[i].runstate;
+		}
+	}
+
+	return CTDB_RUNSTATE_UNKNOWN;
+}
+
+void ctdb_set_runstate(struct ctdb_context *ctdb, enum ctdb_runstate runstate)
+{
+	if (runstate <= ctdb->runstate) {
+		ctdb_fatal(ctdb, "runstate must always increase");
+	}
+
+	DEBUG(DEBUG_NOTICE,("Set runstate to %s (%d)\n",
+			    runstate_to_string(runstate), runstate));
+	ctdb->runstate = runstate;
+}
diff --git a/common/system_aix.c b/common/system_aix.c
index 16b627c..35363d3 100644
--- a/common/system_aix.c
+++ b/common/system_aix.c
@@ -206,8 +206,8 @@ int ctdb_sys_close_capture_socket(void *private_data)
  */
 int ctdb_sys_send_arp(const ctdb_sock_addr *addr, const char *iface)
 {
-	/* We dont do grat arp on aix yet */
-	return 0;
+	/* FIXME AIX: We dont do gratuitous arp yet */
+	return -1;
 }
 
 
@@ -359,6 +359,7 @@ int ctdb_sys_read_tcp_packet(int s, void *private_data,
 
 bool ctdb_sys_check_iface_exists(const char *iface)
 {
+	/* FIXME AIX: Interface always considered present */
 	return true;
 }
 
@@ -375,18 +376,18 @@ int ctdb_get_peer_pid(const int fd, pid_t *peer_pid)
 
 char *ctdb_get_process_name(pid_t pid)
 {
-	/* FIXME: not implemented */
+	/* FIXME AIX: get_process_name not implemented */
 	return NULL;
 }
 
 bool ctdb_get_lock_info(pid_t req_pid, struct ctdb_lock_info *lock_info)
 {
-	/* FIXME: not implemented */
+	/* FIXME AIX: get_lock_info not implemented */
 	return false;
 }
 
 bool ctdb_get_blocker_pid(struct ctdb_lock_info *reqlock, pid_t *blocker_pid)
 {
-	/* FIXME: not implemented */
+	/* FIXME AIX: get_blocker_pid not implemented */
 	return false;
 }
diff --git a/common/system_freebsd.c b/common/system_freebsd.c
index 37f1c74..641e77a 100644
--- a/common/system_freebsd.c
+++ b/common/system_freebsd.c
@@ -75,8 +75,8 @@ static uint16_t tcp_checksum6(uint16_t *data, size_t n, struct ip6_hdr *ip6)
  */
 int ctdb_sys_send_arp(const ctdb_sock_addr *addr, const char *iface)
 {
-	/* FIXME We dont do gratuitous arp on Hurd yet */
-	return 0;
+	/* FIXME FreeBSD: We dont do gratuitous arp yet */
+	return -1;
 }
 
 
@@ -360,29 +360,44 @@ int ctdb_sys_read_tcp_packet(int s, void *private_data,
 
 bool ctdb_sys_check_iface_exists(const char *iface)
 {
+	/* FIXME FreeBSD: Interface always considered present */
 	return true;
 }
 
 int ctdb_get_peer_pid(const int fd, pid_t *peer_pid)
 {
-	/* FIXME not implemented */
+	/* FIXME FreeBSD: get_peer_pid not implemented */
 	return 1;
 }
 
 char *ctdb_get_process_name(pid_t pid)
 {
-	/* FIXME: not implemented */
+	char path[32];
+	char buf[PATH_MAX];
+	char *ptr;
+	int n;
+
+	snprintf(path, sizeof(path), "/proc/%d/exe", pid);
+	n = readlink(path, buf, sizeof(buf));
+	if (n < 0) {
+		return NULL;
+	}
+
+	/* Remove any extra fields */
+	buf[n] = '\0';
+	ptr = strtok(buf, " ");
+	return strdup(ptr);
 	return NULL;
 }
 
 bool ctdb_get_lock_info(pid_t req_pid, struct ctdb_lock_info *lock_info)
 {
-	/* FIXME: not implemented */
+	/* FIXME FreeBSD: get_lock_info not implemented */
 	return false;
 }
 
 bool ctdb_get_blocker_pid(struct ctdb_lock_info *reqlock, pid_t *blocker_pid)
 {
-	/* FIXME: not implemented */
+	/* FIXME FreeBSD: get_blocker_pid not implemented */
 	return false;
 }
diff --git a/common/system_gnu.c b/common/system_gnu.c
index 8a3b5b1..0d79ab5 100644
--- a/common/system_gnu.c
+++ b/common/system_gnu.c
@@ -74,8 +74,8 @@ static uint16_t tcp_checksum6(uint16_t *data, size_t n, struct ip6_hdr *ip6)
  */
 int ctdb_sys_send_arp(const ctdb_sock_addr *addr, const char *iface)
 {
-	/* FIXME We dont do gratuitous arp on Hurd yet */
-	return 0;
+	/* FIXME GNU/Hurd: We dont do gratuitous arp yet */
+	return -1;
 }
 
 
@@ -353,29 +353,30 @@ int ctdb_sys_read_tcp_packet(int s, void *private_data,
 
 bool ctdb_sys_check_iface_exists(const char *iface)
 {
+	/* FIXME GNU/Hurd: Interface always considered present */
 	return true;
 }
 
 int ctdb_get_peer_pid(const int fd, pid_t *peer_pid)
 {
-	/* FIXME not implemented */
+	/* FIXME GNU/Hurd: get_peer_pid not implemented */
 	return 1;
 }
 
 char *ctdb_get_process_name(pid_t pid)
 {
-	/* FIXME: not implemented */
+	/* FIXME GNU/Hurd: get_process_name not implemented */
 	return NULL;
 }
 
 bool ctdb_get_lock_info(pid_t req_pid, struct ctdb_lock_info *lock_info)
 {
-	/* FIXME: not implemented */
+	/* FIXME GNU/Hurd: get_lock_info not implemented */
 	return false;
 }
 
 bool ctdb_get_blocker_pid(struct ctdb_lock_info *reqlock, pid_t *blocker_pid)
 {
-	/* FIXME: not implemented */
+	/* FIXME GNU/Hurd: get_blocker_pid not implemented */
 	return false;
 }
diff --git a/common/system_kfreebsd.c b/common/system_kfreebsd.c
index 5595865..2c05c9e 100644
--- a/common/system_kfreebsd.c
+++ b/common/system_kfreebsd.c
@@ -74,8 +74,8 @@ static uint16_t tcp_checksum6(uint16_t *data, size_t n, struct ip6_hdr *ip6)
  */
 int ctdb_sys_send_arp(const ctdb_sock_addr *addr, const char *iface)
 {
-	/* FIXME We dont do gratuitous arp on Hurd yet */
-	return 0;
+	/* FIXME kFreeBSD: We dont do gratuitous arp yet */
+	return -1;
 }
 
 
@@ -353,29 +353,43 @@ int ctdb_sys_read_tcp_packet(int s, void *private_data,
 
 bool ctdb_sys_check_iface_exists(const char *iface)
 {
+	/* FIXME kFreeBSD: Interface always considered present */
 	return true;
 }
 
 int ctdb_get_peer_pid(const int fd, pid_t *peer_pid)
 {
-	/* FIXME not implemented */
+	/* FIXME kFreeBSD: get_peer_pid not implemented */
 	return 1;
 }
 
 char *ctdb_get_process_name(pid_t pid)
 {
-	/* FIXME: not implemented */
-	return NULL;
+	char path[32];
+	char buf[PATH_MAX];
+	char *ptr;
+	int n;
+
+	snprintf(path, sizeof(path), "/proc/%d/exe", pid);
+	n = readlink(path, buf, sizeof(buf));
+	if (n < 0) {
+		return NULL;
+	}
+
+	/* Remove any extra fields */
+	buf[n] = '\0';
+	ptr = strtok(buf, " ");
+	return strdup(ptr);
 }
 
 bool ctdb_get_lock_info(pid_t req_pid, struct ctdb_lock_info *lock_info)
 {
-	/* FIXME: not implemented */
+	/* FIXME kFreeBSD: get_lock_info not implemented */
 	return false;
 }
 
 bool ctdb_get_blocker_pid(struct ctdb_lock_info *reqlock, pid_t *blocker_pid)
 {
-	/* FIXME: not implemented */
+	/* FIXME kFreeBSD: get_blocker_pid not implemented */
 	return false;
 }
diff --git a/config.guess b/config.guess
old mode 100755
new mode 100644
index e3a2116..0aee604
--- a/config.guess
+++ b/config.guess
@@ -1,14 +1,14 @@
 #! /bin/sh
 # Attempt to guess a canonical system name.
 #   Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999,
-#   2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009
-#   Free Software Foundation, Inc.
+#   2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010,
+#   2011, 2012, 2013 Free Software Foundation, Inc.
 
-timestamp='2009-06-10'
+timestamp='2012-12-30'
 
 # This file 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
+# the Free Software Foundation; either version 3 of the License, or
 # (at your option) any later version.
 #
 # This program is distributed in the hope that it will be useful, but
@@ -17,26 +17,22 @@ timestamp='2009-06-10'
 # 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., 51 Franklin Street - Fifth Floor, Boston, MA
-# 02110-1301, USA.
+# along with this program; if not, see <http://www.gnu.org/licenses/>.
 #
 # As a special exception to the GNU General Public License, if you
 # distribute this file as part of a program that contains a
 # configuration script generated by Autoconf, you may include it under
-# the same distribution terms that you use for the rest of that program.
-
-
-# Originally written by Per Bothner <per at bothner.com>.
-# Please send patches to <config-patches at gnu.org>.  Submit a context
-# diff and a properly formatted ChangeLog entry.
+# the same distribution terms that you use for the rest of that
+# program.  This Exception is an additional permission under section 7
+# of the GNU General Public License, version 3 ("GPLv3").
 #
-# This script attempts to guess a canonical system name similar to
-# config.sub.  If it succeeds, it prints the system name on stdout, and
-# exits with 0.  Otherwise, it exits with 1.
+# Originally written by Per Bothner.
 #
-# The plan is that this can be called by configure scripts if you
-# don't specify an explicit build system type.
+# You can get the latest version of this script from:
+# http://git.savannah.gnu.org/gitweb/?p=config.git;a=blob_plain;f=config.guess;hb=HEAD
+#
+# Please send patches with a ChangeLog entry to config-patches at gnu.org.
+
 
 me=`echo "$0" | sed -e 's,.*/,,'`
 
@@ -56,8 +52,9 @@ version="\
 GNU config.guess ($timestamp)
 
 Originally written by Per Bothner.
-Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001,
-2002, 2003, 2004, 2005, 2006, 2007, 2008 Free Software Foundation, Inc.
+Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000,
+2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011,
+2012, 2013 Free Software Foundation, Inc.
 
 This is free software; see the source for copying conditions.  There is NO
 warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE."
@@ -144,7 +141,7 @@ UNAME_VERSION=`(uname -v) 2>/dev/null` || UNAME_VERSION=unknown
 case "${UNAME_MACHINE}:${UNAME_SYSTEM}:${UNAME_RELEASE}:${UNAME_VERSION}" in
     *:NetBSD:*:*)
 	# NetBSD (nbsd) targets should (where applicable) match one or
-	# more of the tupples: *-*-netbsdelf*, *-*-netbsdaout*,
+	# more of the tuples: *-*-netbsdelf*, *-*-netbsdaout*,
 	# *-*-netbsdecoff* and *-*-netbsd*.  For targets that recently
 	# switched to ELF, *-*-netbsd* would select the old
 	# object file format.  This provides both forward
@@ -180,7 +177,7 @@ case "${UNAME_MACHINE}:${UNAME_SYSTEM}:${UNAME_RELEASE}:${UNAME_VERSION}" in
 		fi
 		;;
 	    *)
-	        os=netbsd
+		os=netbsd
 		;;
 	esac
 	# The OS release
@@ -201,6 +198,10 @@ case "${UNAME_MACHINE}:${UNAME_SYSTEM}:${UNAME_RELEASE}:${UNAME_VERSION}" in
 	# CPU_TYPE-MANUFACTURER-OPERATING_SYSTEM is used.
 	echo "${machine}-${os}${release}"
 	exit ;;
+    *:Bitrig:*:*)
+	UNAME_MACHINE_ARCH=`arch | sed 's/Bitrig.//'`
+	echo ${UNAME_MACHINE_ARCH}-unknown-bitrig${UNAME_RELEASE}
+	exit ;;
     *:OpenBSD:*:*)
 	UNAME_MACHINE_ARCH=`arch | sed 's/OpenBSD.//'`
 	echo ${UNAME_MACHINE_ARCH}-unknown-openbsd${UNAME_RELEASE}
@@ -223,7 +224,7 @@ case "${UNAME_MACHINE}:${UNAME_SYSTEM}:${UNAME_RELEASE}:${UNAME_VERSION}" in
 		UNAME_RELEASE=`/usr/sbin/sizer -v | awk '{print $3}'`
 		;;
 	*5.*)
-	        UNAME_RELEASE=`/usr/sbin/sizer -v | awk '{print $4}'`
+		UNAME_RELEASE=`/usr/sbin/sizer -v | awk '{print $4}'`
 		;;
 	esac
 	# According to Compaq, /usr/sbin/psrinfo has been available on
@@ -269,7 +270,10 @@ case "${UNAME_MACHINE}:${UNAME_SYSTEM}:${UNAME_RELEASE}:${UNAME_VERSION}" in
 	# A Xn.n version is an unreleased experimental baselevel.
 	# 1.2 uses "1.2" for uname -r.
 	echo ${UNAME_MACHINE}-dec-osf`echo ${UNAME_RELEASE} | sed -e 's/^[PVTX]//' | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz'`
-	exit ;;
+	# Reset EXIT trap before exiting to avoid spurious non-zero exit code.
+	exitcode=$?
+	trap '' 0
+	exit $exitcode ;;
     Alpha\ *:Windows_NT*:*)
 	# How do we know it's Interix rather than the generic POSIX subsystem?
 	# Should we change UNAME_MACHINE based on the output of uname instead
@@ -295,12 +299,12 @@ case "${UNAME_MACHINE}:${UNAME_SYSTEM}:${UNAME_RELEASE}:${UNAME_VERSION}" in
 	echo s390-ibm-zvmoe
 	exit ;;
     *:OS400:*:*)
-        echo powerpc-ibm-os400
+	echo powerpc-ibm-os400
 	exit ;;
     arm:RISC*:1.[012]*:*|arm:riscix:1.[012]*:*)
 	echo arm-acorn-riscix${UNAME_RELEASE}
 	exit ;;
-    arm:riscos:*:*|arm:RISCOS:*:*)
+    arm*:riscos:*:*|arm*:RISCOS:*:*)
 	echo arm-unknown-riscos
 	exit ;;
     SR2?01:HI-UX/MPP:*:* | SR8000:HI-UX/MPP:*:*)
@@ -333,6 +337,9 @@ case "${UNAME_MACHINE}:${UNAME_SYSTEM}:${UNAME_RELEASE}:${UNAME_VERSION}" in
     sun4*:SunOS:5.*:* | tadpole*:SunOS:5.*:*)
 	echo sparc-sun-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'`
 	exit ;;
+    i86pc:AuroraUX:5.*:* | i86xen:AuroraUX:5.*:*)
+	echo i386-pc-auroraux${UNAME_RELEASE}
+	exit ;;
     i86pc:SunOS:5.*:* | i86xen:SunOS:5.*:*)
 	eval $set_cc_for_build
 	SUN_ARCH="i386"
@@ -391,23 +398,23 @@ case "${UNAME_MACHINE}:${UNAME_SYSTEM}:${UNAME_RELEASE}:${UNAME_VERSION}" in
     # MiNT.  But MiNT is downward compatible to TOS, so this should
     # be no problem.
     atarist[e]:*MiNT:*:* | atarist[e]:*mint:*:* | atarist[e]:*TOS:*:*)
-        echo m68k-atari-mint${UNAME_RELEASE}
+	echo m68k-atari-mint${UNAME_RELEASE}
 	exit ;;
     atari*:*MiNT:*:* | atari*:*mint:*:* | atarist[e]:*TOS:*:*)
 	echo m68k-atari-mint${UNAME_RELEASE}
-        exit ;;
+	exit ;;
     *falcon*:*MiNT:*:* | *falcon*:*mint:*:* | *falcon*:*TOS:*:*)
-        echo m68k-atari-mint${UNAME_RELEASE}
+	echo m68k-atari-mint${UNAME_RELEASE}
 	exit ;;
     milan*:*MiNT:*:* | milan*:*mint:*:* | *milan*:*TOS:*:*)
-        echo m68k-milan-mint${UNAME_RELEASE}
-        exit ;;
+	echo m68k-milan-mint${UNAME_RELEASE}
+	exit ;;
     hades*:*MiNT:*:* | hades*:*mint:*:* | *hades*:*TOS:*:*)
-        echo m68k-hades-mint${UNAME_RELEASE}
-        exit ;;
+	echo m68k-hades-mint${UNAME_RELEASE}
+	exit ;;
     *:*MiNT:*:* | *:*mint:*:* | *:*TOS:*:*)
-        echo m68k-unknown-mint${UNAME_RELEASE}
-        exit ;;
+	echo m68k-unknown-mint${UNAME_RELEASE}
+	exit ;;
     m68k:machten:*:*)
 	echo m68k-apple-machten${UNAME_RELEASE}
 	exit ;;
@@ -477,8 +484,8 @@ EOF
 	echo m88k-motorola-sysv3
 	exit ;;
     AViiON:dgux:*:*)
-        # DG/UX returns AViiON for all architectures
-        UNAME_PROCESSOR=`/usr/bin/uname -p`
+	# DG/UX returns AViiON for all architectures
+	UNAME_PROCESSOR=`/usr/bin/uname -p`
 	if [ $UNAME_PROCESSOR = mc88100 ] || [ $UNAME_PROCESSOR = mc88110 ]
 	then
 	    if [ ${TARGET_BINARY_INTERFACE}x = m88kdguxelfx ] || \
@@ -491,7 +498,7 @@ EOF
 	else
 	    echo i586-dg-dgux${UNAME_RELEASE}
 	fi
- 	exit ;;
+	exit ;;
     M88*:DolphinOS:*:*)	# DolphinOS (SVR3)
 	echo m88k-dolphin-sysv3
 	exit ;;
@@ -548,7 +555,7 @@ EOF
 		echo rs6000-ibm-aix3.2
 	fi
 	exit ;;
-    *:AIX:*:[456])
+    *:AIX:*:[4567])
 	IBM_CPU_ID=`/usr/sbin/lsdev -C -c processor -S available | sed 1q | awk '{ print $1 }'`
 	if /usr/sbin/lsattr -El ${IBM_CPU_ID} | grep ' POWER' >/dev/null 2>&1; then
 		IBM_ARCH=rs6000
@@ -591,52 +598,52 @@ EOF
 	    9000/[678][0-9][0-9])
 		if [ -x /usr/bin/getconf ]; then
 		    sc_cpu_version=`/usr/bin/getconf SC_CPU_VERSION 2>/dev/null`
-                    sc_kernel_bits=`/usr/bin/getconf SC_KERNEL_BITS 2>/dev/null`
-                    case "${sc_cpu_version}" in
-                      523) HP_ARCH="hppa1.0" ;; # CPU_PA_RISC1_0
-                      528) HP_ARCH="hppa1.1" ;; # CPU_PA_RISC1_1
-                      532)                      # CPU_PA_RISC2_0
-                        case "${sc_kernel_bits}" in
-                          32) HP_ARCH="hppa2.0n" ;;
-                          64) HP_ARCH="hppa2.0w" ;;
+		    sc_kernel_bits=`/usr/bin/getconf SC_KERNEL_BITS 2>/dev/null`
+		    case "${sc_cpu_version}" in
+		      523) HP_ARCH="hppa1.0" ;; # CPU_PA_RISC1_0
+		      528) HP_ARCH="hppa1.1" ;; # CPU_PA_RISC1_1
+		      532)                      # CPU_PA_RISC2_0
+			case "${sc_kernel_bits}" in
+			  32) HP_ARCH="hppa2.0n" ;;
+			  64) HP_ARCH="hppa2.0w" ;;
 			  '') HP_ARCH="hppa2.0" ;;   # HP-UX 10.20
-                        esac ;;
-                    esac
+			esac ;;
+		    esac
 		fi
 		if [ "${HP_ARCH}" = "" ]; then
 		    eval $set_cc_for_build
-		    sed 's/^              //' << EOF >$dummy.c
+		    sed 's/^		//' << EOF >$dummy.c
 
-              #define _HPUX_SOURCE
-              #include <stdlib.h>
-              #include <unistd.h>
+		#define _HPUX_SOURCE
+		#include <stdlib.h>
+		#include <unistd.h>
 
-              int main ()
-              {
-              #if defined(_SC_KERNEL_BITS)
-                  long bits = sysconf(_SC_KERNEL_BITS);
-              #endif
-                  long cpu  = sysconf (_SC_CPU_VERSION);
+		int main ()
+		{
+		#if defined(_SC_KERNEL_BITS)
+		    long bits = sysconf(_SC_KERNEL_BITS);
+		#endif
+		    long cpu  = sysconf (_SC_CPU_VERSION);
 
-                  switch (cpu)
-              	{
-              	case CPU_PA_RISC1_0: puts ("hppa1.0"); break;
-              	case CPU_PA_RISC1_1: puts ("hppa1.1"); break;
-              	case CPU_PA_RISC2_0:
-              #if defined(_SC_KERNEL_BITS)
-              	    switch (bits)
-              		{
-              		case 64: puts ("hppa2.0w"); break;
-              		case 32: puts ("hppa2.0n"); break;
-              		default: puts ("hppa2.0"); break;
-              		} break;
-              #else  /* !defined(_SC_KERNEL_BITS) */
-              	    puts ("hppa2.0"); break;
-              #endif
-              	default: puts ("hppa1.0"); break;
-              	}
-                  exit (0);
-              }
+		    switch (cpu)
+			{
+			case CPU_PA_RISC1_0: puts ("hppa1.0"); break;
+			case CPU_PA_RISC1_1: puts ("hppa1.1"); break;
+			case CPU_PA_RISC2_0:
+		#if defined(_SC_KERNEL_BITS)
+			    switch (bits)
+				{
+				case 64: puts ("hppa2.0w"); break;
+				case 32: puts ("hppa2.0n"); break;
+				default: puts ("hppa2.0"); break;
+				} break;
+		#else  /* !defined(_SC_KERNEL_BITS) */
+			    puts ("hppa2.0"); break;
+		#endif
+			default: puts ("hppa1.0"); break;
+			}
+		    exit (0);
+		}
 EOF
 		    (CCOPTS= $CC_FOR_BUILD -o $dummy $dummy.c 2>/dev/null) && HP_ARCH=`$dummy`
 		    test -z "$HP_ARCH" && HP_ARCH=hppa
@@ -727,22 +734,22 @@ EOF
 	exit ;;
     C1*:ConvexOS:*:* | convex:ConvexOS:C1*:*)
 	echo c1-convex-bsd
-        exit ;;
+	exit ;;
     C2*:ConvexOS:*:* | convex:ConvexOS:C2*:*)
 	if getsysinfo -f scalar_acc
 	then echo c32-convex-bsd
 	else echo c2-convex-bsd
 	fi
-        exit ;;
+	exit ;;
     C34*:ConvexOS:*:* | convex:ConvexOS:C34*:*)
 	echo c34-convex-bsd
-        exit ;;
+	exit ;;
     C38*:ConvexOS:*:* | convex:ConvexOS:C38*:*)
 	echo c38-convex-bsd
-        exit ;;
+	exit ;;
     C4*:ConvexOS:*:* | convex:ConvexOS:C4*:*)
 	echo c4-convex-bsd
-        exit ;;
+	exit ;;
     CRAY*Y-MP:*:*:*)
 	echo ymp-cray-unicos${UNAME_RELEASE} | sed -e 's/\.[^.]*$/.X/'
 	exit ;;
@@ -766,14 +773,14 @@ EOF
 	exit ;;
     F30[01]:UNIX_System_V:*:* | F700:UNIX_System_V:*:*)
 	FUJITSU_PROC=`uname -m | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz'`
-        FUJITSU_SYS=`uname -p | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz' | sed -e 's/\///'`
-        FUJITSU_REL=`echo ${UNAME_RELEASE} | sed -e 's/ /_/'`
-        echo "${FUJITSU_PROC}-fujitsu-${FUJITSU_SYS}${FUJITSU_REL}"
-        exit ;;
+	FUJITSU_SYS=`uname -p | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz' | sed -e 's/\///'`
+	FUJITSU_REL=`echo ${UNAME_RELEASE} | sed -e 's/ /_/'`
+	echo "${FUJITSU_PROC}-fujitsu-${FUJITSU_SYS}${FUJITSU_REL}"
+	exit ;;
     5000:UNIX_System_V:4.*:*)
-        FUJITSU_SYS=`uname -p | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz' | sed -e 's/\///'`
-        FUJITSU_REL=`echo ${UNAME_RELEASE} | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz' | sed -e 's/ /_/'`
-        echo "sparc-fujitsu-${FUJITSU_SYS}${FUJITSU_REL}"
+	FUJITSU_SYS=`uname -p | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz' | sed -e 's/\///'`
+	FUJITSU_REL=`echo ${UNAME_RELEASE} | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz' | sed -e 's/ /_/'`
+	echo "sparc-fujitsu-${FUJITSU_SYS}${FUJITSU_REL}"
 	exit ;;
     i*86:BSD/386:*:* | i*86:BSD/OS:*:* | *:Ascend\ Embedded/OS:*:*)
 	echo ${UNAME_MACHINE}-pc-bsdi${UNAME_RELEASE}
@@ -785,34 +792,39 @@ EOF
 	echo ${UNAME_MACHINE}-unknown-bsdi${UNAME_RELEASE}
 	exit ;;
     *:FreeBSD:*:*)
-	case ${UNAME_MACHINE} in
-	    pc98)
-		echo i386-unknown-freebsd`echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'` ;;
+	UNAME_PROCESSOR=`/usr/bin/uname -p`
+	case ${UNAME_PROCESSOR} in
 	    amd64)
 		echo x86_64-unknown-freebsd`echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'` ;;
 	    *)
-		echo ${UNAME_MACHINE}-unknown-freebsd`echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'` ;;
+		echo ${UNAME_PROCESSOR}-unknown-freebsd`echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'` ;;
 	esac
 	exit ;;
     i*:CYGWIN*:*)
 	echo ${UNAME_MACHINE}-pc-cygwin
 	exit ;;
+    *:MINGW64*:*)
+	echo ${UNAME_MACHINE}-pc-mingw64
+	exit ;;
     *:MINGW*:*)
 	echo ${UNAME_MACHINE}-pc-mingw32
 	exit ;;
+    i*:MSYS*:*)
+	echo ${UNAME_MACHINE}-pc-msys
+	exit ;;
     i*:windows32*:*)
-    	# uname -m includes "-pc" on this system.
-    	echo ${UNAME_MACHINE}-mingw32
+	# uname -m includes "-pc" on this system.
+	echo ${UNAME_MACHINE}-mingw32
 	exit ;;
     i*:PW*:*)
 	echo ${UNAME_MACHINE}-pc-pw32
 	exit ;;
-    *:Interix*:[3456]*)
-    	case ${UNAME_MACHINE} in
+    *:Interix*:*)
+	case ${UNAME_MACHINE} in
 	    x86)
 		echo i586-pc-interix${UNAME_RELEASE}
 		exit ;;
-	    EM64T | authenticamd | genuineintel)
+	    authenticamd | genuineintel | EM64T)
 		echo x86_64-unknown-interix${UNAME_RELEASE}
 		exit ;;
 	    IA64)
@@ -854,6 +866,27 @@ EOF
     i*86:Minix:*:*)
 	echo ${UNAME_MACHINE}-pc-minix
 	exit ;;
+    aarch64:Linux:*:*)
+	echo ${UNAME_MACHINE}-unknown-linux-gnu
+	exit ;;
+    aarch64_be:Linux:*:*)
+	UNAME_MACHINE=aarch64_be
+	echo ${UNAME_MACHINE}-unknown-linux-gnu
+	exit ;;
+    alpha:Linux:*:*)
+	case `sed -n '/^cpu model/s/^.*: \(.*\)/\1/p' < /proc/cpuinfo` in
+	  EV5)   UNAME_MACHINE=alphaev5 ;;
+	  EV56)  UNAME_MACHINE=alphaev56 ;;
+	  PCA56) UNAME_MACHINE=alphapca56 ;;
+	  PCA57) UNAME_MACHINE=alphapca56 ;;
+	  EV6)   UNAME_MACHINE=alphaev6 ;;
+	  EV67)  UNAME_MACHINE=alphaev67 ;;
+	  EV68*) UNAME_MACHINE=alphaev68 ;;
+	esac
+	objdump --private-headers /bin/sh | grep -q ld.so.1
+	if test "$?" = 0 ; then LIBC="libc1" ; else LIBC="" ; fi
+	echo ${UNAME_MACHINE}-unknown-linux-gnu${LIBC}
+	exit ;;
     arm*:Linux:*:*)
 	eval $set_cc_for_build
 	if echo __ARM_EABI__ | $CC_FOR_BUILD -E - 2>/dev/null \
@@ -861,20 +894,40 @@ EOF
 	then
 	    echo ${UNAME_MACHINE}-unknown-linux-gnu
 	else
-	    echo ${UNAME_MACHINE}-unknown-linux-gnueabi
+	    if echo __ARM_PCS_VFP | $CC_FOR_BUILD -E - 2>/dev/null \
+		| grep -q __ARM_PCS_VFP
+	    then
+		echo ${UNAME_MACHINE}-unknown-linux-gnueabi
+	    else
+		echo ${UNAME_MACHINE}-unknown-linux-gnueabihf
+	    fi
 	fi
 	exit ;;
     avr32*:Linux:*:*)
 	echo ${UNAME_MACHINE}-unknown-linux-gnu
 	exit ;;
     cris:Linux:*:*)
-	echo cris-axis-linux-gnu
+	echo ${UNAME_MACHINE}-axis-linux-gnu
 	exit ;;
     crisv32:Linux:*:*)
-	echo crisv32-axis-linux-gnu
+	echo ${UNAME_MACHINE}-axis-linux-gnu
 	exit ;;
     frv:Linux:*:*)
-    	echo frv-unknown-linux-gnu
+	echo ${UNAME_MACHINE}-unknown-linux-gnu
+	exit ;;
+    hexagon:Linux:*:*)
+	echo ${UNAME_MACHINE}-unknown-linux-gnu
+	exit ;;
+    i*86:Linux:*:*)
+	LIBC=gnu
+	eval $set_cc_for_build
+	sed 's/^	//' << EOF >$dummy.c
+	#ifdef __dietlibc__
+	LIBC=dietlibc
+	#endif
+EOF
+	eval `$CC_FOR_BUILD -E $dummy.c 2>/dev/null | grep '^LIBC'`
+	echo "${UNAME_MACHINE}-pc-linux-${LIBC}"
 	exit ;;
     ia64:Linux:*:*)
 	echo ${UNAME_MACHINE}-unknown-linux-gnu
@@ -901,39 +954,18 @@ EOF
 	#endif
 	#endif
 EOF
-	eval "`$CC_FOR_BUILD -E $dummy.c 2>/dev/null | sed -n '
-	    /^CPU/{
-		s: ::g
-		p
-	    }'`"
+	eval `$CC_FOR_BUILD -E $dummy.c 2>/dev/null | grep '^CPU'`
 	test x"${CPU}" != x && { echo "${CPU}-unknown-linux-gnu"; exit; }
 	;;
     or32:Linux:*:*)
-	echo or32-unknown-linux-gnu
-	exit ;;
-    ppc:Linux:*:*)
-	echo powerpc-unknown-linux-gnu
-	exit ;;
-    ppc64:Linux:*:*)
-	echo powerpc64-unknown-linux-gnu
-	exit ;;
-    alpha:Linux:*:*)
-	case `sed -n '/^cpu model/s/^.*: \(.*\)/\1/p' < /proc/cpuinfo` in
-	  EV5)   UNAME_MACHINE=alphaev5 ;;
-	  EV56)  UNAME_MACHINE=alphaev56 ;;
-	  PCA56) UNAME_MACHINE=alphapca56 ;;
-	  PCA57) UNAME_MACHINE=alphapca56 ;;
-	  EV6)   UNAME_MACHINE=alphaev6 ;;
-	  EV67)  UNAME_MACHINE=alphaev67 ;;
-	  EV68*) UNAME_MACHINE=alphaev68 ;;
-        esac
-	objdump --private-headers /bin/sh | grep -q ld.so.1
-	if test "$?" = 0 ; then LIBC="libc1" ; else LIBC="" ; fi
-	echo ${UNAME_MACHINE}-unknown-linux-gnu${LIBC}
+	echo ${UNAME_MACHINE}-unknown-linux-gnu
 	exit ;;
     padre:Linux:*:*)
 	echo sparc-unknown-linux-gnu
 	exit ;;
+    parisc64:Linux:*:* | hppa64:Linux:*:*)
+	echo hppa64-unknown-linux-gnu
+	exit ;;
     parisc:Linux:*:* | hppa:Linux:*:*)
 	# Look for CPU level
 	case `grep '^cpu[^a-z]*:' /proc/cpuinfo 2>/dev/null | cut -d' ' -f2` in
@@ -942,14 +974,17 @@ EOF
 	  *)    echo hppa-unknown-linux-gnu ;;
 	esac
 	exit ;;
-    parisc64:Linux:*:* | hppa64:Linux:*:*)
-	echo hppa64-unknown-linux-gnu
+    ppc64:Linux:*:*)
+	echo powerpc64-unknown-linux-gnu
+	exit ;;
+    ppc:Linux:*:*)
+	echo powerpc-unknown-linux-gnu
 	exit ;;
     s390:Linux:*:* | s390x:Linux:*:*)
 	echo ${UNAME_MACHINE}-ibm-linux
 	exit ;;
     sh64*:Linux:*:*)
-    	echo ${UNAME_MACHINE}-unknown-linux-gnu
+	echo ${UNAME_MACHINE}-unknown-linux-gnu
 	exit ;;
     sh*:Linux:*:*)
 	echo ${UNAME_MACHINE}-unknown-linux-gnu
@@ -957,67 +992,18 @@ EOF
     sparc:Linux:*:* | sparc64:Linux:*:*)
 	echo ${UNAME_MACHINE}-unknown-linux-gnu
 	exit ;;
+    tile*:Linux:*:*)
+	echo ${UNAME_MACHINE}-unknown-linux-gnu
+	exit ;;
     vax:Linux:*:*)
 	echo ${UNAME_MACHINE}-dec-linux-gnu
 	exit ;;
     x86_64:Linux:*:*)
-	echo x86_64-unknown-linux-gnu
+	echo ${UNAME_MACHINE}-unknown-linux-gnu
 	exit ;;
     xtensa*:Linux:*:*)
-    	echo ${UNAME_MACHINE}-unknown-linux-gnu
+	echo ${UNAME_MACHINE}-unknown-linux-gnu
 	exit ;;
-    i*86:Linux:*:*)
-	# The BFD linker knows what the default object file format is, so
-	# first see if it will tell us. cd to the root directory to prevent
-	# problems with other programs or directories called `ld' in the path.
-	# Set LC_ALL=C to ensure ld outputs messages in English.
-	ld_supported_targets=`cd /; LC_ALL=C ld --help 2>&1 \
-			 | sed -ne '/supported targets:/!d
-				    s/[ 	][ 	]*/ /g
-				    s/.*supported targets: *//
-				    s/ .*//
-				    p'`
-        case "$ld_supported_targets" in
-	  elf32-i386)
-		TENTATIVE="${UNAME_MACHINE}-pc-linux-gnu"
-		;;
-	esac
-	# Determine whether the default compiler is a.out or elf
-	eval $set_cc_for_build
-	sed 's/^	//' << EOF >$dummy.c
-	#include <features.h>
-	#ifdef __ELF__
-	# ifdef __GLIBC__
-	#  if __GLIBC__ >= 2
-	LIBC=gnu
-	#  else
-	LIBC=gnulibc1
-	#  endif
-	# else
-	LIBC=gnulibc1
-	# endif
-	#else
-	#if defined(__INTEL_COMPILER) || defined(__PGI) || defined(__SUNPRO_C) || defined(__SUNPRO_CC)
-	LIBC=gnu
-	#else
-	LIBC=gnuaout
-	#endif
-	#endif
-	#ifdef __dietlibc__
-	LIBC=dietlibc
-	#endif
-EOF
-	eval "`$CC_FOR_BUILD -E $dummy.c 2>/dev/null | sed -n '
-	    /^LIBC/{
-		s: ::g
-		p
-	    }'`"
-	test x"${LIBC}" != x && {
-		echo "${UNAME_MACHINE}-pc-linux-${LIBC}"
-		exit
-	}
-	test x"${TENTATIVE}" != x && { echo "${TENTATIVE}"; exit; }
-	;;
     i*86:DYNIX/ptx:4*:*)
 	# ptx 4.0 does uname -s correctly, with DYNIX/ptx in there.
 	# earlier versions are messed up and put the nodename in both
@@ -1025,11 +1011,11 @@ EOF
 	echo i386-sequent-sysv4
 	exit ;;
     i*86:UNIX_SV:4.2MP:2.*)
-        # Unixware is an offshoot of SVR4, but it has its own version
-        # number series starting with 2...
-        # I am not positive that other SVR4 systems won't match this,
+	# Unixware is an offshoot of SVR4, but it has its own version
+	# number series starting with 2...
+	# I am not positive that other SVR4 systems won't match this,
 	# I just have to hope.  -- rms.
-        # Use sysv4.2uw... so that sysv4* matches it.
+	# Use sysv4.2uw... so that sysv4* matches it.
 	echo ${UNAME_MACHINE}-pc-sysv4.2uw${UNAME_VERSION}
 	exit ;;
     i*86:OS/2:*:*)
@@ -1061,7 +1047,7 @@ EOF
 	fi
 	exit ;;
     i*86:*:5:[678]*)
-    	# UnixWare 7.x, OpenUNIX and OpenServer 6.
+	# UnixWare 7.x, OpenUNIX and OpenServer 6.
 	case `/bin/uname -X | grep "^Machine"` in
 	    *486*)	     UNAME_MACHINE=i486 ;;
 	    *Pentium)	     UNAME_MACHINE=i586 ;;
@@ -1089,13 +1075,13 @@ EOF
 	exit ;;
     pc:*:*:*)
 	# Left here for compatibility:
-        # uname -m prints for DJGPP always 'pc', but it prints nothing about
-        # the processor, so we play safe by assuming i586.
+	# uname -m prints for DJGPP always 'pc', but it prints nothing about
+	# the processor, so we play safe by assuming i586.
 	# Note: whatever this is, it MUST be the same as what config.sub
 	# prints for the "djgpp" host, or else GDB configury will decide that
 	# this is a cross-build.
 	echo i586-pc-msdosdjgpp
-        exit ;;
+	exit ;;
     Intel:Mach:3*:*)
 	echo i386-pc-mach3
 	exit ;;
@@ -1130,8 +1116,8 @@ EOF
 	/bin/uname -p 2>/dev/null | /bin/grep entium >/dev/null \
 	  && { echo i586-ncr-sysv4.3${OS_REL}; exit; } ;;
     3[34]??:*:4.0:* | 3[34]??,*:*:4.0:*)
-        /bin/uname -p 2>/dev/null | grep 86 >/dev/null \
-          && { echo i486-ncr-sysv4; exit; } ;;
+	/bin/uname -p 2>/dev/null | grep 86 >/dev/null \
+	  && { echo i486-ncr-sysv4; exit; } ;;
     NCR*:*:4.2:* | MPRAS*:*:4.2:*)
 	OS_REL='.3'
 	test -r /etc/.relid \
@@ -1174,10 +1160,10 @@ EOF
 		echo ns32k-sni-sysv
 	fi
 	exit ;;
-    PENTIUM:*:4.0*:*) # Unisys `ClearPath HMP IX 4000' SVR4/MP effort
-                      # says <Richard.M.Bartel at ccMail.Census.GOV>
-        echo i586-unisys-sysv4
-        exit ;;
+    PENTIUM:*:4.0*:*)	# Unisys `ClearPath HMP IX 4000' SVR4/MP effort
+			# says <Richard.M.Bartel at ccMail.Census.GOV>
+	echo i586-unisys-sysv4
+	exit ;;
     *:UNIX_System_V:4*:FTX*)
 	# From Gerald Hewes <hewes at openmarket.com>.
 	# How about differentiating between stratus architectures? -djm
@@ -1203,11 +1189,11 @@ EOF
 	exit ;;
     R[34]000:*System_V*:*:* | R4000:UNIX_SYSV:*:* | R*000:UNIX_SV:*:*)
 	if [ -d /usr/nec ]; then
-	        echo mips-nec-sysv${UNAME_RELEASE}
+		echo mips-nec-sysv${UNAME_RELEASE}
 	else
-	        echo mips-unknown-sysv${UNAME_RELEASE}
+		echo mips-unknown-sysv${UNAME_RELEASE}
 	fi
-        exit ;;
+	exit ;;
     BeBox:BeOS:*:*)	# BeOS running on hardware made by Be, PPC only.
 	echo powerpc-be-beos
 	exit ;;
@@ -1220,6 +1206,9 @@ EOF
     BePC:Haiku:*:*)	# Haiku running on Intel PC compatible.
 	echo i586-pc-haiku
 	exit ;;
+    x86_64:Haiku:*:*)
+	echo x86_64-unknown-haiku
+	exit ;;
     SX-4:SUPER-UX:*:*)
 	echo sx4-nec-superux${UNAME_RELEASE}
 	exit ;;
@@ -1247,6 +1236,16 @@ EOF
     *:Darwin:*:*)
 	UNAME_PROCESSOR=`uname -p` || UNAME_PROCESSOR=unknown
 	case $UNAME_PROCESSOR in
+	    i386)
+		eval $set_cc_for_build
+		if [ "$CC_FOR_BUILD" != 'no_compiler_found' ]; then
+		  if (echo '#ifdef __LP64__'; echo IS_64BIT_ARCH; echo '#endif') | \
+		      (CCOPTS= $CC_FOR_BUILD -E - 2>/dev/null) | \
+		      grep IS_64BIT_ARCH >/dev/null
+		  then
+		      UNAME_PROCESSOR="x86_64"
+		  fi
+		fi ;;
 	    unknown) UNAME_PROCESSOR=powerpc ;;
 	esac
 	echo ${UNAME_PROCESSOR}-apple-darwin${UNAME_RELEASE}
@@ -1262,7 +1261,10 @@ EOF
     *:QNX:*:4*)
 	echo i386-pc-qnx
 	exit ;;
-    NSE-?:NONSTOP_KERNEL:*:*)
+    NEO-?:NONSTOP_KERNEL:*:*)
+	echo neo-tandem-nsk${UNAME_RELEASE}
+	exit ;;
+    NSE-*:NONSTOP_KERNEL:*:*)
 	echo nse-tandem-nsk${UNAME_RELEASE}
 	exit ;;
     NSR-?:NONSTOP_KERNEL:*:*)
@@ -1307,13 +1309,13 @@ EOF
 	echo pdp10-unknown-its
 	exit ;;
     SEI:*:*:SEIUX)
-        echo mips-sei-seiux${UNAME_RELEASE}
+	echo mips-sei-seiux${UNAME_RELEASE}
 	exit ;;
     *:DragonFly:*:*)
 	echo ${UNAME_MACHINE}-unknown-dragonfly`echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'`
 	exit ;;
     *:*VMS:*:*)
-    	UNAME_MACHINE=`(uname -p) 2>/dev/null`
+	UNAME_MACHINE=`(uname -p) 2>/dev/null`
 	case "${UNAME_MACHINE}" in
 	    A*) echo alpha-dec-vms ; exit ;;
 	    I*) echo ia64-dec-vms ; exit ;;
@@ -1331,11 +1333,11 @@ EOF
     i*86:AROS:*:*)
 	echo ${UNAME_MACHINE}-pc-aros
 	exit ;;
+    x86_64:VMkernel:*:*)
+	echo ${UNAME_MACHINE}-unknown-esx
+	exit ;;
 esac
 
-#echo '(No uname command or uname output not recognized.)' 1>&2
-#echo "${UNAME_MACHINE}:${UNAME_SYSTEM}:${UNAME_RELEASE}:${UNAME_VERSION}" 1>&2
-
 eval $set_cc_for_build
 cat >$dummy.c <<EOF
 #ifdef _SEQUENT_
@@ -1353,11 +1355,11 @@ main ()
 #include <sys/param.h>
   printf ("m68k-sony-newsos%s\n",
 #ifdef NEWSOS4
-          "4"
+	"4"
 #else
-	  ""
+	""
 #endif
-         ); exit (0);
+	); exit (0);
 #endif
 #endif
 
diff --git a/config.h.in b/config.h.in
index e980681..674449d 100644
--- a/config.h.in
+++ b/config.h.in
@@ -3,6 +3,9 @@
 /* Define if building universal (internal helper macro) */
 #undef AC_APPLE_UNIVERSAL_BUILD
 
+/* Does extattr API work */
+#undef BROKEN_EXTATTR
+
 /* Broken RedHat 7.2 system header files */
 #undef BROKEN_REDHAT_7_SYSTEM_HEADERS
 
@@ -33,6 +36,36 @@
 /* Define to 1 if you have the `asprintf' function. */
 #undef HAVE_ASPRINTF
 
+/* Define to 1 if you have the `attropen' function. */
+#undef HAVE_ATTROPEN
+
+/* Define to 1 if you have the `attr_get' function. */
+#undef HAVE_ATTR_GET
+
+/* Define to 1 if you have the `attr_getf' function. */
+#undef HAVE_ATTR_GETF
+
+/* Define to 1 if you have the `attr_list' function. */
+#undef HAVE_ATTR_LIST
+
+/* Define to 1 if you have the `attr_listf' function. */
+#undef HAVE_ATTR_LISTF
+
+/* Define to 1 if you have the `attr_remove' function. */
+#undef HAVE_ATTR_REMOVE
+
+/* Define to 1 if you have the `attr_removef' function. */
+#undef HAVE_ATTR_REMOVEF
+
+/* Define to 1 if you have the `attr_set' function. */
+#undef HAVE_ATTR_SET
+
+/* Define to 1 if you have the `attr_setf' function. */
+#undef HAVE_ATTR_SETF
+
+/* Define to 1 if you have the <attr/xattr.h> header file. */
+#undef HAVE_ATTR_XATTR_H
+
 /* Define to 1 if you have the `backtrace' function. */
 #undef HAVE_BACKTRACE
 
@@ -92,6 +125,10 @@
    don't. */
 #undef HAVE_DECL_SNPRINTF
 
+/* Define to 1 if you have the declaration of `strptime', and to 0 if you
+   don't. */
+#undef HAVE_DECL_STRPTIME
+
 /* Define to 1 if you have the declaration of `TEVENT_TRACE_BEFORE_WAIT', and
    to 0 if you don't. */
 #undef HAVE_DECL_TEVENT_TRACE_BEFORE_WAIT
@@ -156,6 +193,30 @@
 /* Define to 1 if you have the <execinfo.h> header file. */
 #undef HAVE_EXECINFO_H
 
+/* Define to 1 if you have the `extattr_delete_fd' function. */
+#undef HAVE_EXTATTR_DELETE_FD
+
+/* Define to 1 if you have the `extattr_delete_file' function. */
+#undef HAVE_EXTATTR_DELETE_FILE
+
+/* Define to 1 if you have the `extattr_get_fd' function. */
+#undef HAVE_EXTATTR_GET_FD
+
+/* Define to 1 if you have the `extattr_get_file' function. */
+#undef HAVE_EXTATTR_GET_FILE
+
+/* Define to 1 if you have the `extattr_list_fd' function. */
+#undef HAVE_EXTATTR_LIST_FD
+
+/* Define to 1 if you have the `extattr_list_file' function. */
+#undef HAVE_EXTATTR_LIST_FILE
+
+/* Define to 1 if you have the `extattr_set_fd' function. */
+#undef HAVE_EXTATTR_SET_FD
+
+/* Define to 1 if you have the `extattr_set_file' function. */
+#undef HAVE_EXTATTR_SET_FILE
+
 /* Define to 1 if you have the <fcntl.h> header file. */
 #undef HAVE_FCNTL_H
 
@@ -165,6 +226,18 @@
 /* Whether fdatasync() is available */
 #undef HAVE_FDATASYNC_DECL
 
+/* Define to 1 if you have the `fgetea' function. */
+#undef HAVE_FGETEA
+
+/* Define to 1 if you have the `fgetxattr' function. */
+#undef HAVE_FGETXATTR
+
+/* Define to 1 if you have the `flistea' function. */
+#undef HAVE_FLISTEA
+
+/* Define to 1 if you have the `flistxattr' function. */
+#undef HAVE_FLISTXATTR
+
 /* Define to 1 if you have the <float.h> header file. */
 #undef HAVE_FLOAT_H
 
@@ -177,6 +250,18 @@
 /* Whether the system has freeifaddrs */
 #undef HAVE_FREEIFADDRS
 
+/* Define to 1 if you have the `fremoveea' function. */
+#undef HAVE_FREMOVEEA
+
+/* Define to 1 if you have the `fremovexattr' function. */
+#undef HAVE_FREMOVEXATTR
+
+/* Define to 1 if you have the `fsetea' function. */
+#undef HAVE_FSETEA
+
+/* Define to 1 if you have the `fsetxattr' function. */
+#undef HAVE_FSETXATTR
+
 /* Define to 1 if you have the `ftruncate' function. */
 #undef HAVE_FTRUNCATE
 
@@ -195,6 +280,9 @@
 /* Define to 1 if you have the `getdirentries' function. */
 #undef HAVE_GETDIRENTRIES
 
+/* Define to 1 if you have the `getea' function. */
+#undef HAVE_GETEA
+
 /* Define to 1 if you have the `getgrent_r' function. */
 #undef HAVE_GETGRENT_R
 
@@ -225,6 +313,9 @@
 /* Define to 1 if you have the `getpagesize' function. */
 #undef HAVE_GETPAGESIZE
 
+/* Whether we have getpeereid to get socket credentials */
+#undef HAVE_GETPEEREID
+
 /* Define to 1 if you have the `getpgrp' function. */
 #undef HAVE_GETPGRP
 
@@ -243,6 +334,9 @@
 /* Whether gettimeofday() is available */
 #undef HAVE_GETTIMEOFDAY_TZ
 
+/* Define to 1 if you have the `getxattr' function. */
+#undef HAVE_GETXATTR
+
 /* Define to 1 if you have the `get_current_dir_name' function. */
 #undef HAVE_GET_CURRENT_DIR_NAME
 
@@ -270,6 +364,9 @@
 /* Whether the compiler supports immediate structures */
 #undef HAVE_IMMEDIATE_STRUCTURES
 
+/* Whether mmap is incoherent against write */
+#undef HAVE_INCOHERENT_MMAP
+
 /* Define to 1 if you have the `inet_aton' function. */
 #undef HAVE_INET_ATON
 
@@ -306,6 +403,9 @@
 /* Define to 1 if you have the `lchown' function. */
 #undef HAVE_LCHOWN
 
+/* Define to 1 if you have the `attr' library (-lattr). */
+#undef HAVE_LIBATTR
+
 /* Define to 1 if you have the `ibverbs' library (-libverbs). */
 #undef HAVE_LIBIBVERBS
 
@@ -342,6 +442,12 @@
 /* Define to 1 if you have the <linux/types.h> header file. */
 #undef HAVE_LINUX_TYPES_H
 
+/* Define to 1 if you have the `listea' function. */
+#undef HAVE_LISTEA
+
+/* Define to 1 if you have the `listxattr' function. */
+#undef HAVE_LISTXATTR
+
 /* Define to 1 if you have the <locale.h> header file. */
 #undef HAVE_LOCALE_H
 
@@ -351,6 +457,12 @@
 /* Define to 1 if you have the `lstat' function. */
 #undef HAVE_LSTAT
 
+/* Define to 1 if you have the <malloc.h> header file. */
+#undef HAVE_MALLOC_H
+
+/* Define to 1 if you have the `memalign' function. */
+#undef HAVE_MEMALIGN
+
 /* Define to 1 if you have the `memcpy' function. */
 #undef HAVE_MEMCPY
 
@@ -423,6 +535,9 @@
 /* Define to 1 if you have the <pcp/pmda.h> header file. */
 #undef HAVE_PCP_PMDA_H
 
+/* Whether we can use SO_PEERCRED to get socket credentials */
+#undef HAVE_PEERCRED
+
 /* Define to 1 if you have the `pipe' function. */
 #undef HAVE_PIPE
 
@@ -435,6 +550,9 @@
 /* Define to 1 if you have the <popt.h> header file. */
 #undef HAVE_POPT_H
 
+/* Define to 1 if you have the `posix_memalign' function. */
+#undef HAVE_POSIX_MEMALIGN
+
 /* Define to 1 if you have the `pread' function. */
 #undef HAVE_PREAD
 
@@ -471,6 +589,12 @@
 /* Define to 1 if you have the `realpath' function. */
 #undef HAVE_REALPATH
 
+/* Define to 1 if you have the `removeea' function. */
+#undef HAVE_REMOVEEA
+
+/* Define to 1 if you have the `removexattr' function. */
+#undef HAVE_REMOVEXATTR
+
 /* Define to 1 if you have the `rename' function. */
 #undef HAVE_RENAME
 
@@ -489,6 +613,9 @@
 /* Define to 1 if you have the `setbuffer' function. */
 #undef HAVE_SETBUFFER
 
+/* Define to 1 if you have the `setea' function. */
+#undef HAVE_SETEA
+
 /* Define to 1 if you have the `setegid' function. */
 #undef HAVE_SETEGID
 
@@ -501,6 +628,12 @@
 /* Define to 1 if you have the `seteuid' function. */
 #undef HAVE_SETEUID
 
+/* Define to 1 if you have the `setgid' function. */
+#undef HAVE_SETGID
+
+/* Define to 1 if you have the `setgroups' function. */
+#undef HAVE_SETGROUPS
+
 /* Define to 1 if you have the <setjmp.h> header file. */
 #undef HAVE_SETJMP_H
 
@@ -525,6 +658,12 @@
 /* Define to 1 if you have the `setreuid' function. */
 #undef HAVE_SETREUID
 
+/* Define to 1 if you have the `setuid' function. */
+#undef HAVE_SETUID
+
+/* Define to 1 if you have the `setxattr' function. */
+#undef HAVE_SETXATTR
+
 /* Define to 1 if you have the <shadow.h> header file. */
 #undef HAVE_SHADOW_H
 
@@ -627,6 +766,9 @@
 /* Define to 1 if you have the <stropts.h> header file. */
 #undef HAVE_STROPTS_H
 
+/* Define to 1 if you have the `strptime' function. */
+#undef HAVE_STRPTIME
+
 /* Define to 1 if you have the `strtok_r' function. */
 #undef HAVE_STRTOK_R
 
@@ -673,12 +815,21 @@
 /* Define to 1 if you have the `symlink' function. */
 #undef HAVE_SYMLINK
 
+/* Define to 1 if you have the `syscall' function. */
+#undef HAVE_SYSCALL
+
+/* Define to 1 if you have the <syscall.h> header file. */
+#undef HAVE_SYSCALL_H
+
 /* Define to 1 if you have the <syslog.h> header file. */
 #undef HAVE_SYSLOG_H
 
 /* Define to 1 if you have the <sys/acl.h> header file. */
 #undef HAVE_SYS_ACL_H
 
+/* Define to 1 if you have the <sys/attributes.h> header file. */
+#undef HAVE_SYS_ATTRIBUTES_H
+
 /* Define to 1 if you have the <sys/capability.h> header file. */
 #undef HAVE_SYS_CAPABILITY_H
 
@@ -686,9 +837,15 @@
    */
 #undef HAVE_SYS_DIR_H
 
+/* Define to 1 if you have the <sys/ea.h> header file. */
+#undef HAVE_SYS_EA_H
+
 /* Define to 1 if you have the <sys/epoll.h> header file. */
 #undef HAVE_SYS_EPOLL_H
 
+/* Define to 1 if you have the <sys/extattr.h> header file. */
+#undef HAVE_SYS_EXTATTR_H
+
 /* Define to 1 if you have the <sys/fcntl.h> header file. */
 #undef HAVE_SYS_FCNTL_H
 
@@ -732,6 +889,9 @@
 /* Define to 1 if you have the <sys/priv.h> header file. */
 #undef HAVE_SYS_PRIV_H
 
+/* Define to 1 if you have the <sys/proplist.h> header file. */
+#undef HAVE_SYS_PROPLIST_H
+
 /* Define to 1 if you have the <sys/resource.h> header file. */
 #undef HAVE_SYS_RESOURCE_H
 
@@ -753,6 +913,9 @@
 /* Define to 1 if you have the <sys/stat.h> header file. */
 #undef HAVE_SYS_STAT_H
 
+/* Define to 1 if you have the <sys/syscall.h> header file. */
+#undef HAVE_SYS_SYSCALL_H
+
 /* Define to 1 if you have the <sys/syslog.h> header file. */
 #undef HAVE_SYS_SYSLOG_H
 
@@ -765,6 +928,9 @@
 /* Define to 1 if you have the <sys/types.h> header file. */
 #undef HAVE_SYS_TYPES_H
 
+/* Define to 1 if you have the <sys/ucontext.h> header file. */
+#undef HAVE_SYS_UCONTEXT_H
+
 /* Define to 1 if you have the <sys/uio.h> header file. */
 #undef HAVE_SYS_UIO_H
 
@@ -774,6 +940,9 @@
 /* Define to 1 if you have <sys/wait.h> that is POSIX.1 compatible. */
 #undef HAVE_SYS_WAIT_H
 
+/* Define to 1 if you have the <sys/xattr.h> header file. */
+#undef HAVE_SYS_XATTR_H
+
 /* Define to 1 if you have the <talloc.h> header file. */
 #undef HAVE_TALLOC_H
 
@@ -795,6 +964,9 @@
 /* Define to 1 if you have the <time.h> header file. */
 #undef HAVE_TIME_H
 
+/* Whether we have ucontext_t */
+#undef HAVE_UCONTEXT_T
+
 /* Define to 1 if the system has the type `uintptr_t'. */
 #undef HAVE_UINTPTR_T
 
@@ -855,6 +1027,9 @@
 /* Define to 1 if you have the <winsock2.h> header file. */
 #undef HAVE_WINSOCK2_H
 
+/* Whether strptime is working correct */
+#undef HAVE_WORKING_STRPTIME
+
 /* Define to 1 if you have the <ws2tcpip.h> header file. */
 #undef HAVE_WS2TCPIP_H
 
@@ -903,12 +1078,6 @@
 /* Define to the version of this package. */
 #undef PACKAGE_VERSION
 
-/* Whether getpass should be replaced */
-#undef REPLACE_GETPASS
-
-/* getpass returns <9 chars where getpassphrase returns <265 chars */
-#undef REPLACE_GETPASS_BY_GETPASSPHRASE
-
 /* Whether inet_ntoa should be replaced */
 #undef REPLACE_INET_NTOA
 
@@ -921,9 +1090,6 @@
 /* replace readdir using getdirentries() */
 #undef REPLACE_READDIR_GETDIRENTRIES
 
-/* Whether strptime should be replaced */
-#undef REPLACE_STRPTIME
-
 /* Whether seekdir returns an int */
 #undef SEEKDIR_RETURNS_INT
 
@@ -969,6 +1135,9 @@
 /* Whether telldir takes a const pointer */
 #undef TELLDIR_TAKES_CONST_DIR
 
+/* Max signal number value */
+#undef TEVENT_NUM_SIGNALS
+
 /* Define to 1 if you can safely include both <sys/time.h> and <time.h>. */
 #undef TIME_WITH_SYS_TIME
 
@@ -997,6 +1166,18 @@
 #endif
 
 
+/* The value of `NSIG'. */
+#undef VALUEOF_NSIG
+
+/* The value of `SIGRTMAX'. */
+#undef VALUEOF_SIGRTMAX
+
+/* The value of `SIGRTMIN'. */
+#undef VALUEOF_SIGRTMIN
+
+/* The value of `_NSIG'. */
+#undef VALUEOF__NSIG
+
 /* Define WORDS_BIGENDIAN to 1 if your processor stores words with the most
    significant byte first (like Motorola and SPARC, unlike Intel). */
 #if defined AC_APPLE_UNIVERSAL_BUILD
@@ -1009,6 +1190,15 @@
 # endif
 #endif
 
+/* xattr functions have additional options */
+#undef XATTR_ADDITIONAL_OPTIONS
+
+
+#ifndef _BSD_TYPES
+# undef _BSD_TYPES
+#endif
+
+
 /* Enable large inode numbers on Mac OS X 10.5.  */
 #ifndef _DARWIN_USE_64_BIT_INODE
 # define _DARWIN_USE_64_BIT_INODE 1
@@ -1054,6 +1244,12 @@
 #endif
 
 
+/* Define to `long' if <sys/types.h> does not define. */
+#undef blkcnt_t
+
+/* Define to `long' if <sys/types.h> does not define. */
+#undef blksize_t
+
 /* Define to `int' if <sys/types.h> doesn't define. */
 #undef gid_t
 
diff --git a/config.sub b/config.sub
old mode 100755
new mode 100644
index eb0389a..707e9e2
--- a/config.sub
+++ b/config.sub
@@ -1,44 +1,42 @@
 #! /bin/sh
 # Configuration validation subroutine script.
 #   Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999,
-#   2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009
-#   Free Software Foundation, Inc.
+#   2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010,
+#   2011, 2012, 2013 Free Software Foundation, Inc.
 
-timestamp='2009-06-11'
+timestamp='2013-01-11'
 
-# This file is (in principle) common to ALL GNU software.
-# The presence of a machine in this file suggests that SOME GNU software
-# can handle that machine.  It does not imply ALL GNU software can.
-#
-# This file 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
+# This file 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 3 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.
+# 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., 51 Franklin Street - Fifth Floor, Boston, MA
-# 02110-1301, USA.
+# along with this program; if not, see <http://www.gnu.org/licenses/>.
 #
 # As a special exception to the GNU General Public License, if you
 # distribute this file as part of a program that contains a
 # configuration script generated by Autoconf, you may include it under
-# the same distribution terms that you use for the rest of that program.
+# the same distribution terms that you use for the rest of that
+# program.  This Exception is an additional permission under section 7
+# of the GNU General Public License, version 3 ("GPLv3").
 
 
-# Please send patches to <config-patches at gnu.org>.  Submit a context
-# diff and a properly formatted ChangeLog entry.
+# Please send patches with a ChangeLog entry to config-patches at gnu.org.
 #
 # Configuration subroutine to validate and canonicalize a configuration type.
 # Supply the specified configuration type as an argument.
 # If it is invalid, we print an error message on stderr and exit with code 1.
 # Otherwise, we print the canonical config type on stdout and succeed.
 
+# You can get the latest version of this script from:
+# http://git.savannah.gnu.org/gitweb/?p=config.git;a=blob_plain;f=config.sub;hb=HEAD
+
 # This file is supposed to be the same for all GNU packages
 # and recognize all the CPU types, system types and aliases
 # that are meaningful with *any* GNU software.
@@ -72,8 +70,9 @@ Report bugs and patches to <config-patches at gnu.org>."
 version="\
 GNU config.sub ($timestamp)
 
-Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001,
-2002, 2003, 2004, 2005, 2006, 2007, 2008 Free Software Foundation, Inc.
+Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000,
+2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011,
+2012, 2013 Free Software Foundation, Inc.
 
 This is free software; see the source for copying conditions.  There is NO
 warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE."
@@ -120,13 +119,18 @@ esac
 # Here we must recognize all the valid KERNEL-OS combinations.
 maybe_os=`echo $1 | sed 's/^\(.*\)-\([^-]*-[^-]*\)$/\2/'`
 case $maybe_os in
-  nto-qnx* | linux-gnu* | linux-dietlibc | linux-newlib* | linux-uclibc* | \
-  uclinux-uclibc* | uclinux-gnu* | kfreebsd*-gnu* | knetbsd*-gnu* | netbsd*-gnu* | \
+  nto-qnx* | linux-gnu* | linux-android* | linux-dietlibc | linux-newlib* | \
+  linux-musl* | linux-uclibc* | uclinux-uclibc* | uclinux-gnu* | kfreebsd*-gnu* | \
+  knetbsd*-gnu* | netbsd*-gnu* | \
   kopensolaris*-gnu* | \
   storm-chaos* | os2-emx* | rtmk-nova*)
     os=-$maybe_os
     basic_machine=`echo $1 | sed 's/^\(.*\)-\([^-]*-[^-]*\)$/\1/'`
     ;;
+  android-linux)
+    os=-linux-android
+    basic_machine=`echo $1 | sed 's/^\(.*\)-\([^-]*-[^-]*\)$/\1/'`-unknown
+    ;;
   *)
     basic_machine=`echo $1 | sed 's/-[^-]*$//'`
     if [ $basic_machine != $1 ]
@@ -149,12 +153,12 @@ case $os in
 	-convergent* | -ncr* | -news | -32* | -3600* | -3100* | -hitachi* |\
 	-c[123]* | -convex* | -sun | -crds | -omron* | -dg | -ultra | -tti* | \
 	-harris | -dolphin | -highlevel | -gould | -cbm | -ns | -masscomp | \
-	-apple | -axis | -knuth | -cray)
+	-apple | -axis | -knuth | -cray | -microblaze*)
 		os=
 		basic_machine=$1
 		;;
-        -bluegene*)
-	        os=-cnk
+	-bluegene*)
+		os=-cnk
 		;;
 	-sim | -cisco | -oki | -wec | -winbond)
 		os=
@@ -170,10 +174,10 @@ case $os in
 		os=-chorusos
 		basic_machine=$1
 		;;
- 	-chorusrdb)
- 		os=-chorusrdb
+	-chorusrdb)
+		os=-chorusrdb
 		basic_machine=$1
- 		;;
+		;;
 	-hiux*)
 		os=-hiuxwe2
 		;;
@@ -218,6 +222,12 @@ case $os in
 	-isc*)
 		basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
 		;;
+	-lynx*178)
+		os=-lynxos178
+		;;
+	-lynx*5)
+		os=-lynxos5
+		;;
 	-lynx*)
 		os=-lynxos
 		;;
@@ -242,20 +252,27 @@ case $basic_machine in
 	# Some are omitted here because they have special meanings below.
 	1750a | 580 \
 	| a29k \
+	| aarch64 | aarch64_be \
 	| alpha | alphaev[4-8] | alphaev56 | alphaev6[78] | alphapca5[67] \
 	| alpha64 | alpha64ev[4-8] | alpha64ev56 | alpha64ev6[78] | alpha64pca5[67] \
 	| am33_2.0 \
-	| arc | arm | arm[bl]e | arme[lb] | armv[2345] | armv[345][lb] | avr | avr32 \
+	| arc \
+	| arm | arm[bl]e | arme[lb] | armv[2-8] | armv[3-8][lb] | armv7[arm] \
+	| avr | avr32 \
+	| be32 | be64 \
 	| bfin \
 	| c4x | clipper \
 	| d10v | d30v | dlx | dsp16xx \
+	| epiphany \
 	| fido | fr30 | frv \
 	| h8300 | h8500 | hppa | hppa1.[01] | hppa2.0 | hppa2.0[nw] | hppa64 \
+	| hexagon \
 	| i370 | i860 | i960 | ia64 \
 	| ip2k | iq2000 \
+	| le32 | le64 \
 	| lm32 \
 	| m32c | m32r | m32rle | m68000 | m68k | m88k \
-	| maxq | mb | microblaze | mcore | mep | metag \
+	| maxq | mb | microblaze | microblazeel | mcore | mep | metag \
 	| mips | mipsbe | mipseb | mipsel | mipsle \
 	| mips16 \
 	| mips64 | mips64el \
@@ -273,32 +290,45 @@ case $basic_machine in
 	| mipsisa64r2 | mipsisa64r2el \
 	| mipsisa64sb1 | mipsisa64sb1el \
 	| mipsisa64sr71k | mipsisa64sr71kel \
+	| mipsr5900 | mipsr5900el \
 	| mipstx39 | mipstx39el \
 	| mn10200 | mn10300 \
 	| moxie \
 	| mt \
 	| msp430 \
+	| nds32 | nds32le | nds32be \
 	| nios | nios2 \
 	| ns16k | ns32k \
+	| open8 \
 	| or32 \
 	| pdp10 | pdp11 | pj | pjl \
-	| powerpc | powerpc64 | powerpc64le | powerpcle | ppcbe \
+	| powerpc | powerpc64 | powerpc64le | powerpcle \
 	| pyramid \
+	| rl78 | rx \
 	| score \
 	| sh | sh[1234] | sh[24]a | sh[24]aeb | sh[23]e | sh[34]eb | sheb | shbe | shle | sh[1234]le | sh3ele \
 	| sh64 | sh64le \
 	| sparc | sparc64 | sparc64b | sparc64v | sparc86x | sparclet | sparclite \
 	| sparcv8 | sparcv9 | sparcv9b | sparcv9v \
-	| spu | strongarm \
-	| tahoe | thumb | tic4x | tic80 | tron \
-	| v850 | v850e \
+	| spu \
+	| tahoe | tic4x | tic54x | tic55x | tic6x | tic80 | tron \
+	| ubicom32 \
+	| v850 | v850e | v850e1 | v850e2 | v850es | v850e2v3 \
 	| we32k \
-	| x86 | xc16x | xscale | xscalee[bl] | xstormy16 | xtensa \
+	| x86 | xc16x | xstormy16 | xtensa \
 	| z8k | z80)
 		basic_machine=$basic_machine-unknown
 		;;
-	m6811 | m68hc11 | m6812 | m68hc12)
-		# Motorola 68HC11/12.
+	c54x)
+		basic_machine=tic54x-unknown
+		;;
+	c55x)
+		basic_machine=tic55x-unknown
+		;;
+	c6x)
+		basic_machine=tic6x-unknown
+		;;
+	m6811 | m68hc11 | m6812 | m68hc12 | m68hcs12x | picochip)
 		basic_machine=$basic_machine-unknown
 		os=-none
 		;;
@@ -308,6 +338,21 @@ case $basic_machine in
 		basic_machine=mt-unknown
 		;;
 
+	strongarm | thumb | xscale)
+		basic_machine=arm-unknown
+		;;
+	xgate)
+		basic_machine=$basic_machine-unknown
+		os=-none
+		;;
+	xscaleeb)
+		basic_machine=armeb-unknown
+		;;
+
+	xscaleel)
+		basic_machine=armel-unknown
+		;;
+
 	# We use `pc' rather than `unknown'
 	# because (1) that's what they normally are, and
 	# (2) the word "unknown" tends to confuse beginning users.
@@ -322,25 +367,30 @@ case $basic_machine in
 	# Recognize the basic CPU types with company name.
 	580-* \
 	| a29k-* \
+	| aarch64-* | aarch64_be-* \
 	| alpha-* | alphaev[4-8]-* | alphaev56-* | alphaev6[78]-* \
 	| alpha64-* | alpha64ev[4-8]-* | alpha64ev56-* | alpha64ev6[78]-* \
 	| alphapca5[67]-* | alpha64pca5[67]-* | arc-* \
 	| arm-*  | armbe-* | armle-* | armeb-* | armv*-* \
 	| avr-* | avr32-* \
+	| be32-* | be64-* \
 	| bfin-* | bs2000-* \
-	| c[123]* | c30-* | [cjt]90-* | c4x-* | c54x-* | c55x-* | c6x-* \
+	| c[123]* | c30-* | [cjt]90-* | c4x-* \
 	| clipper-* | craynv-* | cydra-* \
 	| d10v-* | d30v-* | dlx-* \
 	| elxsi-* \
 	| f30[01]-* | f700-* | fido-* | fr30-* | frv-* | fx80-* \
 	| h8300-* | h8500-* \
 	| hppa-* | hppa1.[01]-* | hppa2.0-* | hppa2.0[nw]-* | hppa64-* \
+	| hexagon-* \
 	| i*86-* | i860-* | i960-* | ia64-* \
 	| ip2k-* | iq2000-* \
+	| le32-* | le64-* \
 	| lm32-* \
 	| m32c-* | m32r-* | m32rle-* \
 	| m68000-* | m680[012346]0-* | m68360-* | m683?2-* | m68k-* \
 	| m88110-* | m88k-* | maxq-* | mcore-* | metag-* \
+	| microblaze-* | microblazeel-* \
 	| mips-* | mipsbe-* | mipseb-* | mipsel-* | mipsle-* \
 	| mips16-* \
 	| mips64-* | mips64el-* \
@@ -358,28 +408,34 @@ case $basic_machine in
 	| mipsisa64r2-* | mipsisa64r2el-* \
 	| mipsisa64sb1-* | mipsisa64sb1el-* \
 	| mipsisa64sr71k-* | mipsisa64sr71kel-* \
+	| mipsr5900-* | mipsr5900el-* \
 	| mipstx39-* | mipstx39el-* \
 	| mmix-* \
 	| mt-* \
 	| msp430-* \
+	| nds32-* | nds32le-* | nds32be-* \
 	| nios-* | nios2-* \
 	| none-* | np1-* | ns16k-* | ns32k-* \
+	| open8-* \
 	| orion-* \
 	| pdp10-* | pdp11-* | pj-* | pjl-* | pn-* | power-* \
-	| powerpc-* | powerpc64-* | powerpc64le-* | powerpcle-* | ppcbe-* \
+	| powerpc-* | powerpc64-* | powerpc64le-* | powerpcle-* \
 	| pyramid-* \
-	| romp-* | rs6000-* \
+	| rl78-* | romp-* | rs6000-* | rx-* \
 	| sh-* | sh[1234]-* | sh[24]a-* | sh[24]aeb-* | sh[23]e-* | sh[34]eb-* | sheb-* | shbe-* \
 	| shle-* | sh[1234]le-* | sh3ele-* | sh64-* | sh64le-* \
 	| sparc-* | sparc64-* | sparc64b-* | sparc64v-* | sparc86x-* | sparclet-* \
 	| sparclite-* \
-	| sparcv8-* | sparcv9-* | sparcv9b-* | sparcv9v-* | strongarm-* | sv1-* | sx?-* \
-	| tahoe-* | thumb-* \
-	| tic30-* | tic4x-* | tic54x-* | tic55x-* | tic6x-* | tic80-* | tile-* \
+	| sparcv8-* | sparcv9-* | sparcv9b-* | sparcv9v-* | sv1-* | sx?-* \
+	| tahoe-* \
+	| tic30-* | tic4x-* | tic54x-* | tic55x-* | tic6x-* | tic80-* \
+	| tile*-* \
 	| tron-* \
-	| v850-* | v850e-* | vax-* \
+	| ubicom32-* \
+	| v850-* | v850e-* | v850e1-* | v850es-* | v850e2-* | v850e2v3-* \
+	| vax-* \
 	| we32k-* \
-	| x86-* | x86_64-* | xc16x-* | xps100-* | xscale-* | xscalee[bl]-* \
+	| x86-* | x86_64-* | xc16x-* | xps100-* \
 	| xstormy16-* | xtensa*-* \
 	| ymp-* \
 	| z8k-* | z80-*)
@@ -404,7 +460,7 @@ case $basic_machine in
 		basic_machine=a29k-amd
 		os=-udi
 		;;
-    	abacus)
+	abacus)
 		basic_machine=abacus-unknown
 		;;
 	adobe68k)
@@ -474,11 +530,20 @@ case $basic_machine in
 		basic_machine=powerpc-ibm
 		os=-cnk
 		;;
+	c54x-*)
+		basic_machine=tic54x-`echo $basic_machine | sed 's/^[^-]*-//'`
+		;;
+	c55x-*)
+		basic_machine=tic55x-`echo $basic_machine | sed 's/^[^-]*-//'`
+		;;
+	c6x-*)
+		basic_machine=tic6x-`echo $basic_machine | sed 's/^[^-]*-//'`
+		;;
 	c90)
 		basic_machine=c90-cray
 		os=-unicos
 		;;
-        cegcc)
+	cegcc)
 		basic_machine=arm-unknown
 		os=-cegcc
 		;;
@@ -510,7 +575,7 @@ case $basic_machine in
 		basic_machine=craynv-cray
 		os=-unicosmp
 		;;
-	cr16)
+	cr16 | cr16-*)
 		basic_machine=cr16-unknown
 		os=-elf
 		;;
@@ -668,7 +733,6 @@ case $basic_machine in
 	i370-ibm* | ibm*)
 		basic_machine=i370-ibm
 		;;
-# I'm not sure what "Sysv32" means.  Should this be sysv3.2?
 	i*86v32)
 		basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'`
 		os=-sysv32
@@ -726,6 +790,13 @@ case $basic_machine in
 		basic_machine=ns32k-utek
 		os=-sysv
 		;;
+	microblaze*)
+		basic_machine=microblaze-xilinx
+		;;
+	mingw64)
+		basic_machine=x86_64-pc
+		os=-mingw64
+		;;
 	mingw32)
 		basic_machine=i386-pc
 		os=-mingw32
@@ -762,10 +833,18 @@ case $basic_machine in
 	ms1-*)
 		basic_machine=`echo $basic_machine | sed -e 's/ms1-/mt-/'`
 		;;
+	msys)
+		basic_machine=i386-pc
+		os=-msys
+		;;
 	mvs)
 		basic_machine=i370-ibm
 		os=-mvs
 		;;
+	nacl)
+		basic_machine=le32-unknown
+		os=-nacl
+		;;
 	ncr3000)
 		basic_machine=i486-ncr
 		os=-sysv4
@@ -830,6 +909,12 @@ case $basic_machine in
 	np1)
 		basic_machine=np1-gould
 		;;
+	neo-tandem)
+		basic_machine=neo-tandem
+		;;
+	nse-tandem)
+		basic_machine=nse-tandem
+		;;
 	nsr-tandem)
 		basic_machine=nsr-tandem
 		;;
@@ -912,9 +997,10 @@ case $basic_machine in
 		;;
 	power)	basic_machine=power-ibm
 		;;
-	ppc)	basic_machine=powerpc-unknown
+	ppc | ppcbe)	basic_machine=powerpc-unknown
 		;;
-	ppc-*)	basic_machine=powerpc-`echo $basic_machine | sed 's/^[^-]*-//'`
+	ppc-* | ppcbe-*)
+		basic_machine=powerpc-`echo $basic_machine | sed 's/^[^-]*-//'`
 		;;
 	ppcle | powerpclittle | ppc-le | powerpc-little)
 		basic_machine=powerpcle-unknown
@@ -939,7 +1025,11 @@ case $basic_machine in
 		basic_machine=i586-unknown
 		os=-pw32
 		;;
-	rdos)
+	rdos | rdos64)
+		basic_machine=x86_64-pc
+		os=-rdos
+		;;
+	rdos32)
 		basic_machine=i386-pc
 		os=-rdos
 		;;
@@ -1008,6 +1098,9 @@ case $basic_machine in
 		basic_machine=i860-stratus
 		os=-sysv4
 		;;
+	strongarm-* | thumb-*)
+		basic_machine=arm-`echo $basic_machine | sed 's/^[^-]*-//'`
+		;;
 	sun2)
 		basic_machine=m68000-sun
 		;;
@@ -1064,20 +1157,8 @@ case $basic_machine in
 		basic_machine=t90-cray
 		os=-unicos
 		;;
-	tic54x | c54x*)
-		basic_machine=tic54x-unknown
-		os=-coff
-		;;
-	tic55x | c55x*)
-		basic_machine=tic55x-unknown
-		os=-coff
-		;;
-	tic6x | c6x*)
-		basic_machine=tic6x-unknown
-		os=-coff
-		;;
 	tile*)
-		basic_machine=tile-unknown
+		basic_machine=$basic_machine-unknown
 		os=-linux-gnu
 		;;
 	tx39)
@@ -1147,6 +1228,9 @@ case $basic_machine in
 	xps | xps100)
 		basic_machine=xps100-honeywell
 		;;
+	xscale-* | xscalee[bl]-*)
+		basic_machine=`echo $basic_machine | sed 's/^xscale/arm/'`
+		;;
 	ymp)
 		basic_machine=ymp-cray
 		os=-unicos
@@ -1244,9 +1328,12 @@ esac
 if [ x"$os" != x"" ]
 then
 case $os in
-        # First match some system type aliases
-        # that might get confused with valid system types.
+	# First match some system type aliases
+	# that might get confused with valid system types.
 	# -solaris* is a basic system type, with this one exception.
+	-auroraux)
+		os=-auroraux
+		;;
 	-solaris1 | -solaris1.*)
 		os=`echo $os | sed -e 's|solaris1|sunos4|'`
 		;;
@@ -1268,21 +1355,22 @@ case $os in
 	# -sysv* is not here because it comes later, after sysvr4.
 	-gnu* | -bsd* | -mach* | -minix* | -genix* | -ultrix* | -irix* \
 	      | -*vms* | -sco* | -esix* | -isc* | -aix* | -cnk* | -sunos | -sunos[34]*\
-	      | -hpux* | -unos* | -osf* | -luna* | -dgux* | -solaris* | -sym* \
-	      | -kopensolaris* \
+	      | -hpux* | -unos* | -osf* | -luna* | -dgux* | -auroraux* | -solaris* \
+	      | -sym* | -kopensolaris* | -plan9* \
 	      | -amigaos* | -amigados* | -msdos* | -newsos* | -unicos* | -aof* \
 	      | -aos* | -aros* \
 	      | -nindy* | -vxsim* | -vxworks* | -ebmon* | -hms* | -mvs* \
 	      | -clix* | -riscos* | -uniplus* | -iris* | -rtu* | -xenix* \
 	      | -hiux* | -386bsd* | -knetbsd* | -mirbsd* | -netbsd* \
-	      | -openbsd* | -solidbsd* \
+	      | -bitrig* | -openbsd* | -solidbsd* \
 	      | -ekkobsd* | -kfreebsd* | -freebsd* | -riscix* | -lynxos* \
 	      | -bosx* | -nextstep* | -cxux* | -aout* | -elf* | -oabi* \
 	      | -ptx* | -coff* | -ecoff* | -winnt* | -domain* | -vsta* \
 	      | -udi* | -eabi* | -lites* | -ieee* | -go32* | -aux* \
 	      | -chorusos* | -chorusrdb* | -cegcc* \
-	      | -cygwin* | -pe* | -psos* | -moss* | -proelf* | -rtems* \
-	      | -mingw32* | -linux-gnu* | -linux-newlib* | -linux-uclibc* \
+	      | -cygwin* | -msys* | -pe* | -psos* | -moss* | -proelf* | -rtems* \
+	      | -mingw32* | -mingw64* | -linux-gnu* | -linux-android* \
+	      | -linux-newlib* | -linux-musl* | -linux-uclibc* \
 	      | -uxpv* | -beos* | -mpeix* | -udk* \
 	      | -interix* | -uwin* | -mks* | -rhapsody* | -darwin* | -opened* \
 	      | -openstep* | -oskit* | -conix* | -pw32* | -nonstopux* \
@@ -1290,7 +1378,7 @@ case $os in
 	      | -os2* | -vos* | -palmos* | -uclinux* | -nucleus* \
 	      | -morphos* | -superux* | -rtmk* | -rtmk-nova* | -windiss* \
 	      | -powermax* | -dnix* | -nx6 | -nx7 | -sei* | -dragonfly* \
-	      | -skyos* | -haiku* | -rdos* | -toppers* | -drops*)
+	      | -skyos* | -haiku* | -rdos* | -toppers* | -drops* | -es*)
 	# Remember, each alternative MUST END IN *, to match a version number.
 		;;
 	-qnx*)
@@ -1329,7 +1417,7 @@ case $os in
 	-opened*)
 		os=-openedition
 		;;
-        -os400*)
+	-os400*)
 		os=-os400
 		;;
 	-wince*)
@@ -1378,7 +1466,7 @@ case $os in
 	-sinix*)
 		os=-sysv4
 		;;
-        -tpf*)
+	-tpf*)
 		os=-tpf
 		;;
 	-triton*)
@@ -1414,15 +1502,14 @@ case $os in
 	-aros*)
 		os=-aros
 		;;
-	-kaos*)
-		os=-kaos
-		;;
 	-zvmoe)
 		os=-zvmoe
 		;;
 	-dicos*)
 		os=-dicos
 		;;
+	-nacl*)
+		;;
 	-none)
 		;;
 	*)
@@ -1445,10 +1532,10 @@ else
 # system, and we'll never get to this point.
 
 case $basic_machine in
-        score-*)
+	score-*)
 		os=-elf
 		;;
-        spu-*)
+	spu-*)
 		os=-elf
 		;;
 	*-acorn)
@@ -1460,8 +1547,20 @@ case $basic_machine in
 	arm*-semi)
 		os=-aout
 		;;
-        c4x-* | tic4x-*)
-        	os=-coff
+	c4x-* | tic4x-*)
+		os=-coff
+		;;
+	hexagon-*)
+		os=-elf
+		;;
+	tic54x-*)
+		os=-coff
+		;;
+	tic55x-*)
+		os=-coff
+		;;
+	tic6x-*)
+		os=-coff
 		;;
 	# This must come before the *-dec entry.
 	pdp10-*)
@@ -1481,14 +1580,11 @@ case $basic_machine in
 		;;
 	m68000-sun)
 		os=-sunos3
-		# This also exists in the configure program, but was not the
-		# default.
-		# os=-sunos4
 		;;
 	m68*-cisco)
 		os=-aout
 		;;
-        mep-*)
+	mep-*)
 		os=-elf
 		;;
 	mips*-cisco)
@@ -1515,7 +1611,7 @@ case $basic_machine in
 	*-ibm)
 		os=-aix
 		;;
-    	*-knuth)
+	*-knuth)
 		os=-mmixware
 		;;
 	*-wec)
diff --git a/config/ctdb-crash-cleanup.sh b/config/ctdb-crash-cleanup.sh
index f426056..d26838e 100755
--- a/config/ctdb-crash-cleanup.sh
+++ b/config/ctdb-crash-cleanup.sh
@@ -4,16 +4,16 @@
 # all public ip addresses if CTDBD has crashed or stopped running.
 #
 
-# If ctdb is running, just exit
-if ctdb ping >/dev/null 2>&1 ; then
-    exit 0
-fi
-
 [ -n "$CTDB_BASE" ] || \
     export CTDB_BASE=$(cd -P $(dirname "$0") ; echo "$PWD")
 
 . "$CTDB_BASE/functions"
 
+# If ctdb is running, just exit
+if service ctdb status >/dev/null 2>&1 ; then
+    exit 0
+fi
+
 loadconfig ctdb
 
 [ -n "$CTDB_PUBLIC_ADDRESSES" ] || \
@@ -22,8 +22,8 @@ loadconfig ctdb
 [ -f "$CTDB_PUBLIC_ADDRESSES" ] || \
     die "No public addresses file found. Can't clean up."
 
-drop_all_public_ips "ctdb-crash-cleanup"
+drop_all_public_ips "ctdb-crash-cleanup.sh"
 
 if [ -n "$CTDB_NATGW_PUBLIC_IP" ] ; then
-    drop_ip "$CTDB_NATGW_PUBLIC_IP" "ctdb-crash-cleanup"
+    drop_ip "$CTDB_NATGW_PUBLIC_IP" "ctdb-crash-cleanup.sh"
 fi
diff --git a/config/ctdb.init b/config/ctdb.init
index 9f9b686..2ceb45f 100755
--- a/config/ctdb.init
+++ b/config/ctdb.init
@@ -6,7 +6,7 @@
 # chkconfig:           - 90 01
 #
 # description:                 Starts and stops the clustered tdb daemon
-# pidfile:             /var/run/ctdbd/ctdbd.pid
+# pidfile:             /var/run/ctdb/ctdbd.pid
 #
 
 ### BEGIN INIT INFO
@@ -32,6 +32,10 @@ fi
     LC_ALL=en_US.UTF-8
 }
 
+if [ -f /lib/lsb/init-functions ] ; then
+    . /lib/lsb/init-functions
+fi
+
 # Avoid using root's TMPDIR
 unset TMPDIR
 
@@ -50,6 +54,7 @@ detect_init_style
 export CTDB_INIT_STYLE
 
 ctdbd=${CTDBD:-/usr/sbin/ctdbd}
+pidfile="/var/run/ctdb/ctdbd.pid"
 
 if [ "$CTDB_VALGRIND" = "yes" ]; then
     init_style="valgrind"
@@ -84,6 +89,9 @@ build_ctdb_options () {
     }
     maybe_set "--reclock"                "$CTDB_RECOVERY_LOCK"
 
+    mkdir -p $(dirname "$pidfile")
+    maybe_set "--pidfile"                "$pidfile"
+
     # build up CTDB_OPTIONS variable from optional parameters
     maybe_set "--logfile"                "$CTDB_LOGFILE"
     maybe_set "--nlist"                  "$CTDB_NODES"
@@ -95,7 +103,6 @@ build_ctdb_options () {
     maybe_set "--event-script-dir"       "$CTDB_EVENT_SCRIPT_DIR"
     maybe_set "--transport"              "$CTDB_TRANSPORT"
     maybe_set "-d"                       "$CTDB_DEBUGLEVEL"
-    maybe_set "--debug-hung-script"      "$CTDB_DEBUG_HUNG_SCRIPT"
     maybe_set "--notification-script"    "$CTDB_NOTIFY_SCRIPT"
     maybe_set "--start-as-disabled"      "$CTDB_START_AS_DISABLED"    "yes"
     maybe_set "--start-as-stopped "      "$CTDB_START_AS_STOPPED"     "yes"
@@ -108,6 +115,11 @@ build_ctdb_options () {
     maybe_set "--max-persistent-check-errors" "$CTDB_MAX_PERSISTENT_CHECK_ERRORS"
 }
 
+export_debug_variables ()
+{
+    export CTDB_DEBUG_HUNG_SCRIPT CTDB_EXTERNAL_TRACE
+}
+
 # Log given message or stdin to either syslog or a CTDB log file
 do_log ()
 {
@@ -118,17 +130,17 @@ select_tdb_checker ()
 {
     # Find the best TDB consistency check available.
     use_tdb_tool_check=false
-    if [ -x /usr/bin/tdbtool ] && \
-	echo "help" | /usr/bin/tdbtool | grep -q check ; then
+    if which tdbtool >/dev/null 2>&1 && \
+	echo "help" | tdbtool | grep -q check ; then
 
 	use_tdb_tool_check=true
-    elif [ -x /usr/bin/tdbtool -a -x /usr/bin/tdbdump ] ; then
+    elif which tdbtool >/dev/null 2>&1 && which tdbdump >/dev/null 2>&1 ; then
 	    do_log <<EOF
 WARNING: The installed 'tdbtool' does not offer the 'check' subcommand.
  Using 'tdbdump' for database checks.
  Consider updating 'tdbtool' for better checks!
 EOF
-    elif [ -x /usr/bin/tdbdump ] ; then
+    elif which tdbdump >/dev/null 2>&1 ; then
 	do_log <<EOF
 WARNING: 'tdbtool' is not available.
  Using 'tdbdump' to check the databases.
@@ -208,7 +220,7 @@ wait_until_ready () {
     _timeout="${1:-10}" # default is 10 seconds
 
     _count=0
-    while ! ctdb ping >/dev/null 2>&1 ; do
+    while ! ctdb runstate first_recovery startup running >/dev/null 2>&1 ; do
 	if [ $_count -ge $_timeout ] ; then
 	    return 1
 	fi
@@ -217,8 +229,6 @@ wait_until_ready () {
     done
 }
 
-ctdbd=${CTDBD:-/usr/sbin/ctdbd}
-
 start() {
     echo -n $"Starting ctdbd service: "
 
@@ -235,9 +245,11 @@ start() {
 
     build_ctdb_options
 
+    export_debug_variables
+
     # make sure we drop any ips that might still be held if previous
     # instance of ctdb got killed with -9 or similar
-    drop_all_public_ips
+    drop_all_public_ips "ctdb.init"
 
     if select_tdb_checker ; then
 	check_persistent_databases || return $?
@@ -276,6 +288,7 @@ start() {
     if [ $RETVAL -eq 0 ] ; then
 	if ! wait_until_ready ; then
 	    RETVAL=1
+	    echo "Timed out waiting for initialisation - killing CTDB"
 	    pkill -9 -f $ctdbd >/dev/null 2>&1
 	fi
     fi
@@ -323,6 +336,8 @@ stop() {
     # make sure all ips are dropped, pfkill -9 might leave them hanging around
     drop_all_public_ips
 
+    rm -f "$pidfile"
+
     case $init_style in
 	suse)
 	    # re-set the return code to the recorded RETVAL in order
@@ -345,33 +360,47 @@ restart() {
     start
 }
 
-status() {
-    echo -n $"Checking for ctdbd service: "
-    _out=$(ctdb ping 2>&1) || {
-	RETVAL=$?
-	echo -n "  ctdbd not running. "
-	case $init_style in
-	    suse)
-		set_retval $RETVAL
-		rc_status -v
-		;;
-	    redhat)
-		if [ -f /var/lock/subsys/ctdb ]; then
-			echo $"ctdb dead but subsys locked"
-			RETVAL=2
-		else
-			echo $"ctdb is stopped"
-			RETVAL=3
-		fi
-		;;
-	esac
-        echo 'Output from "ctdb ping":'
-        echo "$_out"
+# Given that CTDB_VALGRIND is a debug option we don't support the pid
+# file.  We just do a quick and dirty hack instead.  Otherwise we just
+# end up re-implementing each distro's pidfile support...
+check_status_valgrind ()
+{
+    if pkill -0 -f "valgrind.*${ctdbd}" ; then
+	echo "ctdbd is running under valgrind..."
+	return 0
+    else
+	echo "ctdbd is not running"
+	return 1
+    fi
+}
 
-	return $RETVAL
-    }
-    echo ""
-    ctdb status
+check_status ()
+{
+    # Backward compatibility.  When we arrange to pass --pidfile to
+    # ctdbd we also create the directory that will contain it.  If
+    # that directory is missing then we don't use the pidfile to check
+    # status.
+    if [ -d $(dirname "$pidfile") ] ; then
+	_pf_opt="-p $pidfile"
+    else
+	_pf_opt=""
+    fi
+
+    case "$init_style" in
+	valgrind)
+	    check_status_valgrind
+	    ;;
+	suse)
+	    checkproc $_pf_opt "$ctdbd"
+	    rc_status -v
+	    ;;
+	redhat)
+	    status $_pf_opt -l "ctdb" "$ctdbd"
+	    ;;
+	debian)
+	    status_of_proc $_pf_opt "$ctdbd" "ctdb"
+	    ;;
+    esac
 }
 
 
@@ -388,14 +417,16 @@ case "$1" in
   	restart
 	;;
     status)
-  	status
+  	check_status
 	;;
     condrestart|try-restart)
-  	ctdb status > /dev/null && restart || :
+  	if check_status >/dev/null ; then
+	    restart
+	fi
 	;;
     cron)
 	# used from cron to auto-restart ctdb
-  	ctdb status > /dev/null || restart
+  	check_status >/dev/null || restart
 	;;
     *)
 	echo $"Usage: $0 {start|stop|restart|reload|force-reload|status|cron|condrestart|try-restart}"
diff --git a/config/ctdb.sudoers b/config/ctdb.sudoers
new file mode 100644
index 0000000..1c6619b
--- /dev/null
+++ b/config/ctdb.sudoers
@@ -0,0 +1,3 @@
+Defaults!/etc/ctdb/statd-callout	!requiretty
+
+rpcuser		ALL=(ALL) 	NOPASSWD: /etc/ctdb/statd-callout
diff --git a/config/ctdb.sysconfig b/config/ctdb.sysconfig
index fecc7a5..6f58e8f 100644
--- a/config/ctdb.sysconfig
+++ b/config/ctdb.sysconfig
@@ -291,7 +291,7 @@ CTDB_DEBUGLEVEL=ERR
 
 # Monitor filesystem useage.
 # when set, and the 40.fs_use eventscript is enabled, this variable
-# allows to monitor the filesystem use and flag a node as unhealthy when
+# allows one to monitor the filesystem use and flag a node as unhealthy when
 # the filesystem becomes too full.
 # This is useful for example when /var grows too big.
 # Example: monitor both / and /var and make the node unhealthy when eitehr go
diff --git a/config/events.d/00.ctdb b/config/events.d/00.ctdb
index 0261353..02d1569 100755
--- a/config/events.d/00.ctdb
+++ b/config/events.d/00.ctdb
@@ -53,7 +53,7 @@ wait_until_ready () {
     _timeout="${1:-10}" # default is 10 seconds
 
     _count=0
-    while ! ctdb ping >/dev/null 2>&1 ; do
+    while ! ctdb runstate setup >/dev/null 2>&1 ; do
 	if [ $_count -ge $_timeout ] ; then
 	    return 1
 	fi
@@ -88,11 +88,6 @@ case "$1" in
 	update_config_from_tdb &
 	;;
     monitor)
-	# Inherit the debug level from ctdbd on each monitor run.  If
-	# there's a more urgent need then override CTDB_CURRENT_DEBUGLEVEL
-	# using a file in $CTDB_BASE/rc.local.d/.
-        ctdb_set_current_debuglevel create
-
 	# We should never enter swap, so SwapTotal == SwapFree.
 	[ "$CTDB_CHECK_SWAP_IS_NOT_USED" = "yes" ] && {
 	    if [ -n "`grep '^Swap\(Total\|Free\)' /proc/meminfo | uniq -s 10 -u`" ]; then
diff --git a/config/events.d/01.reclock b/config/events.d/01.reclock
index a3bfc66..ec50989 100755
--- a/config/events.d/01.reclock
+++ b/config/events.d/01.reclock
@@ -15,30 +15,27 @@ case "$1" in
     monitor)
 	RECLOCKFILE=$(ctdb -Y getreclock)
 
+	# Early exit if not using a reclock file
+	[ -n "$RECLOCKFILE" ] || exit 0
+
+	# Try to stat the reclock file as a background process so that
+	# we don't block in case the cluster filesystem is unavailable
+	(
+	    if stat $RECLOCKFILE ; then
+		# We could stat the file, reset the counter
+		ctdb_counter_init
+	    fi
+	) >/dev/null 2>&1 &
+
 	ctdb_counter_incr
-	(ctdb_check_counter_limit 200 >/dev/null 2>&1) || {
-	    echo "Reclock file $RECLOCKFILE\" can not be accessed. Shutting down."
+	if ! ctdb_check_counter "quiet" -ge 200 ; then
+	    echo "Reclock file \"$RECLOCKFILE\" can not be accessed. Shutting down."
 	    df
 	    sleep 1
 	    ctdb shutdown
-	}
-
-	[ -z "$RECLOCKFILE" ] && {
-	    # we are not using a reclock file
-	    ctdb_counter_init
-	    exit 0
-	}
-
-	# try stat the reclock file as a background process
-	# so that we dont block in case the cluster filesystem is unavailable
-	(
-	    stat $RECLOCKFILE && {
-		# we could stat the file, reset the counter
-		ctdb_counter_init
-	    }
-	) >/dev/null 2>/dev/null &
+	fi
 
-	ctdb_check_counter_limit 3 quiet
+	ctdb_check_counter "error" -gt 3
 	;;
 
     *)
diff --git a/config/events.d/11.natgw b/config/events.d/11.natgw
index 12ba9ca..9faba80 100755
--- a/config/events.d/11.natgw
+++ b/config/events.d/11.natgw
@@ -13,19 +13,22 @@ loadconfig
 
 [ -z "$CTDB_NATGW_NODES" ] && exit 0
 
-# Update capabilities to show whether we support teh NATGW capability or not
-if [ "$CTDB_NATGW_SLAVE_ONLY" = "yes" ] ; then
+set_natgw_capability ()
+{
+    # Set NATGW capability depending on configuration
+    if [ "$CTDB_NATGW_SLAVE_ONLY" = "yes" ] ; then
 	ctdb setnatgwstate off
-else
+    else
 	ctdb setnatgwstate on
-fi
+    fi
+}
 
 delete_all() {
 	_ip="${CTDB_NATGW_PUBLIC_IP%/*}"
 	_maskbits="${CTDB_NATGW_PUBLIC_IP#*/}"
 
 	[ -z "$CTDB_NATGW_PUBLIC_IFACE" ] || {
-	    delete_ip_from_iface $CTDB_NATGW_PUBLIC_IFACE $_ip $_maskbits 2>/dev/null
+	    delete_ip_from_iface $CTDB_NATGW_PUBLIC_IFACE $_ip $_maskbits >/dev/null 2>&1
 	}
 	ip route del 0.0.0.0/0 metric 10 >/dev/null 2>/dev/null
 
@@ -58,6 +61,10 @@ ensure_natgwmaster ()
 }
 
 case "$1" in 
+    setup)
+	set_natgw_capability
+	;;
+
     startup)
 	# Error if CTDB_NATGW_PUBLIC_IP is listed in public addresses
 	grep -q "^$CTDB_NATGW_PUBLIC_IP[[:space:]]" "${CTDB_PUBLIC_ADDRESSES:-/etc/ctdb/public_addresses}" && \
@@ -70,6 +77,7 @@ case "$1" in
     recovered|updatenatgw|ipreallocated)
 	mypnn=$(ctdb pnn | cut -d: -f2)
 
+	set_natgw_capability
 	ensure_natgwmaster "$1"
 
 	delete_all
@@ -98,11 +106,12 @@ case "$1" in
 	echo 1 > /proc/sys/net/ipv4/route/flush
 	;;
 
-    shutdown|stopped|removenatgw)
+    shutdown|removenatgw)
 	delete_all
 	;;
 
     monitor)
+	set_natgw_capability
 	ensure_natgwmaster "$1"
 	;;
 
diff --git a/config/events.d/13.per_ip_routing b/config/events.d/13.per_ip_routing
index fe97ffc..4b13546 100755
--- a/config/events.d/13.per_ip_routing
+++ b/config/events.d/13.per_ip_routing
@@ -6,6 +6,8 @@
 . $CTDB_BASE/functions
 loadconfig
 
+service_name=per_ip_routing
+
 # Do nothing if unconfigured 
 [ -n "$CTDB_PER_IP_ROUTING_CONF" ] || exit 0
 
diff --git a/config/events.d/40.vsftpd b/config/events.d/40.vsftpd
index 25964b8..92a0e99 100755
--- a/config/events.d/40.vsftpd
+++ b/config/events.d/40.vsftpd
@@ -53,8 +53,9 @@ case "$1" in
 		ctdb_counter_init
 	    else
 		ctdb_counter_incr
-		ctdb_check_counter_limit
-		exit 0 # only count 1 failure per monitor event
+		ctdb_check_counter
+		ctdb_check_counter "quiet" -ge 1 || \
+		    echo "WARNING: vsftpd not listening but less than $service_fail_limit consecutive failures, not unhealthy yet" 
 	    fi
 	fi	
 	;;
diff --git a/config/events.d/49.winbind b/config/events.d/49.winbind
index d0a154d..ef4eb3f 100755
--- a/config/events.d/49.winbind
+++ b/config/events.d/49.winbind
@@ -54,7 +54,7 @@ case "$1" in
 	;;
 
      monitor)
-	ctdb_check_command "winbind" "wbinfo -p"
+	ctdb_check_command wbinfo -p
 	;;
 
      takeip|releaseip)
diff --git a/config/events.d/50.samba b/config/events.d/50.samba
index ecbe05e..ccc6864 100755
--- a/config/events.d/50.samba
+++ b/config/events.d/50.samba
@@ -68,11 +68,6 @@ service_stop ()
     fi
 }
 
-# set default samba cleanup period - in minutes
-[ -z "$SAMBA_CLEANUP_PERIOD" ] && {
-    SAMBA_CLEANUP_PERIOD=10
-}
-
 # we keep a cached copy of smb.conf here
 smbconf_cache="$service_state_dir/smb.conf.cache"
 
@@ -152,15 +147,6 @@ list_samba_shares ()
 
 
 ###########################
-# periodic cleanup function
-periodic_cleanup() {
-    # running smbstatus scrubs any dead entries from the connections
-    # and sessionid database
-    # echo "Running periodic cleanup of samba databases"
-    smbstatus -np > /dev/null 2>&1 &
-}
-
-###########################
 
 ctdb_start_stop_service
 
@@ -170,28 +156,16 @@ ctdb_service_check_reconfigure
 
 ###########################
 
-case "$1" in 
+case "$1" in
      startup)
 	ctdb_service_start
 	;;
-	
+
      shutdown)
 	ctdb_service_stop
 	;;
 
      monitor)
-	# Create a dummy file to track when we need to do periodic cleanup
-	# of samba databases
-	periodic_cleanup_file="$service_state_dir/periodic_cleanup"
-	[ -f "$periodic_cleanup_file" ] || {
-		touch "$periodic_cleanup_file"
-	}
-	[ `find "$periodic_cleanup_file" -mmin +$SAMBA_CLEANUP_PERIOD | wc -l` -eq 1 ] && {
-		# Cleanup the databases
-	    	periodic_cleanup
-		touch "$periodic_cleanup_file"
-	}
-
 	if [ "$CTDB_SAMBA_SKIP_SHARE_CHECK" != "yes" ] ; then
 	    testparm_background_update
 
@@ -200,7 +174,7 @@ case "$1" in
 		testparm_cat | egrep '^WARNING|^ERROR|^Unknown' && \
 		    die "ERROR: testparm shows smb.conf is not clean"
 	    }
-			
+
 	    list_samba_shares | ctdb_check_directories_probe || {
 		testparm_foreground_update
 		list_samba_shares |
diff --git a/config/events.d/60.ganesha b/config/events.d/60.ganesha
index 4d8736e..0066c54 100755
--- a/config/events.d/60.ganesha
+++ b/config/events.d/60.ganesha
@@ -6,7 +6,10 @@
 
 . $CTDB_BASE/functions
 
-service_name="nfs-ganesha-gpfs"
+GANRECDIR="/var/lib/nfs/ganesha"
+GANRECDIR2="/var/lib/nfs/ganesha/recevents"
+GPFS_STATE="/usr/lpp/mmfs/bin/mmgetstate"
+GANRECDIR3="/var/lib/nfs/ganesha_local"
 
 
 service_start ()
@@ -29,20 +32,17 @@ service_reconfigure ()
 	$CTDB_BASE/statd-callout notify &
     } >/dev/null 2>&1
 }
+
 loadconfig "nfs"
 
-[ "$NFS_SERVER_MODE" = "ganesha" ] || exit 0
 
-ctdb_setup_service_state_dir
+[ -n "$CTDB_CLUSTER_FILESYSTEM_TYPE" ] || CTDB_CLUSTER_FILESYSTEM_TYPE="gpfs"
 
-statd_update_trigger="$service_state_dir/update-trigger"
-# We want this file to always exist.  The corner case is when
-# auto-start/stop is switched off, NFS is added as a managed service
-# some time after ctdbd is started and someone else starts the NFS
-# service for us.  In this case this file might not otherwise exist
-# when we get to a monitor event.
-touch "$statd_update_trigger"
+service_name="nfs-ganesha-$CTDB_CLUSTER_FILESYSTEM_TYPE"
 
+[ "$NFS_SERVER_MODE" = "ganesha" ] || exit 0
+
+ctdb_setup_service_state_dir
 
 ctdb_start_stop_service
 
@@ -50,93 +50,170 @@ is_ctdb_managed_service || exit 0
 
 ctdb_service_check_reconfigure
 
+get_cluster_fs_state  ()
+{
+    case $CTDB_CLUSTER_FILESYSTEM_TYPE in
+        gpfs)
+            STATE=`$GPFS_STATE | awk 'NR <= 3 {next} {printf "%-6s", $3}'`
+            echo $STATE
+            ;;
+        *)
+            die "File system $CTDB_CLUSTER_FILESYSTEM_TYPE not supported"
+            ;;
+   esac
+}
+
+create_ganesha_recdirs ()
+{
+    if [ -z "$(mount -t $CTDB_CLUSTER_FILESYSTEM_TYPE)" ]; then
+      echo "startup $CTDB_CLUSTER_FILESYSTEM_TYPE not ready"
+      exit 1
+    fi
+    MNTPT=`mount -t $CTDB_CLUSTER_FILESYSTEM_TYPE | sort | awk '{print $3}' | head -n 1`
+    mkdir -p $MNTPT/.ganesha
+    if [ -e $GANRECDIR ]; then
+        if [ ! -L $GANRECDIR ] ; then
+            rm -rf $GANRECDIR
+            if ! ln -s $MNTPT/.ganesha  $GANRECDIR ; then
+                echo "ln failed"
+            fi
+        fi
+    else
+        if ! ln -s $MNTPT/.ganesha  $GANRECDIR ; then
+            echo "ln failed"
+        fi
+    fi
+
+    mkdir -p $GANRECDIR2
+    mkdir -p $GANRECDIR3
+}
+
 case "$1" in
      init)
-       # read statd from persistent database
-       ;;
+	# read statd from persistent database
+	;;
      startup)
-       ctdb_service_start
-       ;;
+	create_ganesha_recdirs
+	ctdb_service_start
+	;;
 
      shutdown)
-       ctdb_service_stop
-       ;;
+	ctdb_service_stop
+	;;
 
      takeip)
-       ctdb_service_set_reconfigure
-       ;;
+	if [ -n "$2" ] ; then
+	    case  $CTDB_CLUSTER_FILESYSTEM_TYPE in
+		gpfs)
+		    NNUM=`/usr/lpp/mmfs/bin/mmlsconfig myNodeConfigNumber | awk '{print $2}'`
+		    TDATE=`date +"%s"`
+		    TOUCHTGT=$1"_"$TDATE"_"$NNUM"_"$3"_"$4"_"$2
+		    touch $GANRECDIR2/$TOUCHTGT
+		    ;;
+	    esac
+	fi
+	ctdb_service_set_reconfigure
+	;;
 
      releaseip)
-       ctdb_service_set_reconfigure
-       ;;
-
-      monitor)
+	if [ -n "$2" ] ; then
+	    case  $CTDB_CLUSTER_FILESYSTEM_TYPE in
+		gpfs)
+		    NNUM=`/usr/lpp/mmfs/bin/mmlsconfig myNodeConfigNumber | awk '{print $2}'`
+		    TDATE=`date +"%s"`
+		    TOUCHTGT=$1"_"$TDATE"_"$NNUM"_"$3"_"$4"_"$2
+		    touch $GANRECDIR2/$TOUCHTGT
+		;;
+	    esac
+	fi
+	ctdb_service_set_reconfigure
+	;;
 
-       update_tickles 2049
+     monitor)
+	update_tickles 2049
+	create_ganesha_recdirs
+	service_name=${service_name}_process
 	# check that statd responds to rpc requests
 	# if statd is not running we try to restart it
 	# we only do this IF we have a rpc.statd command.
 	# For platforms where rpc.statd does not exist, we skip
-	# the check completely
-        p="rpc.statd"
-        which $p >/dev/null 2>/dev/null && \
+        # the check completely
+	p="rpc.statd"
+	which $p >/dev/null 2>/dev/null && \
 	    nfs_check_rpc_service "statd" 1 \
-	        -ge 6 "verbose unhealthy" \
-	        -eq 4 "verbose restart" \
-		-eq 2 "restart:bs"
-       
-    PIDFILE="/var/run/ganesha.pid" 
-    RUNNING=0
-    if [ -e $PIDFILE ]
-    then
-       PID=`cat $PIDFILE`
-       GANESHA="/usr/bin/gpfs.ganesha.nfsd"
-       RUNNING=`cat /proc/$PID/cmdline | grep $GANESHA | wc -l`
-    fi
-    if [ $RUNNING != 1 ]
-    then
-        echo "Trying fast restart of NFS service"
-        startstop_ganesha restart
-    fi
-
-	# check that NFS responds to rpc requests
-	if [ "$CTDB_NFS_SKIP_KNFSD_ALIVE_CHECK" != "yes" ] ; then
-	    nfs_check_rpc_service "ganesha" \
 		-ge 6 "verbose unhealthy" \
 		-eq 4 "verbose restart" \
 		-eq 2 "restart:bs"
+
+	PIDFILE="/var/run/ganesha.pid"
+	CUR_STATE=`get_cluster_fs_state`
+	GANESHA="/usr/bin/$CTDB_CLUSTER_FILESYSTEM_TYPE.ganesha.nfsd"
+	if { read PID < $PIDFILE && \
+	    grep "$GANESHA" "/proc/$PID/cmdline" ; } >/dev/null 2>&1 ; then
+		ctdb_counter_init "$service_name"
+	else
+	    if [ $CUR_STATE = "active" ]; then
+		echo "Trying fast restart of NFS service"
+		startstop_ganesha restart
+		ctdb_counter_incr "$service_name"
+		ctdb_check_counter "error" "-ge" "6" "$service_name"
+	    fi
+	fi
+
+	service_name="nfs-ganesha-$CTDB_CLUSTER_FILESYSTEM_TYPE"_service
+	# check that NFS is posting forward progress
+	if [ $CUR_STATE = "active" -a "$CTDB_NFS_SKIP_KNFSD_ALIVE_CHECK" != "yes" ] ; then
+	    MAXREDS=2
+	    MAXSTALL=120
+	    RESTART=0
+
+	    NUMREDS=`ls $GANRECDIR3 | grep "red" | wc -l`
+	    LASTONE=`ls -t $GANRECDIR3 | sed 's/_/ /' | awk 'NR > 1 {next} {printf $1} '`
+	    # Beware of startup
+	    if [ -z $LASTONE ] ; then
+		LASTONE=`date +"%s"`
+	    fi
+	    TNOW=$(date +"%s")
+	    TSTALL=$(($TNOW - $LASTONE))
+	    if [ $NUMREDS -ge $MAXREDS ] ; then
+		echo restarting because of $NUMREDS red conditions
+		RESTART=1
+		ctdb_counter_incr "$service_name"
+		ctdb_check_counter "error" "-ge" "6" "$service_name"
+	    fi
+	    if [ $TSTALL -ge $MAXSTALL ] ; then
+		echo restarting because of $TSTALL second stall
+		RESTART=1
+		ctdb_counter_incr "$service_name"
+		ctdb_check_counter "error" "-ge" "6" "$service_name"
+	    fi
+	    if [ $RESTART -gt 0 ] ; then
+		startstop_ganesha restart
+	    else
+		ctdb_counter_init "$service_name"
+	    fi
 	fi
 
 
 	# rquotad is sometimes not started correctly on RHEL5
 	# not a critical service so we dont flag the node as unhealthy
-	nfs_check_rpc_service "rquotad" 1\
+	nfs_check_rpc_service "rquotad" 1 \
 	    -gt 0 "verbose restart:b"
 
+	# Check that directories for shares actually exist.
+	[ "$CTDB_NFS_SKIP_SHARE_CHECK" = "yes" ] || {
+	    grep Path /etc/ganesha/$CTDB_CLUSTER_FILESYSTEM_TYPE.ganesha.exports.conf |
+ 	    cut -f2 -d\" | ctdb_check_directories
+	} || exit $?
 
-    # Check that directories for shares actually exist.
-    [ "$CTDB_NFS_SKIP_SHARE_CHECK" = "yes" ] || {
-        grep Path /etc/ganesha/gpfs.ganesha.exports.conf |
-        cut -f2 -d\" | ctdb_check_directories
-    } || exit $?
-
-    # once every 60 seconds, update the statd state database for which
-    # clients need notifications
-    LAST_UPDATE=`stat --printf="%Y" "$statd_update_trigger" 2>/dev/null`
-    CURRENT_TIME=`date +"%s"`
-    [ $CURRENT_TIME -ge $(($LAST_UPDATE + 60)) ] && {
-	    touch "$statd_update_trigger"
-        $CTDB_BASE/statd-callout updatelocal &
-        $CTDB_BASE/statd-callout updateremote &
-    }
-        ;;
+	# once every 60 seconds, update the statd state database for which
+	# clients need notifications
+	nfs_statd_update 60
+	;;
 
-    ipreallocated)
-       ctdb_service_set_reconfigure
-       ;;
-    *)
-       ctdb_standard_event_handler "$@"
-       ;;
+     *)
+	ctdb_standard_event_handler "$@"
+        ;;
 esac
 
 exit 0
diff --git a/config/events.d/60.nfs b/config/events.d/60.nfs
index 2cba9a7..eb98ee1 100755
--- a/config/events.d/60.nfs
+++ b/config/events.d/60.nfs
@@ -32,14 +32,6 @@ loadconfig
 
 ctdb_setup_service_state_dir
 
-statd_update_trigger="$service_state_dir/update-trigger"
-# We want this file to always exist.  The corner case is when
-# auto-start/stop is switched off, NFS is added as a managed service
-# some time after ctdbd is started and someone else starts the NFS
-# service for us.  In this case this file might not otherwise exist
-# when we get to a monitor event.
-touch "$statd_update_trigger"
-
 ctdb_start_stop_service
 
 is_ctdb_managed_service || exit 0
@@ -77,50 +69,11 @@ case "$1" in
 
 	update_tickles 2049
 
-	# check that statd responds to rpc requests
-	# if statd is not running we try to restart it
-	# we only do this IF we have a rpc.statd command.
-	# For platforms where rpc.statd does not exist, we skip
-	# the check completely
-        p="rpc.statd"
-        which $p >/dev/null 2>/dev/null && \
-	    nfs_check_rpc_service "statd" \
-	        -ge 6 "verbose unhealthy" \
-	        -eq 4 "verbose restart" \
-		-eq 2 "restart:bs"
-
-	# check that NFS responds to rpc requests
-	if [ "$CTDB_NFS_SKIP_KNFSD_ALIVE_CHECK" != "yes" ] ; then
-	    nfs_check_rpc_service "knfsd" \
-		-ge 6 "verbose unhealthy" \
-		-eq 4 "verbose restart" \
-		-eq 2 "restart:bs"
-	fi
-
-	# check that lockd responds to rpc requests
-	nfs_check_rpc_service "lockd" \
-	    -ge 15 "verbose restart:b unhealthy" \
-	    -eq 10 "restart:bs"
-
-	# mountd is sometimes not started correctly on RHEL5
-	nfs_check_rpc_service "mountd" \
-	    -ge 10 "verbose restart:b unhealthy" \
-	    -eq 5 "restart:b"
-
-	# rquotad is sometimes not started correctly on RHEL5
-	# not a critical service so we dont flag the node as unhealthy
-	nfs_check_rpc_service "rquotad" \
-	    -gt 0 "verbose restart:b"
-
-	# once every 600 seconds, update the statd state database for which
+	nfs_check_rpc_services
+
+	# Every 10 minutes, update the statd state database for which
 	# clients need notifications
-	LAST_UPDATE=`stat --printf="%Y" "$statd_update_trigger"`
-	CURRENT_TIME=`date +"%s"`
-	[ $CURRENT_TIME -ge $(($LAST_UPDATE + 600)) ] && {
-	    touch "$statd_update_trigger"
-	    $CTDB_BASE/statd-callout updatelocal &
-	    $CTDB_BASE/statd-callout updateremote &
-	}
+	nfs_statd_update 600
        	;;
 
     *)
diff --git a/config/events.d/91.lvs b/config/events.d/91.lvs
index c1e6d15..bdbcfa3 100755
--- a/config/events.d/91.lvs
+++ b/config/events.d/91.lvs
@@ -40,7 +40,7 @@ case "$1" in
 	echo 1 > /proc/sys/net/ipv4/route/flush
 	;;
 
-     recovered|stopped|ipreallocated)
+     recovered|ipreallocated)
 	# kill off any tcp connections
 	ipvsadm -D -t $CTDB_LVS_PUBLIC_IP:0
 	ipvsadm -D -u $CTDB_LVS_PUBLIC_IP:0
diff --git a/config/events.d/README b/config/events.d/README
index 6075f39..ea9048f 100644
--- a/config/events.d/README
+++ b/config/events.d/README
@@ -146,12 +146,11 @@ recovered
 	service and also send out statd notifications to all registered 
 	clients.
 	
-stopped
-	This event is called when a node is STOPPED and can be used to
-	perform additional cleanup that is required.
-	Note that a stopped node is considered inactive, so it will not
-	be issuing the recovered event once the cluster has recovered.
-	See 91.lvs for a use of this event.
+ipreallocated
+
+	This event is triggered after releaseip and takeip events in a
+	takeover run.  It can be used to reconfigure services, update
+	routing and many other things.
 
 Additional note for takeip, releaseip, recovered:
 
diff --git a/config/functions b/config/functions
index 8fbc079..f4707a7 100755
--- a/config/functions
+++ b/config/functions
@@ -23,11 +23,18 @@ _loadconfig() {
 	foo="${service_config:-${service_name}}"
 	if [ -n "$foo" ] ; then
 	    loadconfig "$foo"
+	    return
 	fi
-    elif [ "$1" != "ctdb" ] ; then
+    fi
+
+    if [ "$1" != "ctdb" ] ; then
 	loadconfig "ctdb"
     fi
 
+    if [ -z "$1" ] ; then
+	return
+    fi
+
     if [ -f $CTDB_ETCDIR/sysconfig/$1 ]; then
 	. $CTDB_ETCDIR/sysconfig/$1
     elif [ -f $CTDB_ETCDIR/default/$1 ]; then
@@ -42,39 +49,12 @@ loadconfig () {
 }
 
 ##############################################################
-# make sure CTDB_CURRENT_DEBUGLEVEL is set to the desired debug level
-# (integer)
-#
-# If it is already set then do nothing, since it might have been set
-# via a file in rc.local.d/.  If it is not set then set it by sourcing
-# /var/ctdb/eventscript_debuglevel. If this file does not exist then
-# create it using output from "ctdb getdebug".  If the option 1st arg
-# is "create" then don't source an existing file but create a new one
-# instead - this is useful for creating the file just once in each
-# event run in 00.ctdb.  If there's a problem getting the debug level
-# from ctdb then it is silently set to 0 - no use spamming logs if our
-# debug code is broken...
-ctdb_set_current_debuglevel ()
-{
-    [ -z "$CTDB_CURRENT_DEBUGLEVEL" ] || return 0
-
-    _f="$CTDB_VARDIR/eventscript_debuglevel"
-
-    if [ "$1" = "create" -o ! -r "$_f" ] ; then
-	_t=$(ctdb getdebug -Y 2>/dev/null)
-	# get last field of output
-	_t="${_t%:}"
-	_t="${_t##*:}"
-	# Defaults to 0
-	echo "export CTDB_CURRENT_DEBUGLEVEL=\"${_t:-0}\"" >"$_f"
-    fi
-
-    . "$_f"
-}
 
+# CTDB_SCRIPT_DEBUGLEVEL can be overwritten by setting it in a
+# configuration file.
 debug ()
 {
-    if [ $CTDB_CURRENT_DEBUGLEVEL -ge 4 ] ; then
+    if [ ${CTDB_SCRIPT_DEBUGLEVEL:-2} -ge 4 ] ; then
 	# If there are arguments then echo them.  Otherwise expect to
 	# use stdin, which allows us to pass lots of debug using a
 	# here document.
@@ -110,7 +90,7 @@ script_log ()
     esac
 
     if $_using_syslog ; then
-	logger -t "$_tag" "$*"
+	logger -t "ctdbd: ${_tag}" $*
     else
 	{
 	    if [ -n "$*" ] ; then
@@ -128,7 +108,7 @@ background_with_logging ()
 {
     (
 	"$@" 2>&1 </dev/null |
-	script_log "ctdbd: ${script_name}&"
+	script_log "${script_name}&"
     )&
 
     return 0
@@ -250,29 +230,68 @@ nfs_check_rpc_service ()
 {
     _prog_name="$1" ; shift
 
-    _v=""
-    case "$1" in
-	-*) : ;;
-	*) _v="$1" ; shift ;;
+    if _nfs_check_rpc_common "$_prog_name" ; then
+	return
+    fi
+
+    while [ -n "$3" ] ; do
+	if _nfs_check_rpc_action "$1" "$2" "$3" ; then
+	    break
+	fi
+	shift 3
+    done
+}
+
+# The new way of doing things...
+nfs_check_rpc_services ()
+{
+    # Files must end with .check - avoids editor backups, RPM fu, ...
+    for _f in "${CTDB_BASE}/nfs-rpc-checks.d/"[0-9][0-9].*.check ; do
+	_t="${_f%.check}"
+	_prog_name="${_t##*/[0-9][0-9].}"
+
+	if _nfs_check_rpc_common "$_prog_name" ; then
+	    # This RPC service is up, check next service...
+	    continue
+	fi
+
+	# Check each line in the file in turn until one of the limit
+	# checks is hit...
+	while read _cmp _lim _rest ; do
+	    # Skip comments
+	    case "$_cmp" in
+		\#*) continue ;;
+	    esac
+
+	    if _nfs_check_rpc_action "$_cmp" "$_lim" "$_rest" ; then
+		# Limit was hit on this line, no further checking...
+		break
+	    fi
+	done <"$_f"
+    done
+}
+
+_nfs_check_rpc_common ()
+{
+    _prog_name="$1"
+
+    # Some platforms don't have separate programs for all services.
+    case "$_prog_name" in
+	statd)
+	    which "rpc.${_prog_name}" >/dev/null 2>&1 || return 0
     esac
 
-    _version=${_v:-1}
+    _version=1
     _rpc_prog="$_prog_name"
     _restart=""
     _opts=""
     case "$_prog_name" in
-	knfsd)
+	nfsd)
 	    _rpc_prog=nfs
-	    _version=${_v:-3}
+	    _version=3
 	    _restart="echo 'Trying to restart NFS service'"
 	    _restart="${_restart}; startstop_nfs restart"
 	    ;;
-	ganesha)
-	    _rpc_prog=nfs
-	    _version=${_v:-3}
-	    _restart="echo 'Trying to restart Ganesha NFS service'"
-	    _restart="${_restart}; startstop_ganesha restart"
-	    ;;
 	mountd)
 	    _opts="${MOUNTD_PORT:+ -p }${MOUNTD_PORT}"
 	    ;;
@@ -281,7 +300,7 @@ nfs_check_rpc_service ()
 	    ;;
 	lockd)
 	    _rpc_prog=nlockmgr
-	    _version=${_v:-4}
+	    _version=4
 	    _restart="echo 'Trying to restart lock manager service'"
 	    _restart="${_restart}; startstop_nfslock restart"
 	    ;;
@@ -305,56 +324,63 @@ nfs_check_rpc_service ()
 
     ctdb_counter_incr "$_service_name"
 
-    while [ -n "$3" ] ; do
-	ctdb_check_counter "quiet" "$1" "$2" "$_service_name" || {
-	    for _action in $3 ; do
-		case "$_action" in
-		    verbose)
-			echo "$ctdb_check_rpc_out"
-			;;
-		    restart|restart:*)
-			# No explicit command specified, construct rpc command.
-			if [ -z "$_restart" ] ; then
-			    _p="rpc.${_prog_name}"
-			    _restart="echo 'Trying to restart $_prog_name [${_p}${_opts}]'"
-			    _restart="${_restart}; killall -q -9 $_p"
-			    _restart="${_restart}; $_p $_opts"
-			fi
-
-			# Process restart flags...
-			_flags="${_action#restart:}"
-			# There may not have been a colon...
-			[ "$_flags" != "$_action" ] || _flags=""
-			# q=quiet - everything to /dev/null
-			if [ "${_flags#*q}" != "$_flags" ] ; then
-			    _restart="{ ${_restart} ; } >/dev/null 2>&1"
-			fi
-			# s=stealthy - last command to /dev/null
-			if [ "${_flags#*s}" != "$_flags" ] ; then
-			    _restart="${_restart} >/dev/null 2>&1"
-			fi
-			# b=background - the whole thing, easy and reliable
-			if [ "${_flags#*b}" != "$_flags" ] ; then
-			    _restart="{ ${_restart} ; } &"
-			fi
-
-			# Do it!
-			eval "${_restart}"
-			;;
-		    unhealthy)
-			exit 1
-			;;
-		    *)
-			echo "Internal error: unknown action \"$_action\"."
-			exit 1
-		esac
-	    done
+    return 1
+}
 
-	    # Only process the first action group.
-	    break
-	}
-	shift 3
+_nfs_check_rpc_action ()
+{
+    _cmp="$1"
+    _limit="$2"
+    _actions="$3"
+
+    if ctdb_check_counter "quiet" "$_cmp" "$_limit" "$_service_name" ; then
+	return 1
+    fi
+
+    for _action in $_actions ; do
+	case "$_action" in
+	    verbose)
+		echo "$ctdb_check_rpc_out"
+		;;
+	    restart|restart:*)
+		# No explicit command specified, construct rpc command.
+		if [ -z "$_restart" ] ; then
+		    _p="rpc.${_prog_name}"
+		    _restart="echo 'Trying to restart $_prog_name [${_p}${_opts}]'"
+		    _restart="${_restart}; killall -q -9 $_p"
+		    _restart="${_restart}; $_p $_opts"
+		fi
+
+		# Process restart flags...
+		_flags="${_action#restart:}"
+		# There may not have been a colon...
+		[ "$_flags" != "$_action" ] || _flags=""
+		# q=quiet - everything to /dev/null
+		if [ "${_flags#*q}" != "$_flags" ] ; then
+		    _restart="{ ${_restart} ; } >/dev/null 2>&1"
+		fi
+		# s=stealthy - last command to /dev/null
+		if [ "${_flags#*s}" != "$_flags" ] ; then
+		    _restart="${_restart} >/dev/null 2>&1"
+		fi
+		# b=background - the whole thing, easy and reliable
+		if [ "${_flags#*b}" != "$_flags" ] ; then
+		    _restart="{ ${_restart} ; } &"
+		fi
+
+		# Do it!
+		eval "${_restart}"
+		;;
+	    unhealthy)
+		exit 1
+		;;
+	    *)
+		echo "Internal error: unknown action \"$_action\"."
+		exit 1
+	esac
     done
+
+    return 0
 }
 
 ######################################################
@@ -376,11 +402,19 @@ $ctdb_check_rpc_out"
 }
 
 ######################################################
+# Ensure $service_name is set
+assert_service_name ()
+{
+    [ -n "$service_name" ] || die "INTERNAL ERROR: \$service_name not set"
+}
+
+######################################################
 # check a set of directories is available
 # return 1 on a missing directory
-# usage: ctdb_check_directories_probe SERVICE_NAME <directories...>
+# directories are read from stdin
 ######################################################
-ctdb_check_directories_probe() {
+ctdb_check_directories_probe()
+{
     while IFS="" read d ; do
 	case "$d" in
 	    *%*)
@@ -394,12 +428,12 @@ ctdb_check_directories_probe() {
 
 ######################################################
 # check a set of directories is available
-# usage: ctdb_check_directories SERVICE_NAME <directories...>
+# directories are read from stdin
 ######################################################
-ctdb_check_directories() {
-    n="${1:-${service_name}}"
+ctdb_check_directories()
+{
     ctdb_check_directories_probe || {
-	echo "ERROR: $n directory \"$d\" not available"
+	echo "ERROR: $service_name directory \"$d\" not available"
 	exit 1
     }
 }
@@ -415,6 +449,7 @@ ctdb_check_directories() {
 # message if a port check fails.
 _ctdb_check_tcp_common ()
 {
+    assert_service_name
     _ctdb_service_started_file="$ctdb_fail_dir/$service_name.started"
 }
 
@@ -588,152 +623,124 @@ ctdb_check_unix_socket() {
 
 ######################################################
 # check a command returns zero status
-# usage: ctdb_check_command SERVICE_NAME <command>
+# usage: ctdb_check_command <command>
 ######################################################
-ctdb_check_command() {
-  service_name="$1"
-  wait_cmd="$2"
-  [ -z "$wait_cmd" ] && return;
-  $wait_cmd > /dev/null 2>&1 || {
-      echo "ERROR: $service_name - $wait_cmd returned error"
-      exit 1
-  }
+ctdb_check_command ()
+{
+    _out=$("$@" 2>&1) || {
+	echo "ERROR: $* returned error"
+	echo "$_out" | debug
+	exit 1
+    }
 }
 
 ################################################
 # kill off any TCP connections with the given IP
 ################################################
-kill_tcp_connections() {
-    _IP="$1"    
-    _failed=0
-
-    _killcount=0
-    connfile="$CTDB_VARDIR/state/connections.$_IP"
-    netstat -tn |egrep "^tcp.*[[:space:]]+$_IP:.*ESTABLISHED" | awk '{print $4" "$5}' > $connfile
-    netstat -tn |egrep "^tcp.*[[:space:]]+::ffff:$_IP:.*ESTABLISHED" | awk '{print $4" "$5}' >> $connfile
-
-    while read dest src; do
-	srcip=`echo $src | sed -e "s/:[^:]*$//"`
-	srcport=`echo $src | sed -e "s/^.*://"`
-	destip=`echo $dest | sed -e "s/:[^:]*$//"`
-	destport=`echo $dest | sed -e "s/^.*://"`
-	echo "Killing TCP connection $srcip:$srcport $destip:$destport"
-	ctdb killtcp $srcip:$srcport $destip:$destport >/dev/null 2>&1 || _failed=1
-	case $destport in
-	  # we only do one-way killtcp for CIFS
-	  139|445) : ;;
-	  # for all others we do 2-way
-	  *) 
-	  	ctdb killtcp $destip:$destport $srcip:$srcport >/dev/null 2>&1 || _failed=1
-		;;
-	esac
-	_killcount=`expr $_killcount + 1`
-     done < $connfile
-    rm -f $connfile
+kill_tcp_connections ()
+{
+    _ip="$1"
 
-    [ $_failed = 0 ] || {
-	echo "Failed to send killtcp control"
-	return;
-    }
-    [ $_killcount -gt 0 ] || {
-	return;
+    _oneway=false
+    if [ "$2" = "oneway" ] ; then
+	_oneway=true
+    fi
+
+    get_tcp_connections_for_ip "$_ip" | {
+	_killcount=0
+	_failed=false
+
+	while read dest src; do
+	    echo "Killing TCP connection $src $dest"
+	    ctdb killtcp $src $dest >/dev/null 2>&1 || _failed=true
+	    _destport="${dest##*:}"
+	    __oneway=$_oneway
+	    case $_destport in
+		# we only do one-way killtcp for CIFS
+		139|445) __oneway=true ;;
+	    esac
+	    if ! $__oneway ; then
+		ctdb killtcp $dest $src >/dev/null 2>&1 || _failed=true
+	    fi
+
+	    _killcount=$(($_killcount + 1))
+	done
+
+	if $_failed ; then
+	    echo "Failed to send killtcp control"
+	    return
+	fi
+	if [ $_killcount -eq 0 ] ; then
+	    return
+	fi
+
+	_count=0
+	while : ; do
+	    if [ -z "$(get_tcp_connections_for_ip $_ip)" ] ; then
+		echo "Killed $_killcount TCP connections to released IP $_ip"
+		return
+	    fi
+
+	    _count=$(($_count + 1))
+	    if [ $_count -gt 3 ] ; then
+		echo "Timed out killing tcp connections for IP $_ip"
+		return
+	    fi
+
+	    sleep 1
+	done
     }
-    _count=0
-    while netstat -tn |egrep "^tcp.*[[:space:]]+$_IP:.*ESTABLISHED" > /dev/null; do
-	sleep 1
-	_count=`expr $_count + 1`
-	[ $_count -gt 3 ] && {
-	    echo "Timed out killing tcp connections for IP $_IP"
-	    return;
-	}
-    done
-    echo "killed $_killcount TCP connections to released IP $_IP"
 }
 
 ##################################################################
 # kill off the local end for any TCP connections with the given IP
 ##################################################################
-kill_tcp_connections_local_only() {
-    _IP="$1"    
-    _failed=0
-
-    _killcount=0
-    connfile="$CTDB_VARDIR/state/connections.$_IP"
-    netstat -tn |egrep "^tcp.*[[:space:]]+$_IP:.*ESTABLISHED" | awk '{print $4" "$5}' > $connfile
-    netstat -tn |egrep "^tcp.*[[:space:]]+::ffff:$_IP:.*ESTABLISHED" | awk '{print $4" "$5}' >> $connfile
-
-    while read dest src; do
-	srcip=`echo $src | sed -e "s/:[^:]*$//"`
-	srcport=`echo $src | sed -e "s/^.*://"`
-	destip=`echo $dest | sed -e "s/:[^:]*$//"`
-	destport=`echo $dest | sed -e "s/^.*://"`
-	echo "Killing TCP connection $srcip:$srcport $destip:$destport"
-	ctdb killtcp $srcip:$srcport $destip:$destport >/dev/null 2>&1 || _failed=1
-	_killcount=`expr $_killcount + 1`
-     done < $connfile
-    rm -f $connfile
-
-    [ $_failed = 0 ] || {
-	echo "Failed to send killtcp control"
-	return;
-    }
-    [ $_killcount -gt 0 ] || {
-	return;
-    }
-    _count=0
-    while netstat -tn |egrep "^tcp.*[[:space:]]+$_IP:.*ESTABLISHED" > /dev/null; do
-	sleep 1
-	_count=`expr $_count + 1`
-	[ $_count -gt 3 ] && {
-	    echo "Timed out killing tcp connections for IP $_IP"
-	    return;
-	}
-    done
-    echo "killed $_killcount TCP connections to released IP $_IP"
+kill_tcp_connections_local_only ()
+{
+    kill_tcp_connections "$1" "oneway"
 }
 
 ##################################################################
 # tickle any TCP connections with the given IP
 ##################################################################
-tickle_tcp_connections() {
-    _IP="$1"
-    _failed=0
-
-    _killcount=0
-    connfile="$CTDB_VARDIR/state/connections.$_IP"
-    netstat -tn |egrep "^tcp.*[[:space:]]+$_IP:.*ESTABLISHED" | awk '{print $4" "$5}' > $connfile
-    netstat -tn |egrep "^tcp.*[[:space:]]+::ffff:$_IP:.*ESTABLISHED" | awk '{print $4" "$5}' >> $connfile
-
-    while read dest src; do
-	srcip=`echo $src | sed -e "s/:[^:]*$//"`
-	srcport=`echo $src | sed -e "s/^.*://"`
-	destip=`echo $dest | sed -e "s/:[^:]*$//"`
-	destport=`echo $dest | sed -e "s/^.*://"`
-	echo "Tickle TCP connection $srcip:$srcport $destip:$destport"
-	ctdb tickle $srcip:$srcport $destip:$destport >/dev/null 2>&1 || _failed=1
-	echo "Tickle TCP connection $destip:$destport $srcip:$srcport"
-	ctdb tickle $destip:$destport $srcip:$srcport >/dev/null 2>&1 || _failed=1
-     done < $connfile
-    rm -f $connfile
-
-    [ $_failed = 0 ] || {
-	echo "Failed to send tickle control"
-	return;
+tickle_tcp_connections ()
+{
+    _ip="$1"
+
+    get_tcp_connections_for_ip "$_ip" |
+    {
+	_failed=false
+
+	while read dest src; do
+	    echo "Tickle TCP connection $src $dest"
+	    ctdb tickle $src $dest >/dev/null 2>&1 || _failed=true
+	    echo "Tickle TCP connection $dest $src"
+	    ctdb tickle $dest $src >/dev/null 2>&1 || _failed=true
+	done
+
+	if $_failed ; then
+	    echo "Failed to send tickle control"
+	fi
     }
 }
 
+get_tcp_connections_for_ip ()
+{
+    _ip="$1"
+
+    netstat -tn | awk -v ip=$_ip \
+	'index($1, "tcp") == 1 && \
+	 (index($4, ip ":") == 1 || index($4, "::ffff:" ip ":") == 1) \
+	 && $6 == "ESTABLISHED" \
+	 {print $4" "$5}'
+}
+
 ########################################################
 # start/stop the Ganesha nfs service
 ########################################################
 startstop_ganesha()
 {
-    _ganesha_fsal_list="gpfs"
-    for _fsal in $_ganesha_fsal_list ; do
-        _service_name="nfs-ganesha-${_fsal}"
-	if [ -x /etc/init.d/$_service_name ] ; then
-	    break
-	fi
-    done
+    _service_name="nfs-ganesha-$CTDB_CLUSTER_FILESYSTEM_TYPE"
     case "$1" in
 	start)
 	    service "$_service_name" start
@@ -853,6 +860,23 @@ startstop_nfslock() {
 	esac
 }
 
+# Periodically update the statd database
+nfs_statd_update ()
+{
+    _update_period="$1"
+
+    _statd_update_trigger="$service_state_dir/update-trigger"
+    [ -f "$_statd_update_trigger" ] || touch "$_statd_update_trigger"
+
+    _last_update=$(stat --printf="%Y" "$_statd_update_trigger")
+    _current_time=$(date +"%s")
+    if [ $(( $_current_time - $_last_update)) -ge $_update_period ] ; then
+	touch "$_statd_update_trigger"
+	$CTDB_BASE/statd-callout updatelocal &
+	$CTDB_BASE/statd-callout updateremote &
+    fi
+}
+
 add_ip_to_iface()
 {
     _iface=$1
@@ -860,6 +884,7 @@ add_ip_to_iface()
     _maskbits=$3
 
     _lockfile="${CTDB_VARDIR}/state/interface_modify_${_iface}.flock"
+    mkdir -p "${_lockfile%/*}" # dirname
     [ -f "$_lockfile" ] || touch "$_lockfile"
 
     (
@@ -889,6 +914,7 @@ delete_ip_from_iface()
     _maskbits=$3
 
     _lockfile="${CTDB_VARDIR}/state/interface_modify_${_iface}.flock"
+    mkdir -p "${_lockfile%/*}" # dirname
     [ -f "$_lockfile" ] || touch "$_lockfile"
 
     (
@@ -982,7 +1008,7 @@ drop_all_public_ips ()
 # ctdb_check_counter_limit fails when count >= <limit>
 ########################################################
 _ctdb_counter_common () {
-    _service_name="${1:-${service_name}}"
+    _service_name="${1:-${service_name:-${script_name}}}"
     _counter_file="$ctdb_fail_dir/$_service_name"
     mkdir -p "${_counter_file%/*}" # dirname
 }
@@ -997,33 +1023,6 @@ ctdb_counter_incr () {
     # unary counting!
     echo -n 1 >> "$_counter_file"
 }
-ctdb_check_counter_limit () {
-    _ctdb_counter_common
-
-    _limit="${1:-${service_fail_limit}}"
-    _quiet="$2"
-
-    # unary counting!
-    _size=$(stat -c "%s" "$_counter_file" 2>/dev/null || echo 0)
-    if [ $_size -ge $_limit ] ; then
-	echo "ERROR: more than $_limit consecutive failures for $service_name, marking cluster unhealthy"
-	exit 1
-    elif [ $_size -gt 0 -a -z "$_quiet" ] ; then
-	echo "WARNING: less than $_limit consecutive failures ($_size) for $service_name, not unhealthy yet"
-    fi
-}
-ctdb_check_counter_equal () {
-    _ctdb_counter_common
-
-    _limit=$1
-
-    # unary counting!
-    _size=$(stat -c "%s" "$_counter_file" 2>/dev/null || echo 0)
-    if [ $_size -eq $_limit ] ; then
-	return 1
-    fi
-    return 0
-}
 ctdb_check_counter () {
     _msg="${1:-error}"  # "error"  - anything else is silent on fail
     _op="${2:--ge}"  # an integer operator supported by test
@@ -1064,26 +1063,25 @@ ctdb_managed_dir="$CTDB_VARDIR/managed_history"
 
 _ctdb_managed_common ()
 {
-    _service_name="${1:-${service_name}}"
-    _ctdb_managed_file="$ctdb_managed_dir/$_service_name"
+    _ctdb_managed_file="$ctdb_managed_dir/$service_name"
 }
 
 ctdb_service_managed ()
 {
-    _ctdb_managed_common "$@"
+    _ctdb_managed_common
     mkdir -p "$ctdb_managed_dir"
     touch "$_ctdb_managed_file"
 }
 
 ctdb_service_unmanaged ()
 {
-    _ctdb_managed_common "$@"
+    _ctdb_managed_common
     rm -f "$_ctdb_managed_file"
 }
 
 is_ctdb_previously_managed_service ()
 {
-    _ctdb_managed_common "$@"
+    _ctdb_managed_common
     [ -f "$_ctdb_managed_file" ]
 }
 
@@ -1129,35 +1127,35 @@ ctdb_setstatus ()
 
 _ctdb_service_reconfigure_common ()
 {
-    _d="$ctdb_status_dir/${1:-${service_name}}"
+    _d="$ctdb_status_dir/${service_name}"
     mkdir -p "$_d"
     _ctdb_service_reconfigure_flag="$_d/reconfigure"
 }
 
 ctdb_service_needs_reconfigure ()
 {
-    _ctdb_service_reconfigure_common "$@"
+    _ctdb_service_reconfigure_common
     [ -e "$_ctdb_service_reconfigure_flag" ]
 }
 
 ctdb_service_set_reconfigure ()
 {
-    _ctdb_service_reconfigure_common "$@"
+    _ctdb_service_reconfigure_common
     >"$_ctdb_service_reconfigure_flag"
 }
 
 ctdb_service_unset_reconfigure ()
 {
-    _ctdb_service_reconfigure_common "$@"
+    _ctdb_service_reconfigure_common
     rm -f "$_ctdb_service_reconfigure_flag"
 }
 
 ctdb_service_reconfigure ()
 {
-    echo "Reconfiguring service \"$@\"..."
-    ctdb_service_unset_reconfigure "$@"
-    service_reconfigure "$@" || return $?
-    ctdb_counter_init "$@"
+    echo "Reconfiguring service \"${service_name}\"..."
+    ctdb_service_unset_reconfigure
+    service_reconfigure || return $?
+    ctdb_counter_init
 }
 
 # Default service_reconfigure() function does nothing.
@@ -1168,9 +1166,9 @@ service_reconfigure ()
 
 ctdb_reconfigure_try_lock ()
 {
-    
-    _ctdb_service_reconfigure_common "$@"
+    _ctdb_service_reconfigure_common
     _lock="${_d}/reconfigure_lock"
+    mkdir -p "${_lock%/*}" # dirname
     touch "$_lock"
 
     (
@@ -1231,7 +1229,7 @@ ctdb_replay_monitor_status ()
 
 ctdb_service_check_reconfigure ()
 {
-    [ -n "$1" ] || set -- "$service_name"
+    assert_service_name
 
     # We only care about some events in this function.  For others we
     # return now.
@@ -1240,22 +1238,22 @@ ctdb_service_check_reconfigure ()
 	*) return 0 ;;
     esac
 
-    if ctdb_reconfigure_try_lock "$@" ; then
+    if ctdb_reconfigure_try_lock ; then
 	# No events covered by this function are running, so proceed
 	# with gay abandon.
 	case "$event_name" in
 	    reconfigure)
-		(ctdb_service_reconfigure "$@")
+		(ctdb_service_reconfigure)
 		exit $?
 		;;
 	    ipreallocated)
-		if ctdb_service_needs_reconfigure "$@" ; then
-		    ctdb_service_reconfigure "$@"
+		if ctdb_service_needs_reconfigure ; then
+		    ctdb_service_reconfigure
 		fi
 		;;
 	    monitor)
-		if ctdb_service_needs_reconfigure "$@" ; then
-		    ctdb_service_reconfigure "$@"
+		if ctdb_service_needs_reconfigure ; then
+		    ctdb_service_reconfigure
 		    # Given that the reconfigure might not have
 		    # resulted in the service being stable yet, we
 		    # replay the previous status since that's the best
@@ -1297,21 +1295,21 @@ ctdb_service_check_reconfigure ()
 
 ctdb_compat_managed_service ()
 {
-    if [ "$1" = "yes" -a "$2" = "$_service_name" ] ; then
+    if [ "$1" = "yes" -a "$2" = "$service_name" ] ; then
 	CTDB_MANAGED_SERVICES="$CTDB_MANAGED_SERVICES $2"
     fi
 }
 
 is_ctdb_managed_service ()
 {
-    _service_name="${1:-${service_name}}"
+    assert_service_name
 
     # $t is used just for readability and to allow better accurate
     # matching via leading/trailing spaces
     t=" $CTDB_MANAGED_SERVICES "
 
-    # Return 0 if "<space>$_service_name<space>" appears in $t
-    if [ "${t#* ${_service_name} }" != "${t}" ] ; then
+    # Return 0 if "<space>$service_name<space>" appears in $t
+    if [ "${t#* ${service_name} }" != "${t}" ] ; then
 	return 0
     fi
 
@@ -1330,36 +1328,36 @@ is_ctdb_managed_service ()
 
     t=" $CTDB_MANAGED_SERVICES "
 
-    # Return 0 if "<space>$_service_name<space>" appears in $t
-    [ "${t#* ${_service_name} }" != "${t}" ]
+    # Return 0 if "<space>$service_name<space>" appears in $t
+    [ "${t#* ${service_name} }" != "${t}" ]
 }
 
 ctdb_start_stop_service ()
 {
-    _service_name="${1:-${service_name}}"
+    assert_service_name
 
     # Allow service-start/service-stop pseudo-events to start/stop
     # services when we're not auto-starting/stopping and we're not
     # monitoring.
     case "$event_name" in
 	service-start)
-	    if is_ctdb_managed_service "$_service_name" ; then
+	    if is_ctdb_managed_service ; then
 		die 'service-start event not permitted when service is managed'
 	    fi
 	    if [ "$CTDB_SERVICE_AUTOSTARTSTOP" = "yes" ] ; then
 		die 'service-start event not permitted with $CTDB_SERVICE_AUTOSTARTSTOP = yes'
 	    fi
-	    ctdb_service_start "$_service_name"
+	    ctdb_service_start
 	    exit $?
 	    ;;
 	service-stop)
-	    if is_ctdb_managed_service "$_service_name" ; then
+	    if is_ctdb_managed_service ; then
 		die 'service-stop event not permitted when service is managed'
 	    fi
 	    if [ "$CTDB_SERVICE_AUTOSTARTSTOP" = "yes" ] ; then
 		die 'service-stop event not permitted with $CTDB_SERVICE_AUTOSTARTSTOP = yes'
 	    fi
-	    ctdb_service_stop "$_service_name"
+	    ctdb_service_stop
 	    exit $?
 	    ;;
     esac
@@ -1369,16 +1367,16 @@ ctdb_start_stop_service ()
 
     [ "$event_name" = "monitor" ] || return 0
 
-    if is_ctdb_managed_service "$_service_name" ; then
-	if ! is_ctdb_previously_managed_service "$_service_name" ; then
-	    echo "Starting service \"$_service_name\" - now managed"
-	    background_with_logging ctdb_service_start "$_service_name"
+    if is_ctdb_managed_service ; then
+	if ! is_ctdb_previously_managed_service ; then
+	    echo "Starting service \"$service_name\" - now managed"
+	    background_with_logging ctdb_service_start
 	    exit $?
 	fi
     else
-	if is_ctdb_previously_managed_service "$_service_name" ; then
-	    echo "Stopping service \"$_service_name\" - no longer managed"
-	    background_with_logging ctdb_service_stop "$_service_name"
+	if is_ctdb_previously_managed_service ; then
+	    echo "Stopping service \"$service_name\" - no longer managed"
+	    background_with_logging ctdb_service_stop
 	    exit $?
 	fi
     fi
@@ -1387,20 +1385,18 @@ ctdb_start_stop_service ()
 ctdb_service_start ()
 {
     # The service is marked managed if we've ever tried to start it.
-    ctdb_service_managed "$@"
+    ctdb_service_managed
 
-    # Here we only want $1.  If no argument is passed then
-    # service_start needs to know.
-    service_start "$@" || return $?
+    service_start || return $?
 
-    ctdb_counter_init "$@"
+    ctdb_counter_init
     ctdb_check_tcp_init
 }
 
 ctdb_service_stop ()
 {
-    ctdb_service_unmanaged "$@"
-    service_stop "$@"
+    ctdb_service_unmanaged
+    service_stop
 }
 
 # Default service_start() and service_stop() functions.
@@ -1415,12 +1411,12 @@ ctdb_service_stop ()
 # them with the service name as an argument.
 service_start ()
 {
-    service "${1:-${service_name}}" start
+    service "$service_name" start
 }
 
 service_stop ()
 {
-    service "${1:-${service_name}}" stop
+    service "$service_name" stop
 }
 
 ##################################################################
@@ -1446,19 +1442,42 @@ iptables()
 	flock -w 30 $CTDB_VARDIR/iptables-ctdb.flock /sbin/iptables "$@"
 }
 
+# AIX (and perhaps others?) doesn't have mktemp
+if ! which mktemp >/dev/null 2>&1 ; then
+    mktemp ()
+    {
+	_dir=false
+	if [ "$1" = "-d" ] ; then
+	    _dir=true
+	    shift
+	fi
+	_d="${TMPDIR:-/tmp}"
+	_hex10=$(dd if=/dev/urandom count=20 2>/dev/null | \
+	    md5sum | \
+	    sed -e 's@\(..........\).*@\1@')
+	_t="${_d}/tmp.${_hex10}"
+	(
+	    umask 077
+	    if $_dir ; then
+		mkdir "$_t"
+	    else
+		>"$_t"
+	    fi
+	)
+	echo "$_t"
+    }
+fi
+
 ########################################################
 # tickle handling
 ########################################################
 
-# Temporary directory for tickles.
-tickledir="$CTDB_VARDIR/state/tickles"
-mkdir -p "$tickledir"
-
 update_tickles ()
 {
 	_port="$1"
 
-	mkdir -p "$tickledir" # Just in case
+	tickledir="$CTDB_VARDIR/state/tickles"
+	mkdir -p "$tickledir"
 
 	# Who am I?
 	_pnn=$(ctdb pnn) ; _pnn=${_pnn#PNN:}
@@ -1519,12 +1538,6 @@ update_tickles ()
 	done
 }
 
-# We'll call this here to ensure $CTDB_CURRENT_DEBUGLEVEL is set.
-# This gives us a chance to override the debug level using a file in
-# $CTDB_BASE/rc.local.d/.
-ctdb_set_current_debuglevel
-
 script_name="${0##*/}"       # basename
-service_name="$script_name"  # default is just the script name
 service_fail_limit=1
 event_name="$1"
diff --git a/config/nfs-rpc-checks.d/10.statd.check b/config/nfs-rpc-checks.d/10.statd.check
new file mode 100644
index 0000000..dd5e15d
--- /dev/null
+++ b/config/nfs-rpc-checks.d/10.statd.check
@@ -0,0 +1,3 @@
+-ge 6 verbose unhealthy
+-eq 4 verbose restart
+-eq 2 restart:bs
diff --git a/config/nfs-rpc-checks.d/20.nfsd.check b/config/nfs-rpc-checks.d/20.nfsd.check
new file mode 100644
index 0000000..dd5e15d
--- /dev/null
+++ b/config/nfs-rpc-checks.d/20.nfsd.check
@@ -0,0 +1,3 @@
+-ge 6 verbose unhealthy
+-eq 4 verbose restart
+-eq 2 restart:bs
diff --git a/config/nfs-rpc-checks.d/30.lockd.check b/config/nfs-rpc-checks.d/30.lockd.check
new file mode 100644
index 0000000..4bda6c3
--- /dev/null
+++ b/config/nfs-rpc-checks.d/30.lockd.check
@@ -0,0 +1,2 @@
+-ge 15 verbose restart:b unhealthy
+-eq 10 restart:bs
diff --git a/config/nfs-rpc-checks.d/40.mountd.check b/config/nfs-rpc-checks.d/40.mountd.check
new file mode 100644
index 0000000..6b4f801
--- /dev/null
+++ b/config/nfs-rpc-checks.d/40.mountd.check
@@ -0,0 +1,2 @@
+-ge 10 verbose restart:b unhealthy
+-eq 5 restart:b
diff --git a/config/nfs-rpc-checks.d/50.rquotad.check b/config/nfs-rpc-checks.d/50.rquotad.check
new file mode 100644
index 0000000..1ebb828
--- /dev/null
+++ b/config/nfs-rpc-checks.d/50.rquotad.check
@@ -0,0 +1 @@
+-gt 0 verbose restart:b
diff --git a/config/notify.d.README b/config/notify.d.README
new file mode 100755
index 0000000..ffce7fa
--- /dev/null
+++ b/config/notify.d.README
@@ -0,0 +1,44 @@
+This directory should contain executable programs to handle CTDB event
+notifications.  The first and only argument passed to each program is
+the event, which is one of:
+
+  init, setup, startup, unhealthy, healthy
+
+To use notifications with this directory then you need to set:
+
+  CTDB_NOTIFY_SCRIPT=/etc/ctdb/notify.sh
+
+in your CTDB configuration file.
+
+An example script that sends SNMP traps for unhealthy/healthy might
+look like this:
+
+  #!/bin/sh
+
+  case "$1" in
+      unhealthy)
+          # Send an SNMP trap saying that the node is unhealthy:
+          snmptrap -m ALL -v 1 -c public 10.1.1.105 ctdb \
+              $(hostname) 0 0 $(date +"%s") ctdb.nodeHealth.0 i 1
+          ;;
+      healthy)
+          # Send an SNMP trap saying that the node is healthy again:
+          snmptrap -m ALL -v 1 -c public 10.1.1.105 ctdb \
+	      $(hostname) 0 0 $(date +"%s") ctdb.nodeHealth.0 i 0
+	  ;;
+  esac
+
+Alternatively, email could be sent:
+
+  #!/bin/sh
+
+  case "$1" in
+      unhealthy)
+          mail -s "$(hostname) is UNHEALTHY" foo at example.com </dev/null >/dev/null 2>&1
+          ;;
+      healthy)
+          mail -s "$(hostname) is HEALTHY" foo at example.com </dev/null >/dev/null 2>&1
+          ;;
+  esac
+
+When adding programs please note the exclusion patterns in notify.sh.
diff --git a/config/notify.sh b/config/notify.sh
index 8d3eb87..dfcb81a 100755
--- a/config/notify.sh
+++ b/config/notify.sh
@@ -3,47 +3,25 @@
 # This script is activated by setting CTDB_NOTIFY_SCRIPT=/etc/ctdb/notify.sh
 # in /etc/sysconfig/ctdb
 
-# This is script is invoked from ctdb when node UNHEALTHY flag changes.
-# and can be used to send SNMPtraps, email, etc
-# when the status of a node changes
-
-
-event="$1"
-shift
-
-case $event in
-	unhealthy)
-#
-#               Send an snmptrap that the node is unhealthy :
-#		snmptrap -m ALL -v 1 -c public 10.1.1.105 ctdb `hostname` 0 0 `date +"%s"` ctdb.nodeHealth.0 i 1
-#
-#               or send an email :
-#               mail foo at bar -s "`hostname` is UNHEALTHY"   ...
-#
-#               or do something else ...
-		;;
-	healthy)
-#
-#               Send an snmptrap that the node is healthy again :
-#		snmptrap -m ALL -v 1 -c public 10.1.1.105 ctdb `hostname` 0 0 `date +"%s"` ctdb.nodeHealth.0 i 0
-#
-#               or send an email :
-#               mail foo at bar -s "`hostname` is HEALTHY"   ...
-#
-#               or do something else ...
-		;;
-	startup)
-	#		do some extra magic when ctdb has finished the initial
-	#		recovery?
-		;;
-
-	setup)
-	#		do some extra magic when ctdb has setup itself?
-		;;
-
-	init)
-	#		do some extra magic when ctdb has started?
-		;;
-esac
-
-exit 0
+# This is script is invoked from ctdb when certain events happen.  See
+# /etc/ctdb/notify.d/README for more details.
+
+d=$(dirname $0)
+nd="${d}/notify.d"
+
+ok=true
+
+for i in "${nd}/"* ; do
+    # Don't run files matching basename
+    case "${i##*/}" in
+	*~|*,|*.rpm*|*.swp|README) continue ;;
+    esac
+
+    # Files must be executable
+    [ -x "$i" ] || continue
+
+    # Flag failures
+    "$i" "$1" || ok=false
+done
+
+$ok
diff --git a/config/statd-callout b/config/statd-callout
index 72a2ca9..94bd2dd 100755
--- a/config/statd-callout
+++ b/config/statd-callout
@@ -1,5 +1,8 @@
 #!/bin/sh
 
+# This must run as root as CTDB tool commands need to access CTDB socket
+[ $(id -u) -eq 0 ] || exec sudo "$0" "$@"
+
 # this script needs to be installed so that statd points to it with the -H 
 # command line argument. The easiest way to do that is to put something like this in 
 # /etc/sysconfig/nfs:
@@ -136,11 +139,7 @@ case "$1" in
 	# will respond "strangely" immediately after restarting it, which
 	# causes clients to fail to reclaim the locks.
 	# 
-	if [ "$NFS_SERVER_MODE" = "ganesha" ] ; then
-            startstop_ganesha stop >/dev/null 2>&1
-            sleep 2
-            startstop_ganesha start >/dev/null 2>&1
-	else
+	if [ "$NFS_SERVER_MODE" != "ganesha" ] ; then
             startstop_nfslock stop >/dev/null 2>&1
             sleep 2
             startstop_nfslock start >/dev/null 2>&1
diff --git a/configure b/configure
index 3ca622e..db5674d 100755
--- a/configure
+++ b/configure
@@ -1,6 +1,6 @@
 #! /bin/sh
 # Guess values for system-dependent variables and create Makefiles.
-# Generated by GNU Autoconf 2.69 for ctdb 2.1.
+# Generated by GNU Autoconf 2.69 for ctdb 2.2.
 #
 #
 # Copyright (C) 1992-1996, 1998-2012 Free Software Foundation, Inc.
@@ -577,8 +577,8 @@ MAKEFLAGS=
 # Identity of this package.
 PACKAGE_NAME='ctdb'
 PACKAGE_TARNAME='ctdb'
-PACKAGE_VERSION='2.1'
-PACKAGE_STRING='ctdb 2.1'
+PACKAGE_VERSION='2.2'
+PACKAGE_STRING='ctdb 2.2'
 PACKAGE_BUGREPORT=''
 PACKAGE_URL=''
 
@@ -620,12 +620,12 @@ ac_includes_default="\
 #endif"
 
 ac_subst_vars='LTLIBOBJS
-CTDB_PMDA_INSTALL
-CTDB_PMDA
 CTDB_PCAP_LDFLAGS
 CTDB_SCSI_IO
 CTDB_SYSTEM_OBJ
 EXTRA_OBJ
+CTDB_PMDA_INSTALL
+CTDB_PMDA
 SOCKET_WRAPPER_OBJS
 HAVE_SOCKET_WRAPPER
 DEFAULT_TEST_OPTIONS
@@ -732,6 +732,7 @@ with_included_tdb
 with_included_tevent
 enable___enable_infiniband
 enable_socket_wrapper
+enable_pmda
 '
       ac_precious_vars='build_alias
 host_alias
@@ -1282,7 +1283,7 @@ if test "$ac_init_help" = "long"; then
   # Omit some internal or obsolete options to make the list less imposing.
   # This message is too long to be a string in the A/UX 3.1 sh.
   cat <<_ACEOF
-\`configure' configures ctdb 2.1 to adapt to many kinds of systems.
+\`configure' configures ctdb 2.2 to adapt to many kinds of systems.
 
 Usage: $0 [OPTION]... [VAR=VALUE]...
 
@@ -1348,7 +1349,7 @@ fi
 
 if test -n "$ac_init_help"; then
   case $ac_init_help in
-     short | recursive ) echo "Configuration of ctdb 2.1:";;
+     short | recursive ) echo "Configuration of ctdb 2.2:";;
    esac
   cat <<\_ACEOF
 
@@ -1359,6 +1360,7 @@ Optional Features:
   --disable-largefile     omit support for large files
   --enable-infiniband         Turn on infiniband support (default=no)
   --enable-socket-wrapper Turn on socket wrapper library (default=no)
+  --enable-pmda           Turn on PCP pmda support (default=no)
 
 Optional Packages:
   --with-PACKAGE[=ARG]    use PACKAGE [ARG=yes]
@@ -1446,7 +1448,7 @@ fi
 test -n "$ac_init_help" && exit $ac_status
 if $ac_init_version; then
   cat <<\_ACEOF
-ctdb configure 2.1
+ctdb configure 2.2
 generated by GNU Autoconf 2.69
 
 Copyright (C) 2012 Free Software Foundation, Inc.
@@ -2151,7 +2153,7 @@ cat >config.log <<_ACEOF
 This file contains any messages produced by compilers while
 running configure, to aid debugging if configure makes a mistake.
 
-It was created by ctdb $as_me 2.1, which was
+It was created by ctdb $as_me 2.2, which was
 generated by GNU Autoconf 2.69.  Invocation command line was
 
   $ $0 $@
@@ -4744,6 +4746,16 @@ fi
 EOF
 
 
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking checking getconf LFS_CFLAGS for large file support flags" >&5
+$as_echo_n "checking checking getconf LFS_CFLAGS for large file support flags... " >&6; }
+LFS_CFLAGS=`(getconf LFS_CFLAGS) 2>/dev/null` || LFS_CFLAGS=""
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: ${LFS_CFLAGS}" >&5
+$as_echo "${LFS_CFLAGS}" >&6; }
+if test "x$LFS_CFLAGS" != 'x-1' || test "x$LFS_CFLAGS" != "xundefined"; then
+   CFLAGS="$CFLAGS $LFS_CFLAGS"
+fi
+
 # Check whether --enable-largefile was given.
 if test "${enable_largefile+set}" = set; then :
   enableval=$enable_largefile;
@@ -4950,6 +4962,24 @@ case "$host_os" in
 #include <standards.h>
 EOF
 
+
+
+
+ cat >>confdefs.h <<\EOF
+#ifndef _XOPEN_SOURCE
+#define _XOPEN_SOURCE 600
+#endif
+EOF
+
+
+
+
+ cat >>confdefs.h <<\EOF
+#ifndef _BSD_TYPES
+#define _BSD_TYPES 1
+#endif
+EOF
+
 		;;
 	*hpux*)
 		# mmap on HPUX is completely broken...
@@ -5025,9 +5055,15 @@ $as_echo "#define _SYSV 1" >>confdefs.h
 		;;
 esac
 
+# Do not check for standards.h on darwin, we get nasty warnings on
+# OS/X Lion. Probably a positive-list of OS'es like IRIX and AIX
+# would be the better choice, but this seems to work fine
 
-
-for ac_header in standards.h
+case "$host_os" in
+     *darwin*)
+	;;
+     *)
+        for ac_header in standards.h
 do :
   ac_fn_c_check_header_mongrel "$LINENO" "standards.h" "ac_cv_header_standards_h" "$ac_includes_default"
 if test "x$ac_cv_header_standards_h" = xyes; then :
@@ -5039,6 +5075,8 @@ fi
 
 done
 
+	;;
+esac
 
 # Solaris needs HAVE_LONG_LONG defined
 ac_fn_c_check_type "$LINENO" "long long" "ac_cv_type_long_long" "$ac_includes_default"
@@ -5567,7 +5605,7 @@ fi
 LIBREPLACEOBJ="$libreplacedir/replace.o"
 
 
-LIBREPLACEOBJ="${LIBREPLACEOBJ} $libreplacedir/snprintf.o"
+LIBREPLACEOBJ="${LIBREPLACEOBJ} $libreplacedir/snprintf.o  $libreplacedir/xattr.o"
 
 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for uid_t in sys/types.h" >&5
 $as_echo_n "checking for uid_t in sys/types.h... " >&6; }
@@ -5689,6 +5727,28 @@ _ACEOF
 
 fi
 
+ac_fn_c_check_type "$LINENO" "blksize_t" "ac_cv_type_blksize_t" "$ac_includes_default"
+if test "x$ac_cv_type_blksize_t" = xyes; then :
+
+else
+
+cat >>confdefs.h <<_ACEOF
+#define blksize_t long
+_ACEOF
+
+fi
+
+ac_fn_c_check_type "$LINENO" "blkcnt_t" "ac_cv_type_blkcnt_t" "$ac_includes_default"
+if test "x$ac_cv_type_blkcnt_t" = xyes; then :
+
+else
+
+cat >>confdefs.h <<_ACEOF
+#define blkcnt_t long
+_ACEOF
+
+fi
+
 
 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for working memcmp" >&5
 $as_echo_n "checking for working memcmp... " >&6; }
@@ -5779,7 +5839,7 @@ fi
 
 done
 
-for ac_header in setjmp.h utime.h
+for ac_header in setjmp.h utime.h sys/wait.h
 do :
   as_ac_Header=`$as_echo "ac_cv_header_$ac_header" | $as_tr_sh`
 ac_fn_c_check_header_mongrel "$LINENO" "$ac_header" "$as_ac_Header" "$ac_includes_default"
@@ -5925,6 +5985,37 @@ $as_echo "#define HAVE_MREMAP 1" >>confdefs.h
 
 fi
 
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for incoherent mmap" >&5
+$as_echo_n "checking for incoherent mmap... " >&6; }
+if ${libreplace_cv_HAVE_INCOHERENT_MMAP+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+
+if test "$cross_compiling" = yes; then :
+  libreplace_cv_HAVE_INCOHERENT_MMAP=cross
+else
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#include "$libreplacedir/test/incoherent_mmap.c"
+_ACEOF
+if ac_fn_c_try_run "$LINENO"; then :
+  libreplace_cv_HAVE_INCOHERENT_MMAP=yes
+else
+  libreplace_cv_HAVE_INCOHERENT_MMAP=no
+fi
+rm -f core *.core core.conftest.* gmon.out bb.out conftest$ac_exeext \
+  conftest.$ac_objext conftest.beam conftest.$ac_ext
+fi
+
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $libreplace_cv_HAVE_INCOHERENT_MMAP" >&5
+$as_echo "$libreplace_cv_HAVE_INCOHERENT_MMAP" >&6; }
+if test x"$libreplace_cv_HAVE_INCOHERENT_MMAP" = x"yes"; then
+
+$as_echo "#define HAVE_INCOHERENT_MMAP 1" >>confdefs.h
+
+fi
+
 
 for ac_header in sys/syslog.h syslog.h
 do :
@@ -6002,8 +6093,56 @@ fi
 
 done
 
+for ac_header in malloc.h
+do :
+  ac_fn_c_check_header_mongrel "$LINENO" "malloc.h" "ac_cv_header_malloc_h" "$ac_includes_default"
+if test "x$ac_cv_header_malloc_h" = xyes; then :
+  cat >>confdefs.h <<_ACEOF
+#define HAVE_MALLOC_H 1
+_ACEOF
+
+fi
+
+done
+
+for ac_header in syscall.h
+do :
+  ac_fn_c_check_header_mongrel "$LINENO" "syscall.h" "ac_cv_header_syscall_h" "$ac_includes_default"
+if test "x$ac_cv_header_syscall_h" = xyes; then :
+  cat >>confdefs.h <<_ACEOF
+#define HAVE_SYSCALL_H 1
+_ACEOF
+
+fi
+
+done
+
+for ac_header in sys/syscall.h
+do :
+  ac_fn_c_check_header_mongrel "$LINENO" "sys/syscall.h" "ac_cv_header_sys_syscall_h" "$ac_includes_default"
+if test "x$ac_cv_header_sys_syscall_h" = xyes; then :
+  cat >>confdefs.h <<_ACEOF
+#define HAVE_SYS_SYSCALL_H 1
+_ACEOF
+
+fi
+
+done
+
+for ac_header in sys/ucontext.h
+do :
+  ac_fn_c_check_header_mongrel "$LINENO" "sys/ucontext.h" "ac_cv_header_sys_ucontext_h" "$ac_includes_default"
+if test "x$ac_cv_header_sys_ucontext_h" = xyes; then :
+  cat >>confdefs.h <<_ACEOF
+#define HAVE_SYS_UCONTEXT_H 1
+_ACEOF
+
+fi
+
+done
+
 
-for ac_func in seteuid setreuid setresuid setegid setregid setresgid
+for ac_func in syscall setuid seteuid setreuid setresuid setgid setegid setregid setresgid setgroups
 do :
   as_ac_var=`$as_echo "ac_cv_func_$ac_func" | $as_tr_sh`
 ac_fn_c_check_func "$LINENO" "$ac_func" "$as_ac_var"
@@ -6015,7 +6154,7 @@ _ACEOF
 fi
 done
 
-for ac_func in chroot bzero strerror strerror_r
+for ac_func in chroot bzero strerror strerror_r memalign posix_memalign getpagesize
 do :
   as_ac_var=`$as_echo "ac_cv_func_$ac_func" | $as_tr_sh`
 ac_fn_c_check_func "$LINENO" "$ac_func" "$as_ac_var"
@@ -6224,122 +6363,607 @@ fi
 fi
 done
 
-for ac_func in get_current_dir_name
+
+for ac_header in sys/attributes.h attr/xattr.h sys/xattr.h sys/extattr.h sys/uio.h
 do :
-  ac_fn_c_check_func "$LINENO" "get_current_dir_name" "ac_cv_func_get_current_dir_name"
-if test "x$ac_cv_func_get_current_dir_name" = xyes; then :
+  as_ac_Header=`$as_echo "ac_cv_header_$ac_header" | $as_tr_sh`
+ac_fn_c_check_header_mongrel "$LINENO" "$ac_header" "$as_ac_Header" "$ac_includes_default"
+if eval test \"x\$"$as_ac_Header"\" = x"yes"; then :
   cat >>confdefs.h <<_ACEOF
-#define HAVE_GET_CURRENT_DIR_NAME 1
+#define `$as_echo "HAVE_$ac_header" | $as_tr_cpp` 1
 _ACEOF
 
 fi
-done
 
+done
 
- { $as_echo "$as_me:${as_lineno-$LINENO}: checking for setresuid declaration" >&5
-$as_echo_n "checking for setresuid declaration... " >&6; }
-if ${ac_cv_have_setresuid_decl+:} false; then :
-  $as_echo_n "(cached) " >&6
-else
-
-    cat confdefs.h - <<_ACEOF >conftest.$ac_ext
-/* end confdefs.h.  */
-#include <unistd.h>
-int
-main ()
-{
-int i = (int)setresuid
-  ;
-  return 0;
-}
+for ac_header in sys/ea.h sys/proplist.h
+do :
+  as_ac_Header=`$as_echo "ac_cv_header_$ac_header" | $as_tr_sh`
+ac_fn_c_check_header_mongrel "$LINENO" "$ac_header" "$as_ac_Header" "$ac_includes_default"
+if eval test \"x\$"$as_ac_Header"\" = x"yes"; then :
+  cat >>confdefs.h <<_ACEOF
+#define `$as_echo "HAVE_$ac_header" | $as_tr_cpp` 1
 _ACEOF
-if ac_fn_c_try_compile "$LINENO"; then :
-  ac_cv_have_setresuid_decl=yes
-else
-  ac_cv_have_setresuid_decl=no
-fi
-rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+
 fi
-{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_have_setresuid_decl" >&5
-$as_echo "$ac_cv_have_setresuid_decl" >&6; }
- if test x"$ac_cv_have_setresuid_decl" = x"yes"; then
 
-$as_echo "#define HAVE_SETRESUID_DECL 1" >>confdefs.h
+done
 
- fi
 
+LIBREPLACE_FILESYS_LIBS=""
 
- { $as_echo "$as_me:${as_lineno-$LINENO}: checking for setresgid declaration" >&5
-$as_echo_n "checking for setresgid declaration... " >&6; }
-if ${ac_cv_have_setresgid_decl+:} false; then :
+############################################
+# Check for EA implementations
+case "$host_os" in
+  *freebsd4* | *dragonfly* )
+
+$as_echo "#define BROKEN_EXTATTR 1" >>confdefs.h
+
+  ;;
+  *)
+	{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for library containing getxattr" >&5
+$as_echo_n "checking for library containing getxattr... " >&6; }
+if ${ac_cv_search_getxattr+:} false; then :
   $as_echo_n "(cached) " >&6
 else
-
-    cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+  ac_func_search_save_LIBS=$LIBS
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
 /* end confdefs.h.  */
-#include <unistd.h>
+
+/* Override any GCC internal prototype to avoid an error.
+   Use char because int might match the return type of a GCC
+   builtin and then its argument prototype would still apply.  */
+#ifdef __cplusplus
+extern "C"
+#endif
+char getxattr ();
 int
 main ()
 {
-int i = (int)setresgid
+return getxattr ();
   ;
   return 0;
 }
 _ACEOF
-if ac_fn_c_try_compile "$LINENO"; then :
-  ac_cv_have_setresgid_decl=yes
-else
-  ac_cv_have_setresgid_decl=no
+for ac_lib in '' attr; do
+  if test -z "$ac_lib"; then
+    ac_res="none required"
+  else
+    ac_res=-l$ac_lib
+    LIBS="-l$ac_lib  $ac_func_search_save_LIBS"
+  fi
+  if ac_fn_c_try_link "$LINENO"; then :
+  ac_cv_search_getxattr=$ac_res
 fi
-rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext
+  if ${ac_cv_search_getxattr+:} false; then :
+  break
 fi
-{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_have_setresgid_decl" >&5
-$as_echo "$ac_cv_have_setresgid_decl" >&6; }
- if test x"$ac_cv_have_setresgid_decl" = x"yes"; then
+done
+if ${ac_cv_search_getxattr+:} false; then :
 
-$as_echo "#define HAVE_SETRESGID_DECL 1" >>confdefs.h
+else
+  ac_cv_search_getxattr=no
+fi
+rm conftest.$ac_ext
+LIBS=$ac_func_search_save_LIBS
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_search_getxattr" >&5
+$as_echo "$ac_cv_search_getxattr" >&6; }
+ac_res=$ac_cv_search_getxattr
+if test "$ac_res" != no; then :
+  test "$ac_res" = "none required" || LIBS="$ac_res $LIBS"
 
- fi
+fi
 
+	for ac_func in attr_get attr_getf attr_list attr_listf attropen attr_remove
+do :
+  as_ac_var=`$as_echo "ac_cv_func_$ac_func" | $as_tr_sh`
+ac_fn_c_check_func "$LINENO" "$ac_func" "$as_ac_var"
+if eval test \"x\$"$as_ac_var"\" = x"yes"; then :
+  cat >>confdefs.h <<_ACEOF
+#define `$as_echo "HAVE_$ac_func" | $as_tr_cpp` 1
+_ACEOF
 
- { $as_echo "$as_me:${as_lineno-$LINENO}: checking for errno declaration" >&5
-$as_echo_n "checking for errno declaration... " >&6; }
-if ${ac_cv_have_errno_decl+:} false; then :
-  $as_echo_n "(cached) " >&6
-else
+fi
+done
 
-    cat confdefs.h - <<_ACEOF >conftest.$ac_ext
-/* end confdefs.h.  */
-#include <errno.h>
-int
-main ()
-{
-int i = (int)errno
-  ;
-  return 0;
-}
+	for ac_func in attr_removef attr_set attr_setf extattr_delete_fd extattr_delete_file
+do :
+  as_ac_var=`$as_echo "ac_cv_func_$ac_func" | $as_tr_sh`
+ac_fn_c_check_func "$LINENO" "$ac_func" "$as_ac_var"
+if eval test \"x\$"$as_ac_var"\" = x"yes"; then :
+  cat >>confdefs.h <<_ACEOF
+#define `$as_echo "HAVE_$ac_func" | $as_tr_cpp` 1
 _ACEOF
-if ac_fn_c_try_compile "$LINENO"; then :
-  ac_cv_have_errno_decl=yes
-else
-  ac_cv_have_errno_decl=no
-fi
-rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+
 fi
-{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_have_errno_decl" >&5
-$as_echo "$ac_cv_have_errno_decl" >&6; }
- if test x"$ac_cv_have_errno_decl" = x"yes"; then
+done
 
-$as_echo "#define HAVE_ERRNO_DECL 1" >>confdefs.h
+	for ac_func in extattr_get_fd extattr_get_file extattr_list_fd extattr_list_file
+do :
+  as_ac_var=`$as_echo "ac_cv_func_$ac_func" | $as_tr_sh`
+ac_fn_c_check_func "$LINENO" "$ac_func" "$as_ac_var"
+if eval test \"x\$"$as_ac_var"\" = x"yes"; then :
+  cat >>confdefs.h <<_ACEOF
+#define `$as_echo "HAVE_$ac_func" | $as_tr_cpp` 1
+_ACEOF
 
- fi
+fi
+done
 
+	for ac_func in extattr_set_fd extattr_set_file fgetea fgetxattr flistea flistxattr
+do :
+  as_ac_var=`$as_echo "ac_cv_func_$ac_func" | $as_tr_sh`
+ac_fn_c_check_func "$LINENO" "$ac_func" "$as_ac_var"
+if eval test \"x\$"$as_ac_var"\" = x"yes"; then :
+  cat >>confdefs.h <<_ACEOF
+#define `$as_echo "HAVE_$ac_func" | $as_tr_cpp` 1
+_ACEOF
+
+fi
+done
+
+	for ac_func in fremoveea fremovexattr fsetea fsetxattr getea getxattr listea
+do :
+  as_ac_var=`$as_echo "ac_cv_func_$ac_func" | $as_tr_sh`
+ac_fn_c_check_func "$LINENO" "$ac_func" "$as_ac_var"
+if eval test \"x\$"$as_ac_var"\" = x"yes"; then :
+  cat >>confdefs.h <<_ACEOF
+#define `$as_echo "HAVE_$ac_func" | $as_tr_cpp` 1
+_ACEOF
+
+fi
+done
+
+	for ac_func in listxattr removeea removexattr setea setxattr
+do :
+  as_ac_var=`$as_echo "ac_cv_func_$ac_func" | $as_tr_sh`
+ac_fn_c_check_func "$LINENO" "$ac_func" "$as_ac_var"
+if eval test \"x\$"$as_ac_var"\" = x"yes"; then :
+  cat >>confdefs.h <<_ACEOF
+#define `$as_echo "HAVE_$ac_func" | $as_tr_cpp` 1
+_ACEOF
+
+fi
+done
+
+
+
+
+ac_check_lib_ext_save_LIBS=$LIBS
+LIBS="-lattr $LIBREPLACE_FILESYS_LIBS  $LIBS"
+
+
+
+        { $as_echo "$as_me:${as_lineno-$LINENO}: checking for flistea in -lattr" >&5
+$as_echo_n "checking for flistea in -lattr... " >&6; }
+if ${ac_cv_lib_ext_attr_flistea+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+/* Override any GCC internal prototype to avoid an error.
+   Use char because int might match the return type of a GCC
+   builtin and then its argument prototype would still apply.  */
+#ifdef __cplusplus
+extern "C"
+#endif
+char flistea ();
+int
+main ()
+{
+return flistea ();
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_link "$LINENO"; then :
+  ac_cv_lib_ext_attr_flistea=yes;
+		  ac_cv_lib_ext_attr=yes
+else
+  ac_cv_lib_ext_attr_flistea=no;
+		  ac_cv_lib_ext_attr=no
+fi
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext conftest.$ac_ext
+
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_ext_attr_flistea" >&5
+$as_echo "$ac_cv_lib_ext_attr_flistea" >&6; }
+    if test $ac_cv_lib_ext_attr_flistea = yes; then :
+  cat >>confdefs.h <<_ACEOF
+#define HAVE_FLISTEA 1
+_ACEOF
+
+fi
+LIBS=$ac_check_lib_ext_save_LIBS
+
+if test $ac_cv_lib_ext_attr = yes; then :
+  cat >>confdefs.h <<_ACEOF
+#define HAVE_LIBATTR 1
+_ACEOF
+
+		case "$LIBREPLACE_FILESYS_LIBS" in
+		    *-lattr*)
+			;;
+		    *)
+			LIBREPLACE_FILESYS_LIBS="-lattr $LIBREPLACE_FILESYS_LIBS"
+			;;
+		esac
+
+
+fi
+
+
+ac_check_lib_ext_save_LIBS=$LIBS
+LIBS="-lattr $LIBREPLACE_FILESYS_LIBS  $LIBS"
+
+
+
+        { $as_echo "$as_me:${as_lineno-$LINENO}: checking for flistxattr in -lattr" >&5
+$as_echo_n "checking for flistxattr in -lattr... " >&6; }
+if ${ac_cv_lib_ext_attr_flistxattr+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+/* Override any GCC internal prototype to avoid an error.
+   Use char because int might match the return type of a GCC
+   builtin and then its argument prototype would still apply.  */
+#ifdef __cplusplus
+extern "C"
+#endif
+char flistxattr ();
+int
+main ()
+{
+return flistxattr ();
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_link "$LINENO"; then :
+  ac_cv_lib_ext_attr_flistxattr=yes;
+		  ac_cv_lib_ext_attr=yes
+else
+  ac_cv_lib_ext_attr_flistxattr=no;
+		  ac_cv_lib_ext_attr=no
+fi
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext conftest.$ac_ext
+
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_ext_attr_flistxattr" >&5
+$as_echo "$ac_cv_lib_ext_attr_flistxattr" >&6; }
+    if test $ac_cv_lib_ext_attr_flistxattr = yes; then :
+  cat >>confdefs.h <<_ACEOF
+#define HAVE_FLISTXATTR 1
+_ACEOF
+
+fi
+LIBS=$ac_check_lib_ext_save_LIBS
+
+if test $ac_cv_lib_ext_attr = yes; then :
+  cat >>confdefs.h <<_ACEOF
+#define HAVE_LIBATTR 1
+_ACEOF
+
+		case "$LIBREPLACE_FILESYS_LIBS" in
+		    *-lattr*)
+			;;
+		    *)
+			LIBREPLACE_FILESYS_LIBS="-lattr $LIBREPLACE_FILESYS_LIBS"
+			;;
+		esac
+
+
+fi
+
+
+ac_check_lib_ext_save_LIBS=$LIBS
+LIBS="-lattr $LIBREPLACE_FILESYS_LIBS  $LIBS"
+
+
+
+        { $as_echo "$as_me:${as_lineno-$LINENO}: checking for attr_listf in -lattr" >&5
+$as_echo_n "checking for attr_listf in -lattr... " >&6; }
+if ${ac_cv_lib_ext_attr_attr_listf+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+/* Override any GCC internal prototype to avoid an error.
+   Use char because int might match the return type of a GCC
+   builtin and then its argument prototype would still apply.  */
+#ifdef __cplusplus
+extern "C"
+#endif
+char attr_listf ();
+int
+main ()
+{
+return attr_listf ();
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_link "$LINENO"; then :
+  ac_cv_lib_ext_attr_attr_listf=yes;
+		  ac_cv_lib_ext_attr=yes
+else
+  ac_cv_lib_ext_attr_attr_listf=no;
+		  ac_cv_lib_ext_attr=no
+fi
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext conftest.$ac_ext
+
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_ext_attr_attr_listf" >&5
+$as_echo "$ac_cv_lib_ext_attr_attr_listf" >&6; }
+    if test $ac_cv_lib_ext_attr_attr_listf = yes; then :
+  cat >>confdefs.h <<_ACEOF
+#define HAVE_ATTR_LISTF 1
+_ACEOF
+
+fi
+LIBS=$ac_check_lib_ext_save_LIBS
+
+if test $ac_cv_lib_ext_attr = yes; then :
+  cat >>confdefs.h <<_ACEOF
+#define HAVE_LIBATTR 1
+_ACEOF
+
+		case "$LIBREPLACE_FILESYS_LIBS" in
+		    *-lattr*)
+			;;
+		    *)
+			LIBREPLACE_FILESYS_LIBS="-lattr $LIBREPLACE_FILESYS_LIBS"
+			;;
+		esac
+
+
+fi
+
+
+ac_check_lib_ext_save_LIBS=$LIBS
+LIBS="-lattr $LIBREPLACE_FILESYS_LIBS  $LIBS"
+
+
+
+        { $as_echo "$as_me:${as_lineno-$LINENO}: checking for extattr_list_fd in -lattr" >&5
+$as_echo_n "checking for extattr_list_fd in -lattr... " >&6; }
+if ${ac_cv_lib_ext_attr_extattr_list_fd+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+/* Override any GCC internal prototype to avoid an error.
+   Use char because int might match the return type of a GCC
+   builtin and then its argument prototype would still apply.  */
+#ifdef __cplusplus
+extern "C"
+#endif
+char extattr_list_fd ();
+int
+main ()
+{
+return extattr_list_fd ();
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_link "$LINENO"; then :
+  ac_cv_lib_ext_attr_extattr_list_fd=yes;
+		  ac_cv_lib_ext_attr=yes
+else
+  ac_cv_lib_ext_attr_extattr_list_fd=no;
+		  ac_cv_lib_ext_attr=no
+fi
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext conftest.$ac_ext
+
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_ext_attr_extattr_list_fd" >&5
+$as_echo "$ac_cv_lib_ext_attr_extattr_list_fd" >&6; }
+    if test $ac_cv_lib_ext_attr_extattr_list_fd = yes; then :
+  cat >>confdefs.h <<_ACEOF
+#define HAVE_EXTATTR_LIST_FD 1
+_ACEOF
+
+fi
+LIBS=$ac_check_lib_ext_save_LIBS
+
+if test $ac_cv_lib_ext_attr = yes; then :
+  cat >>confdefs.h <<_ACEOF
+#define HAVE_LIBATTR 1
+_ACEOF
+
+		case "$LIBREPLACE_FILESYS_LIBS" in
+		    *-lattr*)
+			;;
+		    *)
+			LIBREPLACE_FILESYS_LIBS="-lattr $LIBREPLACE_FILESYS_LIBS"
+			;;
+		esac
 
-{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for secure mkstemp" >&5
-$as_echo_n "checking for secure mkstemp... " >&6; }
-if ${libreplace_cv_HAVE_SECURE_MKSTEMP+:} false; then :
-  $as_echo_n "(cached) " >&6
-else
+
+fi
+
+  ;;
+esac
+
+
+########################################################
+# Do xattr functions take additional options like on Darwin?
+if test x"$ac_cv_func_getxattr" = x"yes" ; then
+	{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether xattr interface takes additional options" >&5
+$as_echo_n "checking whether xattr interface takes additional options... " >&6; }
+if ${smb_attr_cv_xattr_add_opt+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+
+		old_LIBS=$LIBS
+		LIBS="$LIBS $LIBREPLACE_FILESYS_LIBS"
+		cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+			#include <sys/types.h>
+			#if HAVE_ATTR_XATTR_H
+			#include <attr/xattr.h>
+			#elif HAVE_SYS_XATTR_H
+			#include <sys/xattr.h>
+			#endif
+
+int
+main ()
+{
+
+			getxattr(0, 0, 0, 0, 0, 0);
+
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_compile "$LINENO"; then :
+  smb_attr_cv_xattr_add_opt=yes
+else
+  smb_attr_cv_xattr_add_opt=no;LIBS=$old_LIBS
+fi
+rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $smb_attr_cv_xattr_add_opt" >&5
+$as_echo "$smb_attr_cv_xattr_add_opt" >&6; }
+	if test x"$smb_attr_cv_xattr_add_opt" = x"yes"; then
+
+$as_echo "#define XATTR_ADDITIONAL_OPTIONS 1" >>confdefs.h
+
+	fi
+fi
+
+for ac_func in get_current_dir_name
+do :
+  ac_fn_c_check_func "$LINENO" "get_current_dir_name" "ac_cv_func_get_current_dir_name"
+if test "x$ac_cv_func_get_current_dir_name" = xyes; then :
+  cat >>confdefs.h <<_ACEOF
+#define HAVE_GET_CURRENT_DIR_NAME 1
+_ACEOF
+
+fi
+done
+
+
+ { $as_echo "$as_me:${as_lineno-$LINENO}: checking for setresuid declaration" >&5
+$as_echo_n "checking for setresuid declaration... " >&6; }
+if ${ac_cv_have_setresuid_decl+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+
+    cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#include <unistd.h>
+int
+main ()
+{
+int i = (int)setresuid
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_compile "$LINENO"; then :
+  ac_cv_have_setresuid_decl=yes
+else
+  ac_cv_have_setresuid_decl=no
+fi
+rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_have_setresuid_decl" >&5
+$as_echo "$ac_cv_have_setresuid_decl" >&6; }
+ if test x"$ac_cv_have_setresuid_decl" = x"yes"; then
+
+$as_echo "#define HAVE_SETRESUID_DECL 1" >>confdefs.h
+
+ fi
+
+
+ { $as_echo "$as_me:${as_lineno-$LINENO}: checking for setresgid declaration" >&5
+$as_echo_n "checking for setresgid declaration... " >&6; }
+if ${ac_cv_have_setresgid_decl+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+
+    cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#include <unistd.h>
+int
+main ()
+{
+int i = (int)setresgid
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_compile "$LINENO"; then :
+  ac_cv_have_setresgid_decl=yes
+else
+  ac_cv_have_setresgid_decl=no
+fi
+rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_have_setresgid_decl" >&5
+$as_echo "$ac_cv_have_setresgid_decl" >&6; }
+ if test x"$ac_cv_have_setresgid_decl" = x"yes"; then
+
+$as_echo "#define HAVE_SETRESGID_DECL 1" >>confdefs.h
+
+ fi
+
+
+ { $as_echo "$as_me:${as_lineno-$LINENO}: checking for errno declaration" >&5
+$as_echo_n "checking for errno declaration... " >&6; }
+if ${ac_cv_have_errno_decl+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+
+    cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#include <errno.h>
+int
+main ()
+{
+int i = (int)errno
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_compile "$LINENO"; then :
+  ac_cv_have_errno_decl=yes
+else
+  ac_cv_have_errno_decl=no
+fi
+rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_have_errno_decl" >&5
+$as_echo "$ac_cv_have_errno_decl" >&6; }
+ if test x"$ac_cv_have_errno_decl" = x"yes"; then
+
+$as_echo "#define HAVE_ERRNO_DECL 1" >>confdefs.h
+
+ fi
+
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for secure mkstemp" >&5
+$as_echo_n "checking for secure mkstemp... " >&6; }
+if ${libreplace_cv_HAVE_SECURE_MKSTEMP+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
 
 if test "$cross_compiling" = yes; then :
   libreplace_cv_HAVE_SECURE_MKSTEMP=cross
@@ -6353,11 +6977,26 @@ else
 main() {
   struct stat st;
   char tpl[20]="/tmp/test.XXXXXX";
+  char tpl2[20]="/tmp/test.XXXXXX";
   int fd = mkstemp(tpl);
-  if (fd == -1) exit(1);
+  int fd2 = mkstemp(tpl2);
+  if (fd == -1) {
+        if (fd2 != -1) {
+                unlink(tpl2);
+        }
+        exit(1);
+  }
+  if (fd2 == -1) exit(1);
   unlink(tpl);
+  unlink(tpl2);
   if (fstat(fd, &st) != 0) exit(1);
   if ((st.st_mode & 0777) != 0600) exit(1);
+  if (strcmp(tpl, "/tmp/test.XXXXXX") == 0) {
+        exit(1);
+  }
+  if (strcmp(tpl, tpl2) == 0) {
+        exit(1);
+  }
   exit(0);
 }
 _ACEOF
@@ -6836,43 +7475,6 @@ $as_echo "#define HAVE_SIG_ATOMIC_T_TYPE 1" >>confdefs.h
 fi
 
 
-{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for O_DIRECT flag to open(2)" >&5
-$as_echo_n "checking for O_DIRECT flag to open(2)... " >&6; }
-if ${libreplace_cv_HAVE_OPEN_O_DIRECT+:} false; then :
-  $as_echo_n "(cached) " >&6
-else
-
-cat confdefs.h - <<_ACEOF >conftest.$ac_ext
-/* end confdefs.h.  */
-
-#include <unistd.h>
-#ifdef HAVE_FCNTL_H
-#include <fcntl.h>
-#endif
-int
-main ()
-{
-int fd = open("/dev/null", O_DIRECT);
-  ;
-  return 0;
-}
-_ACEOF
-if ac_fn_c_try_compile "$LINENO"; then :
-  libreplace_cv_HAVE_OPEN_O_DIRECT=yes
-else
-  libreplace_cv_HAVE_OPEN_O_DIRECT=no
-fi
-rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
-fi
-{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $libreplace_cv_HAVE_OPEN_O_DIRECT" >&5
-$as_echo "$libreplace_cv_HAVE_OPEN_O_DIRECT" >&6; }
-if test x"$libreplace_cv_HAVE_OPEN_O_DIRECT" = x"yes"; then
-
-$as_echo "#define HAVE_OPEN_O_DIRECT 1" >>confdefs.h
-
-fi
-
-
 { $as_echo "$as_me:${as_lineno-$LINENO}: checking that the C compiler understands volatile" >&5
 $as_echo_n "checking that the C compiler understands volatile... " >&6; }
 if ${libreplace_cv_volatile+:} false; then :
@@ -7735,12 +8337,48 @@ if eval test \"x\$"$as_ac_Header"\" = x"yes"; then :
   cat >>confdefs.h <<_ACEOF
 #define `$as_echo "HAVE_$ac_header" | $as_tr_cpp` 1
 _ACEOF
-
+
+fi
+
+done
+
+
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for O_DIRECT flag to open(2)" >&5
+$as_echo_n "checking for O_DIRECT flag to open(2)... " >&6; }
+if ${libreplace_cv_HAVE_OPEN_O_DIRECT+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+#include <unistd.h>
+#ifdef HAVE_FCNTL_H
+#include <fcntl.h>
+#endif
+int
+main ()
+{
+int fd = open("/dev/null", O_DIRECT);
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_compile "$LINENO"; then :
+  libreplace_cv_HAVE_OPEN_O_DIRECT=yes
+else
+  libreplace_cv_HAVE_OPEN_O_DIRECT=no
 fi
+rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $libreplace_cv_HAVE_OPEN_O_DIRECT" >&5
+$as_echo "$libreplace_cv_HAVE_OPEN_O_DIRECT" >&6; }
+if test x"$libreplace_cv_HAVE_OPEN_O_DIRECT" = x"yes"; then
 
-done
-
+$as_echo "#define HAVE_OPEN_O_DIRECT 1" >>confdefs.h
 
+fi
 
 save_LIBS="$LIBS"
 LIBS=""
@@ -7966,68 +8604,28 @@ LIBDL="$LIBS"
 
 LIBS="$save_LIBS"
 
-ac_fn_c_check_func "$LINENO" "getpass" "ac_cv_func_getpass"
-if test "x$ac_cv_func_getpass" = xyes; then :
-  libreplace_cv_HAVE_GETPASS=yes
-fi
-
-ac_fn_c_check_func "$LINENO" "getpassphrase" "ac_cv_func_getpassphrase"
-if test "x$ac_cv_func_getpassphrase" = xyes; then :
-  libreplace_cv_HAVE_GETPASSPHRASE=yes
-fi
-
-if test x"$libreplace_cv_HAVE_GETPASS" = x"yes" -a x"$libreplace_cv_HAVE_GETPASSPHRASE" = x"yes"; then
-
-$as_echo "#define REPLACE_GETPASS_BY_GETPASSPHRASE 1" >>confdefs.h
-
-
-$as_echo "#define REPLACE_GETPASS 1" >>confdefs.h
-
-	LIBREPLACEOBJ="${LIBREPLACEOBJ} $libreplacedir/getpass.o"
-else
-
-{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether getpass should be replaced" >&5
-$as_echo_n "checking whether getpass should be replaced... " >&6; }
-if ${libreplace_cv_REPLACE_GETPASS+:} false; then :
-  $as_echo_n "(cached) " >&6
-else
-
-SAVE_CPPFLAGS="$CPPFLAGS"
-CPPFLAGS="$CPPFLAGS -I$libreplacedir/"
-cat confdefs.h - <<_ACEOF >conftest.$ac_ext
-/* end confdefs.h.  */
-
-#include "confdefs.h"
-#define NO_CONFIG_H
-#include "$libreplacedir/getpass.c"
-
-int
-main ()
-{
-
-  ;
-  return 0;
-}
+for ac_func in strptime
+do :
+  ac_fn_c_check_func "$LINENO" "strptime" "ac_cv_func_strptime"
+if test "x$ac_cv_func_strptime" = xyes; then :
+  cat >>confdefs.h <<_ACEOF
+#define HAVE_STRPTIME 1
 _ACEOF
-if ac_fn_c_try_compile "$LINENO"; then :
-  libreplace_cv_REPLACE_GETPASS=yes
-else
-  libreplace_cv_REPLACE_GETPASS=no
-fi
-rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
-CPPFLAGS="$SAVE_CPPFLAGS"
 
 fi
-{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $libreplace_cv_REPLACE_GETPASS" >&5
-$as_echo "$libreplace_cv_REPLACE_GETPASS" >&6; }
-if test x"$libreplace_cv_REPLACE_GETPASS" = x"yes"; then
-
-$as_echo "#define REPLACE_GETPASS 1" >>confdefs.h
+done
 
-	LIBREPLACEOBJ="${LIBREPLACEOBJ} $libreplacedir/getpass.o"
+ac_fn_c_check_decl "$LINENO" "strptime" "ac_cv_have_decl_strptime" "#include <time.h>
+"
+if test "x$ac_cv_have_decl_strptime" = xyes; then :
+  ac_have_decl=1
+else
+  ac_have_decl=0
 fi
 
-fi
+cat >>confdefs.h <<_ACEOF
+#define HAVE_DECL_STRPTIME $ac_have_decl
+_ACEOF
 
 { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether strptime is available and works" >&5
 $as_echo_n "checking whether strptime is available and works... " >&6; }
@@ -8059,10 +8657,11 @@ fi
 { $as_echo "$as_me:${as_lineno-$LINENO}: result: $libreplace_cv_STRPTIME_OK" >&5
 $as_echo "$libreplace_cv_STRPTIME_OK" >&6; }
 if test x"$libreplace_cv_STRPTIME_OK" != x"yes"; then
+        LIBREPLACEOBJ="${LIBREPLACEOBJ} $libreplacedir/strptime.o"
+else
 
-$as_echo "#define REPLACE_STRPTIME 1" >>confdefs.h
+$as_echo "#define HAVE_WORKING_STRPTIME 1" >>confdefs.h
 
-        LIBREPLACEOBJ="${LIBREPLACEOBJ} $libreplacedir/strptime.o"
 fi
 
 for ac_header in direct.h windows.h winsock2.h ws2tcpip.h
@@ -8700,6 +9299,43 @@ $as_echo "#define HAVE_STRUCT_TIMESPEC 1" >>confdefs.h
 
 fi
 
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for ucontext_t type" >&5
+$as_echo_n "checking for ucontext_t type... " >&6; }
+if ${libreplace_cv_ucontext_t+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+
+    cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+#include <signal.h>
+#if HAVE_SYS_UCONTEXT_H
+#include <sys/ucontext.h>
+# endif
+
+int
+main ()
+{
+ucontext_t uc; sigaddset(&uc.uc_sigmask, SIGUSR1);
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_compile "$LINENO"; then :
+  libreplace_cv_ucontext_t=yes
+else
+  libreplace_cv_ucontext_t=no
+fi
+rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $libreplace_cv_ucontext_t" >&5
+$as_echo "$libreplace_cv_ucontext_t" >&6; }
+if test x"$libreplace_cv_ucontext_t" = x"yes"; then
+
+$as_echo "#define HAVE_UCONTEXT_T 1" >>confdefs.h
+
+fi
+
 for ac_func in printf memset memcpy
 do :
   as_ac_var=`$as_echo "ac_cv_func_$ac_func" | $as_tr_sh`
@@ -10530,6 +11166,78 @@ fi
 LIBS=$old_LIBS
 CPPFLAGS="$libreplace_SAVE_CPPFLAGS"
 
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for SO_PEERCRED" >&5
+$as_echo_n "checking for SO_PEERCRED... " >&6; }
+if ${libreplace_cv_HAVE_PEERCRED+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#include <sys/types.h>
+#include <sys/socket.h>
+int
+main ()
+{
+struct ucred cred;
+ socklen_t cred_len;
+ int ret = getsockopt(0, SOL_SOCKET, SO_PEERCRED, &cred, &cred_len);
+
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_compile "$LINENO"; then :
+  libreplace_cv_HAVE_PEERCRED=yes
+else
+  libreplace_cv_HAVE_PEERCRED=no
+fi
+rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $libreplace_cv_HAVE_PEERCRED" >&5
+$as_echo "$libreplace_cv_HAVE_PEERCRED" >&6; }
+if test x"$libreplace_cv_HAVE_PEERCRED" = x"yes"; then
+
+$as_echo "#define HAVE_PEERCRED 1" >>confdefs.h
+
+fi
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for getpeereid" >&5
+$as_echo_n "checking for getpeereid... " >&6; }
+if ${libreplace_cv_HAVE_GETPEEREID+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#include <sys/types.h>
+#include <unistd.h>
+int
+main ()
+{
+uid_t uid; gid_t gid; int ret;
+ ret = getpeereid(0, &uid, &gid);
+
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_c_try_link "$LINENO"; then :
+  libreplace_cv_HAVE_GETPEEREID=yes
+else
+  libreplace_cv_HAVE_GETPEEREID=no
+fi
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext conftest.$ac_ext
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $libreplace_cv_HAVE_GETPEEREID" >&5
+$as_echo "$libreplace_cv_HAVE_GETPEEREID" >&6; }
+if test x"$libreplace_cv_HAVE_GETPEEREID" = xyes; then
+
+$as_echo "#define HAVE_GETPEEREID 1" >>confdefs.h
+
+fi
+
 LIBREPLACEOBJ="${LIBREPLACEOBJ} ${LIBREPLACE_NETWORK_OBJS}"
 
 echo "LIBREPLACE_NETWORK_CHECKS: END"
@@ -10955,7 +11663,7 @@ if test x"$INCLUDED_TDB" != x"no" ; then
        as_fn_error $? "cannot find tdb source in $tdbpaths" "$LINENO" 5
     fi
     TDB_OBJ="common/tdb.o common/dump.o common/transaction.o common/error.o common/traverse.o"
-    TDB_OBJ="$TDB_OBJ common/freelist.o common/freelistcheck.o common/io.o common/lock.o common/open.o common/check.o common/hash.o"
+    TDB_OBJ="$TDB_OBJ common/freelist.o common/freelistcheck.o common/io.o common/lock.o common/open.o common/check.o common/hash.o common/summary.o common/rescue.o"
 
 
     TDB_LIBS=""
@@ -11128,7 +11836,8 @@ if test "x$ac_cv_lib_tevent_tevent_context_init" = xyes; then :
    TEVENT_LIBS="-ltevent"
 fi
 
-    ac_fn_c_check_decl "$LINENO" "TEVENT_TRACE_BEFORE_WAIT" "ac_cv_have_decl_TEVENT_TRACE_BEFORE_WAIT" "$ac_includes_default"
+    ac_fn_c_check_decl "$LINENO" "TEVENT_TRACE_BEFORE_WAIT" "ac_cv_have_decl_TEVENT_TRACE_BEFORE_WAIT" "#include <tevent.h>
+"
 if test "x$ac_cv_have_decl_TEVENT_TRACE_BEFORE_WAIT" = xyes; then :
   ac_have_decl=1
 else
@@ -11138,9 +11847,6 @@ fi
 cat >>confdefs.h <<_ACEOF
 #define HAVE_DECL_TEVENT_TRACE_BEFORE_WAIT $ac_have_decl
 _ACEOF
-if test $ac_have_decl = 1; then :
-  #include <tevent.h>
-fi
 
     if test x"$ac_cv_header_tevent_h" = x"no" -o \
 	x"$ac_cv_lib_tevent_tevent_context_init" = x"no" -o \
@@ -11210,6 +11916,128 @@ done
 $as_echo "#define HAVE_EPOLL 1" >>confdefs.h
 
     fi
+
+    tevent_num_signals_includes="$ac_includes_default
+    #include <signal.h>
+    "
+    tevent_num_signals=64
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking value of NSIG" >&5
+$as_echo_n "checking value of NSIG... " >&6; }
+if ${ac_cv_valueof_NSIG+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  if ac_fn_c_compute_int "$LINENO" "(long int) (NSIG)" "ac_cv_valueof_NSIG"        "$tevent_num_signals_includes
+"; then :
+
+fi
+
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_valueof_NSIG" >&5
+$as_echo "$ac_cv_valueof_NSIG" >&6; }
+
+
+
+cat >>confdefs.h <<_ACEOF
+#define VALUEOF_NSIG $ac_cv_valueof_NSIG
+_ACEOF
+
+
+    v=$ac_cv_valueof_NSIG
+    test -n "$v" && test "$v" -gt "$tevent_num_signals" && {
+            tevent_num_signals=$v
+    }
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking value of _NSIG" >&5
+$as_echo_n "checking value of _NSIG... " >&6; }
+if ${ac_cv_valueof__NSIG+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  if ac_fn_c_compute_int "$LINENO" "(long int) (_NSIG)" "ac_cv_valueof__NSIG"        "$tevent_num_signals_includes
+"; then :
+
+fi
+
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_valueof__NSIG" >&5
+$as_echo "$ac_cv_valueof__NSIG" >&6; }
+
+
+
+cat >>confdefs.h <<_ACEOF
+#define VALUEOF__NSIG $ac_cv_valueof__NSIG
+_ACEOF
+
+
+    v=$ac_cv_valueof__NSIG
+    test -n "$v" && test "$v" -gt "$tevent_num_signals" && {
+            tevent_num_signals=$v
+    }
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking value of SIGRTMAX" >&5
+$as_echo_n "checking value of SIGRTMAX... " >&6; }
+if ${ac_cv_valueof_SIGRTMAX+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  if ac_fn_c_compute_int "$LINENO" "(long int) (SIGRTMAX)" "ac_cv_valueof_SIGRTMAX"        "$tevent_num_signals_includes
+"; then :
+
+fi
+
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_valueof_SIGRTMAX" >&5
+$as_echo "$ac_cv_valueof_SIGRTMAX" >&6; }
+
+
+
+cat >>confdefs.h <<_ACEOF
+#define VALUEOF_SIGRTMAX $ac_cv_valueof_SIGRTMAX
+_ACEOF
+
+
+    v=$ac_cv_valueof_SIGRTMAX
+    test -n "$v" && test "$v" -gt "$tevent_num_signals" && {
+            tevent_num_signals=$v
+    }
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking value of SIGRTMIN" >&5
+$as_echo_n "checking value of SIGRTMIN... " >&6; }
+if ${ac_cv_valueof_SIGRTMIN+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  if ac_fn_c_compute_int "$LINENO" "(long int) (SIGRTMIN)" "ac_cv_valueof_SIGRTMIN"        "$tevent_num_signals_includes
+"; then :
+
+fi
+
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_valueof_SIGRTMIN" >&5
+$as_echo "$ac_cv_valueof_SIGRTMIN" >&6; }
+
+
+
+cat >>confdefs.h <<_ACEOF
+#define VALUEOF_SIGRTMIN $ac_cv_valueof_SIGRTMIN
+_ACEOF
+
+
+    v=$ac_cv_valueof_SIGRTMIN
+    test -n "$v" && {
+            v=`expr $v + $v`
+    }
+    test -n "$v" && test "$v" -gt "$tevent_num_signals" && {
+            tevent_num_signals=$v
+    }
+
+cat >>confdefs.h <<_ACEOF
+#define TEVENT_NUM_SIGNALS $tevent_num_signals
+_ACEOF
+
+
+    if test x"$VERSIONSCRIPT" != "x"; then
+        EXPORTSFILE=tevent.exports
+
+    fi
 fi
 
 # Check whether --enable---enable-infiniband was given.
@@ -11567,28 +12395,29 @@ fi
 
 
 
+# Check whether --enable-pmda was given.
+if test "${enable_pmda+set}" = set; then :
+  enableval=$enable_pmda;
+fi
 
-for ac_header in sched.h
-do :
-  ac_fn_c_check_header_mongrel "$LINENO" "sched.h" "ac_cv_header_sched_h" "$ac_includes_default"
-if test "x$ac_cv_header_sched_h" = xyes; then :
-  cat >>confdefs.h <<_ACEOF
-#define HAVE_SCHED_H 1
-_ACEOF
 
-fi
+HAVE_PMDA=no
 
-done
+if eval "test x$enable_pmda = xyes"; then
+	HAVE_PMDA=yes
 
-for ac_header in pcp/pmapi.h pcp/impl.h pcp/pmda.h
+	for ac_header in pcp/pmapi.h pcp/impl.h pcp/pmda.h
 do :
   as_ac_Header=`$as_echo "ac_cv_header_$ac_header" | $as_tr_sh`
 ac_fn_c_check_header_compile "$LINENO" "$ac_header" "$as_ac_Header" "#ifdef HAVE_PCP_PMAPI_H
-# include <pcp/pmapi.h>
-#endif
-#ifdef HAVE_PCP_IMPL_H
-# include <pcp/impl.h>
-#endif
+	# include <pcp/pmapi.h>
+	#endif
+	#ifdef HAVE_PCP_IMPL_H
+	# include <pcp/impl.h>
+	#endif
+	#ifdef HAVE_PCP_PMDA_H
+	# include <pcp/pmda.h>
+	#endif
 
 "
 if eval test \"x\$"$as_ac_Header"\" = x"yes"; then :
@@ -11596,6 +12425,34 @@ if eval test \"x\$"$as_ac_Header"\" = x"yes"; then :
 #define `$as_echo "HAVE_$ac_header" | $as_tr_cpp` 1
 _ACEOF
 
+else
+  as_fn_error $? "Missing PCP pmda headers" "$LINENO" 5
+fi
+
+done
+
+fi
+
+if test x"$HAVE_PMDA" = x"yes"; then
+    CTDB_PMDA=bin/pmdactdb
+    CTDB_PMDA_INSTALL=install_pmda
+else
+    CTDB_PMDA=
+    CTDB_PMDA_INSTALL=
+fi
+
+
+
+
+
+for ac_header in sched.h
+do :
+  ac_fn_c_check_header_mongrel "$LINENO" "sched.h" "ac_cv_header_sched_h" "$ac_includes_default"
+if test "x$ac_cv_header_sched_h" = xyes; then :
+  cat >>confdefs.h <<_ACEOF
+#define HAVE_SCHED_H 1
+_ACEOF
+
 fi
 
 done
@@ -11671,17 +12528,6 @@ $as_echo "#define HAVE_SOCK_SIN_LEN 1" >>confdefs.h
 
 fi
 
-if test x"$ac_cv_header_pcp_pmda_h" = x"yes"; then
-    CTDB_PMDA=bin/pmdactdb
-    CTDB_PMDA_INSTALL=install_pmda
-else
-    CTDB_PMDA=
-    CTDB_PMDA_INSTALL=
-fi
-
-
-
-
 
 
 
@@ -12196,7 +13042,7 @@ cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1
 # report actual input values of CONFIG_FILES etc. instead of their
 # values after options handling.
 ac_log="
-This file was extended by ctdb $as_me 2.1, which was
+This file was extended by ctdb $as_me 2.2, which was
 generated by GNU Autoconf 2.69.  Invocation command line was
 
   CONFIG_FILES    = $CONFIG_FILES
@@ -12262,7 +13108,7 @@ _ACEOF
 cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1
 ac_cs_config="`$as_echo "$ac_configure_args" | sed 's/^ //; s/[\\""\`\$]/\\\\&/g'`"
 ac_cs_version="\\
-ctdb config.status 2.1
+ctdb config.status 2.2
 configured by $0, generated by GNU Autoconf 2.69,
   with options \\"\$ac_cs_config\\"
 
diff --git a/configure.ac b/configure.ac
index 85934a7..37b5a64 100644
--- a/configure.ac
+++ b/configure.ac
@@ -94,16 +94,9 @@ m4_include(ib/config.m4)
 m4_include(lib/util/signal.m4)
 m4_include(lib/util/fault.m4)
 m4_include(lib/socket_wrapper/config.m4)
+m4_include(utils/pmda/config.m4)
 
 AC_CHECK_HEADERS(sched.h)
-AC_CHECK_HEADERS(pcp/pmapi.h pcp/impl.h pcp/pmda.h, [], [],
-[[#ifdef HAVE_PCP_PMAPI_H
-# include <pcp/pmapi.h>
-#endif
-#ifdef HAVE_PCP_IMPL_H
-# include <pcp/impl.h>
-#endif
-]])
 
 AC_CHECK_DECL([ETIME], [],[AC_DEFINE([ETIME], ETIMEDOUT, [ETIME on non-supporting platforms])], [
 #include <errno.h>
@@ -122,20 +115,9 @@ if test x"$ctdb_cv_HAVE_SOCK_SIN_LEN" = x"yes"; then
     AC_DEFINE(HAVE_SOCK_SIN_LEN,1,[Whether the sockaddr_in struct has a sin_len property])
 fi
 
-if test x"$ac_cv_header_pcp_pmda_h" = x"yes"; then
-    CTDB_PMDA=bin/pmdactdb
-    CTDB_PMDA_INSTALL=install_pmda
-else
-    CTDB_PMDA=
-    CTDB_PMDA_INSTALL=
-fi
-
-
 AC_SUBST(EXTRA_OBJ)
 AC_SUBST(CTDB_SYSTEM_OBJ)
 AC_SUBST(CTDB_SCSI_IO)
 AC_SUBST(CTDB_PCAP_LDFLAGS)
-AC_SUBST(CTDB_PMDA)
-AC_SUBST(CTDB_PMDA_INSTALL)
 
 AC_OUTPUT(Makefile ctdb.pc)
diff --git a/doc/ctdb.1 b/doc/ctdb.1
index d99acd2..45d981e 100644
--- a/doc/ctdb.1
+++ b/doc/ctdb.1
@@ -1,13 +1,22 @@
 '\" t
 .\"     Title: ctdb
 .\"    Author: [FIXME: author] [see http://docbook.sf.net/el/author]
-.\" Generator: DocBook XSL Stylesheets v1.75.2 <http://docbook.sf.net/>
-.\"      Date: 01/09/2013
+.\" Generator: DocBook XSL Stylesheets v1.78.1 <http://docbook.sf.net/>
+.\"      Date: 05/30/2013
 .\"    Manual: CTDB - clustered TDB database
 .\"    Source: ctdb
 .\"  Language: English
 .\"
-.TH "CTDB" "1" "01/09/2013" "ctdb" "CTDB \- clustered TDB database"
+.TH "CTDB" "1" "05/30/2013" "ctdb" "CTDB \- clustered TDB database"
+.\" -----------------------------------------------------------------
+.\" * Define some portability stuff
+.\" -----------------------------------------------------------------
+.\" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+.\" http://bugs.debian.org/507673
+.\" http://lists.gnu.org/archive/html/groff/2009-02/msg00013.html
+.\" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+.ie \n(.g .ds Aq \(aq
+.el       .ds Aq '
 .\" -----------------------------------------------------------------
 .\" * set default formatting
 .\" -----------------------------------------------------------------
@@ -283,6 +292,26 @@ response from 3 time=0\&.000114 sec  (2 clients)
 .if n \{\
 .RE
 .\}
+.SS "runstate [setup|first_recovery|startup|running]"
+.PP
+Print the runstate of the specified node\&. Runstates are used to serialise important state transitions in CTDB, particularly during startup\&.
+.PP
+If one or more optional runstate arguments are specified then the node must be in one of these runstates for the command to succeed\&.
+.PP
+Example: ctdb runstate
+.PP
+Example output:
+.sp
+.if n \{\
+.RS 4
+.\}
+.nf
+RUNNING
+      
+.fi
+.if n \{\
+.RE
+.\}
 .SS "ifaces"
 .PP
 This command will display the list of network interfaces, which could host public addresses, along with their status\&.
@@ -432,12 +461,12 @@ Example output:
 .PP
 This command is used to disable an eventscript\&.
 .PP
-This will take effect the next time the eventscripts are being executed so it can take a short while until this is reflected in \'scriptstatus\'\&.
+This will take effect the next time the eventscripts are being executed so it can take a short while until this is reflected in \*(Aqscriptstatus\*(Aq\&.
 .SS "enablescript <script>"
 .PP
 This command is used to enable an eventscript\&.
 .PP
-This will take effect the next time the eventscripts are being executed so it can take a short while until this is reflected in \'scriptstatus\'\&.
+This will take effect the next time the eventscripts are being executed so it can take a short while until this is reflected in \*(Aqscriptstatus\*(Aq\&.
 .SS "getvar <name>"
 .PP
 Get the runtime value of a tuneable variable\&.
@@ -733,29 +762,29 @@ This command is used when adding new nodes, or removing existing nodes from an e
 .PP
 Procedure to add a node:
 .PP
-1, To expand an existing cluster, first ensure with \'ctdb status\' that all nodes are up and running and that they are all healthy\&. Do not try to expand a cluster unless it is completely healthy!
+1, To expand an existing cluster, first ensure with \*(Aqctdb status\*(Aq that all nodes are up and running and that they are all healthy\&. Do not try to expand a cluster unless it is completely healthy!
 .PP
 2, On all nodes, edit /etc/ctdb/nodes and add the new node as the last entry to the file\&. The new node MUST be added to the end of this file!
 .PP
 3, Verify that all the nodes have identical /etc/ctdb/nodes files after you edited them and added the new node!
 .PP
-4, Run \'ctdb reloadnodes\' to force all nodes to reload the nodesfile\&.
+4, Run \*(Aqctdb reloadnodes\*(Aq to force all nodes to reload the nodesfile\&.
 .PP
-5, Use \'ctdb status\' on all nodes and verify that they now show the additional node\&.
+5, Use \*(Aqctdb status\*(Aq on all nodes and verify that they now show the additional node\&.
 .PP
 6, Install and configure the new node and bring it online\&.
 .PP
 Procedure to remove a node:
 .PP
-1, To remove a node from an existing cluster, first ensure with \'ctdb status\' that all nodes, except the node to be deleted, are up and running and that they are all healthy\&. Do not try to remove a node from a cluster unless the cluster is completely healthy!
+1, To remove a node from an existing cluster, first ensure with \*(Aqctdb status\*(Aq that all nodes, except the node to be deleted, are up and running and that they are all healthy\&. Do not try to remove a node from a cluster unless the cluster is completely healthy!
 .PP
 2, Shutdown and poweroff the node to be removed\&.
 .PP
-3, On all other nodes, edit the /etc/ctdb/nodes file and comment out the node to be removed\&. Do not delete the line for that node, just comment it out by adding a \'#\' at the beginning of the line\&.
+3, On all other nodes, edit the /etc/ctdb/nodes file and comment out the node to be removed\&. Do not delete the line for that node, just comment it out by adding a \*(Aq#\*(Aq at the beginning of the line\&.
 .PP
-4, Run \'ctdb reloadnodes\' to force all nodes to reload the nodesfile\&.
+4, Run \*(Aqctdb reloadnodes\*(Aq to force all nodes to reload the nodesfile\&.
 .PP
-5, Use \'ctdb status\' on all nodes and verify that the deleted node no longer shows up in the list\&.\&.
+5, Use \*(Aqctdb status\*(Aq on all nodes and verify that the deleted node no longer shows up in the list\&.\&.
 .PP
 .SS "reloadips"
 .PP
@@ -765,7 +794,7 @@ Procedure to update the public address configuration on a single node:
 .PP
 1, Update the /etc/ctdb/public_addresses file on the node
 .PP
-2, Run \'ctdb reloadips\' on the node\&.
+2, Run \*(Aqctdb reloadips\*(Aq on the node\&.
 .PP
 The file will then be reloaded on the node and addresses will be added or removed as required to match the newly loaded file\&. When updating a single node it may take a little while before any newly added addresses are failed onto the node\&.
 .PP
@@ -774,7 +803,7 @@ Procedure to update the public address configuration on whole cluster:
 .PP
 1, Update the /etc/ctdb/public_addresses file on all nodes
 .PP
-2, Run \'ctdb reloadips \-n all\'\&.
+2, Run \*(Aqctdb reloadips \-n all\*(Aq\&.
 .PP
 This command will then force all nodes to reload and update the addresses\&. This process is controlled and synchronized by the recovery master to ensure that all addresses are added to all nodes as one single operation, after which any required ip node rebalancing may may take place\&.
 .SS "tickle <srcip:port> <dstip:port>"
@@ -847,7 +876,7 @@ This command checks if a specific process exists on the CTDB host\&. This is mai
 .PP
 This command lists all clustered TDB databases that the CTDB daemon has attached to\&. Some databases are flagged as PERSISTENT, this means that the database stores data persistently and the data will remain across reboots\&. One example of such a database is secrets\&.tdb where information about how the cluster was joined to the domain is stored\&.
 .PP
-If a PERSISTENT database is not in a healthy state the database is flagged as UNHEALTHY\&. If there\'s at least one completely healthy node running in the cluster, it\'s possible that the content is restored by a recovery run automaticly\&. Otherwise an administrator needs to analyze the problem\&.
+If a PERSISTENT database is not in a healthy state the database is flagged as UNHEALTHY\&. If there\*(Aqs at least one completely healthy node running in the cluster, it\*(Aqs possible that the content is restored by a recovery run automaticly\&. Otherwise an administrator needs to analyze the problem\&.
 .PP
 See also "ctdb getdbstatus", "ctdb backupdb", "ctdb restoredb", "ctdb dumpbackup", "ctdb wipedb", "ctdb setvar AllowUnhealthyDBRead 1" and (if samba or tdb\-utils are installed) "tdbtool check"\&.
 .PP
@@ -940,7 +969,7 @@ dbid: 0xf2a58948
 name: registry\&.tdb
 path: /var/ctdb/persistent/registry\&.tdb\&.0
 PERSISTENT: yes
-HEALTH: NO\-HEALTHY\-NODES \- ERROR \- Backup of corrupted TDB in \'/var/ctdb/persistent/registry\&.tdb\&.0\&.corrupted\&.20091208091949\&.0Z\'
+HEALTH: NO\-HEALTHY\-NODES \- ERROR \- Backup of corrupted TDB in \*(Aq/var/ctdb/persistent/registry\&.tdb\&.0\&.corrupted\&.20091208091949\&.0Z\*(Aq
       
 .fi
 .if n \{\
diff --git a/doc/ctdb.1.html b/doc/ctdb.1.html
index e8f20d3..a05f2d0 100644
--- a/doc/ctdb.1.html
+++ b/doc/ctdb.1.html
@@ -1,6 +1,6 @@
-<html><head><meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1"><title>ctdb</title><meta name="generator" content="DocBook XSL Stylesheets V1.75.2"></head><body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF"><div class="refentry" title="ctdb"><a name="ctdb.1"></a><div class="titlepage"></div><div class="refnamediv"><h2>Name</h2><p>ctdb — clustered tdb database management utility</p></div><div class="refsynopsisdiv" title="Synopsis"><h2>Synopsis</h2><div class="cmdsynopsis"><p><code class="command">ctdb [ OPTIONS ] COMMAND ...</code> </p></div><div class="cmdsynopsis"><p><code class="command">ctdb</code>  [-n <node>] [-Y] [-t <timeout>] [-T <timelimit>] [-? --help] [--usage] [-d --debug=<INTEGER>] [--socket=<filename>] [--print-emptyrecords] [--print-datasize] [--print-lmaster] [--print-hash] [--print-recordflags]</p></div></div><div class="refsect1" title="DESCRIPTION"><a name="id529348"></a><h2>DESCRIPTION</h2><p>
+<html><head><meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1"><title>ctdb</title><meta name="generator" content="DocBook XSL Stylesheets V1.78.1"></head><body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF"><div class="refentry"><a name="ctdb.1"></a><div class="titlepage"></div><div class="refnamediv"><h2>Name</h2><p>ctdb — clustered tdb database management utility</p></div><div class="refsynopsisdiv"><h2>Synopsis</h2><div class="cmdsynopsis"><p><code class="command">ctdb [ OPTIONS ] COMMAND ...</code> </p></div><div class="cmdsynopsis"><p><code class="command">ctdb</code>  [-n <node>] [-Y] [-t <timeout>] [-T <timelimit>] [-? --help] [--usage] [-d --debug=<INTEGER>] [--socket=<filename>] [--print-emptyrecords] [--print-datasize] [--print-lmaster] [--print-hash] [--print-recordflags]</p></div></div><div class="refsect1"><a name="idm264423591616"></a><h2>DESCRIPTION</h2><p>
       ctdb is a utility to view and manage a ctdb cluster.
-    </p></div><div class="refsect1" title="OPTIONS"><a name="id529358"></a><h2>OPTIONS</h2><div class="variablelist"><dl><dt><span class="term">-n <pnn></span></dt><dd><p>
+    </p></div><div class="refsect1"><a name="idm264423590512"></a><h2>OPTIONS</h2><div class="variablelist"><dl class="variablelist"><dt><span class="term">-n <pnn></span></dt><dd><p>
             This specifies the physical node number on which to execute the 
 	    command. Default is to run the command on the daemon running on 
 	    the local host.
@@ -46,13 +46,13 @@
             This lets catdb and dumpdbbackup print the
             record flags for each record. Note that cattdb always
             prints the flags.
-          </p></dd></dl></div></div><div class="refsect1" title="Administrative Commands"><a name="id529553"></a><h2>Administrative Commands</h2><p>
+          </p></dd></dl></div></div><div class="refsect1"><a name="idm264423567536"></a><h2>Administrative Commands</h2><p>
       These are commands used to monitor and administrate a CTDB cluster.
-    </p><div class="refsect2" title="pnn"><a name="id529562"></a><h3>pnn</h3><p>
+    </p><div class="refsect2"><a name="idm264423566512"></a><h3>pnn</h3><p>
         This command displays the pnn of the current node.
-      </p></div><div class="refsect2" title="status"><a name="id529571"></a><h3>status</h3><p>
+      </p></div><div class="refsect2"><a name="idm264423565440"></a><h3>status</h3><p>
         This command shows the current status of the ctdb node.
-      </p><div class="refsect3" title="node status"><a name="id529580"></a><h4>node status</h4><p>
+      </p><div class="refsect3"><a name="idm264423564512"></a><h4>node status</h4><p>
           Node status reflects the current status of the node. There are five possible states:
         </p><p>
           OK - This node is fully functional.
@@ -75,7 +75,7 @@
 	in a cluster like a node that is ok. Some interfaces to serve
 	public ip addresses are down, but at least one interface is up.
 	See also "ctdb ifaces".
-        </p></div><div class="refsect3" title="generation"><a name="id529629"></a><h4>generation</h4><p>
+        </p></div><div class="refsect3"><a name="idm264423558592"></a><h4>generation</h4><p>
           The generation id is a number that indicates the current generation 
           of a cluster instance. Each time a cluster goes through a 
           reconfiguration or a recovery its generation id will be changed.
@@ -96,10 +96,10 @@
 	  All nodes start with generation "INVALID" and are not assigned a real
 	  generation id until they have successfully been merged with a cluster
 	  through a recovery.
-        </p></div><div class="refsect3" title="VNNMAP"><a name="id529654"></a><h4>VNNMAP</h4><p>
+        </p></div><div class="refsect3"><a name="idm264423555536"></a><h4>VNNMAP</h4><p>
           The list of Virtual Node Numbers. This is a list of all nodes that actively participates in the cluster and that share the workload of hosting the Clustered TDB database records.
           Only nodes that are participating in the vnnmap can become lmaster or dmaster for a database record.
-        </p></div><div class="refsect3" title="Recovery mode"><a name="id529666"></a><h4>Recovery mode</h4><p>
+        </p></div><div class="refsect3"><a name="idm264423554160"></a><h4>Recovery mode</h4><p>
           This is the current recovery mode of the cluster. There are two possible modes:
         </p><p>
           NORMAL - The cluster is fully operational.
@@ -119,7 +119,7 @@
 	have been recovered, the node mode will change into NORMAL mode
 	and the databases will be "thawed", allowing samba to access the
 	databases again.
-	</p></div><div class="refsect3" title="Recovery master"><a name="id529698"></a><h4>Recovery master</h4><p>
+	</p></div><div class="refsect3"><a name="idm264423550384"></a><h4>Recovery master</h4><p>
           This is the cluster node that is currently designated as the recovery master. This node is responsible of monitoring the consistency of the cluster and to perform the actual recovery process when reqired.
         </p><p>
 	Only one node at a time can be the designated recovery master. Which
@@ -141,9 +141,9 @@ hash:2 lmaster:2
 hash:3 lmaster:3
 Recovery mode:NORMAL (0)
 Recovery master:0
-      </pre></div><div class="refsect2" title="recmaster"><a name="id529731"></a><h3>recmaster</h3><p>
+      </pre></div><div class="refsect2"><a name="idm264423546544"></a><h3>recmaster</h3><p>
         This command shows the pnn of the node which is currently the recmaster.
-      </p></div><div class="refsect2" title="uptime"><a name="id529741"></a><h3>uptime</h3><p>
+      </p></div><div class="refsect2"><a name="idm264423545376"></a><h3>uptime</h3><p>
         This command shows the uptime for the ctdb daemon. When the last recovery or ip-failover completed and how long it took. If the "duration" is shown as a negative number, this indicates that there is a recovery/failover in progress and it started that many seconds ago.
       </p><p>
 	Example: ctdb uptime
@@ -152,7 +152,7 @@ Current time of node          :                Thu Oct 29 10:38:54 2009
 Ctdbd start time              : (000 16:54:28) Wed Oct 28 17:44:26 2009
 Time of last recovery/failover: (000 16:53:31) Wed Oct 28 17:45:23 2009
 Duration of last recovery/failover: 2.248552 seconds
-      </pre></div><div class="refsect2" title="listnodes"><a name="id529767"></a><h3>listnodes</h3><p>
+      </pre></div><div class="refsect2"><a name="idm264423542224"></a><h3>listnodes</h3><p>
         This command shows lists the ip addresses of all the nodes in the cluster.
       </p><p>
 	Example: ctdb listnodes
@@ -161,7 +161,7 @@ Duration of last recovery/failover: 2.248552 seconds
 10.0.0.72
 10.0.0.73
 10.0.0.74
-      </pre></div><div class="refsect2" title="ping"><a name="id529790"></a><h3>ping</h3><p>
+      </pre></div><div class="refsect2"><a name="idm264423539552"></a><h3>ping</h3><p>
         This command will "ping" all CTDB daemons in the cluster to verify that they are processing commands correctly.
       </p><p>
 	Example: ctdb ping
@@ -172,7 +172,21 @@ response from 0 time=0.000054 sec  (3 clients)
 response from 1 time=0.000144 sec  (2 clients)
 response from 2 time=0.000105 sec  (2 clients)
 response from 3 time=0.000114 sec  (2 clients)
-      </pre></div><div class="refsect2" title="ifaces"><a name="id529814"></a><h3>ifaces</h3><p>
+      </pre></div><div class="refsect2"><a name="idm264423536624"></a><h3>runstate [setup|first_recovery|startup|running]</h3><p>
+        Print the runstate of the specified node.  Runstates are used
+        to serialise important state transitions in CTDB, particularly
+        during startup.
+      </p><p>
+        If one or more optional runstate arguments are specified then
+        the node must be in one of these runstates for the command to
+        succeed.
+      </p><p>
+	Example: ctdb runstate
+      </p><p>
+	Example output:
+      </p><pre class="screen">
+RUNNING
+      </pre></div><div class="refsect2"><a name="idm264418543872"></a><h3>ifaces</h3><p>
 	This command will display the list of network interfaces, which could
 	host public addresses, along with their status.
       </p><p>
@@ -195,13 +209,13 @@ name:eth2 link:up references:1
 :eth4:0:0
 :eth3:1:1
 :eth2:1:1
-      </pre></div><div class="refsect2" title="setifacelink <iface> <status>"><a name="id529852"></a><h3>setifacelink <iface> <status></h3><p>
+      </pre></div><div class="refsect2"><a name="idm264418539648"></a><h3>setifacelink <iface> <status></h3><p>
 	This command will set the status of a network interface.
 	The status needs to be "up" or "down". This is typically
 	used in the 10.interfaces script in the "monitor" event.
       </p><p>
 	Example: ctdb setifacelink eth0 up
-      </p></div><div class="refsect2" title="ip"><a name="id529866"></a><h3>ip</h3><p>
+      </p></div><div class="refsect2"><a name="idm264418538048"></a><h3>ip</h3><p>
         This command will display the list of public addresses that are provided by the cluster and which physical node is currently serving this ip. By default this command will ONLY show those public addresses that are known to the node itself. To see the full list of all public ips across the cluster you must use "ctdb ip -n all".
       </p><p>
 	Example: ctdb ip
@@ -231,7 +245,7 @@ Public IPs on node 0
 :172.31.92.83:0:eth5:eth5:eth4,eth5:
 :172.31.92.84:1::eth5:eth4,eth5:
 :172.31.92.85:0:eth5:eth5:eth4,eth5:
-      </pre></div><div class="refsect2" title="ipinfo <ip>"><a name="id529917"></a><h3>ipinfo <ip></h3><p>
+      </pre></div><div class="refsect2"><a name="idm264418532864"></a><h3>ipinfo <ip></h3><p>
         This command will display details about the specified public addresses.
       </p><p>
 	Example: ctdb ipinfo 172.31.92.85
@@ -244,7 +258,7 @@ CurrentNode:0
 NumInterfaces:2
 Interface[1]: Name:eth4 Link:down References:0
 Interface[2]: Name:eth5 Link:up References:2 (active)
-      </pre></div><div class="refsect2" title="scriptstatus"><a name="id529941"></a><h3>scriptstatus</h3><p>
+      </pre></div><div class="refsect2"><a name="idm264418530144"></a><h3>scriptstatus</h3><p>
         This command displays which scripts where run in the previous monitoring cycle and the result of each script. If a script failed with an error, causing the node to become unhealthy, the output from that script is also shown.
       </p><p>
 	Example: ctdb scriptstatus
@@ -261,15 +275,15 @@ Interface[2]: Name:eth5 Link:up References:2 (active)
 41.httpd             Status:OK    Duration:0.039 Tue Mar 24 18:56:57 2009
 50.samba             Status:ERROR    Duration:0.082 Tue Mar 24 18:56:57 2009
    OUTPUT:ERROR: Samba tcp port 445 is not responding
-      </pre></div><div class="refsect2" title="disablescript <script>"><a name="id529970"></a><h3>disablescript <script></h3><p>
+      </pre></div><div class="refsect2"><a name="idm264418526784"></a><h3>disablescript <script></h3><p>
 	This command is used to disable an eventscript.
       </p><p>
 	This will take effect the next time the eventscripts are being executed so it can take a short while until this is reflected in 'scriptstatus'.
-      </p></div><div class="refsect2" title="enablescript <script>"><a name="id529984"></a><h3>enablescript <script></h3><p>
+      </p></div><div class="refsect2"><a name="idm264418525200"></a><h3>enablescript <script></h3><p>
 	This command is used to enable an eventscript.
       </p><p>
 	This will take effect the next time the eventscripts are being executed so it can take a short while until this is reflected in 'scriptstatus'.
-      </p></div><div class="refsect2" title="getvar <name>"><a name="id529999"></a><h3>getvar <name></h3><p>
+      </p></div><div class="refsect2"><a name="idm264418523616"></a><h3>getvar <name></h3><p>
         Get the runtime value of a tuneable variable.
       </p><p>
 	Example: ctdb getvar MaxRedirectCount
@@ -277,11 +291,11 @@ Interface[2]: Name:eth5 Link:up References:2 (active)
 	Example output:
       </p><pre class="screen">
 MaxRedirectCount    = 3
-      </pre></div><div class="refsect2" title="setvar <name> <value>"><a name="id530021"></a><h3>setvar <name> <value></h3><p>
+      </pre></div><div class="refsect2"><a name="idm264418521200"></a><h3>setvar <name> <value></h3><p>
         Set the runtime value of a tuneable variable.
       </p><p>
 	Example: ctdb setvar MaxRedirectCount 5
-      </p></div><div class="refsect2" title="listvars"><a name="id530035"></a><h3>listvars</h3><p>
+      </p></div><div class="refsect2"><a name="idm264418519712"></a><h3>listvars</h3><p>
       List all tuneable variables, except the values of the obsolete tunables
       like VacuumMinInterval. The obsolete tunables can be retrieved only
       explicitly with the "ctdb getvar" command.
@@ -334,7 +348,7 @@ StatHistoryInterval     = 1
 DeferredAttachTO        = 120
 AllowClientDBAttach     = 1
 RecoverPDBBySeqNum      = 0
-      </pre></div><div class="refsect2" title="lvsmaster"><a name="id530069"></a><h3>lvsmaster</h3><p>
+      </pre></div><div class="refsect2"><a name="idm264418515776"></a><h3>lvsmaster</h3><p>
       This command shows which node is currently the LVSMASTER. The
       LVSMASTER is the node in the cluster which drives the LVS system and
       which receives all incoming traffic from clients.
@@ -345,7 +359,7 @@ RecoverPDBBySeqNum      = 0
       evenly onto the other nodes in the cluster. This is an alternative to using
       public ip addresses. See the manpage for ctdbd for more information
       about LVS.
-      </p></div><div class="refsect2" title="lvs"><a name="id530086"></a><h3>lvs</h3><p>
+      </p></div><div class="refsect2"><a name="idm264418513728"></a><h3>lvs</h3><p>
       This command shows which nodes in the cluster are currently active in the
       LVS configuration. I.e. which nodes we are currently loadbalancing
       the single ip address across.
@@ -360,7 +374,7 @@ RecoverPDBBySeqNum      = 0
       </p><pre class="screen">
 2:10.0.0.13
 3:10.0.0.14
-      </pre></div><div class="refsect2" title="getcapabilities"><a name="id530112"></a><h3>getcapabilities</h3><p>
+      </pre></div><div class="refsect2"><a name="idm264418510768"></a><h3>getcapabilities</h3><p>
       This command shows the capabilities of the current node.
       Please see manpage for ctdbd for a full list of all capabilities and
       more detailed description.
@@ -379,7 +393,7 @@ RecoverPDBBySeqNum      = 0
 RECMASTER: YES
 LMASTER: YES
 LVS: NO
-      </pre></div><div class="refsect2" title="statistics"><a name="id530143"></a><h3>statistics</h3><p>
+      </pre></div><div class="refsect2"><a name="idm264418507264"></a><h3>statistics</h3><p>
         Collect statistics from the CTDB daemon about how many calls it has served.
       </p><p>
 	Example: ctdb statistics
@@ -421,23 +435,23 @@ CTDB version 1
  max_hop_count                      0
  max_call_latency                   4.948321 sec
  max_lockwait_latency               0.000000 sec
-      </pre></div><div class="refsect2" title="statisticsreset"><a name="id530176"></a><h3>statisticsreset</h3><p>
+      </pre></div><div class="refsect2"><a name="idm264418503472"></a><h3>statisticsreset</h3><p>
         This command is used to clear all statistics counters in a node.
       </p><p>
 	Example: ctdb statisticsreset
-      </p></div><div class="refsect2" title="getreclock"><a name="id530189"></a><h3>getreclock</h3><p>
+      </p></div><div class="refsect2"><a name="idm264418501968"></a><h3>getreclock</h3><p>
 	This command is used to show the filename of the reclock file that is used.
       </p><p>
 	Example output:
       </p><pre class="screen">
 Reclock file:/gpfs/.ctdb/shared
-      </pre></div><div class="refsect2" title="setreclock [filename]"><a name="id530208"></a><h3>setreclock [filename]</h3><p>
+      </pre></div><div class="refsect2"><a name="idm264418499840"></a><h3>setreclock [filename]</h3><p>
 	This command is used to modify, or clear, the file that is used as the reclock file at runtime. When this command is used, the reclock file checks are disabled. To re-enable the checks the administrator needs to activate the "VerifyRecoveryLock" tunable using "ctdb setvar".
       </p><p>
 	If run with no parameter this will remove the reclock file completely. If run with a parameter the parameter specifies the new filename to use for the recovery lock.
       </p><p>
 	This command only affects the runtime settings of a ctdb node and will be lost when ctdb is restarted. For persistent changes to the reclock file setting you must edit /etc/sysconfig/ctdb.
-      </p></div><div class="refsect2" title="getdebug"><a name="id530229"></a><h3>getdebug</h3><p>
+      </p></div><div class="refsect2"><a name="idm264418497344"></a><h3>getdebug</h3><p>
         Get the current debug level for the node. the debug level controls what information is written to the log file.
       </p><p>
 	The debug levels are mapped to the corresponding syslog levels.
@@ -447,42 +461,42 @@ Reclock file:/gpfs/.ctdb/shared
 	The list of debug levels from highest to lowest are :
       </p><p>
 	EMERG ALERT CRIT ERR WARNING NOTICE INFO DEBUG
-      </p></div><div class="refsect2" title="setdebug <debuglevel>"><a name="id530252"></a><h3>setdebug <debuglevel></h3><p>
+      </p></div><div class="refsect2"><a name="idm264418494752"></a><h3>setdebug <debuglevel></h3><p>
         Set the debug level of a node. This controls what information will be logged.
       </p><p>
 	The debuglevel is one of EMERG ALERT CRIT ERR WARNING NOTICE INFO DEBUG
-      </p></div><div class="refsect2" title="getpid"><a name="id530265"></a><h3>getpid</h3><p>
+      </p></div><div class="refsect2"><a name="idm264418493136"></a><h3>getpid</h3><p>
         This command will return the process id of the ctdb daemon.
-      </p></div><div class="refsect2" title="disable"><a name="id530275"></a><h3>disable</h3><p>
+      </p></div><div class="refsect2"><a name="idm264418492016"></a><h3>disable</h3><p>
         This command is used to administratively disable a node in the cluster.
         A disabled node will still participate in the cluster and host
         clustered TDB records but its public ip address has been taken over by
         a different node and it no longer hosts any services.
-      </p></div><div class="refsect2" title="enable"><a name="id530286"></a><h3>enable</h3><p>
+      </p></div><div class="refsect2"><a name="idm264418490672"></a><h3>enable</h3><p>
         Re-enable a node that has been administratively disabled.
-      </p></div><div class="refsect2" title="stop"><a name="id530296"></a><h3>stop</h3><p>
+      </p></div><div class="refsect2"><a name="idm264418489552"></a><h3>stop</h3><p>
         This command is used to administratively STOP a node in the cluster.
         A STOPPED node is connected to the cluster but will not host any
 	public ip addresse, nor does it participate in the VNNMAP.
 	The difference between a DISABLED node and a STOPPED node is that
 	a STOPPED node does not host any parts of the database which means
 	that a recovery is required to stop/continue nodes.
-      </p></div><div class="refsect2" title="continue"><a name="id530308"></a><h3>continue</h3><p>
+      </p></div><div class="refsect2"><a name="idm264418488112"></a><h3>continue</h3><p>
         Re-start a node that has been administratively stopped.
-      </p></div><div class="refsect2" title="addip <public_ip/mask> <iface>"><a name="id530318"></a><h3>addip <public_ip/mask> <iface></h3><p>
+      </p></div><div class="refsect2"><a name="idm264418487008"></a><h3>addip <public_ip/mask> <iface></h3><p>
 	This command is used to add a new public ip to a node during runtime.
 	This allows public addresses to be added to a cluster without having
 	to restart the ctdb daemons.
       </p><p>
 	Note that this only updates the runtime instance of ctdb. Any changes will be lost next time ctdb is restarted and the public addresses file is re-read.
  If you want this change to be permanent you must also update the public addresses file manually.
-      </p></div><div class="refsect2" title="delip <public_ip>"><a name="id530334"></a><h3>delip <public_ip></h3><p>
+      </p></div><div class="refsect2"><a name="idm264418485056"></a><h3>delip <public_ip></h3><p>
 	This command is used to remove a public ip from a node during runtime.
 	If this public ip is currently hosted by the node it being removed from, the ip will first be failed over to another node, if possible, before it is removed.
       </p><p>
 	Note that this only updates the runtime instance of ctdb. Any changes will be lost next time ctdb is restarted and the public addresses file is re-read.
  If you want this change to be permanent you must also update the public addresses file manually.
-      </p></div><div class="refsect2" title="moveip <public_ip> <node>"><a name="id530351"></a><h3>moveip <public_ip> <node></h3><p>
+      </p></div><div class="refsect2"><a name="idm264418483120"></a><h3>moveip <public_ip> <node></h3><p>
       This command can be used to manually fail a public ip address to a
       specific node.
       </p><p>
@@ -493,14 +507,14 @@ Reclock file:/gpfs/.ctdb/shared
       DeterministicIPs = 0
       </p><p>
       NoIPFailback = 1
-      </p></div><div class="refsect2" title="shutdown"><a name="id530373"></a><h3>shutdown</h3><p>
+      </p></div><div class="refsect2"><a name="idm264418480608"></a><h3>shutdown</h3><p>
         This command will shutdown a specific CTDB daemon.
-      </p></div><div class="refsect2" title="recover"><a name="id530382"></a><h3>recover</h3><p>
+      </p></div><div class="refsect2"><a name="idm264418479504"></a><h3>recover</h3><p>
         This command will trigger the recovery daemon to do a cluster
         recovery.
-      </p></div><div class="refsect2" title="ipreallocate"><a name="id530392"></a><h3>ipreallocate</h3><p>
+      </p></div><div class="refsect2"><a name="idm264418478368"></a><h3>ipreallocate</h3><p>
         This command will force the recovery master to perform a full ip reallocation process and redistribute all ip addresses. This is useful to "reset" the allocations back to its default state if they have been changed using the "moveip" command. While a "recover" will also perform this reallocation, a recovery is much more hevyweight since it will also rebuild all the databases.
-      </p></div><div class="refsect2" title="setlmasterrole <on|off>"><a name="id530404"></a><h3>setlmasterrole <on|off></h3><p>
+      </p></div><div class="refsect2"><a name="idm264418476928"></a><h3>setlmasterrole <on|off></h3><p>
 	This command is used ot enable/disable the LMASTER capability for a node at runtime. This capability determines whether or not a node can be used as an LMASTER for records in the database. A node that does not have the LMASTER capability will not show up in the vnnmap.
       </p><p>
 	Nodes will by default have this capability, but it can be stripped off nodes by the setting in the sysconfig file or by using this command.
@@ -508,21 +522,21 @@ Reclock file:/gpfs/.ctdb/shared
 	Once this setting has been enabled/disabled, you need to perform a recovery for it to take effect.
       </p><p>
 	See also "ctdb getcapabilities"
-      </p></div><div class="refsect2" title="setrecmasterrole <on|off>"><a name="id530428"></a><h3>setrecmasterrole <on|off></h3><p>
+      </p></div><div class="refsect2"><a name="idm264418474176"></a><h3>setrecmasterrole <on|off></h3><p>
 	This command is used ot enable/disable the RECMASTER capability for a node at runtime. This capability determines whether or not a node can be used as an RECMASTER for the cluster. A node that does not have the RECMASTER capability can not win a recmaster election. A node that already is the recmaster for the cluster when the capability is stripped off the node will remain the recmaster until the next cluster election.
       </p><p>
 	Nodes will by default have this capability, but it can be stripped off nodes by the setting in the sysconfig file or by using this command.
       </p><p>
 	See also "ctdb getcapabilities"
-      </p></div><div class="refsect2" title="killtcp <srcip:port> <dstip:port>"><a name="id530449"></a><h3>killtcp <srcip:port> <dstip:port></h3><p>
+      </p></div><div class="refsect2"><a name="idm264418471776"></a><h3>killtcp <srcip:port> <dstip:port></h3><p>
         This command will kill the specified TCP connection by issuing a
         TCP RST to the srcip:port endpoint. This is a command used by the 
 	ctdb eventscripts.
-      </p></div><div class="refsect2" title="gratiousarp <ip> <interface>"><a name="id530460"></a><h3>gratiousarp <ip> <interface></h3><p>
+      </p></div><div class="refsect2"><a name="idm264418470560"></a><h3>gratiousarp <ip> <interface></h3><p>
 	This command will send out a gratious arp for the specified interface
 	through the specified interface. This command is mainly used by the
 	ctdb eventscripts.
-      </p></div><div class="refsect2" title="reloadnodes"><a name="id530470"></a><h3>reloadnodes</h3><p>
+      </p></div><div class="refsect2"><a name="idm264418469280"></a><h3>reloadnodes</h3><p>
       This command is used when adding new nodes, or removing existing nodes from an existing cluster.
       </p><p>
       Procedure to add a node:
@@ -556,7 +570,7 @@ Reclock file:/gpfs/.ctdb/shared
       </p><p>
       5, Use 'ctdb status' on all nodes and verify that the deleted node no longer shows up in the list..
       </p><p>
-      </p></div><div class="refsect2" title="reloadips"><a name="id530540"></a><h3>reloadips</h3><p>
+      </p></div><div class="refsect2"><a name="idm264418461056"></a><h3>reloadips</h3><p>
       This command is used to reload the public addresses file and update the
 	ip configuration of the running daemon.
       </p><p>
@@ -583,7 +597,7 @@ Reclock file:/gpfs/.ctdb/shared
 	master to ensure that all addresses are added to all nodes as one
 	single operation, after which any required ip node rebalancing may
 	may take place.
-      </p></div><div class="refsect2" title="tickle <srcip:port> <dstip:port>"><a name="id530588"></a><h3>tickle <srcip:port> <dstip:port></h3><p>
+      </p></div><div class="refsect2"><a name="idm264418455472"></a><h3>tickle <srcip:port> <dstip:port></h3><p>
         This command will will send a TCP tickle to the source host for the
         specified TCP connection.
 	A TCP tickle is a TCP ACK packet with an invalid sequence and 
@@ -595,10 +609,10 @@ Reclock file:/gpfs/.ctdb/shared
         TCP connection has been disrupted and that the client will need
         to reestablish. This greatly speeds up the time it takes for a client
         to detect and reestablish after an IP failover in the ctdb cluster.
-      </p></div><div class="refsect2" title="gettickles <ip>"><a name="id530606"></a><h3>gettickles <ip></h3><p>
+      </p></div><div class="refsect2"><a name="idm264418453328"></a><h3>gettickles <ip></h3><p>
 	This command is used to show which TCP connections are registered with
 	CTDB to be "tickled" if there is a failover.
-      </p></div><div class="refsect2" title="repack [max_freelist]"><a name="id530617"></a><h3>repack [max_freelist]</h3><p>
+      </p></div><div class="refsect2"><a name="idm264418452160"></a><h3>repack [max_freelist]</h3><p>
 	Over time, when records are created and deleted in a TDB, the TDB list of free space will become fragmented. This can lead to a slowdown in accessing TDB records.
 	This command is used to defragment a TDB database and pruning the freelist.
       </p><p>
@@ -613,7 +627,7 @@ Reclock file:/gpfs/.ctdb/shared
 	Example: ctdb repack 1000
       </p><p>
 	 By default, this operation is issued from the 00.ctdb event script every 5 minutes.
-      </p></div><div class="refsect2" title="vacuum [max_records]"><a name="id530655"></a><h3>vacuum [max_records]</h3><p>
+      </p></div><div class="refsect2"><a name="idm264418447664"></a><h3>vacuum [max_records]</h3><p>
 	Over time CTDB databases will fill up with empty deleted records which will lead to a progressive slow down of CTDB database access.
 	This command is used to prune all databases and delete all empty records from the cluster.
       </p><p>
@@ -629,17 +643,17 @@ Reclock file:/gpfs/.ctdb/shared
 	Example: ctdb vacuum
       </p><p>
 	 By default, this operation is issued from the 00.ctdb event script every 5 minutes.
-      </p></div><div class="refsect2" title="backupdb <dbname> <file>"><a name="id530685"></a><h3>backupdb <dbname> <file></h3><p>
+      </p></div><div class="refsect2"><a name="idm264418444208"></a><h3>backupdb <dbname> <file></h3><p>
         This command can be used to copy the entire content of a database out to a file. This file can later be read back into ctdb using the restoredb command.
 This is mainly useful for backing up persistent databases such as secrets.tdb and similar.
-      </p></div><div class="refsect2" title="restoredb <file> [<dbname>]"><a name="id530696"></a><h3>restoredb <file> [<dbname>]</h3><p>
+      </p></div><div class="refsect2"><a name="idm264418442912"></a><h3>restoredb <file> [<dbname>]</h3><p>
         This command restores a persistent database that was previously backed up using backupdb.
 	By default the data will be restored back into the same database as
 	it was created from. By specifying dbname you can restore the data
 	into a different database.
-      </p></div><div class="refsect2" title="wipedb <dbname>"><a name="id530708"></a><h3>wipedb <dbname></h3><p>
+      </p></div><div class="refsect2"><a name="idm264418441520"></a><h3>wipedb <dbname></h3><p>
         This command can be used to remove all content of a database.
-      </p></div></div><div class="refsect2" title="getlog [<level>] [recoverd]"><a name="id530718"></a><h3>getlog [<level>] [recoverd]</h3><p>
+      </p></div></div><div class="refsect2"><a name="idm264418440272"></a><h3>getlog [<level>] [recoverd]</h3><p>
 	In addition to the normal logging to a log file,
 	CTDBD also keeps a in-memory ringbuffer containing the most recent
 	log entries for all log levels (except DEBUG).
@@ -657,25 +671,25 @@ This is mainly useful for backing up persistent databases such as secrets.tdb an
 	By default, logs are extracted from the main CTDB daemon.  If
 	the recoverd option is given then logs are extracted from the
 	recovery daemon.
-      </p></div><div class="refsect2" title="clearlog [recoverd]"><a name="id530744"></a><h3>clearlog [recoverd]</h3><p>
+      </p></div><div class="refsect2"><a name="idm264418437152"></a><h3>clearlog [recoverd]</h3><p>
 	This command clears the in-memory logging ringbuffer.
       </p><p>
 	By default, logs are cleared in the main CTDB daemon.  If the
 	recoverd option is given then logs are cleared in the recovery
 	daemon.
-      </p></div><div class="refsect2" title="setdbreadonly <dbname|hash>"><a name="id530758"></a><h3>setdbreadonly <dbname|hash></h3><p>
+      </p></div><div class="refsect2"><a name="idm264418435504"></a><h3>setdbreadonly <dbname|hash></h3><p>
         This command will enable the ReadOnly record support for a database.
 	This is an experimental feature to improve performance for contended
 	records primarily in locking.tdb and brlock.tdb.
 	When enabling this feature you must set it on all nodes in the cluster.
 	For now, this feature requires a special patch to samba in order to 
 	use it.
-      </p></div><div class="refsect1" title="Debugging Commands"><a name="id530770"></a><h2>Debugging Commands</h2><p>
+      </p></div><div class="refsect1"><a name="idm264418434112"></a><h2>Debugging Commands</h2><p>
       These commands are primarily used for CTDB development and testing and
       should not be used for normal administration.
-    </p><div class="refsect2" title="process-exists <pid>"><a name="id530779"></a><h3>process-exists <pid></h3><p>
+    </p><div class="refsect2"><a name="idm264418433072"></a><h3>process-exists <pid></h3><p>
         This command checks if a specific process exists on the CTDB host. This is mainly used by Samba to check if remote instances of samba are still running or not.
-      </p></div><div class="refsect2" title="getdbmap"><a name="id530790"></a><h3>getdbmap</h3><p>
+      </p></div><div class="refsect2"><a name="idm264418431856"></a><h3>getdbmap</h3><p>
         This command lists all clustered TDB databases that the CTDB daemon has attached to. Some databases are flagged as PERSISTENT, this means that the database stores data persistently and the data will remain across reboots. One example of such a database is secrets.tdb where information about how the cluster was joined to the domain is stored.
       </p><p>
 	If a PERSISTENT database is not in a healthy state the database is
@@ -715,7 +729,7 @@ dbid:0xb775fff6 name:secrets.tdb path:/var/ctdb/persistent/secrets.tdb.0 PERSIST
       </p><pre class="screen">
 :ID:Name:Path:Persistent:Unhealthy:
 :0x7bbbd26c:passdb.tdb:/var/ctdb/persistent/passdb.tdb.0:1:0:
-      </pre></div><div class="refsect2" title="getdbstatus <dbname>"><a name="id530857"></a><h3>getdbstatus <dbname></h3><p>
+      </pre></div><div class="refsect2"><a name="idm264418424016"></a><h3>getdbstatus <dbname></h3><p>
 	This command displays more details about a database.
       </p><p>
 	Example: ctdb getdbstatus test.tdb.0
@@ -737,35 +751,35 @@ name: registry.tdb
 path: /var/ctdb/persistent/registry.tdb.0
 PERSISTENT: yes
 HEALTH: NO-HEALTHY-NODES - ERROR - Backup of corrupted TDB in '/var/ctdb/persistent/registry.tdb.0.corrupted.20091208091949.0Z'
-      </pre></div><div class="refsect2" title="catdb <dbname>"><a name="id530896"></a><h3>catdb <dbname></h3><p>
+      </pre></div><div class="refsect2"><a name="idm264418419696"></a><h3>catdb <dbname></h3><p>
         This command will dump a clustered TDB database to the screen. This is a debugging command.
-      </p></div><div class="refsect2" title="cattdb <dbname>"><a name="id530906"></a><h3>cattdb <dbname></h3><p>
+      </p></div><div class="refsect2"><a name="idm264418418544"></a><h3>cattdb <dbname></h3><p>
         This command will dump the content of the local TDB database to the screen. This is a debugging command.
-      </p></div><div class="refsect2" title="dumpdbbackup <backup-file>"><a name="id530916"></a><h3>dumpdbbackup <backup-file></h3><p>
+      </p></div><div class="refsect2"><a name="idm264418417376"></a><h3>dumpdbbackup <backup-file></h3><p>
 	This command will dump the content of database backup to the screen
 	(similar to ctdb catdb). This is a debugging command.
-      </p></div><div class="refsect2" title="getmonmode"><a name="id530926"></a><h3>getmonmode</h3><p>
+      </p></div><div class="refsect2"><a name="idm264418416208"></a><h3>getmonmode</h3><p>
         This command returns the monutoring mode of a node. The monitoring mode is either ACTIVE or DISABLED. Normally a node will continuously monitor that all other nodes that are expected are in fact connected and that they respond to commands.
       </p><p>
         ACTIVE - This is the normal mode. The node is actively monitoring all other nodes, both that the transport is connected and also that the node responds to commands. If a node becomes unavailable, it will be marked as DISCONNECTED and a recovery is initiated to restore the cluster.
       </p><p>
         DISABLED - This node is not monitoring that other nodes are available. In this mode a node failure will not be detected and no recovery will be performed. This mode is useful when for debugging purposes one wants to attach GDB to a ctdb process but wants to prevent the rest of the cluster from marking this node as DISCONNECTED and do a recovery.
-      </p></div><div class="refsect2" title="setmonmode <0|1>"><a name="id530949"></a><h3>setmonmode <0|1></h3><p>
+      </p></div><div class="refsect2"><a name="idm264418413440"></a><h3>setmonmode <0|1></h3><p>
         This command can be used to explicitly disable/enable monitoring mode on a node. The main purpose is if one wants to attach GDB to a running ctdb daemon but wants to prevent the other nodes from marking it as DISCONNECTED and issuing a recovery. To do this, set monitoring mode to 0 on all nodes before attaching with GDB. Remember to set monitoring mode back to 1 afterwards.
-      </p></div><div class="refsect2" title="attach <dbname> [persistent]"><a name="id530961"></a><h3>attach <dbname> [persistent]</h3><p>
+      </p></div><div class="refsect2"><a name="idm264418412000"></a><h3>attach <dbname> [persistent]</h3><p>
         This is a debugging command. This command will make the CTDB daemon create a new CTDB database and attach to it.
-      </p></div><div class="refsect2" title="dumpmemory"><a name="id530972"></a><h3>dumpmemory</h3><p>
+      </p></div><div class="refsect2"><a name="idm264418410752"></a><h3>dumpmemory</h3><p>
         This is a debugging command. This command will make the ctdb
         daemon to write a fill memory allocation map to standard output.
-      </p></div><div class="refsect2" title="rddumpmemory"><a name="id530982"></a><h3>rddumpmemory</h3><p>
+      </p></div><div class="refsect2"><a name="idm264418409568"></a><h3>rddumpmemory</h3><p>
         This is a debugging command. This command will dump the talloc memory
 	allocation tree for the recovery daemon to standard output.
-      </p></div><div class="refsect2" title="thaw"><a name="id530992"></a><h3>thaw</h3><p>
+      </p></div><div class="refsect2"><a name="idm264418408384"></a><h3>thaw</h3><p>
         Thaw a previously frozen node.
-      </p></div><div class="refsect2" title="eventscript <arguments>"><a name="id531001"></a><h3>eventscript <arguments></h3><p>
+      </p></div><div class="refsect2"><a name="idm264418407360"></a><h3>eventscript <arguments></h3><p>
         This is a debugging command. This command can be used to manually
 	invoke and run the eventscritps with arbitrary arguments.
-      </p></div><div class="refsect2" title="ban <bantime|0>"><a name="id531012"></a><h3>ban <bantime|0></h3><p>
+      </p></div><div class="refsect2"><a name="idm264418406176"></a><h3>ban <bantime|0></h3><p>
         Administratively ban a node for bantime seconds. A bantime of 0 means that the node should be permanently banned. 
       </p><p>
         A banned node does not participate in the cluster and does not host any records for the clustered TDB. Its ip address has been taken over by another node and no services are hosted.
@@ -774,11 +788,11 @@ HEALTH: NO-HEALTHY-NODES - ERROR - Backup of corrupted TDB in '/var/ctdb/persist
         cluster recoveries.
       </p><p>
 	This is primarily a testing command. Note that the recovery daemon controls the overall ban state and it may automatically unban nodes at will. Meaning that a node that has been banned by the administrator can and ofter are unbanned before the admin specifid timeout triggers. If wanting to "drop" a node out from the cluster for mainentance or other reasons, use the "stop" / "continue" commands instad of "ban" / "unban". 
-      </p></div><div class="refsect2" title="unban"><a name="id531038"></a><h3>unban</h3><p>
+      </p></div><div class="refsect2"><a name="idm264418403072"></a><h3>unban</h3><p>
         This command is used to unban a node that has either been 
         administratively banned using the ban command or has been automatically
         banned by the recovery daemon.
-      </p></div><div class="refsect2" title="check_srvids <srvid> ..."><a name="id531049"></a><h3>check_srvids <srvid> ...</h3><p>
+      </p></div><div class="refsect2"><a name="idm264418401840"></a><h3>check_srvids <srvid> ...</h3><p>
 	This command checks whether a set of srvid message ports are registered on the
 	node or not. The command takes a list of values to check.
       </p><p>
@@ -790,10 +804,10 @@ Server id 0:1 does not exist
 Server id 0:2 does not exist
 Server id 0:3 does not exist
 Server id 0:14765 exists
-      </pre></div></div><div class="refsect1" title="SEE ALSO"><a name="id531074"></a><h2>SEE ALSO</h2><p>
+      </pre></div></div><div class="refsect1"><a name="idm264418399008"></a><h2>SEE ALSO</h2><p>
       ctdbd(1), onnode(1)
       <a class="ulink" href="http://ctdb.samba.org/" target="_top">http://ctdb.samba.org/</a>
-    </p></div><div class="refsect1" title="COPYRIGHT/LICENSE"><a name="id531087"></a><h2>COPYRIGHT/LICENSE</h2><div class="literallayout"><p><br>
+    </p></div><div class="refsect1"><a name="idm264418397488"></a><h2>COPYRIGHT/LICENSE</h2><div class="literallayout"><p><br>
 Copyright (C) Andrew Tridgell 2007<br>
 Copyright (C) Ronnie sahlberg 2007<br>
 <br>
diff --git a/doc/ctdb.1.xml b/doc/ctdb.1.xml
index 83d0ac0..ce83a3e 100644
--- a/doc/ctdb.1.xml
+++ b/doc/ctdb.1.xml
@@ -382,6 +382,28 @@ response from 3 time=0.000114 sec  (2 clients)
       </screen>
     </refsect2>
 
+    <refsect2><title>runstate [setup|first_recovery|startup|running]</title>
+      <para>
+        Print the runstate of the specified node.  Runstates are used
+        to serialise important state transitions in CTDB, particularly
+        during startup.
+      </para>
+      <para>
+        If one or more optional runstate arguments are specified then
+        the node must be in one of these runstates for the command to
+        succeed.
+      </para>
+      <para>
+	Example: ctdb runstate
+      </para>
+      <para>
+	Example output:
+      </para>
+      <screen format="linespecific">
+RUNNING
+      </screen>
+    </refsect2>
+
     <refsect2><title>ifaces</title>
       <para>
 	This command will display the list of network interfaces, which could
diff --git a/doc/ctdbd.1 b/doc/ctdbd.1
index d805d95..0964f01 100644
--- a/doc/ctdbd.1
+++ b/doc/ctdbd.1
@@ -1,13 +1,22 @@
 '\" t
 .\"     Title: ctdbd
 .\"    Author: [FIXME: author] [see http://docbook.sf.net/el/author]
-.\" Generator: DocBook XSL Stylesheets v1.75.2 <http://docbook.sf.net/>
-.\"      Date: 01/09/2013
+.\" Generator: DocBook XSL Stylesheets v1.78.1 <http://docbook.sf.net/>
+.\"      Date: 05/30/2013
 .\"    Manual: CTDB - clustered TDB database
 .\"    Source: ctdb
 .\"  Language: English
 .\"
-.TH "CTDBD" "1" "01/09/2013" "ctdb" "CTDB \- clustered TDB database"
+.TH "CTDBD" "1" "05/30/2013" "ctdb" "CTDB \- clustered TDB database"
+.\" -----------------------------------------------------------------
+.\" * Define some portability stuff
+.\" -----------------------------------------------------------------
+.\" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+.\" http://bugs.debian.org/507673
+.\" http://lists.gnu.org/archive/html/groff/2009-02/msg00013.html
+.\" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+.ie \n(.g .ds Aq \(aq
+.el       .ds Aq '
 .\" -----------------------------------------------------------------
 .\" * set default formatting
 .\" -----------------------------------------------------------------
@@ -118,7 +127,7 @@ This is a ctdbd debugging option\&. this option is only used when debugging ctdb
 .sp
 Normally ctdb will change its scheduler to run as a real\-time process\&. This is the default mode for a normal ctdbd operation to gurarantee that ctdbd always gets the cpu cycles that it needs\&.
 .sp
-This option is used to tell ctdbd to NOT run as a real\-time process and instead run ctdbd as a normal userspace process\&. This is useful for debugging and when you want to run ctdbd under valgrind or gdb\&. (You don\'t want to attach valgrind or gdb to a real\-time process\&.)
+This option is used to tell ctdbd to NOT run as a real\-time process and instead run ctdbd as a normal userspace process\&. This is useful for debugging and when you want to run ctdbd under valgrind or gdb\&. (You don\*(Aqt want to attach valgrind or gdb to a real\-time process\&.)
 .RE
 .PP
 \-\-notification\-script=<filename>
@@ -141,7 +150,7 @@ This is usually the file /etc/ctdb/public_addresses
 .RS 4
 This option tells ctdb which interface to attach public\-addresses to and also where to attach the single\-public\-ip when used\&.
 .sp
-This is only required when using public ip addresses and only when you don\'t specify the interface explicitly in /etc/ctdb/public_addresses or when you are using \-\-single\-public\-ip\&.
+This is only required when using public ip addresses and only when you don\*(Aqt specify the interface explicitly in /etc/ctdb/public_addresses or when you are using \-\-single\-public\-ip\&.
 .sp
 If you omit this argument when using public addresses or single public ip, ctdb will not be able to send out Gratious ARPs correctly or be able to kill tcp connections correctly which will lead to application failures\&.
 .RE
@@ -251,7 +260,7 @@ A public address on the other hand is not attached to an interface\&. This addre
 .PP
 The ctdb cluster will assign/reassign these public addresses across the available healthy nodes in the cluster\&. When one node fails, its public address will be migrated to and taken over by a different node in the cluster to ensure that all public addresses are always available to clients as long as there are still nodes available capable of hosting this address\&.
 .PP
-These addresses are not physically attached to a specific node\&. The \'ctdb ip\' command can be used to view the current assignment of public addresses and which physical node is currently serving it\&.
+These addresses are not physically attached to a specific node\&. The \*(Aqctdb ip\*(Aq command can be used to view the current assignment of public addresses and which physical node is currently serving it\&.
 .PP
 On each node this file contains a list of the public addresses that this node is capable of hosting\&. The list also contain the netmask and the interface where this address should be attached for the case where you may want to serve data out through multiple different interfaces\&.
 
@@ -307,7 +316,7 @@ In this example nodes 0 and 1 host two public addresses on the 10\&.1\&.1\&.x ne
 Ip address 10\&.1\&.1\&.1 can be hosted by either of nodes 0 or 1 and will be available to clients as long as at least one of these two nodes are available\&. If both nodes 0 and node 1 become unavailable 10\&.1\&.1\&.1 also becomes unavailable\&. 10\&.1\&.1\&.1 can not be failed over to node 2 or node 3 since these nodes do not have this ip address listed in their public addresses file\&.
 .SH "NODE STATUS"
 .PP
-The current status of each node in the cluster can be viewed by the \'ctdb status\' command\&.
+The current status of each node in the cluster can be viewed by the \*(Aqctdb status\*(Aq command\&.
 .PP
 There are five possible states for a node\&.
 .PP
@@ -338,7 +347,7 @@ Default: 1000
 .PP
 Some databases have seqnum tracking enabled, so that samba will be able to detect asynchronously when there has been updates to the database\&. Everytime a database is updated its sequence number is increased\&.
 .PP
-This tunable is used to specify in \'ms\' how frequently ctdb will send out updates to remote nodes to inform them that the sequence number is increased\&.
+This tunable is used to specify in \*(Aqms\*(Aq how frequently ctdb will send out updates to remote nodes to inform them that the sequence number is increased\&.
 .SS "ControlTimeout"
 .PP
 Default: 60
@@ -415,7 +424,7 @@ During recoveries, if a node has not caused recovery failures during the last gr
 .PP
 Default: 300
 .PP
-If a node becomes banned causing repetitive recovery failures\&. The node will eventually become banned from the cluster\&. This controls how long the culprit node will be banned from the cluster before it is allowed to try to join the cluster again\&. Don\'t set to small\&. A node gets banned for a reason and it is usually due to real problems with the node\&.
+If a node becomes banned causing repetitive recovery failures\&. The node will eventually become banned from the cluster\&. This controls how long the culprit node will be banned from the cluster before it is allowed to try to join the cluster again\&. Don\*(Aqt set to small\&. A node gets banned for a reason and it is usually due to real problems with the node\&.
 .SS "DatabaseHashSize"
 .PP
 Default: 100001
@@ -435,7 +444,7 @@ Once a recovery has completed, no additional recoveries are permitted until this
 .PP
 Default: 1
 .PP
-When set to 0, this disables BANNING completely in the cluster and thus nodes can not get banned, even it they break\&. Don\'t set to 0 unless you know what you are doing\&.
+When set to 0, this disables BANNING completely in the cluster and thus nodes can not get banned, even it they break\&. Don\*(Aqt set to 0 unless you know what you are doing\&.
 .SS "DeterministicIPs"
 .PP
 Default: 0
@@ -461,24 +470,24 @@ When set to 1, ctdb will not perform failback of IP addresses when a node become
 .PP
 Use with caution! Normally when a node becomes available to the cluster ctdb will try to reassign public IP addresses onto the new node as a way to distribute the workload evenly across the clusternode\&. Ctdb tries to make sure that all running nodes have approximately the same number of public addresses it hosts\&.
 .PP
-When you enable this tunable, CTDB will no longer attempt to rebalance the cluster by failing IP addresses back to the new nodes\&. An unbalanced cluster will therefore remain unbalanced until there is manual intervention from the administrator\&. When this parameter is set, you can manually fail public IP addresses over to the new node(s) using the \'ctdb moveip\' command\&.
+When you enable this tunable, CTDB will no longer attempt to rebalance the cluster by failing IP addresses back to the new nodes\&. An unbalanced cluster will therefore remain unbalanced until there is manual intervention from the administrator\&. When this parameter is set, you can manually fail public IP addresses over to the new node(s) using the \*(Aqctdb moveip\*(Aq command\&.
 .SS "DisableIPFailover"
 .PP
 Default: 0
 .PP
 When enabled, ctdb will not perform failover or failback\&. Even if a node fails while holding public IPs, ctdb will not recover the IPs or assign them to another node\&.
 .PP
-When you enable this tunable, CTDB will no longer attempt to recover the cluster by failing IP addresses over to other nodes\&. This leads to a service outage until the administrator has manually performed failover to replacement nodes using the \'ctdb moveip\' command\&.
+When you enable this tunable, CTDB will no longer attempt to recover the cluster by failing IP addresses over to other nodes\&. This leads to a service outage until the administrator has manually performed failover to replacement nodes using the \*(Aqctdb moveip\*(Aq command\&.
 .SS "NoIPTakeover"
 .PP
 Default: 0
 .PP
 When set to 1, ctdb will allow ip addresses to be failed over onto this node\&. Any ip addresses that the node currently hosts will remain on the node but no new ip addresses can be failed over onto the node\&.
-.SS "NoIPTakeoverOnDisabled"
+.SS "NoIPHostOnAllDisabled"
 .PP
 Default: 0
 .PP
-If no nodes are healthy then by default ctdb will happily host public IPs on disabled (unhealthy or administratively disabled) nodes\&. This can cause problems, for example if the underlying cluster filesystem is not mounted\&. When set to 1 this behaviour is switched off and disabled nodes will not be able to takeover IPs\&.
+If no nodes are healthy then by default ctdb will happily host public IPs on disabled (unhealthy or administratively disabled) nodes\&. This can cause problems, for example if the underlying cluster filesystem is not mounted\&. When set to 1 on a node and that node is disabled it, any IPs hosted by this node will be released and the node will not takeover any IPs until it is no longer disabled\&.
 .SS "DBRecordCountWarn"
 .PP
 Default: 100000
@@ -513,7 +522,7 @@ If the recovery daemon has failed to ping the main dameon for this many consecut
 .PP
 Default: 0
 .PP
-When set to non\-zero, this will make the main daemon log any operation that took longer than this value, in \'ms\', to complete\&. These include "how long time a lockwait child process needed", "how long time to write to a persistent database" but also "how long did it take to get a response to a CALL from a remote node"\&.
+When set to non\-zero, this will make the main daemon log any operation that took longer than this value, in \*(Aqms\*(Aq, to complete\&. These include "how long time a lockwait child process needed", "how long time to write to a persistent database" but also "how long did it take to get a response to a CALL from a remote node"\&.
 .SS "RecLockLatencyMs"
 .PP
 Default: 1000
@@ -540,9 +549,9 @@ This timeout controls how long we will defer the request from the client before
 .PP
 Default: 50
 .PP
-If the database is set to \'STICKY\' mode, using the \'ctdb setdbsticky\' command, any record that is seen as very hot and migrating so fast that hopcount surpasses 50 is set to become a STICKY record for StickyDuration seconds\&. This means that after each migration the record will be kept on the node and prevented from being migrated off the node\&.
+If the database is set to \*(AqSTICKY\*(Aq mode, using the \*(Aqctdb setdbsticky\*(Aq command, any record that is seen as very hot and migrating so fast that hopcount surpasses 50 is set to become a STICKY record for StickyDuration seconds\&. This means that after each migration the record will be kept on the node and prevented from being migrated off the node\&.
 .PP
-This setting allows to try to identify such records and stop them from migrating across the cluster so fast\&. This will improve performance for certain workloads, such as locking\&.tdb if many clients are opening/closing the same file concurrently\&.
+This setting allows one to try to identify such records and stop them from migrating across the cluster so fast\&. This will improve performance for certain workloads, such as locking\&.tdb if many clients are opening/closing the same file concurrently\&.
 .SS "StickyDuration"
 .PP
 Default: 600
@@ -591,7 +600,7 @@ Default: 60
 Number of seconds to determine if ctdb is in deadlock with samba\&.
 .PP
 When ctdb daemon is blocked waiting for a lock on a database which is blocked by some other process, ctdb logs a warning every 10 seconds\&. Most often this is caused by samba locking databases and waiting on ctdb and result in a deadlock\&. If the lock is not obtained by ctdb before deadlock timeout expires, ctdb will detect it as a deadlock and terminate the blocking samba process\&. Setting this value to 0 disables deadlock detection\&.
-.SS "Samba3AvoidDeadlock"
+.SS "Samba3AvoidDeadlocks"
 .PP
 Default: 0
 .PP
@@ -788,7 +797,7 @@ If you want to remove NATGW completely from a node, use these steps:
 .RS 4
 .\}
 .nf
-1, Run \'CTDB_BASE=/etc/ctdb /etc/ctdb/events\&.d/11\&.natgw removenatgw\'
+1, Run \*(AqCTDB_BASE=/etc/ctdb /etc/ctdb/events\&.d/11\&.natgw removenatgw\*(Aq
 2, Then remove the configuration from /etc/sysconfig/ctdb
     
 .fi
@@ -802,9 +811,9 @@ If you want to change the NATGW configuration on a node :
 .RS 4
 .\}
 .nf
-1, Run \'CTDB_BASE=/etc/ctdb /etc/ctdb/events\&.d/11\&.natgw removenatgw\'
+1, Run \*(AqCTDB_BASE=/etc/ctdb /etc/ctdb/events\&.d/11\&.natgw removenatgw\*(Aq
 2, Then change the configuration in /etc/sysconfig/ctdb
-3, Run \'CTDB_BASE=/etc/ctdb /etc/ctdb/events\&.d/11\&.natgw updatenatgw\'
+3, Run \*(AqCTDB_BASE=/etc/ctdb /etc/ctdb/events\&.d/11\&.natgw updatenatgw\*(Aq
     
 .fi
 .if n \{\
@@ -812,7 +821,7 @@ If you want to change the NATGW configuration on a node :
 .\}
 .SH "POLICY ROUTING"
 .PP
-A node running CTDB may be a component of a complex network topology\&. In particular, public addresses may be spread across several different networks (or VLANs) and it may not be possible to route packets from these public addresses via the system\'s default route\&. Therefore, CTDB has support for policy routing via the 13\&.per_ip_routing eventscript\&. This allows routing to be specified for packets sourced from each public address\&. The routes are added and removed as CTDB moves public addresses between nodes\&.
+A node running CTDB may be a component of a complex network topology\&. In particular, public addresses may be spread across several different networks (or VLANs) and it may not be possible to route packets from these public addresses via the system\*(Aqs default route\&. Therefore, CTDB has support for policy routing via the 13\&.per_ip_routing eventscript\&. This allows routing to be specified for packets sourced from each public address\&. The routes are added and removed as CTDB moves public addresses between nodes\&.
 .SS "Configuration variables"
 .PP
 There are 4 configuration variables related to policy routing:
@@ -859,7 +868,7 @@ The format of each line is:
 .RE
 .\}
 .PP
-Leading whitespace is ignored and arbitrary whitespace may be used as a separator\&. Lines that have a "public address" item that doesn\'t match an actual public address are ignored\&. This means that comment lines can be added using a leading character such as \'#\', since this will never match an IP address\&.
+Leading whitespace is ignored and arbitrary whitespace may be used as a separator\&. Lines that have a "public address" item that doesn\*(Aqt match an actual public address are ignored\&. This means that comment lines can be added using a leading character such as \*(Aq#\*(Aq, since this will never match an IP address\&.
 .PP
 A line without a gateway indicates a link local route\&.
 .PP
@@ -889,7 +898,6 @@ If the corresponding public_addresses line is:
 .RE
 .\}
 .PP
-
 \fICTDB_PER_IP_ROUTING_RULE_PREF\fR
 is 100, and CTDB adds the address to eth2 then the following routing information is added:
 .sp
@@ -925,7 +933,6 @@ command will show (something like \- depending on other public addresses and oth
 .RE
 .\}
 .PP
-
 \fBip route show table ctdb\&.192\&.168\&.1\&.99\fR
 will show:
 .sp
diff --git a/doc/ctdbd.1.html b/doc/ctdbd.1.html
index fa94d5f..afb8201 100644
--- a/doc/ctdbd.1.html
+++ b/doc/ctdbd.1.html
@@ -1,4 +1,4 @@
-<html><head><meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1"><title>ctdbd</title><meta name="generator" content="DocBook XSL Stylesheets V1.75.2"></head><body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF"><div class="refentry" title="ctdbd"><a name="ctdbd.1"></a><div class="titlepage"></div><div class="refnamediv"><h2>Name</h2><p>ctdbd — The CTDB cluster daemon</p></div><div class="refsynopsisdiv" title="Synopsis"><h2>Synopsis</h2><div class="cmdsynopsis"><p><code class="command">ctdbd</code> </p></div><div class="cmdsynopsis"><p><code class="command">ctdbd</code>  [-? --help] [-d --debug=<INTEGER>] {--dbdir=<directory>} {--dbdir-persistent=<directory>} [--event-script-dir=<directory>] [-i --interactive] [--listen=<address>] [--logfile=<filename>] [--lvs] {--nlist=<filename>} [--no-lmaster] [--no-recmaster] [--nosetsched] {--notification-script=<filename>} [--public-addresses=<filename>] [--public-interface=<interface>] {--reclock=<filename>} [--single-public-ip=<address>] [--socket=<filename>] [--start-as-disabled] [--start-as-stopped] [--syslog] [--log-ringbuf-size=<num-entries>] [--torture] [--transport=<STRING>] [--usage]</p></div></div><div class="refsect1" title="DESCRIPTION"><a name="id517337"></a><h2>DESCRIPTION</h2><p>
+<html><head><meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1"><title>ctdbd</title><meta name="generator" content="DocBook XSL Stylesheets V1.78.1"></head><body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF"><div class="refentry"><a name="ctdbd.1"></a><div class="titlepage"></div><div class="refnamediv"><h2>Name</h2><p>ctdbd — The CTDB cluster daemon</p></div><div class="refsynopsisdiv"><h2>Synopsis</h2><div class="cmdsynopsis"><p><code class="command">ctdbd</code> </p></div><div class="cmdsynopsis"><p><code class="command">ctdbd</code>  [-? --help] [-d --debug=<INTEGER>] {--dbdir=<directory>} {--dbdir-persistent=<directory>} [--event-script-dir=<directory>] [-i --interactive] [--listen=<address>] [--logfile=<filename>] [--lvs] {--nlist=<filename>} [--no-lmaster] [--no-recmaster] [--nosetsched] {--notification-script=<filename>} [--public-addresses=<filename>] [--public-interface=<interface>] {--reclock=<filename>} [--single-public-ip=<address>] [--socket=<filename>] [--start-as-disabled] [--start-as-stopped] [--syslog] [--log-ringbuf-size=<num-entries>] [--torture] [--transport=<STRING>] [--usage]</p></div></div><div class="refsect1"><a name="idm264408585072"></a><h2>DESCRIPTION</h2><p>
       ctdbd is the main ctdb daemon.
     </p><p>
       ctdbd provides a clustered version of the TDB database with automatic rebuild/recovery of the databases upon nodefailures.
@@ -8,7 +8,7 @@
       ctdbd provides monitoring of all nodes in the cluster and automatically reconfigures the cluster and recovers upon node failures.
     </p><p>
       ctdbd is the main component in clustered Samba that provides a high-availability load-sharing CIFS server cluster.
-    </p></div><div class="refsect1" title="OPTIONS"><a name="id517364"></a><h2>OPTIONS</h2><div class="variablelist"><dl><dt><span class="term">-? --help</span></dt><dd><p>
+    </p></div><div class="refsect1"><a name="idm264408581808"></a><h2>OPTIONS</h2><div class="variablelist"><dl class="variablelist"><dt><span class="term">-? --help</span></dt><dd><p>
             Print some help text to the screen.
           </p></dd><dt><span class="term">-d --debug=<DEBUGLEVEL></span></dt><dd><p>
             This option sets the debuglevel on the ctdbd daemon which controls what will be written to the logfile. The default is 0 which will only log important events and errors. A larger number will provide additional logging.
@@ -154,10 +154,10 @@
 	    implemented in the future.
           </p></dd><dt><span class="term">--usage</span></dt><dd><p>
             Print useage information to the screen.
-          </p></dd></dl></div></div><div class="refsect1" title="Private vs Public addresses"><a name="id517843"></a><h2>Private vs Public addresses</h2><p>
+          </p></dd></dl></div></div><div class="refsect1"><a name="idm264403537648"></a><h2>Private vs Public addresses</h2><p>
       When used for ip takeover in a HA environment, each node in a ctdb 
       cluster has multiple ip addresses assigned to it. One private and one or more public.
-    </p><div class="refsect2" title="Private address"><a name="id517852"></a><h3>Private address</h3><p>
+    </p><div class="refsect2"><a name="idm264403536560"></a><h3>Private address</h3><p>
         This is the physical ip address of the node which is configured in 
         linux and attached to a physical interface. This address uniquely
         identifies a physical node in the cluster and is the ip addresses
@@ -187,7 +187,7 @@
         10.1.1.2
         10.1.1.3
         10.1.1.4
-      </pre></div><div class="refsect2" title="Public address"><a name="id517889"></a><h3>Public address</h3><p>
+      </pre></div><div class="refsect2"><a name="idm264403532336"></a><h3>Public address</h3><p>
         A public address on the other hand is not attached to an interface.
         This address is managed by ctdbd itself and is attached/detached to
         a physical node at runtime.
@@ -248,7 +248,7 @@
 	unavailable. 10.1.1.1 can not be failed over to node 2 or node 3 since
 	these nodes do not have this ip address listed in their public
 	addresses file.
-	</p></div></div><div class="refsect1" title="Node status"><a name="id517950"></a><h2>Node status</h2><p>
+	</p></div></div><div class="refsect1"><a name="idm264403525136"></a><h2>Node status</h2><p>
       The current status of each node in the cluster can be viewed by the 
       'ctdb status' command.
     </p><p>
@@ -285,9 +285,9 @@
       RECMASTER or NATGW.
       This node does not perticipate in the CTDB cluster but can still be
       communicated with. I.e. ctdb commands can be sent to it.
-    </p></div><div class="refsect1" title="PUBLIC TUNABLES"><a name="id518000"></a><h2>PUBLIC TUNABLES</h2><p>
+    </p></div><div class="refsect1"><a name="idm264403519424"></a><h2>PUBLIC TUNABLES</h2><p>
     These are the public tuneables that can be used to control how ctdb behaves.
-    </p><div class="refsect2" title="MaxRedirectCount"><a name="id518009"></a><h3>MaxRedirectCount</h3><p>Default: 3</p><p>
+    </p><div class="refsect2"><a name="idm264403518304"></a><h3>MaxRedirectCount</h3><p>Default: 3</p><p>
     If we are not the DMASTER and need to fetch a record across the network
     we first send the request to the LMASTER after which the record
     is passed onto the current DMASTER. If the DMASTER changes before
@@ -301,7 +301,7 @@
     </p><p>
     When chasing a record, this is how many hops we will chase the record
     for before going back to the LMASTER to ask for new guidance.
-    </p></div><div class="refsect2" title="SeqnumInterval"><a name="id518032"></a><h3>SeqnumInterval</h3><p>Default: 1000</p><p>
+    </p></div><div class="refsect2"><a name="idm264403515712"></a><h3>SeqnumInterval</h3><p>Default: 1000</p><p>
     Some databases have seqnum tracking enabled, so that samba will be able
     to detect asynchronously when there has been updates to the database.
     Everytime a database is updated its sequence number is increased.
@@ -309,17 +309,17 @@
     This tunable is used to specify in 'ms' how frequently ctdb will
     send out updates to remote nodes to inform them that the sequence
     number is increased.
-    </p></div><div class="refsect2" title="ControlTimeout"><a name="id518051"></a><h3>ControlTimeout</h3><p>Default: 60</p><p>
+    </p></div><div class="refsect2"><a name="idm264403513488"></a><h3>ControlTimeout</h3><p>Default: 60</p><p>
     This is the default
     setting for timeout for when sending a control message to either the
     local or a remote ctdb daemon.
-    </p></div><div class="refsect2" title="TraverseTimeout"><a name="id518064"></a><h3>TraverseTimeout</h3><p>Default: 20</p><p>
+    </p></div><div class="refsect2"><a name="idm264403511920"></a><h3>TraverseTimeout</h3><p>Default: 20</p><p>
     This setting controls how long we allow a traverse process to run.
     After this timeout triggers, the main ctdb daemon will abort the
     traverse if it has not yet finished.
-    </p></div><div class="refsect2" title="KeepaliveInterval"><a name="id518078"></a><h3>KeepaliveInterval</h3><p>Default: 5</p><p>
+    </p></div><div class="refsect2"><a name="idm264403510304"></a><h3>KeepaliveInterval</h3><p>Default: 5</p><p>
     How often in seconds should the nodes send keepalives to eachother.
-    </p></div><div class="refsect2" title="KeepaliveLimit"><a name="id518091"></a><h3>KeepaliveLimit</h3><p>Default: 5</p><p>
+    </p></div><div class="refsect2"><a name="idm264403508800"></a><h3>KeepaliveLimit</h3><p>Default: 5</p><p>
     After how many keepalive intervals without any traffic should a node
     wait until marking the peer as DISCONNECTED.
     </p><p>
@@ -328,60 +328,60 @@
     require a recovery. This limitshould not be set too high since we want
     a hung node to be detectec, and expunged from the cluster well before
     common CIFS timeouts (45-90 seconds) kick in.
-    </p></div><div class="refsect2" title="RecoverTimeout"><a name="id518111"></a><h3>RecoverTimeout</h3><p>Default: 20</p><p>
+    </p></div><div class="refsect2"><a name="idm264403506496"></a><h3>RecoverTimeout</h3><p>Default: 20</p><p>
     This is the default setting for timeouts for controls when sent from the
     recovery daemon. We allow longer control timeouts from the recovery daemon
     than from normal use since the recovery dameon often use controls that 
     can take a lot longer than normal controls.
-    </p></div><div class="refsect2" title="RecoverInterval"><a name="id518126"></a><h3>RecoverInterval</h3><p>Default: 1</p><p>
+    </p></div><div class="refsect2"><a name="idm264403504784"></a><h3>RecoverInterval</h3><p>Default: 1</p><p>
     How frequently in seconds should the recovery daemon perform the
     consistency checks that determine if we need to perform a recovery or not.
-    </p></div><div class="refsect2" title="ElectionTimeout"><a name="id518140"></a><h3>ElectionTimeout</h3><p>Default: 3</p><p>
+    </p></div><div class="refsect2"><a name="idm264403503200"></a><h3>ElectionTimeout</h3><p>Default: 3</p><p>
     When electing a new recovery master, this is how many seconds we allow
     the election to take before we either deem the election finished
     or we fail the election and start a new one.
-    </p></div><div class="refsect2" title="TakeoverTimeout"><a name="id518154"></a><h3>TakeoverTimeout</h3><p>Default: 9</p><p>
+    </p></div><div class="refsect2"><a name="idm264403501584"></a><h3>TakeoverTimeout</h3><p>Default: 9</p><p>
     This is how many seconds we allow controls to take for IP failover events.
-    </p></div><div class="refsect2" title="MonitorInterval"><a name="id518167"></a><h3>MonitorInterval</h3><p>Default: 15</p><p>
+    </p></div><div class="refsect2"><a name="idm264403500080"></a><h3>MonitorInterval</h3><p>Default: 15</p><p>
     How often should ctdb run the event scripts to check for a nodes health.
-    </p></div><div class="refsect2" title="TickleUpdateInterval"><a name="id518180"></a><h3>TickleUpdateInterval</h3><p>Default: 20</p><p>
+    </p></div><div class="refsect2"><a name="idm264403498576"></a><h3>TickleUpdateInterval</h3><p>Default: 20</p><p>
     How often will ctdb record and store the "tickle" information used to
     kickstart stalled tcp connections after a recovery.
-    </p></div><div class="refsect2" title="EventScriptTimeout"><a name="id518193"></a><h3>EventScriptTimeout</h3><p>Default: 20</p><p>
+    </p></div><div class="refsect2"><a name="idm264403497024"></a><h3>EventScriptTimeout</h3><p>Default: 20</p><p>
     How long should ctdb let an event script run before aborting it and
     marking the node unhealthy.
-    </p></div><div class="refsect2" title="EventScriptTimeoutCount"><a name="id518206"></a><h3>EventScriptTimeoutCount</h3><p>Default: 1</p><p>
+    </p></div><div class="refsect2"><a name="idm264403495488"></a><h3>EventScriptTimeoutCount</h3><p>Default: 1</p><p>
     How many events in a row needs to timeout before we flag the node UNHEALTHY.
     This setting is useful if your scripts can not be written so that they
     do not hang for benign reasons.
-    </p></div><div class="refsect2" title="EventScriptUnhealthyOnTimeout"><a name="id518220"></a><h3>EventScriptUnhealthyOnTimeout</h3><p>Default: 0</p><p>
+    </p></div><div class="refsect2"><a name="idm264403493872"></a><h3>EventScriptUnhealthyOnTimeout</h3><p>Default: 0</p><p>
     This setting can be be used to make ctdb never become UNHEALTHY if your
     eventscripts keep hanging/timing out.
-    </p></div><div class="refsect2" title="RecoveryGracePeriod"><a name="id518234"></a><h3>RecoveryGracePeriod</h3><p>Default: 120</p><p>
+    </p></div><div class="refsect2"><a name="idm264403492320"></a><h3>RecoveryGracePeriod</h3><p>Default: 120</p><p>
     During recoveries, if a node has not caused recovery failures during the
     last grace period, any records of transgressions that the node has caused
     recovery failures will be forgiven. This resets the ban-counter back to 
     zero for that node.
-    </p></div><div class="refsect2" title="RecoveryBanPeriod"><a name="id518249"></a><h3>RecoveryBanPeriod</h3><p>Default: 300</p><p>
+    </p></div><div class="refsect2"><a name="idm264403490640"></a><h3>RecoveryBanPeriod</h3><p>Default: 300</p><p>
     If a node becomes banned causing repetitive recovery failures. The node will
     eventually become banned from the cluster.
     This controls how long the culprit node will be banned from the cluster
     before it is allowed to try to join the cluster again.
     Don't set to small. A node gets banned for a reason and it is usually due
     to real problems with the node.
-    </p></div><div class="refsect2" title="DatabaseHashSize"><a name="id518267"></a><h3>DatabaseHashSize</h3><p>Default: 100001</p><p>
+    </p></div><div class="refsect2"><a name="idm264403488448"></a><h3>DatabaseHashSize</h3><p>Default: 100001</p><p>
     Size of the hash chains for the local store of the tdbs that ctdb manages.
-    </p></div><div class="refsect2" title="DatabaseMaxDead"><a name="id518280"></a><h3>DatabaseMaxDead</h3><p>Default: 5</p><p>
+    </p></div><div class="refsect2"><a name="idm264403486944"></a><h3>DatabaseMaxDead</h3><p>Default: 5</p><p>
     How many dead records per hashchain in the TDB database do we allow before
     the freelist needs to be processed.
-    </p></div><div class="refsect2" title="RerecoveryTimeout"><a name="id518294"></a><h3>RerecoveryTimeout</h3><p>Default: 10</p><p>
+    </p></div><div class="refsect2"><a name="idm264403485392"></a><h3>RerecoveryTimeout</h3><p>Default: 10</p><p>
     Once a recovery has completed, no additional recoveries are permitted
     until this timeout has expired.
-    </p></div><div class="refsect2" title="EnableBans"><a name="id518307"></a><h3>EnableBans</h3><p>Default: 1</p><p>
+    </p></div><div class="refsect2"><a name="idm264403483856"></a><h3>EnableBans</h3><p>Default: 1</p><p>
     When set to 0, this disables BANNING completely in the cluster and thus
     nodes can not get banned, even it they break. Don't set to 0 unless you
     know what you are doing.
-    </p></div><div class="refsect2" title="DeterministicIPs"><a name="id518321"></a><h3>DeterministicIPs</h3><p>Default: 0</p><p>
+    </p></div><div class="refsect2"><a name="idm264403482240"></a><h3>DeterministicIPs</h3><p>Default: 0</p><p>
     When enabled, this tunable makes ctdb try to keep public IP addresses
     locked to specific nodes as far as possible. This makes it easier for
     debugging since you can know that as long as all nodes are healthy
@@ -392,12 +392,12 @@
     public IP assignment changes in the cluster. This tunable may increase
     the number of IP failover/failbacks that are performed on the cluster
     by a small margin.
-    </p></div><div class="refsect2" title="LCP2PublicIPs"><a name="id518342"></a><h3>LCP2PublicIPs</h3><p>Default: 1</p><p>
+    </p></div><div class="refsect2"><a name="idm264403479824"></a><h3>LCP2PublicIPs</h3><p>Default: 1</p><p>
     When enabled this switches ctdb to use the LCP2 ip allocation
     algorithm.
-    </p></div><div class="refsect2" title="ReclockPingPeriod"><a name="id518355"></a><h3>ReclockPingPeriod</h3><p>Default: x</p><p>
+    </p></div><div class="refsect2"><a name="idm264403478320"></a><h3>ReclockPingPeriod</h3><p>Default: x</p><p>
     Obsolete
-    </p></div><div class="refsect2" title="NoIPFailback"><a name="id518368"></a><h3>NoIPFailback</h3><p>Default: 0</p><p>
+    </p></div><div class="refsect2"><a name="idm264403476912"></a><h3>NoIPFailback</h3><p>Default: 0</p><p>
     When set to 1, ctdb will not perform failback of IP addresses when a node
     becomes healthy. Ctdb WILL perform failover of public IP addresses when a
     node becomes UNHEALTHY, but when the node becomes HEALTHY again, ctdb
@@ -415,7 +415,7 @@
     intervention from the administrator. When this parameter is set, you can
     manually fail public IP addresses over to the new node(s) using the
     'ctdb moveip' command.
-    </p></div><div class="refsect2" title="DisableIPFailover"><a name="id518395"></a><h3>DisableIPFailover</h3><p>Default: 0</p><p>
+    </p></div><div class="refsect2"><a name="idm264403473680"></a><h3>DisableIPFailover</h3><p>Default: 0</p><p>
     When enabled, ctdb will not perform failover or failback. Even if a
     node fails while holding public IPs, ctdb will not recover the IPs or
     assign them to another node.
@@ -424,59 +424,60 @@
     the cluster by failing IP addresses over to other nodes. This leads to
     a service outage until the administrator has manually performed failover
     to replacement nodes using the 'ctdb moveip' command.
-    </p></div><div class="refsect2" title="NoIPTakeover"><a name="id518415"></a><h3>NoIPTakeover</h3><p>Default: 0</p><p>
+    </p></div><div class="refsect2"><a name="idm264403471376"></a><h3>NoIPTakeover</h3><p>Default: 0</p><p>
     When set to 1, ctdb will allow ip addresses to be failed over onto this
     node. Any ip addresses that the node currently hosts will remain on the
     node but no new ip addresses can be failed over onto the node.
-    </p></div><div class="refsect2" title="NoIPTakeoverOnDisabled"><a name="id518429"></a><h3>NoIPTakeoverOnDisabled</h3><p>Default: 0</p><p>
+    </p></div><div class="refsect2"><a name="idm264403469728"></a><h3>NoIPHostOnAllDisabled</h3><p>Default: 0</p><p>
     If no nodes are healthy then by default ctdb will happily host
     public IPs on disabled (unhealthy or administratively disabled)
     nodes.  This can cause problems, for example if the underlying
-    cluster filesystem is not mounted.  When set to 1 this behaviour
-    is switched off and disabled nodes will not be able to takeover
-    IPs.
-    </p></div><div class="refsect2" title="DBRecordCountWarn"><a name="id518444"></a><h3>DBRecordCountWarn</h3><p>Default: 100000</p><p>
+    cluster filesystem is not mounted.  When set to 1 on a node and
+    that node is disabled it, any IPs hosted by this node will be
+    released and the node will not takeover any IPs until it is no
+    longer disabled.
+    </p></div><div class="refsect2"><a name="idm264403467872"></a><h3>DBRecordCountWarn</h3><p>Default: 100000</p><p>
     When set to non-zero, ctdb will log a warning when we try to recover a
     database with more than this many records. This will produce a warning
     if a database grows uncontrollably with orphaned records.
-    </p></div><div class="refsect2" title="DBRecordSizeWarn"><a name="id518459"></a><h3>DBRecordSizeWarn</h3><p>Default: 10000000</p><p>
+    </p></div><div class="refsect2"><a name="idm264403466224"></a><h3>DBRecordSizeWarn</h3><p>Default: 10000000</p><p>
     When set to non-zero, ctdb will log a warning when we try to recover a
     database where a single record is bigger than this. This will produce
     a warning if a database record grows uncontrollably with orphaned
     sub-records.
-    </p></div><div class="refsect2" title="DBSizeWarn"><a name="id518473"></a><h3>DBSizeWarn</h3><p>Default: 1000000000</p><p>
+    </p></div><div class="refsect2"><a name="idm264403464560"></a><h3>DBSizeWarn</h3><p>Default: 1000000000</p><p>
     When set to non-zero, ctdb will log a warning when we try to recover a
     database bigger than this. This will produce
     a warning if a database grows uncontrollably.
-    </p></div><div class="refsect2" title="VerboseMemoryNames"><a name="id518487"></a><h3>VerboseMemoryNames</h3><p>Default: 0</p><p>
+    </p></div><div class="refsect2"><a name="idm264403462960"></a><h3>VerboseMemoryNames</h3><p>Default: 0</p><p>
     This feature consumes additional memory. when used the talloc library
     will create more verbose names for all talloc allocated objects.
-    </p></div><div class="refsect2" title="RecdPingTimeout"><a name="id518500"></a><h3>RecdPingTimeout</h3><p>Default: 60</p><p>
+    </p></div><div class="refsect2"><a name="idm264403461392"></a><h3>RecdPingTimeout</h3><p>Default: 60</p><p>
     If the main dameon has not heard a "ping" from the recovery dameon for
     this many seconds, the main dameon will log a message that the recovery
     daemon is potentially hung.
-    </p></div><div class="refsect2" title="RecdFailCount"><a name="id518514"></a><h3>RecdFailCount</h3><p>Default: 10</p><p>
+    </p></div><div class="refsect2"><a name="idm264403459776"></a><h3>RecdFailCount</h3><p>Default: 10</p><p>
     If the recovery daemon has failed to ping the main dameon for this many
     consecutive intervals, the main daemon will consider the recovery daemon
     as hung and will try to restart it to recover.
-    </p></div><div class="refsect2" title="LogLatencyMs"><a name="id518529"></a><h3>LogLatencyMs</h3><p>Default: 0</p><p>
+    </p></div><div class="refsect2"><a name="idm264403458144"></a><h3>LogLatencyMs</h3><p>Default: 0</p><p>
     When set to non-zero, this will make the main daemon log any operation that
     took longer than this value, in 'ms', to complete.
     These include "how long time a lockwait child process needed", 
     "how long time to write to a persistent database" but also
     "how long did it take to get a response to a CALL from a remote node".
-    </p></div><div class="refsect2" title="RecLockLatencyMs"><a name="id518544"></a><h3>RecLockLatencyMs</h3><p>Default: 1000</p><p>
+    </p></div><div class="refsect2"><a name="idm264403456368"></a><h3>RecLockLatencyMs</h3><p>Default: 1000</p><p>
     When using a reclock file for split brain prevention, if set to non-zero
     this tunable will make the recovery dameon log a message if the fcntl()
     call to lock/testlock the recovery file takes longer than this number of 
     ms.
-    </p></div><div class="refsect2" title="RecoveryDropAllIPs"><a name="id518558"></a><h3>RecoveryDropAllIPs</h3><p>Default: 120</p><p>
+    </p></div><div class="refsect2"><a name="idm264403454704"></a><h3>RecoveryDropAllIPs</h3><p>Default: 120</p><p>
     If we have been stuck in recovery, or stopped, or banned, mode for
     this many seconds we will force drop all held public addresses.
-    </p></div><div class="refsect2" title="verifyRecoveryLock"><a name="id518572"></a><h3>verifyRecoveryLock</h3><p>Default: 1</p><p>
+    </p></div><div class="refsect2"><a name="idm264403453136"></a><h3>verifyRecoveryLock</h3><p>Default: 1</p><p>
     Should we take a fcntl() lock on the reclock file to verify that we are the
     sole recovery master node on the cluster or not.
-    </p></div><div class="refsect2" title="DeferredAttachTO"><a name="id518586"></a><h3>DeferredAttachTO</h3><p>Default: 120</p><p>
+    </p></div><div class="refsect2"><a name="idm264403451568"></a><h3>DeferredAttachTO</h3><p>Default: 120</p><p>
     When databases are frozen we do not allow clients to attach to the
     databases. Instead of returning an error immediately to the application
     the attach request from the client is deferred until the database
@@ -484,26 +485,26 @@
     </p><p>
     This timeout controls how long we will defer the request from the client
     before timing it out and returning an error to the client.
-    </p></div><div class="refsect2" title="HopcountMakeSticky"><a name="id518605"></a><h3>HopcountMakeSticky</h3><p>Default: 50</p><p>
+    </p></div><div class="refsect2"><a name="idm264403449312"></a><h3>HopcountMakeSticky</h3><p>Default: 50</p><p>
     If the database is set to 'STICKY' mode, using the 'ctdb setdbsticky' 
     command, any record that is seen as very hot and migrating so fast that
     hopcount surpasses 50 is set to become a STICKY record for StickyDuration
     seconds. This means that after each migration the record will be kept on
     the node and prevented from being migrated off the node.
     </p><p>
-    This setting allows to try to identify such records and stop them from 
+    This setting allows one to try to identify such records and stop them from
     migrating across the cluster so fast. This will improve performance for
     certain workloads, such as locking.tdb if many clients are opening/closing
     the same file concurrently.
-    </p></div><div class="refsect2" title="StickyDuration"><a name="id518626"></a><h3>StickyDuration</h3><p>Default: 600</p><p>
+    </p></div><div class="refsect2"><a name="idm264403446848"></a><h3>StickyDuration</h3><p>Default: 600</p><p>
     Once a record has been found to be fetch-lock hot and has been flagged to
     become STICKY, this is for how long, in seconds, the record will be 
     flagged as a STICKY record.
-    </p></div><div class="refsect2" title="StickyPindown"><a name="id518640"></a><h3>StickyPindown</h3><p>Default: 200</p><p>
+    </p></div><div class="refsect2"><a name="idm264403445232"></a><h3>StickyPindown</h3><p>Default: 200</p><p>
     Once a STICKY record has been migrated onto a node, it will be pinned down
     on that node for this number of ms. Any request from other nodes to migrate
     the record off the node will be deferred until the pindown timer expires.
-    </p></div><div class="refsect2" title="MaxLACount"><a name="id518654"></a><h3>MaxLACount</h3><p>Default: 20</p><p>
+    </p></div><div class="refsect2"><a name="idm264403443568"></a><h3>MaxLACount</h3><p>Default: 20</p><p>
     When record content is fetched from a remote node, if it is only for 
     reading the record, pass back the content of the record but do not yet 
     migrate the record. Once MaxLACount identical requests from the 
@@ -511,13 +512,13 @@
     onto the requesting node. This reduces the amount of migration for a 
     database read-mostly workload at the expense of more frequent network
     roundtrips.
-    </p></div><div class="refsect2" title="StatHistoryInterval"><a name="id518671"></a><h3>StatHistoryInterval</h3><p>Default: 1</p><p>
+    </p></div><div class="refsect2"><a name="idm264403441680"></a><h3>StatHistoryInterval</h3><p>Default: 1</p><p>
     Granularity of the statistics collected in the statistics history.
-    </p></div><div class="refsect2" title="AllowClientDBAttach"><a name="id518684"></a><h3>AllowClientDBAttach</h3><p>Default: 1</p><p>
+    </p></div><div class="refsect2"><a name="idm264403440176"></a><h3>AllowClientDBAttach</h3><p>Default: 1</p><p>
     When set to 0, clients are not allowed to attach to any databases.
     This can be used to temporarily block any new processes from attaching
     to and accessing the databases.
-    </p></div><div class="refsect2" title="RecoverPDBBySeqNum"><a name="id518698"></a><h3>RecoverPDBBySeqNum</h3><p>Default: 0</p><p>
+    </p></div><div class="refsect2"><a name="idm264403438560"></a><h3>RecoverPDBBySeqNum</h3><p>Default: 0</p><p>
     When set to non-zero, this will change how the recovery process for
     persistent databases ar performed. By default, when performing a database
     recovery, for normal as for persistent databases, recovery is
@@ -528,7 +529,7 @@
     a whole db and not by individual records. The node that contains the
     highest value stored in the record "__db_sequence_number__" is selected
     and the copy of that nodes database is used as the recovered database.
-    </p></div><div class="refsect2" title="FetchCollapse"><a name="id518719"></a><h3>FetchCollapse</h3><p>Default: 1</p><p>
+    </p></div><div class="refsect2"><a name="idm264403436096"></a><h3>FetchCollapse</h3><p>Default: 1</p><p>
     When many clients across many nodes try to access the same record at the
     same time this can lead to a fetch storm where the record becomes very
     active and bounces between nodes very fast. This leads to high CPU
@@ -544,7 +545,7 @@
     </p><p>
     This timeout controls if we should collapse multiple fetch operations
     of the same record into a single request and defer all duplicates or not.
-    </p></div><div class="refsect2" title="DeadlockTimeout"><a name="id518748"></a><h3>DeadlockTimeout</h3><p>Default: 60</p><p>
+    </p></div><div class="refsect2"><a name="idm264403432992"></a><h3>DeadlockTimeout</h3><p>Default: 60</p><p>
     Number of seconds to determine if ctdb is in deadlock with samba.
     </p><p>
     When ctdb daemon is blocked waiting for a lock on a database which is
@@ -554,14 +555,14 @@
     timeout expires, ctdb will detect it as a deadlock and terminate the
     blocking samba process. Setting this value to 0 disables deadlock
     detection.
-    </p></div><div class="refsect2" title="Samba3AvoidDeadlock"><a name="id518768"></a><h3>Samba3AvoidDeadlock</h3><p>Default: 0</p><p>
+    </p></div><div class="refsect2"><a name="idm264403430624"></a><h3>Samba3AvoidDeadlocks</h3><p>Default: 0</p><p>
     Enable code that prevents deadlocks with Samba (only for Samba 3.x).
     </p><p>
     This should be set to 1 when using Samba version 3.x to enable special
     code in CTDB to avoid deadlock with Samba version 3.x.  This code
     is not required for Samba version 4.x and must not be enabled for
     Samba 4.x.
-    </p></div></div><div class="refsect1" title="LVS"><a name="id518788"></a><h2>LVS</h2><p>
+    </p></div></div><div class="refsect1"><a name="idm264403428352"></a><h2>LVS</h2><p>
     LVS is a mode where CTDB presents one single IP address for the entire
     cluster. This is an alternative to using public IP addresses and round-robin
     DNS to loadbalance clients across the cluster.
@@ -602,7 +603,7 @@
     the processing node back to the clients. For read-intensive i/o patterns you can acheive very high throughput rates in this mode.
     </p><p>
     Note: you can use LVS and public addresses at the same time.
-    </p><div class="refsect2" title="Configuration"><a name="id518847"></a><h3>Configuration</h3><p>
+    </p><div class="refsect2"><a name="idm264403421456"></a><h3>Configuration</h3><p>
     To activate LVS on a CTDB node you must specify CTDB_PUBLIC_INTERFACE and 
     CTDB_LVS_PUBLIC_ADDRESS in /etc/sysconfig/ctdb.
 	</p><p>
@@ -625,7 +626,7 @@ You must also specify the "--lvs" command line argument to ctdbd to activate LVS
     all of the clients from the node BEFORE you enable LVS. Also make sure
     that when you ping these hosts that the traffic is routed out through the
     eth0 interface.
-    </p></div><div class="refsect1" title="REMOTE CLUSTER NODES"><a name="id518885"></a><h2>REMOTE CLUSTER NODES</h2><p>
+    </p></div><div class="refsect1"><a name="idm264403417056"></a><h2>REMOTE CLUSTER NODES</h2><p>
 It is possible to have a CTDB cluster that spans across a WAN link. 
 For example where you have a CTDB cluster in your datacentre but you also
 want to have one additional CTDB node located at a remote branch site.
@@ -654,7 +655,7 @@ CTDB_CAPABILITY_RECMASTER=no
     </p><p>
 	Verify with the command "ctdb getcapabilities" that that node no longer
 	has the recmaster or the lmaster capabilities.
-    </p></div><div class="refsect1" title="NAT-GW"><a name="id518924"></a><h2>NAT-GW</h2><p>
+    </p></div><div class="refsect1"><a name="idm264403412480"></a><h2>NAT-GW</h2><p>
       Sometimes it is desireable to run services on the CTDB node which will
       need to originate outgoing traffic to external servers. This might
       be contacting NIS servers, LDAP servers etc. etc.
@@ -677,7 +678,7 @@ CTDB_CAPABILITY_RECMASTER=no
       if there are no public addresses assigned to the node.
       This is the simplest way but it uses up a lot of ip addresses since you
       have to assign both static and also public addresses to each node.
-    </p><div class="refsect2" title="NAT-GW"><a name="id518954"></a><h3>NAT-GW</h3><p>
+    </p><div class="refsect2"><a name="idm264403409024"></a><h3>NAT-GW</h3><p>
       A second way is to use the built in NAT-GW feature in CTDB.
       With NAT-GW you assign one public NATGW address for each natgw group.
       Each NATGW group is a set of nodes in the cluster that shares the same
@@ -692,7 +693,7 @@ CTDB_CAPABILITY_RECMASTER=no
       In each NATGW group, one of the nodes is designated the NAT Gateway
       through which all traffic that is originated by nodes in this group
       will be routed through if a public addresses are not available. 
-    </p></div><div class="refsect2" title="Configuration"><a name="id518976"></a><h3>Configuration</h3><p>
+    </p></div><div class="refsect2"><a name="idm264403406336"></a><h3>Configuration</h3><p>
       NAT-GW is configured in /etc/sysconfig/ctdb by setting the following
       variables:
     </p><pre class="screen">
@@ -740,31 +741,31 @@ CTDB_CAPABILITY_RECMASTER=no
 # become natgw master.
 #
 # CTDB_NATGW_SLAVE_ONLY=yes
-    </pre></div><div class="refsect2" title="CTDB_NATGW_PUBLIC_IP"><a name="id519009"></a><h3>CTDB_NATGW_PUBLIC_IP</h3><p>
+    </pre></div><div class="refsect2"><a name="idm264403402512"></a><h3>CTDB_NATGW_PUBLIC_IP</h3><p>
       This is an ip address in the public network that is used for all outgoing
       traffic when the public addresses are not assigned.
       This address will be assigned to one of the nodes in the cluster which
       will masquerade all traffic for the other nodes.
     </p><p>
       Format of this parameter is IPADDRESS/NETMASK
-    </p></div><div class="refsect2" title="CTDB_NATGW_PUBLIC_IFACE"><a name="id519024"></a><h3>CTDB_NATGW_PUBLIC_IFACE</h3><p>
+    </p></div><div class="refsect2"><a name="idm264403400816"></a><h3>CTDB_NATGW_PUBLIC_IFACE</h3><p>
       This is the physical interface where the CTDB_NATGW_PUBLIC_IP will be
       assigned to. This should be an interface connected to the public network.
     </p><p>
       Format of this parameter is INTERFACE
-    </p></div><div class="refsect2" title="CTDB_NATGW_DEFAULT_GATEWAY"><a name="id519038"></a><h3>CTDB_NATGW_DEFAULT_GATEWAY</h3><p>
+    </p></div><div class="refsect2"><a name="idm264403399232"></a><h3>CTDB_NATGW_DEFAULT_GATEWAY</h3><p>
       This is the default gateway to use on the node that is elected to host
       the CTDB_NATGW_PUBLIC_IP. This is the default gateway on the public network.
     </p><p>
       Format of this parameter is IPADDRESS
-    </p></div><div class="refsect2" title="CTDB_NATGW_PRIVATE_NETWORK"><a name="id519052"></a><h3>CTDB_NATGW_PRIVATE_NETWORK</h3><p>
+    </p></div><div class="refsect2"><a name="idm264403397648"></a><h3>CTDB_NATGW_PRIVATE_NETWORK</h3><p>
       This is the network/netmask used for the interal private network.
     </p><p>
       Format of this parameter is IPADDRESS/NETMASK
-    </p></div><div class="refsect2" title="CTDB_NATGW_NODES"><a name="id519065"></a><h3>CTDB_NATGW_NODES</h3><p>
+    </p></div><div class="refsect2"><a name="idm264403396064"></a><h3>CTDB_NATGW_NODES</h3><p>
       This is the list of all nodes that belong to the same NATGW group
       as this node. The default is /etc/ctdb/natgw_nodes.
-    </p></div><div class="refsect2" title="Operation"><a name="id519075"></a><h3>Operation</h3><p>
+    </p></div><div class="refsect2"><a name="idm264403394896"></a><h3>Operation</h3><p>
       When the NAT-GW functionality is used, one of the nodes is elected
       to act as a NAT router for all the other nodes in the group when
       they need to originate traffic to the external public network.
@@ -783,7 +784,7 @@ CTDB_CAPABILITY_RECMASTER=no
     </p><p>
       This is implemented in the 11.natgw eventscript. Please see the
       eventscript for further information.
-    </p></div><div class="refsect2" title="Removing/Changing NATGW at runtime"><a name="id519102"></a><h3>Removing/Changing NATGW at runtime</h3><p>
+    </p></div><div class="refsect2"><a name="idm264403391696"></a><h3>Removing/Changing NATGW at runtime</h3><p>
       The following are the procedures to change/remove a NATGW configuration 
       at runtime, without having to restart ctdbd.
     </p><p>
@@ -797,7 +798,7 @@ CTDB_CAPABILITY_RECMASTER=no
 1, Run 'CTDB_BASE=/etc/ctdb /etc/ctdb/events.d/11.natgw removenatgw'
 2, Then change the configuration in /etc/sysconfig/ctdb
 3, Run 'CTDB_BASE=/etc/ctdb /etc/ctdb/events.d/11.natgw updatenatgw'
-    </pre></div></div><div class="refsect1" title="POLICY ROUTING"><a name="id519135"></a><h2>POLICY ROUTING</h2><p>
+    </pre></div></div><div class="refsect1"><a name="idm264403387856"></a><h2>POLICY ROUTING</h2><p>
       A node running CTDB may be a component of a complex network
       topology.  In particular, public addresses may be spread across
       several different networks (or VLANs) and it may not be possible
@@ -807,9 +808,9 @@ CTDB_CAPABILITY_RECMASTER=no
       be specified for packets sourced from each public address.  The
       routes are added and removed as CTDB moves public addresses
       between nodes.
-    </p><div class="refsect2" title="Configuration variables"><a name="id519154"></a><h3>Configuration variables</h3><p>
+    </p><div class="refsect2"><a name="idm264403385664"></a><h3>Configuration variables</h3><p>
 	There are 4 configuration variables related to policy routing:
-      </p><div class="variablelist"><dl><dt><span class="term"><code class="varname">CTDB_PER_IP_ROUTING_CONF</code></span></dt><dd><p>
+      </p><div class="variablelist"><dl class="variablelist"><dt><span class="term"><code class="varname">CTDB_PER_IP_ROUTING_CONF</code></span></dt><dd><p>
 	    The name of a configuration file that specifies the
 	    desired routes for each source address.  The configuration
 	    file format is discussed below.  A recommended value is
@@ -848,7 +849,7 @@ CTDB_CAPABILITY_RECMASTER=no
 	      The label for a public address <addr;gt; will look
 	      like ctdb.<addr>.  This means that the associated
 	      rules and routes are easy to read (and manipulate).
-	    </p></dd></dl></div></div><div class="refsect2" title="Configuration file"><a name="id519256"></a><h3>Configuration file</h3><p>
+	    </p></dd></dl></div></div><div class="refsect2"><a name="idm264403373520"></a><h3>Configuration file</h3><p>
 	The format of each line is:
       </p><pre class="screen">
     <public_address> <network> [ <gateway> ]
@@ -909,7 +910,7 @@ CTDB_CAPABILITY_RECMASTER=no
       </p><pre class="screen">
   192.168.1.0/24 dev eth2 scope link 
   default via 192.168.1.1 dev eth2 
-      </pre></div><div class="refsect2" title="Example configuration"><a name="id519363"></a><h3>Example configuration</h3><p>
+      </pre></div><div class="refsect2"><a name="idm264403358720"></a><h3>Example configuration</h3><p>
 	Here is a more complete example configuration.
       </p><pre class="screen">
 /etc/ctdb/public_addresses:
@@ -929,7 +930,7 @@ CTDB_CAPABILITY_RECMASTER=no
 	The routes local packets as expected, the default route is as
 	previously discussed, but packets to 192.168.200.0/24 are
 	routed via the alternate gateway 192.168.1.254.
-      </p></div></div><div class="refsect1" title="NOTIFICATION SCRIPT"><a name="id519385"></a><h2>NOTIFICATION SCRIPT</h2><p>
+      </p></div></div><div class="refsect1"><a name="idm264403355888"></a><h2>NOTIFICATION SCRIPT</h2><p>
       Notification scripts are used with ctdb to have a call-out from ctdb
       to a user-specified script when certain state changes occur in ctdb.
       This is commonly to set up either sending SNMP traps or emails
@@ -941,17 +942,17 @@ CTDB_CAPABILITY_RECMASTER=no
       See /etc/ctdb/notify.sh for an example script.
     </p><p>
       CTDB currently generates notifications on these state changes:
-    </p><div class="refsect2" title="unhealthy"><a name="id519410"></a><h3>unhealthy</h3><p>
+    </p><div class="refsect2"><a name="idm264403353008"></a><h3>unhealthy</h3><p>
       This call-out is triggered when the node changes to UNHEALTHY state.
-    </p></div><div class="refsect2" title="healthy"><a name="id519419"></a><h3>healthy</h3><p>
+    </p></div><div class="refsect2"><a name="idm264403351888"></a><h3>healthy</h3><p>
       This call-out is triggered when the node changes to HEALTHY state.
-    </p></div><div class="refsect2" title="startup"><a name="id519429"></a><h3>startup</h3><p>
+    </p></div><div class="refsect2"><a name="idm264403350768"></a><h3>startup</h3><p>
       This call-out is triggered when ctdb has started up and all managed services are up and running.
-    </p></div></div><div class="refsect1" title="ClamAV Daemon"><a name="id519440"></a><h2>ClamAV Daemon</h2><p>
+    </p></div></div><div class="refsect1"><a name="idm264403349488"></a><h2>ClamAV Daemon</h2><p>
 CTDB has support to manage the popular anti-virus daemon ClamAV.
 This support is implemented through the
 eventscript : /etc/ctdb/events.d/31.clamd.
-</p><div class="refsect2" title="Configuration"><a name="id519449"></a><h3>Configuration</h3><p>
+</p><div class="refsect2"><a name="idm264403348432"></a><h3>Configuration</h3><p>
 Start by configuring CLAMAV normally and test that it works. Once this is
 done, copy the configuration files over to all the nodes so that all nodes
 share identical CLAMAV configurations.
@@ -980,10 +981,10 @@ Once you have restarted CTDBD, use
 ctdb scriptstatus
 </pre><p>
 and verify that the 31.clamd eventscript is listed and that it was executed successfully.
-</p></div></div><div class="refsect1" title="SEE ALSO"><a name="id519503"></a><h2>SEE ALSO</h2><p>
+</p></div></div><div class="refsect1"><a name="idm264403342368"></a><h2>SEE ALSO</h2><p>
       ctdb(1), onnode(1)
       <a class="ulink" href="http://ctdb.samba.org/" target="_top">http://ctdb.samba.org/</a>
-    </p></div><div class="refsect1" title="COPYRIGHT/LICENSE"><a name="id519516"></a><h2>COPYRIGHT/LICENSE</h2><div class="literallayout"><p><br>
+    </p></div><div class="refsect1"><a name="idm264403340848"></a><h2>COPYRIGHT/LICENSE</h2><div class="literallayout"><p><br>
 Copyright (C) Andrew Tridgell 2007<br>
 Copyright (C) Ronnie sahlberg 2007<br>
 <br>
diff --git a/doc/ctdbd.1.xml b/doc/ctdbd.1.xml
index a0cba99..9516164 100644
--- a/doc/ctdbd.1.xml
+++ b/doc/ctdbd.1.xml
@@ -862,15 +862,16 @@
     </para>
     </refsect2>
 
-    <refsect2><title>NoIPTakeoverOnDisabled</title>
+    <refsect2><title>NoIPHostOnAllDisabled</title>
     <para>Default: 0</para>
     <para>
     If no nodes are healthy then by default ctdb will happily host
     public IPs on disabled (unhealthy or administratively disabled)
     nodes.  This can cause problems, for example if the underlying
-    cluster filesystem is not mounted.  When set to 1 this behaviour
-    is switched off and disabled nodes will not be able to takeover
-    IPs.
+    cluster filesystem is not mounted.  When set to 1 on a node and
+    that node is disabled it, any IPs hosted by this node will be
+    released and the node will not takeover any IPs until it is no
+    longer disabled.
     </para>
     </refsect2>
 
@@ -989,7 +990,7 @@
     the node and prevented from being migrated off the node.
     </para>
     <para>
-    This setting allows to try to identify such records and stop them from 
+    This setting allows one to try to identify such records and stop them from
     migrating across the cluster so fast. This will improve performance for
     certain workloads, such as locking.tdb if many clients are opening/closing
     the same file concurrently.
@@ -1099,7 +1100,7 @@
     </para>
     </refsect2>
 
-    <refsect2><title>Samba3AvoidDeadlock</title>
+    <refsect2><title>Samba3AvoidDeadlocks</title>
     <para>Default: 0</para>
     <para>
     Enable code that prevents deadlocks with Samba (only for Samba 3.x).
diff --git a/doc/ltdbtool.1 b/doc/ltdbtool.1
index b182171..9c80835 100644
--- a/doc/ltdbtool.1
+++ b/doc/ltdbtool.1
@@ -1,13 +1,22 @@
 '\" t
 .\"     Title: ltdbtool
 .\"    Author: [FIXME: author] [see http://docbook.sf.net/el/author]
-.\" Generator: DocBook XSL Stylesheets v1.75.2 <http://docbook.sf.net/>
-.\"      Date: 01/09/2013
+.\" Generator: DocBook XSL Stylesheets v1.78.1 <http://docbook.sf.net/>
+.\"      Date: 05/30/2013
 .\"    Manual:  
 .\"    Source:  
 .\"  Language: English
 .\"
-.TH "LTDBTOOL" "1" "01/09/2013" "" ""
+.TH "LTDBTOOL" "1" "05/30/2013" "" ""
+.\" -----------------------------------------------------------------
+.\" * Define some portability stuff
+.\" -----------------------------------------------------------------
+.\" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+.\" http://bugs.debian.org/507673
+.\" http://lists.gnu.org/archive/html/groff/2009-02/msg00013.html
+.\" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+.ie \n(.g .ds Aq \(aq
+.el       .ds Aq '
 .\" -----------------------------------------------------------------
 .\" * set default formatting
 .\" -----------------------------------------------------------------
@@ -19,13 +28,13 @@
 .\" * MAIN CONTENT STARTS HERE *
 .\" -----------------------------------------------------------------
 .SH "NAME"
-ltdbtool \- handle ctdb\'s local tdb copies
+ltdbtool \- handle ctdb\*(Aqs local tdb copies
 .SH "SYNOPSIS"
 .HP \w'\fBltdbtool\ [OPTIONS]\ COMMAND\fR\ 'u
 \fBltdbtool [OPTIONS] COMMAND\fR
 .SH "DESCRIPTION"
 .PP
-ltdbtool is a utility to cope with ctdb\'s local tdb copies (LTDBs) without connecting to a ctdb daemon\&.
+ltdbtool is a utility to cope with ctdb\*(Aqs local tdb copies (LTDBs) without connecting to a ctdb daemon\&.
 .PP
 It can be used to
 .sp
@@ -62,7 +71,6 @@ convert between an LTDB and a non\-clustered tdb by adding or removing ctdb head
 convert between 64 and 32 bit LTDBs where the ctdb record headers differ by 4 bytes of padding\&.
 .RE
 .sp
-.RE
 .SH "COMMANDS"
 .PP
 help
diff --git a/doc/ltdbtool.1.html b/doc/ltdbtool.1.html
index 49897fa..e4300d3 100644
--- a/doc/ltdbtool.1.html
+++ b/doc/ltdbtool.1.html
@@ -1,8 +1,8 @@
-<html><head><meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1"><title>ltdbtool</title><meta name="generator" content="DocBook XSL Stylesheets V1.75.2"></head><body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF"><div class="refentry" title="ltdbtool"><a name="ltdbtool.1"></a><div class="titlepage"></div><div class="refnamediv"><h2>Name</h2><p>ltdbtool — handle ctdb's local tdb copies </p></div><div class="refsynopsisdiv" title="Synopsis"><h2>Synopsis</h2><div class="cmdsynopsis"><p><code class="command">ltdbtool [OPTIONS] COMMAND</code> </p></div></div><div class="refsect1" title="DESCRIPTION"><a name="id471178"></a><h2>DESCRIPTION</h2><p>
+<html><head><meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1"><title>ltdbtool</title><meta name="generator" content="DocBook XSL Stylesheets V1.78.1"></head><body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF"><div class="refentry"><a name="ltdbtool.1"></a><div class="titlepage"></div><div class="refnamediv"><h2>Name</h2><p>ltdbtool — handle ctdb's local tdb copies </p></div><div class="refsynopsisdiv"><h2>Synopsis</h2><div class="cmdsynopsis"><p><code class="command">ltdbtool [OPTIONS] COMMAND</code> </p></div></div><div class="refsect1"><a name="idm264395311664"></a><h2>DESCRIPTION</h2><p>
       ltdbtool is a utility to cope with ctdb's local tdb copies (LTDBs)
       without connecting to a ctdb daemon.
     </p><p>It can be used to
-    </p><div class="itemizedlist"><ul class="itemizedlist" type="disc" compact><li class="listitem"><p>
+    </p><div class="itemizedlist"><ul class="itemizedlist compact" style="list-style-type: disc; "><li class="listitem"><p>
 	  dump the contents of a LTDB, optionally printing the ctdb
 	  record header information,
 	</p></li><li class="listitem"><p>
@@ -11,19 +11,19 @@
 	</p></li><li class="listitem"><p>convert between 64 and 32 bit LTDBs where the ctdb record
 	headers differ by 4 bytes of padding.
 	</p></li></ul></div><p>
-    </p></div><div class="refsect1" title="COMMANDS"><a name="id471224"></a><h2>COMMANDS</h2><div class="variablelist"><dl><dt><span class="term">help</span></dt><dd><p>
+    </p></div><div class="refsect1"><a name="idm264395060864"></a><h2>COMMANDS</h2><div class="variablelist"><dl class="variablelist"><dt><span class="term">help</span></dt><dd><p>
 	    Print a help text.
 	  </p></dd><dt><span class="term">dump <IDB></span></dt><dd><p>
 	    Dump the contents of a LTDB file to standard output in a
 	    human-readable format.
 	  </p></dd><dt><span class="term">convert <IDB> <ODB></span></dt><dd><p>
 	    Make a copy of a LTDB optionally adding or removing ctdb headers.
-	  </p></dd></dl></div></div><div class="refsect1" title="OPTIONS"><a name="id471272"></a><h2>OPTIONS</h2><div class="variablelist"><dl><dt><span class="term">-p</span></dt><dd><p>
+	  </p></dd></dl></div></div><div class="refsect1"><a name="idm264395088960"></a><h2>OPTIONS</h2><div class="variablelist"><dl class="variablelist"><dt><span class="term">-p</span></dt><dd><p>
 	    Dump with header information, similar to "ctdb catdb".
 	  </p></dd><dt><span class="term">-s {0|32|64}</span></dt><dd><p>
 	    Specify how to determine the ctdb record header size
 	    for the input database:
-	    </p><div class="variablelist"><dl><dt><span class="term">0</span></dt><dd><p>no ctdb header</p></dd><dt><span class="term">32</span></dt><dd><p>ctdb header size of a 32 bit system (20 bytes)</p></dd><dt><span class="term">64</span></dt><dd><p>ctdb header size of a 64 bit system (24 bytes)</p></dd></dl></div><p>
+	    </p><div class="variablelist"><dl class="variablelist"><dt><span class="term">0</span></dt><dd><p>no ctdb header</p></dd><dt><span class="term">32</span></dt><dd><p>ctdb header size of a 32 bit system (20 bytes)</p></dd><dt><span class="term">64</span></dt><dd><p>ctdb header size of a 64 bit system (24 bytes)</p></dd></dl></div><p>
 	    The default is 32 or 64 depending on the system architecture.
 	  </p></dd><dt><span class="term">-o {0|32|64}</span></dt><dd><p>
 	    Specify how to determine the ctdb record header size
@@ -34,7 +34,7 @@
 	    Explicitly specify the ctdb record header size for the output database in bytes.
 	  </p></dd><dt><span class="term">-h</span></dt><dd><p>
             Print a help text.
-	  </p></dd></dl></div></div><div class="refsect1" title="EXAMPLES"><a name="id471401"></a><h2>EXAMPLES</h2><p>
+	  </p></dd></dl></div></div><div class="refsect1"><a name="idm264393451168"></a><h2>EXAMPLES</h2><p>
       Print a local tdb in "tdbdump" style:
     </p><pre class="screen">
       ltdbtool dump idmap2.tdb.0
@@ -62,10 +62,10 @@
       Add a default header:
     </p><pre class="screen">
       ltdbtool convert -s0 idmap.tdb idmap2.tdb.0
-    </pre></div><div class="refsect1" title="SEE ALSO"><a name="id471476"></a><h2>SEE ALSO</h2><p>
+    </pre></div><div class="refsect1"><a name="idm264395258096"></a><h2>SEE ALSO</h2><p>
       ctdbd(1), ctdb(1), tdbdump(1), tdbrestore(1),
       <a class="ulink" href="http://ctdb.samba.org/" target="_top">http://ctdb.samba.org/</a>
-    </p></div><div class="refsect1" title="COPYRIGHT/LICENSE"><a name="id471490"></a><h2>COPYRIGHT/LICENSE</h2><div class="literallayout"><p><br>
+    </p></div><div class="refsect1"><a name="idm264393419200"></a><h2>COPYRIGHT/LICENSE</h2><div class="literallayout"><p><br>
 Copyright (C) Gregor Beck 2011<br>
 Copyright (C) Michael Adam 2011<br>
 <br>
diff --git a/doc/onnode.1 b/doc/onnode.1
index 162c912..40733eb 100644
--- a/doc/onnode.1
+++ b/doc/onnode.1
@@ -1,13 +1,22 @@
 '\" t
 .\"     Title: onnode
 .\"    Author: [FIXME: author] [see http://docbook.sf.net/el/author]
-.\" Generator: DocBook XSL Stylesheets v1.75.2 <http://docbook.sf.net/>
-.\"      Date: 01/09/2013
+.\" Generator: DocBook XSL Stylesheets v1.78.1 <http://docbook.sf.net/>
+.\"      Date: 05/30/2013
 .\"    Manual:  
 .\"    Source:  
 .\"  Language: English
 .\"
-.TH "ONNODE" "1" "01/09/2013" "" ""
+.TH "ONNODE" "1" "05/30/2013" "" ""
+.\" -----------------------------------------------------------------
+.\" * Define some portability stuff
+.\" -----------------------------------------------------------------
+.\" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+.\" http://bugs.debian.org/507673
+.\" http://lists.gnu.org/archive/html/groff/2009-02/msg00013.html
+.\" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+.ie \n(.g .ds Aq \(aq
+.el       .ds Aq '
 .\" -----------------------------------------------------------------
 .\" * set default formatting
 .\" -----------------------------------------------------------------
@@ -92,7 +101,7 @@ Do not print node addresses\&. Normally, onnode prints informational node addres
 .PP
 \-n
 .RS 4
-Allow nodes to be specified by name rather than node numbers\&. These nodes don\'t need to be listed in the nodes file\&. You can avoid the nodes file entirely by combining this with
+Allow nodes to be specified by name rather than node numbers\&. These nodes don\*(Aqt need to be listed in the nodes file\&. You can avoid the nodes file entirely by combining this with
 \-f /dev/null\&.
 .RE
 .PP
@@ -132,7 +141,7 @@ The following command would show the process ID of ctdb on all nodes
 .RE
 .\}
 .PP
-The following command would show the last 5 lines of log on each node, preceded by the node\'s hostname
+The following command would show the last 5 lines of log on each node, preceded by the node\*(Aqs hostname
 .sp
 .if n \{\
 .RS 4
@@ -182,7 +191,7 @@ in the FILES section for more details\&.
 .PP
 /etc/ctdb/nodes
 .RS 4
-Default file containing a list of each node\'s IP address or hostname\&.
+Default file containing a list of each node\*(Aqs IP address or hostname\&.
 .sp
 Actually, the default is
 $\fBCTDB_BASE\fR/nodes, where
diff --git a/doc/onnode.1.html b/doc/onnode.1.html
index 54ceb78..706ddad 100644
--- a/doc/onnode.1.html
+++ b/doc/onnode.1.html
@@ -1,4 +1,4 @@
-<html><head><meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1"><title>onnode</title><meta name="generator" content="DocBook XSL Stylesheets V1.75.2"></head><body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF"><div class="refentry" title="onnode"><a name="onnode.1"></a><div class="titlepage"></div><div class="refnamediv"><h2>Name</h2><p>onnode — run commands on ctdb nodes</p></div><div class="refsynopsisdiv" title="Synopsis"><h2>Synopsis</h2><div class="cmdsynopsis"><p><code class="command">onnode [OPTION] ... NODES COMMAND ...</code> </p></div></div><div class="refsect1" title="DESCRIPTION"><a name="id402190"></a><h2>DESCRIPTION</h2><p>
+<html><head><meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1"><title>onnode</title><meta name="generator" content="DocBook XSL Stylesheets V1.78.1"></head><body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF"><div class="refentry"><a name="onnode.1"></a><div class="titlepage"></div><div class="refnamediv"><h2>Name</h2><p>onnode — run commands on ctdb nodes</p></div><div class="refsynopsisdiv"><h2>Synopsis</h2><div class="cmdsynopsis"><p><code class="command">onnode [OPTION] ... NODES COMMAND ...</code> </p></div></div><div class="refsect1"><a name="idm264400708784"></a><h2>DESCRIPTION</h2><p>
       onnode is a utility to run commands on a specific node of a CTDB
       cluster, or on all nodes.
     </p><p>
@@ -13,10 +13,10 @@
     </p><p>
       The COMMAND can be any shell command. The onnode utility uses
       ssh or rsh to connect to the remote nodes and run the command.
-    </p></div><div class="refsect1" title="DESCRIPTIVE NODE SPECIFICATIONS"><a name="id402213"></a><h2>DESCRIPTIVE NODE SPECIFICATIONS</h2><p>
+    </p></div><div class="refsect1"><a name="idm264402864768"></a><h2>DESCRIPTIVE NODE SPECIFICATIONS</h2><p>
       The following descriptive node specification can be used in
       place of numeric node numbers:
-    </p><div class="variablelist"><dl><dt><span class="term">all</span></dt><dd><p>
+    </p><div class="variablelist"><dl class="variablelist"><dt><span class="term">all</span></dt><dd><p>
             All nodes.
 	  </p></dd><dt><span class="term">any</span></dt><dd><p>
              A node where ctdbd is running.  This semi-random but
@@ -32,7 +32,7 @@
             The current NAT gateway.
 	  </p></dd><dt><span class="term">rm | recmaster</span></dt><dd><p>
             The current recovery master.
-	  </p></dd></dl></div></div><div class="refsect1" title="OPTIONS"><a name="id402315"></a><h2>OPTIONS</h2><div class="variablelist"><dl><dt><span class="term">-c</span></dt><dd><p>
+	  </p></dd></dl></div></div><div class="refsect1"><a name="idm264402957984"></a><h2>OPTIONS</h2><div class="variablelist"><dl class="variablelist"><dt><span class="term">-c</span></dt><dd><p>
             Execute COMMAND in the current working directory on the
             specified nodes.
 	  </p></dd><dt><span class="term">-o <prefix></span></dt><dd><p>
@@ -66,7 +66,7 @@
             - filenames with whitespace in them are not supported.
 	  </p></dd><dt><span class="term">-h, --help</span></dt><dd><p>
             Show a short usage guide.
-	  </p></dd></dl></div></div><div class="refsect1" title="EXAMPLES"><a name="id402453"></a><h2>EXAMPLES</h2><p>
+	  </p></dd></dl></div></div><div class="refsect1"><a name="idm264402941280"></a><h2>EXAMPLES</h2><p>
       The following command would show the process ID of ctdb on all nodes
     </p><pre class="screen">
       onnode all pidof ctdbd
@@ -84,12 +84,12 @@
       directory, in parallel, on nodes 0, 2, 3 and 4.
     </p><pre class="screen">
       onnode -c -p 0,2-4 ./foo
-    </pre></div><div class="refsect1" title="ENVIRONMENT"><a name="id402500"></a><h2>ENVIRONMENT</h2><div class="variablelist"><dl><dt><span class="term"><code class="envar">CTDB_NODES_FILE</code></span></dt><dd><p>
+    </pre></div><div class="refsect1"><a name="idm264402936064"></a><h2>ENVIRONMENT</h2><div class="variablelist"><dl class="variablelist"><dt><span class="term"><code class="envar">CTDB_NODES_FILE</code></span></dt><dd><p>
 	    Name of alternative nodes file to use instead of the
             default.  See the discussion of
             <code class="filename">/etc/ctdb/nodes</code> in the FILES section
             for more details.
-	  </p></dd></dl></div></div><div class="refsect1" title="FILES"><a name="id402527"></a><h2>FILES</h2><div class="variablelist"><dl><dt><span class="term"><code class="filename">/etc/ctdb/nodes</code></span></dt><dd><p>
+	  </p></dd></dl></div></div><div class="refsect1"><a name="idm264402932624"></a><h2>FILES</h2><div class="variablelist"><dl class="variablelist"><dt><span class="term"><code class="filename">/etc/ctdb/nodes</code></span></dt><dd><p>
             Default file containing a list of each node's IP address
             or hostname.
 	  </p><p>
@@ -107,9 +107,9 @@
             something other than "ssh".  In this case the -t option is
             ignored.  For example, the administrator may choose to use
             use rsh instead of ssh.
-	  </p></dd></dl></div></div><div class="refsect1" title="SEE ALSO"><a name="id402595"></a><h2>SEE ALSO</h2><p>
+	  </p></dd></dl></div></div><div class="refsect1"><a name="idm264402923216"></a><h2>SEE ALSO</h2><p>
       ctdbd(1), ctdb(1), <a class="ulink" href="http://ctdb.samba.org/" target="_top">http://ctdb.samba.org/</a>
-    </p></div><div class="refsect1" title="COPYRIGHT/LICENSE"><a name="id402609"></a><h2>COPYRIGHT/LICENSE</h2><div class="literallayout"><p><br>
+    </p></div><div class="refsect1"><a name="idm264402921584"></a><h2>COPYRIGHT/LICENSE</h2><div class="literallayout"><p><br>
 Copyright (C) Andrew Tridgell 2007<br>
 Copyright (C) Ronnie sahlberg 2007<br>
 Copyright (C) Martin Schwenke 2008<br>
diff --git a/doc/ping_pong.1 b/doc/ping_pong.1
index 5af87e7..c8a57f0 100644
--- a/doc/ping_pong.1
+++ b/doc/ping_pong.1
@@ -1,13 +1,22 @@
 '\" t
 .\"     Title: ping_pong
 .\"    Author: [FIXME: author] [see http://docbook.sf.net/el/author]
-.\" Generator: DocBook XSL Stylesheets v1.75.2 <http://docbook.sf.net/>
-.\"      Date: 01/09/2013
+.\" Generator: DocBook XSL Stylesheets v1.78.1 <http://docbook.sf.net/>
+.\"      Date: 05/30/2013
 .\"    Manual:  
 .\"    Source:  
 .\"  Language: English
 .\"
-.TH "PING_PONG" "1" "01/09/2013" "" ""
+.TH "PING_PONG" "1" "05/30/2013" "" ""
+.\" -----------------------------------------------------------------
+.\" * Define some portability stuff
+.\" -----------------------------------------------------------------
+.\" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+.\" http://bugs.debian.org/507673
+.\" http://lists.gnu.org/archive/html/groff/2009-02/msg00013.html
+.\" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+.ie \n(.g .ds Aq \(aq
+.el       .ds Aq '
 .\" -----------------------------------------------------------------
 .\" * set default formatting
 .\" -----------------------------------------------------------------
@@ -91,7 +100,6 @@ Testing IO coherence
 .\}
 .SH "SEE ALSO"
 .PP
-
 \m[blue]\fB\%https://wiki.samba.org/index.php/Ping_pong\fR\m[], ctdb(1), ctdbd(1)
 .SH "COPYRIGHT/LICENSE"
 .sp
diff --git a/doc/ping_pong.1.html b/doc/ping_pong.1.html
index a14c88a..f158338 100644
--- a/doc/ping_pong.1.html
+++ b/doc/ping_pong.1.html
@@ -1,9 +1,9 @@
-<html><head><meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1"><title>ping_pong</title><meta name="generator" content="DocBook XSL Stylesheets V1.75.2"></head><body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF"><div class="refentry" title="ping_pong"><a name="ping_pong.1"></a><div class="titlepage"></div><div class="refnamediv"><h2>Name</h2><p>ping_pong — measures the ping-pong byte range lock latency</p></div><div class="refsynopsisdiv" title="Synopsis"><h2>Synopsis</h2><div class="cmdsynopsis"><p><code class="command">ping_pong [options] <file> <num_locks></code> </p></div><div class="cmdsynopsis"><p><code class="command">ping_pong</code>  [-r] [-w] [-m] [-c]</p></div></div><div class="refsect1" title="DESCRIPTION"><a name="id270212"></a><h2>DESCRIPTION</h2><p>
+<html><head><meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1"><title>ping_pong</title><meta name="generator" content="DocBook XSL Stylesheets V1.78.1"></head><body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF"><div class="refentry"><a name="ping_pong.1"></a><div class="titlepage"></div><div class="refnamediv"><h2>Name</h2><p>ping_pong — measures the ping-pong byte range lock latency</p></div><div class="refsynopsisdiv"><h2>Synopsis</h2><div class="cmdsynopsis"><p><code class="command">ping_pong [options] <file> <num_locks></code> </p></div><div class="cmdsynopsis"><p><code class="command">ping_pong</code>  [-r] [-w] [-m] [-c]</p></div></div><div class="refsect1"><a name="idm264401738896"></a><h2>DESCRIPTION</h2><p>
       This measures the ping-pong byte range lock latency. It is
       especially useful on a cluster of nodes sharing a common lock
       manager as it will give some indication of the lock managers
       performance under stress.
-    </p></div><div class="refsect1" title="OPTIONS"><a name="id270224"></a><h2>OPTIONS</h2><div class="variablelist"><dl><dt><span class="term">-r</span></dt><dd><p>
+    </p></div><div class="refsect1"><a name="idm264401737536"></a><h2>OPTIONS</h2><div class="variablelist"><dl class="variablelist"><dt><span class="term">-r</span></dt><dd><p>
 	    do reads
 	  </p></dd><dt><span class="term">-w</span></dt><dd><p>
 	    do writes
@@ -11,7 +11,7 @@
 	    use mmap
 	  </p></dd><dt><span class="term">-c</span></dt><dd><p>
 	    validate the locks
-	  </p></dd></dl></div></div><div class="refsect1" title="EXAMPLES"><a name="id270284"></a><h2>EXAMPLES</h2><p>
+	  </p></dd></dl></div></div><div class="refsect1"><a name="idm264401881872"></a><h2>EXAMPLES</h2><p>
       Testing lock coherence
     </p><pre class="screen">
       ping_pong test.dat N
@@ -23,9 +23,9 @@
       Testing IO coherence
     </p><pre class="screen">
       ping_pong -rw test.dat N
-    </pre></div><div class="refsect1" title="SEE ALSO"><a name="id270318"></a><h2>SEE ALSO</h2><p>
+    </pre></div><div class="refsect1"><a name="idm264401839360"></a><h2>SEE ALSO</h2><p>
       <a class="ulink" href="https://wiki.samba.org/index.php/Ping_pong" target="_top">https://wiki.samba.org/index.php/Ping_pong</a>, ctdb(1), ctdbd(1)
-    </p></div><div class="refsect1" title="COPYRIGHT/LICENSE"><a name="id270332"></a><h2>COPYRIGHT/LICENSE</h2><div class="literallayout"><p><br>
+    </p></div><div class="refsect1"><a name="idm264401837760"></a><h2>COPYRIGHT/LICENSE</h2><div class="literallayout"><p><br>
 Copyright (C) Andrew Tridgell 2002<br>
 <br>
 This program is free software; you can redistribute it and/or modify<br>
diff --git a/include/ctdb_client.h b/include/ctdb_client.h
index 9f0589f..8739923 100644
--- a/include/ctdb_client.h
+++ b/include/ctdb_client.h
@@ -100,7 +100,6 @@ int ctdb_ip_to_nodeid(struct ctdb_context *ctdb, const char *nodeip);
   start the ctdb protocol
 */
 int ctdb_start(struct ctdb_context *ctdb);
-int ctdb_start_daemon(struct ctdb_context *ctdb, bool do_fork, bool use_syslog, const char *public_address_list);
 
 /*
   attach to a ctdb database
@@ -296,6 +295,11 @@ int ctdb_ctrl_process_exists(struct ctdb_context *ctdb, uint32_t destnode, pid_t
 
 int ctdb_ctrl_ping(struct ctdb_context *ctdb, uint32_t destnode);
 
+int ctdb_ctrl_get_runstate(struct ctdb_context *ctdb, 
+			   struct timeval timeout, 
+			   uint32_t destnode,
+			   uint32_t *runstate);
+
 int ctdb_ctrl_get_config(struct ctdb_context *ctdb);
 
 int ctdb_ctrl_get_debuglevel(struct ctdb_context *ctdb, uint32_t destnode, int32_t *level);
@@ -507,6 +511,11 @@ int ctdb_ctrl_setreclock(struct ctdb_context *ctdb,
 	const char *reclock);
 
 
+uint32_t *list_of_nodes(struct ctdb_context *ctdb,
+			struct ctdb_node_map *node_map,
+			TALLOC_CTX *mem_ctx,
+			uint32_t mask,
+			int exclude_pnn);
 uint32_t *list_of_connected_nodes(struct ctdb_context *ctdb,
 				struct ctdb_node_map *node_map,
 				TALLOC_CTX *mem_ctx,
diff --git a/include/ctdb_private.h b/include/ctdb_private.h
index 5b519fb..eadd963 100644
--- a/include/ctdb_private.h
+++ b/include/ctdb_private.h
@@ -135,7 +135,7 @@ struct ctdb_tunable {
 	uint32_t db_record_size_warn;
 	uint32_t db_size_warn;
 	uint32_t pulldb_preallocation_size;
-	uint32_t no_ip_takeover_on_disabled;
+	uint32_t no_ip_host_on_all_disabled;
 	uint32_t deadlock_timeout;
 	uint32_t samba3_hack;
 };
@@ -286,10 +286,15 @@ struct ctdb_upcalls {
 
 /* list of message handlers - needs to be changed to a more efficient data
    structure so we can find a message handler given a srvid quickly */
-struct ctdb_message_list {
+struct ctdb_message_list_header {
+	struct ctdb_message_list_header *next, *prev;
 	struct ctdb_context *ctdb;
-	struct ctdb_message_list *next, *prev;
 	uint64_t srvid;
+	struct ctdb_message_list *m;
+};
+struct ctdb_message_list {
+	struct ctdb_message_list *next, *prev;
+	struct ctdb_message_list_header *h;
 	ctdb_msg_fn_t message_handler;
 	void *message_private;
 };
@@ -431,6 +436,20 @@ struct ctdb_write_record {
 
 enum ctdb_freeze_mode {CTDB_FREEZE_NONE, CTDB_FREEZE_PENDING, CTDB_FREEZE_FROZEN};
 
+enum ctdb_runstate {
+	CTDB_RUNSTATE_UNKNOWN,
+	CTDB_RUNSTATE_INIT,
+	CTDB_RUNSTATE_SETUP,
+	CTDB_RUNSTATE_FIRST_RECOVERY,
+	CTDB_RUNSTATE_STARTUP,
+	CTDB_RUNSTATE_RUNNING,
+	CTDB_RUNSTATE_SHUTDOWN,
+};
+
+const char *runstate_to_string(enum ctdb_runstate runstate);
+enum ctdb_runstate runstate_from_string(const char *label);
+void ctdb_set_runstate(struct ctdb_context *ctdb, enum ctdb_runstate runstate);
+
 #define CTDB_MONITORING_ACTIVE		0
 #define CTDB_MONITORING_DISABLED	1
 
@@ -478,7 +497,8 @@ struct ctdb_context {
 	const struct ctdb_upcalls *upcalls; /* transport upcalls */
 	void *private_data; /* private to transport */
 	struct ctdb_db_context *db_list;
-	struct ctdb_message_list *message_list;
+	struct ctdb_message_list_header *message_list_header;
+	struct tdb_context *message_list_indexdb;
 	struct ctdb_daemon_data daemon;
 	struct ctdb_statistics statistics;
 	struct ctdb_statistics statistics_current;
@@ -494,13 +514,12 @@ struct ctdb_context {
 	bool do_setsched;
 	void *saved_scheduler_param;
 	const char *event_script_dir;
-	const char *debug_hung_script;
 	const char *notification_script;
 	const char *default_public_interface;
 	pid_t ctdbd_pid;
 	pid_t recoverd_pid;
 	pid_t syslogd_pid;
-	bool done_startup;
+	enum ctdb_runstate runstate;
 	struct ctdb_monitor_state *monitor;
 	struct ctdb_log_state *log;
 	int start_as_disabled;
@@ -539,7 +558,6 @@ struct ctdb_context {
 
 	const char *public_addresses_file;
 	struct trbt_tree *child_processes; 
-	TALLOC_CTX *debug_hung_script_ctx;
 
 	/* Used for locking record/db/alldb */
 	int lock_num_current;
@@ -756,7 +774,9 @@ struct ctdb_call_state *ctdb_call_local_send(struct ctdb_db_context *ctdb_db,
 					     TDB_DATA *data);
 
 
-int ctdbd_start(struct ctdb_context *ctdb);
+int ctdb_start_daemon(struct ctdb_context *ctdb, bool do_fork,
+		      bool use_syslog,
+		      const char *public_address_list);
 struct ctdb_call_state *ctdbd_call_send(struct ctdb_db_context *ctdb_db, struct ctdb_call *call);
 int ctdbd_call_recv(struct ctdb_call_state *state, struct ctdb_call *call);
 
@@ -1011,11 +1031,13 @@ int32_t ctdb_control_traverse_start_ext(struct ctdb_context *ctdb,
 int32_t ctdb_control_traverse_start(struct ctdb_context *ctdb, TDB_DATA indata, 
 				    TDB_DATA *outdata, uint32_t srcnode, uint32_t client_id);
 int32_t ctdb_control_traverse_all(struct ctdb_context *ctdb, TDB_DATA data, TDB_DATA *outdata);
+int32_t ctdb_control_traverse_all_ext(struct ctdb_context *ctdb, TDB_DATA data, TDB_DATA *outdata);
 int32_t ctdb_control_traverse_data(struct ctdb_context *ctdb, TDB_DATA data, TDB_DATA *outdata);
 int32_t ctdb_control_traverse_kill(struct ctdb_context *ctdb, TDB_DATA indata, 
 				    TDB_DATA *outdata, uint32_t srcnode);
 
 int ctdb_dispatch_message(struct ctdb_context *ctdb, uint64_t srvid, TDB_DATA data);
+bool ctdb_check_message_handler(struct ctdb_context *ctdb, uint64_t srvid);
 
 int daemon_register_message_handler(struct ctdb_context *ctdb, uint32_t client_id, uint64_t srvid);
 int ctdb_deregister_message_handler(struct ctdb_context *ctdb, uint64_t srvid, void *private_data);
@@ -1036,7 +1058,6 @@ struct ctdb_rec_data *ctdb_marshall_loop_next(struct ctdb_marshall_buffer *m, st
 
 int32_t ctdb_control_pull_db(struct ctdb_context *ctdb, TDB_DATA indata, TDB_DATA *outdata);
 int32_t ctdb_control_push_db(struct ctdb_context *ctdb, TDB_DATA indata);
-int32_t ctdb_control_set_dmaster(struct ctdb_context *ctdb, TDB_DATA indata);
 
 int32_t ctdb_control_set_recmode(struct ctdb_context *ctdb, 
 				 struct ctdb_req_control *c,
@@ -1074,6 +1095,9 @@ void ctdb_restore_scheduler(struct ctdb_context *ctdb);
 
 struct tevent_signal *ctdb_init_sigchld(struct ctdb_context *ctdb);
 pid_t ctdb_fork(struct ctdb_context *ctdb);
+pid_t ctdb_fork_no_free_ringbuffer(struct ctdb_context *ctdb);
+void ctdb_set_child_info(TALLOC_CTX *mem_ctx, const char *child_name_fmt, ...);
+bool ctdb_is_child_process(void);
 int ctdb_kill(struct ctdb_context *ctdb, pid_t pid, int signum);
 
 int32_t ctdb_control_takeover_ip(struct ctdb_context *ctdb, 
@@ -1092,6 +1116,9 @@ int32_t ctdb_control_release_ipv4(struct ctdb_context *ctdb,
 				 struct ctdb_req_control *c,
 				 TDB_DATA indata, 
 				 bool *async_reply);
+int32_t ctdb_control_ipreallocated(struct ctdb_context *ctdb, 
+				 struct ctdb_req_control *c,
+				 bool *async_reply);
 int32_t ctdb_control_start_recovery(struct ctdb_context *ctdb, 
 				 struct ctdb_req_control *c,
 				 bool *async_reply);
@@ -1204,7 +1231,6 @@ int ctdb_set_single_public_ip(struct ctdb_context *ctdb,
 			      const char *ip);
 int ctdb_set_event_script(struct ctdb_context *ctdb, const char *script);
 int ctdb_set_event_script_dir(struct ctdb_context *ctdb, const char *script_dir);
-int ctdb_set_debug_hung_script(struct ctdb_context *ctdb, const char *script);
 int ctdb_set_notification_script(struct ctdb_context *ctdb, const char *script);
 void lcp2_forcerebalance(struct ctdb_context *ctdb, uint32_t pnn);
 int ctdb_takeover_run(struct ctdb_context *ctdb, struct ctdb_node_map *nodemap, client_async_callback fail_callback, void *callback_data);
@@ -1244,6 +1270,7 @@ int32_t ctdb_control_get_tunable(struct ctdb_context *ctdb, TDB_DATA indata,
 int32_t ctdb_control_set_tunable(struct ctdb_context *ctdb, TDB_DATA indata);
 int32_t ctdb_control_list_tunables(struct ctdb_context *ctdb, TDB_DATA *outdata);
 int32_t ctdb_control_try_delete_records(struct ctdb_context *ctdb, TDB_DATA indata, TDB_DATA *outdata);
+int32_t ctdb_control_receive_records(struct ctdb_context *ctdb, TDB_DATA indata, TDB_DATA *outdata);
 int32_t ctdb_control_add_public_address(struct ctdb_context *ctdb, TDB_DATA indata);
 int32_t ctdb_control_del_public_address(struct ctdb_context *ctdb, TDB_DATA indata);
 
@@ -1393,6 +1420,7 @@ int32_t ctdb_control_set_recmaster(struct ctdb_context *ctdb, uint32_t opcode, T
 
 extern int script_log_level;
 extern bool fast_start;
+extern const char *ctdbd_pidfile;
 
 int32_t ctdb_control_get_event_script_status(struct ctdb_context *ctdb,
 					     uint32_t call_type,
@@ -1401,7 +1429,7 @@ int32_t ctdb_control_get_event_script_status(struct ctdb_context *ctdb,
 int ctdb_log_event_script_output(struct ctdb_context *ctdb, char *str, uint16_t len);
 int ctdb_ctrl_report_recd_lock_latency(struct ctdb_context *ctdb, struct timeval timeout, double latency);
 
-int32_t ctdb_control_stop_node(struct ctdb_context *ctdb, struct ctdb_req_control *c, bool *async_reply);
+int32_t ctdb_control_stop_node(struct ctdb_context *ctdb);
 int32_t ctdb_control_continue_node(struct ctdb_context *ctdb);
 
 void ctdb_stop_vacuuming(struct ctdb_context *ctdb);
@@ -1435,7 +1463,7 @@ void ctdb_collect_log(struct ctdb_context *ctdb, struct ctdb_get_log_addr *log_a
 void ctdb_clear_log(struct ctdb_context *ctdb);
 int32_t ctdb_control_get_log(struct ctdb_context *ctdb, TDB_DATA addr);
 int32_t ctdb_control_clear_log(struct ctdb_context *ctdb);
-
+void ctdb_log_ringbuffer_free(void);
 
 struct ctdb_log_state *ctdb_fork_with_logging(TALLOC_CTX *mem_ctx,
 					      struct ctdb_context *ctdb,
@@ -1550,8 +1578,6 @@ int ctdb_start_monitoring_interfaces(struct ctdb_context *ctdb);
 /* from server/ctdb_lock.c */
 struct lock_request;
 
-int ctdb_lockall_prio(struct ctdb_context *ctdb, uint32_t priority);
-int ctdb_unlockall_prio(struct ctdb_context *ctdb, uint32_t priority);
 int ctdb_lockall_mark_prio(struct ctdb_context *ctdb, uint32_t priority);
 int ctdb_lockall_unmark_prio(struct ctdb_context *ctdb, uint32_t priority);
 
diff --git a/include/ctdb_protocol.h b/include/ctdb_protocol.h
index cc3ea3f..10f643b 100644
--- a/include/ctdb_protocol.h
+++ b/include/ctdb_protocol.h
@@ -240,7 +240,7 @@ enum ctdb_eventscript_call {
 	CTDB_EVENT_RECOVERED,		/* CTDB recovery finished: no args. */
 	CTDB_EVENT_TAKE_IP,		/* IP taken: interface, IP address, netmask bits. */
 	CTDB_EVENT_RELEASE_IP,		/* IP released: interface, IP address, netmask bits. */
-	CTDB_EVENT_STOPPED,		/* This node is stopped: no args. */
+	CTDB_EVENT_STOPPED,		/* Deprecated, do not use. */
 	CTDB_EVENT_MONITOR,		/* Please check if service is healthy: no args. */
 	CTDB_EVENT_STATUS,		/* Report service status: no args. */
 	CTDB_EVENT_SHUTDOWN,		/* CTDB shutting down: no args. */
@@ -283,7 +283,7 @@ enum ctdb_controls {CTDB_CONTROL_PROCESS_EXISTS          = 0,
 		    CTDB_CONTROL_SET_DEBUG               = 8,
 		    CTDB_CONTROL_GET_DBMAP               = 9,
 		    CTDB_CONTROL_GET_NODEMAPv4           = 10, /* obsolete */
-		    CTDB_CONTROL_SET_DMASTER             = 11,
+		    CTDB_CONTROL_SET_DMASTER             = 11, /* obsolete */
 		    /* #12 removed */
 		    CTDB_CONTROL_PULL_DB                 = 13,
 		    CTDB_CONTROL_PUSH_DB                 = 14,
@@ -402,6 +402,10 @@ enum ctdb_controls {CTDB_CONTROL_PROCESS_EXISTS          = 0,
 		    CTDB_CONTROL_GET_DB_STATISTICS	 = 132,
 		    CTDB_CONTROL_SET_DB_STICKY		 = 133,
 		    CTDB_CONTROL_RELOAD_PUBLIC_IPS	 = 134,
+		    CTDB_CONTROL_TRAVERSE_ALL_EXT	 = 135,
+		    CTDB_CONTROL_RECEIVE_RECORDS	 = 136,
+		    CTDB_CONTROL_IPREALLOCATED		 = 137,
+		    CTDB_CONTROL_GET_RUNSTATE		 = 138,
 };
 
 /*
@@ -530,6 +534,10 @@ struct ctdb_ltdb_header {
 #define CTDB_REC_RO_HAVE_READONLY		0x02000000
 #define CTDB_REC_RO_REVOKING_READONLY		0x04000000
 #define CTDB_REC_RO_REVOKE_COMPLETE		0x08000000
+#define CTDB_REC_RO_FLAGS			(CTDB_REC_RO_HAVE_DELEGATIONS|\
+						 CTDB_REC_RO_HAVE_READONLY|\
+						 CTDB_REC_RO_REVOKING_READONLY|\
+						 CTDB_REC_RO_REVOKE_COMPLETE)
 	uint32_t flags;
 };
 
@@ -577,9 +585,6 @@ struct ctdb_node_map {
 #define NODE_FLAGS_DISABLED		(NODE_FLAGS_UNHEALTHY|NODE_FLAGS_PERMANENTLY_DISABLED)
 #define NODE_FLAGS_INACTIVE		(NODE_FLAGS_DELETED|NODE_FLAGS_DISCONNECTED|NODE_FLAGS_BANNED|NODE_FLAGS_STOPPED)
 
-#define NODE_FLAGS_NOIPTAKEOVER		0x01000000 /* this node can takeover any new ip addresses, this flag is ONLY valid within the recovery daemon */
-
-
 /*
  * Node capabilities
  */
diff --git a/include/version.h b/include/ctdb_version.h
similarity index 64%
rename from include/version.h
rename to include/ctdb_version.h
index 5cc0472..a867913 100644
--- a/include/version.h
+++ b/include/ctdb_version.h
@@ -1,4 +1,4 @@
 /* This file is auto-genrated by packaging/mkversion.sh */
 
-#define CTDB_VERSION_STRING "2.1"
+#define CTDB_VERSION_STRING "2.2"
 
diff --git a/include/includes.h b/include/includes.h
index e0ce06b..3747198 100644
--- a/include/includes.h
+++ b/include/includes.h
@@ -58,6 +58,7 @@ double timeval_elapsed(struct timeval *tv);
 double timeval_delta(struct timeval *tv2, struct timeval *tv);
 char **file_lines_load(const char *fname, int *numlines, TALLOC_CTX *mem_ctx);
 char *hex_encode_talloc(TALLOC_CTX *mem_ctx, const unsigned char *buff_in, size_t len);
+uint8_t *hex_decode_talloc(TALLOC_CTX *mem_ctx, const char *hex_in, size_t *len);
 _PUBLIC_ const char **str_list_add(const char **list, const char *s);
 _PUBLIC_ int set_blocking(int fd, bool set);
 
diff --git a/lib/replace/Makefile.in b/lib/replace/Makefile.in
deleted file mode 100644
index 65f8125..0000000
--- a/lib/replace/Makefile.in
+++ /dev/null
@@ -1,70 +0,0 @@
-#!gmake
-#
-CC = @CC@
-prefix = @prefix@
-exec_prefix = @exec_prefix@
-bindir = @bindir@
-includedir = @includedir@
-libdir = @libdir@
-VPATH = @libreplacedir@
-srcdir = @srcdir@
-builddir = @builddir@
-sharedbuilddir = @sharedbuilddir@
-INSTALLCMD = @INSTALL@
-LIBS = @LIBS@
-
-.PHONY: test all showflags install installcheck clean distclean realdistclean
-
-CFLAGS=-I. @CFLAGS@
-LDFLAGS=@LDFLAGS@
-
-OBJS = @LIBREPLACEOBJ@
-
-all: showflags libreplace.a testsuite
-
-showflags:
-	@echo 'libreplace will be compiled with flags:'
-	@echo '  CC     = $(CC)'
-	@echo '  CFLAGS = $(CFLAGS)'
-	@echo '  LDFLAGS= $(LDFLAGS)'
-	@echo '  LIBS   = $(LIBS)'
-
-install: all
-	${INSTALLCMD} -d $(libdir)
-	${INSTALLCMD} -m 644 libreplace.a $(libdir)
-
-shared-build: all
-	${INSTALLCMD} -d $(sharedbuilddir)/include
-	${INSTALLCMD} -m 644 replace.h $(sharedbuilddir)/include
-	${INSTALLCMD} -d $(sharedbuilddir)/lib
-	${INSTALLCMD} -m 644 libreplace.a $(sharedbuilddir)/lib
-
-libreplace.a: $(OBJS)
-	ar -rcsv $@ $(OBJS)
-
-test: all
-	./testsuite
-
-installcheck: install test
-
-TEST_OBJS = test/main.o test/testsuite.o test/os2_delete.o test/strptime.o test/getifaddrs.o
-
-testsuite: libreplace.a $(TEST_OBJS)
-	$(CC) -o testsuite $(TEST_OBJS) -L. -lreplace $(LDFLAGS) $(LIBS)
-
-.c.o:
-	@echo Compiling $*.c
-	@mkdir -p `dirname $@`
-	@$(CC) $(CFLAGS) -c $< -o $@
-
-clean:
-	rm -f *.o test/*.o *.a testsuite
-	rm -f testfile.dat
-
-distclean: clean
-	rm -f *~ */*~
-	rm -f config.log config.status config.h config.cache
-	rm -f Makefile
-
-realdistclean: distclean
-	rm -f configure config.h.in
diff --git a/lib/replace/README b/lib/replace/README
index bf4e67f..9dd4f73 100644
--- a/lib/replace/README
+++ b/lib/replace/README
@@ -49,7 +49,6 @@ pread
 pwrite
 chown
 lchown
-getpass
 readline (the library)
 inet_ntoa
 inet_ntop
@@ -72,6 +71,8 @@ link
 readlink
 symlink
 realpath
+poll
+setproctitle
 
 Types:
 bool
@@ -80,6 +81,8 @@ uint{8,16,32,64}_t
 int{8,16,32,64}_t
 intptr_t
 sig_atomic_t
+blksize_t
+blkcnt_t
 
 Constants:
 PATH_NAME_MAX
diff --git a/lib/replace/aclocal.m4 b/lib/replace/aclocal.m4
deleted file mode 100644
index 5605e47..0000000
--- a/lib/replace/aclocal.m4
+++ /dev/null
@@ -1 +0,0 @@
-m4_include(libreplace.m4)
diff --git a/lib/replace/autogen-autotools.sh b/lib/replace/autogen-autotools.sh
deleted file mode 100755
index d46a427..0000000
--- a/lib/replace/autogen-autotools.sh
+++ /dev/null
@@ -1,13 +0,0 @@
-#!/bin/sh
-
-rm -rf autom4te.cache
-rm -f configure config.h.in
-
-autoheader || exit 1
-autoconf || exit 1
-
-rm -rf autom4te.cache
-
-echo "Now run ./configure and then make."
-exit 0
-
diff --git a/lib/replace/autogen.sh b/lib/replace/autogen.sh
deleted file mode 100755
index d46a427..0000000
--- a/lib/replace/autogen.sh
+++ /dev/null
@@ -1,13 +0,0 @@
-#!/bin/sh
-
-rm -rf autom4te.cache
-rm -f configure config.h.in
-
-autoheader || exit 1
-autoconf || exit 1
-
-rm -rf autom4te.cache
-
-echo "Now run ./configure and then make."
-exit 0
-
diff --git a/lib/replace/build_macros.m4 b/lib/replace/build_macros.m4
deleted file mode 100644
index c036668..0000000
--- a/lib/replace/build_macros.m4
+++ /dev/null
@@ -1,14 +0,0 @@
-AC_DEFUN(BUILD_WITH_SHARED_BUILD_DIR,
-  [ AC_ARG_WITH([shared-build-dir],
-                [AC_HELP_STRING([--with-shared-build-dir=DIR],
-                                [temporary build directory where libraries are installed [$srcdir/sharedbuild]])])
-
-    sharedbuilddir="$srcdir/sharedbuild"
-    if test x"$with_shared_build_dir" != x; then
-        sharedbuilddir=$with_shared_build_dir
-        CFLAGS="$CFLAGS -I$with_shared_build_dir/include"
-        LDFLAGS="$LDFLAGS -L$with_shared_build_dir/lib"
-    fi
-    AC_SUBST(sharedbuilddir)
-  ])
-
diff --git a/lib/replace/config.guess b/lib/replace/config.guess
deleted file mode 100755
index da83314..0000000
--- a/lib/replace/config.guess
+++ /dev/null
@@ -1,1561 +0,0 @@
-#! /bin/sh
-# Attempt to guess a canonical system name.
-#   Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999,
-#   2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008
-#   Free Software Foundation, Inc.
-
-timestamp='2009-04-27'
-
-# This file 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., 51 Franklin Street - Fifth Floor, Boston, MA
-# 02110-1301, USA.
-#
-# As a special exception to the GNU General Public License, if you
-# distribute this file as part of a program that contains a
-# configuration script generated by Autoconf, you may include it under
-# the same distribution terms that you use for the rest of that program.
-
-
-# Originally written by Per Bothner <per at bothner.com>.
-# Please send patches to <config-patches at gnu.org>.  Submit a context
-# diff and a properly formatted ChangeLog entry.
-#
-# This script attempts to guess a canonical system name similar to
-# config.sub.  If it succeeds, it prints the system name on stdout, and
-# exits with 0.  Otherwise, it exits with 1.
-#
-# The plan is that this can be called by configure scripts if you
-# don't specify an explicit build system type.
-
-me=`echo "$0" | sed -e 's,.*/,,'`
-
-usage="\
-Usage: $0 [OPTION]
-
-Output the configuration name of the system \`$me' is run on.
-
-Operation modes:
-  -h, --help         print this help, then exit
-  -t, --time-stamp   print date of last modification, then exit
-  -v, --version      print version number, then exit
-
-Report bugs and patches to <config-patches at gnu.org>."
-
-version="\
-GNU config.guess ($timestamp)
-
-Originally written by Per Bothner.
-Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001,
-2002, 2003, 2004, 2005, 2006, 2007, 2008 Free Software Foundation, Inc.
-
-This is free software; see the source for copying conditions.  There is NO
-warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE."
-
-help="
-Try \`$me --help' for more information."
-
-# Parse command line
-while test $# -gt 0 ; do
-  case $1 in
-    --time-stamp | --time* | -t )
-       echo "$timestamp" ; exit ;;
-    --version | -v )
-       echo "$version" ; exit ;;
-    --help | --h* | -h )
-       echo "$usage"; exit ;;
-    -- )     # Stop option processing
-       shift; break ;;
-    - )	# Use stdin as input.
-       break ;;
-    -* )
-       echo "$me: invalid option $1$help" >&2
-       exit 1 ;;
-    * )
-       break ;;
-  esac
-done
-
-if test $# != 0; then
-  echo "$me: too many arguments$help" >&2
-  exit 1
-fi
-
-trap 'exit 1' 1 2 15
-
-# CC_FOR_BUILD -- compiler used by this script. Note that the use of a
-# compiler to aid in system detection is discouraged as it requires
-# temporary files to be created and, as you can see below, it is a
-# headache to deal with in a portable fashion.
-
-# Historically, `CC_FOR_BUILD' used to be named `HOST_CC'. We still
-# use `HOST_CC' if defined, but it is deprecated.
-
-# Portable tmp directory creation inspired by the Autoconf team.
-
-set_cc_for_build='
-trap "exitcode=\$?; (rm -f \$tmpfiles 2>/dev/null; rmdir \$tmp 2>/dev/null) && exit \$exitcode" 0 ;
-trap "rm -f \$tmpfiles 2>/dev/null; rmdir \$tmp 2>/dev/null; exit 1" 1 2 13 15 ;
-: ${TMPDIR=/tmp} ;
- { tmp=`(umask 077 && mktemp -d "$TMPDIR/cgXXXXXX") 2>/dev/null` && test -n "$tmp" && test -d "$tmp" ; } ||
- { test -n "$RANDOM" && tmp=$TMPDIR/cg$$-$RANDOM && (umask 077 && mkdir $tmp) ; } ||
- { tmp=$TMPDIR/cg-$$ && (umask 077 && mkdir $tmp) && echo "Warning: creating insecure temp directory" >&2 ; } ||
- { echo "$me: cannot create a temporary directory in $TMPDIR" >&2 ; exit 1 ; } ;
-dummy=$tmp/dummy ;
-tmpfiles="$dummy.c $dummy.o $dummy.rel $dummy" ;
-case $CC_FOR_BUILD,$HOST_CC,$CC in
- ,,)    echo "int x;" > $dummy.c ;
-	for c in cc gcc c89 c99 ; do
-	  if ($c -c -o $dummy.o $dummy.c) >/dev/null 2>&1 ; then
-	     CC_FOR_BUILD="$c"; break ;
-	  fi ;
-	done ;
-	if test x"$CC_FOR_BUILD" = x ; then
-	  CC_FOR_BUILD=no_compiler_found ;
-	fi
-	;;
- ,,*)   CC_FOR_BUILD=$CC ;;
- ,*,*)  CC_FOR_BUILD=$HOST_CC ;;
-esac ; set_cc_for_build= ;'
-
-# This is needed to find uname on a Pyramid OSx when run in the BSD universe.
-# (ghazi at noc.rutgers.edu 1994-08-24)
-if (test -f /.attbin/uname) >/dev/null 2>&1 ; then
-	PATH=$PATH:/.attbin ; export PATH
-fi
-
-UNAME_MACHINE=`(uname -m) 2>/dev/null` || UNAME_MACHINE=unknown
-UNAME_RELEASE=`(uname -r) 2>/dev/null` || UNAME_RELEASE=unknown
-UNAME_SYSTEM=`(uname -s) 2>/dev/null`  || UNAME_SYSTEM=unknown
-UNAME_VERSION=`(uname -v) 2>/dev/null` || UNAME_VERSION=unknown
-
-# Note: order is significant - the case branches are not exclusive.
-
-case "${UNAME_MACHINE}:${UNAME_SYSTEM}:${UNAME_RELEASE}:${UNAME_VERSION}" in
-    *:NetBSD:*:*)
-	# NetBSD (nbsd) targets should (where applicable) match one or
-	# more of the tupples: *-*-netbsdelf*, *-*-netbsdaout*,
-	# *-*-netbsdecoff* and *-*-netbsd*.  For targets that recently
-	# switched to ELF, *-*-netbsd* would select the old
-	# object file format.  This provides both forward
-	# compatibility and a consistent mechanism for selecting the
-	# object file format.
-	#
-	# Note: NetBSD doesn't particularly care about the vendor
-	# portion of the name.  We always set it to "unknown".
-	sysctl="sysctl -n hw.machine_arch"
-	UNAME_MACHINE_ARCH=`(/sbin/$sysctl 2>/dev/null || \
-	    /usr/sbin/$sysctl 2>/dev/null || echo unknown)`
-	case "${UNAME_MACHINE_ARCH}" in
-	    armeb) machine=armeb-unknown ;;
-	    arm*) machine=arm-unknown ;;
-	    sh3el) machine=shl-unknown ;;
-	    sh3eb) machine=sh-unknown ;;
-	    sh5el) machine=sh5le-unknown ;;
-	    *) machine=${UNAME_MACHINE_ARCH}-unknown ;;
-	esac
-	# The Operating System including object format, if it has switched
-	# to ELF recently, or will in the future.
-	case "${UNAME_MACHINE_ARCH}" in
-	    arm*|i386|m68k|ns32k|sh3*|sparc|vax)
-		eval $set_cc_for_build
-		if echo __ELF__ | $CC_FOR_BUILD -E - 2>/dev/null \
-			| grep __ELF__ >/dev/null
-		then
-		    # Once all utilities can be ECOFF (netbsdecoff) or a.out (netbsdaout).
-		    # Return netbsd for either.  FIX?
-		    os=netbsd
-		else
-		    os=netbsdelf
-		fi
-		;;
-	    *)
-	        os=netbsd
-		;;
-	esac
-	# The OS release
-	# Debian GNU/NetBSD machines have a different userland, and
-	# thus, need a distinct triplet. However, they do not need
-	# kernel version information, so it can be replaced with a
-	# suitable tag, in the style of linux-gnu.
-	case "${UNAME_VERSION}" in
-	    Debian*)
-		release='-gnu'
-		;;
-	    *)
-		release=`echo ${UNAME_RELEASE}|sed -e 's/[-_].*/\./'`
-		;;
-	esac
-	# Since CPU_TYPE-MANUFACTURER-KERNEL-OPERATING_SYSTEM:
-	# contains redundant information, the shorter form:
-	# CPU_TYPE-MANUFACTURER-OPERATING_SYSTEM is used.
-	echo "${machine}-${os}${release}"
-	exit ;;
-    *:OpenBSD:*:*)
-	UNAME_MACHINE_ARCH=`arch | sed 's/OpenBSD.//'`
-	echo ${UNAME_MACHINE_ARCH}-unknown-openbsd${UNAME_RELEASE}
-	exit ;;
-    *:ekkoBSD:*:*)
-	echo ${UNAME_MACHINE}-unknown-ekkobsd${UNAME_RELEASE}
-	exit ;;
-    *:SolidBSD:*:*)
-	echo ${UNAME_MACHINE}-unknown-solidbsd${UNAME_RELEASE}
-	exit ;;
-    macppc:MirBSD:*:*)
-	echo powerpc-unknown-mirbsd${UNAME_RELEASE}
-	exit ;;
-    *:MirBSD:*:*)
-	echo ${UNAME_MACHINE}-unknown-mirbsd${UNAME_RELEASE}
-	exit ;;
-    alpha:OSF1:*:*)
-	case $UNAME_RELEASE in
-	*4.0)
-		UNAME_RELEASE=`/usr/sbin/sizer -v | awk '{print $3}'`
-		;;
-	*5.*)
-	        UNAME_RELEASE=`/usr/sbin/sizer -v | awk '{print $4}'`
-		;;
-	esac
-	# According to Compaq, /usr/sbin/psrinfo has been available on
-	# OSF/1 and Tru64 systems produced since 1995.  I hope that
-	# covers most systems running today.  This code pipes the CPU
-	# types through head -n 1, so we only detect the type of CPU 0.
-	ALPHA_CPU_TYPE=`/usr/sbin/psrinfo -v | sed -n -e 's/^  The alpha \(.*\) processor.*$/\1/p' | head -n 1`
-	case "$ALPHA_CPU_TYPE" in
-	    "EV4 (21064)")
-		UNAME_MACHINE="alpha" ;;
-	    "EV4.5 (21064)")
-		UNAME_MACHINE="alpha" ;;
-	    "LCA4 (21066/21068)")
-		UNAME_MACHINE="alpha" ;;
-	    "EV5 (21164)")
-		UNAME_MACHINE="alphaev5" ;;
-	    "EV5.6 (21164A)")
-		UNAME_MACHINE="alphaev56" ;;
-	    "EV5.6 (21164PC)")
-		UNAME_MACHINE="alphapca56" ;;
-	    "EV5.7 (21164PC)")
-		UNAME_MACHINE="alphapca57" ;;
-	    "EV6 (21264)")
-		UNAME_MACHINE="alphaev6" ;;
-	    "EV6.7 (21264A)")
-		UNAME_MACHINE="alphaev67" ;;
-	    "EV6.8CB (21264C)")
-		UNAME_MACHINE="alphaev68" ;;
-	    "EV6.8AL (21264B)")
-		UNAME_MACHINE="alphaev68" ;;
-	    "EV6.8CX (21264D)")
-		UNAME_MACHINE="alphaev68" ;;
-	    "EV6.9A (21264/EV69A)")
-		UNAME_MACHINE="alphaev69" ;;
-	    "EV7 (21364)")
-		UNAME_MACHINE="alphaev7" ;;
-	    "EV7.9 (21364A)")
-		UNAME_MACHINE="alphaev79" ;;
-	esac
-	# A Pn.n version is a patched version.
-	# A Vn.n version is a released version.
-	# A Tn.n version is a released field test version.
-	# A Xn.n version is an unreleased experimental baselevel.
-	# 1.2 uses "1.2" for uname -r.
-	echo ${UNAME_MACHINE}-dec-osf`echo ${UNAME_RELEASE} | sed -e 's/^[PVTX]//' | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz'`
-	exit ;;
-    Alpha\ *:Windows_NT*:*)
-	# How do we know it's Interix rather than the generic POSIX subsystem?
-	# Should we change UNAME_MACHINE based on the output of uname instead
-	# of the specific Alpha model?
-	echo alpha-pc-interix
-	exit ;;
-    21064:Windows_NT:50:3)
-	echo alpha-dec-winnt3.5
-	exit ;;
-    Amiga*:UNIX_System_V:4.0:*)
-	echo m68k-unknown-sysv4
-	exit ;;
-    *:[Aa]miga[Oo][Ss]:*:*)
-	echo ${UNAME_MACHINE}-unknown-amigaos
-	exit ;;
-    *:[Mm]orph[Oo][Ss]:*:*)
-	echo ${UNAME_MACHINE}-unknown-morphos
-	exit ;;
-    *:OS/390:*:*)
-	echo i370-ibm-openedition
-	exit ;;
-    *:z/VM:*:*)
-	echo s390-ibm-zvmoe
-	exit ;;
-    *:OS400:*:*)
-        echo powerpc-ibm-os400
-	exit ;;
-    arm:RISC*:1.[012]*:*|arm:riscix:1.[012]*:*)
-	echo arm-acorn-riscix${UNAME_RELEASE}
-	exit ;;
-    arm:riscos:*:*|arm:RISCOS:*:*)
-	echo arm-unknown-riscos
-	exit ;;
-    SR2?01:HI-UX/MPP:*:* | SR8000:HI-UX/MPP:*:*)
-	echo hppa1.1-hitachi-hiuxmpp
-	exit ;;
-    Pyramid*:OSx*:*:* | MIS*:OSx*:*:* | MIS*:SMP_DC-OSx*:*:*)
-	# akee at wpdis03.wpafb.af.mil (Earle F. Ake) contributed MIS and NILE.
-	if test "`(/bin/universe) 2>/dev/null`" = att ; then
-		echo pyramid-pyramid-sysv3
-	else
-		echo pyramid-pyramid-bsd
-	fi
-	exit ;;
-    NILE*:*:*:dcosx)
-	echo pyramid-pyramid-svr4
-	exit ;;
-    DRS?6000:unix:4.0:6*)
-	echo sparc-icl-nx6
-	exit ;;
-    DRS?6000:UNIX_SV:4.2*:7* | DRS?6000:isis:4.2*:7*)
-	case `/usr/bin/uname -p` in
-	    sparc) echo sparc-icl-nx7; exit ;;
-	esac ;;
-    s390x:SunOS:*:*)
-	echo ${UNAME_MACHINE}-ibm-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'`
-	exit ;;
-    sun4H:SunOS:5.*:*)
-	echo sparc-hal-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'`
-	exit ;;
-    sun4*:SunOS:5.*:* | tadpole*:SunOS:5.*:*)
-	echo sparc-sun-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'`
-	exit ;;
-    i86pc:SunOS:5.*:* | i86xen:SunOS:5.*:*)
-	eval $set_cc_for_build
-	SUN_ARCH="i386"
-	# If there is a compiler, see if it is configured for 64-bit objects.
-	# Note that the Sun cc does not turn __LP64__ into 1 like gcc does.
-	# This test works for both compilers.
-	if [ "$CC_FOR_BUILD" != 'no_compiler_found' ]; then
-	    if (echo '#ifdef __amd64'; echo IS_64BIT_ARCH; echo '#endif') | \
-		(CCOPTS= $CC_FOR_BUILD -E - 2>/dev/null) | \
-		grep IS_64BIT_ARCH >/dev/null
-	    then
-		SUN_ARCH="x86_64"
-	    fi
-	fi
-	echo ${SUN_ARCH}-pc-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'`
-	exit ;;
-    sun4*:SunOS:6*:*)
-	# According to config.sub, this is the proper way to canonicalize
-	# SunOS6.  Hard to guess exactly what SunOS6 will be like, but
-	# it's likely to be more like Solaris than SunOS4.
-	echo sparc-sun-solaris3`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'`
-	exit ;;
-    sun4*:SunOS:*:*)
-	case "`/usr/bin/arch -k`" in
-	    Series*|S4*)
-		UNAME_RELEASE=`uname -v`
-		;;
-	esac
-	# Japanese Language versions have a version number like `4.1.3-JL'.
-	echo sparc-sun-sunos`echo ${UNAME_RELEASE}|sed -e 's/-/_/'`
-	exit ;;
-    sun3*:SunOS:*:*)
-	echo m68k-sun-sunos${UNAME_RELEASE}
-	exit ;;
-    sun*:*:4.2BSD:*)
-	UNAME_RELEASE=`(sed 1q /etc/motd | awk '{print substr($5,1,3)}') 2>/dev/null`
-	test "x${UNAME_RELEASE}" = "x" && UNAME_RELEASE=3
-	case "`/bin/arch`" in
-	    sun3)
-		echo m68k-sun-sunos${UNAME_RELEASE}
-		;;
-	    sun4)
-		echo sparc-sun-sunos${UNAME_RELEASE}
-		;;
-	esac
-	exit ;;
-    aushp:SunOS:*:*)
-	echo sparc-auspex-sunos${UNAME_RELEASE}
-	exit ;;
-    # The situation for MiNT is a little confusing.  The machine name
-    # can be virtually everything (everything which is not
-    # "atarist" or "atariste" at least should have a processor
-    # > m68000).  The system name ranges from "MiNT" over "FreeMiNT"
-    # to the lowercase version "mint" (or "freemint").  Finally
-    # the system name "TOS" denotes a system which is actually not
-    # MiNT.  But MiNT is downward compatible to TOS, so this should
-    # be no problem.
-    atarist[e]:*MiNT:*:* | atarist[e]:*mint:*:* | atarist[e]:*TOS:*:*)
-        echo m68k-atari-mint${UNAME_RELEASE}
-	exit ;;
-    atari*:*MiNT:*:* | atari*:*mint:*:* | atarist[e]:*TOS:*:*)
-	echo m68k-atari-mint${UNAME_RELEASE}
-        exit ;;
-    *falcon*:*MiNT:*:* | *falcon*:*mint:*:* | *falcon*:*TOS:*:*)
-        echo m68k-atari-mint${UNAME_RELEASE}
-	exit ;;
-    milan*:*MiNT:*:* | milan*:*mint:*:* | *milan*:*TOS:*:*)
-        echo m68k-milan-mint${UNAME_RELEASE}
-        exit ;;
-    hades*:*MiNT:*:* | hades*:*mint:*:* | *hades*:*TOS:*:*)
-        echo m68k-hades-mint${UNAME_RELEASE}
-        exit ;;
-    *:*MiNT:*:* | *:*mint:*:* | *:*TOS:*:*)
-        echo m68k-unknown-mint${UNAME_RELEASE}
-        exit ;;
-    m68k:machten:*:*)
-	echo m68k-apple-machten${UNAME_RELEASE}
-	exit ;;
-    powerpc:machten:*:*)
-	echo powerpc-apple-machten${UNAME_RELEASE}
-	exit ;;
-    RISC*:Mach:*:*)
-	echo mips-dec-mach_bsd4.3
-	exit ;;
-    RISC*:ULTRIX:*:*)
-	echo mips-dec-ultrix${UNAME_RELEASE}
-	exit ;;
-    VAX*:ULTRIX*:*:*)
-	echo vax-dec-ultrix${UNAME_RELEASE}
-	exit ;;
-    2020:CLIX:*:* | 2430:CLIX:*:*)
-	echo clipper-intergraph-clix${UNAME_RELEASE}
-	exit ;;
-    mips:*:*:UMIPS | mips:*:*:RISCos)
-	eval $set_cc_for_build
-	sed 's/^	//' << EOF >$dummy.c
-#ifdef __cplusplus
-#include <stdio.h>  /* for printf() prototype */
-	int main (int argc, char *argv[]) {
-#else
-	int main (argc, argv) int argc; char *argv[]; {
-#endif
-	#if defined (host_mips) && defined (MIPSEB)
-	#if defined (SYSTYPE_SYSV)
-	  printf ("mips-mips-riscos%ssysv\n", argv[1]); exit (0);
-	#endif
-	#if defined (SYSTYPE_SVR4)
-	  printf ("mips-mips-riscos%ssvr4\n", argv[1]); exit (0);
-	#endif
-	#if defined (SYSTYPE_BSD43) || defined(SYSTYPE_BSD)
-	  printf ("mips-mips-riscos%sbsd\n", argv[1]); exit (0);
-	#endif
-	#endif
-	  exit (-1);
-	}
-EOF
-	$CC_FOR_BUILD -o $dummy $dummy.c &&
-	  dummyarg=`echo "${UNAME_RELEASE}" | sed -n 's/\([0-9]*\).*/\1/p'` &&
-	  SYSTEM_NAME=`$dummy $dummyarg` &&
-	    { echo "$SYSTEM_NAME"; exit; }
-	echo mips-mips-riscos${UNAME_RELEASE}
-	exit ;;
-    Motorola:PowerMAX_OS:*:*)
-	echo powerpc-motorola-powermax
-	exit ;;
-    Motorola:*:4.3:PL8-*)
-	echo powerpc-harris-powermax
-	exit ;;
-    Night_Hawk:*:*:PowerMAX_OS | Synergy:PowerMAX_OS:*:*)
-	echo powerpc-harris-powermax
-	exit ;;
-    Night_Hawk:Power_UNIX:*:*)
-	echo powerpc-harris-powerunix
-	exit ;;
-    m88k:CX/UX:7*:*)
-	echo m88k-harris-cxux7
-	exit ;;
-    m88k:*:4*:R4*)
-	echo m88k-motorola-sysv4
-	exit ;;
-    m88k:*:3*:R3*)
-	echo m88k-motorola-sysv3
-	exit ;;
-    AViiON:dgux:*:*)
-        # DG/UX returns AViiON for all architectures
-        UNAME_PROCESSOR=`/usr/bin/uname -p`
-	if [ $UNAME_PROCESSOR = mc88100 ] || [ $UNAME_PROCESSOR = mc88110 ]
-	then
-	    if [ ${TARGET_BINARY_INTERFACE}x = m88kdguxelfx ] || \
-	       [ ${TARGET_BINARY_INTERFACE}x = x ]
-	    then
-		echo m88k-dg-dgux${UNAME_RELEASE}
-	    else
-		echo m88k-dg-dguxbcs${UNAME_RELEASE}
-	    fi
-	else
-	    echo i586-dg-dgux${UNAME_RELEASE}
-	fi
- 	exit ;;
-    M88*:DolphinOS:*:*)	# DolphinOS (SVR3)
-	echo m88k-dolphin-sysv3
-	exit ;;
-    M88*:*:R3*:*)
-	# Delta 88k system running SVR3
-	echo m88k-motorola-sysv3
-	exit ;;
-    XD88*:*:*:*) # Tektronix XD88 system running UTekV (SVR3)
-	echo m88k-tektronix-sysv3
-	exit ;;
-    Tek43[0-9][0-9]:UTek:*:*) # Tektronix 4300 system running UTek (BSD)
-	echo m68k-tektronix-bsd
-	exit ;;
-    *:IRIX*:*:*)
-	echo mips-sgi-irix`echo ${UNAME_RELEASE}|sed -e 's/-/_/g'`
-	exit ;;
-    ????????:AIX?:[12].1:2)   # AIX 2.2.1 or AIX 2.1.1 is RT/PC AIX.
-	echo romp-ibm-aix     # uname -m gives an 8 hex-code CPU id
-	exit ;;               # Note that: echo "'`uname -s`'" gives 'AIX '
-    i*86:AIX:*:*)
-	echo i386-ibm-aix
-	exit ;;
-    ia64:AIX:*:*)
-	if [ -x /usr/bin/oslevel ] ; then
-		IBM_REV=`/usr/bin/oslevel`
-	else
-		IBM_REV=${UNAME_VERSION}.${UNAME_RELEASE}
-	fi
-	echo ${UNAME_MACHINE}-ibm-aix${IBM_REV}
-	exit ;;
-    *:AIX:2:3)
-	if grep bos325 /usr/include/stdio.h >/dev/null 2>&1; then
-		eval $set_cc_for_build
-		sed 's/^		//' << EOF >$dummy.c
-		#include <sys/systemcfg.h>
-
-		main()
-			{
-			if (!__power_pc())
-				exit(1);
-			puts("powerpc-ibm-aix3.2.5");
-			exit(0);
-			}
-EOF
-		if $CC_FOR_BUILD -o $dummy $dummy.c && SYSTEM_NAME=`$dummy`
-		then
-			echo "$SYSTEM_NAME"
-		else
-			echo rs6000-ibm-aix3.2.5
-		fi
-	elif grep bos324 /usr/include/stdio.h >/dev/null 2>&1; then
-		echo rs6000-ibm-aix3.2.4
-	else
-		echo rs6000-ibm-aix3.2
-	fi
-	exit ;;
-    *:AIX:*:[456])
-	IBM_CPU_ID=`/usr/sbin/lsdev -C -c processor -S available | sed 1q | awk '{ print $1 }'`
-	if /usr/sbin/lsattr -El ${IBM_CPU_ID} | grep ' POWER' >/dev/null 2>&1; then
-		IBM_ARCH=rs6000
-	else
-		IBM_ARCH=powerpc
-	fi
-	if [ -x /usr/bin/oslevel ] ; then
-		IBM_REV=`/usr/bin/oslevel`
-	else
-		IBM_REV=${UNAME_VERSION}.${UNAME_RELEASE}
-	fi
-	echo ${IBM_ARCH}-ibm-aix${IBM_REV}
-	exit ;;
-    *:AIX:*:*)
-	echo rs6000-ibm-aix
-	exit ;;
-    ibmrt:4.4BSD:*|romp-ibm:BSD:*)
-	echo romp-ibm-bsd4.4
-	exit ;;
-    ibmrt:*BSD:*|romp-ibm:BSD:*)            # covers RT/PC BSD and
-	echo romp-ibm-bsd${UNAME_RELEASE}   # 4.3 with uname added to
-	exit ;;                             # report: romp-ibm BSD 4.3
-    *:BOSX:*:*)
-	echo rs6000-bull-bosx
-	exit ;;
-    DPX/2?00:B.O.S.:*:*)
-	echo m68k-bull-sysv3
-	exit ;;
-    9000/[34]??:4.3bsd:1.*:*)
-	echo m68k-hp-bsd
-	exit ;;
-    hp300:4.4BSD:*:* | 9000/[34]??:4.3bsd:2.*:*)
-	echo m68k-hp-bsd4.4
-	exit ;;
-    9000/[34678]??:HP-UX:*:*)
-	HPUX_REV=`echo ${UNAME_RELEASE}|sed -e 's/[^.]*.[0B]*//'`
-	case "${UNAME_MACHINE}" in
-	    9000/31? )            HP_ARCH=m68000 ;;
-	    9000/[34]?? )         HP_ARCH=m68k ;;
-	    9000/[678][0-9][0-9])
-		if [ -x /usr/bin/getconf ]; then
-		    sc_cpu_version=`/usr/bin/getconf SC_CPU_VERSION 2>/dev/null`
-                    sc_kernel_bits=`/usr/bin/getconf SC_KERNEL_BITS 2>/dev/null`
-                    case "${sc_cpu_version}" in
-                      523) HP_ARCH="hppa1.0" ;; # CPU_PA_RISC1_0
-                      528) HP_ARCH="hppa1.1" ;; # CPU_PA_RISC1_1
-                      532)                      # CPU_PA_RISC2_0
-                        case "${sc_kernel_bits}" in
-                          32) HP_ARCH="hppa2.0n" ;;
-                          64) HP_ARCH="hppa2.0w" ;;
-			  '') HP_ARCH="hppa2.0" ;;   # HP-UX 10.20
-                        esac ;;
-                    esac
-		fi
-		if [ "${HP_ARCH}" = "" ]; then
-		    eval $set_cc_for_build
-		    sed 's/^              //' << EOF >$dummy.c
-
-              #define _HPUX_SOURCE
-              #include <stdlib.h>
-              #include <unistd.h>
-
-              int main ()
-              {
-              #if defined(_SC_KERNEL_BITS)
-                  long bits = sysconf(_SC_KERNEL_BITS);
-              #endif
-                  long cpu  = sysconf (_SC_CPU_VERSION);
-
-                  switch (cpu)
-              	{
-              	case CPU_PA_RISC1_0: puts ("hppa1.0"); break;
-              	case CPU_PA_RISC1_1: puts ("hppa1.1"); break;
-              	case CPU_PA_RISC2_0:
-              #if defined(_SC_KERNEL_BITS)
-              	    switch (bits)
-              		{
-              		case 64: puts ("hppa2.0w"); break;
-              		case 32: puts ("hppa2.0n"); break;
-              		default: puts ("hppa2.0"); break;
-              		} break;
-              #else  /* !defined(_SC_KERNEL_BITS) */
-              	    puts ("hppa2.0"); break;
-              #endif
-              	default: puts ("hppa1.0"); break;
-              	}
-                  exit (0);
-              }
-EOF
-		    (CCOPTS= $CC_FOR_BUILD -o $dummy $dummy.c 2>/dev/null) && HP_ARCH=`$dummy`
-		    test -z "$HP_ARCH" && HP_ARCH=hppa
-		fi ;;
-	esac
-	if [ ${HP_ARCH} = "hppa2.0w" ]
-	then
-	    eval $set_cc_for_build
-
-	    # hppa2.0w-hp-hpux* has a 64-bit kernel and a compiler generating
-	    # 32-bit code.  hppa64-hp-hpux* has the same kernel and a compiler
-	    # generating 64-bit code.  GNU and HP use different nomenclature:
-	    #
-	    # $ CC_FOR_BUILD=cc ./config.guess
-	    # => hppa2.0w-hp-hpux11.23
-	    # $ CC_FOR_BUILD="cc +DA2.0w" ./config.guess
-	    # => hppa64-hp-hpux11.23
-
-	    if echo __LP64__ | (CCOPTS= $CC_FOR_BUILD -E - 2>/dev/null) |
-		grep __LP64__ >/dev/null
-	    then
-		HP_ARCH="hppa2.0w"
-	    else
-		HP_ARCH="hppa64"
-	    fi
-	fi
-	echo ${HP_ARCH}-hp-hpux${HPUX_REV}
-	exit ;;
-    ia64:HP-UX:*:*)
-	HPUX_REV=`echo ${UNAME_RELEASE}|sed -e 's/[^.]*.[0B]*//'`
-	echo ia64-hp-hpux${HPUX_REV}
-	exit ;;
-    3050*:HI-UX:*:*)
-	eval $set_cc_for_build
-	sed 's/^	//' << EOF >$dummy.c
-	#include <unistd.h>
-	int
-	main ()
-	{
-	  long cpu = sysconf (_SC_CPU_VERSION);
-	  /* The order matters, because CPU_IS_HP_MC68K erroneously returns
-	     true for CPU_PA_RISC1_0.  CPU_IS_PA_RISC returns correct
-	     results, however.  */
-	  if (CPU_IS_PA_RISC (cpu))
-	    {
-	      switch (cpu)
-		{
-		  case CPU_PA_RISC1_0: puts ("hppa1.0-hitachi-hiuxwe2"); break;
-		  case CPU_PA_RISC1_1: puts ("hppa1.1-hitachi-hiuxwe2"); break;
-		  case CPU_PA_RISC2_0: puts ("hppa2.0-hitachi-hiuxwe2"); break;
-		  default: puts ("hppa-hitachi-hiuxwe2"); break;
-		}
-	    }
-	  else if (CPU_IS_HP_MC68K (cpu))
-	    puts ("m68k-hitachi-hiuxwe2");
-	  else puts ("unknown-hitachi-hiuxwe2");
-	  exit (0);
-	}
-EOF
-	$CC_FOR_BUILD -o $dummy $dummy.c && SYSTEM_NAME=`$dummy` &&
-		{ echo "$SYSTEM_NAME"; exit; }
-	echo unknown-hitachi-hiuxwe2
-	exit ;;
-    9000/7??:4.3bsd:*:* | 9000/8?[79]:4.3bsd:*:* )
-	echo hppa1.1-hp-bsd
-	exit ;;
-    9000/8??:4.3bsd:*:*)
-	echo hppa1.0-hp-bsd
-	exit ;;
-    *9??*:MPE/iX:*:* | *3000*:MPE/iX:*:*)
-	echo hppa1.0-hp-mpeix
-	exit ;;
-    hp7??:OSF1:*:* | hp8?[79]:OSF1:*:* )
-	echo hppa1.1-hp-osf
-	exit ;;
-    hp8??:OSF1:*:*)
-	echo hppa1.0-hp-osf
-	exit ;;
-    i*86:OSF1:*:*)
-	if [ -x /usr/sbin/sysversion ] ; then
-	    echo ${UNAME_MACHINE}-unknown-osf1mk
-	else
-	    echo ${UNAME_MACHINE}-unknown-osf1
-	fi
-	exit ;;
-    parisc*:Lites*:*:*)
-	echo hppa1.1-hp-lites
-	exit ;;
-    C1*:ConvexOS:*:* | convex:ConvexOS:C1*:*)
-	echo c1-convex-bsd
-        exit ;;
-    C2*:ConvexOS:*:* | convex:ConvexOS:C2*:*)
-	if getsysinfo -f scalar_acc
-	then echo c32-convex-bsd
-	else echo c2-convex-bsd
-	fi
-        exit ;;
-    C34*:ConvexOS:*:* | convex:ConvexOS:C34*:*)
-	echo c34-convex-bsd
-        exit ;;
-    C38*:ConvexOS:*:* | convex:ConvexOS:C38*:*)
-	echo c38-convex-bsd
-        exit ;;
-    C4*:ConvexOS:*:* | convex:ConvexOS:C4*:*)
-	echo c4-convex-bsd
-        exit ;;
-    CRAY*Y-MP:*:*:*)
-	echo ymp-cray-unicos${UNAME_RELEASE} | sed -e 's/\.[^.]*$/.X/'
-	exit ;;
-    CRAY*[A-Z]90:*:*:*)
-	echo ${UNAME_MACHINE}-cray-unicos${UNAME_RELEASE} \
-	| sed -e 's/CRAY.*\([A-Z]90\)/\1/' \
-	      -e y/ABCDEFGHIJKLMNOPQRSTUVWXYZ/abcdefghijklmnopqrstuvwxyz/ \
-	      -e 's/\.[^.]*$/.X/'
-	exit ;;
-    CRAY*TS:*:*:*)
-	echo t90-cray-unicos${UNAME_RELEASE} | sed -e 's/\.[^.]*$/.X/'
-	exit ;;
-    CRAY*T3E:*:*:*)
-	echo alphaev5-cray-unicosmk${UNAME_RELEASE} | sed -e 's/\.[^.]*$/.X/'
-	exit ;;
-    CRAY*SV1:*:*:*)
-	echo sv1-cray-unicos${UNAME_RELEASE} | sed -e 's/\.[^.]*$/.X/'
-	exit ;;
-    *:UNICOS/mp:*:*)
-	echo craynv-cray-unicosmp${UNAME_RELEASE} | sed -e 's/\.[^.]*$/.X/'
-	exit ;;
-    F30[01]:UNIX_System_V:*:* | F700:UNIX_System_V:*:*)
-	FUJITSU_PROC=`uname -m | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz'`
-        FUJITSU_SYS=`uname -p | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz' | sed -e 's/\///'`
-        FUJITSU_REL=`echo ${UNAME_RELEASE} | sed -e 's/ /_/'`
-        echo "${FUJITSU_PROC}-fujitsu-${FUJITSU_SYS}${FUJITSU_REL}"
-        exit ;;
-    5000:UNIX_System_V:4.*:*)
-        FUJITSU_SYS=`uname -p | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz' | sed -e 's/\///'`
-        FUJITSU_REL=`echo ${UNAME_RELEASE} | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz' | sed -e 's/ /_/'`
-        echo "sparc-fujitsu-${FUJITSU_SYS}${FUJITSU_REL}"
-	exit ;;
-    i*86:BSD/386:*:* | i*86:BSD/OS:*:* | *:Ascend\ Embedded/OS:*:*)
-	echo ${UNAME_MACHINE}-pc-bsdi${UNAME_RELEASE}
-	exit ;;
-    sparc*:BSD/OS:*:*)
-	echo sparc-unknown-bsdi${UNAME_RELEASE}
-	exit ;;
-    *:BSD/OS:*:*)
-	echo ${UNAME_MACHINE}-unknown-bsdi${UNAME_RELEASE}
-	exit ;;
-    *:FreeBSD:*:*)
-	case ${UNAME_MACHINE} in
-	    pc98)
-		echo i386-unknown-freebsd`echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'` ;;
-	    amd64)
-		echo x86_64-unknown-freebsd`echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'` ;;
-	    *)
-		echo ${UNAME_MACHINE}-unknown-freebsd`echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'` ;;
-	esac
-	exit ;;
-    i*:CYGWIN*:*)
-	echo ${UNAME_MACHINE}-pc-cygwin
-	exit ;;
-    *:MINGW*:*)
-	echo ${UNAME_MACHINE}-pc-mingw32
-	exit ;;
-    i*:windows32*:*)
-    	# uname -m includes "-pc" on this system.
-    	echo ${UNAME_MACHINE}-mingw32
-	exit ;;
-    i*:PW*:*)
-	echo ${UNAME_MACHINE}-pc-pw32
-	exit ;;
-    *:Interix*:[3456]*)
-    	case ${UNAME_MACHINE} in
-	    x86)
-		echo i586-pc-interix${UNAME_RELEASE}
-		exit ;;
-	    EM64T | authenticamd | genuineintel)
-		echo x86_64-unknown-interix${UNAME_RELEASE}
-		exit ;;
-	    IA64)
-		echo ia64-unknown-interix${UNAME_RELEASE}
-		exit ;;
-	esac ;;
-    [345]86:Windows_95:* | [345]86:Windows_98:* | [345]86:Windows_NT:*)
-	echo i${UNAME_MACHINE}-pc-mks
-	exit ;;
-    i*:Windows_NT*:* | Pentium*:Windows_NT*:*)
-	# How do we know it's Interix rather than the generic POSIX subsystem?
-	# It also conflicts with pre-2.0 versions of AT&T UWIN. Should we
-	# UNAME_MACHINE based on the output of uname instead of i386?
-	echo i586-pc-interix
-	exit ;;
-    i*:UWIN*:*)
-	echo ${UNAME_MACHINE}-pc-uwin
-	exit ;;
-    amd64:CYGWIN*:*:* | x86_64:CYGWIN*:*:*)
-	echo x86_64-unknown-cygwin
-	exit ;;
-    p*:CYGWIN*:*)
-	echo powerpcle-unknown-cygwin
-	exit ;;
-    prep*:SunOS:5.*:*)
-	echo powerpcle-unknown-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'`
-	exit ;;
-    *:GNU:*:*)
-	# the GNU system
-	echo `echo ${UNAME_MACHINE}|sed -e 's,[-/].*$,,'`-unknown-gnu`echo ${UNAME_RELEASE}|sed -e 's,/.*$,,'`
-	exit ;;
-    *:GNU/*:*:*)
-	# other systems with GNU libc and userland
-	echo ${UNAME_MACHINE}-unknown-`echo ${UNAME_SYSTEM} | sed 's,^[^/]*/,,' | tr '[A-Z]' '[a-z]'``echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'`-gnu
-	exit ;;
-    i*86:Minix:*:*)
-	echo ${UNAME_MACHINE}-pc-minix
-	exit ;;
-    arm*:Linux:*:*)
-	eval $set_cc_for_build
-	if echo __ARM_EABI__ | $CC_FOR_BUILD -E - 2>/dev/null \
-	    | grep -q __ARM_EABI__
-	then
-	    echo ${UNAME_MACHINE}-unknown-linux-gnu
-	else
-	    echo ${UNAME_MACHINE}-unknown-linux-gnueabi
-	fi
-	exit ;;
-    avr32*:Linux:*:*)
-	echo ${UNAME_MACHINE}-unknown-linux-gnu
-	exit ;;
-    cris:Linux:*:*)
-	echo cris-axis-linux-gnu
-	exit ;;
-    crisv32:Linux:*:*)
-	echo crisv32-axis-linux-gnu
-	exit ;;
-    frv:Linux:*:*)
-    	echo frv-unknown-linux-gnu
-	exit ;;
-    ia64:Linux:*:*)
-	echo ${UNAME_MACHINE}-unknown-linux-gnu
-	exit ;;
-    m32r*:Linux:*:*)
-	echo ${UNAME_MACHINE}-unknown-linux-gnu
-	exit ;;
-    m68*:Linux:*:*)
-	echo ${UNAME_MACHINE}-unknown-linux-gnu
-	exit ;;
-    mips:Linux:*:*)
-	eval $set_cc_for_build
-	sed 's/^	//' << EOF >$dummy.c
-	#undef CPU
-	#undef mips
-	#undef mipsel
-	#if defined(__MIPSEL__) || defined(__MIPSEL) || defined(_MIPSEL) || defined(MIPSEL)
-	CPU=mipsel
-	#else
-	#if defined(__MIPSEB__) || defined(__MIPSEB) || defined(_MIPSEB) || defined(MIPSEB)
-	CPU=mips
-	#else
-	CPU=
-	#endif
-	#endif
-EOF
-	eval "`$CC_FOR_BUILD -E $dummy.c 2>/dev/null | sed -n '
-	    /^CPU/{
-		s: ::g
-		p
-	    }'`"
-	test x"${CPU}" != x && { echo "${CPU}-unknown-linux-gnu"; exit; }
-	;;
-    mips64:Linux:*:*)
-	eval $set_cc_for_build
-	sed 's/^	//' << EOF >$dummy.c
-	#undef CPU
-	#undef mips64
-	#undef mips64el
-	#if defined(__MIPSEL__) || defined(__MIPSEL) || defined(_MIPSEL) || defined(MIPSEL)
-	CPU=mips64el
-	#else
-	#if defined(__MIPSEB__) || defined(__MIPSEB) || defined(_MIPSEB) || defined(MIPSEB)
-	CPU=mips64
-	#else
-	CPU=
-	#endif
-	#endif
-EOF
-	eval "`$CC_FOR_BUILD -E $dummy.c 2>/dev/null | sed -n '
-	    /^CPU/{
-		s: ::g
-		p
-	    }'`"
-	test x"${CPU}" != x && { echo "${CPU}-unknown-linux-gnu"; exit; }
-	;;
-    or32:Linux:*:*)
-	echo or32-unknown-linux-gnu
-	exit ;;
-    ppc:Linux:*:*)
-	echo powerpc-unknown-linux-gnu
-	exit ;;
-    ppc64:Linux:*:*)
-	echo powerpc64-unknown-linux-gnu
-	exit ;;
-    alpha:Linux:*:*)
-	case `sed -n '/^cpu model/s/^.*: \(.*\)/\1/p' < /proc/cpuinfo` in
-	  EV5)   UNAME_MACHINE=alphaev5 ;;
-	  EV56)  UNAME_MACHINE=alphaev56 ;;
-	  PCA56) UNAME_MACHINE=alphapca56 ;;
-	  PCA57) UNAME_MACHINE=alphapca56 ;;
-	  EV6)   UNAME_MACHINE=alphaev6 ;;
-	  EV67)  UNAME_MACHINE=alphaev67 ;;
-	  EV68*) UNAME_MACHINE=alphaev68 ;;
-        esac
-	objdump --private-headers /bin/sh | grep ld.so.1 >/dev/null
-	if test "$?" = 0 ; then LIBC="libc1" ; else LIBC="" ; fi
-	echo ${UNAME_MACHINE}-unknown-linux-gnu${LIBC}
-	exit ;;
-    padre:Linux:*:*)
-	echo sparc-unknown-linux-gnu
-	exit ;;
-    parisc:Linux:*:* | hppa:Linux:*:*)
-	# Look for CPU level
-	case `grep '^cpu[^a-z]*:' /proc/cpuinfo 2>/dev/null | cut -d' ' -f2` in
-	  PA7*) echo hppa1.1-unknown-linux-gnu ;;
-	  PA8*) echo hppa2.0-unknown-linux-gnu ;;
-	  *)    echo hppa-unknown-linux-gnu ;;
-	esac
-	exit ;;
-    parisc64:Linux:*:* | hppa64:Linux:*:*)
-	echo hppa64-unknown-linux-gnu
-	exit ;;
-    s390:Linux:*:* | s390x:Linux:*:*)
-	echo ${UNAME_MACHINE}-ibm-linux
-	exit ;;
-    sh64*:Linux:*:*)
-    	echo ${UNAME_MACHINE}-unknown-linux-gnu
-	exit ;;
-    sh*:Linux:*:*)
-	echo ${UNAME_MACHINE}-unknown-linux-gnu
-	exit ;;
-    sparc:Linux:*:* | sparc64:Linux:*:*)
-	echo ${UNAME_MACHINE}-unknown-linux-gnu
-	exit ;;
-    vax:Linux:*:*)
-	echo ${UNAME_MACHINE}-dec-linux-gnu
-	exit ;;
-    x86_64:Linux:*:*)
-	echo x86_64-unknown-linux-gnu
-	exit ;;
-    xtensa*:Linux:*:*)
-    	echo ${UNAME_MACHINE}-unknown-linux-gnu
-	exit ;;
-    i*86:Linux:*:*)
-	# The BFD linker knows what the default object file format is, so
-	# first see if it will tell us. cd to the root directory to prevent
-	# problems with other programs or directories called `ld' in the path.
-	# Set LC_ALL=C to ensure ld outputs messages in English.
-	ld_supported_targets=`cd /; LC_ALL=C ld --help 2>&1 \
-			 | sed -ne '/supported targets:/!d
-				    s/[ 	][ 	]*/ /g
-				    s/.*supported targets: *//
-				    s/ .*//
-				    p'`
-        case "$ld_supported_targets" in
-	  elf32-i386)
-		TENTATIVE="${UNAME_MACHINE}-pc-linux-gnu"
-		;;
-	  a.out-i386-linux)
-		echo "${UNAME_MACHINE}-pc-linux-gnuaout"
-		exit ;;
-	  "")
-		# Either a pre-BFD a.out linker (linux-gnuoldld) or
-		# one that does not give us useful --help.
-		echo "${UNAME_MACHINE}-pc-linux-gnuoldld"
-		exit ;;
-	esac
-	# Determine whether the default compiler is a.out or elf
-	eval $set_cc_for_build
-	sed 's/^	//' << EOF >$dummy.c
-	#include <features.h>
-	#ifdef __ELF__
-	# ifdef __GLIBC__
-	#  if __GLIBC__ >= 2
-	LIBC=gnu
-	#  else
-	LIBC=gnulibc1
-	#  endif
-	# else
-	LIBC=gnulibc1
-	# endif
-	#else
-	#if defined(__INTEL_COMPILER) || defined(__PGI) || defined(__SUNPRO_C) || defined(__SUNPRO_CC)
-	LIBC=gnu
-	#else
-	LIBC=gnuaout
-	#endif
-	#endif
-	#ifdef __dietlibc__
-	LIBC=dietlibc
-	#endif
-EOF
-	eval "`$CC_FOR_BUILD -E $dummy.c 2>/dev/null | sed -n '
-	    /^LIBC/{
-		s: ::g
-		p
-	    }'`"
-	test x"${LIBC}" != x && {
-		echo "${UNAME_MACHINE}-pc-linux-${LIBC}"
-		exit
-	}
-	test x"${TENTATIVE}" != x && { echo "${TENTATIVE}"; exit; }
-	;;
-    i*86:DYNIX/ptx:4*:*)
-	# ptx 4.0 does uname -s correctly, with DYNIX/ptx in there.
-	# earlier versions are messed up and put the nodename in both
-	# sysname and nodename.
-	echo i386-sequent-sysv4
-	exit ;;
-    i*86:UNIX_SV:4.2MP:2.*)
-        # Unixware is an offshoot of SVR4, but it has its own version
-        # number series starting with 2...
-        # I am not positive that other SVR4 systems won't match this,
-	# I just have to hope.  -- rms.
-        # Use sysv4.2uw... so that sysv4* matches it.
-	echo ${UNAME_MACHINE}-pc-sysv4.2uw${UNAME_VERSION}
-	exit ;;
-    i*86:OS/2:*:*)
-	# If we were able to find `uname', then EMX Unix compatibility
-	# is probably installed.
-	echo ${UNAME_MACHINE}-pc-os2-emx
-	exit ;;
-    i*86:XTS-300:*:STOP)
-	echo ${UNAME_MACHINE}-unknown-stop
-	exit ;;
-    i*86:atheos:*:*)
-	echo ${UNAME_MACHINE}-unknown-atheos
-	exit ;;
-    i*86:syllable:*:*)
-	echo ${UNAME_MACHINE}-pc-syllable
-	exit ;;
-    i*86:LynxOS:2.*:* | i*86:LynxOS:3.[01]*:* | i*86:LynxOS:4.0*:*)
-	echo i386-unknown-lynxos${UNAME_RELEASE}
-	exit ;;
-    i*86:*DOS:*:*)
-	echo ${UNAME_MACHINE}-pc-msdosdjgpp
-	exit ;;
-    i*86:*:4.*:* | i*86:SYSTEM_V:4.*:*)
-	UNAME_REL=`echo ${UNAME_RELEASE} | sed 's/\/MP$//'`
-	if grep Novell /usr/include/link.h >/dev/null 2>/dev/null; then
-		echo ${UNAME_MACHINE}-univel-sysv${UNAME_REL}
-	else
-		echo ${UNAME_MACHINE}-pc-sysv${UNAME_REL}
-	fi
-	exit ;;
-    i*86:*:5:[678]*)
-    	# UnixWare 7.x, OpenUNIX and OpenServer 6.
-	case `/bin/uname -X | grep "^Machine"` in
-	    *486*)	     UNAME_MACHINE=i486 ;;
-	    *Pentium)	     UNAME_MACHINE=i586 ;;
-	    *Pent*|*Celeron) UNAME_MACHINE=i686 ;;
-	esac
-	echo ${UNAME_MACHINE}-unknown-sysv${UNAME_RELEASE}${UNAME_SYSTEM}${UNAME_VERSION}
-	exit ;;
-    i*86:*:3.2:*)
-	if test -f /usr/options/cb.name; then
-		UNAME_REL=`sed -n 's/.*Version //p' </usr/options/cb.name`
-		echo ${UNAME_MACHINE}-pc-isc$UNAME_REL
-	elif /bin/uname -X 2>/dev/null >/dev/null ; then
-		UNAME_REL=`(/bin/uname -X|grep Release|sed -e 's/.*= //')`
-		(/bin/uname -X|grep i80486 >/dev/null) && UNAME_MACHINE=i486
-		(/bin/uname -X|grep '^Machine.*Pentium' >/dev/null) \
-			&& UNAME_MACHINE=i586
-		(/bin/uname -X|grep '^Machine.*Pent *II' >/dev/null) \
-			&& UNAME_MACHINE=i686
-		(/bin/uname -X|grep '^Machine.*Pentium Pro' >/dev/null) \
-			&& UNAME_MACHINE=i686
-		echo ${UNAME_MACHINE}-pc-sco$UNAME_REL
-	else
-		echo ${UNAME_MACHINE}-pc-sysv32
-	fi
-	exit ;;
-    pc:*:*:*)
-	# Left here for compatibility:
-        # uname -m prints for DJGPP always 'pc', but it prints nothing about
-        # the processor, so we play safe by assuming i586.
-	# Note: whatever this is, it MUST be the same as what config.sub
-	# prints for the "djgpp" host, or else GDB configury will decide that
-	# this is a cross-build.
-	echo i586-pc-msdosdjgpp
-        exit ;;
-    Intel:Mach:3*:*)
-	echo i386-pc-mach3
-	exit ;;
-    paragon:*:*:*)
-	echo i860-intel-osf1
-	exit ;;
-    i860:*:4.*:*) # i860-SVR4
-	if grep Stardent /usr/include/sys/uadmin.h >/dev/null 2>&1 ; then
-	  echo i860-stardent-sysv${UNAME_RELEASE} # Stardent Vistra i860-SVR4
-	else # Add other i860-SVR4 vendors below as they are discovered.
-	  echo i860-unknown-sysv${UNAME_RELEASE}  # Unknown i860-SVR4
-	fi
-	exit ;;
-    mini*:CTIX:SYS*5:*)
-	# "miniframe"
-	echo m68010-convergent-sysv
-	exit ;;
-    mc68k:UNIX:SYSTEM5:3.51m)
-	echo m68k-convergent-sysv
-	exit ;;
-    M680?0:D-NIX:5.3:*)
-	echo m68k-diab-dnix
-	exit ;;
-    M68*:*:R3V[5678]*:*)
-	test -r /sysV68 && { echo 'm68k-motorola-sysv'; exit; } ;;
-    3[345]??:*:4.0:3.0 | 3[34]??A:*:4.0:3.0 | 3[34]??,*:*:4.0:3.0 | 3[34]??/*:*:4.0:3.0 | 4400:*:4.0:3.0 | 4850:*:4.0:3.0 | SKA40:*:4.0:3.0 | SDS2:*:4.0:3.0 | SHG2:*:4.0:3.0 | S7501*:*:4.0:3.0)
-	OS_REL=''
-	test -r /etc/.relid \
-	&& OS_REL=.`sed -n 's/[^ ]* [^ ]* \([0-9][0-9]\).*/\1/p' < /etc/.relid`
-	/bin/uname -p 2>/dev/null | grep 86 >/dev/null \
-	  && { echo i486-ncr-sysv4.3${OS_REL}; exit; }
-	/bin/uname -p 2>/dev/null | /bin/grep entium >/dev/null \
-	  && { echo i586-ncr-sysv4.3${OS_REL}; exit; } ;;
-    3[34]??:*:4.0:* | 3[34]??,*:*:4.0:*)
-        /bin/uname -p 2>/dev/null | grep 86 >/dev/null \
-          && { echo i486-ncr-sysv4; exit; } ;;
-    NCR*:*:4.2:* | MPRAS*:*:4.2:*)
-	OS_REL='.3'
-	test -r /etc/.relid \
-	    && OS_REL=.`sed -n 's/[^ ]* [^ ]* \([0-9][0-9]\).*/\1/p' < /etc/.relid`
-	/bin/uname -p 2>/dev/null | grep 86 >/dev/null \
-	    && { echo i486-ncr-sysv4.3${OS_REL}; exit; }
-	/bin/uname -p 2>/dev/null | /bin/grep entium >/dev/null \
-	    && { echo i586-ncr-sysv4.3${OS_REL}; exit; }
-	/bin/uname -p 2>/dev/null | /bin/grep pteron >/dev/null \
-	    && { echo i586-ncr-sysv4.3${OS_REL}; exit; } ;;
-    m68*:LynxOS:2.*:* | m68*:LynxOS:3.0*:*)
-	echo m68k-unknown-lynxos${UNAME_RELEASE}
-	exit ;;
-    mc68030:UNIX_System_V:4.*:*)
-	echo m68k-atari-sysv4
-	exit ;;
-    TSUNAMI:LynxOS:2.*:*)
-	echo sparc-unknown-lynxos${UNAME_RELEASE}
-	exit ;;
-    rs6000:LynxOS:2.*:*)
-	echo rs6000-unknown-lynxos${UNAME_RELEASE}
-	exit ;;
-    PowerPC:LynxOS:2.*:* | PowerPC:LynxOS:3.[01]*:* | PowerPC:LynxOS:4.0*:*)
-	echo powerpc-unknown-lynxos${UNAME_RELEASE}
-	exit ;;
-    SM[BE]S:UNIX_SV:*:*)
-	echo mips-dde-sysv${UNAME_RELEASE}
-	exit ;;
-    RM*:ReliantUNIX-*:*:*)
-	echo mips-sni-sysv4
-	exit ;;
-    RM*:SINIX-*:*:*)
-	echo mips-sni-sysv4
-	exit ;;
-    *:SINIX-*:*:*)
-	if uname -p 2>/dev/null >/dev/null ; then
-		UNAME_MACHINE=`(uname -p) 2>/dev/null`
-		echo ${UNAME_MACHINE}-sni-sysv4
-	else
-		echo ns32k-sni-sysv
-	fi
-	exit ;;
-    PENTIUM:*:4.0*:*) # Unisys `ClearPath HMP IX 4000' SVR4/MP effort
-                      # says <Richard.M.Bartel at ccMail.Census.GOV>
-        echo i586-unisys-sysv4
-        exit ;;
-    *:UNIX_System_V:4*:FTX*)
-	# From Gerald Hewes <hewes at openmarket.com>.
-	# How about differentiating between stratus architectures? -djm
-	echo hppa1.1-stratus-sysv4
-	exit ;;
-    *:*:*:FTX*)
-	# From seanf at swdc.stratus.com.
-	echo i860-stratus-sysv4
-	exit ;;
-    i*86:VOS:*:*)
-	# From Paul.Green at stratus.com.
-	echo ${UNAME_MACHINE}-stratus-vos
-	exit ;;
-    *:VOS:*:*)
-	# From Paul.Green at stratus.com.
-	echo hppa1.1-stratus-vos
-	exit ;;
-    mc68*:A/UX:*:*)
-	echo m68k-apple-aux${UNAME_RELEASE}
-	exit ;;
-    news*:NEWS-OS:6*:*)
-	echo mips-sony-newsos6
-	exit ;;
-    R[34]000:*System_V*:*:* | R4000:UNIX_SYSV:*:* | R*000:UNIX_SV:*:*)
-	if [ -d /usr/nec ]; then
-	        echo mips-nec-sysv${UNAME_RELEASE}
-	else
-	        echo mips-unknown-sysv${UNAME_RELEASE}
-	fi
-        exit ;;
-    BeBox:BeOS:*:*)	# BeOS running on hardware made by Be, PPC only.
-	echo powerpc-be-beos
-	exit ;;
-    BeMac:BeOS:*:*)	# BeOS running on Mac or Mac clone, PPC only.
-	echo powerpc-apple-beos
-	exit ;;
-    BePC:BeOS:*:*)	# BeOS running on Intel PC compatible.
-	echo i586-pc-beos
-	exit ;;
-    BePC:Haiku:*:*)	# Haiku running on Intel PC compatible.
-	echo i586-pc-haiku
-	exit ;;
-    SX-4:SUPER-UX:*:*)
-	echo sx4-nec-superux${UNAME_RELEASE}
-	exit ;;
-    SX-5:SUPER-UX:*:*)
-	echo sx5-nec-superux${UNAME_RELEASE}
-	exit ;;
-    SX-6:SUPER-UX:*:*)
-	echo sx6-nec-superux${UNAME_RELEASE}
-	exit ;;
-    SX-7:SUPER-UX:*:*)
-	echo sx7-nec-superux${UNAME_RELEASE}
-	exit ;;
-    SX-8:SUPER-UX:*:*)
-	echo sx8-nec-superux${UNAME_RELEASE}
-	exit ;;
-    SX-8R:SUPER-UX:*:*)
-	echo sx8r-nec-superux${UNAME_RELEASE}
-	exit ;;
-    Power*:Rhapsody:*:*)
-	echo powerpc-apple-rhapsody${UNAME_RELEASE}
-	exit ;;
-    *:Rhapsody:*:*)
-	echo ${UNAME_MACHINE}-apple-rhapsody${UNAME_RELEASE}
-	exit ;;
-    *:Darwin:*:*)
-	UNAME_PROCESSOR=`uname -p` || UNAME_PROCESSOR=unknown
-	case $UNAME_PROCESSOR in
-	    unknown) UNAME_PROCESSOR=powerpc ;;
-	esac
-	echo ${UNAME_PROCESSOR}-apple-darwin${UNAME_RELEASE}
-	exit ;;
-    *:procnto*:*:* | *:QNX:[0123456789]*:*)
-	UNAME_PROCESSOR=`uname -p`
-	if test "$UNAME_PROCESSOR" = "x86"; then
-		UNAME_PROCESSOR=i386
-		UNAME_MACHINE=pc
-	fi
-	echo ${UNAME_PROCESSOR}-${UNAME_MACHINE}-nto-qnx${UNAME_RELEASE}
-	exit ;;
-    *:QNX:*:4*)
-	echo i386-pc-qnx
-	exit ;;
-    NSE-?:NONSTOP_KERNEL:*:*)
-	echo nse-tandem-nsk${UNAME_RELEASE}
-	exit ;;
-    NSR-?:NONSTOP_KERNEL:*:*)
-	echo nsr-tandem-nsk${UNAME_RELEASE}
-	exit ;;
-    *:NonStop-UX:*:*)
-	echo mips-compaq-nonstopux
-	exit ;;
-    BS2000:POSIX*:*:*)
-	echo bs2000-siemens-sysv
-	exit ;;
-    DS/*:UNIX_System_V:*:*)
-	echo ${UNAME_MACHINE}-${UNAME_SYSTEM}-${UNAME_RELEASE}
-	exit ;;
-    *:Plan9:*:*)
-	# "uname -m" is not consistent, so use $cputype instead. 386
-	# is converted to i386 for consistency with other x86
-	# operating systems.
-	if test "$cputype" = "386"; then
-	    UNAME_MACHINE=i386
-	else
-	    UNAME_MACHINE="$cputype"
-	fi
-	echo ${UNAME_MACHINE}-unknown-plan9
-	exit ;;
-    *:TOPS-10:*:*)
-	echo pdp10-unknown-tops10
-	exit ;;
-    *:TENEX:*:*)
-	echo pdp10-unknown-tenex
-	exit ;;
-    KS10:TOPS-20:*:* | KL10:TOPS-20:*:* | TYPE4:TOPS-20:*:*)
-	echo pdp10-dec-tops20
-	exit ;;
-    XKL-1:TOPS-20:*:* | TYPE5:TOPS-20:*:*)
-	echo pdp10-xkl-tops20
-	exit ;;
-    *:TOPS-20:*:*)
-	echo pdp10-unknown-tops20
-	exit ;;
-    *:ITS:*:*)
-	echo pdp10-unknown-its
-	exit ;;
-    SEI:*:*:SEIUX)
-        echo mips-sei-seiux${UNAME_RELEASE}
-	exit ;;
-    *:DragonFly:*:*)
-	echo ${UNAME_MACHINE}-unknown-dragonfly`echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'`
-	exit ;;
-    *:*VMS:*:*)
-    	UNAME_MACHINE=`(uname -p) 2>/dev/null`
-	case "${UNAME_MACHINE}" in
-	    A*) echo alpha-dec-vms ; exit ;;
-	    I*) echo ia64-dec-vms ; exit ;;
-	    V*) echo vax-dec-vms ; exit ;;
-	esac ;;
-    *:XENIX:*:SysV)
-	echo i386-pc-xenix
-	exit ;;
-    i*86:skyos:*:*)
-	echo ${UNAME_MACHINE}-pc-skyos`echo ${UNAME_RELEASE}` | sed -e 's/ .*$//'
-	exit ;;
-    i*86:rdos:*:*)
-	echo ${UNAME_MACHINE}-pc-rdos
-	exit ;;
-    i*86:AROS:*:*)
-	echo ${UNAME_MACHINE}-pc-aros
-	exit ;;
-esac
-
-#echo '(No uname command or uname output not recognized.)' 1>&2
-#echo "${UNAME_MACHINE}:${UNAME_SYSTEM}:${UNAME_RELEASE}:${UNAME_VERSION}" 1>&2
-
-eval $set_cc_for_build
-cat >$dummy.c <<EOF
-#ifdef _SEQUENT_
-# include <sys/types.h>
-# include <sys/utsname.h>
-#endif
-main ()
-{
-#if defined (sony)
-#if defined (MIPSEB)
-  /* BFD wants "bsd" instead of "newsos".  Perhaps BFD should be changed,
-     I don't know....  */
-  printf ("mips-sony-bsd\n"); exit (0);
-#else
-#include <sys/param.h>
-  printf ("m68k-sony-newsos%s\n",
-#ifdef NEWSOS4
-          "4"
-#else
-	  ""
-#endif
-         ); exit (0);
-#endif
-#endif
-
-#if defined (__arm) && defined (__acorn) && defined (__unix)
-  printf ("arm-acorn-riscix\n"); exit (0);
-#endif
-
-#if defined (hp300) && !defined (hpux)
-  printf ("m68k-hp-bsd\n"); exit (0);
-#endif
-
-#if defined (NeXT)
-#if !defined (__ARCHITECTURE__)
-#define __ARCHITECTURE__ "m68k"
-#endif
-  int version;
-  version=`(hostinfo | sed -n 's/.*NeXT Mach \([0-9]*\).*/\1/p') 2>/dev/null`;
-  if (version < 4)
-    printf ("%s-next-nextstep%d\n", __ARCHITECTURE__, version);
-  else
-    printf ("%s-next-openstep%d\n", __ARCHITECTURE__, version);
-  exit (0);
-#endif
-
-#if defined (MULTIMAX) || defined (n16)
-#if defined (UMAXV)
-  printf ("ns32k-encore-sysv\n"); exit (0);
-#else
-#if defined (CMU)
-  printf ("ns32k-encore-mach\n"); exit (0);
-#else
-  printf ("ns32k-encore-bsd\n"); exit (0);
-#endif
-#endif
-#endif
-
-#if defined (__386BSD__)
-  printf ("i386-pc-bsd\n"); exit (0);
-#endif
-
-#if defined (sequent)
-#if defined (i386)
-  printf ("i386-sequent-dynix\n"); exit (0);
-#endif
-#if defined (ns32000)
-  printf ("ns32k-sequent-dynix\n"); exit (0);
-#endif
-#endif
-
-#if defined (_SEQUENT_)
-    struct utsname un;
-
-    uname(&un);
-
-    if (strncmp(un.version, "V2", 2) == 0) {
-	printf ("i386-sequent-ptx2\n"); exit (0);
-    }
-    if (strncmp(un.version, "V1", 2) == 0) { /* XXX is V1 correct? */
-	printf ("i386-sequent-ptx1\n"); exit (0);
-    }
-    printf ("i386-sequent-ptx\n"); exit (0);
-
-#endif
-
-#if defined (vax)
-# if !defined (ultrix)
-#  include <sys/param.h>
-#  if defined (BSD)
-#   if BSD == 43
-      printf ("vax-dec-bsd4.3\n"); exit (0);
-#   else
-#    if BSD == 199006
-      printf ("vax-dec-bsd4.3reno\n"); exit (0);
-#    else
-      printf ("vax-dec-bsd\n"); exit (0);
-#    endif
-#   endif
-#  else
-    printf ("vax-dec-bsd\n"); exit (0);
-#  endif
-# else
-    printf ("vax-dec-ultrix\n"); exit (0);
-# endif
-#endif
-
-#if defined (alliant) && defined (i860)
-  printf ("i860-alliant-bsd\n"); exit (0);
-#endif
-
-  exit (1);
-}
-EOF
-
-$CC_FOR_BUILD -o $dummy $dummy.c 2>/dev/null && SYSTEM_NAME=`$dummy` &&
-	{ echo "$SYSTEM_NAME"; exit; }
-
-# Apollos put the system type in the environment.
-
-test -d /usr/apollo && { echo ${ISP}-apollo-${SYSTYPE}; exit; }
-
-# Convex versions that predate uname can use getsysinfo(1)
-
-if [ -x /usr/convex/getsysinfo ]
-then
-    case `getsysinfo -f cpu_type` in
-    c1*)
-	echo c1-convex-bsd
-	exit ;;
-    c2*)
-	if getsysinfo -f scalar_acc
-	then echo c32-convex-bsd
-	else echo c2-convex-bsd
-	fi
-	exit ;;
-    c34*)
-	echo c34-convex-bsd
-	exit ;;
-    c38*)
-	echo c38-convex-bsd
-	exit ;;
-    c4*)
-	echo c4-convex-bsd
-	exit ;;
-    esac
-fi
-
-cat >&2 <<EOF
-$0: unable to guess system type
-
-This script, last modified $timestamp, has failed to recognize
-the operating system you are using. It is advised that you
-download the most up to date version of the config scripts from
-
-  http://git.savannah.gnu.org/gitweb/?p=config.git;a=blob_plain;f=config.guess;hb=HEAD
-and
-  http://git.savannah.gnu.org/gitweb/?p=config.git;a=blob_plain;f=config.sub;hb=HEAD
-
-If the version you run ($0) is already up to date, please
-send the following data and any information you think might be
-pertinent to <config-patches at gnu.org> in order to provide the needed
-information to handle your system.
-
-config.guess timestamp = $timestamp
-
-uname -m = `(uname -m) 2>/dev/null || echo unknown`
-uname -r = `(uname -r) 2>/dev/null || echo unknown`
-uname -s = `(uname -s) 2>/dev/null || echo unknown`
-uname -v = `(uname -v) 2>/dev/null || echo unknown`
-
-/usr/bin/uname -p = `(/usr/bin/uname -p) 2>/dev/null`
-/bin/uname -X     = `(/bin/uname -X) 2>/dev/null`
-
-hostinfo               = `(hostinfo) 2>/dev/null`
-/bin/universe          = `(/bin/universe) 2>/dev/null`
-/usr/bin/arch -k       = `(/usr/bin/arch -k) 2>/dev/null`
-/bin/arch              = `(/bin/arch) 2>/dev/null`
-/usr/bin/oslevel       = `(/usr/bin/oslevel) 2>/dev/null`
-/usr/convex/getsysinfo = `(/usr/convex/getsysinfo) 2>/dev/null`
-
-UNAME_MACHINE = ${UNAME_MACHINE}
-UNAME_RELEASE = ${UNAME_RELEASE}
-UNAME_SYSTEM  = ${UNAME_SYSTEM}
-UNAME_VERSION = ${UNAME_VERSION}
-EOF
-
-exit 1
-
-# Local variables:
-# eval: (add-hook 'write-file-hooks 'time-stamp)
-# time-stamp-start: "timestamp='"
-# time-stamp-format: "%:y-%02m-%02d"
-# time-stamp-end: "'"
-# End:
diff --git a/lib/replace/config.h.in b/lib/replace/config.h.in
deleted file mode 100644
index 1fcf7e9..0000000
--- a/lib/replace/config.h.in
+++ /dev/null
@@ -1,690 +0,0 @@
-/* config.h.in.  Generated from configure.ac by autoheader.  */
-
-/* Whether strndup is broken */
-#undef BROKEN_STRNDUP
-
-/* Whether strnlen is broken */
-#undef BROKEN_STRNLEN
-
-/* Define to 1 if you have the <acl/libacl.h> header file. */
-#undef HAVE_ACL_LIBACL_H
-
-/* Define to 1 if you have the <arpa/inet.h> header file. */
-#undef HAVE_ARPA_INET_H
-
-/* Define to 1 if you have the `asprintf' function. */
-#undef HAVE_ASPRINTF
-
-/* Whether the bool type is available */
-#undef HAVE_BOOL
-
-/* Define to 1 if you have the `bzero' function. */
-#undef HAVE_BZERO
-
-/* Whether there is a C99 compliant vsnprintf */
-#undef HAVE_C99_VSNPRINTF
-
-/* Define to 1 if you have the `chroot' function. */
-#undef HAVE_CHROOT
-
-/* Define to 1 if you have the `chsize' function. */
-#undef HAVE_CHSIZE
-
-/* Whether or not we have comparison_fn_t */
-#undef HAVE_COMPARISON_FN_T
-
-/* Define to 1 if you have the <compat.h> header file. */
-#undef HAVE_COMPAT_H
-
-/* Define to 1 if you have the <ctype.h> header file. */
-#undef HAVE_CTYPE_H
-
-/* Define to 1 if you have the declaration of `asprintf', and to 0 if you
-   don't. */
-#undef HAVE_DECL_ASPRINTF
-
-/* Define to 1 if you have the declaration of `snprintf', and to 0 if you
-   don't. */
-#undef HAVE_DECL_SNPRINTF
-
-/* Define to 1 if you have the declaration of `vasprintf', and to 0 if you
-   don't. */
-#undef HAVE_DECL_VASPRINTF
-
-/* Define to 1 if you have the declaration of `vsnprintf', and to 0 if you
-   don't. */
-#undef HAVE_DECL_VSNPRINTF
-
-/* Define to 1 if you have the <direct.h> header file. */
-#undef HAVE_DIRECT_H
-
-/* Define to 1 if you have the <dirent.h> header file, and it defines `DIR'.
-   */
-#undef HAVE_DIRENT_H
-
-/* Define to 1 if you have the `dlclose' function. */
-#undef HAVE_DLCLOSE
-
-/* Define to 1 if you have the `dlerror' function. */
-#undef HAVE_DLERROR
-
-/* Define to 1 if you have the <dlfcn.h> header file. */
-#undef HAVE_DLFCN_H
-
-/* Define to 1 if you have the `dlopen' function. */
-#undef HAVE_DLOPEN
-
-/* Define to 1 if you have the `dlsym' function. */
-#undef HAVE_DLSYM
-
-/* Whether errno() is available */
-#undef HAVE_ERRNO_DECL
-
-/* Define to 1 if you have the <fcntl.h> header file. */
-#undef HAVE_FCNTL_H
-
-/* Define to 1 if you have the <fnmatch.h> header file. */
-#undef HAVE_FNMATCH_H
-
-/* Define to 1 if you have the `ftruncate' function. */
-#undef HAVE_FTRUNCATE
-
-/* Whether there is a __FUNCTION__ macro */
-#undef HAVE_FUNCTION_MACRO
-
-/* Define to 1 if you have the `getdents' function. */
-#undef HAVE_GETDENTS
-
-/* Define to 1 if you have the `getdirentries' function. */
-#undef HAVE_GETDIRENTRIES
-
-/* Define to 1 if you have the `getpgrp' function. */
-#undef HAVE_GETPGRP
-
-/* Define to 1 if you have the <grp.h> header file. */
-#undef HAVE_GRP_H
-
-/* Whether the compiler supports immediate structures */
-#undef HAVE_IMMEDIATE_STRUCTURES
-
-/* Define to 1 if you have the `initgroups' function. */
-#undef HAVE_INITGROUPS
-
-/* Define to 1 if you have the <inttypes.h> header file. */
-#undef HAVE_INTTYPES_H
-
-/* Define to 1 if you have the <limits.h> header file. */
-#undef HAVE_LIMITS_H
-
-/* Define to 1 if you have the <locale.h> header file. */
-#undef HAVE_LOCALE_H
-
-/* Define to 1 if the system has the type `long long'. */
-#undef HAVE_LONG_LONG
-
-/* Define to 1 if you have the `lstat' function. */
-#undef HAVE_LSTAT
-
-/* Define to 1 if you have the `memcpy' function. */
-#undef HAVE_MEMCPY
-
-/* Define to 1 if you have the `memmove' function. */
-#undef HAVE_MEMMOVE
-
-/* Define to 1 if you have the <memory.h> header file. */
-#undef HAVE_MEMORY_H
-
-/* Define to 1 if you have the `memset' function. */
-#undef HAVE_MEMSET
-
-/* Define if target mkdir supports mode option */
-#undef HAVE_MKDIR_MODE
-
-/* Define to 1 if you have the `mkdtemp' function. */
-#undef HAVE_MKDTEMP
-
-/* Define to 1 if you have the `mktime' function. */
-#undef HAVE_MKTIME
-
-/* Whether mmap works */
-#undef HAVE_MMAP
-
-/* Define to 1 if you have the <ndir.h> header file, and it defines `DIR'. */
-#undef HAVE_NDIR_H
-
-/* Define to 1 if you have the <netdb.h> header file. */
-#undef HAVE_NETDB_H
-
-/* Define to 1 if you have the <netinet/in.h> header file. */
-#undef HAVE_NETINET_IN_H
-
-/* Define to 1 if you have the <netinet/in_ip.h> header file. */
-#undef HAVE_NETINET_IN_IP_H
-
-/* Define to 1 if you have the <netinet/in_systm.h> header file. */
-#undef HAVE_NETINET_IN_SYSTM_H
-
-/* Define to 1 if you have the <netinet/ip.h> header file. */
-#undef HAVE_NETINET_IP_H
-
-/* Define to 1 if you have the <netinet/tcp.h> header file. */
-#undef HAVE_NETINET_TCP_H
-
-/* usability of net/if.h */
-#undef HAVE_NET_IF_H
-
-/* Whether the open(2) accepts O_DIRECT */
-#undef HAVE_OPEN_O_DIRECT
-
-/* Define to 1 if you have the `pipe' function. */
-#undef HAVE_PIPE
-
-/* Define to 1 if you have the `pread' function. */
-#undef HAVE_PREAD
-
-/* Define to 1 if you have the `printf' function. */
-#undef HAVE_PRINTF
-
-/* Define to 1 if you have the <pwd.h> header file. */
-#undef HAVE_PWD_H
-
-/* Define to 1 if you have the `pwrite' function. */
-#undef HAVE_PWRITE
-
-/* Define to 1 if you have the `rand' function. */
-#undef HAVE_RAND
-
-/* Define to 1 if you have the `random' function. */
-#undef HAVE_RANDOM
-
-/* Define to 1 if you have the `rename' function. */
-#undef HAVE_RENAME
-
-/* Whether mkstemp is secure */
-#undef HAVE_SECURE_MKSTEMP
-
-/* Define to 1 if you have the `setbuffer' function. */
-#undef HAVE_SETBUFFER
-
-/* Define to 1 if you have the `setegid' function. */
-#undef HAVE_SETEGID
-
-/* Define to 1 if you have the `setenv' function. */
-#undef HAVE_SETENV
-
-/* Whether setenv() is available */
-#undef HAVE_SETENV_DECL
-
-/* Define to 1 if you have the `seteuid' function. */
-#undef HAVE_SETEUID
-
-/* Define to 1 if you have the <setjmp.h> header file. */
-#undef HAVE_SETJMP_H
-
-/* Define to 1 if you have the `setlinebuf' function. */
-#undef HAVE_SETLINEBUF
-
-/* Define to 1 if you have the `setresgid' function. */
-#undef HAVE_SETRESGID
-
-/* Whether setresgid() is available */
-#undef HAVE_SETRESGID_DECL
-
-/* Define to 1 if you have the `setresuid' function. */
-#undef HAVE_SETRESUID
-
-/* Whether setresuid() is available */
-#undef HAVE_SETRESUID_DECL
-
-/* Define to 1 if you have the <shadow.h> header file. */
-#undef HAVE_SHADOW_H
-
-/* Whether we have the atomic_t variable type */
-#undef HAVE_SIG_ATOMIC_T_TYPE
-
-/* Define to 1 if you have the `snprintf' function. */
-#undef HAVE_SNPRINTF
-
-/* Define to 1 if you have the `socketpair' function. */
-#undef HAVE_SOCKETPAIR
-
-/* Define to 1 if you have the `srand' function. */
-#undef HAVE_SRAND
-
-/* Define to 1 if you have the `srandom' function. */
-#undef HAVE_SRANDOM
-
-/* Define to 1 if you have the <standards.h> header file. */
-#undef HAVE_STANDARDS_H
-
-/* Define to 1 if you have the <stdarg.h> header file. */
-#undef HAVE_STDARG_H
-
-/* Define to 1 if you have the <stdbool.h> header file. */
-#undef HAVE_STDBOOL_H
-
-/* Define to 1 if you have the <stdint.h> header file. */
-#undef HAVE_STDINT_H
-
-/* Define to 1 if you have the <stdio.h> header file. */
-#undef HAVE_STDIO_H
-
-/* Define to 1 if you have the <stdlib.h> header file. */
-#undef HAVE_STDLIB_H
-
-/* Define to 1 if you have the `strcasestr' function. */
-#undef HAVE_STRCASESTR
-
-/* Define to 1 if you have the `strdup' function. */
-#undef HAVE_STRDUP
-
-/* Define to 1 if you have the `strerror' function. */
-#undef HAVE_STRERROR
-
-/* Define to 1 if you have the `strftime' function. */
-#undef HAVE_STRFTIME
-
-/* Define to 1 if you have the <strings.h> header file. */
-#undef HAVE_STRINGS_H
-
-/* Define to 1 if you have the <string.h> header file. */
-#undef HAVE_STRING_H
-
-/* Define to 1 if you have the `strlcat' function. */
-#undef HAVE_STRLCAT
-
-/* Define to 1 if you have the `strlcpy' function. */
-#undef HAVE_STRLCPY
-
-/* Define to 1 if you have the `strndup' function. */
-#undef HAVE_STRNDUP
-
-/* Define to 1 if you have the `strnlen' function. */
-#undef HAVE_STRNLEN
-
-/* Define to 1 if you have the `strtok_r' function. */
-#undef HAVE_STRTOK_R
-
-/* Define to 1 if you have the `strtoll' function. */
-#undef HAVE_STRTOLL
-
-/* Define to 1 if you have the `strtoq' function. */
-#undef HAVE_STRTOQ
-
-/* Define to 1 if you have the `strtoull' function. */
-#undef HAVE_STRTOULL
-
-/* Define to 1 if you have the `strtouq' function. */
-#undef HAVE_STRTOUQ
-
-/* Define to 1 if `st_rdev' is member of `struct stat'. */
-#undef HAVE_STRUCT_STAT_ST_RDEV
-
-/* Define to 1 if your `struct stat' has `st_rdev'. Deprecated, use
-   `HAVE_STRUCT_STAT_ST_RDEV' instead. */
-#undef HAVE_ST_RDEV
-
-/* Define to 1 if you have the `syslog' function. */
-#undef HAVE_SYSLOG
-
-/* Define to 1 if you have the <syslog.h> header file. */
-#undef HAVE_SYSLOG_H
-
-/* Define to 1 if you have the <sys/acl.h> header file. */
-#undef HAVE_SYS_ACL_H
-
-/* Define to 1 if you have the <sys/capability.h> header file. */
-#undef HAVE_SYS_CAPABILITY_H
-
-/* Define to 1 if you have the <sys/dir.h> header file, and it defines `DIR'.
-   */
-#undef HAVE_SYS_DIR_H
-
-/* Define to 1 if you have the <sys/fcntl.h> header file. */
-#undef HAVE_SYS_FCNTL_H
-
-/* Define to 1 if you have the <sys/filio.h> header file. */
-#undef HAVE_SYS_FILIO_H
-
-/* Define to 1 if you have the <sys/filsys.h> header file. */
-#undef HAVE_SYS_FILSYS_H
-
-/* Define to 1 if you have the <sys/fs/s5param.h> header file. */
-#undef HAVE_SYS_FS_S5PARAM_H
-
-/* Define to 1 if you have the <sys/id.h> header file. */
-#undef HAVE_SYS_ID_H
-
-/* Define to 1 if you have the <sys/ioctl.h> header file. */
-#undef HAVE_SYS_IOCTL_H
-
-/* Define to 1 if you have the <sys/ipc.h> header file. */
-#undef HAVE_SYS_IPC_H
-
-/* Define to 1 if you have the <sys/mman.h> header file. */
-#undef HAVE_SYS_MMAN_H
-
-/* Define to 1 if you have the <sys/mode.h> header file. */
-#undef HAVE_SYS_MODE_H
-
-/* Define to 1 if you have the <sys/ndir.h> header file, and it defines `DIR'.
-   */
-#undef HAVE_SYS_NDIR_H
-
-/* Define to 1 if you have the <sys/param.h> header file. */
-#undef HAVE_SYS_PARAM_H
-
-/* Define to 1 if you have the <sys/priv.h> header file. */
-#undef HAVE_SYS_PRIV_H
-
-/* Define to 1 if you have the <sys/resource.h> header file. */
-#undef HAVE_SYS_RESOURCE_H
-
-/* Define to 1 if you have the <sys/security.h> header file. */
-#undef HAVE_SYS_SECURITY_H
-
-/* Define to 1 if you have the <sys/select.h> header file. */
-#undef HAVE_SYS_SELECT_H
-
-/* Define to 1 if you have the <sys/shm.h> header file. */
-#undef HAVE_SYS_SHM_H
-
-/* Define to 1 if you have the <sys/socket.h> header file. */
-#undef HAVE_SYS_SOCKET_H
-
-/* Define to 1 if you have the <sys/sockio.h> header file. */
-#undef HAVE_SYS_SOCKIO_H
-
-/* Define to 1 if you have the <sys/stat.h> header file. */
-#undef HAVE_SYS_STAT_H
-
-/* Define to 1 if you have the <sys/syslog.h> header file. */
-#undef HAVE_SYS_SYSLOG_H
-
-/* Define to 1 if you have the <sys/termio.h> header file. */
-#undef HAVE_SYS_TERMIO_H
-
-/* Define to 1 if you have the <sys/time.h> header file. */
-#undef HAVE_SYS_TIME_H
-
-/* Define to 1 if you have the <sys/types.h> header file. */
-#undef HAVE_SYS_TYPES_H
-
-/* Define to 1 if you have the <sys/un.h> header file. */
-#undef HAVE_SYS_UN_H
-
-/* Define to 1 if you have <sys/wait.h> that is POSIX.1 compatible. */
-#undef HAVE_SYS_WAIT_H
-
-/* Define to 1 if you have the <termios.h> header file. */
-#undef HAVE_TERMIOS_H
-
-/* Define to 1 if you have the <termio.h> header file. */
-#undef HAVE_TERMIO_H
-
-/* Define to 1 if you have the `timegm' function. */
-#undef HAVE_TIMEGM
-
-/* Define to 1 if you have the <time.h> header file. */
-#undef HAVE_TIME_H
-
-/* Define to 1 if you have the <unistd.h> header file. */
-#undef HAVE_UNISTD_H
-
-/* Define to 1 if you have the `unsetenv' function. */
-#undef HAVE_UNSETENV
-
-/* Define to 1 if you have the `usleep' function. */
-#undef HAVE_USLEEP
-
-/* Define to 1 if you have the <utime.h> header file. */
-#undef HAVE_UTIME_H
-
-/* Define to 1 if you have the <vararg.h> header file. */
-#undef HAVE_VARARG_H
-
-/* Define to 1 if you have the `vasprintf' function. */
-#undef HAVE_VASPRINTF
-
-/* Whether va_copy() is available */
-#undef HAVE_VA_COPY
-
-/* Whether the C compiler understands volatile */
-#undef HAVE_VOLATILE
-
-/* Define to 1 if you have the `vsnprintf' function. */
-#undef HAVE_VSNPRINTF
-
-/* Define to 1 if you have the `vsyslog' function. */
-#undef HAVE_VSYSLOG
-
-/* Define to 1 if you have the `waitpid' function. */
-#undef HAVE_WAITPID
-
-/* Define to 1 if you have the <windows.h> header file. */
-#undef HAVE_WINDOWS_H
-
-/* Define to 1 if you have the <winsock2.h> header file. */
-#undef HAVE_WINSOCK2_H
-
-/* Define to 1 if you have the <ws2tcpip.h> header file. */
-#undef HAVE_WS2TCPIP_H
-
-/* Whether the _Bool type is available */
-#undef HAVE__Bool
-
-/* Whether the __VA_ARGS__ macro is available */
-#undef HAVE__VA_ARGS__MACRO
-
-/* Define to 1 if you have the `__strtoll' function. */
-#undef HAVE___STRTOLL
-
-/* Define to 1 if you have the `__strtoull' function. */
-#undef HAVE___STRTOULL
-
-/* Whether __va_copy() is available */
-#undef HAVE___VA_COPY
-
-/* Whether there is a __func__ macro */
-#undef HAVE_func_MACRO
-
-/* Whether MMAP is broken */
-#undef MMAP_BLACKLIST
-
-/* Define to the address where bug reports for this package should be sent. */
-#undef PACKAGE_BUGREPORT
-
-/* Define to the full name of this package. */
-#undef PACKAGE_NAME
-
-/* Define to the full name and version of this package. */
-#undef PACKAGE_STRING
-
-/* Define to the one symbol short name of this package. */
-#undef PACKAGE_TARNAME
-
-/* Define to the version of this package. */
-#undef PACKAGE_VERSION
-
-/* Whether getpass should be replaced */
-#undef REPLACE_GETPASS
-
-/* Whether inet_ntoa should be replaced */
-#undef REPLACE_INET_NTOA
-
-/* replace readdir */
-#undef REPLACE_READDIR
-
-/* replace readdir using getdents() */
-#undef REPLACE_READDIR_GETDENTS
-
-/* replace readdir using getdirentries() */
-#undef REPLACE_READDIR_GETDIRENTRIES
-
-/* Whether strptime should be replaced */
-#undef REPLACE_STRPTIME
-
-/* Define as the return type of signal handlers (`int' or `void'). */
-#undef RETSIGTYPE
-
-/* Whether seekdir returns an int */
-#undef SEEKDIR_RETURNS_INT
-
-/* The size of `char', as computed by sizeof. */
-#undef SIZEOF_CHAR
-
-/* The size of `int', as computed by sizeof. */
-#undef SIZEOF_INT
-
-/* The size of `long', as computed by sizeof. */
-#undef SIZEOF_LONG
-
-/* The size of `long long', as computed by sizeof. */
-#undef SIZEOF_LONG_LONG
-
-/* The size of `off_t', as computed by sizeof. */
-#undef SIZEOF_OFF_T
-
-/* The size of `short', as computed by sizeof. */
-#undef SIZEOF_SHORT
-
-/* The size of `size_t', as computed by sizeof. */
-#undef SIZEOF_SIZE_T
-
-/* The size of `ssize_t', as computed by sizeof. */
-#undef SIZEOF_SSIZE_T
-
-/* Define to 1 if you have the ANSI C header files. */
-#undef STDC_HEADERS
-
-/* Whether telldir takes a const pointer */
-#undef TELLDIR_TAKES_CONST_DIR
-
-/* Define to 1 if you can safely include both <sys/time.h> and <time.h>. */
-#undef TIME_WITH_SYS_TIME
-
-/* Define to 1 if your processor stores words with the most significant byte
-   first (like Motorola and SPARC, unlike Intel and VAX). */
-#undef WORDS_BIGENDIAN
-
-/* Define to 1 if on AIX 3.
-   System headers sometimes define this.
-   We just want to avoid a redefinition error message.  */
-#ifndef _ALL_SOURCE
-# undef _ALL_SOURCE
-#endif
-
-/* Number of bits in a file offset, on hosts where this is settable. */
-#undef _FILE_OFFSET_BITS
-
-/* Enable GNU extensions on systems that have them.  */
-#ifndef _GNU_SOURCE
-# undef _GNU_SOURCE
-#endif
-
-/* Define for large files, on AIX-style hosts. */
-#undef _LARGE_FILES
-
-/* Define to 1 if on MINIX. */
-#undef _MINIX
-
-#ifndef _OSF_SOURCE
-# define _OSF_SOURCE 1
-#endif
-
-/* Define to 2 if the system does not provide POSIX.1 features except with
-   this defined. */
-#undef _POSIX_1_SOURCE
-
-/* Whether to enable POSIX support */
-#undef _POSIX_C_SOURCE
-
-/* Define to 1 if you need to in order for `stat' and other things to work. */
-#undef _POSIX_SOURCE
-
-/* Whether to enable System V compatibility */
-#undef _SYSV
-
-#ifndef _XOPEN_SOURCE_EXTENDED
-# define _XOPEN_SOURCE_EXTENDED 1
-#endif
-
-/* Enable extensions on Solaris.  */
-#ifndef __EXTENSIONS__
-# undef __EXTENSIONS__
-#endif
-#ifndef _POSIX_PTHREAD_SEMANTICS
-# undef _POSIX_PTHREAD_SEMANTICS
-#endif
-
-/* Define to `int' if <sys/types.h> doesn't define. */
-#undef gid_t
-
-/* Define to `__inline__' or `__inline' if that's what the C compiler
-   calls it, or to nothing if 'inline' is not supported under any name.  */
-#ifndef __cplusplus
-#undef inline
-#endif
-
-/* Define to `unsigned' if <sys/types.h> does not define. */
-#undef ino_t
-
-/* Define to `short' if <sys/types.h> does not define. */
-#undef int16_t
-
-/* Define to `long' if <sys/types.h> does not define. */
-#undef int32_t
-
-/* Define to `long long' if <sys/types.h> does not define. */
-#undef int64_t
-
-/* Define to `char' if <sys/types.h> does not define. */
-#undef int8_t
-
-/* Define to `unsigned long long' if <sys/types.h> does not define. */
-#undef intptr_t
-
-/* Define to `off_t' if <sys/types.h> does not define. */
-#undef loff_t
-
-/* Define to `int' if <sys/types.h> does not define. */
-#undef mode_t
-
-/* Define to `long int' if <sys/types.h> does not define. */
-#undef off_t
-
-/* Define to `loff_t' if <sys/types.h> does not define. */
-#undef offset_t
-
-/* Define to `int' if <sys/types.h> does not define. */
-#undef pid_t
-
-/* Define to `unsigned long long' if <sys/types.h> does not define. */
-#undef ptrdiff_t
-
-/* Define to `unsigned int' if <sys/types.h> does not define. */
-#undef size_t
-
-/* Socket length type */
-#undef socklen_t
-
-/* Define to `int' if <sys/types.h> does not define. */
-#undef ssize_t
-
-/* Define to `int' if <sys/types.h> doesn't define. */
-#undef uid_t
-
-/* Define to `unsigned short' if <sys/types.h> does not define. */
-#undef uint16_t
-
-/* Define to `unsigned long' if <sys/types.h> does not define. */
-#undef uint32_t
-
-/* Define to `unsigned long long' if <sys/types.h> does not define. */
-#undef uint64_t
-
-/* Define to `unsigned char' if <sys/types.h> does not define. */
-#undef uint8_t
-
-/* Define to `unsigned int' if <sys/types.h> does not define. */
-#undef uint_t
diff --git a/lib/replace/config.sub b/lib/replace/config.sub
deleted file mode 100755
index a39437d..0000000
--- a/lib/replace/config.sub
+++ /dev/null
@@ -1,1686 +0,0 @@
-#! /bin/sh
-# Configuration validation subroutine script.
-#   Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999,
-#   2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008
-#   Free Software Foundation, Inc.
-
-timestamp='2009-04-17'
-
-# This file is (in principle) common to ALL GNU software.
-# The presence of a machine in this file suggests that SOME GNU software
-# can handle that machine.  It does not imply ALL GNU software can.
-#
-# This file 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., 51 Franklin Street - Fifth Floor, Boston, MA
-# 02110-1301, USA.
-#
-# As a special exception to the GNU General Public License, if you
-# distribute this file as part of a program that contains a
-# configuration script generated by Autoconf, you may include it under
-# the same distribution terms that you use for the rest of that program.
-
-
-# Please send patches to <config-patches at gnu.org>.  Submit a context
-# diff and a properly formatted ChangeLog entry.
-#
-# Configuration subroutine to validate and canonicalize a configuration type.
-# Supply the specified configuration type as an argument.
-# If it is invalid, we print an error message on stderr and exit with code 1.
-# Otherwise, we print the canonical config type on stdout and succeed.
-
-# This file is supposed to be the same for all GNU packages
-# and recognize all the CPU types, system types and aliases
-# that are meaningful with *any* GNU software.
-# Each package is responsible for reporting which valid configurations
-# it does not support.  The user should be able to distinguish
-# a failure to support a valid configuration from a meaningless
-# configuration.
-
-# The goal of this file is to map all the various variations of a given
-# machine specification into a single specification in the form:
-#	CPU_TYPE-MANUFACTURER-OPERATING_SYSTEM
-# or in some cases, the newer four-part form:
-#	CPU_TYPE-MANUFACTURER-KERNEL-OPERATING_SYSTEM
-# It is wrong to echo any other type of specification.
-
-me=`echo "$0" | sed -e 's,.*/,,'`
-
-usage="\
-Usage: $0 [OPTION] CPU-MFR-OPSYS
-       $0 [OPTION] ALIAS
-
-Canonicalize a configuration name.
-
-Operation modes:
-  -h, --help         print this help, then exit
-  -t, --time-stamp   print date of last modification, then exit
-  -v, --version      print version number, then exit
-
-Report bugs and patches to <config-patches at gnu.org>."
-
-version="\
-GNU config.sub ($timestamp)
-
-Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001,
-2002, 2003, 2004, 2005, 2006, 2007, 2008 Free Software Foundation, Inc.
-
-This is free software; see the source for copying conditions.  There is NO
-warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE."
-
-help="
-Try \`$me --help' for more information."
-
-# Parse command line
-while test $# -gt 0 ; do
-  case $1 in
-    --time-stamp | --time* | -t )
-       echo "$timestamp" ; exit ;;
-    --version | -v )
-       echo "$version" ; exit ;;
-    --help | --h* | -h )
-       echo "$usage"; exit ;;
-    -- )     # Stop option processing
-       shift; break ;;
-    - )	# Use stdin as input.
-       break ;;
-    -* )
-       echo "$me: invalid option $1$help"
-       exit 1 ;;
-
-    *local*)
-       # First pass through any local machine types.
-       echo $1
-       exit ;;
-
-    * )
-       break ;;
-  esac
-done
-
-case $# in
- 0) echo "$me: missing argument$help" >&2
-    exit 1;;
- 1) ;;
- *) echo "$me: too many arguments$help" >&2
-    exit 1;;
-esac
-
-# Separate what the user gave into CPU-COMPANY and OS or KERNEL-OS (if any).
-# Here we must recognize all the valid KERNEL-OS combinations.
-maybe_os=`echo $1 | sed 's/^\(.*\)-\([^-]*-[^-]*\)$/\2/'`
-case $maybe_os in
-  nto-qnx* | linux-gnu* | linux-dietlibc | linux-newlib* | linux-uclibc* | \
-  uclinux-uclibc* | uclinux-gnu* | kfreebsd*-gnu* | knetbsd*-gnu* | netbsd*-gnu* | \
-  kopensolaris*-gnu* | \
-  storm-chaos* | os2-emx* | rtmk-nova*)
-    os=-$maybe_os
-    basic_machine=`echo $1 | sed 's/^\(.*\)-\([^-]*-[^-]*\)$/\1/'`
-    ;;
-  *)
-    basic_machine=`echo $1 | sed 's/-[^-]*$//'`
-    if [ $basic_machine != $1 ]
-    then os=`echo $1 | sed 's/.*-/-/'`
-    else os=; fi
-    ;;
-esac
-
-### Let's recognize common machines as not being operating systems so
-### that things like config.sub decstation-3100 work.  We also
-### recognize some manufacturers as not being operating systems, so we
-### can provide default operating systems below.
-case $os in
-	-sun*os*)
-		# Prevent following clause from handling this invalid input.
-		;;
-	-dec* | -mips* | -sequent* | -encore* | -pc532* | -sgi* | -sony* | \
-	-att* | -7300* | -3300* | -delta* | -motorola* | -sun[234]* | \
-	-unicom* | -ibm* | -next | -hp | -isi* | -apollo | -altos* | \
-	-convergent* | -ncr* | -news | -32* | -3600* | -3100* | -hitachi* |\
-	-c[123]* | -convex* | -sun | -crds | -omron* | -dg | -ultra | -tti* | \
-	-harris | -dolphin | -highlevel | -gould | -cbm | -ns | -masscomp | \
-	-apple | -axis | -knuth | -cray)
-		os=
-		basic_machine=$1
-		;;
-	-sim | -cisco | -oki | -wec | -winbond)
-		os=
-		basic_machine=$1
-		;;
-	-scout)
-		;;
-	-wrs)
-		os=-vxworks
-		basic_machine=$1
-		;;
-	-chorusos*)
-		os=-chorusos
-		basic_machine=$1
-		;;
- 	-chorusrdb)
- 		os=-chorusrdb
-		basic_machine=$1
- 		;;
-	-hiux*)
-		os=-hiuxwe2
-		;;
-	-sco6)
-		os=-sco5v6
-		basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
-		;;
-	-sco5)
-		os=-sco3.2v5
-		basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
-		;;
-	-sco4)
-		os=-sco3.2v4
-		basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
-		;;
-	-sco3.2.[4-9]*)
-		os=`echo $os | sed -e 's/sco3.2./sco3.2v/'`
-		basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
-		;;
-	-sco3.2v[4-9]*)
-		# Don't forget version if it is 3.2v4 or newer.
-		basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
-		;;
-	-sco5v6*)
-		# Don't forget version if it is 3.2v4 or newer.
-		basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
-		;;
-	-sco*)
-		os=-sco3.2v2
-		basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
-		;;
-	-udk*)
-		basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
-		;;
-	-isc)
-		os=-isc2.2
-		basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
-		;;
-	-clix*)
-		basic_machine=clipper-intergraph
-		;;
-	-isc*)
-		basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
-		;;
-	-lynx*)
-		os=-lynxos
-		;;
-	-ptx*)
-		basic_machine=`echo $1 | sed -e 's/86-.*/86-sequent/'`
-		;;
-	-windowsnt*)
-		os=`echo $os | sed -e 's/windowsnt/winnt/'`
-		;;
-	-psos*)
-		os=-psos
-		;;
-	-mint | -mint[0-9]*)
-		basic_machine=m68k-atari
-		os=-mint
-		;;
-esac
-
-# Decode aliases for certain CPU-COMPANY combinations.
-case $basic_machine in
-	# Recognize the basic CPU types without company name.
-	# Some are omitted here because they have special meanings below.
-	1750a | 580 \
-	| a29k \
-	| alpha | alphaev[4-8] | alphaev56 | alphaev6[78] | alphapca5[67] \
-	| alpha64 | alpha64ev[4-8] | alpha64ev56 | alpha64ev6[78] | alpha64pca5[67] \
-	| am33_2.0 \
-	| arc | arm | arm[bl]e | arme[lb] | armv[2345] | armv[345][lb] | avr | avr32 \
-	| bfin \
-	| c4x | clipper \
-	| d10v | d30v | dlx | dsp16xx \
-	| fido | fr30 | frv \
-	| h8300 | h8500 | hppa | hppa1.[01] | hppa2.0 | hppa2.0[nw] | hppa64 \
-	| i370 | i860 | i960 | ia64 \
-	| ip2k | iq2000 \
-	| lm32 \
-	| m32c | m32r | m32rle | m68000 | m68k | m88k \
-	| maxq | mb | microblaze | mcore | mep | metag \
-	| mips | mipsbe | mipseb | mipsel | mipsle \
-	| mips16 \
-	| mips64 | mips64el \
-	| mips64octeon | mips64octeonel \
-	| mips64orion | mips64orionel \
-	| mips64r5900 | mips64r5900el \
-	| mips64vr | mips64vrel \
-	| mips64vr4100 | mips64vr4100el \
-	| mips64vr4300 | mips64vr4300el \
-	| mips64vr5000 | mips64vr5000el \
-	| mips64vr5900 | mips64vr5900el \
-	| mipsisa32 | mipsisa32el \
-	| mipsisa32r2 | mipsisa32r2el \
-	| mipsisa64 | mipsisa64el \
-	| mipsisa64r2 | mipsisa64r2el \
-	| mipsisa64sb1 | mipsisa64sb1el \
-	| mipsisa64sr71k | mipsisa64sr71kel \
-	| mipstx39 | mipstx39el \
-	| mn10200 | mn10300 \
-	| moxie \
-	| mt \
-	| msp430 \
-	| nios | nios2 \
-	| ns16k | ns32k \
-	| or32 \
-	| pdp10 | pdp11 | pj | pjl \
-	| powerpc | powerpc64 | powerpc64le | powerpcle | ppcbe \
-	| pyramid \
-	| score \
-	| sh | sh[1234] | sh[24]a | sh[24]aeb | sh[23]e | sh[34]eb | sheb | shbe | shle | sh[1234]le | sh3ele \
-	| sh64 | sh64le \
-	| sparc | sparc64 | sparc64b | sparc64v | sparc86x | sparclet | sparclite \
-	| sparcv8 | sparcv9 | sparcv9b | sparcv9v \
-	| spu | strongarm \
-	| tahoe | thumb | tic4x | tic80 | tron \
-	| v850 | v850e \
-	| we32k \
-	| x86 | xc16x | xscale | xscalee[bl] | xstormy16 | xtensa \
-	| z8k | z80)
-		basic_machine=$basic_machine-unknown
-		;;
-	m6811 | m68hc11 | m6812 | m68hc12)
-		# Motorola 68HC11/12.
-		basic_machine=$basic_machine-unknown
-		os=-none
-		;;
-	m88110 | m680[12346]0 | m683?2 | m68360 | m5200 | v70 | w65 | z8k)
-		;;
-	ms1)
-		basic_machine=mt-unknown
-		;;
-
-	# We use `pc' rather than `unknown'
-	# because (1) that's what they normally are, and
-	# (2) the word "unknown" tends to confuse beginning users.
-	i*86 | x86_64)
-	  basic_machine=$basic_machine-pc
-	  ;;
-	# Object if more than one company name word.
-	*-*-*)
-		echo Invalid configuration \`$1\': machine \`$basic_machine\' not recognized 1>&2
-		exit 1
-		;;
-	# Recognize the basic CPU types with company name.
-	580-* \
-	| a29k-* \
-	| alpha-* | alphaev[4-8]-* | alphaev56-* | alphaev6[78]-* \
-	| alpha64-* | alpha64ev[4-8]-* | alpha64ev56-* | alpha64ev6[78]-* \
-	| alphapca5[67]-* | alpha64pca5[67]-* | arc-* \
-	| arm-*  | armbe-* | armle-* | armeb-* | armv*-* \
-	| avr-* | avr32-* \
-	| bfin-* | bs2000-* \
-	| c[123]* | c30-* | [cjt]90-* | c4x-* | c54x-* | c55x-* | c6x-* \
-	| clipper-* | craynv-* | cydra-* \
-	| d10v-* | d30v-* | dlx-* \
-	| elxsi-* \
-	| f30[01]-* | f700-* | fido-* | fr30-* | frv-* | fx80-* \
-	| h8300-* | h8500-* \
-	| hppa-* | hppa1.[01]-* | hppa2.0-* | hppa2.0[nw]-* | hppa64-* \
-	| i*86-* | i860-* | i960-* | ia64-* \
-	| ip2k-* | iq2000-* \
-	| lm32-* \
-	| m32c-* | m32r-* | m32rle-* \
-	| m68000-* | m680[012346]0-* | m68360-* | m683?2-* | m68k-* \
-	| m88110-* | m88k-* | maxq-* | mcore-* | metag-* \
-	| mips-* | mipsbe-* | mipseb-* | mipsel-* | mipsle-* \
-	| mips16-* \
-	| mips64-* | mips64el-* \
-	| mips64octeon-* | mips64octeonel-* \
-	| mips64orion-* | mips64orionel-* \
-	| mips64r5900-* | mips64r5900el-* \
-	| mips64vr-* | mips64vrel-* \
-	| mips64vr4100-* | mips64vr4100el-* \
-	| mips64vr4300-* | mips64vr4300el-* \
-	| mips64vr5000-* | mips64vr5000el-* \
-	| mips64vr5900-* | mips64vr5900el-* \
-	| mipsisa32-* | mipsisa32el-* \
-	| mipsisa32r2-* | mipsisa32r2el-* \
-	| mipsisa64-* | mipsisa64el-* \
-	| mipsisa64r2-* | mipsisa64r2el-* \
-	| mipsisa64sb1-* | mipsisa64sb1el-* \
-	| mipsisa64sr71k-* | mipsisa64sr71kel-* \
-	| mipstx39-* | mipstx39el-* \
-	| mmix-* \
-	| mt-* \
-	| msp430-* \
-	| nios-* | nios2-* \
-	| none-* | np1-* | ns16k-* | ns32k-* \
-	| orion-* \
-	| pdp10-* | pdp11-* | pj-* | pjl-* | pn-* | power-* \
-	| powerpc-* | powerpc64-* | powerpc64le-* | powerpcle-* | ppcbe-* \
-	| pyramid-* \
-	| romp-* | rs6000-* \
-	| sh-* | sh[1234]-* | sh[24]a-* | sh[24]aeb-* | sh[23]e-* | sh[34]eb-* | sheb-* | shbe-* \
-	| shle-* | sh[1234]le-* | sh3ele-* | sh64-* | sh64le-* \
-	| sparc-* | sparc64-* | sparc64b-* | sparc64v-* | sparc86x-* | sparclet-* \
-	| sparclite-* \
-	| sparcv8-* | sparcv9-* | sparcv9b-* | sparcv9v-* | strongarm-* | sv1-* | sx?-* \
-	| tahoe-* | thumb-* \
-	| tic30-* | tic4x-* | tic54x-* | tic55x-* | tic6x-* | tic80-* | tile-* \
-	| tron-* \
-	| v850-* | v850e-* | vax-* \
-	| we32k-* \
-	| x86-* | x86_64-* | xc16x-* | xps100-* | xscale-* | xscalee[bl]-* \
-	| xstormy16-* | xtensa*-* \
-	| ymp-* \
-	| z8k-* | z80-*)
-		;;
-	# Recognize the basic CPU types without company name, with glob match.
-	xtensa*)
-		basic_machine=$basic_machine-unknown
-		;;
-	# Recognize the various machine names and aliases which stand
-	# for a CPU type and a company and sometimes even an OS.
-	386bsd)
-		basic_machine=i386-unknown
-		os=-bsd
-		;;
-	3b1 | 7300 | 7300-att | att-7300 | pc7300 | safari | unixpc)
-		basic_machine=m68000-att
-		;;
-	3b*)
-		basic_machine=we32k-att
-		;;
-	a29khif)
-		basic_machine=a29k-amd
-		os=-udi
-		;;
-    	abacus)
-		basic_machine=abacus-unknown
-		;;
-	adobe68k)
-		basic_machine=m68010-adobe
-		os=-scout
-		;;
-	alliant | fx80)
-		basic_machine=fx80-alliant
-		;;
-	altos | altos3068)
-		basic_machine=m68k-altos
-		;;
-	am29k)
-		basic_machine=a29k-none
-		os=-bsd
-		;;
-	amd64)
-		basic_machine=x86_64-pc
-		;;
-	amd64-*)
-		basic_machine=x86_64-`echo $basic_machine | sed 's/^[^-]*-//'`
-		;;
-	amdahl)
-		basic_machine=580-amdahl
-		os=-sysv
-		;;
-	amiga | amiga-*)
-		basic_machine=m68k-unknown
-		;;
-	amigaos | amigados)
-		basic_machine=m68k-unknown
-		os=-amigaos
-		;;
-	amigaunix | amix)
-		basic_machine=m68k-unknown
-		os=-sysv4
-		;;
-	apollo68)
-		basic_machine=m68k-apollo
-		os=-sysv
-		;;
-	apollo68bsd)
-		basic_machine=m68k-apollo
-		os=-bsd
-		;;
-	aros)
-		basic_machine=i386-pc
-		os=-aros
-		;;
-	aux)
-		basic_machine=m68k-apple
-		os=-aux
-		;;
-	balance)
-		basic_machine=ns32k-sequent
-		os=-dynix
-		;;
-	blackfin)
-		basic_machine=bfin-unknown
-		os=-linux
-		;;
-	blackfin-*)
-		basic_machine=bfin-`echo $basic_machine | sed 's/^[^-]*-//'`
-		os=-linux
-		;;
-	c90)
-		basic_machine=c90-cray
-		os=-unicos
-		;;
-        cegcc)
-		basic_machine=arm-unknown
-		os=-cegcc
-		;;
-	convex-c1)
-		basic_machine=c1-convex
-		os=-bsd
-		;;
-	convex-c2)
-		basic_machine=c2-convex
-		os=-bsd
-		;;
-	convex-c32)
-		basic_machine=c32-convex
-		os=-bsd
-		;;
-	convex-c34)
-		basic_machine=c34-convex
-		os=-bsd
-		;;
-	convex-c38)
-		basic_machine=c38-convex
-		os=-bsd
-		;;
-	cray | j90)
-		basic_machine=j90-cray
-		os=-unicos
-		;;
-	craynv)
-		basic_machine=craynv-cray
-		os=-unicosmp
-		;;
-	cr16)
-		basic_machine=cr16-unknown
-		os=-elf
-		;;
-	crds | unos)
-		basic_machine=m68k-crds
-		;;
-	crisv32 | crisv32-* | etraxfs*)
-		basic_machine=crisv32-axis
-		;;
-	cris | cris-* | etrax*)
-		basic_machine=cris-axis
-		;;
-	crx)
-		basic_machine=crx-unknown
-		os=-elf
-		;;
-	da30 | da30-*)
-		basic_machine=m68k-da30
-		;;
-	decstation | decstation-3100 | pmax | pmax-* | pmin | dec3100 | decstatn)
-		basic_machine=mips-dec
-		;;
-	decsystem10* | dec10*)
-		basic_machine=pdp10-dec
-		os=-tops10
-		;;
-	decsystem20* | dec20*)
-		basic_machine=pdp10-dec
-		os=-tops20
-		;;
-	delta | 3300 | motorola-3300 | motorola-delta \
-	      | 3300-motorola | delta-motorola)
-		basic_machine=m68k-motorola
-		;;
-	delta88)
-		basic_machine=m88k-motorola
-		os=-sysv3
-		;;
-	dicos)
-		basic_machine=i686-pc
-		os=-dicos
-		;;
-	djgpp)
-		basic_machine=i586-pc
-		os=-msdosdjgpp
-		;;
-	dpx20 | dpx20-*)
-		basic_machine=rs6000-bull
-		os=-bosx
-		;;
-	dpx2* | dpx2*-bull)
-		basic_machine=m68k-bull
-		os=-sysv3
-		;;
-	ebmon29k)
-		basic_machine=a29k-amd
-		os=-ebmon
-		;;
-	elxsi)
-		basic_machine=elxsi-elxsi
-		os=-bsd
-		;;
-	encore | umax | mmax)
-		basic_machine=ns32k-encore
-		;;
-	es1800 | OSE68k | ose68k | ose | OSE)
-		basic_machine=m68k-ericsson
-		os=-ose
-		;;
-	fx2800)
-		basic_machine=i860-alliant
-		;;
-	genix)
-		basic_machine=ns32k-ns
-		;;
-	gmicro)
-		basic_machine=tron-gmicro
-		os=-sysv
-		;;
-	go32)
-		basic_machine=i386-pc
-		os=-go32
-		;;
-	h3050r* | hiux*)
-		basic_machine=hppa1.1-hitachi
-		os=-hiuxwe2
-		;;
-	h8300hms)
-		basic_machine=h8300-hitachi
-		os=-hms
-		;;
-	h8300xray)
-		basic_machine=h8300-hitachi
-		os=-xray
-		;;
-	h8500hms)
-		basic_machine=h8500-hitachi
-		os=-hms
-		;;
-	harris)
-		basic_machine=m88k-harris
-		os=-sysv3
-		;;
-	hp300-*)
-		basic_machine=m68k-hp
-		;;
-	hp300bsd)
-		basic_machine=m68k-hp
-		os=-bsd
-		;;
-	hp300hpux)
-		basic_machine=m68k-hp
-		os=-hpux
-		;;
-	hp3k9[0-9][0-9] | hp9[0-9][0-9])
-		basic_machine=hppa1.0-hp
-		;;
-	hp9k2[0-9][0-9] | hp9k31[0-9])
-		basic_machine=m68000-hp
-		;;
-	hp9k3[2-9][0-9])
-		basic_machine=m68k-hp
-		;;
-	hp9k6[0-9][0-9] | hp6[0-9][0-9])
-		basic_machine=hppa1.0-hp
-		;;
-	hp9k7[0-79][0-9] | hp7[0-79][0-9])
-		basic_machine=hppa1.1-hp
-		;;
-	hp9k78[0-9] | hp78[0-9])
-		# FIXME: really hppa2.0-hp
-		basic_machine=hppa1.1-hp
-		;;
-	hp9k8[67]1 | hp8[67]1 | hp9k80[24] | hp80[24] | hp9k8[78]9 | hp8[78]9 | hp9k893 | hp893)
-		# FIXME: really hppa2.0-hp
-		basic_machine=hppa1.1-hp
-		;;
-	hp9k8[0-9][13679] | hp8[0-9][13679])
-		basic_machine=hppa1.1-hp
-		;;
-	hp9k8[0-9][0-9] | hp8[0-9][0-9])
-		basic_machine=hppa1.0-hp
-		;;
-	hppa-next)
-		os=-nextstep3
-		;;
-	hppaosf)
-		basic_machine=hppa1.1-hp
-		os=-osf
-		;;
-	hppro)
-		basic_machine=hppa1.1-hp
-		os=-proelf
-		;;
-	i370-ibm* | ibm*)
-		basic_machine=i370-ibm
-		;;
-# I'm not sure what "Sysv32" means.  Should this be sysv3.2?
-	i*86v32)
-		basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'`
-		os=-sysv32
-		;;
-	i*86v4*)
-		basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'`
-		os=-sysv4
-		;;
-	i*86v)
-		basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'`
-		os=-sysv
-		;;
-	i*86sol2)
-		basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'`
-		os=-solaris2
-		;;
-	i386mach)
-		basic_machine=i386-mach
-		os=-mach
-		;;
-	i386-vsta | vsta)
-		basic_machine=i386-unknown
-		os=-vsta
-		;;
-	iris | iris4d)
-		basic_machine=mips-sgi
-		case $os in
-		    -irix*)
-			;;
-		    *)
-			os=-irix4
-			;;
-		esac
-		;;
-	isi68 | isi)
-		basic_machine=m68k-isi
-		os=-sysv
-		;;
-	m68knommu)
-		basic_machine=m68k-unknown
-		os=-linux
-		;;
-	m68knommu-*)
-		basic_machine=m68k-`echo $basic_machine | sed 's/^[^-]*-//'`
-		os=-linux
-		;;
-	m88k-omron*)
-		basic_machine=m88k-omron
-		;;
-	magnum | m3230)
-		basic_machine=mips-mips
-		os=-sysv
-		;;
-	merlin)
-		basic_machine=ns32k-utek
-		os=-sysv
-		;;
-	mingw32)
-		basic_machine=i386-pc
-		os=-mingw32
-		;;
-	mingw32ce)
-		basic_machine=arm-unknown
-		os=-mingw32ce
-		;;
-	miniframe)
-		basic_machine=m68000-convergent
-		;;
-	*mint | -mint[0-9]* | *MiNT | *MiNT[0-9]*)
-		basic_machine=m68k-atari
-		os=-mint
-		;;
-	mips3*-*)
-		basic_machine=`echo $basic_machine | sed -e 's/mips3/mips64/'`
-		;;
-	mips3*)
-		basic_machine=`echo $basic_machine | sed -e 's/mips3/mips64/'`-unknown
-		;;
-	monitor)
-		basic_machine=m68k-rom68k
-		os=-coff
-		;;
-	morphos)
-		basic_machine=powerpc-unknown
-		os=-morphos
-		;;
-	msdos)
-		basic_machine=i386-pc
-		os=-msdos
-		;;
-	ms1-*)
-		basic_machine=`echo $basic_machine | sed -e 's/ms1-/mt-/'`
-		;;
-	mvs)
-		basic_machine=i370-ibm
-		os=-mvs
-		;;
-	ncr3000)
-		basic_machine=i486-ncr
-		os=-sysv4
-		;;
-	netbsd386)
-		basic_machine=i386-unknown
-		os=-netbsd
-		;;
-	netwinder)
-		basic_machine=armv4l-rebel
-		os=-linux
-		;;
-	news | news700 | news800 | news900)
-		basic_machine=m68k-sony
-		os=-newsos
-		;;
-	news1000)
-		basic_machine=m68030-sony
-		os=-newsos
-		;;
-	news-3600 | risc-news)
-		basic_machine=mips-sony
-		os=-newsos
-		;;
-	necv70)
-		basic_machine=v70-nec
-		os=-sysv
-		;;
-	next | m*-next )
-		basic_machine=m68k-next
-		case $os in
-		    -nextstep* )
-			;;
-		    -ns2*)
-		      os=-nextstep2
-			;;
-		    *)
-		      os=-nextstep3
-			;;
-		esac
-		;;
-	nh3000)
-		basic_machine=m68k-harris
-		os=-cxux
-		;;
-	nh[45]000)
-		basic_machine=m88k-harris
-		os=-cxux
-		;;
-	nindy960)
-		basic_machine=i960-intel
-		os=-nindy
-		;;
-	mon960)
-		basic_machine=i960-intel
-		os=-mon960
-		;;
-	nonstopux)
-		basic_machine=mips-compaq
-		os=-nonstopux
-		;;
-	np1)
-		basic_machine=np1-gould
-		;;
-	nsr-tandem)
-		basic_machine=nsr-tandem
-		;;
-	op50n-* | op60c-*)
-		basic_machine=hppa1.1-oki
-		os=-proelf
-		;;
-	openrisc | openrisc-*)
-		basic_machine=or32-unknown
-		;;
-	os400)
-		basic_machine=powerpc-ibm
-		os=-os400
-		;;
-	OSE68000 | ose68000)
-		basic_machine=m68000-ericsson
-		os=-ose
-		;;
-	os68k)
-		basic_machine=m68k-none
-		os=-os68k
-		;;
-	pa-hitachi)
-		basic_machine=hppa1.1-hitachi
-		os=-hiuxwe2
-		;;
-	paragon)
-		basic_machine=i860-intel
-		os=-osf
-		;;
-	parisc)
-		basic_machine=hppa-unknown
-		os=-linux
-		;;
-	parisc-*)
-		basic_machine=hppa-`echo $basic_machine | sed 's/^[^-]*-//'`
-		os=-linux
-		;;
-	pbd)
-		basic_machine=sparc-tti
-		;;
-	pbb)
-		basic_machine=m68k-tti
-		;;
-	pc532 | pc532-*)
-		basic_machine=ns32k-pc532
-		;;
-	pc98)
-		basic_machine=i386-pc
-		;;
-	pc98-*)
-		basic_machine=i386-`echo $basic_machine | sed 's/^[^-]*-//'`
-		;;
-	pentium | p5 | k5 | k6 | nexgen | viac3)
-		basic_machine=i586-pc
-		;;
-	pentiumpro | p6 | 6x86 | athlon | athlon_*)
-		basic_machine=i686-pc
-		;;
-	pentiumii | pentium2 | pentiumiii | pentium3)
-		basic_machine=i686-pc
-		;;
-	pentium4)
-		basic_machine=i786-pc
-		;;
-	pentium-* | p5-* | k5-* | k6-* | nexgen-* | viac3-*)
-		basic_machine=i586-`echo $basic_machine | sed 's/^[^-]*-//'`
-		;;
-	pentiumpro-* | p6-* | 6x86-* | athlon-*)
-		basic_machine=i686-`echo $basic_machine | sed 's/^[^-]*-//'`
-		;;
-	pentiumii-* | pentium2-* | pentiumiii-* | pentium3-*)
-		basic_machine=i686-`echo $basic_machine | sed 's/^[^-]*-//'`
-		;;
-	pentium4-*)
-		basic_machine=i786-`echo $basic_machine | sed 's/^[^-]*-//'`
-		;;
-	pn)
-		basic_machine=pn-gould
-		;;
-	power)	basic_machine=power-ibm
-		;;
-	ppc)	basic_machine=powerpc-unknown
-		;;
-	ppc-*)	basic_machine=powerpc-`echo $basic_machine | sed 's/^[^-]*-//'`
-		;;
-	ppcle | powerpclittle | ppc-le | powerpc-little)
-		basic_machine=powerpcle-unknown
-		;;
-	ppcle-* | powerpclittle-*)
-		basic_machine=powerpcle-`echo $basic_machine | sed 's/^[^-]*-//'`
-		;;
-	ppc64)	basic_machine=powerpc64-unknown
-		;;
-	ppc64-*) basic_machine=powerpc64-`echo $basic_machine | sed 's/^[^-]*-//'`
-		;;
-	ppc64le | powerpc64little | ppc64-le | powerpc64-little)
-		basic_machine=powerpc64le-unknown
-		;;
-	ppc64le-* | powerpc64little-*)
-		basic_machine=powerpc64le-`echo $basic_machine | sed 's/^[^-]*-//'`
-		;;
-	ps2)
-		basic_machine=i386-ibm
-		;;
-	pw32)
-		basic_machine=i586-unknown
-		os=-pw32
-		;;
-	rdos)
-		basic_machine=i386-pc
-		os=-rdos
-		;;
-	rom68k)
-		basic_machine=m68k-rom68k
-		os=-coff
-		;;
-	rm[46]00)
-		basic_machine=mips-siemens
-		;;
-	rtpc | rtpc-*)
-		basic_machine=romp-ibm
-		;;
-	s390 | s390-*)
-		basic_machine=s390-ibm
-		;;
-	s390x | s390x-*)
-		basic_machine=s390x-ibm
-		;;
-	sa29200)
-		basic_machine=a29k-amd
-		os=-udi
-		;;
-	sb1)
-		basic_machine=mipsisa64sb1-unknown
-		;;
-	sb1el)
-		basic_machine=mipsisa64sb1el-unknown
-		;;
-	sde)
-		basic_machine=mipsisa32-sde
-		os=-elf
-		;;
-	sei)
-		basic_machine=mips-sei
-		os=-seiux
-		;;
-	sequent)
-		basic_machine=i386-sequent
-		;;
-	sh)
-		basic_machine=sh-hitachi
-		os=-hms
-		;;
-	sh5el)
-		basic_machine=sh5le-unknown
-		;;
-	sh64)
-		basic_machine=sh64-unknown
-		;;
-	sparclite-wrs | simso-wrs)
-		basic_machine=sparclite-wrs
-		os=-vxworks
-		;;
-	sps7)
-		basic_machine=m68k-bull
-		os=-sysv2
-		;;
-	spur)
-		basic_machine=spur-unknown
-		;;
-	st2000)
-		basic_machine=m68k-tandem
-		;;
-	stratus)
-		basic_machine=i860-stratus
-		os=-sysv4
-		;;
-	sun2)
-		basic_machine=m68000-sun
-		;;
-	sun2os3)
-		basic_machine=m68000-sun
-		os=-sunos3
-		;;
-	sun2os4)
-		basic_machine=m68000-sun
-		os=-sunos4
-		;;
-	sun3os3)
-		basic_machine=m68k-sun
-		os=-sunos3
-		;;
-	sun3os4)
-		basic_machine=m68k-sun
-		os=-sunos4
-		;;
-	sun4os3)
-		basic_machine=sparc-sun
-		os=-sunos3
-		;;
-	sun4os4)
-		basic_machine=sparc-sun
-		os=-sunos4
-		;;
-	sun4sol2)
-		basic_machine=sparc-sun
-		os=-solaris2
-		;;
-	sun3 | sun3-*)
-		basic_machine=m68k-sun
-		;;
-	sun4)
-		basic_machine=sparc-sun
-		;;
-	sun386 | sun386i | roadrunner)
-		basic_machine=i386-sun
-		;;
-	sv1)
-		basic_machine=sv1-cray
-		os=-unicos
-		;;
-	symmetry)
-		basic_machine=i386-sequent
-		os=-dynix
-		;;
-	t3e)
-		basic_machine=alphaev5-cray
-		os=-unicos
-		;;
-	t90)
-		basic_machine=t90-cray
-		os=-unicos
-		;;
-	tic54x | c54x*)
-		basic_machine=tic54x-unknown
-		os=-coff
-		;;
-	tic55x | c55x*)
-		basic_machine=tic55x-unknown
-		os=-coff
-		;;
-	tic6x | c6x*)
-		basic_machine=tic6x-unknown
-		os=-coff
-		;;
-	tile*)
-		basic_machine=tile-unknown
-		os=-linux-gnu
-		;;
-	tx39)
-		basic_machine=mipstx39-unknown
-		;;
-	tx39el)
-		basic_machine=mipstx39el-unknown
-		;;
-	toad1)
-		basic_machine=pdp10-xkl
-		os=-tops20
-		;;
-	tower | tower-32)
-		basic_machine=m68k-ncr
-		;;
-	tpf)
-		basic_machine=s390x-ibm
-		os=-tpf
-		;;
-	udi29k)
-		basic_machine=a29k-amd
-		os=-udi
-		;;
-	ultra3)
-		basic_machine=a29k-nyu
-		os=-sym1
-		;;
-	v810 | necv810)
-		basic_machine=v810-nec
-		os=-none
-		;;
-	vaxv)
-		basic_machine=vax-dec
-		os=-sysv
-		;;
-	vms)
-		basic_machine=vax-dec
-		os=-vms
-		;;
-	vpp*|vx|vx-*)
-		basic_machine=f301-fujitsu
-		;;
-	vxworks960)
-		basic_machine=i960-wrs
-		os=-vxworks
-		;;
-	vxworks68)
-		basic_machine=m68k-wrs
-		os=-vxworks
-		;;
-	vxworks29k)
-		basic_machine=a29k-wrs
-		os=-vxworks
-		;;
-	w65*)
-		basic_machine=w65-wdc
-		os=-none
-		;;
-	w89k-*)
-		basic_machine=hppa1.1-winbond
-		os=-proelf
-		;;
-	xbox)
-		basic_machine=i686-pc
-		os=-mingw32
-		;;
-	xps | xps100)
-		basic_machine=xps100-honeywell
-		;;
-	ymp)
-		basic_machine=ymp-cray
-		os=-unicos
-		;;
-	z8k-*-coff)
-		basic_machine=z8k-unknown
-		os=-sim
-		;;
-	z80-*-coff)
-		basic_machine=z80-unknown
-		os=-sim
-		;;
-	none)
-		basic_machine=none-none
-		os=-none
-		;;
-
-# Here we handle the default manufacturer of certain CPU types.  It is in
-# some cases the only manufacturer, in others, it is the most popular.
-	w89k)
-		basic_machine=hppa1.1-winbond
-		;;
-	op50n)
-		basic_machine=hppa1.1-oki
-		;;
-	op60c)
-		basic_machine=hppa1.1-oki
-		;;
-	romp)
-		basic_machine=romp-ibm
-		;;
-	mmix)
-		basic_machine=mmix-knuth
-		;;
-	rs6000)
-		basic_machine=rs6000-ibm
-		;;
-	vax)
-		basic_machine=vax-dec
-		;;
-	pdp10)
-		# there are many clones, so DEC is not a safe bet
-		basic_machine=pdp10-unknown
-		;;
-	pdp11)
-		basic_machine=pdp11-dec
-		;;
-	we32k)
-		basic_machine=we32k-att
-		;;
-	sh[1234] | sh[24]a | sh[24]aeb | sh[34]eb | sh[1234]le | sh[23]ele)
-		basic_machine=sh-unknown
-		;;
-	sparc | sparcv8 | sparcv9 | sparcv9b | sparcv9v)
-		basic_machine=sparc-sun
-		;;
-	cydra)
-		basic_machine=cydra-cydrome
-		;;
-	orion)
-		basic_machine=orion-highlevel
-		;;
-	orion105)
-		basic_machine=clipper-highlevel
-		;;
-	mac | mpw | mac-mpw)
-		basic_machine=m68k-apple
-		;;
-	pmac | pmac-mpw)
-		basic_machine=powerpc-apple
-		;;
-	*-unknown)
-		# Make sure to match an already-canonicalized machine name.
-		;;
-	*)
-		echo Invalid configuration \`$1\': machine \`$basic_machine\' not recognized 1>&2
-		exit 1
-		;;
-esac
-
-# Here we canonicalize certain aliases for manufacturers.
-case $basic_machine in
-	*-digital*)
-		basic_machine=`echo $basic_machine | sed 's/digital.*/dec/'`
-		;;
-	*-commodore*)
-		basic_machine=`echo $basic_machine | sed 's/commodore.*/cbm/'`
-		;;
-	*)
-		;;
-esac
-
-# Decode manufacturer-specific aliases for certain operating systems.
-
-if [ x"$os" != x"" ]
-then
-case $os in
-        # First match some system type aliases
-        # that might get confused with valid system types.
-	# -solaris* is a basic system type, with this one exception.
-	-solaris1 | -solaris1.*)
-		os=`echo $os | sed -e 's|solaris1|sunos4|'`
-		;;
-	-solaris)
-		os=-solaris2
-		;;
-	-svr4*)
-		os=-sysv4
-		;;
-	-unixware*)
-		os=-sysv4.2uw
-		;;
-	-gnu/linux*)
-		os=`echo $os | sed -e 's|gnu/linux|linux-gnu|'`
-		;;
-	# First accept the basic system types.
-	# The portable systems comes first.
-	# Each alternative MUST END IN A *, to match a version number.
-	# -sysv* is not here because it comes later, after sysvr4.
-	-gnu* | -bsd* | -mach* | -minix* | -genix* | -ultrix* | -irix* \
-	      | -*vms* | -sco* | -esix* | -isc* | -aix* | -sunos | -sunos[34]*\
-	      | -hpux* | -unos* | -osf* | -luna* | -dgux* | -solaris* | -sym* \
-	      | -kopensolaris* \
-	      | -amigaos* | -amigados* | -msdos* | -newsos* | -unicos* | -aof* \
-	      | -aos* | -aros* \
-	      | -nindy* | -vxsim* | -vxworks* | -ebmon* | -hms* | -mvs* \
-	      | -clix* | -riscos* | -uniplus* | -iris* | -rtu* | -xenix* \
-	      | -hiux* | -386bsd* | -knetbsd* | -mirbsd* | -netbsd* \
-	      | -openbsd* | -solidbsd* \
-	      | -ekkobsd* | -kfreebsd* | -freebsd* | -riscix* | -lynxos* \
-	      | -bosx* | -nextstep* | -cxux* | -aout* | -elf* | -oabi* \
-	      | -ptx* | -coff* | -ecoff* | -winnt* | -domain* | -vsta* \
-	      | -udi* | -eabi* | -lites* | -ieee* | -go32* | -aux* \
-	      | -chorusos* | -chorusrdb* | -cegcc* \
-	      | -cygwin* | -pe* | -psos* | -moss* | -proelf* | -rtems* \
-	      | -mingw32* | -linux-gnu* | -linux-newlib* | -linux-uclibc* \
-	      | -uxpv* | -beos* | -mpeix* | -udk* \
-	      | -interix* | -uwin* | -mks* | -rhapsody* | -darwin* | -opened* \
-	      | -openstep* | -oskit* | -conix* | -pw32* | -nonstopux* \
-	      | -storm-chaos* | -tops10* | -tenex* | -tops20* | -its* \
-	      | -os2* | -vos* | -palmos* | -uclinux* | -nucleus* \
-	      | -morphos* | -superux* | -rtmk* | -rtmk-nova* | -windiss* \
-	      | -powermax* | -dnix* | -nx6 | -nx7 | -sei* | -dragonfly* \
-	      | -skyos* | -haiku* | -rdos* | -toppers* | -drops*)
-	# Remember, each alternative MUST END IN *, to match a version number.
-		;;
-	-qnx*)
-		case $basic_machine in
-		    x86-* | i*86-*)
-			;;
-		    *)
-			os=-nto$os
-			;;
-		esac
-		;;
-	-nto-qnx*)
-		;;
-	-nto*)
-		os=`echo $os | sed -e 's|nto|nto-qnx|'`
-		;;
-	-sim | -es1800* | -hms* | -xray | -os68k* | -none* | -v88r* \
-	      | -windows* | -osx | -abug | -netware* | -os9* | -beos* | -haiku* \
-	      | -macos* | -mpw* | -magic* | -mmixware* | -mon960* | -lnews*)
-		;;
-	-mac*)
-		os=`echo $os | sed -e 's|mac|macos|'`
-		;;
-	-linux-dietlibc)
-		os=-linux-dietlibc
-		;;
-	-linux*)
-		os=`echo $os | sed -e 's|linux|linux-gnu|'`
-		;;
-	-sunos5*)
-		os=`echo $os | sed -e 's|sunos5|solaris2|'`
-		;;
-	-sunos6*)
-		os=`echo $os | sed -e 's|sunos6|solaris3|'`
-		;;
-	-opened*)
-		os=-openedition
-		;;
-        -os400*)
-		os=-os400
-		;;
-	-wince*)
-		os=-wince
-		;;
-	-osfrose*)
-		os=-osfrose
-		;;
-	-osf*)
-		os=-osf
-		;;
-	-utek*)
-		os=-bsd
-		;;
-	-dynix*)
-		os=-bsd
-		;;
-	-acis*)
-		os=-aos
-		;;
-	-atheos*)
-		os=-atheos
-		;;
-	-syllable*)
-		os=-syllable
-		;;
-	-386bsd)
-		os=-bsd
-		;;
-	-ctix* | -uts*)
-		os=-sysv
-		;;
-	-nova*)
-		os=-rtmk-nova
-		;;
-	-ns2 )
-		os=-nextstep2
-		;;
-	-nsk*)
-		os=-nsk
-		;;
-	# Preserve the version number of sinix5.
-	-sinix5.*)
-		os=`echo $os | sed -e 's|sinix|sysv|'`
-		;;
-	-sinix*)
-		os=-sysv4
-		;;
-        -tpf*)
-		os=-tpf
-		;;
-	-triton*)
-		os=-sysv3
-		;;
-	-oss*)
-		os=-sysv3
-		;;
-	-svr4)
-		os=-sysv4
-		;;
-	-svr3)
-		os=-sysv3
-		;;
-	-sysvr4)
-		os=-sysv4
-		;;
-	# This must come after -sysvr4.
-	-sysv*)
-		;;
-	-ose*)
-		os=-ose
-		;;
-	-es1800*)
-		os=-ose
-		;;
-	-xenix)
-		os=-xenix
-		;;
-	-*mint | -mint[0-9]* | -*MiNT | -MiNT[0-9]*)
-		os=-mint
-		;;
-	-aros*)
-		os=-aros
-		;;
-	-kaos*)
-		os=-kaos
-		;;
-	-zvmoe)
-		os=-zvmoe
-		;;
-	-dicos*)
-		os=-dicos
-		;;
-	-none)
-		;;
-	*)
-		# Get rid of the `-' at the beginning of $os.
-		os=`echo $os | sed 's/[^-]*-//'`
-		echo Invalid configuration \`$1\': system \`$os\' not recognized 1>&2
-		exit 1
-		;;
-esac
-else
-
-# Here we handle the default operating systems that come with various machines.
-# The value should be what the vendor currently ships out the door with their
-# machine or put another way, the most popular os provided with the machine.
-
-# Note that if you're going to try to match "-MANUFACTURER" here (say,
-# "-sun"), then you have to tell the case statement up towards the top
-# that MANUFACTURER isn't an operating system.  Otherwise, code above
-# will signal an error saying that MANUFACTURER isn't an operating
-# system, and we'll never get to this point.
-
-case $basic_machine in
-        score-*)
-		os=-elf
-		;;
-        spu-*)
-		os=-elf
-		;;
-	*-acorn)
-		os=-riscix1.2
-		;;
-	arm*-rebel)
-		os=-linux
-		;;
-	arm*-semi)
-		os=-aout
-		;;
-        c4x-* | tic4x-*)
-        	os=-coff
-		;;
-	# This must come before the *-dec entry.
-	pdp10-*)
-		os=-tops20
-		;;
-	pdp11-*)
-		os=-none
-		;;
-	*-dec | vax-*)
-		os=-ultrix4.2
-		;;
-	m68*-apollo)
-		os=-domain
-		;;
-	i386-sun)
-		os=-sunos4.0.2
-		;;
-	m68000-sun)
-		os=-sunos3
-		# This also exists in the configure program, but was not the
-		# default.
-		# os=-sunos4
-		;;
-	m68*-cisco)
-		os=-aout
-		;;
-        mep-*)
-		os=-elf
-		;;
-	mips*-cisco)
-		os=-elf
-		;;
-	mips*-*)
-		os=-elf
-		;;
-	or32-*)
-		os=-coff
-		;;
-	*-tti)	# must be before sparc entry or we get the wrong os.
-		os=-sysv3
-		;;
-	sparc-* | *-sun)
-		os=-sunos4.1.1
-		;;
-	*-be)
-		os=-beos
-		;;
-	*-haiku)
-		os=-haiku
-		;;
-	*-ibm)
-		os=-aix
-		;;
-    	*-knuth)
-		os=-mmixware
-		;;
-	*-wec)
-		os=-proelf
-		;;
-	*-winbond)
-		os=-proelf
-		;;
-	*-oki)
-		os=-proelf
-		;;
-	*-hp)
-		os=-hpux
-		;;
-	*-hitachi)
-		os=-hiux
-		;;
-	i860-* | *-att | *-ncr | *-altos | *-motorola | *-convergent)
-		os=-sysv
-		;;
-	*-cbm)
-		os=-amigaos
-		;;
-	*-dg)
-		os=-dgux
-		;;
-	*-dolphin)
-		os=-sysv3
-		;;
-	m68k-ccur)
-		os=-rtu
-		;;
-	m88k-omron*)
-		os=-luna
-		;;
-	*-next )
-		os=-nextstep
-		;;
-	*-sequent)
-		os=-ptx
-		;;
-	*-crds)
-		os=-unos
-		;;
-	*-ns)
-		os=-genix
-		;;
-	i370-*)
-		os=-mvs
-		;;
-	*-next)
-		os=-nextstep3
-		;;
-	*-gould)
-		os=-sysv
-		;;
-	*-highlevel)
-		os=-bsd
-		;;
-	*-encore)
-		os=-bsd
-		;;
-	*-sgi)
-		os=-irix
-		;;
-	*-siemens)
-		os=-sysv4
-		;;
-	*-masscomp)
-		os=-rtu
-		;;
-	f30[01]-fujitsu | f700-fujitsu)
-		os=-uxpv
-		;;
-	*-rom68k)
-		os=-coff
-		;;
-	*-*bug)
-		os=-coff
-		;;
-	*-apple)
-		os=-macos
-		;;
-	*-atari*)
-		os=-mint
-		;;
-	*)
-		os=-none
-		;;
-esac
-fi
-
-# Here we handle the case where we know the os, and the CPU type, but not the
-# manufacturer.  We pick the logical manufacturer.
-vendor=unknown
-case $basic_machine in
-	*-unknown)
-		case $os in
-			-riscix*)
-				vendor=acorn
-				;;
-			-sunos*)
-				vendor=sun
-				;;
-			-aix*)
-				vendor=ibm
-				;;
-			-beos*)
-				vendor=be
-				;;
-			-hpux*)
-				vendor=hp
-				;;
-			-mpeix*)
-				vendor=hp
-				;;
-			-hiux*)
-				vendor=hitachi
-				;;
-			-unos*)
-				vendor=crds
-				;;
-			-dgux*)
-				vendor=dg
-				;;
-			-luna*)
-				vendor=omron
-				;;
-			-genix*)
-				vendor=ns
-				;;
-			-mvs* | -opened*)
-				vendor=ibm
-				;;
-			-os400*)
-				vendor=ibm
-				;;
-			-ptx*)
-				vendor=sequent
-				;;
-			-tpf*)
-				vendor=ibm
-				;;
-			-vxsim* | -vxworks* | -windiss*)
-				vendor=wrs
-				;;
-			-aux*)
-				vendor=apple
-				;;
-			-hms*)
-				vendor=hitachi
-				;;
-			-mpw* | -macos*)
-				vendor=apple
-				;;
-			-*mint | -mint[0-9]* | -*MiNT | -MiNT[0-9]*)
-				vendor=atari
-				;;
-			-vos*)
-				vendor=stratus
-				;;
-		esac
-		basic_machine=`echo $basic_machine | sed "s/unknown/$vendor/"`
-		;;
-esac
-
-echo $basic_machine$os
-exit
-
-# Local variables:
-# eval: (add-hook 'write-file-hooks 'time-stamp)
-# time-stamp-start: "timestamp='"
-# time-stamp-format: "%:y-%02m-%02d"
-# time-stamp-end: "'"
-# End:
diff --git a/lib/replace/configure.ac b/lib/replace/configure.ac
deleted file mode 100644
index 0361825..0000000
--- a/lib/replace/configure.ac
+++ /dev/null
@@ -1,33 +0,0 @@
-AC_PREREQ(2.50)
-AC_INIT(replace.c)
-AC_CONFIG_SRCDIR([replace.c])
-AC_CONFIG_HEADER(config.h)
-
-CFLAGS="$CFLAGS -I$srcdir"
-
-AC_LIBREPLACE_ALL_CHECKS
-AC_LIBREPLACE_NETWORK_CHECKS
-
-if test "$ac_cv_prog_gcc" = yes; then
-   CFLAGS="$CFLAGS -Wall"
-   CFLAGS="$CFLAGS -W"
-   CFLAGS="$CFLAGS -Wshadow"
-   CFLAGS="$CFLAGS -Wstrict-prototypes"
-   CFLAGS="$CFLAGS -Wpointer-arith"
-   CFLAGS="$CFLAGS -Wcast-qual"
-   CFLAGS="$CFLAGS -Wcast-align"
-   CFLAGS="$CFLAGS -Wwrite-strings"
-   CFLAGS="$CFLAGS -Werror-implicit-function-declaration"
-   CFLAGS="$CFLAGS -Wformat=2"
-   CFLAGS="$CFLAGS -Wno-format-y2k"
-fi
-
-m4_include(build_macros.m4)
-BUILD_WITH_SHARED_BUILD_DIR
-
-LIBS="${LIBREPLACE_NETWORK_LIBS}"
-AC_SUBST(LIBS)
-
-AC_SUBST(LDFLAGS)
-
-AC_OUTPUT(Makefile)
diff --git a/lib/replace/getaddrinfo.m4 b/lib/replace/getaddrinfo.m4
deleted file mode 100644
index bc6e69e..0000000
--- a/lib/replace/getaddrinfo.m4
+++ /dev/null
@@ -1,32 +0,0 @@
-dnl test for getaddrinfo/getnameinfo
-AC_CACHE_CHECK([for getaddrinfo],libreplace_cv_HAVE_GETADDRINFO,[
-AC_TRY_LINK([
-#include <sys/types.h>
-#if STDC_HEADERS
-#include <stdlib.h>
-#include <stddef.h>
-#endif
-#include <sys/socket.h>
-#include <netdb.h>],
-[
-struct sockaddr sa;
-struct addrinfo *ai = NULL;
-int ret = getaddrinfo(NULL, NULL, NULL, &ai);
-if (ret != 0) {
-	const char *es = gai_strerror(ret);
-}
-freeaddrinfo(ai);
-ret = getnameinfo(&sa, sizeof(sa),
-		NULL, 0,
-		NULL, 0, 0);
-
-],
-libreplace_cv_HAVE_GETADDRINFO=yes,libreplace_cv_HAVE_GETADDRINFO=no)])
-if test x"$libreplace_cv_HAVE_GETADDRINFO" = x"yes"; then
-	AC_DEFINE(HAVE_GETADDRINFO,1,[Whether the system has getaddrinfo])
-	AC_DEFINE(HAVE_GETNAMEINFO,1,[Whether the system has getnameinfo])
-	AC_DEFINE(HAVE_FREEADDRINFO,1,[Whether the system has freeaddrinfo])
-	AC_DEFINE(HAVE_GAI_STRERROR,1,[Whether the system has gai_strerror])
-else
-	LIBREPLACEOBJ="${LIBREPLACEOBJ} getaddrinfo.o"
-fi
diff --git a/lib/replace/getifaddrs.m4 b/lib/replace/getifaddrs.m4
deleted file mode 100644
index 297a82d..0000000
--- a/lib/replace/getifaddrs.m4
+++ /dev/null
@@ -1,101 +0,0 @@
-AC_CHECK_HEADERS([ifaddrs.h])
-
-dnl Used when getifaddrs is not available
-AC_CHECK_MEMBERS([struct sockaddr.sa_len], 
-	 [AC_DEFINE(HAVE_SOCKADDR_SA_LEN, 1, [Whether struct sockaddr has a sa_len member])],
-	 [],
-	 [#include <sys/socket.h>])
-
-dnl test for getifaddrs and freeifaddrs
-AC_CACHE_CHECK([for getifaddrs and freeifaddrs],samba_cv_HAVE_GETIFADDRS,[
-AC_TRY_COMPILE([
-#include <sys/types.h>
-#if STDC_HEADERS
-#include <stdlib.h>
-#include <stddef.h>
-#endif
-#include <sys/socket.h>
-#include <netinet/in.h>
-#include <arpa/inet.h>
-#include <ifaddrs.h>
-#include <netdb.h>],
-[
-struct ifaddrs *ifp = NULL;
-int ret = getifaddrs (&ifp);
-freeifaddrs(ifp);
-],
-samba_cv_HAVE_GETIFADDRS=yes,samba_cv_HAVE_GETIFADDRS=no)])
-if test x"$samba_cv_HAVE_GETIFADDRS" = x"yes"; then
-    AC_DEFINE(HAVE_GETIFADDRS,1,[Whether the system has getifaddrs])
-    AC_DEFINE(HAVE_FREEIFADDRS,1,[Whether the system has freeifaddrs])
-	AC_DEFINE(HAVE_STRUCT_IFADDRS,1,[Whether struct ifaddrs is available])
-fi
-
-##################
-# look for a method of finding the list of network interfaces
-#
-# This tests need LIBS="$NSL_LIBS $SOCKET_LIBS"
-#
-old_LIBS=$LIBS
-LIBS="$NSL_LIBS $SOCKET_LIBS"
-iface=no;
-##################
-# look for a method of finding the list of network interfaces
-iface=no;
-AC_CACHE_CHECK([for iface getifaddrs],samba_cv_HAVE_IFACE_GETIFADDRS,[
-SAVE_CPPFLAGS="$CPPFLAGS"
-CPPFLAGS="$CPPFLAGS ${SAMBA_CONFIGURE_CPPFLAGS}"
-AC_TRY_RUN([
-#define NO_CONFIG_H 1
-#define HAVE_IFACE_GETIFADDRS 1
-#define AUTOCONF_TEST 1
-#include "$libreplacedir/replace.c"
-#include "$libreplacedir/getifaddrs.c"],
-           samba_cv_HAVE_IFACE_GETIFADDRS=yes,samba_cv_HAVE_IFACE_GETIFADDRS=no,samba_cv_HAVE_IFACE_GETIFADDRS=cross)])
-CPPFLAGS="$SAVE_CPPFLAGS"
-if test x"$samba_cv_HAVE_IFACE_GETIFADDRS" = x"yes"; then
-    iface=yes;AC_DEFINE(HAVE_IFACE_GETIFADDRS,1,[Whether iface getifaddrs is available])
-else
-	LIBREPLACEOBJ="${LIBREPLACEOBJ} getifaddrs.o"
-fi
-
-
-if test $iface = no; then
-AC_CACHE_CHECK([for iface AIX],samba_cv_HAVE_IFACE_AIX,[
-AC_TRY_RUN([
-#define HAVE_IFACE_AIX 1
-#define AUTOCONF_TEST 1
-#undef _XOPEN_SOURCE_EXTENDED
-#include "$libreplacedir/getifaddrs.c"],
-           samba_cv_HAVE_IFACE_AIX=yes,samba_cv_HAVE_IFACE_AIX=no,samba_cv_HAVE_IFACE_AIX=cross)])
-if test x"$samba_cv_HAVE_IFACE_AIX" = x"yes"; then
-    iface=yes;AC_DEFINE(HAVE_IFACE_AIX,1,[Whether iface AIX is available])
-fi
-fi
-
-
-if test $iface = no; then
-AC_CACHE_CHECK([for iface ifconf],samba_cv_HAVE_IFACE_IFCONF,[
-AC_TRY_RUN([
-#define HAVE_IFACE_IFCONF 1
-#define AUTOCONF_TEST 1
-#include "$libreplacedir/getifaddrs.c"],
-           samba_cv_HAVE_IFACE_IFCONF=yes,samba_cv_HAVE_IFACE_IFCONF=no,samba_cv_HAVE_IFACE_IFCONF=cross)])
-if test x"$samba_cv_HAVE_IFACE_IFCONF" = x"yes"; then
-    iface=yes;AC_DEFINE(HAVE_IFACE_IFCONF,1,[Whether iface ifconf is available])
-fi
-fi
-
-if test $iface = no; then
-AC_CACHE_CHECK([for iface ifreq],samba_cv_HAVE_IFACE_IFREQ,[
-AC_TRY_RUN([
-#define HAVE_IFACE_IFREQ 1
-#define AUTOCONF_TEST 1
-#include "$libreplacedir/getifaddrs.c"],
-           samba_cv_HAVE_IFACE_IFREQ=yes,samba_cv_HAVE_IFACE_IFREQ=no,samba_cv_HAVE_IFACE_IFREQ=cross)])
-if test x"$samba_cv_HAVE_IFACE_IFREQ" = x"yes"; then
-    iface=yes;AC_DEFINE(HAVE_IFACE_IFREQ,1,[Whether iface ifreq is available])
-fi
-fi
-
-LIBS=$old_LIBS
diff --git a/lib/replace/getpass.c b/lib/replace/getpass.c
deleted file mode 100644
index f95109f..0000000
--- a/lib/replace/getpass.c
+++ /dev/null
@@ -1,218 +0,0 @@
-/* Copyright (C) 1992-1998 Free Software Foundation, Inc.
-This file is part of the GNU C Library.
-
-The GNU C Library is free software; you can redistribute it and/or
-modify it under the terms of the GNU Lesser General Public License as
-published by the Free Software Foundation; either version 3 of the
-License, or (at your option) any later version.
-
-The GNU C Library 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
-Library General Public License for more details.
-
-You should have received a copy of the GNU Lesser General Public
-License along with the GNU C Library; see the file COPYING.LIB.  If
-not, see <http://www.gnu.org/licenses/>.  */
-
-/* Modified to use with samba by Jeremy Allison, 8th July 1995. */
-
-#include "replace.h"
-#include "system/filesys.h"
-#include "system/wait.h"
-#include "system/terminal.h"
-#include "system/passwd.h"
-
-/*
- * Define additional missing types
- */
-#ifndef HAVE_SIG_ATOMIC_T_TYPE
-typedef int sig_atomic_t;
-#endif
-
-#ifndef SIGCLD
-#define SIGCLD SIGCHLD
-#endif
-
-#ifdef SYSV_TERMIO 
-
-/* SYSTEM V TERMIO HANDLING */
-
-static struct termio t;
-
-#define ECHO_IS_ON(t) ((t).c_lflag & ECHO)
-#define TURN_ECHO_OFF(t) ((t).c_lflag &= ~ECHO)
-#define TURN_ECHO_ON(t) ((t).c_lflag |= ECHO)
-
-#ifndef TCSAFLUSH
-#define TCSAFLUSH 1
-#endif
-
-#ifndef TCSANOW
-#define TCSANOW 0
-#endif
-
-static int tcgetattr(int fd, struct termio *_t)
-{
-	return ioctl(fd, TCGETA, _t);
-}
-
-static int tcsetattr(int fd, int flags, struct termio *_t)
-{
-	if(flags & TCSAFLUSH)
-		ioctl(fd, TCFLSH, TCIOFLUSH);
-	return ioctl(fd, TCSETS, _t);
-}
-
-#elif !defined(TCSAFLUSH)
-
-/* BSD TERMIO HANDLING */
-
-static struct sgttyb t;  
-
-#define ECHO_IS_ON(t) ((t).sg_flags & ECHO)
-#define TURN_ECHO_OFF(t) ((t).sg_flags &= ~ECHO)
-#define TURN_ECHO_ON(t) ((t).sg_flags |= ECHO)
-
-#define TCSAFLUSH 1
-#define TCSANOW 0
-
-static int tcgetattr(int fd, struct sgttyb *_t)
-{
-	return ioctl(fd, TIOCGETP, (char *)_t);
-}
-
-static int tcsetattr(int fd, int flags, struct sgttyb *_t)
-{
-	return ioctl(fd, TIOCSETP, (char *)_t);
-}
-
-#else /* POSIX TERMIO HANDLING */
-#define ECHO_IS_ON(t) ((t).c_lflag & ECHO)
-#define TURN_ECHO_OFF(t) ((t).c_lflag &= ~ECHO)
-#define TURN_ECHO_ON(t) ((t).c_lflag |= ECHO)
-
-static struct termios t;
-#endif /* SYSV_TERMIO */
-
-static void catch_signal(int signum, void (*handler)(int ))
-{
-#ifdef HAVE_SIGACTION
-	struct sigaction act;
-	struct sigaction oldact;
-
-	memset(&act, 0, sizeof(act));
-
-	act.sa_handler = handler;
-#ifdef SA_RESTART
-	/*
-	 * We *want* SIGALRM to interrupt a system call.
-	 */
-	if(signum != SIGALRM)
-		act.sa_flags = SA_RESTART;
-#endif
-	sigemptyset(&act.sa_mask);
-	sigaddset(&act.sa_mask,signum);
-	sigaction(signum,&act,&oldact);
-#else /* !HAVE_SIGACTION */
-	/* FIXME: need to handle sigvec and systems with broken signal() */
-	signal(signum, handler);
-#endif
-}
-
-static sig_atomic_t gotintr;
-static int in_fd = -1;
-
-/***************************************************************
- Signal function to tell us were ^C'ed.
-****************************************************************/
-
-static void gotintr_sig(int signum)
-{
-	gotintr = 1;
-	if (in_fd != -1)
-		close(in_fd); /* Safe way to force a return. */
-	in_fd = -1;
-}
-
-char *rep_getpass(const char *prompt)
-{
-	FILE *in, *out;
-	int echo_off;
-	static char buf[256];
-	static size_t bufsize = sizeof(buf);
-	size_t nread;
-
-	/* Catch problematic signals */
-	catch_signal(SIGINT, gotintr_sig);
-
-	/* Try to write to and read from the terminal if we can.
-		If we can't open the terminal, use stderr and stdin.  */
-
-	in = fopen ("/dev/tty", "w+");
-	if (in == NULL) {
-		in = stdin;
-		out = stderr;
-	} else {
-		out = in;
-	}
-
-	setvbuf(in, NULL, _IONBF, 0);
-
-	/* Turn echoing off if it is on now.  */
-
-	if (tcgetattr (fileno (in), &t) == 0) {
-		if (ECHO_IS_ON(t)) {
-			TURN_ECHO_OFF(t);
-			echo_off = tcsetattr (fileno (in), TCSAFLUSH, &t) == 0;
-			TURN_ECHO_ON(t);
-		} else {
-			echo_off = 0;
-		}
-	} else {
-		echo_off = 0;
-	}
-
-	/* Write the prompt.  */
-	fputs(prompt, out);
-	fflush(out);
-
-	/* Read the password.  */
-	buf[0] = 0;
-	if (!gotintr) {
-		in_fd = fileno(in);
-		if (fgets(buf, bufsize, in) == NULL) {
-			buf[0] = 0;
-		}
-	}
-	nread = strlen(buf);
-	if (nread) {
-		if (buf[nread - 1] == '\n')
-			buf[nread - 1] = '\0';
-	}
-
-	/* Restore echoing.  */
-	if (echo_off) {
-		if (gotintr && in_fd == -1) {
-			in = fopen ("/dev/tty", "w+");
-		}
-		if (in != NULL)
-			tcsetattr (fileno (in), TCSANOW, &t);
-	}
-
-	fprintf(out, "\n");
-	fflush(out);
-
-	if (in && in != stdin) /* We opened the terminal; now close it.  */
-		fclose(in);
-
-	/* Catch problematic signals */
-	catch_signal(SIGINT, SIG_DFL);
-
-	if (gotintr) {
-		printf("Interrupted by signal.\n");
-		fflush(stdout);
-		exit(1);
-	}
-	return buf;
-}
diff --git a/lib/replace/getpass.m4 b/lib/replace/getpass.m4
deleted file mode 100644
index 78a0afe..0000000
--- a/lib/replace/getpass.m4
+++ /dev/null
@@ -1,24 +0,0 @@
-AC_CHECK_FUNC(getpass, libreplace_cv_HAVE_GETPASS=yes)
-AC_CHECK_FUNC(getpassphrase, libreplace_cv_HAVE_GETPASSPHRASE=yes)
-if test x"$libreplace_cv_HAVE_GETPASS" = x"yes" -a x"$libreplace_cv_HAVE_GETPASSPHRASE" = x"yes"; then
-        AC_DEFINE(REPLACE_GETPASS_BY_GETPASSPHRASE, 1, [getpass returns <9 chars where getpassphrase returns <265 chars])
-	AC_DEFINE(REPLACE_GETPASS,1,[Whether getpass should be replaced])
-	LIBREPLACEOBJ="${LIBREPLACEOBJ} $libreplacedir/getpass.o"
-else
-
-AC_CACHE_CHECK([whether getpass should be replaced],libreplace_cv_REPLACE_GETPASS,[
-SAVE_CPPFLAGS="$CPPFLAGS"
-CPPFLAGS="$CPPFLAGS -I$libreplacedir/"
-AC_TRY_COMPILE([
-#include "confdefs.h"
-#define NO_CONFIG_H
-#include "$libreplacedir/getpass.c"
-],[],libreplace_cv_REPLACE_GETPASS=yes,libreplace_cv_REPLACE_GETPASS=no)
-CPPFLAGS="$SAVE_CPPFLAGS"
-])
-if test x"$libreplace_cv_REPLACE_GETPASS" = x"yes"; then
-	AC_DEFINE(REPLACE_GETPASS,1,[Whether getpass should be replaced])
-	LIBREPLACEOBJ="${LIBREPLACEOBJ} $libreplacedir/getpass.o"
-fi
-
-fi
diff --git a/lib/replace/havenone.h b/lib/replace/havenone.h
deleted file mode 100644
index 76031cd..0000000
--- a/lib/replace/havenone.h
+++ /dev/null
@@ -1,51 +0,0 @@
-#undef HAVE_TIMEGM
-#undef HAVE_ASPRINTF
-#undef HAVE_BOOL
-#undef HAVE_BZERO
-#undef HAVE_C99_VSNPRINTF
-#undef HAVE_CHROOT
-#undef HAVE_CHSIZE
-#undef HAVE_COMPARISON_FN_T
-#undef HAVE_DECL_ASPRINTF
-#undef HAVE_DECL_SNPRINTF
-#undef HAVE_DECL_VASPRINTF
-#undef HAVE_DECL_VSNPRINTF
-#undef HAVE_DLCLOSE
-#undef HAVE_DLERROR
-#undef HAVE_DLOPEN
-#undef HAVE_DLSYM
-#undef HAVE_ENDNETGRENT
-#undef HAVE_GETNETGRENT
-#undef HAVE_INITGROUPS
-#undef HAVE_INNETGR
-#undef HAVE_MEMCPY
-#undef HAVE_MEMMOVE
-#undef HAVE_MEMSET
-#undef HAVE_MKDTEMP
-#undef HAVE_MKTIME
-#undef HAVE_PREAD
-#undef HAVE_PRINTF
-#undef HAVE_PWRITE
-#undef HAVE_RENAME
-#undef HAVE_SECURE_MKSTEMP
-#undef HAVE_SETENV
-#undef HAVE_SETLINEBUF
-#undef HAVE_SETNETGRENT
-#undef HAVE_SETRESGID
-#undef HAVE_SETRESUID
-#undef HAVE_SIG_ATOMIC_T_TYPE
-#undef HAVE_SNPRINTF
-#undef HAVE_STRCASESTR
-#undef HAVE_STRDUP
-#undef HAVE_STRLCAT
-#undef HAVE_STRLCPY
-#undef HAVE_STRNDUP
-#undef HAVE_STRNLEN
-#undef HAVE_STRTOK_R
-#undef HAVE_SYSLOG
-#undef HAVE_TIMEGM
-#undef HAVE_VASPRINTF
-#undef HAVE_VA_COPY
-#undef HAVE_VSNPRINTF
-#undef HAVE_VSYSLOG
-#undef HAVE_WAITPID
diff --git a/lib/replace/inet_ntop.m4 b/lib/replace/inet_ntop.m4
deleted file mode 100644
index 6f39056..0000000
--- a/lib/replace/inet_ntop.m4
+++ /dev/null
@@ -1 +0,0 @@
-AC_CHECK_FUNCS(inet_ntop,[],[LIBREPLACEOBJ="${LIBREPLACEOBJ} inet_ntop.o"])
diff --git a/lib/replace/inet_pton.m4 b/lib/replace/inet_pton.m4
deleted file mode 100644
index 51de927..0000000
--- a/lib/replace/inet_pton.m4
+++ /dev/null
@@ -1 +0,0 @@
-AC_CHECK_FUNCS(inet_pton,[],[LIBREPLACEOBJ="${LIBREPLACEOBJ} inet_pton.o"])
diff --git a/lib/replace/libreplace.m4 b/lib/replace/libreplace.m4
index ca0c684..f4ae715 100644
--- a/lib/replace/libreplace.m4
+++ b/lib/replace/libreplace.m4
@@ -49,7 +49,7 @@ fi
 LIBREPLACEOBJ="$libreplacedir/replace.o"
 AC_SUBST(LIBREPLACEOBJ)
 
-LIBREPLACEOBJ="${LIBREPLACEOBJ} $libreplacedir/snprintf.o"
+LIBREPLACEOBJ="${LIBREPLACEOBJ} $libreplacedir/snprintf.o  $libreplacedir/xattr.o"
 
 AC_TYPE_UID_T
 AC_TYPE_MODE_T
@@ -60,13 +60,15 @@ AC_STRUCT_ST_RDEV
 AC_CHECK_TYPE(ino_t,unsigned)
 AC_CHECK_TYPE(loff_t,off_t)
 AC_CHECK_TYPE(offset_t,loff_t)
+AC_CHECK_TYPE(blksize_t,long)
+AC_CHECK_TYPE(blkcnt_t,long)
 
 AC_FUNC_MEMCMP
 
 AC_CHECK_FUNCS([pipe strftime srandom random srand rand usleep setbuffer lstat getpgrp utime utimes])
 
 AC_CHECK_HEADERS(stdbool.h stdint.h sys/select.h)
-AC_CHECK_HEADERS(setjmp.h utime.h)
+AC_CHECK_HEADERS(setjmp.h utime.h sys/wait.h)
 
 LIBREPLACE_PROVIDE_HEADER([stdint.h])
 LIBREPLACE_PROVIDE_HEADER([stdbool.h])
@@ -107,6 +109,13 @@ if test x"$libreplace_cv_HAVE_MREMAP" = x"yes"; then
     AC_DEFINE(HAVE_MREMAP,1,[Whether mremap works])
 fi
 
+AC_CACHE_CHECK([for incoherent mmap],libreplace_cv_HAVE_INCOHERENT_MMAP,[
+AC_TRY_RUN([#include "$libreplacedir/test/incoherent_mmap.c"],
+           libreplace_cv_HAVE_INCOHERENT_MMAP=yes,libreplace_cv_HAVE_INCOHERENT_MMAP=no,libreplace_cv_HAVE_INCOHERENT_MMAP=cross)])
+if test x"$libreplace_cv_HAVE_INCOHERENT_MMAP" = x"yes"; then
+    AC_DEFINE(HAVE_INCOHERENT_MMAP,1,[Whether mmap is incoherent against write])
+fi
+
 
 AC_CHECK_HEADERS(sys/syslog.h syslog.h)
 AC_CHECK_HEADERS(sys/time.h time.h)
@@ -114,9 +123,13 @@ AC_CHECK_HEADERS(stdarg.h vararg.h)
 AC_CHECK_HEADERS(sys/mount.h mntent.h)
 AC_CHECK_HEADERS(stropts.h)
 AC_CHECK_HEADERS(unix.h)
+AC_CHECK_HEADERS(malloc.h)
+AC_CHECK_HEADERS(syscall.h)
+AC_CHECK_HEADERS(sys/syscall.h)
+AC_CHECK_HEADERS(sys/ucontext.h)
 
-AC_CHECK_FUNCS(seteuid setreuid setresuid setegid setregid setresgid)
-AC_CHECK_FUNCS(chroot bzero strerror strerror_r)
+AC_CHECK_FUNCS(syscall setuid seteuid setreuid setresuid setgid setegid setregid setresgid setgroups)
+AC_CHECK_FUNCS(chroot bzero strerror strerror_r memalign posix_memalign getpagesize)
 AC_CHECK_FUNCS(vsyslog setlinebuf mktime ftruncate chsize rename)
 AC_CHECK_FUNCS(waitpid wait4 strlcpy strlcat initgroups memmove strdup)
 AC_CHECK_FUNCS(pread pwrite strndup strcasestr strtok_r mkdtemp dup2 dprintf vdprintf)
@@ -134,6 +147,60 @@ AC_CHECK_FUNCS(clock_gettime,libreplace_cv_have_clock_gettime=yes,[
 		libreplace_cv_have_clock_gettime=yes
 		AC_DEFINE(HAVE_CLOCK_GETTIME, 1, Define to 1 if there is support for clock_gettime)])
 ])
+
+AC_CHECK_HEADERS(sys/attributes.h attr/xattr.h sys/xattr.h sys/extattr.h sys/uio.h)
+AC_CHECK_HEADERS(sys/ea.h sys/proplist.h)
+
+LIBREPLACE_FILESYS_LIBS=""
+
+############################################
+# Check for EA implementations
+case "$host_os" in
+  *freebsd4* | *dragonfly* )
+	AC_DEFINE(BROKEN_EXTATTR, 1, [Does extattr API work])
+  ;;
+  *)
+	AC_SEARCH_LIBS(getxattr, [attr])
+	AC_CHECK_FUNCS(attr_get attr_getf attr_list attr_listf attropen attr_remove)
+	AC_CHECK_FUNCS(attr_removef attr_set attr_setf extattr_delete_fd extattr_delete_file)
+	AC_CHECK_FUNCS(extattr_get_fd extattr_get_file extattr_list_fd extattr_list_file)
+	AC_CHECK_FUNCS(extattr_set_fd extattr_set_file fgetea fgetxattr flistea flistxattr)
+	AC_CHECK_FUNCS(fremoveea fremovexattr fsetea fsetxattr getea getxattr listea)
+	AC_CHECK_FUNCS(listxattr removeea removexattr setea setxattr)
+
+	AC_CHECK_LIB_EXT(attr, LIBREPLACE_FILESYS_LIBS, flistea)
+	AC_CHECK_LIB_EXT(attr, LIBREPLACE_FILESYS_LIBS, flistxattr)
+	AC_CHECK_LIB_EXT(attr, LIBREPLACE_FILESYS_LIBS, attr_listf)
+	AC_CHECK_LIB_EXT(attr, LIBREPLACE_FILESYS_LIBS, extattr_list_fd)
+
+  ;;
+esac
+
+
+########################################################
+# Do xattr functions take additional options like on Darwin?
+if test x"$ac_cv_func_getxattr" = x"yes" ; then
+	AC_CACHE_CHECK([whether xattr interface takes additional options], smb_attr_cv_xattr_add_opt, [
+		old_LIBS=$LIBS
+		LIBS="$LIBS $LIBREPLACE_FILESYS_LIBS"
+		AC_TRY_COMPILE([
+			#include <sys/types.h>
+			#if HAVE_ATTR_XATTR_H
+			#include <attr/xattr.h>
+			#elif HAVE_SYS_XATTR_H
+			#include <sys/xattr.h>
+			#endif
+		],[
+			getxattr(0, 0, 0, 0, 0, 0);
+		],
+	        [smb_attr_cv_xattr_add_opt=yes],
+		[smb_attr_cv_xattr_add_opt=no;LIBS=$old_LIBS])
+	])
+	if test x"$smb_attr_cv_xattr_add_opt" = x"yes"; then
+		AC_DEFINE(XATTR_ADDITIONAL_OPTIONS, 1, [xattr functions have additional options])
+	fi
+fi
+
 AC_CHECK_FUNCS(get_current_dir_name)
 AC_HAVE_DECL(setresuid, [#include <unistd.h>])
 AC_HAVE_DECL(setresgid, [#include <unistd.h>])
@@ -146,12 +213,27 @@ AC_TRY_RUN([#include <stdlib.h>
 #include <unistd.h>
 main() { 
   struct stat st;
-  char tpl[20]="/tmp/test.XXXXXX"; 
-  int fd = mkstemp(tpl); 
-  if (fd == -1) exit(1);
+  char tpl[20]="/tmp/test.XXXXXX";
+  char tpl2[20]="/tmp/test.XXXXXX";
+  int fd = mkstemp(tpl);
+  int fd2 = mkstemp(tpl2);
+  if (fd == -1) {
+        if (fd2 != -1) {
+                unlink(tpl2);
+        }
+        exit(1);
+  }
+  if (fd2 == -1) exit(1);
   unlink(tpl);
+  unlink(tpl2);
   if (fstat(fd, &st) != 0) exit(1);
   if ((st.st_mode & 0777) != 0600) exit(1);
+  if (strcmp(tpl, "/tmp/test.XXXXXX") == 0) {
+        exit(1);
+  }
+  if (strcmp(tpl, tpl2) == 0) {
+        exit(1);
+  }
   exit(0);
 }],
 libreplace_cv_HAVE_SECURE_MKSTEMP=yes,
@@ -276,6 +358,16 @@ if test x"$libreplace_cv_sig_atomic_t" = x"yes"; then
 fi
 
 
+dnl Check if the C compiler understands volatile (it should, being ANSI).
+AC_CACHE_CHECK([that the C compiler understands volatile],libreplace_cv_volatile, [
+	AC_TRY_COMPILE([#include <sys/types.h>],[volatile int i = 0],
+		libreplace_cv_volatile=yes,libreplace_cv_volatile=no)])
+if test x"$libreplace_cv_volatile" = x"yes"; then
+	AC_DEFINE(HAVE_VOLATILE, 1, [Whether the C compiler understands volatile])
+fi
+
+m4_include(system/config.m4)
+
 AC_CACHE_CHECK([for O_DIRECT flag to open(2)],libreplace_cv_HAVE_OPEN_O_DIRECT,[
 AC_TRY_COMPILE([
 #include <unistd.h>
@@ -288,19 +380,7 @@ if test x"$libreplace_cv_HAVE_OPEN_O_DIRECT" = x"yes"; then
     AC_DEFINE(HAVE_OPEN_O_DIRECT,1,[Whether the open(2) accepts O_DIRECT])
 fi
 
-
-dnl Check if the C compiler understands volatile (it should, being ANSI).
-AC_CACHE_CHECK([that the C compiler understands volatile],libreplace_cv_volatile, [
-	AC_TRY_COMPILE([#include <sys/types.h>],[volatile int i = 0],
-		libreplace_cv_volatile=yes,libreplace_cv_volatile=no)])
-if test x"$libreplace_cv_volatile" = x"yes"; then
-	AC_DEFINE(HAVE_VOLATILE, 1, [Whether the C compiler understands volatile])
-fi
-
-m4_include(system/config.m4)
-
 m4_include(dlfcn.m4)
-m4_include(getpass.m4)
 m4_include(strptime.m4)
 m4_include(win32.m4)
 m4_include(timegm.m4)
@@ -336,6 +416,18 @@ if test x"$libreplace_cv_struct_timespec" = x"yes"; then
    AC_DEFINE(HAVE_STRUCT_TIMESPEC,1,[Whether we have struct timespec])
 fi
 
+AC_CACHE_CHECK([for ucontext_t type],libreplace_cv_ucontext_t, [
+    AC_TRY_COMPILE([
+#include <signal.h>
+#if HAVE_SYS_UCONTEXT_H
+#include <sys/ucontext.h>
+# endif
+],[ucontext_t uc; sigaddset(&uc.uc_sigmask, SIGUSR1);],
+	libreplace_cv_ucontext_t=yes,libreplace_cv_ucontext_t=no)])
+if test x"$libreplace_cv_ucontext_t" = x"yes"; then
+   AC_DEFINE(HAVE_UCONTEXT_T,1,[Whether we have ucontext_t])
+fi
+
 AC_CHECK_FUNCS([printf memset memcpy],,[AC_MSG_ERROR([Required function not found])])
 
 echo "LIBREPLACE_BROKEN_CHECKS: END"
diff --git a/lib/replace/libreplace_cc.m4 b/lib/replace/libreplace_cc.m4
index 48d9e84..50cb735 100644
--- a/lib/replace/libreplace_cc.m4
+++ b/lib/replace/libreplace_cc.m4
@@ -50,11 +50,21 @@ AC_PROG_INSTALL
 AC_ISC_POSIX
 AC_N_DEFINE(_XOPEN_SOURCE_EXTENDED)
 
+AC_MSG_CHECKING(checking getconf LFS_CFLAGS for large file support flags)
+LFS_CFLAGS=`(getconf LFS_CFLAGS) 2>/dev/null` || LFS_CFLAGS=""
+
+AC_MSG_RESULT(${LFS_CFLAGS})
+if test "x$LFS_CFLAGS" != 'x-1' || test "x$LFS_CFLAGS" != "xundefined"; then
+   CFLAGS="$CFLAGS $LFS_CFLAGS"
+fi
+
 AC_SYS_LARGEFILE
 
 dnl Add #include for broken IRIX header files
 case "$host_os" in
 	*irix6*) AC_ADD_INCLUDE(<standards.h>)
+		AC_N_DEFINE(_XOPEN_SOURCE,600)
+		AC_N_DEFINE(_BSD_TYPES)
 		;;
 	*hpux*)
 		# mmap on HPUX is completely broken...
@@ -102,9 +112,17 @@ case "$host_os" in
 		;;
 esac
 
+# Do not check for standards.h on darwin, we get nasty warnings on
+# OS/X Lion. Probably a positive-list of OS'es like IRIX and AIX
+# would be the better choice, but this seems to work fine
 
-
-AC_CHECK_HEADERS([standards.h])
+case "$host_os" in
+     *darwin*)
+	;;
+     *)
+        AC_CHECK_HEADERS([standards.h])
+	;;
+esac
 
 # Solaris needs HAVE_LONG_LONG defined
 AC_CHECK_TYPES(long long)
diff --git a/lib/replace/libreplace_macros.m4 b/lib/replace/libreplace_macros.m4
index 42b8847..f3753c4 100644
--- a/lib/replace/libreplace_macros.m4
+++ b/lib/replace/libreplace_macros.m4
@@ -330,3 +330,18 @@ fi
   AC_DEFINE_UNQUOTED($ac_tr_hdr, 1, [Define if you have type `$1'])
 fi
 ])
+
+# AC_CHECK_VALUEOF(TYPE, [INCLUDES = DEFAULT-INCLUDES])
+# ---------------------------------------------------------------
+AC_DEFUN([AC_CHECK_VALUEOF],
+[AS_LITERAL_IF(m4_translit([[$1]], [*], [p]), [],
+	       [m4_fatal([$0: requires literal arguments])])]dnl
+[
+_AC_CACHE_CHECK_INT([value of $1], [AS_TR_SH([ac_cv_valueof_$1])],
+  [(long int) ($1)],
+  [AC_INCLUDES_DEFAULT([$2])],
+  [])
+
+AC_DEFINE_UNQUOTED(AS_TR_CPP(valueof_$1), $AS_TR_SH([ac_cv_valueof_$1]),
+		   [The value of `$1'.])
+])# AC_CHECK_VALUEOF
diff --git a/lib/replace/libreplace_network.m4 b/lib/replace/libreplace_network.m4
index eadcc6b..bb2a843 100644
--- a/lib/replace/libreplace_network.m4
+++ b/lib/replace/libreplace_network.m4
@@ -473,6 +473,30 @@ fi
 LIBS=$old_LIBS
 CPPFLAGS="$libreplace_SAVE_CPPFLAGS"
 
+AC_CACHE_CHECK([for SO_PEERCRED],libreplace_cv_HAVE_PEERCRED,[
+AC_TRY_COMPILE([#include <sys/types.h>
+#include <sys/socket.h>],
+[struct ucred cred;
+ socklen_t cred_len;
+ int ret = getsockopt(0, SOL_SOCKET, SO_PEERCRED, &cred, &cred_len);
+],
+libreplace_cv_HAVE_PEERCRED=yes,libreplace_cv_HAVE_PEERCRED=no,libreplace_cv_HAVE_PEERCRED=cross)])
+if test x"$libreplace_cv_HAVE_PEERCRED" = x"yes"; then
+    AC_DEFINE(HAVE_PEERCRED,1,[Whether we can use SO_PEERCRED to get socket credentials])
+fi
+
+AC_CACHE_CHECK([for getpeereid],libreplace_cv_HAVE_GETPEEREID,[
+AC_TRY_LINK([#include <sys/types.h>
+#include <unistd.h>],
+[uid_t uid; gid_t gid; int ret;
+ ret = getpeereid(0, &uid, &gid);
+],
+libreplace_cv_HAVE_GETPEEREID=yes,libreplace_cv_HAVE_GETPEEREID=no)])
+if test x"$libreplace_cv_HAVE_GETPEEREID" = xyes; then
+   AC_DEFINE(HAVE_GETPEEREID,1,
+	     [Whether we have getpeereid to get socket credentials])
+fi
+
 LIBREPLACEOBJ="${LIBREPLACEOBJ} ${LIBREPLACE_NETWORK_OBJS}"
 
 echo "LIBREPLACE_NETWORK_CHECKS: END"
diff --git a/lib/replace/poll.c b/lib/replace/poll.c
index e41548d..1105617 100644
--- a/lib/replace/poll.c
+++ b/lib/replace/poll.c
@@ -30,6 +30,12 @@
 
 #include "replace.h"
 #include "system/select.h"
+#ifdef HAVE_SYS_TIME_H
+#include <sys/time.h>
+#endif
+#ifdef HAVE_SYS_IOCTL_H
+#include <sys/ioctl.h>
+#endif
 
 
 int rep_poll(struct pollfd *fds, nfds_t nfds, int timeout)
@@ -40,7 +46,7 @@ int rep_poll(struct pollfd *fds, nfds_t nfds, int timeout)
 	int rc;
 	nfds_t i;
 
-	if (fds == NULL) {
+	if ((fds == NULL) && (nfds != 0)) {
 		errno = EFAULT;
 		return -1;
 	}
diff --git a/lib/replace/replace-test.h b/lib/replace/replace-test.h
index a522853..ed8e75e 100644
--- a/lib/replace/replace-test.h
+++ b/lib/replace/replace-test.h
@@ -1,10 +1,6 @@
 #ifndef __LIB_REPLACE_REPLACE_TEST_H__
 #define __LIB_REPLACE_REPLACE_TEST_H__
 
-#include <stdbool.h>
-struct torture_context;
-
-bool torture_local_replace(struct torture_context *ctx);
 int libreplace_test_strptime(void);
 int test_readdir_os2_delete(void);
 int getifaddrs_test(void);
diff --git a/lib/replace/replace-testsuite.h b/lib/replace/replace-testsuite.h
new file mode 100644
index 0000000..b28dbec
--- /dev/null
+++ b/lib/replace/replace-testsuite.h
@@ -0,0 +1,10 @@
+#ifndef __LIB_REPLACE_REPLACE_TESTSUITE_H__
+#define __LIB_REPLACE_REPLACE_TESTSUITE_H__
+
+#include <stdbool.h>
+struct torture_context;
+
+bool torture_local_replace(struct torture_context *ctx);
+
+#endif /* __LIB_REPLACE_REPLACE_TESTSUITE_H__ */
+
diff --git a/lib/replace/replace.c b/lib/replace/replace.c
index d9a96ff..37edb31 100644
--- a/lib/replace/replace.c
+++ b/lib/replace/replace.c
@@ -27,6 +27,7 @@
 
 #include "system/filesys.h"
 #include "system/time.h"
+#include "system/network.h"
 #include "system/passwd.h"
 #include "system/syslog.h"
 #include "system/locale.h"
@@ -213,16 +214,6 @@ int rep_initgroups(char *name, gid_t id)
 #endif /* HAVE_INITGROUPS */
 
 
-#if (defined(SecureWare) && defined(SCO))
-/* This is needed due to needing the nap() function but we don't want
-   to include the Xenix libraries since that will break other things...
-   BTW: system call # 0x0c28 is the same as calling nap() */
-long nap(long milliseconds) {
-	 return syscall(0x0c28, milliseconds);
- }
-#endif
-
-
 #ifndef HAVE_MEMMOVE
 /*******************************************************************
 safely copies memory, ensuring no overlap problems.
@@ -411,10 +402,10 @@ int rep_mkstemp(char *template)
 {
 	/* have a reasonable go at emulating it. Hope that
 	   the system mktemp() isn't completely hopeless */
-	char *p = mktemp(template);
-	if (!p)
+	mktemp(template);
+	if (template[0] == 0)
 		return -1;
-	return open(p, O_CREAT|O_EXCL|O_RDWR, 0600);
+	return open(template, O_CREAT|O_EXCL|O_RDWR, 0600);
 }
 #endif
 
@@ -750,7 +741,7 @@ void *rep_memmem(const void *haystack, size_t haystacklen,
 }
 #endif
 
-#ifndef HAVE_VDPRINTF
+#if !defined(HAVE_VDPRINTF) || !defined(HAVE_C99_VSNPRINTF)
 int rep_vdprintf(int fd, const char *format, va_list ap)
 {
 	char *s = NULL;
@@ -767,7 +758,7 @@ int rep_vdprintf(int fd, const char *format, va_list ap)
 }
 #endif
 
-#ifndef HAVE_DPRINTF
+#if !defined(HAVE_DPRINTF) || !defined(HAVE_C99_VSNPRINTF)
 int rep_dprintf(int fd, const char *format, ...)
 {
 	int ret;
@@ -794,7 +785,7 @@ char *rep_get_current_dir_name(void)
 }
 #endif
 
-#if !defined(HAVE_STRERROR_R) || !defined(STRERROR_R_PROTO_COMPATIBLE)
+#ifndef HAVE_STRERROR_R
 int rep_strerror_r(int errnum, char *buf, size_t buflen)
 {
 	char *s = strerror(errnum);
@@ -828,3 +819,84 @@ int rep_clock_gettime(clockid_t clk_id, struct timespec *tp)
 	return 0;
 }
 #endif
+
+#ifndef HAVE_MEMALIGN
+void *rep_memalign( size_t align, size_t size )
+{
+#if defined(HAVE_POSIX_MEMALIGN)
+	void *p = NULL;
+	int ret = posix_memalign( &p, align, size );
+	if ( ret == 0 )
+		return p;
+
+	return NULL;
+#else
+	/* On *BSD systems memaligns doesn't exist, but memory will
+	 * be aligned on allocations of > pagesize. */
+#if defined(SYSCONF_SC_PAGESIZE)
+	size_t pagesize = (size_t)sysconf(_SC_PAGESIZE);
+#elif defined(HAVE_GETPAGESIZE)
+	size_t pagesize = (size_t)getpagesize();
+#else
+	size_t pagesize = (size_t)-1;
+#endif
+	if (pagesize == (size_t)-1) {
+		errno = ENOSYS;
+		return NULL;
+	}
+	if (size < pagesize) {
+		size = pagesize;
+	}
+	return malloc(size);
+#endif
+}
+#endif
+
+#ifndef HAVE_GETPEEREID
+int rep_getpeereid(int s, uid_t *uid, gid_t *gid)
+{
+#if defined(HAVE_PEERCRED)
+	struct ucred cred;
+	socklen_t cred_len = sizeof(struct ucred);
+	int ret;
+
+#undef getsockopt
+	ret = getsockopt(s, SOL_SOCKET, SO_PEERCRED, (void *)&cred, &cred_len);
+	if (ret != 0) {
+		return -1;
+	}
+
+	if (cred_len != sizeof(struct ucred)) {
+		errno = EINVAL;
+		return -1;
+	}
+
+	*uid = cred.uid;
+	*gid = cred.gid;
+	return 0;
+#else
+	errno = ENOSYS;
+	return -1;
+#endif
+}
+#endif
+
+#ifndef HAVE_USLEEP
+int rep_usleep(useconds_t sec)
+{
+	struct timeval tval;
+	/*
+	 * Fake it with select...
+	 */
+	tval.tv_sec = 0;
+	tval.tv_usec = usecs/1000;
+	select(0,NULL,NULL,NULL,&tval);
+	return 0;
+}
+#endif /* HAVE_USLEEP */
+
+#ifndef HAVE_SETPROCTITLE
+void rep_setproctitle(const char *fmt, ...)
+{
+}
+#endif
diff --git a/lib/replace/replace.h b/lib/replace/replace.h
index c081f23..c0b7997 100644
--- a/lib/replace/replace.h
+++ b/lib/replace/replace.h
@@ -46,18 +46,22 @@
 #endif
 
 
-#ifdef HAVE_STDINT_H
+#ifdef HAVE_INTTYPES_H
+#define __STDC_FORMAT_MACROS
+#include <inttypes.h>
+#elif HAVE_STDINT_H
 #include <stdint.h>
 /* force off HAVE_INTTYPES_H so that roken doesn't try to include both,
    which causes a warning storm on irix */
 #undef HAVE_INTTYPES_H
-#elif HAVE_INTTYPES_H
-#define __STDC_FORMAT_MACROS
-#include <inttypes.h>
+#endif
+
+#ifdef HAVE_MALLOC_H
+#include <malloc.h>
 #endif
 
 #ifndef __PRI64_PREFIX
-# if __WORDSIZE == 64
+# if __WORDSIZE == 64 && ! defined __APPLE__
 #  define __PRI64_PREFIX	"l"
 # else
 #  define __PRI64_PREFIX	"ll"
@@ -104,6 +108,53 @@
 # define PRIu64		__PRI64_PREFIX "u"
 #endif
 
+#ifndef SCNd8
+# define SCNd8		"hhd"
+#endif
+#ifndef SCNd16
+# define SCNd16		"hd"
+#endif
+#ifndef SCNd32
+# define SCNd32		"d"
+#endif
+#ifndef SCNd64
+# define SCNd64		__PRI64_PREFIX "d"
+#endif
+
+#ifndef SCNi8
+# define SCNi8		"hhi"
+#endif
+#ifndef SCNi16
+# define SCNi16		"hi"
+#endif
+#ifndef SCNi32
+# define SCNi32		"i"
+#endif
+#ifndef SCNi64
+# define SCNi64		__PRI64_PREFIX "i"
+#endif
+
+#ifndef SCNu8
+# define SCNu8		"hhu"
+#endif
+#ifndef SCNu16
+# define SCNu16		"hu"
+#endif
+#ifndef SCNu32
+# define SCNu32		"u"
+#endif
+#ifndef SCNu64
+# define SCNu64		__PRI64_PREFIX "u"
+#endif
+
+#ifdef HAVE_BSD_STRING_H
+#include <bsd/string.h>
+#endif
+
+#ifdef HAVE_BSD_UNISTD_H
+#include <bsd/unistd.h>
+#endif
+
 #ifdef HAVE_STRING_H
 #include <string.h>
 #endif
@@ -116,6 +167,10 @@
 #include <sys/types.h>
 #endif
 
+#ifdef HAVE_SETPROCTITLE_H
+#include <setproctitle.h>
+#endif
+
 #if STDC_HEADERS
 #include <stdlib.h>
 #include <stddef.h>
@@ -153,6 +208,11 @@ void *rep_memmem(const void *haystack, size_t haystacklen,
 		 const void *needle, size_t needlelen);
 #endif
 
+#ifndef HAVE_MEMALIGN
+#define memalign rep_memalign
+void *rep_memalign(size_t boundary, size_t size);
+#endif
+
 #ifndef HAVE_MKTIME
 #define mktime rep_mktime
 /* prototype is in "system/time.h" */
@@ -355,16 +415,6 @@ int rep_dlclose(void *handle);
 /* prototype is in system/network.h */
 #endif
 
-#ifndef HAVE_VDPRINTF
-#define vdprintf rep_vdprintf
-int rep_vdprintf(int fd, const char *format, va_list ap);
-#endif
-
-#ifndef HAVE_DPRINTF
-#define dprintf rep_dprintf
-int rep_dprintf(int fd, const char *format, ...);
-#endif
-
 #ifndef PRINTF_ATTRIBUTE
 #if (__GNUC__ >= 3) && (__GNUC_MINOR__ >= 1 )
 /** Use gcc attribute to check printf fns.  a1 is the 1-based index of
@@ -385,7 +435,17 @@ int rep_dprintf(int fd, const char *format, ...);
 #endif
 #endif
 
-#ifndef HAVE_VASPRINTF
+#if !defined(HAVE_VDPRINTF) || !defined(HAVE_C99_VSNPRINTF)
+#define vdprintf rep_vdprintf
+int rep_vdprintf(int fd, const char *format, va_list ap) PRINTF_ATTRIBUTE(2,0);
+#endif
+
+#if !defined(HAVE_DPRINTF) || !defined(HAVE_C99_VSNPRINTF)
+#define dprintf rep_dprintf
+int rep_dprintf(int fd, const char *format, ...) PRINTF_ATTRIBUTE(2,3);
+#endif
+
+#if !defined(HAVE_VASPRINTF) || !defined(HAVE_C99_VSNPRINTF)
 #define vasprintf rep_vasprintf
 int rep_vasprintf(char **ptr, const char *format, va_list ap) PRINTF_ATTRIBUTE(2,0);
 #endif
@@ -400,11 +460,29 @@ int rep_snprintf(char *,size_t ,const char *, ...) PRINTF_ATTRIBUTE(3,4);
 int rep_vsnprintf(char *,size_t ,const char *, va_list ap) PRINTF_ATTRIBUTE(3,0);
 #endif
 
-#ifndef HAVE_ASPRINTF
+#if !defined(HAVE_ASPRINTF) || !defined(HAVE_C99_VSNPRINTF)
 #define asprintf rep_asprintf
 int rep_asprintf(char **,const char *, ...) PRINTF_ATTRIBUTE(2,3);
 #endif
 
+#if !defined(HAVE_C99_VSNPRINTF)
+#ifdef REPLACE_BROKEN_PRINTF
+/*
+ * We do not redefine printf by default
+ * as it breaks the build if system headers
+ * use __attribute__((format(printf, 3, 0)))
+ * instead of __attribute__((format(__printf__, 3, 0)))
+ */
+#define printf rep_printf
+#endif
+int rep_printf(const char *, ...) PRINTF_ATTRIBUTE(1,2);
+#endif
+
+#if !defined(HAVE_C99_VSNPRINTF)
+#define fprintf rep_fprintf
+int rep_fprintf(FILE *stream, const char *, ...) PRINTF_ATTRIBUTE(2,3);
+#endif
+
 #ifndef HAVE_VSYSLOG
 #ifdef HAVE_SYSLOG
 #define vsyslog rep_vsyslog
@@ -434,7 +512,7 @@ void rep_vsyslog (int facility_priority, const char *format, va_list arglist) PR
 typedef int (*comparison_fn_t)(const void *, const void *);
 #endif
 
-#ifdef REPLACE_STRPTIME
+#ifndef HAVE_WORKING_STRPTIME
 #define strptime rep_strptime
 struct tm;
 char *rep_strptime(const char *buf, const char *format, struct tm *tm);
@@ -531,8 +609,7 @@ ssize_t rep_pwrite(int __fd, const void *__buf, size_t __nbytes, off_t __offset)
 char *rep_get_current_dir_name(void);
 #endif
 
-#if !defined(HAVE_STRERROR_R) || !defined(STRERROR_R_PROTO_COMPATIBLE)
-#undef strerror_r
+#ifndef HAVE_STRERROR_R
 #define strerror_r rep_strerror_r
 int rep_strerror_r(int errnum, char *buf, size_t buflen);
 #endif
@@ -569,6 +646,10 @@ int rep_strerror_r(int errnum, char *buf, size_t buflen);
 #define UINT64_MAX ((uint64_t)-1)
 #endif
 
+#ifndef INT64_MAX
+#define INT64_MAX 9223372036854775807LL
+#endif
+
 #ifndef CHAR_BIT
 #define CHAR_BIT 8
 #endif
@@ -802,4 +883,20 @@ int fdatasync(int );
 /* prototype is in "system/network.h" */
 #endif
 
+#ifndef HAVE_GETPEEREID
+#define getpeereid rep_getpeereid
+int rep_getpeereid(int s, uid_t *uid, gid_t *gid);
+#endif
+
+#ifndef HAVE_USLEEP
+#define usleep rep_usleep
+typedef long useconds_t;
+int usleep(useconds_t);
+#endif
+
+#ifndef HAVE_SETPROCTITLE
+#define setproctitle rep_setproctitle
+void rep_setproctitle(const char *fmt, ...) PRINTF_ATTRIBUTE(1, 2);
+#endif
+
 #endif /* _LIBREPLACE_REPLACE_H */
diff --git a/lib/replace/samba.m4 b/lib/replace/samba.m4
deleted file mode 100644
index b758220..0000000
--- a/lib/replace/samba.m4
+++ /dev/null
@@ -1,34 +0,0 @@
-AC_LIBREPLACE_BROKEN_CHECKS
-AC_LIBREPLACE_NETWORK_CHECKS
-
-SMB_EXT_LIB(LIBREPLACE_EXT, [${LIBDL} ${CRYPT_LIBS}])
-SMB_ENABLE(LIBREPLACE_EXT)
-
-SMB_EXT_LIB(LIBREPLACE_NETWORK, [${LIBREPLACE_NETWORK_LIBS}])
-SMB_ENABLE(LIBREPLACE_NETWORK)
-
-# remove leading ./
-LIBREPLACE_DIR=`echo ${libreplacedir} |sed -e 's/^\.\///g'`
-
-# remove leading srcdir .. we are looking for the relative
-# path within the samba source tree or wherever libreplace is.
-# We need to make sure the object is not forced to end up in
-# the source directory because we might be using a separate
-# build directory.
-LIBREPLACE_DIR=`echo ${LIBREPLACE_DIR} | sed -e "s|^$srcdir/||g"`
-
-LIBREPLACE_OBJS="${LIBREPLACEOBJ}"
-
-SMB_SUBSYSTEM(LIBREPLACE,
-	[${LIBREPLACE_OBJS}],
-	[LIBREPLACE_EXT LIBREPLACE_NETWORK],
-	[-Ilib/replace])
-
-LIBREPLACE_HOSTCC_OBJS=`echo ${LIBREPLACE_OBJS} |sed -e 's/\.o/\.ho/g'`
-
-SMB_SUBSYSTEM(LIBREPLACE_HOSTCC,
-	[${LIBREPLACE_HOSTCC_OBJS}],
-	[],
-	[-Ilib/replace])
-
-AC_CHECK_FUNCS([syslog],,[AC_MSG_ERROR([Required function not found])])
diff --git a/lib/replace/snprintf.c b/lib/replace/snprintf.c
index bca7742..6b4a711 100644
--- a/lib/replace/snprintf.c
+++ b/lib/replace/snprintf.c
@@ -1187,7 +1187,7 @@ static int add_cnk_list_entry(struct pr_chunk_x **list,
 	return max;
 }
 
- int vsnprintf (char *str, size_t count, const char *fmt, va_list args)
+ int rep_vsnprintf (char *str, size_t count, const char *fmt, va_list args)
 {
 	return dopr(str, count, fmt, args);
 }
@@ -1200,7 +1200,7 @@ static int add_cnk_list_entry(struct pr_chunk_x **list,
  * that doesn't work properly according to the autoconf test.
  */
 #if !defined(HAVE_SNPRINTF) || !defined(HAVE_C99_VSNPRINTF)
- int snprintf(char *str,size_t count,const char *fmt,...)
+ int rep_snprintf(char *str,size_t count,const char *fmt,...)
 {
 	size_t ret;
 	va_list ap;
@@ -1213,7 +1213,7 @@ static int add_cnk_list_entry(struct pr_chunk_x **list,
 #endif
 
 #ifndef HAVE_C99_VSNPRINTF
- int printf(const char *fmt, ...)
+ int rep_printf(const char *fmt, ...)
 {
 	va_list ap;
 	int ret;
@@ -1234,7 +1234,7 @@ static int add_cnk_list_entry(struct pr_chunk_x **list,
 #endif
 
 #ifndef HAVE_C99_VSNPRINTF
- int fprintf(FILE *stream, const char *fmt, ...)
+ int rep_fprintf(FILE *stream, const char *fmt, ...)
 {
 	va_list ap;
 	int ret;
@@ -1256,8 +1256,8 @@ static int add_cnk_list_entry(struct pr_chunk_x **list,
 
 #endif 
 
-#ifndef HAVE_VASPRINTF
- int vasprintf(char **ptr, const char *format, va_list ap)
+#if !defined(HAVE_VASPRINTF) || !defined(HAVE_C99_VSNPRINTF)
+ int rep_vasprintf(char **ptr, const char *format, va_list ap)
 {
 	int ret;
 	va_list ap2;
@@ -1278,9 +1278,8 @@ static int add_cnk_list_entry(struct pr_chunk_x **list,
 }
 #endif
 
-
-#ifndef HAVE_ASPRINTF
- int asprintf(char **ptr, const char *format, ...)
+#if !defined(HAVE_ASPRINTF) || !defined(HAVE_C99_VSNPRINTF)
+ int rep_asprintf(char **ptr, const char *format, ...)
 {
 	va_list ap;
 	int ret;
diff --git a/lib/replace/strptime.c b/lib/replace/strptime.c
index 0e40f75..20e5d8c 100644
--- a/lib/replace/strptime.c
+++ b/lib/replace/strptime.c
@@ -251,7 +251,6 @@ strptime_internal (rp, fmt, tm, decided, era_cnt)
      enum locale_status *decided;
      int era_cnt;
 {
-  const char *rp_backup;
   int cnt;
   size_t val;
   int have_I, is_pm;
@@ -261,15 +260,17 @@ strptime_internal (rp, fmt, tm, decided, era_cnt)
   int have_yday;
   int have_mon, have_mday;
 #ifdef _NL_CURRENT
+  const char *rp_backup;
   size_t num_eras;
-#endif
   struct era_entry *era;
 
+  era = NULL;
+#endif
+
   have_I = is_pm = 0;
   century = -1;
   want_century = 0;
   want_era = 0;
-  era = NULL;
 
   have_wday = want_xday = have_yday = have_mon = have_mday = 0;
 
@@ -299,8 +300,10 @@ strptime_internal (rp, fmt, tm, decided, era_cnt)
     start_over:
 #endif
 
+#ifdef _NL_CURRENT
       /* Make back up of current processing pointer.  */
       rp_backup = rp;
+#endif
 
       switch (*fmt++)
 	{
diff --git a/lib/replace/strptime.m4 b/lib/replace/strptime.m4
index b1a56b4..8ac22f6 100644
--- a/lib/replace/strptime.m4
+++ b/lib/replace/strptime.m4
@@ -1,3 +1,5 @@
+AC_CHECK_FUNCS(strptime)
+AC_CHECK_DECLS(strptime, [], [], [#include <time.h>])
 AC_CACHE_CHECK([whether strptime is available and works],libreplace_cv_STRPTIME_OK,[
 	AC_TRY_RUN([
 		#define LIBREPLACE_CONFIGURE_TEST_STRPTIME
@@ -8,6 +10,7 @@ AC_CACHE_CHECK([whether strptime is available and works],libreplace_cv_STRPTIME_
 		[libreplace_cv_STRPTIME_OK="assuming not"])
 ])
 if test x"$libreplace_cv_STRPTIME_OK" != x"yes"; then
-        AC_DEFINE(REPLACE_STRPTIME,1,[Whether strptime should be replaced])
         LIBREPLACEOBJ="${LIBREPLACEOBJ} $libreplacedir/strptime.o"
+else
+        AC_DEFINE(HAVE_WORKING_STRPTIME,1,[Whether strptime is working correct])
 fi
diff --git a/lib/replace/system/filesys.h b/lib/replace/system/filesys.h
index e2c3c1d..c8ac2b4 100644
--- a/lib/replace/system/filesys.h
+++ b/lib/replace/system/filesys.h
@@ -114,6 +114,8 @@
 
 #if HAVE_SYS_ATTRIBUTES_H
 #include <sys/attributes.h>
+#elif HAVE_ATTR_ATTRIBUTES_H
+#include <attr/attributes.h>
 #endif
 
 /* mutually exclusive (SuSE 8.2) */
@@ -123,11 +125,26 @@
 #include <sys/xattr.h>
 #endif
 
+#ifdef HAVE_SYS_EA_H
+#include <sys/ea.h>
+#endif
+
+#ifdef HAVE_SYS_EXTATTR_H
+#include <sys/extattr.h>
+#endif
 
 #ifdef HAVE_SYS_RESOURCE_H
 #include <sys/resource.h>
 #endif
 
+#ifndef XATTR_CREATE
+#define XATTR_CREATE  0x1       /* set value, fail if attr already exists */
+#endif
+
+#ifndef XATTR_REPLACE
+#define XATTR_REPLACE 0x2       /* set value, fail if attr does not exist */
+#endif
+
 /* Some POSIX definitions for those without */
 
 #ifndef S_IFDIR
@@ -200,4 +217,61 @@
 # define uwrap_enabled() 0
 #endif /* UID_WRAPPER */
 
+/*
+   this allows us to use a uniform error handling for our xattr
+   wrappers
+*/
+#ifndef ENOATTR
+#define ENOATTR ENODATA
+#endif
+
+
+#if !defined(HAVE_GETXATTR) || defined(XATTR_ADDITIONAL_OPTIONS)
+ssize_t rep_getxattr (const char *path, const char *name, void *value, size_t size);
+#define getxattr(path, name, value, size) rep_getxattr(path, name, value, size)
+/* define is in "replace.h" */
+#endif
+
+#if !defined(HAVE_FGETXATTR) || defined(XATTR_ADDITIONAL_OPTIONS)
+ssize_t rep_fgetxattr (int filedes, const char *name, void *value, size_t size);
+#define fgetxattr(filedes, name, value, size) rep_fgetxattr(filedes, name, value, size)
+/* define is in "replace.h" */
+#endif
+
+#if !defined(HAVE_LISTXATTR) || defined(XATTR_ADDITIONAL_OPTIONS)
+ssize_t rep_listxattr (const char *path, char *list, size_t size);
+#define listxattr(path, list, size) rep_listxattr(path, list, size)
+/* define is in "replace.h" */
+#endif
+
+#if !defined(HAVE_FLISTXATTR) || defined(XATTR_ADDITIONAL_OPTIONS)
+ssize_t rep_flistxattr (int filedes, char *list, size_t size);
+#define flistxattr(filedes, value, size) rep_flistxattr(filedes, value, size)
+/* define is in "replace.h" */
+#endif
+
+#if !defined(HAVE_REMOVEXATTR) || defined(XATTR_ADDITIONAL_OPTIONS)
+int rep_removexattr (const char *path, const char *name);
+#define removexattr(path, name) rep_removexattr(path, name)
+/* define is in "replace.h" */
+#endif
+
+#if !defined(HAVE_FREMOVEXATTR) || defined(XATTR_ADDITIONAL_OPTIONS)
+int rep_fremovexattr (int filedes, const char *name);
+#define fremovexattr(filedes, name) rep_fremovexattr(filedes, name)
+/* define is in "replace.h" */
+#endif
+
+#if !defined(HAVE_SETXATTR) || defined(XATTR_ADDITIONAL_OPTIONS)
+int rep_setxattr (const char *path, const char *name, const void *value, size_t size, int flags);
+#define setxattr(path, name, value, size, flags) rep_setxattr(path, name, value, size, flags)
+/* define is in "replace.h" */
+#endif
+
+#if !defined(HAVE_FSETXATTR) || defined(XATTR_ADDITIONAL_OPTIONS)
+int rep_fsetxattr (int filedes, const char *name, const void *value, size_t size, int flags);
+#define fsetxattr(filedes, name, value, size, flags) rep_fsetxattr(filedes, name, value, size, flags)
+/* define is in "replace.h" */
+#endif
+
 #endif
diff --git a/lib/replace/system/printing.h b/lib/replace/system/gssapi.h
similarity index 64%
rename from lib/replace/system/printing.h
rename to lib/replace/system/gssapi.h
index 7eb02d0..6386c7b 100644
--- a/lib/replace/system/printing.h
+++ b/lib/replace/system/gssapi.h
@@ -1,17 +1,17 @@
-#ifndef _system_printing_h
-#define _system_printing_h
+#ifndef _system_gssapi_h
+#define _system_gssapi_h
 
-/* 
+/*
    Unix SMB/CIFS implementation.
 
-   printing system include wrappers
+   GSSAPI system include wrappers
 
    Copyright (C) Andrew Tridgell 2004
-   
+
      ** NOTE! The following LGPL license applies to the replace
      ** library. This does NOT imply that all of Samba is released
      ** under the LGPL
-   
+
    This library is free software; you can redistribute it and/or
    modify it under the terms of the GNU Lesser General Public
    License as published by the Free Software Foundation; either
@@ -27,24 +27,27 @@
 
 */
 
-#ifdef AIX
-#define DEFAULT_PRINTING PRINT_AIX
-#define PRINTCAP_NAME "/etc/qconfig"
-#endif
+#ifdef HAVE_GSSAPI
 
-#ifdef HPUX
-#define DEFAULT_PRINTING PRINT_HPUX
+#ifdef HAVE_GSSAPI_GSSAPI_EXT_H
+#include <gssapi/gssapi_ext.h>
+#elif HAVE_GSSAPI_GSSAPI_H
+#include <gssapi/gssapi.h>
+#elif HAVE_GSSAPI_GSSAPI_GENERIC_H
+#include <gssapi/gssapi_generic.h>
+#elif HAVE_GSSAPI_H
+#include <gssapi.h>
 #endif
 
-#ifdef QNX
-#define DEFAULT_PRINTING PRINT_QNX
+#if HAVE_GSSAPI_GSSAPI_KRB5_H
+#include <gssapi/gssapi_krb5.h>
 #endif
 
-#ifndef DEFAULT_PRINTING
-#define DEFAULT_PRINTING PRINT_BSD
-#endif
-#ifndef PRINTCAP_NAME
-#define PRINTCAP_NAME "/etc/printcap"
+#if HAVE_GSSAPI_GSSAPI_SPNEGO_H
+#include <gssapi/gssapi_spnego.h>
+#elif HAVE_GSSAPI_SPNEGO_H
+#include <gssapi_spnego.h>
 #endif
 
 #endif
+#endif
diff --git a/lib/replace/system/kerberos.h b/lib/replace/system/kerberos.h
index 7762d4b..636ce0f 100644
--- a/lib/replace/system/kerberos.h
+++ b/lib/replace/system/kerberos.h
@@ -7,11 +7,11 @@
    kerberos system include wrappers
 
    Copyright (C) Andrew Tridgell 2004
-   
+
      ** NOTE! The following LGPL license applies to the replace
      ** library. This does NOT imply that all of Samba is released
      ** under the LGPL
-   
+
    This library is free software; you can redistribute it and/or
    modify it under the terms of the GNU Lesser General Public
    License as published by the Free Software Foundation; either
@@ -37,19 +37,5 @@
 #include <com_err.h>
 #endif
 
-#ifdef HAVE_GSSAPI_GSSAPI_EXT_H
-#include <gssapi/gssapi_ext.h>
-#elif HAVE_GSSAPI_GSSAPI_H
-#include <gssapi/gssapi.h>
-#elif HAVE_GSSAPI_GSSAPI_GENERIC_H
-#include <gssapi/gssapi_generic.h>
-#elif HAVE_GSSAPI_H
-#include <gssapi.h>
-#endif
-
-#if HAVE_GSSAPI_GSSAPI_KRB5_H
-#include <gssapi/gssapi_krb5.h>
-#endif
-
 #endif
 #endif
diff --git a/lib/replace/system/passwd.h b/lib/replace/system/passwd.h
index f630012..8257e06 100644
--- a/lib/replace/system/passwd.h
+++ b/lib/replace/system/passwd.h
@@ -67,15 +67,6 @@
 #include <compat.h>
 #endif
 
-#ifdef REPLACE_GETPASS
-#if defined(REPLACE_GETPASS_BY_GETPASSPHRASE)
-#define getpass(prompt) getpassphrase(prompt)
-#else
-#define getpass(prompt) rep_getpass(prompt)
-char *rep_getpass(const char *prompt);
-#endif
-#endif
-
 #ifndef NGROUPS_MAX
 #define NGROUPS_MAX 32 /* Guess... */
 #endif
diff --git a/lib/replace/system/wait.h b/lib/replace/system/wait.h
index f0c3bdc..146c61a 100644
--- a/lib/replace/system/wait.h
+++ b/lib/replace/system/wait.h
@@ -40,6 +40,10 @@
 #include <setjmp.h>
 #endif
 
+#ifdef HAVE_SYS_UCONTEXT_H
+#include <sys/ucontext.h>
+#endif
+
 #if !defined(HAVE_SIG_ATOMIC_T_TYPE)
 typedef int sig_atomic_t;
 #endif
diff --git a/lib/replace/test/incoherent_mmap.c b/lib/replace/test/incoherent_mmap.c
new file mode 100644
index 0000000..ee288fd
--- /dev/null
+++ b/lib/replace/test/incoherent_mmap.c
@@ -0,0 +1,83 @@
+/* In OpenBSD, if you write to a file, another process doesn't see it
+ * in its mmap.  Returns with exit status 0 if that is the case, 1 if
+ * it's coherent, and other if there's a problem. */
+#include <err.h>
+#include <sys/mman.h>
+#include <unistd.h>
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <fcntl.h>
+#include <stdlib.h>
+#include <string.h>
+#include <errno.h>
+
+#define DATA "coherent.mmap"
+
+int main(int argc, char *argv[])
+{
+	int tochild[2], toparent[2];
+	int fd;
+	volatile unsigned char *map;
+	unsigned char *page;
+        const char *fname = argv[1];
+	char c = 0;
+
+	if (pipe(tochild) != 0 || pipe(toparent) != 0)
+		err(2, "Creating pipe");
+
+	if (!fname)
+		fname = DATA;
+
+	fd = open(fname, O_RDWR|O_CREAT|O_TRUNC, 0600);
+	if (fd < 0)
+		err(2, "opening %s", fname);
+	unlink(fname);
+
+	switch (fork()) {
+	case -1:
+		err(2, "Fork");
+	case 0:
+		close(tochild[1]);
+		close(toparent[0]);
+
+		/* Wait for parent to create file. */
+		if (read(tochild[0], &c, 1) != 1)
+			err(2, "reading from parent");
+
+		/* Alter first byte. */
+		pwrite(fd, &c, 1, 0);
+
+		if (write(toparent[1], &c, 1) != 1)
+			err(2, "writing to parent");
+		exit(0);
+
+	default:
+		close(tochild[0]);
+		close(toparent[1]);
+
+		/* Create a file and mmap it. */
+		page = malloc(getpagesize());
+		memset(page, 0x42, getpagesize());
+		if (write(fd, page, getpagesize()) != getpagesize())
+			err(2, "writing first page");
+		map = mmap(NULL, getpagesize(), PROT_READ|PROT_WRITE,
+			   MAP_SHARED, fd, 0);
+		if (map == MAP_FAILED)
+			err(2, "mapping file");
+
+		if (*map != 0x42)
+			errx(2, "first byte isn't 0x42!");
+
+		/* Tell child to alter file. */
+		if (write(tochild[1], &c, 1) != 1)
+			err(2, "writing to child");
+
+		if (read(toparent[0], &c, 1) != 1)
+			err(2, "reading from child");
+
+		if (*map)
+			errx(0, "mmap incoherent: first byte isn't 0.");
+
+		exit(1);
+	}
+}
diff --git a/lib/replace/test/main.c b/lib/replace/test/main.c
index 9bd1284..94264d7 100644
--- a/lib/replace/test/main.c
+++ b/lib/replace/test/main.c
@@ -24,9 +24,7 @@
 */
 
 #include "replace.h"
-
-struct torture_context;
-bool torture_local_replace(struct torture_context *ctx);
+#include "replace-testsuite.h"
 
 int main(void)
 {
diff --git a/lib/replace/test/testsuite.c b/lib/replace/test/testsuite.c
index 0c1fac6..52629ec 100644
--- a/lib/replace/test/testsuite.c
+++ b/lib/replace/test/testsuite.c
@@ -24,6 +24,8 @@
 */
 
 #include "replace.h"
+#include "replace-test.h"
+#include "replace-testsuite.h"
 
 /*
   we include all the system/ include files here so that libreplace tests
@@ -48,8 +50,6 @@
 
 #define TESTFILE "testfile.dat"
 
-struct torture_context;
-bool torture_local_replace(struct torture_context *ctx);
 
 /*
   test ftruncate() function
@@ -379,8 +379,6 @@ static int test_opendir(void)
 	return true;
 }
 
-extern int test_readdir_os2_delete(void);
-
 static int test_readdir(void)
 {
 	printf("test: readdir\n");
@@ -465,12 +463,6 @@ static int test_pwrite(void)
 	return true;
 }
 
-static int test_getpass(void)
-{
-	/* FIXME */
-	return true;
-}
-
 static int test_inet_ntoa(void)
 {
 	/* FIXME */
@@ -1091,7 +1083,6 @@ bool torture_local_replace(struct torture_context *ctx)
 	ret &= test_mkstemp();
 	ret &= test_pread();
 	ret &= test_pwrite();
-	ret &= test_getpass();
 	ret &= test_inet_ntoa();
 	ret &= test_strtoll();
 	ret &= test_strtoull();
diff --git a/lib/replace/wscript b/lib/replace/wscript
index e4fc72b..2117f56 100644
--- a/lib/replace/wscript
+++ b/lib/replace/wscript
@@ -38,17 +38,49 @@ def configure(conf):
         conf.DEFINE('_OSF_SOURCE', 1, add_to_cflags=True)
         conf.DEFINE('_XOPEN_SOURCE', 600, add_to_cflags=True)
 
+    # SCM_RIGHTS is only avail if _XOPEN_SOURCE iѕ defined on IRIX
+    if conf.env['SYSTEM_UNAME_SYSNAME'] == 'IRIX':
+        conf.DEFINE('_XOPEN_SOURCE', 600, add_to_cflags=True)
+        conf.DEFINE('_BSD_TYPES', 1, add_to_cflags=True)
+
+    # Try to find the right extra flags for C99 initialisers
+    for f in ["", "-AC99", "-qlanglvl=extc99", "-qlanglvl=stdc99", "-c99"]:
+        if conf.CHECK_CFLAGS([f], '''
+struct foo {int x;char y;};
+struct foo bar = { .y = 'X', .x = 1 };
+'''):
+            if f != "":
+                conf.ADD_CFLAGS(f)
+            break
+
+    if conf.CHECK_CFLAGS(['-fstack-protector']) and conf.CHECK_LDFLAGS(['-fstack-protector']):
+        conf.ADD_CFLAGS('-fstack-protector')
+        conf.ADD_LDFLAGS('-fstack-protector')
+
+    # Try to find the right extra flags for -Werror behaviour
+    for f in ["-Werror",       # GCC
+	      "-errwarn=%all", # Sun Studio
+	      "-qhalt=w",     # IBM xlc
+	      "-w2",           # Tru64
+	      ]:
+        if conf.CHECK_CFLAGS([f], '''
+'''):
+            if not 'WERROR_CFLAGS' in conf.env:
+                conf.env['WERROR_CFLAGS'] = []
+            conf.env['WERROR_CFLAGS'].extend([f])
+            break
+
     conf.CHECK_HEADERS('linux/types.h crypt.h locale.h acl/libacl.h compat.h')
     conf.CHECK_HEADERS('acl/libacl.h attr/xattr.h compat.h ctype.h dustat.h')
     conf.CHECK_HEADERS('fcntl.h fnmatch.h glob.h history.h krb5.h langinfo.h')
     conf.CHECK_HEADERS('libaio.h locale.h ndir.h pwd.h')
     conf.CHECK_HEADERS('shadow.h sys/acl.h')
-    conf.CHECK_HEADERS('sys/attributes.h sys/capability.h sys/dir.h sys/epoll.h')
+    conf.CHECK_HEADERS('sys/attributes.h attr/attributes.h sys/capability.h sys/dir.h sys/epoll.h')
     conf.CHECK_HEADERS('sys/fcntl.h sys/filio.h sys/filsys.h sys/fs/s5param.h sys/fs/vx/quota.h')
     conf.CHECK_HEADERS('sys/id.h sys/ioctl.h sys/ipc.h sys/mman.h sys/mode.h sys/ndir.h sys/priv.h')
     conf.CHECK_HEADERS('sys/resource.h sys/security.h sys/shm.h sys/statfs.h sys/statvfs.h sys/termio.h')
     conf.CHECK_HEADERS('sys/vfs.h sys/xattr.h termio.h termios.h sys/file.h')
-    conf.CHECK_HEADERS('sys/wait.h sys/stat.h malloc.h grp.h')
+    conf.CHECK_HEADERS('sys/ucontext.h sys/wait.h sys/stat.h malloc.h grp.h')
     conf.CHECK_HEADERS('sys/select.h setjmp.h utime.h sys/syslog.h syslog.h')
     conf.CHECK_HEADERS('stdarg.h vararg.h sys/mount.h mntent.h')
     conf.CHECK_HEADERS('stropts.h unix.h string.h strings.h sys/param.h limits.h')
@@ -60,18 +92,44 @@ def configure(conf):
     conf.CHECK_HEADERS('libintl.h errno.h')
     conf.CHECK_HEADERS('gcrypt.h getopt.h iconv.h')
     conf.CHECK_HEADERS('sys/inotify.h memory.h nss.h sasl/sasl.h')
-    conf.CHECK_HEADERS('security/pam_appl.h sys/inotify.h zlib.h asm/unistd.h')
+    conf.CHECK_HEADERS('security/pam_appl.h zlib.h asm/unistd.h')
     conf.CHECK_HEADERS('aio.h sys/unistd.h rpc/rpc.h rpc/nettype.h alloca.h float.h')
 
-    conf.CHECK_HEADERS('rpcsvc/nis.h rpcsvc/ypclnt.h sys/prctl.h sys/sysctl.h')
+    conf.CHECK_HEADERS('rpcsvc/nis.h rpcsvc/ypclnt.h sys/sysctl.h')
     conf.CHECK_HEADERS('sys/fileio.h sys/filesys.h sys/dustat.h sys/sysmacros.h')
-    conf.CHECK_HEADERS('xfs/libxfs.h netgroup.h rpcsvc/yp_prot.h')
+    conf.CHECK_HEADERS('xfs/libxfs.h netgroup.h')
+
+    conf.CHECK_CODE('', headers='rpc/rpc.h rpcsvc/yp_prot.h', define='HAVE_RPCSVC_YP_PROT_H')
+
     conf.CHECK_HEADERS('valgrind.h valgrind/valgrind.h valgrind/memcheck.h')
     conf.CHECK_HEADERS('nss_common.h nsswitch.h ns_api.h')
     conf.CHECK_HEADERS('sys/extattr.h sys/ea.h sys/proplist.h sys/cdefs.h')
-    conf.CHECK_HEADERS('utmp.h utmpx.h lastlog.h')
+    conf.CHECK_HEADERS('utmp.h utmpx.h lastlog.h malloc.h')
     conf.CHECK_HEADERS('syscall.h sys/syscall.h inttypes.h')
 
+    # Check for process set name support
+    conf.CHECK_CODE('''
+                    #include <sys/prctl.h>
+                    int main(void) {
+                        prctl(0);
+                        return 0;
+                    }
+                    ''',
+                    'HAVE_PRCTL',
+                    headers='sys/prctl.h',
+                    msg='Checking for prctl syscall')
+
+    conf.CHECK_CODE('''
+                    #include <unistd.h>
+                    #ifdef HAVE_FCNTL_H
+                    #include <fcntl.h>
+                    #endif
+                    int main(void) { int fd = open("/dev/null", O_DIRECT); }
+                    ''',
+                    define='HAVE_OPEN_O_DIRECT',
+                    addmain=False,
+                    msg='Checking for O_DIRECT flag to open(2)')
+
     conf.CHECK_TYPES('"long long" intptr_t uintptr_t ptrdiff_t comparison_fn_t')
     conf.CHECK_TYPE('_Bool', define='HAVE__Bool')
     conf.CHECK_TYPE('bool', define='HAVE_BOOL')
@@ -91,6 +149,8 @@ def configure(conf):
     conf.CHECK_TYPE('offset_t', 'loff_t')
     conf.CHECK_TYPE('volatile int', define='HAVE_VOLATILE')
     conf.CHECK_TYPE('uint_t', 'unsigned int')
+    conf.CHECK_TYPE('blksize_t', 'long', headers='sys/types.h sys/stat.h unistd.h')
+    conf.CHECK_TYPE('blkcnt_t', 'long', headers='sys/types.h sys/stat.h unistd.h')
 
     conf.CHECK_SIZEOF('bool char int "long long" long short size_t ssize_t')
     conf.CHECK_SIZEOF('int8_t uint8_t int16_t uint16_t int32_t uint32_t int64_t uint64_t')
@@ -156,19 +216,60 @@ def configure(conf):
                     lib='nsl socket',
                     headers='sys/socket.h netdb.h netinet/in.h')
 
+    if conf.CONFIG_SET('HAVE_SYS_UCONTEXT_H') and conf.CONFIG_SET('HAVE_SIGNAL_H'):
+        conf.CHECK_CODE('''
+                       ucontext_t uc;
+                       sigaddset(&uc.uc_sigmask, SIGUSR1);
+                       ''',
+                       'HAVE_UCONTEXT_T',
+                       msg="Checking whether we have ucontext_t",
+                       headers='signal.h sys/ucontext.h')
+
     # these may be builtins, so we need the link=False strategy
     conf.CHECK_FUNCS('strdup memmem printf memset memcpy memmove strcpy strncpy bzero', link=False)
 
+    # See https://bugzilla.samba.org/show_bug.cgi?id=1097
+    #
+    # Ported in from autoconf where it was added with this commit:
+    # commit 804cfb20a067b4b687089dc72a8271b3abf20f31
+    # Author: Simo Sorce <idra at samba.org>
+    # Date:   Wed Aug 25 14:24:16 2004 +0000
+    #     r2070: Let's try to overload srnlen and strndup for AIX where they are natly broken.
+
+    host_os = sys.platform
+    if host_os.rfind('aix') > -1:
+        conf.DEFINE('BROKEN_STRNLEN', 1)
+        conf.DEFINE('BROKEN_STRNDUP', 1)
+
     conf.CHECK_FUNCS('shl_load shl_unload shl_findsym')
     conf.CHECK_FUNCS('pipe strftime srandom random srand rand usleep setbuffer')
-    conf.CHECK_FUNCS('lstat getpgrp utime utimes seteuid setreuid setresuid setegid')
+    conf.CHECK_FUNCS('lstat getpgrp utime utimes setuid seteuid setreuid setresuid setgid setegid')
     conf.CHECK_FUNCS('setregid setresgid chroot strerror vsyslog setlinebuf mktime')
-    conf.CHECK_FUNCS('ftruncate chsize rename waitpid wait4 strlcpy strlcat')
+    conf.CHECK_FUNCS('ftruncate chsize rename waitpid wait4')
     conf.CHECK_FUNCS('initgroups pread pwrite strndup strcasestr')
     conf.CHECK_FUNCS('strtok_r mkdtemp dup2 dprintf vdprintf isatty chown lchown')
     conf.CHECK_FUNCS('link readlink symlink realpath snprintf vsnprintf')
     conf.CHECK_FUNCS('asprintf vasprintf setenv unsetenv strnlen strtoull __strtoull')
-    conf.CHECK_FUNCS('strtouq strtoll __strtoll strtoq')
+    conf.CHECK_FUNCS('strtouq strtoll __strtoll strtoq memalign posix_memalign')
+    conf.CHECK_FUNCS('prctl')
+
+    # libbsd on some platforms provides strlcpy and strlcat
+    if not conf.CHECK_FUNCS('strlcpy strlcat'):
+        conf.CHECK_FUNCS_IN('strlcpy strlcat', 'bsd', headers='bsd/string.h',
+                checklibc=True)
+    if not conf.CHECK_FUNCS('getpeereid'):
+        conf.CHECK_FUNCS_IN('getpeereid', 'bsd', headers='sys/types.h bsd/unistd.h')
+    if not conf.CHECK_FUNCS_IN('setproctitle', 'bsd', headers='sys/types.h bsd/unistd.h'):
+        conf.CHECK_FUNCS_IN('setproctitle', 'setproctitle', headers='setproctitle.h')
+
+    conf.CHECK_CODE('''
+                struct ucred cred;
+                socklen_t cred_len;
+                int ret = getsockopt(0, SOL_SOCKET, SO_PEERCRED, &cred, &cred_len);''',
+                'HAVE_PEERCRED',
+                msg="Checking whether we can use SO_PEERCRED to get socket credentials",
+                headers='sys/types.h sys/socket.h')
+
     #Some OS (ie. freebsd) return EINVAL if the convertion could not be done, it's not what we expect
     #Let's detect those cases
     if conf.CONFIG_SET('HAVE_STRTOLL'):
@@ -183,16 +284,49 @@ def configure(conf):
                         msg="Checking correct behavior of strtoll",
                         headers = 'errno.h',
                         execute = True,
-                        define_ret = True,
                         define = 'HAVE_BSD_STRTOLL',
                         )
     conf.CHECK_FUNCS('if_nametoindex strerror_r')
     conf.CHECK_FUNCS('getdirentries getdents syslog')
     conf.CHECK_FUNCS('gai_strerror get_current_dir_name')
-    conf.CHECK_FUNCS('timegm getifaddrs freeifaddrs mmap setgroups setsid')
+    conf.CHECK_FUNCS('timegm getifaddrs freeifaddrs mmap setgroups syscall setsid')
     conf.CHECK_FUNCS('getgrent_r getgrgid_r getgrnam_r getgrouplist getpagesize')
     conf.CHECK_FUNCS('getpwent_r getpwnam_r getpwuid_r epoll_create')
 
+    conf.SET_TARGET_TYPE('attr', 'EMPTY')
+
+    xattr_headers='sys/attributes.h attr/xattr.h sys/xattr.h'
+
+    conf.CHECK_FUNCS_IN('''
+fgetxattr flistea flistxattr
+fremovexattr fsetxattr getxattr
+listxattr removexattr setxattr
+''', 'attr', checklibc=True, headers=xattr_headers)
+
+    # We need to check for linux xattrs first, as we do not wish to link to -lattr
+    # (the XFS compat API) on Linux systems with the native xattr API
+    if not conf.CONFIG_SET('HAVE_GETXATTR'):
+        conf.CHECK_FUNCS_IN('''
+attr_get attr_getf attr_list attr_listf attropen attr_remove
+attr_removef attr_set attr_setf extattr_delete_fd extattr_delete_file
+extattr_get_fd extattr_get_file extattr_list_fd extattr_list_file
+extattr_set_fd extattr_set_file fgetea
+fremoveea fsetea getea listea
+removeea setea
+''', 'attr', checklibc=True, headers=xattr_headers)
+
+    if (conf.CONFIG_SET('HAVE_ATTR_LISTF') or
+        conf.CONFIG_SET('HAVE_EXTATTR_LIST_FD') or
+        conf.CONFIG_SET('HAVE_FLISTEA') or
+        conf.CONFIG_SET('HAVE_FLISTXATTR')):
+            conf.DEFINE('HAVE_XATTR_SUPPORT', 1)
+
+    # Darwin has extra options to xattr-family functions
+    conf.CHECK_CODE('getxattr(NULL, NULL, NULL, 0, 0, 0)',
+                    headers=xattr_headers, local_include=False,
+                    define='XATTR_ADDITIONAL_OPTIONS',
+                    msg="Checking whether xattr interface takes additional options")
+
     conf.CHECK_FUNCS_IN('dlopen dlsym dlerror dlclose', 'dl',
                         checklibc=True, headers='dlfcn.h dl.h')
 
@@ -206,19 +340,19 @@ def configure(conf):
     if conf.CHECK_FUNCS_IN('clock_gettime', 'rt', checklibc=True):
         for c in ['CLOCK_MONOTONIC', 'CLOCK_PROCESS_CPUTIME_ID', 'CLOCK_REALTIME']:
             conf.CHECK_CODE('''
-			    #if TIME_WITH_SYS_TIME
-			    # include <sys/time.h>
-			    # include <time.h>
-			    #else
-			    # if HAVE_SYS_TIME_H
-			    #  include <sys/time.h>
-			    # else
-			    #  include <time.h>
-			    # endif
-			    #endif
-			    clockid_t clk = %s''' % c,
-			    'HAVE_%s' % c,
-			    msg='Checking whether the clock_gettime clock ID %s is available' % c)
+                #if TIME_WITH_SYS_TIME
+                # include <sys/time.h>
+                # include <time.h>
+                #else
+                # if HAVE_SYS_TIME_H
+                #  include <sys/time.h>
+                # else
+                #  include <time.h>
+                # endif
+                #endif
+                clockid_t clk = %s''' % c,
+                'HAVE_%s' % c,
+                msg='Checking whether the clock_gettime clock ID %s is available' % c)
 
     conf.CHECK_TYPE('struct timespec', headers='sys/time.h time.h')
 
@@ -259,40 +393,40 @@ def configure(conf):
     conf.CHECK_HEADERS('poll.h')
     conf.CHECK_FUNCS('poll')
 
-    if not conf.CHECK_CODE('''#define LIBREPLACE_CONFIGURE_TEST_STRPTIME
-                           #include "test/strptime.c"''',
-                           define='HAVE_STRPTIME',
-                           addmain=False,
-                           msg='Checking for working strptime'):
-        conf.DEFINE('REPLACE_STRPTIME', 1)
-    else:
-       conf.CHECK_CODE('''
-                        const char *s = "20070414101546Z";
-                        char *ret;
-                        struct tm t;
-                        memset(&t, 0, sizeof(t));
-                        ret = strptime(s, "%Y%m%d%H%M%S", &t);
-                        if (ret == NULL || t.tm_wday != 6) {
-                            return 0;
-                        } else {
-                            return 1;
-                        }
-                        ''',
-                        msg="Checking correct behavior of strptime",
-                        headers = 'time.h',
-                        execute = True,
-                        define_ret = True,
-                        define = 'REPLACE_STRPTIME',
-                        )
+    conf.CHECK_FUNCS('strptime')
+    conf.CHECK_DECLS('strptime', headers='time.h')
+    conf.CHECK_CODE('''#define LIBREPLACE_CONFIGURE_TEST_STRPTIME
+                       #include "test/strptime.c"''',
+                       define='HAVE_WORKING_STRPTIME',
+                       execute=True,
+                       addmain=False,
+                       msg='Checking for working strptime')
 
     conf.CHECK_CODE('gettimeofday(NULL, NULL)', 'HAVE_GETTIMEOFDAY_TZ', execute=False)
 
     conf.CHECK_CODE('#include "test/snprintf.c"',
                     define="HAVE_C99_VSNPRINTF",
-                    execute=1,
+                    execute=True,
                     addmain=False,
                     msg="Checking for C99 vsnprintf")
 
+    conf.CHECK_CODE('#include "test/shared_mmap.c"',
+                    addmain=False, add_headers=False, execute=True,
+                    define='HAVE_SHARED_MMAP',
+                    msg="Checking for HAVE_SHARED_MMAP")
+
+    conf.CHECK_CODE('#include "test/shared_mremap.c"',
+                    addmain=False, add_headers=False, execute=True,
+                    define='HAVE_MREMAP',
+                    msg="Checking for HAVE_MREMAP")
+
+    # OpenBSD (and I've heard HPUX) doesn't sync between mmap and write.
+    # FIXME: Anything other than a 0 or 1 exit code should abort configure!
+    conf.CHECK_CODE('#include "test/incoherent_mmap.c"',
+                    addmain=False, add_headers=False, execute=True,
+                    define='HAVE_INCOHERENT_MMAP',
+                    msg="Checking for HAVE_INCOHERENT_MMAP")
+
     conf.SAMBA_BUILD_ENV()
 
     conf.CHECK_CODE('''
@@ -342,11 +476,26 @@ def configure(conf):
     conf.CHECK_CODE('''
                     struct stat st;
                     char tpl[20]="/tmp/test.XXXXXX";
+                    char tpl2[20]="/tmp/test.XXXXXX";
                     int fd = mkstemp(tpl);
-                    if (fd == -1) exit(1);
+                    int fd2 = mkstemp(tpl2);
+                    if (fd == -1) {
+                          if (fd2 != -1) {
+                                  unlink(tpl2);
+                          }
+                          exit(1);
+                    }
+                    if (fd2 == -1) exit(1);
                     unlink(tpl);
+                    unlink(tpl2);
                     if (fstat(fd, &st) != 0) exit(1);
                     if ((st.st_mode & 0777) != 0600) exit(1);
+                    if (strcmp(tpl, "/tmp/test.XXXXXX") == 0) {
+                          exit(1);
+                    }
+                    if (strcmp(tpl, tpl2) == 0) {
+                          exit(1);
+                    }
                     exit(0);
                     ''',
                     define='HAVE_SECURE_MKSTEMP',
@@ -380,40 +529,55 @@ def configure(conf):
                            execute=True):
             break
 
-    if conf.CHECK_FUNCS('getpass getpassphrase'):
-        # if we have both, then we prefer getpassphrase
-        conf.DEFINE('REPLACE_GETPASS_BY_GETPASSPHRASE', 1)
-        conf.DEFINE('REPLACE_GETPASS', 1)
-    else:
-        conf.CHECK_CODE('''#include "getpass.c"
-                       int main(void) { return 0; }''',
-                    addmain=False,
-                    define='REPLACE_GETPASS',
-                    cflags='-DNO_CONFIG_H')
-
     conf.RECURSE('system')
     conf.SAMBA_CONFIG_H()
 
 
+REPLACEMENT_FUNCTIONS = {
+    'replace.c': ['ftruncate', 'strlcpy', 'strlcat', 'mktime', 'initgroups',
+                  'memmove', 'strdup', 'setlinebuf', 'vsyslog', 'strnlen',
+                  'strndup', 'waitpid', 'seteuid', 'setegid', 'chroot',
+                  'mkstemp', 'mkdtemp', 'pread', 'pwrite', 'strcasestr',
+                  'strtok_r', 'strtoll', 'strtoull', 'setenv', 'unsetenv',
+                  'utime', 'utimes', 'dup2', 'chown', 'link', 'readlink',
+                  'symlink', 'lchown', 'realpath', 'memmem', 'vdprintf',
+                  'dprintf', 'get_current_dir_name',
+                  'strerror_r', 'clock_gettime'],
+    'timegm.c': ['timegm'],
+    # Note: C99_VSNPRINTF is not a function, but a special condition
+    # for replacement
+    'snprintf.c': ['C99_VSNPRINTF', 'snprintf', 'vsnprintf', 'asprintf', 'vasprintf'],
+    # Note: WORKING_STRPTIME is not a function, but a special condition
+    # for replacement
+    'strptime.c': ['WORKING_STRPTIME', 'strptime'],
+    }
+
+
 def build(bld):
     bld.RECURSE('buildtools/wafsamba')
 
-    REPLACE_HOSTCC_SOURCE = 'replace.c snprintf.c'
+    REPLACE_HOSTCC_SOURCE = ''
+
+    for filename, functions in REPLACEMENT_FUNCTIONS.iteritems():
+        for function in functions:
+            if not bld.CONFIG_SET('HAVE_%s' % function.upper()):
+                REPLACE_HOSTCC_SOURCE += ' %s' % filename
+                break
 
-    if bld.CONFIG_SET('REPLACE_STRPTIME'):       REPLACE_HOSTCC_SOURCE += ' strptime.c'
-    if not bld.CONFIG_SET('HAVE_TIMEGM'):        REPLACE_HOSTCC_SOURCE += ' timegm.c'
+    extra_libs = ''
+    if bld.CONFIG_SET('HAVE_LIBBSD'): extra_libs += ' bsd'
 
     bld.SAMBA_SUBSYSTEM('LIBREPLACE_HOSTCC',
         REPLACE_HOSTCC_SOURCE,
         use_hostcc=True,
         use_global_deps=False,
         cflags='-DSOCKET_WRAPPER_DISABLE=1 -DNSS_WRAPPER_DISABLE=1 -DUID_WRAPPER_DISABLE=1 -D_SAMBA_HOSTCC_',
-        group='compiler_libraries'
+        group='compiler_libraries',
+        deps = extra_libs
     )
 
     REPLACE_SOURCE = REPLACE_HOSTCC_SOURCE
 
-    if bld.CONFIG_SET('REPLACE_GETPASS'):        REPLACE_SOURCE += ' getpass.c'
     if not bld.CONFIG_SET('HAVE_CRYPT'):         REPLACE_SOURCE += ' crypt.c'
     if not bld.CONFIG_SET('HAVE_DLOPEN'):        REPLACE_SOURCE += ' dlfcn.c'
     if not bld.CONFIG_SET('HAVE_POLL'):          REPLACE_SOURCE += ' poll.c'
@@ -426,6 +590,8 @@ def build(bld):
     if not bld.CONFIG_SET('HAVE_INET_ATON'):     REPLACE_SOURCE += ' inet_aton.c'
     if not bld.CONFIG_SET('HAVE_INET_NTOP'):     REPLACE_SOURCE += ' inet_ntop.c'
     if not bld.CONFIG_SET('HAVE_INET_PTON'):     REPLACE_SOURCE += ' inet_pton.c'
+    if not bld.CONFIG_SET('HAVE_GETXATTR') or bld.CONFIG_SET('XATTR_ADDITIONAL_OPTIONS'):
+                                                 REPLACE_SOURCE += ' xattr.c'
 
     bld.SAMBA_LIBRARY('replace',
                       source=REPLACE_SOURCE,
@@ -436,7 +602,7 @@ def build(bld):
                       # at the moment:
                       # hide_symbols=bld.BUILTIN_LIBRARY('replace'),
                       private_library=True,
-                      deps='crypt dl nsl socket rt')
+                      deps='crypt dl nsl socket rt attr' + extra_libs)
 
     bld.SAMBA_SUBSYSTEM('replace-test',
                       source='''test/testsuite.c test/strptime.c
diff --git a/lib/replace/xattr.c b/lib/replace/xattr.c
new file mode 100644
index 0000000..a26ff67
--- /dev/null
+++ b/lib/replace/xattr.c
@@ -0,0 +1,729 @@
+/* 
+   Unix SMB/CIFS implementation.
+   replacement routines for xattr implementations
+   Copyright (C) Jeremy Allison  1998-2005
+   Copyright (C) Timur Bakeyev        2005
+   Copyright (C) Bjoern Jacke    2006-2007
+   Copyright (C) Herb Lewis           2003
+   Copyright (C) Andrew Bartlett      2012
+
+     ** NOTE! The following LGPL license applies to the replace
+     ** library. This does NOT imply that all of Samba is released
+     ** under the LGPL
+   
+   This library is free software; you can redistribute it and/or
+   modify it under the terms of the GNU Lesser General Public
+   License as published by the Free Software Foundation; either
+   version 3 of the License, or (at your option) any later version.
+
+   This library 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
+   Lesser General Public License for more details.
+
+   You should have received a copy of the GNU Lesser General Public
+   License along with this library; if not, see <http://www.gnu.org/licenses/>.
+*/
+
+#include "replace.h"
+#include "system/filesys.h"
+#include "system/dir.h"
+
+/******** Solaris EA helper function prototypes ********/
+#ifdef HAVE_ATTROPEN
+#define SOLARIS_ATTRMODE S_IRUSR|S_IWUSR|S_IRGRP|S_IWGRP
+static int solaris_write_xattr(int attrfd, const char *value, size_t size);
+static ssize_t solaris_read_xattr(int attrfd, void *value, size_t size);
+static ssize_t solaris_list_xattr(int attrdirfd, char *list, size_t size);
+static int solaris_unlinkat(int attrdirfd, const char *name);
+static int solaris_attropen(const char *path, const char *attrpath, int oflag, mode_t mode);
+static int solaris_openat(int fildes, const char *path, int oflag, mode_t mode);
+#endif
+
+/**************************************************************************
+ Wrappers for extented attribute calls. Based on the Linux package with
+ support for IRIX and (Net|Free)BSD also. Expand as other systems have them.
+****************************************************************************/
+
+ssize_t rep_getxattr (const char *path, const char *name, void *value, size_t size)
+{
+#if defined(HAVE_GETXATTR)
+#ifndef XATTR_ADDITIONAL_OPTIONS
+	return getxattr(path, name, value, size);
+#else
+
+/* So that we do not recursivly call this function */
+#undef getxattr
+	int options = 0;
+	return getxattr(path, name, value, size, 0, options);
+#endif
+#elif defined(HAVE_GETEA)
+	return getea(path, name, value, size);
+#elif defined(HAVE_EXTATTR_GET_FILE)
+	char *s;
+	ssize_t retval;
+	int attrnamespace = (strncmp(name, "system", 6) == 0) ? 
+		EXTATTR_NAMESPACE_SYSTEM : EXTATTR_NAMESPACE_USER;
+	const char *attrname = ((s=strchr(name, '.')) == NULL) ? name : s + 1;
+	/*
+	 * The BSD implementation has a nasty habit of silently truncating
+	 * the returned value to the size of the buffer, so we have to check
+	 * that the buffer is large enough to fit the returned value.
+	 */
+	if((retval=extattr_get_file(path, attrnamespace, attrname, NULL, 0)) >= 0) {
+		if (size == 0) {
+			return retval;
+		} else if (retval > size) {
+			errno = ERANGE;
+			return -1;
+		}
+		if((retval=extattr_get_file(path, attrnamespace, attrname, value, size)) >= 0)
+			return retval;
+	}
+
+	return -1;
+#elif defined(HAVE_ATTR_GET)
+	int retval, flags = 0;
+	int valuelength = (int)size;
+	char *attrname = strchr(name,'.') + 1;
+
+	if (strncmp(name, "system", 6) == 0) flags |= ATTR_ROOT;
+
+	retval = attr_get(path, attrname, (char *)value, &valuelength, flags);
+	if (size == 0 && retval == -1 && errno == E2BIG) {
+		return valuelength;
+	}
+
+	return retval ? retval : valuelength;
+#elif defined(HAVE_ATTROPEN)
+	ssize_t ret = -1;
+	int attrfd = solaris_attropen(path, name, O_RDONLY, 0);
+	if (attrfd >= 0) {
+		ret = solaris_read_xattr(attrfd, value, size);
+		close(attrfd);
+	}
+	return ret;
+#else
+	errno = ENOSYS;
+	return -1;
+#endif
+}
+
+ssize_t rep_fgetxattr (int filedes, const char *name, void *value, size_t size)
+{
+#if defined(HAVE_FGETXATTR)
+#ifndef XATTR_ADDITIONAL_OPTIONS
+	return fgetxattr(filedes, name, value, size);
+#else
+
+/* So that we do not recursivly call this function */
+#undef fgetxattr
+	int options = 0;
+	return fgetxattr(filedes, name, value, size, 0, options);
+#endif
+#elif defined(HAVE_FGETEA)
+	return fgetea(filedes, name, value, size);
+#elif defined(HAVE_EXTATTR_GET_FD)
+	char *s;
+	ssize_t retval;
+	int attrnamespace = (strncmp(name, "system", 6) == 0) ? 
+		EXTATTR_NAMESPACE_SYSTEM : EXTATTR_NAMESPACE_USER;
+	const char *attrname = ((s=strchr(name, '.')) == NULL) ? name : s + 1;
+
+	if((retval=extattr_get_fd(filedes, attrnamespace, attrname, NULL, 0)) >= 0) {
+		if (size == 0) {
+			return retval;
+		} else if (retval > size) {
+			errno = ERANGE;
+			return -1;
+		}
+		if((retval=extattr_get_fd(filedes, attrnamespace, attrname, value, size)) >= 0)
+			return retval;
+	}
+
+	return -1;
+#elif defined(HAVE_ATTR_GETF)
+	int retval, flags = 0;
+	int valuelength = (int)size;
+	char *attrname = strchr(name,'.') + 1;
+
+	if (strncmp(name, "system", 6) == 0) flags |= ATTR_ROOT;
+
+	retval = attr_getf(filedes, attrname, (char *)value, &valuelength, flags);
+	if (size == 0 && retval == -1 && errno == E2BIG) {
+		return valuelength;
+	}
+	return retval ? retval : valuelength;
+#elif defined(HAVE_ATTROPEN)
+	ssize_t ret = -1;
+	int attrfd = solaris_openat(filedes, name, O_RDONLY|O_XATTR, 0);
+	if (attrfd >= 0) {
+		ret = solaris_read_xattr(attrfd, value, size);
+		close(attrfd);
+	}
+	return ret;
+#else
+	errno = ENOSYS;
+	return -1;
+#endif
+}
+
+#if defined(HAVE_EXTATTR_LIST_FILE)
+
+#define EXTATTR_PREFIX(s)	(s), (sizeof((s))-1)
+
+static struct {
+        int space;
+	const char *name;
+	size_t len;
+} 
+extattr[] = {
+	{ EXTATTR_NAMESPACE_SYSTEM, EXTATTR_PREFIX("system.") },
+        { EXTATTR_NAMESPACE_USER, EXTATTR_PREFIX("user.") },
+};
+
+typedef union {
+	const char *path;
+	int filedes;
+} extattr_arg;
+
+static ssize_t bsd_attr_list (int type, extattr_arg arg, char *list, size_t size)
+{
+	ssize_t list_size, total_size = 0;
+	int i, t, len;
+	char *buf;
+	/* Iterate through extattr(2) namespaces */
+	for(t = 0; t < ARRAY_SIZE(extattr); t++) {
+		switch(type) {
+#if defined(HAVE_EXTATTR_LIST_FILE)
+			case 0:
+				list_size = extattr_list_file(arg.path, extattr[t].space, list, size);
+				break;
+#endif
+#if defined(HAVE_EXTATTR_LIST_LINK)
+			case 1:
+				list_size = extattr_list_link(arg.path, extattr[t].space, list, size);
+				break;
+#endif
+#if defined(HAVE_EXTATTR_LIST_FD)
+			case 2:
+				list_size = extattr_list_fd(arg.filedes, extattr[t].space, list, size);
+				break;
+#endif
+			default:
+				errno = ENOSYS;
+				return -1;
+		}
+		/* Some error happend. Errno should be set by the previous call */
+		if(list_size < 0)
+			return -1;
+		/* No attributes */
+		if(list_size == 0)
+			continue;
+		/* XXX: Call with an empty buffer may be used to calculate
+		   necessary buffer size. Unfortunately, we can't say, how
+		   many attributes were returned, so here is the potential
+		   problem with the emulation.
+		*/
+		if(list == NULL) {
+			/* Take the worse case of one char attribute names - 
+			   two bytes per name plus one more for sanity.
+			*/
+			total_size += list_size + (list_size/2 + 1)*extattr[t].len;
+			continue;
+		}
+		/* Count necessary offset to fit namespace prefixes */
+		len = 0;
+		for(i = 0; i < list_size; i += list[i] + 1)
+			len += extattr[t].len;
+
+		total_size += list_size + len;
+		/* Buffer is too small to fit the results */
+		if(total_size > size) {
+			errno = ERANGE;
+			return -1;
+		}
+		/* Shift results back, so we can prepend prefixes */
+		buf = (char *)memmove(list + len, list, list_size);
+
+		for(i = 0; i < list_size; i += len + 1) {
+			len = buf[i];
+			strncpy(list, extattr[t].name, extattr[t].len + 1);
+			list += extattr[t].len;
+			strncpy(list, buf + i + 1, len);
+			list[len] = '\0';
+			list += len + 1;
+		}
+		size -= total_size;
+	}
+	return total_size;
+}
+
+#endif
+
+#if defined(HAVE_ATTR_LIST) && (defined(HAVE_SYS_ATTRIBUTES_H) || defined(HAVE_ATTR_ATTRIBUTES_H))
+static char attr_buffer[ATTR_MAX_VALUELEN];
+
+static ssize_t irix_attr_list(const char *path, int filedes, char *list, size_t size, int flags)
+{
+	int retval = 0, index;
+	attrlist_cursor_t *cursor = 0;
+	int total_size = 0;
+	attrlist_t * al = (attrlist_t *)attr_buffer;
+	attrlist_ent_t *ae;
+	size_t ent_size, left = size;
+	char *bp = list;
+
+	while (true) {
+	    if (filedes)
+		retval = attr_listf(filedes, attr_buffer, ATTR_MAX_VALUELEN, flags, cursor);
+	    else
+		retval = attr_list(path, attr_buffer, ATTR_MAX_VALUELEN, flags, cursor);
+	    if (retval) break;
+	    for (index = 0; index < al->al_count; index++) {
+		ae = ATTR_ENTRY(attr_buffer, index);
+		ent_size = strlen(ae->a_name) + sizeof("user.");
+		if (left >= ent_size) {
+		    strncpy(bp, "user.", sizeof("user."));
+		    strncat(bp, ae->a_name, ent_size - sizeof("user."));
+		    bp += ent_size;
+		    left -= ent_size;
+		} else if (size) {
+		    errno = ERANGE;
+		    retval = -1;
+		    break;
+		}
+		total_size += ent_size;
+	    }
+	    if (al->al_more == 0) break;
+	}
+	if (retval == 0) {
+	    flags |= ATTR_ROOT;
+	    cursor = 0;
+	    while (true) {
+		if (filedes)
+		    retval = attr_listf(filedes, attr_buffer, ATTR_MAX_VALUELEN, flags, cursor);
+		else
+		    retval = attr_list(path, attr_buffer, ATTR_MAX_VALUELEN, flags, cursor);
+		if (retval) break;
+		for (index = 0; index < al->al_count; index++) {
+		    ae = ATTR_ENTRY(attr_buffer, index);
+		    ent_size = strlen(ae->a_name) + sizeof("system.");
+		    if (left >= ent_size) {
+			strncpy(bp, "system.", sizeof("system."));
+			strncat(bp, ae->a_name, ent_size - sizeof("system."));
+			bp += ent_size;
+			left -= ent_size;
+		    } else if (size) {
+			errno = ERANGE;
+			retval = -1;
+			break;
+		    }
+		    total_size += ent_size;
+		}
+		if (al->al_more == 0) break;
+	    }
+	}
+	return (ssize_t)(retval ? retval : total_size);
+}
+
+#endif
+
+ssize_t rep_listxattr (const char *path, char *list, size_t size)
+{
+#if defined(HAVE_LISTXATTR)
+#ifndef XATTR_ADDITIONAL_OPTIONS
+	return listxattr(path, list, size);
+#else
+/* So that we do not recursivly call this function */
+#undef listxattr
+	int options = 0;
+	return listxattr(path, list, size, options);
+#endif
+#elif defined(HAVE_LISTEA)
+	return listea(path, list, size);
+#elif defined(HAVE_EXTATTR_LIST_FILE)
+	extattr_arg arg;
+	arg.path = path;
+	return bsd_attr_list(0, arg, list, size);
+#elif defined(HAVE_ATTR_LIST) && defined(HAVE_SYS_ATTRIBUTES_H)
+	return irix_attr_list(path, 0, list, size, 0);
+#elif defined(HAVE_ATTROPEN)
+	ssize_t ret = -1;
+	int attrdirfd = solaris_attropen(path, ".", O_RDONLY, 0);
+	if (attrdirfd >= 0) {
+		ret = solaris_list_xattr(attrdirfd, list, size);
+		close(attrdirfd);
+	}
+	return ret;
+#else
+	errno = ENOSYS;
+	return -1;
+#endif
+}
+
+ssize_t rep_flistxattr (int filedes, char *list, size_t size)
+{
+#if defined(HAVE_FLISTXATTR)
+#ifndef XATTR_ADDITIONAL_OPTIONS
+	return flistxattr(filedes, list, size);
+#else
+/* So that we do not recursivly call this function */
+#undef flistxattr
+	int options = 0;
+	return flistxattr(filedes, list, size, options);
+#endif
+#elif defined(HAVE_FLISTEA)
+	return flistea(filedes, list, size);
+#elif defined(HAVE_EXTATTR_LIST_FD)
+	extattr_arg arg;
+	arg.filedes = filedes;
+	return bsd_attr_list(2, arg, list, size);
+#elif defined(HAVE_ATTR_LISTF)
+	return irix_attr_list(NULL, filedes, list, size, 0);
+#elif defined(HAVE_ATTROPEN)
+	ssize_t ret = -1;
+	int attrdirfd = solaris_openat(filedes, ".", O_RDONLY|O_XATTR, 0);
+	if (attrdirfd >= 0) {
+		ret = solaris_list_xattr(attrdirfd, list, size);
+		close(attrdirfd);
+	}
+	return ret;
+#else
+	errno = ENOSYS;
+	return -1;
+#endif
+}
+
+int rep_removexattr (const char *path, const char *name)
+{
+#if defined(HAVE_REMOVEXATTR)
+#ifndef XATTR_ADDITIONAL_OPTIONS
+	return removexattr(path, name);
+#else
+/* So that we do not recursivly call this function */
+#undef removexattr
+	int options = 0;
+	return removexattr(path, name, options);
+#endif
+#elif defined(HAVE_REMOVEEA)
+	return removeea(path, name);
+#elif defined(HAVE_EXTATTR_DELETE_FILE)
+	char *s;
+	int attrnamespace = (strncmp(name, "system", 6) == 0) ? 
+		EXTATTR_NAMESPACE_SYSTEM : EXTATTR_NAMESPACE_USER;
+	const char *attrname = ((s=strchr(name, '.')) == NULL) ? name : s + 1;
+
+	return extattr_delete_file(path, attrnamespace, attrname);
+#elif defined(HAVE_ATTR_REMOVE)
+	int flags = 0;
+	char *attrname = strchr(name,'.') + 1;
+
+	if (strncmp(name, "system", 6) == 0) flags |= ATTR_ROOT;
+
+	return attr_remove(path, attrname, flags);
+#elif defined(HAVE_ATTROPEN)
+	int ret = -1;
+	int attrdirfd = solaris_attropen(path, ".", O_RDONLY, 0);
+	if (attrdirfd >= 0) {
+		ret = solaris_unlinkat(attrdirfd, name);
+		close(attrdirfd);
+	}
+	return ret;
+#else
+	errno = ENOSYS;
+	return -1;
+#endif
+}
+
+int rep_fremovexattr (int filedes, const char *name)
+{
+#if defined(HAVE_FREMOVEXATTR)
+#ifndef XATTR_ADDITIONAL_OPTIONS
+	return fremovexattr(filedes, name);
+#else
+/* So that we do not recursivly call this function */
+#undef fremovexattr
+	int options = 0;
+	return fremovexattr(filedes, name, options);
+#endif
+#elif defined(HAVE_FREMOVEEA)
+	return fremoveea(filedes, name);
+#elif defined(HAVE_EXTATTR_DELETE_FD)
+	char *s;
+	int attrnamespace = (strncmp(name, "system", 6) == 0) ? 
+		EXTATTR_NAMESPACE_SYSTEM : EXTATTR_NAMESPACE_USER;
+	const char *attrname = ((s=strchr(name, '.')) == NULL) ? name : s + 1;
+
+	return extattr_delete_fd(filedes, attrnamespace, attrname);
+#elif defined(HAVE_ATTR_REMOVEF)
+	int flags = 0;
+	char *attrname = strchr(name,'.') + 1;
+
+	if (strncmp(name, "system", 6) == 0) flags |= ATTR_ROOT;
+
+	return attr_removef(filedes, attrname, flags);
+#elif defined(HAVE_ATTROPEN)
+	int ret = -1;
+	int attrdirfd = solaris_openat(filedes, ".", O_RDONLY|O_XATTR, 0);
+	if (attrdirfd >= 0) {
+		ret = solaris_unlinkat(attrdirfd, name);
+		close(attrdirfd);
+	}
+	return ret;
+#else
+	errno = ENOSYS;
+	return -1;
+#endif
+}
+
+int rep_setxattr (const char *path, const char *name, const void *value, size_t size, int flags)
+{
+#if defined(HAVE_SETXATTR)
+#ifndef XATTR_ADDITIONAL_OPTIONS
+	return setxattr(path, name, value, size, flags);
+#else
+/* So that we do not recursivly call this function */
+#undef setxattr
+	int options = 0;
+	return setxattr(path, name, value, size, 0, options);
+#endif
+#elif defined(HAVE_SETEA)
+	return setea(path, name, value, size, flags);
+#elif defined(HAVE_EXTATTR_SET_FILE)
+	char *s;
+	int retval = 0;
+	int attrnamespace = (strncmp(name, "system", 6) == 0) ? 
+		EXTATTR_NAMESPACE_SYSTEM : EXTATTR_NAMESPACE_USER;
+	const char *attrname = ((s=strchr(name, '.')) == NULL) ? name : s + 1;
+	if (flags) {
+		/* Check attribute existence */
+		retval = extattr_get_file(path, attrnamespace, attrname, NULL, 0);
+		if (retval < 0) {
+			/* REPLACE attribute, that doesn't exist */
+			if (flags & XATTR_REPLACE && errno == ENOATTR) {
+				errno = ENOATTR;
+				return -1;
+			}
+			/* Ignore other errors */
+		}
+		else {
+			/* CREATE attribute, that already exists */
+			if (flags & XATTR_CREATE) {
+				errno = EEXIST;
+				return -1;
+			}
+		}
+	}
+	retval = extattr_set_file(path, attrnamespace, attrname, value, size);
+	return (retval < 0) ? -1 : 0;
+#elif defined(HAVE_ATTR_SET)
+	int myflags = 0;
+	char *attrname = strchr(name,'.') + 1;
+
+	if (strncmp(name, "system", 6) == 0) myflags |= ATTR_ROOT;
+	if (flags & XATTR_CREATE) myflags |= ATTR_CREATE;
+	if (flags & XATTR_REPLACE) myflags |= ATTR_REPLACE;
+
+	return attr_set(path, attrname, (const char *)value, size, myflags);
+#elif defined(HAVE_ATTROPEN)
+	int ret = -1;
+	int myflags = O_RDWR;
+	int attrfd;
+	if (flags & XATTR_CREATE) myflags |= O_EXCL;
+	if (!(flags & XATTR_REPLACE)) myflags |= O_CREAT;
+	attrfd = solaris_attropen(path, name, myflags, (mode_t) SOLARIS_ATTRMODE);
+	if (attrfd >= 0) {
+		ret = solaris_write_xattr(attrfd, value, size);
+		close(attrfd);
+	}
+	return ret;
+#else
+	errno = ENOSYS;
+	return -1;
+#endif
+}
+
+int rep_fsetxattr (int filedes, const char *name, const void *value, size_t size, int flags)
+{
+#if defined(HAVE_FSETXATTR)
+#ifndef XATTR_ADDITIONAL_OPTIONS
+	return fsetxattr(filedes, name, value, size, flags);
+#else
+/* So that we do not recursivly call this function */
+#undef fsetxattr
+	int options = 0;
+	return fsetxattr(filedes, name, value, size, 0, options);
+#endif
+#elif defined(HAVE_FSETEA)
+	return fsetea(filedes, name, value, size, flags);
+#elif defined(HAVE_EXTATTR_SET_FD)
+	char *s;
+	int retval = 0;
+	int attrnamespace = (strncmp(name, "system", 6) == 0) ? 
+		EXTATTR_NAMESPACE_SYSTEM : EXTATTR_NAMESPACE_USER;
+	const char *attrname = ((s=strchr(name, '.')) == NULL) ? name : s + 1;
+	if (flags) {
+		/* Check attribute existence */
+		retval = extattr_get_fd(filedes, attrnamespace, attrname, NULL, 0);
+		if (retval < 0) {
+			/* REPLACE attribute, that doesn't exist */
+			if (flags & XATTR_REPLACE && errno == ENOATTR) {
+				errno = ENOATTR;
+				return -1;
+			}
+			/* Ignore other errors */
+		}
+		else {
+			/* CREATE attribute, that already exists */
+			if (flags & XATTR_CREATE) {
+				errno = EEXIST;
+				return -1;
+			}
+		}
+	}
+	retval = extattr_set_fd(filedes, attrnamespace, attrname, value, size);
+	return (retval < 0) ? -1 : 0;
+#elif defined(HAVE_ATTR_SETF)
+	int myflags = 0;
+	char *attrname = strchr(name,'.') + 1;
+
+	if (strncmp(name, "system", 6) == 0) myflags |= ATTR_ROOT;
+	if (flags & XATTR_CREATE) myflags |= ATTR_CREATE;
+	if (flags & XATTR_REPLACE) myflags |= ATTR_REPLACE;
+
+	return attr_setf(filedes, attrname, (const char *)value, size, myflags);
+#elif defined(HAVE_ATTROPEN)
+	int ret = -1;
+	int myflags = O_RDWR | O_XATTR;
+	int attrfd;
+	if (flags & XATTR_CREATE) myflags |= O_EXCL;
+	if (!(flags & XATTR_REPLACE)) myflags |= O_CREAT;
+	attrfd = solaris_openat(filedes, name, myflags, (mode_t) SOLARIS_ATTRMODE);
+	if (attrfd >= 0) {
+		ret = solaris_write_xattr(attrfd, value, size);
+		close(attrfd);
+	}
+	return ret;
+#else
+	errno = ENOSYS;
+	return -1;
+#endif
+}
+
+/**************************************************************************
+ helper functions for Solaris' EA support
+****************************************************************************/
+#ifdef HAVE_ATTROPEN
+static ssize_t solaris_read_xattr(int attrfd, void *value, size_t size)
+{
+	struct stat sbuf;
+
+	if (fstat(attrfd, &sbuf) == -1) {
+		errno = ENOATTR;
+		return -1;
+	}
+
+	/* This is to return the current size of the named extended attribute */
+	if (size == 0) {
+		return sbuf.st_size;
+	}
+
+	/* check size and read xattr */
+	if (sbuf.st_size > size) {
+		errno = ERANGE;
+		return -1;
+	}
+
+	return read(attrfd, value, sbuf.st_size);
+}
+
+static ssize_t solaris_list_xattr(int attrdirfd, char *list, size_t size)
+{
+	ssize_t len = 0;
+	DIR *dirp;
+	struct dirent *de;
+	int newfd = dup(attrdirfd);
+	/* CAUTION: The originating file descriptor should not be
+	            used again following the call to fdopendir().
+	            For that reason we dup() the file descriptor
+		    here to make things more clear. */
+	dirp = fdopendir(newfd);
+
+	while ((de = readdir(dirp))) {
+		size_t listlen = strlen(de->d_name) + 1;
+		if (!strcmp(de->d_name, ".") || !strcmp(de->d_name, "..")) {
+			/* we don't want "." and ".." here: */
+			continue;
+		}
+
+		if (size == 0) {
+			/* return the current size of the list of extended attribute names*/
+			len += listlen;
+		} else {
+			/* check size and copy entrieѕ + nul into list. */
+			if ((len + listlen) > size) {
+				errno = ERANGE;
+				len = -1;
+				break;
+			} else {
+				strlcpy(list + len, de->d_name, listlen);
+				len += listlen;
+			}
+		}
+	}
+
+	if (closedir(dirp) == -1) {
+		return -1;
+	}
+	return len;
+}
+
+static int solaris_unlinkat(int attrdirfd, const char *name)
+{
+	if (unlinkat(attrdirfd, name, 0) == -1) {
+		if (errno == ENOENT) {
+			errno = ENOATTR;
+		}
+		return -1;
+	}
+	return 0;
+}
+
+static int solaris_attropen(const char *path, const char *attrpath, int oflag, mode_t mode)
+{
+	int filedes = attropen(path, attrpath, oflag, mode);
+	if (filedes == -1) {
+		if (errno == EINVAL) {
+			errno = ENOTSUP;
+		} else {
+			errno = ENOATTR;
+		}
+	}
+	return filedes;
+}
+
+static int solaris_openat(int fildes, const char *path, int oflag, mode_t mode)
+{
+	int filedes = openat(fildes, path, oflag, mode);
+	if (filedes == -1) {
+		if (errno == EINVAL) {
+			errno = ENOTSUP;
+		} else {
+			errno = ENOATTR;
+		}
+	}
+	return filedes;
+}
+
+static int solaris_write_xattr(int attrfd, const char *value, size_t size)
+{
+	if ((ftruncate(attrfd, 0) == 0) && (write(attrfd, value, size) == size)) {
+		return 0;
+	} else {
+		return -1;
+	}
+}
+#endif /*HAVE_ATTROPEN*/
+
+
diff --git a/lib/talloc/ABI/talloc-2.0.7.sigs b/lib/talloc/ABI/talloc-2.0.7.sigs
deleted file mode 100644
index 6e236d5..0000000
--- a/lib/talloc/ABI/talloc-2.0.7.sigs
+++ /dev/null
@@ -1,62 +0,0 @@
-_talloc: void *(const void *, size_t)
-_talloc_array: void *(const void *, size_t, unsigned int, const char *)
-_talloc_free: int (void *, const char *)
-_talloc_get_type_abort: void *(const void *, const char *, const char *)
-_talloc_memdup: void *(const void *, const void *, size_t, const char *)
-_talloc_move: void *(const void *, const void *)
-_talloc_realloc: void *(const void *, void *, size_t, const char *)
-_talloc_realloc_array: void *(const void *, void *, size_t, unsigned int, const char *)
-_talloc_reference_loc: void *(const void *, const void *, const char *)
-_talloc_set_destructor: void (const void *, int (*)(void *))
-_talloc_steal_loc: void *(const void *, const void *, const char *)
-_talloc_zero: void *(const void *, size_t, const char *)
-_talloc_zero_array: void *(const void *, size_t, unsigned int, const char *)
-talloc_asprintf: char *(const void *, const char *, ...)
-talloc_asprintf_append: char *(char *, const char *, ...)
-talloc_asprintf_append_buffer: char *(char *, const char *, ...)
-talloc_autofree_context: void *(void)
-talloc_check_name: void *(const void *, const char *)
-talloc_disable_null_tracking: void (void)
-talloc_enable_leak_report: void (void)
-talloc_enable_leak_report_full: void (void)
-talloc_enable_null_tracking: void (void)
-talloc_enable_null_tracking_no_autofree: void (void)
-talloc_find_parent_byname: void *(const void *, const char *)
-talloc_free_children: void (void *)
-talloc_get_name: const char *(const void *)
-talloc_get_size: size_t (const void *)
-talloc_increase_ref_count: int (const void *)
-talloc_init: void *(const char *, ...)
-talloc_is_parent: int (const void *, const void *)
-talloc_named: void *(const void *, size_t, const char *, ...)
-talloc_named_const: void *(const void *, size_t, const char *)
-talloc_parent: void *(const void *)
-talloc_parent_name: const char *(const void *)
-talloc_pool: void *(const void *, size_t)
-talloc_realloc_fn: void *(const void *, void *, size_t)
-talloc_reference_count: size_t (const void *)
-talloc_reparent: void *(const void *, const void *, const void *)
-talloc_report: void (const void *, FILE *)
-talloc_report_depth_cb: void (const void *, int, int, void (*)(const void *, int, int, int, void *), void *)
-talloc_report_depth_file: void (const void *, int, int, FILE *)
-talloc_report_full: void (const void *, FILE *)
-talloc_set_abort_fn: void (void (*)(const char *))
-talloc_set_log_fn: void (void (*)(const char *))
-talloc_set_log_stderr: void (void)
-talloc_set_name: const char *(const void *, const char *, ...)
-talloc_set_name_const: void (const void *, const char *)
-talloc_show_parents: void (const void *, FILE *)
-talloc_strdup: char *(const void *, const char *)
-talloc_strdup_append: char *(char *, const char *)
-talloc_strdup_append_buffer: char *(char *, const char *)
-talloc_strndup: char *(const void *, const char *, size_t)
-talloc_strndup_append: char *(char *, const char *, size_t)
-talloc_strndup_append_buffer: char *(char *, const char *, size_t)
-talloc_total_blocks: size_t (const void *)
-talloc_total_size: size_t (const void *)
-talloc_unlink: int (const void *, void *)
-talloc_vasprintf: char *(const void *, const char *, va_list)
-talloc_vasprintf_append: char *(char *, const char *, va_list)
-talloc_vasprintf_append_buffer: char *(char *, const char *, va_list)
-talloc_version_major: int (void)
-talloc_version_minor: int (void)
diff --git a/lib/talloc/doc/mainpage.dox b/lib/talloc/doc/mainpage.dox
deleted file mode 100644
index 3204e8a..0000000
--- a/lib/talloc/doc/mainpage.dox
+++ /dev/null
@@ -1,105 +0,0 @@
-/**
- * @mainpage
- *
- * talloc is a hierarchical, reference counted memory pool system with
- * destructors. It is the core memory allocator used in Samba.
- *
- * @section talloc_download Download
- *
- * You can download the latest releases of talloc from the
- * <a href="http://samba.org/ftp/talloc" target="_blank">talloc directory</a>
- * on the samba public source archive.
- *
- * @section talloc_bugs Discussion and bug reports
- *
- * talloc does not currently have its own mailing list or bug tracking system.
- * For now, please use the
- * <a href="https://lists.samba.org/mailman/listinfo/samba-technical" target="_blank">samba-technical</a>
- * mailing list, and the
- * <a href="http://bugzilla.samba.org/" target="_blank">Samba bugzilla</a>
- * bug tracking system.
- *
- * @section talloc_devel Development
- * You can download the latest code either via git or rsync.
- *
- * To fetch via git see the following guide:
- *
- * <a href="http://wiki.samba.org/index.php/Using_Git_for_Samba_Development" target="_blank">Using Git for Samba Development</a>
- *
- * Once you have cloned the tree switch to the master branch and cd into the
- * lib/tevent directory.
- *
- * To fetch via rsync use this command:
- *
- * rsync -Pavz samba.org::ftp/unpacked/standalone_projects/lib/talloc .
- *
- * @section talloc_preample Preamble
- *
- * talloc is a hierarchical, reference counted memory pool system with
- * destructors.
- *
- * Perhaps the biggest difference from other memory pool systems is that there
- * is no distinction between a "talloc context" and a "talloc pointer". Any
- * pointer returned from talloc() is itself a valid talloc context. This means
- * you can do this:
- *
- * @code
- *      struct foo *X = talloc(mem_ctx, struct foo);
- *      X->name = talloc_strdup(X, "foo");
- * @endcode
- *
- * The pointer X->name would be a "child" of the talloc context "X" which is
- * itself a child of mem_ctx. So if you do talloc_free(mem_ctx) then it is all
- * destroyed, whereas if you do talloc_free(X) then just X and X->name are
- * destroyed, and if you do talloc_free(X->name) then just the name element of
- * X is destroyed.
- *
- * If you think about this, then what this effectively gives you is an n-ary
- * tree, where you can free any part of the tree with talloc_free().
- *
- * If you find this confusing, then run the testsuite to watch talloc in
- * action. You may also like to add your own tests to testsuite.c to clarify
- * how some particular situation is handled.
- *
- * @section talloc_performance Performance
- *
- * All the additional features of talloc() over malloc() do come at a price. We
- * have a simple performance test in Samba4 that measures talloc() versus
- * malloc() performance, and it seems that talloc() is about 4% slower than
- * malloc() on my x86 Debian Linux box. For Samba, the great reduction in code
- * complexity that we get by using talloc makes this worthwhile, especially as
- * the total overhead of talloc/malloc in Samba is already quite small.
- *
- * @section talloc_named Named blocks
- *
- * Every talloc chunk has a name that can be used as a dynamic type-checking
- * system. If for some reason like a callback function you had to cast a
- * "struct foo *" to a "void *" variable, later you can safely reassign the
- * "void *" pointer to a "struct foo *" by using the talloc_get_type() or
- * talloc_get_type_abort() macros.
- *
- * @code
- *      struct foo *X = talloc_get_type_abort(ptr, struct foo);
- * @endcode
- *
- * This will abort if "ptr" does not contain a pointer that has been created
- * with talloc(mem_ctx, struct foo).
- *
- * @section talloc_threading Multi-threading
- *
- * talloc itself does not deal with threads. It is thread-safe (assuming the
- * underlying "malloc" is), as long as each thread uses different memory
- * contexts.
- *
- * If two threads uses the same context then they need to synchronize in order
- * to be safe. In particular:
- *
- *   - when using talloc_enable_leak_report(), giving directly NULL as a parent
- *     context implicitly refers to a hidden "null context" global variable, so
- *     this should not be used in a multi-threaded environment without proper
- *     synchronization.
- *   - the context returned by talloc_autofree_context() is also global so
- *     shouldn't be used by several threads simultaneously without
- *     synchronization.
- *
- */
diff --git a/lib/talloc/doxy.config b/lib/talloc/doxy.config
deleted file mode 100644
index 5e3a319..0000000
--- a/lib/talloc/doxy.config
+++ /dev/null
@@ -1,1538 +0,0 @@
-# Doxyfile 1.6.1
-
-# This file describes the settings to be used by the documentation system
-# doxygen (www.doxygen.org) for a project
-#
-# All text after a hash (#) is considered a comment and will be ignored
-# The format is:
-#       TAG = value [value, ...]
-# For lists items can also be appended using:
-#       TAG += value [value, ...]
-# Values that contain spaces should be placed between quotes (" ")
-
-#---------------------------------------------------------------------------
-# Project related configuration options
-#---------------------------------------------------------------------------
-
-# This tag specifies the encoding used for all characters in the config file
-# that follow. The default is UTF-8 which is also the encoding used for all
-# text before the first occurrence of this tag. Doxygen uses libiconv (or the
-# iconv built into libc) for the transcoding. See
-# http://www.gnu.org/software/libiconv for the list of possible encodings.
-
-DOXYFILE_ENCODING      = UTF-8
-
-# The PROJECT_NAME tag is a single word (or a sequence of words surrounded
-# by quotes) that should identify the project.
-
-PROJECT_NAME           = talloc
-
-# The PROJECT_NUMBER tag can be used to enter a project or revision number.
-# This could be handy for archiving the generated documentation or
-# if some version control system is used.
-
-PROJECT_NUMBER         = 2.0
-
-# The OUTPUT_DIRECTORY tag is used to specify the (relative or absolute)
-# base path where the generated documentation will be put.
-# If a relative path is entered, it will be relative to the location
-# where doxygen was started. If left blank the current directory will be used.
-
-OUTPUT_DIRECTORY       = doc
-
-# If the CREATE_SUBDIRS tag is set to YES, then doxygen will create
-# 4096 sub-directories (in 2 levels) under the output directory of each output
-# format and will distribute the generated files over these directories.
-# Enabling this option can be useful when feeding doxygen a huge amount of
-# source files, where putting all generated files in the same directory would
-# otherwise cause performance problems for the file system.
-
-CREATE_SUBDIRS         = NO
-
-# The OUTPUT_LANGUAGE tag is used to specify the language in which all
-# documentation generated by doxygen is written. Doxygen will use this
-# information to generate all constant output in the proper language.
-# The default language is English, other supported languages are:
-# Afrikaans, Arabic, Brazilian, Catalan, Chinese, Chinese-Traditional,
-# Croatian, Czech, Danish, Dutch, Esperanto, Farsi, Finnish, French, German,
-# Greek, Hungarian, Italian, Japanese, Japanese-en (Japanese with English
-# messages), Korean, Korean-en, Lithuanian, Norwegian, Macedonian, Persian,
-# Polish, Portuguese, Romanian, Russian, Serbian, Serbian-Cyrilic, Slovak,
-# Slovene, Spanish, Swedish, Ukrainian, and Vietnamese.
-
-OUTPUT_LANGUAGE        = English
-
-# If the BRIEF_MEMBER_DESC tag is set to YES (the default) Doxygen will
-# include brief member descriptions after the members that are listed in
-# the file and class documentation (similar to JavaDoc).
-# Set to NO to disable this.
-
-BRIEF_MEMBER_DESC      = YES
-
-# If the REPEAT_BRIEF tag is set to YES (the default) Doxygen will prepend
-# the brief description of a member or function before the detailed description.
-# Note: if both HIDE_UNDOC_MEMBERS and BRIEF_MEMBER_DESC are set to NO, the
-# brief descriptions will be completely suppressed.
-
-REPEAT_BRIEF           = YES
-
-# This tag implements a quasi-intelligent brief description abbreviator
-# that is used to form the text in various listings. Each string
-# in this list, if found as the leading text of the brief description, will be
-# stripped from the text and the result after processing the whole list, is
-# used as the annotated text. Otherwise, the brief description is used as-is.
-# If left blank, the following values are used ("$name" is automatically
-# replaced with the name of the entity): "The $name class" "The $name widget"
-# "The $name file" "is" "provides" "specifies" "contains"
-# "represents" "a" "an" "the"
-
-ABBREVIATE_BRIEF       = "The $name class" \
-                         "The $name widget" \
-                         "The $name file" \
-                         is \
-                         provides \
-                         specifies \
-                         contains \
-                         represents \
-                         a \
-                         an \
-                         the
-
-# If the ALWAYS_DETAILED_SEC and REPEAT_BRIEF tags are both set to YES then
-# Doxygen will generate a detailed section even if there is only a brief
-# description.
-
-ALWAYS_DETAILED_SEC    = NO
-
-# If the INLINE_INHERITED_MEMB tag is set to YES, doxygen will show all
-# inherited members of a class in the documentation of that class as if those
-# members were ordinary class members. Constructors, destructors and assignment
-# operators of the base classes will not be shown.
-
-INLINE_INHERITED_MEMB  = NO
-
-# If the FULL_PATH_NAMES tag is set to YES then Doxygen will prepend the full
-# path before files name in the file list and in the header files. If set
-# to NO the shortest path that makes the file name unique will be used.
-
-FULL_PATH_NAMES        = YES
-
-# If the FULL_PATH_NAMES tag is set to YES then the STRIP_FROM_PATH tag
-# can be used to strip a user-defined part of the path. Stripping is
-# only done if one of the specified strings matches the left-hand part of
-# the path. The tag can be used to show relative paths in the file list.
-# If left blank the directory from which doxygen is run is used as the
-# path to strip.
-
-STRIP_FROM_PATH        =
-
-# The STRIP_FROM_INC_PATH tag can be used to strip a user-defined part of
-# the path mentioned in the documentation of a class, which tells
-# the reader which header file to include in order to use a class.
-# If left blank only the name of the header file containing the class
-# definition is used. Otherwise one should specify the include paths that
-# are normally passed to the compiler using the -I flag.
-
-STRIP_FROM_INC_PATH    =
-
-# If the SHORT_NAMES tag is set to YES, doxygen will generate much shorter
-# (but less readable) file names. This can be useful is your file systems
-# doesn't support long names like on DOS, Mac, or CD-ROM.
-
-SHORT_NAMES            = NO
-
-# If the JAVADOC_AUTOBRIEF tag is set to YES then Doxygen
-# will interpret the first line (until the first dot) of a JavaDoc-style
-# comment as the brief description. If set to NO, the JavaDoc
-# comments will behave just like regular Qt-style comments
-# (thus requiring an explicit @brief command for a brief description.)
-
-JAVADOC_AUTOBRIEF      = YES
-
-# If the QT_AUTOBRIEF tag is set to YES then Doxygen will
-# interpret the first line (until the first dot) of a Qt-style
-# comment as the brief description. If set to NO, the comments
-# will behave just like regular Qt-style comments (thus requiring
-# an explicit \brief command for a brief description.)
-
-QT_AUTOBRIEF           = NO
-
-# The MULTILINE_CPP_IS_BRIEF tag can be set to YES to make Doxygen
-# treat a multi-line C++ special comment block (i.e. a block of //! or ///
-# comments) as a brief description. This used to be the default behaviour.
-# The new default is to treat a multi-line C++ comment block as a detailed
-# description. Set this tag to YES if you prefer the old behaviour instead.
-
-MULTILINE_CPP_IS_BRIEF = NO
-
-# If the INHERIT_DOCS tag is set to YES (the default) then an undocumented
-# member inherits the documentation from any documented member that it
-# re-implements.
-
-INHERIT_DOCS           = YES
-
-# If the SEPARATE_MEMBER_PAGES tag is set to YES, then doxygen will produce
-# a new page for each member. If set to NO, the documentation of a member will
-# be part of the file/class/namespace that contains it.
-
-SEPARATE_MEMBER_PAGES  = NO
-
-# The TAB_SIZE tag can be used to set the number of spaces in a tab.
-# Doxygen uses this value to replace tabs by spaces in code fragments.
-
-TAB_SIZE               = 8
-
-# This tag can be used to specify a number of aliases that acts
-# as commands in the documentation. An alias has the form "name=value".
-# For example adding "sideeffect=\par Side Effects:\n" will allow you to
-# put the command \sideeffect (or @sideeffect) in the documentation, which
-# will result in a user-defined paragraph with heading "Side Effects:".
-# You can put \n's in the value part of an alias to insert newlines.
-
-ALIASES                =
-
-# Set the OPTIMIZE_OUTPUT_FOR_C tag to YES if your project consists of C
-# sources only. Doxygen will then generate output that is more tailored for C.
-# For instance, some of the names that are used will be different. The list
-# of all members will be omitted, etc.
-
-OPTIMIZE_OUTPUT_FOR_C  = YES
-
-# Set the OPTIMIZE_OUTPUT_JAVA tag to YES if your project consists of Java
-# sources only. Doxygen will then generate output that is more tailored for
-# Java. For instance, namespaces will be presented as packages, qualified
-# scopes will look different, etc.
-
-OPTIMIZE_OUTPUT_JAVA   = NO
-
-# Set the OPTIMIZE_FOR_FORTRAN tag to YES if your project consists of Fortran
-# sources only. Doxygen will then generate output that is more tailored for
-# Fortran.
-
-OPTIMIZE_FOR_FORTRAN   = NO
-
-# Set the OPTIMIZE_OUTPUT_VHDL tag to YES if your project consists of VHDL
-# sources. Doxygen will then generate output that is tailored for
-# VHDL.
-
-OPTIMIZE_OUTPUT_VHDL   = NO
-
-# Doxygen selects the parser to use depending on the extension of the files it parses.
-# With this tag you can assign which parser to use for a given extension.
-# Doxygen has a built-in mapping, but you can override or extend it using this tag.
-# The format is ext=language, where ext is a file extension, and language is one of
-# the parsers supported by doxygen: IDL, Java, Javascript, C#, C, C++, D, PHP,
-# Objective-C, Python, Fortran, VHDL, C, C++. For instance to make doxygen treat
-# .inc files as Fortran files (default is PHP), and .f files as C (default is Fortran),
-# use: inc=Fortran f=C. Note that for custom extensions you also need to set FILE_PATTERNS otherwise the files are not read by doxygen.
-
-EXTENSION_MAPPING      =
-
-# If you use STL classes (i.e. std::string, std::vector, etc.) but do not want
-# to include (a tag file for) the STL sources as input, then you should
-# set this tag to YES in order to let doxygen match functions declarations and
-# definitions whose arguments contain STL classes (e.g. func(std::string); v.s.
-# func(std::string) {}). This also make the inheritance and collaboration
-# diagrams that involve STL classes more complete and accurate.
-
-BUILTIN_STL_SUPPORT    = NO
-
-# If you use Microsoft's C++/CLI language, you should set this option to YES to
-# enable parsing support.
-
-CPP_CLI_SUPPORT        = NO
-
-# Set the SIP_SUPPORT tag to YES if your project consists of sip sources only.
-# Doxygen will parse them like normal C++ but will assume all classes use public
-# instead of private inheritance when no explicit protection keyword is present.
-
-SIP_SUPPORT            = NO
-
-# For Microsoft's IDL there are propget and propput attributes to indicate getter
-# and setter methods for a property. Setting this option to YES (the default)
-# will make doxygen to replace the get and set methods by a property in the
-# documentation. This will only work if the methods are indeed getting or
-# setting a simple type. If this is not the case, or you want to show the
-# methods anyway, you should set this option to NO.
-
-IDL_PROPERTY_SUPPORT   = YES
-
-# If member grouping is used in the documentation and the DISTRIBUTE_GROUP_DOC
-# tag is set to YES, then doxygen will reuse the documentation of the first
-# member in the group (if any) for the other members of the group. By default
-# all members of a group must be documented explicitly.
-
-DISTRIBUTE_GROUP_DOC   = NO
-
-# Set the SUBGROUPING tag to YES (the default) to allow class member groups of
-# the same type (for instance a group of public functions) to be put as a
-# subgroup of that type (e.g. under the Public Functions section). Set it to
-# NO to prevent subgrouping. Alternatively, this can be done per class using
-# the \nosubgrouping command.
-
-SUBGROUPING            = YES
-
-# When TYPEDEF_HIDES_STRUCT is enabled, a typedef of a struct, union, or enum
-# is documented as struct, union, or enum with the name of the typedef. So
-# typedef struct TypeS {} TypeT, will appear in the documentation as a struct
-# with name TypeT. When disabled the typedef will appear as a member of a file,
-# namespace, or class. And the struct will be named TypeS. This can typically
-# be useful for C code in case the coding convention dictates that all compound
-# types are typedef'ed and only the typedef is referenced, never the tag name.
-
-TYPEDEF_HIDES_STRUCT   = NO
-
-# The SYMBOL_CACHE_SIZE determines the size of the internal cache use to
-# determine which symbols to keep in memory and which to flush to disk.
-# When the cache is full, less often used symbols will be written to disk.
-# For small to medium size projects (<1000 input files) the default value is
-# probably good enough. For larger projects a too small cache size can cause
-# doxygen to be busy swapping symbols to and from disk most of the time
-# causing a significant performance penality.
-# If the system has enough physical memory increasing the cache will improve the
-# performance by keeping more symbols in memory. Note that the value works on
-# a logarithmic scale so increasing the size by one will rougly double the
-# memory usage. The cache size is given by this formula:
-# 2^(16+SYMBOL_CACHE_SIZE). The valid range is 0..9, the default is 0,
-# corresponding to a cache size of 2^16 = 65536 symbols
-
-SYMBOL_CACHE_SIZE      = 0
-
-#---------------------------------------------------------------------------
-# Build related configuration options
-#---------------------------------------------------------------------------
-
-# If the EXTRACT_ALL tag is set to YES doxygen will assume all entities in
-# documentation are documented, even if no documentation was available.
-# Private class members and static file members will be hidden unless
-# the EXTRACT_PRIVATE and EXTRACT_STATIC tags are set to YES
-
-EXTRACT_ALL            = NO
-
-# If the EXTRACT_PRIVATE tag is set to YES all private members of a class
-# will be included in the documentation.
-
-EXTRACT_PRIVATE        = NO
-
-# If the EXTRACT_STATIC tag is set to YES all static members of a file
-# will be included in the documentation.
-
-EXTRACT_STATIC         = NO
-
-# If the EXTRACT_LOCAL_CLASSES tag is set to YES classes (and structs)
-# defined locally in source files will be included in the documentation.
-# If set to NO only classes defined in header files are included.
-
-EXTRACT_LOCAL_CLASSES  = NO
-
-# This flag is only useful for Objective-C code. When set to YES local
-# methods, which are defined in the implementation section but not in
-# the interface are included in the documentation.
-# If set to NO (the default) only methods in the interface are included.
-
-EXTRACT_LOCAL_METHODS  = NO
-
-# If this flag is set to YES, the members of anonymous namespaces will be
-# extracted and appear in the documentation as a namespace called
-# 'anonymous_namespace{file}', where file will be replaced with the base
-# name of the file that contains the anonymous namespace. By default
-# anonymous namespace are hidden.
-
-EXTRACT_ANON_NSPACES   = NO
-
-# If the HIDE_UNDOC_MEMBERS tag is set to YES, Doxygen will hide all
-# undocumented members of documented classes, files or namespaces.
-# If set to NO (the default) these members will be included in the
-# various overviews, but no documentation section is generated.
-# This option has no effect if EXTRACT_ALL is enabled.
-
-HIDE_UNDOC_MEMBERS     = YES
-
-# If the HIDE_UNDOC_CLASSES tag is set to YES, Doxygen will hide all
-# undocumented classes that are normally visible in the class hierarchy.
-# If set to NO (the default) these classes will be included in the various
-# overviews. This option has no effect if EXTRACT_ALL is enabled.
-
-HIDE_UNDOC_CLASSES     = YES
-
-# If the HIDE_FRIEND_COMPOUNDS tag is set to YES, Doxygen will hide all
-# friend (class|struct|union) declarations.
-# If set to NO (the default) these declarations will be included in the
-# documentation.
-
-HIDE_FRIEND_COMPOUNDS  = NO
-
-# If the HIDE_IN_BODY_DOCS tag is set to YES, Doxygen will hide any
-# documentation blocks found inside the body of a function.
-# If set to NO (the default) these blocks will be appended to the
-# function's detailed documentation block.
-
-HIDE_IN_BODY_DOCS      = NO
-
-# The INTERNAL_DOCS tag determines if documentation
-# that is typed after a \internal command is included. If the tag is set
-# to NO (the default) then the documentation will be excluded.
-# Set it to YES to include the internal documentation.
-
-INTERNAL_DOCS          = NO
-
-# If the CASE_SENSE_NAMES tag is set to NO then Doxygen will only generate
-# file names in lower-case letters. If set to YES upper-case letters are also
-# allowed. This is useful if you have classes or files whose names only differ
-# in case and if your file system supports case sensitive file names. Windows
-# and Mac users are advised to set this option to NO.
-
-CASE_SENSE_NAMES       = YES
-
-# If the HIDE_SCOPE_NAMES tag is set to NO (the default) then Doxygen
-# will show members with their full class and namespace scopes in the
-# documentation. If set to YES the scope will be hidden.
-
-HIDE_SCOPE_NAMES       = NO
-
-# If the SHOW_INCLUDE_FILES tag is set to YES (the default) then Doxygen
-# will put a list of the files that are included by a file in the documentation
-# of that file.
-
-SHOW_INCLUDE_FILES     = YES
-
-# If the INLINE_INFO tag is set to YES (the default) then a tag [inline]
-# is inserted in the documentation for inline members.
-
-INLINE_INFO            = YES
-
-# If the SORT_MEMBER_DOCS tag is set to YES (the default) then doxygen
-# will sort the (detailed) documentation of file and class members
-# alphabetically by member name. If set to NO the members will appear in
-# declaration order.
-
-SORT_MEMBER_DOCS       = YES
-
-# If the SORT_BRIEF_DOCS tag is set to YES then doxygen will sort the
-# brief documentation of file, namespace and class members alphabetically
-# by member name. If set to NO (the default) the members will appear in
-# declaration order.
-
-SORT_BRIEF_DOCS        = NO
-
-# If the SORT_MEMBERS_CTORS_1ST tag is set to YES then doxygen will sort the (brief and detailed) documentation of class members so that constructors and destructors are listed first. If set to NO (the default) the constructors will appear in the respective orders defined by SORT_MEMBER_DOCS and SORT_BRIEF_DOCS. This tag will be ignored for brief docs if SORT_BRIEF_DOCS is set to NO and ignored for detailed docs if SORT_MEMBER_DOCS is set to NO.
-
-SORT_MEMBERS_CTORS_1ST = NO
-
-# If the SORT_GROUP_NAMES tag is set to YES then doxygen will sort the
-# hierarchy of group names into alphabetical order. If set to NO (the default)
-# the group names will appear in their defined order.
-
-SORT_GROUP_NAMES       = NO
-
-# If the SORT_BY_SCOPE_NAME tag is set to YES, the class list will be
-# sorted by fully-qualified names, including namespaces. If set to
-# NO (the default), the class list will be sorted only by class name,
-# not including the namespace part.
-# Note: This option is not very useful if HIDE_SCOPE_NAMES is set to YES.
-# Note: This option applies only to the class list, not to the
-# alphabetical list.
-
-SORT_BY_SCOPE_NAME     = NO
-
-# The GENERATE_TODOLIST tag can be used to enable (YES) or
-# disable (NO) the todo list. This list is created by putting \todo
-# commands in the documentation.
-
-GENERATE_TODOLIST      = YES
-
-# The GENERATE_TESTLIST tag can be used to enable (YES) or
-# disable (NO) the test list. This list is created by putting \test
-# commands in the documentation.
-
-GENERATE_TESTLIST      = YES
-
-# The GENERATE_BUGLIST tag can be used to enable (YES) or
-# disable (NO) the bug list. This list is created by putting \bug
-# commands in the documentation.
-
-GENERATE_BUGLIST       = YES
-
-# The GENERATE_DEPRECATEDLIST tag can be used to enable (YES) or
-# disable (NO) the deprecated list. This list is created by putting
-# \deprecated commands in the documentation.
-
-GENERATE_DEPRECATEDLIST= YES
-
-# The ENABLED_SECTIONS tag can be used to enable conditional
-# documentation sections, marked by \if sectionname ... \endif.
-
-ENABLED_SECTIONS       =
-
-# The MAX_INITIALIZER_LINES tag determines the maximum number of lines
-# the initial value of a variable or define consists of for it to appear in
-# the documentation. If the initializer consists of more lines than specified
-# here it will be hidden. Use a value of 0 to hide initializers completely.
-# The appearance of the initializer of individual variables and defines in the
-# documentation can be controlled using \showinitializer or \hideinitializer
-# command in the documentation regardless of this setting.
-
-MAX_INITIALIZER_LINES  = 30
-
-# Set the SHOW_USED_FILES tag to NO to disable the list of files generated
-# at the bottom of the documentation of classes and structs. If set to YES the
-# list will mention the files that were used to generate the documentation.
-
-SHOW_USED_FILES        = YES
-
-# If the sources in your project are distributed over multiple directories
-# then setting the SHOW_DIRECTORIES tag to YES will show the directory hierarchy
-# in the documentation. The default is NO.
-
-SHOW_DIRECTORIES       = NO
-
-# Set the SHOW_FILES tag to NO to disable the generation of the Files page.
-# This will remove the Files entry from the Quick Index and from the
-# Folder Tree View (if specified). The default is YES.
-
-SHOW_FILES             = YES
-
-# Set the SHOW_NAMESPACES tag to NO to disable the generation of the
-# Namespaces page.
-# This will remove the Namespaces entry from the Quick Index
-# and from the Folder Tree View (if specified). The default is YES.
-
-SHOW_NAMESPACES        = YES
-
-# The FILE_VERSION_FILTER tag can be used to specify a program or script that
-# doxygen should invoke to get the current version for each file (typically from
-# the version control system). Doxygen will invoke the program by executing (via
-# popen()) the command <command> <input-file>, where <command> is the value of
-# the FILE_VERSION_FILTER tag, and <input-file> is the name of an input file
-# provided by doxygen. Whatever the program writes to standard output
-# is used as the file version. See the manual for examples.
-
-FILE_VERSION_FILTER    =
-
-# The LAYOUT_FILE tag can be used to specify a layout file which will be parsed by
-# doxygen. The layout file controls the global structure of the generated output files
-# in an output format independent way. The create the layout file that represents
-# doxygen's defaults, run doxygen with the -l option. You can optionally specify a
-# file name after the option, if omitted DoxygenLayout.xml will be used as the name
-# of the layout file.
-
-LAYOUT_FILE            =
-
-#---------------------------------------------------------------------------
-# configuration options related to warning and progress messages
-#---------------------------------------------------------------------------
-
-# The QUIET tag can be used to turn on/off the messages that are generated
-# by doxygen. Possible values are YES and NO. If left blank NO is used.
-
-QUIET                  = NO
-
-# The WARNINGS tag can be used to turn on/off the warning messages that are
-# generated by doxygen. Possible values are YES and NO. If left blank
-# NO is used.
-
-WARNINGS               = YES
-
-# If WARN_IF_UNDOCUMENTED is set to YES, then doxygen will generate warnings
-# for undocumented members. If EXTRACT_ALL is set to YES then this flag will
-# automatically be disabled.
-
-WARN_IF_UNDOCUMENTED   = YES
-
-# If WARN_IF_DOC_ERROR is set to YES, doxygen will generate warnings for
-# potential errors in the documentation, such as not documenting some
-# parameters in a documented function, or documenting parameters that
-# don't exist or using markup commands wrongly.
-
-WARN_IF_DOC_ERROR      = YES
-
-# This WARN_NO_PARAMDOC option can be abled to get warnings for
-# functions that are documented, but have no documentation for their parameters
-# or return value. If set to NO (the default) doxygen will only warn about
-# wrong or incomplete parameter documentation, but not about the absence of
-# documentation.
-
-WARN_NO_PARAMDOC       = NO
-
-# The WARN_FORMAT tag determines the format of the warning messages that
-# doxygen can produce. The string should contain the $file, $line, and $text
-# tags, which will be replaced by the file and line number from which the
-# warning originated and the warning text. Optionally the format may contain
-# $version, which will be replaced by the version of the file (if it could
-# be obtained via FILE_VERSION_FILTER)
-
-WARN_FORMAT            = "$file:$line: $text"
-
-# The WARN_LOGFILE tag can be used to specify a file to which warning
-# and error messages should be written. If left blank the output is written
-# to stderr.
-
-WARN_LOGFILE           =
-
-#---------------------------------------------------------------------------
-# configuration options related to the input files
-#---------------------------------------------------------------------------
-
-# The INPUT tag can be used to specify the files and/or directories that contain
-# documented source files. You may enter file names like "myfile.cpp" or
-# directories like "/usr/src/myproject". Separate the files or directories
-# with spaces.
-
-INPUT                  = . doc
-
-# This tag can be used to specify the character encoding of the source files
-# that doxygen parses. Internally doxygen uses the UTF-8 encoding, which is
-# also the default input encoding. Doxygen uses libiconv (or the iconv built
-# into libc) for the transcoding. See http://www.gnu.org/software/libiconv for
-# the list of possible encodings.
-
-INPUT_ENCODING         = UTF-8
-
-# If the value of the INPUT tag contains directories, you can use the
-# FILE_PATTERNS tag to specify one or more wildcard pattern (like *.cpp
-# and *.h) to filter out the source-files in the directories. If left
-# blank the following patterns are tested:
-# *.c *.cc *.cxx *.cpp *.c++ *.java *.ii *.ixx *.ipp *.i++ *.inl *.h *.hh *.hxx
-# *.hpp *.h++ *.idl *.odl *.cs *.php *.php3 *.inc *.m *.mm *.py *.f90
-
-FILE_PATTERNS          = *.cpp \
-                         *.cc \
-                         *.c \
-                         *.h \
-                         *.hh \
-                         *.hpp \
-                         *.dox
-
-# The RECURSIVE tag can be used to turn specify whether or not subdirectories
-# should be searched for input files as well. Possible values are YES and NO.
-# If left blank NO is used.
-
-RECURSIVE              = NO
-
-# The EXCLUDE tag can be used to specify files and/or directories that should
-# excluded from the INPUT source files. This way you can easily exclude a
-# subdirectory from a directory tree whose root is specified with the INPUT tag.
-
-EXCLUDE                =
-
-# The EXCLUDE_SYMLINKS tag can be used select whether or not files or
-# directories that are symbolic links (a Unix filesystem feature) are excluded
-# from the input.
-
-EXCLUDE_SYMLINKS       = NO
-
-# If the value of the INPUT tag contains directories, you can use the
-# EXCLUDE_PATTERNS tag to specify one or more wildcard patterns to exclude
-# certain files from those directories. Note that the wildcards are matched
-# against the file with absolute path, so to exclude all test directories
-# for example use the pattern */test/*
-
-EXCLUDE_PATTERNS       = */.git/* \
-                         */.svn/* \
-                         */cmake/* \
-                         */build/*
-
-# The EXCLUDE_SYMBOLS tag can be used to specify one or more symbol names
-# (namespaces, classes, functions, etc.) that should be excluded from the
-# output. The symbol name can be a fully qualified name, a word, or if the
-# wildcard * is used, a substring. Examples: ANamespace, AClass,
-# AClass::ANamespace, ANamespace::*Test
-
-EXCLUDE_SYMBOLS        =
-
-# The EXAMPLE_PATH tag can be used to specify one or more files or
-# directories that contain example code fragments that are included (see
-# the \include command).
-
-EXAMPLE_PATH           =
-
-# If the value of the EXAMPLE_PATH tag contains directories, you can use the
-# EXAMPLE_PATTERNS tag to specify one or more wildcard pattern (like *.cpp
-# and *.h) to filter out the source-files in the directories. If left
-# blank all files are included.
-
-EXAMPLE_PATTERNS       =
-
-# If the EXAMPLE_RECURSIVE tag is set to YES then subdirectories will be
-# searched for input files to be used with the \include or \dontinclude
-# commands irrespective of the value of the RECURSIVE tag.
-# Possible values are YES and NO. If left blank NO is used.
-
-EXAMPLE_RECURSIVE      = NO
-
-# The IMAGE_PATH tag can be used to specify one or more files or
-# directories that contain image that are included in the documentation (see
-# the \image command).
-
-IMAGE_PATH             =
-
-# The INPUT_FILTER tag can be used to specify a program that doxygen should
-# invoke to filter for each input file. Doxygen will invoke the filter program
-# by executing (via popen()) the command <filter> <input-file>, where <filter>
-# is the value of the INPUT_FILTER tag, and <input-file> is the name of an
-# input file. Doxygen will then use the output that the filter program writes
-# to standard output.
-# If FILTER_PATTERNS is specified, this tag will be
-# ignored.
-
-INPUT_FILTER           =
-
-# The FILTER_PATTERNS tag can be used to specify filters on a per file pattern
-# basis.
-# Doxygen will compare the file name with each pattern and apply the
-# filter if there is a match.
-# The filters are a list of the form:
-# pattern=filter (like *.cpp=my_cpp_filter). See INPUT_FILTER for further
-# info on how filters are used. If FILTER_PATTERNS is empty, INPUT_FILTER
-# is applied to all files.
-
-FILTER_PATTERNS        =
-
-# If the FILTER_SOURCE_FILES tag is set to YES, the input filter (if set using
-# INPUT_FILTER) will be used to filter the input files when producing source
-# files to browse (i.e. when SOURCE_BROWSER is set to YES).
-
-FILTER_SOURCE_FILES    = NO
-
-#---------------------------------------------------------------------------
-# configuration options related to source browsing
-#---------------------------------------------------------------------------
-
-# If the SOURCE_BROWSER tag is set to YES then a list of source files will
-# be generated. Documented entities will be cross-referenced with these sources.
-# Note: To get rid of all source code in the generated output, make sure also
-# VERBATIM_HEADERS is set to NO.
-
-SOURCE_BROWSER         = NO
-
-# Setting the INLINE_SOURCES tag to YES will include the body
-# of functions and classes directly in the documentation.
-
-INLINE_SOURCES         = NO
-
-# Setting the STRIP_CODE_COMMENTS tag to YES (the default) will instruct
-# doxygen to hide any special comment blocks from generated source code
-# fragments. Normal C and C++ comments will always remain visible.
-
-STRIP_CODE_COMMENTS    = YES
-
-# If the REFERENCED_BY_RELATION tag is set to YES
-# then for each documented function all documented
-# functions referencing it will be listed.
-
-REFERENCED_BY_RELATION = NO
-
-# If the REFERENCES_RELATION tag is set to YES
-# then for each documented function all documented entities
-# called/used by that function will be listed.
-
-REFERENCES_RELATION    = NO
-
-# If the REFERENCES_LINK_SOURCE tag is set to YES (the default)
-# and SOURCE_BROWSER tag is set to YES, then the hyperlinks from
-# functions in REFERENCES_RELATION and REFERENCED_BY_RELATION lists will
-# link to the source code.
-# Otherwise they will link to the documentation.
-
-REFERENCES_LINK_SOURCE = YES
-
-# If the USE_HTAGS tag is set to YES then the references to source code
-# will point to the HTML generated by the htags(1) tool instead of doxygen
-# built-in source browser. The htags tool is part of GNU's global source
-# tagging system (see http://www.gnu.org/software/global/global.html). You
-# will need version 4.8.6 or higher.
-
-USE_HTAGS              = NO
-
-# If the VERBATIM_HEADERS tag is set to YES (the default) then Doxygen
-# will generate a verbatim copy of the header file for each class for
-# which an include is specified. Set to NO to disable this.
-
-VERBATIM_HEADERS       = YES
-
-#---------------------------------------------------------------------------
-# configuration options related to the alphabetical class index
-#---------------------------------------------------------------------------
-
-# If the ALPHABETICAL_INDEX tag is set to YES, an alphabetical index
-# of all compounds will be generated. Enable this if the project
-# contains a lot of classes, structs, unions or interfaces.
-
-ALPHABETICAL_INDEX     = NO
-
-# If the alphabetical index is enabled (see ALPHABETICAL_INDEX) then
-# the COLS_IN_ALPHA_INDEX tag can be used to specify the number of columns
-# in which this list will be split (can be a number in the range [1..20])
-
-COLS_IN_ALPHA_INDEX    = 5
-
-# In case all classes in a project start with a common prefix, all
-# classes will be put under the same header in the alphabetical index.
-# The IGNORE_PREFIX tag can be used to specify one or more prefixes that
-# should be ignored while generating the index headers.
-
-IGNORE_PREFIX          =
-
-#---------------------------------------------------------------------------
-# configuration options related to the HTML output
-#---------------------------------------------------------------------------
-
-# If the GENERATE_HTML tag is set to YES (the default) Doxygen will
-# generate HTML output.
-
-GENERATE_HTML          = YES
-
-# If the HTML_FOOTER_DESCRIPTION tag is set to YES, Doxygen will
-# add generated date, project name and doxygen version to HTML footer.
-
-HTML_FOOTER_DESCRIPTION= NO
-
-# The HTML_OUTPUT tag is used to specify where the HTML docs will be put.
-# If a relative path is entered the value of OUTPUT_DIRECTORY will be
-# put in front of it. If left blank `html' will be used as the default path.
-
-HTML_OUTPUT            = html
-
-# The HTML_FILE_EXTENSION tag can be used to specify the file extension for
-# each generated HTML page (for example: .htm,.php,.asp). If it is left blank
-# doxygen will generate files with .html extension.
-
-HTML_FILE_EXTENSION    = .html
-
-# The HTML_HEADER tag can be used to specify a personal HTML header for
-# each generated HTML page. If it is left blank doxygen will generate a
-# standard header.
-
-HTML_HEADER            =
-
-# The HTML_FOOTER tag can be used to specify a personal HTML footer for
-# each generated HTML page. If it is left blank doxygen will generate a
-# standard footer.
-
-HTML_FOOTER            =
-
-# The HTML_STYLESHEET tag can be used to specify a user-defined cascading
-# style sheet that is used by each HTML page. It can be used to
-# fine-tune the look of the HTML output. If the tag is left blank doxygen
-# will generate a default style sheet. Note that doxygen will try to copy
-# the style sheet file to the HTML output directory, so don't put your own
-# stylesheet in the HTML output directory as well, or it will be erased!
-
-HTML_STYLESHEET        =
-
-# If the HTML_ALIGN_MEMBERS tag is set to YES, the members of classes,
-# files or namespaces will be aligned in HTML using tables. If set to
-# NO a bullet list will be used.
-
-HTML_ALIGN_MEMBERS     = YES
-
-# If the HTML_DYNAMIC_SECTIONS tag is set to YES then the generated HTML
-# documentation will contain sections that can be hidden and shown after the
-# page has loaded. For this to work a browser that supports
-# JavaScript and DHTML is required (for instance Mozilla 1.0+, Firefox
-# Netscape 6.0+, Internet explorer 5.0+, Konqueror, or Safari).
-
-HTML_DYNAMIC_SECTIONS  = NO
-
-# If the GENERATE_DOCSET tag is set to YES, additional index files
-# will be generated that can be used as input for Apple's Xcode 3
-# integrated development environment, introduced with OSX 10.5 (Leopard).
-# To create a documentation set, doxygen will generate a Makefile in the
-# HTML output directory. Running make will produce the docset in that
-# directory and running "make install" will install the docset in
-# ~/Library/Developer/Shared/Documentation/DocSets so that Xcode will find
-# it at startup.
-# See http://developer.apple.com/tools/creatingdocsetswithdoxygen.html for more information.
-
-GENERATE_DOCSET        = NO
-
-# When GENERATE_DOCSET tag is set to YES, this tag determines the name of the
-# feed. A documentation feed provides an umbrella under which multiple
-# documentation sets from a single provider (such as a company or product suite)
-# can be grouped.
-
-DOCSET_FEEDNAME        = "Doxygen generated docs"
-
-# When GENERATE_DOCSET tag is set to YES, this tag specifies a string that
-# should uniquely identify the documentation set bundle. This should be a
-# reverse domain-name style string, e.g. com.mycompany.MyDocSet. Doxygen
-# will append .docset to the name.
-
-DOCSET_BUNDLE_ID       = org.doxygen.Project
-
-# If the GENERATE_HTMLHELP tag is set to YES, additional index files
-# will be generated that can be used as input for tools like the
-# Microsoft HTML help workshop to generate a compiled HTML help file (.chm)
-# of the generated HTML documentation.
-
-GENERATE_HTMLHELP      = NO
-
-# If the GENERATE_HTMLHELP tag is set to YES, the CHM_FILE tag can
-# be used to specify the file name of the resulting .chm file. You
-# can add a path in front of the file if the result should not be
-# written to the html output directory.
-
-CHM_FILE               =
-
-# If the GENERATE_HTMLHELP tag is set to YES, the HHC_LOCATION tag can
-# be used to specify the location (absolute path including file name) of
-# the HTML help compiler (hhc.exe). If non-empty doxygen will try to run
-# the HTML help compiler on the generated index.hhp.
-
-HHC_LOCATION           =
-
-# If the GENERATE_HTMLHELP tag is set to YES, the GENERATE_CHI flag
-# controls if a separate .chi index file is generated (YES) or that
-# it should be included in the master .chm file (NO).
-
-GENERATE_CHI           = NO
-
-# If the GENERATE_HTMLHELP tag is set to YES, the CHM_INDEX_ENCODING
-# is used to encode HtmlHelp index (hhk), content (hhc) and project file
-# content.
-
-CHM_INDEX_ENCODING     =
-
-# If the GENERATE_HTMLHELP tag is set to YES, the BINARY_TOC flag
-# controls whether a binary table of contents is generated (YES) or a
-# normal table of contents (NO) in the .chm file.
-
-BINARY_TOC             = NO
-
-# The TOC_EXPAND flag can be set to YES to add extra items for group members
-# to the contents of the HTML help documentation and to the tree view.
-
-TOC_EXPAND             = NO
-
-# If the GENERATE_QHP tag is set to YES and both QHP_NAMESPACE and QHP_VIRTUAL_FOLDER
-# are set, an additional index file will be generated that can be used as input for
-# Qt's qhelpgenerator to generate a Qt Compressed Help (.qch) of the generated
-# HTML documentation.
-
-GENERATE_QHP           = NO
-
-# If the QHG_LOCATION tag is specified, the QCH_FILE tag can
-# be used to specify the file name of the resulting .qch file.
-# The path specified is relative to the HTML output folder.
-
-QCH_FILE               =
-
-# The QHP_NAMESPACE tag specifies the namespace to use when generating
-# Qt Help Project output. For more information please see
-# http://doc.trolltech.com/qthelpproject.html#namespace
-
-QHP_NAMESPACE          =
-
-# The QHP_VIRTUAL_FOLDER tag specifies the namespace to use when generating
-# Qt Help Project output. For more information please see
-# http://doc.trolltech.com/qthelpproject.html#virtual-folders
-
-QHP_VIRTUAL_FOLDER     = doc
-
-# If QHP_CUST_FILTER_NAME is set, it specifies the name of a custom filter to add.
-# For more information please see
-# http://doc.trolltech.com/qthelpproject.html#custom-filters
-
-QHP_CUST_FILTER_NAME   =
-
-# The QHP_CUST_FILT_ATTRS tag specifies the list of the attributes of the custom filter to add.For more information please see
-# <a href="http://doc.trolltech.com/qthelpproject.html#custom-filters">Qt Help Project / Custom Filters</a>.
-
-QHP_CUST_FILTER_ATTRS  =
-
-# The QHP_SECT_FILTER_ATTRS tag specifies the list of the attributes this project's
-# filter section matches.
-# <a href="http://doc.trolltech.com/qthelpproject.html#filter-attributes">Qt Help Project / Filter Attributes</a>.
-
-QHP_SECT_FILTER_ATTRS  =
-
-# If the GENERATE_QHP tag is set to YES, the QHG_LOCATION tag can
-# be used to specify the location of Qt's qhelpgenerator.
-# If non-empty doxygen will try to run qhelpgenerator on the generated
-# .qhp file.
-
-QHG_LOCATION           =
-
-# The DISABLE_INDEX tag can be used to turn on/off the condensed index at
-# top of each HTML page. The value NO (the default) enables the index and
-# the value YES disables it.
-
-DISABLE_INDEX          = NO
-
-# This tag can be used to set the number of enum values (range [1..20])
-# that doxygen will group on one line in the generated HTML documentation.
-
-ENUM_VALUES_PER_LINE   = 4
-
-# The GENERATE_TREEVIEW tag is used to specify whether a tree-like index
-# structure should be generated to display hierarchical information.
-# If the tag value is set to YES, a side panel will be generated
-# containing a tree-like index structure (just like the one that
-# is generated for HTML Help). For this to work a browser that supports
-# JavaScript, DHTML, CSS and frames is required (i.e. any modern browser).
-# Windows users are probably better off using the HTML help feature.
-
-GENERATE_TREEVIEW      = NONE
-
-# By enabling USE_INLINE_TREES, doxygen will generate the Groups, Directories,
-# and Class Hierarchy pages using a tree view instead of an ordered list.
-
-USE_INLINE_TREES       = NO
-
-# If the treeview is enabled (see GENERATE_TREEVIEW) then this tag can be
-# used to set the initial width (in pixels) of the frame in which the tree
-# is shown.
-
-TREEVIEW_WIDTH         = 250
-
-# Use this tag to change the font size of Latex formulas included
-# as images in the HTML documentation. The default is 10. Note that
-# when you change the font size after a successful doxygen run you need
-# to manually remove any form_*.png images from the HTML output directory
-# to force them to be regenerated.
-
-FORMULA_FONTSIZE       = 10
-
-# When the SEARCHENGINE tag is enable doxygen will generate a search box for the HTML output. The underlying search engine uses javascript
-# and DHTML and should work on any modern browser. Note that when using HTML help (GENERATE_HTMLHELP) or Qt help (GENERATE_QHP)
-# there is already a search function so this one should typically
-# be disabled.
-
-SEARCHENGINE           = NO
-
-#---------------------------------------------------------------------------
-# configuration options related to the LaTeX output
-#---------------------------------------------------------------------------
-
-# If the GENERATE_LATEX tag is set to YES (the default) Doxygen will
-# generate Latex output.
-
-GENERATE_LATEX         = YES
-
-# The LATEX_OUTPUT tag is used to specify where the LaTeX docs will be put.
-# If a relative path is entered the value of OUTPUT_DIRECTORY will be
-# put in front of it. If left blank `latex' will be used as the default path.
-
-LATEX_OUTPUT           = latex
-
-# The LATEX_CMD_NAME tag can be used to specify the LaTeX command name to be
-# invoked. If left blank `latex' will be used as the default command name.
-
-LATEX_CMD_NAME         = latex
-
-# The MAKEINDEX_CMD_NAME tag can be used to specify the command name to
-# generate index for LaTeX. If left blank `makeindex' will be used as the
-# default command name.
-
-MAKEINDEX_CMD_NAME     = makeindex
-
-# If the COMPACT_LATEX tag is set to YES Doxygen generates more compact
-# LaTeX documents. This may be useful for small projects and may help to
-# save some trees in general.
-
-COMPACT_LATEX          = NO
-
-# The PAPER_TYPE tag can be used to set the paper type that is used
-# by the printer. Possible values are: a4, a4wide, letter, legal and
-# executive. If left blank a4wide will be used.
-
-PAPER_TYPE             = a4wide
-
-# The EXTRA_PACKAGES tag can be to specify one or more names of LaTeX
-# packages that should be included in the LaTeX output.
-
-EXTRA_PACKAGES         =
-
-# The LATEX_HEADER tag can be used to specify a personal LaTeX header for
-# the generated latex document. The header should contain everything until
-# the first chapter. If it is left blank doxygen will generate a
-# standard header. Notice: only use this tag if you know what you are doing!
-
-LATEX_HEADER           =
-
-# If the PDF_HYPERLINKS tag is set to YES, the LaTeX that is generated
-# is prepared for conversion to pdf (using ps2pdf). The pdf file will
-# contain links (just like the HTML output) instead of page references
-# This makes the output suitable for online browsing using a pdf viewer.
-
-PDF_HYPERLINKS         = YES
-
-# If the USE_PDFLATEX tag is set to YES, pdflatex will be used instead of
-# plain latex in the generated Makefile. Set this option to YES to get a
-# higher quality PDF documentation.
-
-USE_PDFLATEX           = YES
-
-# If the LATEX_BATCHMODE tag is set to YES, doxygen will add the \\batchmode.
-# command to the generated LaTeX files. This will instruct LaTeX to keep
-# running if errors occur, instead of asking the user for help.
-# This option is also used when generating formulas in HTML.
-
-LATEX_BATCHMODE        = NO
-
-# If LATEX_HIDE_INDICES is set to YES then doxygen will not
-# include the index chapters (such as File Index, Compound Index, etc.)
-# in the output.
-
-LATEX_HIDE_INDICES     = NO
-
-# If LATEX_SOURCE_CODE is set to YES then doxygen will include source code with syntax highlighting in the LaTeX output. Note that which sources are shown also depends on other settings such as SOURCE_BROWSER.
-
-LATEX_SOURCE_CODE      = NO
-
-#---------------------------------------------------------------------------
-# configuration options related to the RTF output
-#---------------------------------------------------------------------------
-
-# If the GENERATE_RTF tag is set to YES Doxygen will generate RTF output
-# The RTF output is optimized for Word 97 and may not look very pretty with
-# other RTF readers or editors.
-
-GENERATE_RTF           = NO
-
-# The RTF_OUTPUT tag is used to specify where the RTF docs will be put.
-# If a relative path is entered the value of OUTPUT_DIRECTORY will be
-# put in front of it. If left blank `rtf' will be used as the default path.
-
-RTF_OUTPUT             = rtf
-
-# If the COMPACT_RTF tag is set to YES Doxygen generates more compact
-# RTF documents. This may be useful for small projects and may help to
-# save some trees in general.
-
-COMPACT_RTF            = NO
-
-# If the RTF_HYPERLINKS tag is set to YES, the RTF that is generated
-# will contain hyperlink fields. The RTF file will
-# contain links (just like the HTML output) instead of page references.
-# This makes the output suitable for online browsing using WORD or other
-# programs which support those fields.
-# Note: wordpad (write) and others do not support links.
-
-RTF_HYPERLINKS         = NO
-
-# Load stylesheet definitions from file. Syntax is similar to doxygen's
-# config file, i.e. a series of assignments. You only have to provide
-# replacements, missing definitions are set to their default value.
-
-RTF_STYLESHEET_FILE    =
-
-# Set optional variables used in the generation of an rtf document.
-# Syntax is similar to doxygen's config file.
-
-RTF_EXTENSIONS_FILE    =
-
-#---------------------------------------------------------------------------
-# configuration options related to the man page output
-#---------------------------------------------------------------------------
-
-# If the GENERATE_MAN tag is set to YES (the default) Doxygen will
-# generate man pages
-
-GENERATE_MAN           = YES
-
-# The MAN_OUTPUT tag is used to specify where the man pages will be put.
-# If a relative path is entered the value of OUTPUT_DIRECTORY will be
-# put in front of it. If left blank `man' will be used as the default path.
-
-MAN_OUTPUT             = man
-
-# The MAN_EXTENSION tag determines the extension that is added to
-# the generated man pages (default is the subroutine's section .3)
-
-MAN_EXTENSION          = .3
-
-# If the MAN_LINKS tag is set to YES and Doxygen generates man output,
-# then it will generate one additional man file for each entity
-# documented in the real man page(s). These additional files
-# only source the real man page, but without them the man command
-# would be unable to find the correct page. The default is NO.
-
-MAN_LINKS              = NO
-
-#---------------------------------------------------------------------------
-# configuration options related to the XML output
-#---------------------------------------------------------------------------
-
-# If the GENERATE_XML tag is set to YES Doxygen will
-# generate an XML file that captures the structure of
-# the code including all documentation.
-
-GENERATE_XML           = NO
-
-# The XML_OUTPUT tag is used to specify where the XML pages will be put.
-# If a relative path is entered the value of OUTPUT_DIRECTORY will be
-# put in front of it. If left blank `xml' will be used as the default path.
-
-XML_OUTPUT             = xml
-
-# The XML_SCHEMA tag can be used to specify an XML schema,
-# which can be used by a validating XML parser to check the
-# syntax of the XML files.
-
-XML_SCHEMA             =
-
-# The XML_DTD tag can be used to specify an XML DTD,
-# which can be used by a validating XML parser to check the
-# syntax of the XML files.
-
-XML_DTD                =
-
-# If the XML_PROGRAMLISTING tag is set to YES Doxygen will
-# dump the program listings (including syntax highlighting
-# and cross-referencing information) to the XML output. Note that
-# enabling this will significantly increase the size of the XML output.
-
-XML_PROGRAMLISTING     = YES
-
-#---------------------------------------------------------------------------
-# configuration options for the AutoGen Definitions output
-#---------------------------------------------------------------------------
-
-# If the GENERATE_AUTOGEN_DEF tag is set to YES Doxygen will
-# generate an AutoGen Definitions (see autogen.sf.net) file
-# that captures the structure of the code including all
-# documentation. Note that this feature is still experimental
-# and incomplete at the moment.
-
-GENERATE_AUTOGEN_DEF   = NO
-
-#---------------------------------------------------------------------------
-# configuration options related to the Perl module output
-#---------------------------------------------------------------------------
-
-# If the GENERATE_PERLMOD tag is set to YES Doxygen will
-# generate a Perl module file that captures the structure of
-# the code including all documentation. Note that this
-# feature is still experimental and incomplete at the
-# moment.
-
-GENERATE_PERLMOD       = NO
-
-# If the PERLMOD_LATEX tag is set to YES Doxygen will generate
-# the necessary Makefile rules, Perl scripts and LaTeX code to be able
-# to generate PDF and DVI output from the Perl module output.
-
-PERLMOD_LATEX          = NO
-
-# If the PERLMOD_PRETTY tag is set to YES the Perl module output will be
-# nicely formatted so it can be parsed by a human reader.
-# This is useful
-# if you want to understand what is going on.
-# On the other hand, if this
-# tag is set to NO the size of the Perl module output will be much smaller
-# and Perl will parse it just the same.
-
-PERLMOD_PRETTY         = YES
-
-# The names of the make variables in the generated doxyrules.make file
-# are prefixed with the string contained in PERLMOD_MAKEVAR_PREFIX.
-# This is useful so different doxyrules.make files included by the same
-# Makefile don't overwrite each other's variables.
-
-PERLMOD_MAKEVAR_PREFIX =
-
-#---------------------------------------------------------------------------
-# Configuration options related to the preprocessor
-#---------------------------------------------------------------------------
-
-# If the ENABLE_PREPROCESSING tag is set to YES (the default) Doxygen will
-# evaluate all C-preprocessor directives found in the sources and include
-# files.
-
-ENABLE_PREPROCESSING   = YES
-
-# If the MACRO_EXPANSION tag is set to YES Doxygen will expand all macro
-# names in the source code. If set to NO (the default) only conditional
-# compilation will be performed. Macro expansion can be done in a controlled
-# way by setting EXPAND_ONLY_PREDEF to YES.
-
-MACRO_EXPANSION        = YES
-
-# If the EXPAND_ONLY_PREDEF and MACRO_EXPANSION tags are both set to YES
-# then the macro expansion is limited to the macros specified with the
-# PREDEFINED and EXPAND_AS_DEFINED tags.
-
-EXPAND_ONLY_PREDEF     = YES
-
-# If the SEARCH_INCLUDES tag is set to YES (the default) the includes files
-# in the INCLUDE_PATH (see below) will be search if a #include is found.
-
-SEARCH_INCLUDES        = YES
-
-# The INCLUDE_PATH tag can be used to specify one or more directories that
-# contain include files that are not input files but should be processed by
-# the preprocessor.
-
-INCLUDE_PATH           =
-
-# You can use the INCLUDE_FILE_PATTERNS tag to specify one or more wildcard
-# patterns (like *.h and *.hpp) to filter out the header-files in the
-# directories. If left blank, the patterns specified with FILE_PATTERNS will
-# be used.
-
-INCLUDE_FILE_PATTERNS  =
-
-# The PREDEFINED tag can be used to specify one or more macro names that
-# are defined before the preprocessor is started (similar to the -D option of
-# gcc). The argument of the tag is a list of macros of the form: name
-# or name=definition (no spaces). If the definition and the = are
-# omitted =1 is assumed. To prevent a macro definition from being
-# undefined via #undef or recursively expanded use the := operator
-# instead of the = operator.
-
-PREDEFINED             = DOXYGEN PRINTF_ATTRIBUTE(x,y)=
-
-# If the MACRO_EXPANSION and EXPAND_ONLY_PREDEF tags are set to YES then
-# this tag can be used to specify a list of macro names that should be expanded.
-# The macro definition that is found in the sources will be used.
-# Use the PREDEFINED tag if you want to use a different macro definition.
-
-EXPAND_AS_DEFINED      =
-
-# If the SKIP_FUNCTION_MACROS tag is set to YES (the default) then
-# doxygen's preprocessor will remove all function-like macros that are alone
-# on a line, have an all uppercase name, and do not end with a semicolon. Such
-# function macros are typically used for boiler-plate code, and will confuse
-# the parser if not removed.
-
-SKIP_FUNCTION_MACROS   = YES
-
-#---------------------------------------------------------------------------
-# Configuration::additions related to external references
-#---------------------------------------------------------------------------
-
-# The TAGFILES option can be used to specify one or more tagfiles.
-# Optionally an initial location of the external documentation
-# can be added for each tagfile. The format of a tag file without
-# this location is as follows:
-#
-# TAGFILES = file1 file2 ...
-# Adding location for the tag files is done as follows:
-#
-# TAGFILES = file1=loc1 "file2 = loc2" ...
-# where "loc1" and "loc2" can be relative or absolute paths or
-# URLs. If a location is present for each tag, the installdox tool
-# does not have to be run to correct the links.
-# Note that each tag file must have a unique name
-# (where the name does NOT include the path)
-# If a tag file is not located in the directory in which doxygen
-# is run, you must also specify the path to the tagfile here.
-
-TAGFILES               =
-
-# When a file name is specified after GENERATE_TAGFILE, doxygen will create
-# a tag file that is based on the input files it reads.
-
-GENERATE_TAGFILE       =
-
-# If the ALLEXTERNALS tag is set to YES all external classes will be listed
-# in the class index. If set to NO only the inherited external classes
-# will be listed.
-
-ALLEXTERNALS           = NO
-
-# If the EXTERNAL_GROUPS tag is set to YES all external groups will be listed
-# in the modules index. If set to NO, only the current project's groups will
-# be listed.
-
-EXTERNAL_GROUPS        = YES
-
-# The PERL_PATH should be the absolute path and name of the perl script
-# interpreter (i.e. the result of `which perl').
-
-PERL_PATH              = /usr/bin/perl
-
-#---------------------------------------------------------------------------
-# Configuration options related to the dot tool
-#---------------------------------------------------------------------------
-
-# If the CLASS_DIAGRAMS tag is set to YES (the default) Doxygen will
-# generate a inheritance diagram (in HTML, RTF and LaTeX) for classes with base
-# or super classes. Setting the tag to NO turns the diagrams off. Note that
-# this option is superseded by the HAVE_DOT option below. This is only a
-# fallback. It is recommended to install and use dot, since it yields more
-# powerful graphs.
-
-CLASS_DIAGRAMS         = YES
-
-# You can define message sequence charts within doxygen comments using the \msc
-# command. Doxygen will then run the mscgen tool (see
-# http://www.mcternan.me.uk/mscgen/) to produce the chart and insert it in the
-# documentation. The MSCGEN_PATH tag allows you to specify the directory where
-# the mscgen tool resides. If left empty the tool is assumed to be found in the
-# default search path.
-
-MSCGEN_PATH            =
-
-# If set to YES, the inheritance and collaboration graphs will hide
-# inheritance and usage relations if the target is undocumented
-# or is not a class.
-
-HIDE_UNDOC_RELATIONS   = YES
-
-# If you set the HAVE_DOT tag to YES then doxygen will assume the dot tool is
-# available from the path. This tool is part of Graphviz, a graph visualization
-# toolkit from AT&T and Lucent Bell Labs. The other options in this section
-# have no effect if this option is set to NO (the default)
-
-HAVE_DOT               = NO
-
-# By default doxygen will write a font called FreeSans.ttf to the output
-# directory and reference it in all dot files that doxygen generates. This
-# font does not include all possible unicode characters however, so when you need
-# these (or just want a differently looking font) you can specify the font name
-# using DOT_FONTNAME. You need need to make sure dot is able to find the font,
-# which can be done by putting it in a standard location or by setting the
-# DOTFONTPATH environment variable or by setting DOT_FONTPATH to the directory
-# containing the font.
-
-DOT_FONTNAME           = FreeSans
-
-# The DOT_FONTSIZE tag can be used to set the size of the font of dot graphs.
-# The default size is 10pt.
-
-DOT_FONTSIZE           = 10
-
-# By default doxygen will tell dot to use the output directory to look for the
-# FreeSans.ttf font (which doxygen will put there itself). If you specify a
-# different font using DOT_FONTNAME you can set the path where dot
-# can find it using this tag.
-
-DOT_FONTPATH           =
-
-# If the CLASS_GRAPH and HAVE_DOT tags are set to YES then doxygen
-# will generate a graph for each documented class showing the direct and
-# indirect inheritance relations. Setting this tag to YES will force the
-# the CLASS_DIAGRAMS tag to NO.
-
-CLASS_GRAPH            = YES
-
-# If the COLLABORATION_GRAPH and HAVE_DOT tags are set to YES then doxygen
-# will generate a graph for each documented class showing the direct and
-# indirect implementation dependencies (inheritance, containment, and
-# class references variables) of the class with other documented classes.
-
-COLLABORATION_GRAPH    = YES
-
-# If the GROUP_GRAPHS and HAVE_DOT tags are set to YES then doxygen
-# will generate a graph for groups, showing the direct groups dependencies
-
-GROUP_GRAPHS           = YES
-
-# If the UML_LOOK tag is set to YES doxygen will generate inheritance and
-# collaboration diagrams in a style similar to the OMG's Unified Modeling
-# Language.
-
-UML_LOOK               = NO
-
-# If set to YES, the inheritance and collaboration graphs will show the
-# relations between templates and their instances.
-
-TEMPLATE_RELATIONS     = NO
-
-# If the ENABLE_PREPROCESSING, SEARCH_INCLUDES, INCLUDE_GRAPH, and HAVE_DOT
-# tags are set to YES then doxygen will generate a graph for each documented
-# file showing the direct and indirect include dependencies of the file with
-# other documented files.
-
-INCLUDE_GRAPH          = YES
-
-# If the ENABLE_PREPROCESSING, SEARCH_INCLUDES, INCLUDED_BY_GRAPH, and
-# HAVE_DOT tags are set to YES then doxygen will generate a graph for each
-# documented header file showing the documented files that directly or
-# indirectly include this file.
-
-INCLUDED_BY_GRAPH      = YES
-
-# If the CALL_GRAPH and HAVE_DOT options are set to YES then
-# doxygen will generate a call dependency graph for every global function
-# or class method. Note that enabling this option will significantly increase
-# the time of a run. So in most cases it will be better to enable call graphs
-# for selected functions only using the \callgraph command.
-
-CALL_GRAPH             = NO
-
-# If the CALLER_GRAPH and HAVE_DOT tags are set to YES then
-# doxygen will generate a caller dependency graph for every global function
-# or class method. Note that enabling this option will significantly increase
-# the time of a run. So in most cases it will be better to enable caller
-# graphs for selected functions only using the \callergraph command.
-
-CALLER_GRAPH           = NO
-
-# If the GRAPHICAL_HIERARCHY and HAVE_DOT tags are set to YES then doxygen
-# will graphical hierarchy of all classes instead of a textual one.
-
-GRAPHICAL_HIERARCHY    = YES
-
-# If the DIRECTORY_GRAPH, SHOW_DIRECTORIES and HAVE_DOT tags are set to YES
-# then doxygen will show the dependencies a directory has on other directories
-# in a graphical way. The dependency relations are determined by the #include
-# relations between the files in the directories.
-
-DIRECTORY_GRAPH        = YES
-
-# The DOT_IMAGE_FORMAT tag can be used to set the image format of the images
-# generated by dot. Possible values are png, jpg, or gif
-# If left blank png will be used.
-
-DOT_IMAGE_FORMAT       = png
-
-# The tag DOT_PATH can be used to specify the path where the dot tool can be
-# found. If left blank, it is assumed the dot tool can be found in the path.
-
-DOT_PATH               =
-
-# The DOTFILE_DIRS tag can be used to specify one or more directories that
-# contain dot files that are included in the documentation (see the
-# \dotfile command).
-
-DOTFILE_DIRS           =
-
-# The DOT_GRAPH_MAX_NODES tag can be used to set the maximum number of
-# nodes that will be shown in the graph. If the number of nodes in a graph
-# becomes larger than this value, doxygen will truncate the graph, which is
-# visualized by representing a node as a red box. Note that doxygen if the
-# number of direct children of the root node in a graph is already larger than
-# DOT_GRAPH_MAX_NODES then the graph will not be shown at all. Also note
-# that the size of a graph can be further restricted by MAX_DOT_GRAPH_DEPTH.
-
-DOT_GRAPH_MAX_NODES    = 50
-
-# The MAX_DOT_GRAPH_DEPTH tag can be used to set the maximum depth of the
-# graphs generated by dot. A depth value of 3 means that only nodes reachable
-# from the root by following a path via at most 3 edges will be shown. Nodes
-# that lay further from the root node will be omitted. Note that setting this
-# option to 1 or 2 may greatly reduce the computation time needed for large
-# code bases. Also note that the size of a graph can be further restricted by
-# DOT_GRAPH_MAX_NODES. Using a depth of 0 means no depth restriction.
-
-MAX_DOT_GRAPH_DEPTH    = 0
-
-# Set the DOT_TRANSPARENT tag to YES to generate images with a transparent
-# background. This is disabled by default, because dot on Windows does not
-# seem to support this out of the box. Warning: Depending on the platform used,
-# enabling this option may lead to badly anti-aliased labels on the edges of
-# a graph (i.e. they become hard to read).
-
-DOT_TRANSPARENT        = YES
-
-# Set the DOT_MULTI_TARGETS tag to YES allow dot to generate multiple output
-# files in one run (i.e. multiple -o and -T options on the command line). This
-# makes dot run faster, but since only newer versions of dot (>1.8.10)
-# support this, this feature is disabled by default.
-
-DOT_MULTI_TARGETS      = NO
-
-# If the GENERATE_LEGEND tag is set to YES (the default) Doxygen will
-# generate a legend page explaining the meaning of the various boxes and
-# arrows in the dot generated graphs.
-
-GENERATE_LEGEND        = YES
-
-# If the DOT_CLEANUP tag is set to YES (the default) Doxygen will
-# remove the intermediate dot files that are used to generate
-# the various graphs.
-
-DOT_CLEANUP            = YES
diff --git a/lib/talloc/install-sh b/lib/talloc/install-sh
deleted file mode 100755
index 5871924..0000000
--- a/lib/talloc/install-sh
+++ /dev/null
@@ -1,238 +0,0 @@
-#! /bin/sh
-#
-# install - install a program, script, or datafile
-# This comes from X11R5.
-#
-# Calling this script install-sh is preferred over install.sh, to prevent
-# `make' implicit rules from creating a file called install from it
-# when there is no Makefile.
-#
-# This script is compatible with the BSD install script, but was written
-# from scratch.
-#
-
-
-# set DOITPROG to echo to test this script
-
-# Don't use :- since 4.3BSD and earlier shells don't like it.
-doit="${DOITPROG-}"
-
-
-# put in absolute paths if you don't have them in your path; or use env. vars.
-
-mvprog="${MVPROG-mv}"
-cpprog="${CPPROG-cp}"
-chmodprog="${CHMODPROG-chmod}"
-chownprog="${CHOWNPROG-chown}"
-chgrpprog="${CHGRPPROG-chgrp}"
-stripprog="${STRIPPROG-strip}"
-rmprog="${RMPROG-rm}"
-mkdirprog="${MKDIRPROG-mkdir}"
-
-transformbasename=""
-transform_arg=""
-instcmd="$mvprog"
-chmodcmd="$chmodprog 0755"
-chowncmd=""
-chgrpcmd=""
-stripcmd=""
-rmcmd="$rmprog -f"
-mvcmd="$mvprog"
-src=""
-dst=""
-dir_arg=""
-
-while [ x"$1" != x ]; do
-    case $1 in
-	-c) instcmd="$cpprog"
-	    shift
-	    continue;;
-
-	-d) dir_arg=true
-	    shift
-	    continue;;
-
-	-m) chmodcmd="$chmodprog $2"
-	    shift
-	    shift
-	    continue;;
-
-	-o) chowncmd="$chownprog $2"
-	    shift
-	    shift
-	    continue;;
-
-	-g) chgrpcmd="$chgrpprog $2"
-	    shift
-	    shift
-	    continue;;
-
-	-s) stripcmd="$stripprog"
-	    shift
-	    continue;;
-
-	-t=*) transformarg=`echo $1 | sed 's/-t=//'`
-	    shift
-	    continue;;
-
-	-b=*) transformbasename=`echo $1 | sed 's/-b=//'`
-	    shift
-	    continue;;
-
-	*)  if [ x"$src" = x ]
-	    then
-		src=$1
-	    else
-		# this colon is to work around a 386BSD /bin/sh bug
-		:
-		dst=$1
-	    fi
-	    shift
-	    continue;;
-    esac
-done
-
-if [ x"$src" = x ]
-then
-	echo "install:	no input file specified"
-	exit 1
-else
-	true
-fi
-
-if [ x"$dir_arg" != x ]; then
-	dst=$src
-	src=""
-	
-	if [ -d $dst ]; then
-		instcmd=:
-	else
-		instcmd=mkdir
-	fi
-else
-
-# Waiting for this to be detected by the "$instcmd $src $dsttmp" command
-# might cause directories to be created, which would be especially bad 
-# if $src (and thus $dsttmp) contains '*'.
-
-	if [ -f $src -o -d $src ]
-	then
-		true
-	else
-		echo "install:  $src does not exist"
-		exit 1
-	fi
-	
-	if [ x"$dst" = x ]
-	then
-		echo "install:	no destination specified"
-		exit 1
-	else
-		true
-	fi
-
-# If destination is a directory, append the input filename; if your system
-# does not like double slashes in filenames, you may need to add some logic
-
-	if [ -d $dst ]
-	then
-		dst="$dst"/`basename $src`
-	else
-		true
-	fi
-fi
-
-## this sed command emulates the dirname command
-dstdir=`echo $dst | sed -e 's,[^/]*$,,;s,/$,,;s,^$,.,'`
-
-# Make sure that the destination directory exists.
-#  this part is taken from Noah Friedman's mkinstalldirs script
-
-# Skip lots of stat calls in the usual case.
-if [ ! -d "$dstdir" ]; then
-defaultIFS='	
-'
-IFS="${IFS-${defaultIFS}}"
-
-oIFS="${IFS}"
-# Some sh's can't handle IFS=/ for some reason.
-IFS='%'
-set - `echo ${dstdir} | sed -e 's@/@%@g' -e 's@^%@/@'`
-IFS="${oIFS}"
-
-pathcomp=''
-
-while [ $# -ne 0 ] ; do
-	pathcomp="${pathcomp}${1}"
-	shift
-
-	if [ ! -d "${pathcomp}" ] ;
-        then
-		$mkdirprog "${pathcomp}"
-	else
-		true
-	fi
-
-	pathcomp="${pathcomp}/"
-done
-fi
-
-if [ x"$dir_arg" != x ]
-then
-	$doit $instcmd $dst &&
-
-	if [ x"$chowncmd" != x ]; then $doit $chowncmd $dst; else true ; fi &&
-	if [ x"$chgrpcmd" != x ]; then $doit $chgrpcmd $dst; else true ; fi &&
-	if [ x"$stripcmd" != x ]; then $doit $stripcmd $dst; else true ; fi &&
-	if [ x"$chmodcmd" != x ]; then $doit $chmodcmd $dst; else true ; fi
-else
-
-# If we're going to rename the final executable, determine the name now.
-
-	if [ x"$transformarg" = x ] 
-	then
-		dstfile=`basename $dst`
-	else
-		dstfile=`basename $dst $transformbasename | 
-			sed $transformarg`$transformbasename
-	fi
-
-# don't allow the sed command to completely eliminate the filename
-
-	if [ x"$dstfile" = x ] 
-	then
-		dstfile=`basename $dst`
-	else
-		true
-	fi
-
-# Make a temp file name in the proper directory.
-
-	dsttmp=$dstdir/#inst.$$#
-
-# Move or copy the file name to the temp name
-
-	$doit $instcmd $src $dsttmp &&
-
-	trap "rm -f ${dsttmp}" 0 &&
-
-# and set any options; do chmod last to preserve setuid bits
-
-# If any of these fail, we abort the whole thing.  If we want to
-# ignore errors from any of these, just make sure not to ignore
-# errors from the above "$doit $instcmd $src $dsttmp" command.
-
-	if [ x"$chowncmd" != x ]; then $doit $chowncmd $dsttmp; else true;fi &&
-	if [ x"$chgrpcmd" != x ]; then $doit $chgrpcmd $dsttmp; else true;fi &&
-	if [ x"$stripcmd" != x ]; then $doit $stripcmd $dsttmp; else true;fi &&
-	if [ x"$chmodcmd" != x ]; then $doit $chmodcmd $dsttmp; else true;fi &&
-
-# Now rename the file to the real destination.
-
-	$doit $rmcmd -f $dstdir/$dstfile &&
-	$doit $mvcmd $dsttmp $dstdir/$dstfile 
-
-fi &&
-
-
-exit 0
diff --git a/lib/talloc/libtalloc.m4 b/lib/talloc/libtalloc.m4
deleted file mode 100644
index 65227d8..0000000
--- a/lib/talloc/libtalloc.m4
+++ /dev/null
@@ -1,63 +0,0 @@
-dnl Check to see if we should use the included talloc
-
-INCLUDED_TALLOC=auto
-AC_ARG_WITH(included-talloc,
-    [AC_HELP_STRING([--with-included-talloc], [use bundled talloc library, not from system])],
-    [ INCLUDED_TALLOC=$withval ])
-
-AC_SUBST(TALLOC_LIBS)
-AC_SUBST(TALLOC_CFLAGS)
-
-if test x"$INCLUDED_TALLOC" != x"yes" ; then
-    AC_CHECK_HEADERS(talloc.h)
-    AC_CHECK_LIB(talloc, talloc_init, [ TALLOC_LIBS="-ltalloc" ])
-    if test x"$ac_cv_header_talloc_h" = x"no" -o x"$ac_cv_lib_talloc_talloc_init" = x"no" ; then
-        INCLUDED_TALLOC=yes
-        TALLOC_CFLAGS=""
-    else
-        INCLUDED_TALLOC=no
-    fi
-fi
-
-AC_MSG_CHECKING(whether to use included talloc)
-AC_MSG_RESULT($INCLUDED_TALLOC)
-if test x"$INCLUDED_TALLOC" != x"no" ; then
-    dnl find the talloc sources. This is meant to work both for 
-    dnl talloc standalone builds, and builds of packages using talloc
-    tallocdir=""
-    tallocpaths=". lib/talloc talloc ../talloc ../lib/talloc"
-    for d in $tallocpaths; do
-    	if test -f "$srcdir/$d/talloc.c"; then
-    		tallocdir="$d"
-    		AC_SUBST(tallocdir)
-    		break
-    	fi
-    done
-    if test x"$tallocdir" = "x"; then
-        AC_MSG_ERROR([cannot find talloc source in $tallocpaths])
-    fi
-    TALLOC_OBJ="talloc.o"
-    AC_SUBST(TALLOC_OBJ)
-
-    TALLOC_CFLAGS="-I$srcdir/$tallocdir"
-    AC_SUBST(TALLOC_CFLAGS)
-
-    TALLOC_LIBS=""
-    AC_SUBST(TALLOC_LIBS)
-fi
-
-AC_CHECK_SIZEOF(size_t,cross)
-AC_CHECK_SIZEOF(void *,cross)
-
-if test $ac_cv_sizeof_size_t -lt $ac_cv_sizeof_void_p; then
-	AC_WARN([size_t cannot represent the amount of used memory of a process])
-	AC_WARN([please report this to <samba-technical at samba.org>])
-	AC_WARN([sizeof(size_t) = $ac_cv_sizeof_size_t])
-	AC_WARN([sizeof(void *) = $ac_cv_sizeof_void_p])
-	AC_ERROR([sizeof(size_t) < sizeof(void *)])
-fi
-
-if test x"$VERSIONSCRIPT" != "x"; then
-    EXPORTSFILE=talloc.exports
-    AC_SUBST(EXPORTSFILE)
-fi
diff --git a/lib/talloc/talloc.3.xml b/lib/talloc/talloc.3.xml
deleted file mode 100644
index 7a2f27e..0000000
--- a/lib/talloc/talloc.3.xml
+++ /dev/null
@@ -1,801 +0,0 @@
-<?xml version="1.0"?>
-<!DOCTYPE refentry PUBLIC "-//OASIS//DTD DocBook XML V4.2//EN" "http://www.oasis-open.org/docbook/xml/4.2/docbookx.dtd">
-<refentry>
-  <refmeta>
-    <refentrytitle>talloc</refentrytitle>
-    <manvolnum>3</manvolnum>
-  </refmeta>
-  <refnamediv>
-    <refname>talloc</refname>
-<refpurpose>hierarchical reference counted memory pool system with destructors</refpurpose>
-  </refnamediv>
-  <refsynopsisdiv>
-<synopsis>#include <talloc.h></synopsis>
-  </refsynopsisdiv>
-  <refsect1><title>DESCRIPTION</title>
-    <para>
-      If you are used to talloc from Samba3 then please read this
-      carefully, as talloc has changed a lot.
-    </para>
-    <para>
-      The new talloc is a hierarchical, reference counted memory pool
-      system with destructors.	Quite a mouthful really, but not too bad
-      once you get used to it.
-    </para>
-    <para>
-      Perhaps the biggest change from Samba3 is that there is no
-      distinction between a "talloc context" and a "talloc pointer".  Any
-      pointer returned from talloc() is itself a valid talloc context. 
-      This means you can do this:
-    </para>
-    <programlisting>
-    struct foo *X = talloc(mem_ctx, struct foo);
-    X->name = talloc_strdup(X, "foo");
-    </programlisting>
-    <para>
-      and the pointer <literal role="code">X->name</literal>
-      would be a "child" of the talloc context <literal
-      role="code">X</literal> which is itself a child of
-      <literal role="code">mem_ctx</literal>.  So if you do
-      <literal role="code">talloc_free(mem_ctx)</literal> then
-      it is all destroyed, whereas if you do <literal
-      role="code">talloc_free(X)</literal> then just <literal
-      role="code">X</literal> and <literal
-      role="code">X->name</literal> are destroyed, and if
-      you do <literal
-      role="code">talloc_free(X->name)</literal> then just
-      the name element of <literal role="code">X</literal> is
-      destroyed.
-    </para>
-    <para>
-      If you think about this, then what this effectively gives you is an
-      n-ary tree, where you can free any part of the tree with
-      talloc_free().
-    </para>
-    <para>
-      If you find this confusing, then I suggest you run the <literal
-      role="code">testsuite</literal> program to watch talloc
-      in action.  You may also like to add your own tests to <literal
-      role="code">testsuite.c</literal> to clarify how some
-      particular situation is handled.
-    </para>
-  </refsect1>
-  <refsect1><title>TALLOC API</title>
-    <para>
-      The following is a complete guide to the talloc API. Read it all at
-      least twice.
-    </para>
-    <refsect2><title>(type *)talloc(const void *ctx, type);</title>
-        <para>
-	  The talloc() macro is the core of the talloc library.  It takes a
-	  memory <emphasis role="italic">ctx</emphasis> and a <emphasis
-	  role="italic">type</emphasis>, and returns a pointer to a new
-	  area of memory of the given <emphasis
-	  role="italic">type</emphasis>.
-        </para>
-        <para>
-	  The returned pointer is itself a talloc context, so you can use
-	  it as the <emphasis role="italic">ctx</emphasis> argument to more
-	  calls to talloc() if you wish.
-        </para>
-        <para>
-	  The returned pointer is a "child" of the supplied context.  This
-	  means that if you talloc_free() the <emphasis
-	  role="italic">ctx</emphasis> then the new child disappears as
-	  well.  Alternatively you can free just the child.
-        </para>
-        <para>
-	  The <emphasis role="italic">ctx</emphasis> argument to talloc()
-	  can be NULL, in which case a new top level context is created.
-        </para>
-    </refsect2>
-    <refsect2><title>void *talloc_size(const void *ctx, size_t size);</title>
-        <para>
-	  The function talloc_size() should be used when you don't have a
-	  convenient type to pass to talloc().	Unlike talloc(), it is not
-	  type safe (as it returns a void *), so you are on your own for
-	  type checking.
-        </para>
-    </refsect2>
-    <refsect2><title>(typeof(ptr)) talloc_ptrtype(const void *ctx, ptr);</title>
-        <para>
-	  The talloc_ptrtype() macro should be used when you have a pointer and
-	  want to allocate memory to point at with this pointer. When compiling
-	  with gcc >= 3 it is typesafe. Note this is a wrapper of talloc_size()
-	  and talloc_get_name() will return the current location in the source file.
-	  and not the type.
-        </para>
-    </refsect2>
-    <refsect2><title>int talloc_free(void *ptr);</title>
-        <para>
-	  The talloc_free() function frees a piece of talloc memory, and
-	  all its children.  You can call talloc_free() on any pointer
-	  returned by talloc().
-        </para>
-        <para>
-	  The return value of talloc_free() indicates success or failure,
-	  with 0 returned for success and -1 for failure.  The only
-	  possible failure condition is if <emphasis
-	  role="italic">ptr</emphasis> had a destructor attached to it and
-	  the destructor returned -1.  See <link
-	  linkend="talloc_set_destructor"><quote>talloc_set_destructor()</quote></link>
-	  for details on destructors.
-        </para>
-        <para>
-	  If this pointer has an additional parent when talloc_free() is
-	  called then the memory is not actually released, but instead the
-	  most recently established parent is destroyed.  See <link
-	  linkend="talloc_reference"><quote>talloc_reference()</quote></link>
-	  for details on establishing additional parents.
-        </para>
-        <para>
-	  For more control on which parent is removed, see <link
-	  linkend="talloc_unlink"><quote>talloc_unlink()</quote></link>.
-        </para>
-        <para>
-	  talloc_free() operates recursively on its children.
-        </para>
-	<para>
-	  From the 2.0 version of talloc, as a special case,
-	  talloc_free() is refused on pointers that have more than one
-	  parent, as talloc would have no way of knowing which parent
-	  should be removed. To free a pointer that has more than one
-	  parent please use talloc_unlink().
-	</para>
-	<para>
-	  To help you find problems in your code caused by this behaviour, if
-	  you do try and free a pointer with more than one parent then the
-	  talloc logging function will be called to give output like this:
-	</para>
-	<para>
-	  <screen format="linespecific">
-	    ERROR: talloc_free with references at some_dir/source/foo.c:123
-		reference at some_dir/source/other.c:325
-		reference at some_dir/source/third.c:121
-	  </screen>
-	</para>
-	<para>
-	  Please see the documentation for talloc_set_log_fn() and
-	  talloc_set_log_stderr() for more information on talloc logging
-	  functions.
-	</para>
-    </refsect2>
-    <refsect2 id="talloc_reference"><title>void *talloc_reference(const void *ctx, const void *ptr);</title>
-        <para>
-	  The talloc_reference() function makes <emphasis
-	  role="italic">ctx</emphasis> an additional parent of <emphasis
-	  role="italic">ptr</emphasis>.
-        </para>
-        <para>
-	  The return value of talloc_reference() is always the original
-	  pointer <emphasis role="italic">ptr</emphasis>, unless talloc ran
-	  out of memory in creating the reference in which case it will
-	  return NULL (each additional reference consumes around 48 bytes
-	  of memory on intel x86 platforms).
-        </para>
-        <para>
-	  If <emphasis role="italic">ptr</emphasis> is NULL, then the
-	  function is a no-op, and simply returns NULL.
-        </para>
-        <para>
-	  After creating a reference you can free it in one of the
-	  following ways:
-        </para>
-      <para>
-        <itemizedlist>
-          <listitem>
-            <para>
-	      you can talloc_free() any parent of the original pointer. 
-	      That will reduce the number of parents of this pointer by 1,
-	      and will cause this pointer to be freed if it runs out of
-	      parents.
-            </para>
-          </listitem>
-          <listitem>
-            <para>
-	      you can talloc_free() the pointer itself.  That will destroy
-	      the most recently established parent to the pointer and leave
-	      the pointer as a child of its current parent.
-            </para>
-          </listitem>
-        </itemizedlist>
-      </para>
-      <para>
-	For more control on which parent to remove, see <link
-	linkend="talloc_unlink"><quote>talloc_unlink()</quote></link>.
-      </para>
-    </refsect2>
-    <refsect2 id="talloc_unlink"><title>int talloc_unlink(const void *ctx, const void *ptr);</title>
-        <para>
-	  The talloc_unlink() function removes a specific parent from
-	  <emphasis role="italic">ptr</emphasis>. The <emphasis
-	  role="italic">ctx</emphasis> passed must either be a context used
-	  in talloc_reference() with this pointer, or must be a direct
-	  parent of ptr.
-        </para>
-        <para>
-	  Note that if the parent has already been removed using
-	  talloc_free() then this function will fail and will return -1. 
-	  Likewise, if <emphasis role="italic">ptr</emphasis> is NULL, then
-	  the function will make no modifications and return -1.
-        </para>
-        <para>
-	  Usually you can just use talloc_free() instead of
-	  talloc_unlink(), but sometimes it is useful to have the
-	  additional control on which parent is removed.
-        </para>
-    </refsect2>
-    <refsect2 id="talloc_set_destructor"><title>void talloc_set_destructor(const void *ptr, int (*destructor)(void *));</title>
-        <para>
-	  The function talloc_set_destructor() sets the <emphasis
-	  role="italic">destructor</emphasis> for the pointer <emphasis
-	  role="italic">ptr</emphasis>.  A <emphasis
-	  role="italic">destructor</emphasis> is a function that is called
-	  when the memory used by a pointer is about to be released.  The
-	  destructor receives <emphasis role="italic">ptr</emphasis> as an
-	  argument, and should return 0 for success and -1 for failure.
-        </para>
-        <para>
-	  The <emphasis role="italic">destructor</emphasis> can do anything
-	  it wants to, including freeing other pieces of memory.  A common
-	  use for destructors is to clean up operating system resources
-	  (such as open file descriptors) contained in the structure the
-	  destructor is placed on.
-        </para>
-        <para>
-	  You can only place one destructor on a pointer.  If you need more
-	  than one destructor then you can create a zero-length child of
-	  the pointer and place an additional destructor on that.
-        </para>
-        <para>
-	  To remove a destructor call talloc_set_destructor() with NULL for
-	  the destructor.
-        </para>
-        <para>
-	  If your destructor attempts to talloc_free() the pointer that it
-	  is the destructor for then talloc_free() will return -1 and the
-	  free will be ignored.  This would be a pointless operation
-	  anyway, as the destructor is only called when the memory is just
-	  about to go away.
-        </para>
-    </refsect2>
-    <refsect2><title>int talloc_increase_ref_count(const void *<emphasis role="italic">ptr</emphasis>);</title>
-        <para>
-	  The talloc_increase_ref_count(<emphasis
-	  role="italic">ptr</emphasis>) function is exactly equivalent to:
-        </para>
-        <programlisting>talloc_reference(NULL, ptr);</programlisting>
-        <para>
-	  You can use either syntax, depending on which you think is
-	  clearer in your code.
-        </para>
-        <para>
-	  It returns 0 on success and -1 on failure.
-        </para>
-    </refsect2>
-    <refsect2><title>size_t talloc_reference_count(const void *<emphasis role="italic">ptr</emphasis>);</title>
-        <para>
-	  Return the number of references to the pointer.
-        </para>
-    </refsect2>
-    <refsect2 id="talloc_set_name"><title>void talloc_set_name(const void *ptr, const char *fmt, ...);</title>
-        <para>
-	  Each talloc pointer has a "name".  The name is used principally
-	  for debugging purposes, although it is also possible to set and
-	  get the name on a pointer in as a way of "marking" pointers in
-	  your code.
-        </para>
-        <para>
-	  The main use for names on pointer is for "talloc reports".  See
-	  <link
-	  linkend="talloc_report"><quote>talloc_report_depth_cb()</quote></link>,
-	  <link
-	  linkend="talloc_report"><quote>talloc_report_depth_file()</quote></link>,
-	  <link
-	  linkend="talloc_report"><quote>talloc_report()</quote></link>
-	  <link
-	  linkend="talloc_report"><quote>talloc_report()</quote></link>
-	  and <link
-	  linkend="talloc_report_full"><quote>talloc_report_full()</quote></link>
-	  for details.	Also see <link
-	  linkend="talloc_enable_leak_report"><quote>talloc_enable_leak_report()</quote></link>
-	  and <link
-	  linkend="talloc_enable_leak_report_full"><quote>talloc_enable_leak_report_full()</quote></link>.
-        </para>
-        <para>
-	  The talloc_set_name() function allocates memory as a child of the
-	  pointer.  It is logically equivalent to:
-        </para>
-        <programlisting>talloc_set_name_const(ptr, talloc_asprintf(ptr, fmt, ...));</programlisting>
-        <para>
-	  Note that multiple calls to talloc_set_name() will allocate more
-	  memory without releasing the name.  All of the memory is released
-	  when the ptr is freed using talloc_free().
-        </para>
-    </refsect2>
-    <refsect2><title>void talloc_set_name_const(const void *<emphasis role="italic">ptr</emphasis>, const char *<emphasis role="italic">name</emphasis>);</title>
-        <para>
-	  The function talloc_set_name_const() is just like
-	  talloc_set_name(), but it takes a string constant, and is much
-	  faster.  It is extensively used by the "auto naming" macros, such
-	  as talloc_p().
-        </para>
-        <para>
-	  This function does not allocate any memory.  It just copies the
-	  supplied pointer into the internal representation of the talloc
-	  ptr. This means you must not pass a <emphasis
-	  role="italic">name</emphasis> pointer to memory that will
-	  disappear before <emphasis role="italic">ptr</emphasis> is freed
-	  with talloc_free().
-        </para>
-    </refsect2>
-    <refsect2><title>void *talloc_named(const void *<emphasis role="italic">ctx</emphasis>, size_t <emphasis role="italic">size</emphasis>, const char *<emphasis role="italic">fmt</emphasis>, ...);</title>
-        <para>
-	  The talloc_named() function creates a named talloc pointer.  It
-	  is equivalent to:
-        </para>
-        <programlisting>ptr = talloc_size(ctx, size);
-talloc_set_name(ptr, fmt, ....);</programlisting>
-    </refsect2>
-    <refsect2><title>void *talloc_named_const(const void *<emphasis role="italic">ctx</emphasis>, size_t <emphasis role="italic">size</emphasis>, const char *<emphasis role="italic">name</emphasis>);</title>
-        <para>
-	  This is equivalent to:
-        </para>
-        <programlisting>ptr = talloc_size(ctx, size);
-talloc_set_name_const(ptr, name);</programlisting>
-    </refsect2>
-    <refsect2><title>const char *talloc_get_name(const void *<emphasis role="italic">ptr</emphasis>);</title>
-        <para>
-	  This returns the current name for the given talloc pointer,
-	  <emphasis role="italic">ptr</emphasis>. See <link
-	  linkend="talloc_set_name"><quote>talloc_set_name()</quote></link>
-	  for details.
-        </para>
-    </refsect2>
-    <refsect2><title>void *talloc_init(const char *<emphasis role="italic">fmt</emphasis>, ...);</title>
-        <para>
-	  This function creates a zero length named talloc context as a top
-	  level context.  It is equivalent to:
-        </para>
-        <programlisting>talloc_named(NULL, 0, fmt, ...);</programlisting>
-    </refsect2>
-    <refsect2><title>void *talloc_new(void *<emphasis role="italic">ctx</emphasis>);</title>
-        <para>
-	  This is a utility macro that creates a new memory context hanging
-	  off an existing context, automatically naming it "talloc_new:
-	  __location__" where __location__ is the source line it is called
-	  from.  It is particularly useful for creating a new temporary
-	  working context.
-        </para>
-    </refsect2>
-    <refsect2><title>(<emphasis role="italic">type</emphasis> *)talloc_realloc(const void *<emphasis role="italic">ctx</emphasis>, void *<emphasis role="italic">ptr</emphasis>, <emphasis role="italic">type</emphasis>, <emphasis role="italic">count</emphasis>);</title>
-        <para>
-	  The talloc_realloc() macro changes the size of a talloc pointer. 
-	  It has the following equivalences:
-        </para>
-        <programlisting>talloc_realloc(ctx, NULL, type, 1) ==> talloc(ctx, type);
-talloc_realloc(ctx, ptr, type, 0)  ==> talloc_free(ptr);</programlisting>
-        <para>
-	  The <emphasis role="italic">ctx</emphasis> argument is only used
-	  if <emphasis role="italic">ptr</emphasis> is not NULL, otherwise
-	  it is ignored.
-        </para>
-        <para>
-	  talloc_realloc() returns the new pointer, or NULL on failure. 
-	  The call will fail either due to a lack of memory, or because the
-	  pointer has more than one parent (see <link
-	  linkend="talloc_reference"><quote>talloc_reference()</quote></link>).
-        </para>
-    </refsect2>
-    <refsect2><title>void *talloc_realloc_size(const void *ctx, void *ptr, size_t size);</title>
-        <para>
-	  the talloc_realloc_size() function is useful when the type is not
-	  known so the type-safe talloc_realloc() cannot be used.
-        </para>
-    </refsect2>
-    <refsect2><title>TYPE *talloc_steal(const void *<emphasis role="italic">new_ctx</emphasis>, const TYPE *<emphasis role="italic">ptr</emphasis>);</title>
-        <para>
-	  The talloc_steal() function changes the parent context of a
-	  talloc pointer.  It is typically used when the context that the
-	  pointer is currently a child of is going to be freed and you wish
-	  to keep the memory for a longer time.
-        </para>
-        <para>
-	  The talloc_steal() function returns the pointer that you pass it.
-	   It does not have any failure modes.
-        </para>
-        <para>
-	  It is possible to produce loops in the parent/child
-	  relationship if you are not careful with talloc_steal().  No
-	  guarantees are provided as to your sanity or the safety of your
-	  data if you do this.
-        </para>
-        <para>
-	  Note that if you try and call talloc_steal() on a pointer that has
-	  more than one parent then the result is ambiguous. Talloc will choose
-	  to remove the parent that is currently indicated by talloc_parent()
-	  and replace it with the chosen parent. You will also get a message
-	  like this via the talloc logging functions:
-        </para>
-        <para>
-	  <screen format="linespecific">
-	  WARNING: talloc_steal with references at some_dir/source/foo.c:123
-		reference at some_dir/source/other.c:325
-		reference at some_dir/source/third.c:121
-	  </screen>
-        </para>
-        <para>
-	  To unambiguously change the parent of a pointer please see
-	  the
-	  function <link linkend="talloc_reference"><quote>talloc_reparent()</quote></link>. See
-	  the talloc_set_log_fn() documentation for more information
-	  on talloc logging.
-	</para>
-    </refsect2>
-    <refsect2><title>TYPE *talloc_reparent(const void *<emphasis role="italic">old_parent</emphasis>, const void *<emphasis role="italic">new_parent</emphasis>, const TYPE *<emphasis role="italic">ptr</emphasis>);</title>
-        <para>
-	  The talloc_reparent() function changes the parent context of a talloc
-	  pointer. It is typically used when the context that the pointer is
-	  currently a child of is going to be freed and you wish to keep the
-	  memory for a longer time.
-        </para>
-        <para>
-	  The talloc_reparent() function returns the pointer that you pass it. It
-	  does not have any failure modes.
-        </para>
-        <para>
-	  The difference between talloc_reparent() and talloc_steal() is that
-	  talloc_reparent() can specify which parent you wish to change. This is
-	  useful when a pointer has multiple parents via references.
-        </para>
-    </refsect2>
-    <refsect2><title>TYPE *talloc_move(const void *<emphasis role="italic">new_ctx</emphasis>, TYPE **<emphasis role="italic">ptr</emphasis>);</title>
-        <para>
-	  The talloc_move() function is a wrapper around
-	  talloc_steal() which zeros the source pointer after the
-	  move. This avoids a potential source of bugs where a
-	  programmer leaves a pointer in two structures, and uses the
-	  pointer from the old structure after it has been moved to a
-	  new one.
-        </para>
-    </refsect2>
-    <refsect2><title>size_t talloc_total_size(const void *<emphasis role="italic">ptr</emphasis>);</title>
-        <para>
-	  The talloc_total_size() function returns the total size in bytes
-	  used by this pointer and all child pointers.	Mostly useful for
-	  debugging.
-        </para>
-        <para>
-	  Passing NULL is allowed, but it will only give a meaningful
-	  result if talloc_enable_leak_report() or
-	  talloc_enable_leak_report_full() has been called.
-        </para>
-    </refsect2>
-    <refsect2><title>size_t talloc_total_blocks(const void *<emphasis role="italic">ptr</emphasis>);</title>
-        <para>
-	  The talloc_total_blocks() function returns the total memory block
-	  count used by this pointer and all child pointers.  Mostly useful
-	  for debugging.
-        </para>
-        <para>
-	  Passing NULL is allowed, but it will only give a meaningful
-	  result if talloc_enable_leak_report() or
-	  talloc_enable_leak_report_full() has been called.
-        </para>
-    </refsect2>
-    <refsect2 id="talloc_report"><title>void talloc_report(const void *ptr, FILE *f);</title>
-        <para>
-	  The talloc_report() function prints a summary report of all
-	  memory used by <emphasis role="italic">ptr</emphasis>.  One line
-	  of report is printed for each immediate child of ptr, showing the
-	  total memory and number of blocks used by that child.
-        </para>
-        <para>
-	  You can pass NULL for the pointer, in which case a report is
-	  printed for the top level memory context, but only if
-	  talloc_enable_leak_report() or talloc_enable_leak_report_full()
-	  has been called.
-        </para>
-    </refsect2>
-    <refsect2 id="talloc_report_full"><title>void talloc_report_full(const void *<emphasis role="italic">ptr</emphasis>, FILE *<emphasis role="italic">f</emphasis>);</title>
-        <para>
-	  This provides a more detailed report than talloc_report().  It
-	  will recursively print the entire tree of memory referenced by
-	  the pointer. References in the tree are shown by giving the name
-	  of the pointer that is referenced.
-        </para>
-        <para>
-	  You can pass NULL for the pointer, in which case a report is
-	  printed for the top level memory context, but only if
-	  talloc_enable_leak_report() or talloc_enable_leak_report_full()
-	  has been called.
-        </para>
-    </refsect2>
-    <refsect2 id="talloc_report_depth_cb">
-     <funcsynopsis><funcprototype>
-      <funcdef>void <function>talloc_report_depth_cb</function></funcdef>
-      <paramdef><parameter>const void *ptr</parameter></paramdef>
-      <paramdef><parameter>int depth</parameter></paramdef>
-      <paramdef><parameter>int max_depth</parameter></paramdef>
-      <paramdef><parameter>void (*callback)(const void *ptr, int depth, int max_depth, int is_ref, void *priv)</parameter></paramdef>
-      <paramdef><parameter>void *priv</parameter></paramdef>
-     </funcprototype></funcsynopsis>
-        <para>
-	  This provides a more flexible reports than talloc_report(). It
-	  will recursively call the callback for the entire tree of memory
-	  referenced by the pointer. References in the tree are passed with
-	  <emphasis role="italic">is_ref = 1</emphasis> and the pointer that is referenced.
-        </para>
-        <para>
-	  You can pass NULL for the pointer, in which case a report is
-	  printed for the top level memory context, but only if
-	  talloc_enable_leak_report() or talloc_enable_leak_report_full()
-	  has been called.
-        </para>
-        <para>
-	  The recursion is stopped when depth >= max_depth.
-	  max_depth = -1 means only stop at leaf nodes.
-        </para>
-    </refsect2>
-    <refsect2 id="talloc_report_depth_file">
-     <funcsynopsis><funcprototype>
-      <funcdef>void <function>talloc_report_depth_file</function></funcdef>
-      <paramdef><parameter>const void *ptr</parameter></paramdef>
-      <paramdef><parameter>int depth</parameter></paramdef>
-      <paramdef><parameter>int max_depth</parameter></paramdef>
-      <paramdef><parameter>FILE *f</parameter></paramdef>
-     </funcprototype></funcsynopsis>
-        <para>
-	  This provides a more flexible reports than talloc_report(). It
-	  will let you specify the depth and max_depth.
-        </para>
-    </refsect2>
-    <refsect2 id="talloc_enable_leak_report"><title>void talloc_enable_leak_report(void);</title>
-        <para>
-	  This enables calling of talloc_report(NULL, stderr) when the
-	  program exits.  In Samba4 this is enabled by using the
-	  --leak-report command line option.
-        </para>
-        <para>
-	  For it to be useful, this function must be called before any
-	  other talloc function as it establishes a "null context" that
-	  acts as the top of the tree.	If you don't call this function
-	  first then passing NULL to talloc_report() or
-	  talloc_report_full() won't give you the full tree printout.
-        </para>
-        <para>
-	  Here is a typical talloc report:
-        </para>
-        <screen format="linespecific">talloc report on 'null_context' (total 267 bytes in 15 blocks)
-libcli/auth/spnego_parse.c:55  contains   31 bytes in   2 blocks
-libcli/auth/spnego_parse.c:55  contains   31 bytes in   2 blocks
-iconv(UTF8,CP850)              contains   42 bytes in   2 blocks
-libcli/auth/spnego_parse.c:55  contains   31 bytes in   2 blocks
-iconv(CP850,UTF8)              contains   42 bytes in   2 blocks
-iconv(UTF8,UTF-16LE)           contains   45 bytes in   2 blocks
-iconv(UTF-16LE,UTF8)           contains   45 bytes in   2 blocks
-      </screen>
-    </refsect2>
-    <refsect2 id="talloc_enable_leak_report_full"><title>void talloc_enable_leak_report_full(void);</title>
-        <para>
-	  This enables calling of talloc_report_full(NULL, stderr) when the
-	  program exits.  In Samba4 this is enabled by using the
-	  --leak-report-full command line option.
-        </para>
-        <para>
-	  For it to be useful, this function must be called before any
-	  other talloc function as it establishes a "null context" that
-	  acts as the top of the tree.	If you don't call this function
-	  first then passing NULL to talloc_report() or
-	  talloc_report_full() won't give you the full tree printout.
-        </para>
-        <para>
-	  Here is a typical full report:
-        </para>
-        <screen format="linespecific">full talloc report on 'root' (total 18 bytes in 8 blocks)
-p1               contains     18 bytes in   7 blocks (ref 0)
-    r1               contains     13 bytes in   2 blocks (ref 0)
-        reference to: p2
-    p2               contains      1 bytes in   1 blocks (ref 1)
-    x3               contains      1 bytes in   1 blocks (ref 0)
-    x2               contains      1 bytes in   1 blocks (ref 0)
-    x1               contains      1 bytes in   1 blocks (ref 0)
-      </screen>
-    </refsect2>
-    <refsect2><title>(<emphasis role="italic">type</emphasis> *)talloc_zero(const void *<emphasis role="italic">ctx</emphasis>, <emphasis role="italic">type</emphasis>);</title>
-        <para>
-	  The talloc_zero() macro is equivalent to:
-        </para>
-        <programlisting>ptr = talloc(ctx, type);
-if (ptr) memset(ptr, 0, sizeof(type));</programlisting>
-    </refsect2>
-    <refsect2><title>void *talloc_zero_size(const void *<emphasis role="italic">ctx</emphasis>, size_t <emphasis role="italic">size</emphasis>)</title>
-        <para>
-	  The talloc_zero_size() function is useful when you don't have a
-	  known type.
-        </para>
-    </refsect2>
-    <refsect2><title>void *talloc_memdup(const void *<emphasis role="italic">ctx</emphasis>, const void *<emphasis role="italic">p</emphasis>, size_t size);</title>
-        <para>
-	  The talloc_memdup() function is equivalent to:
-        </para>
-        <programlisting>ptr = talloc_size(ctx, size);
-if (ptr) memcpy(ptr, p, size);</programlisting>
-    </refsect2>
-    <refsect2><title>char *talloc_strdup(const void *<emphasis role="italic">ctx</emphasis>, const char *<emphasis role="italic">p</emphasis>);</title>
-        <para>
-	  The talloc_strdup() function is equivalent to:
-        </para>
-        <programlisting>ptr = talloc_size(ctx, strlen(p)+1);
-if (ptr) memcpy(ptr, p, strlen(p)+1);</programlisting>
-        <para>
-	  This function sets the name of the new pointer to the passed
-	  string. This is equivalent to:
-        </para>
-        <programlisting>talloc_set_name_const(ptr, ptr)</programlisting>
-    </refsect2>
-    <refsect2><title>char *talloc_strndup(const void *<emphasis role="italic">t</emphasis>, const char *<emphasis role="italic">p</emphasis>, size_t <emphasis role="italic">n</emphasis>);</title>
-        <para>
-	  The talloc_strndup() function is the talloc equivalent of the C
-	  library function strndup(3).
-        </para>
-        <para>
-	  This function sets the name of the new pointer to the passed
-	  string. This is equivalent to:
-        </para>
-        <programlisting>talloc_set_name_const(ptr, ptr)</programlisting>
-    </refsect2>
-    <refsect2><title>char *talloc_vasprintf(const void *<emphasis role="italic">t</emphasis>, const char *<emphasis role="italic">fmt</emphasis>, va_list <emphasis role="italic">ap</emphasis>);</title>
-        <para>
-	  The talloc_vasprintf() function is the talloc equivalent of the C
-	  library function vasprintf(3).
-        </para>
-        <para>
-	  This function sets the name of the new pointer to the new
-	  string. This is equivalent to:
-        </para>
-        <programlisting>talloc_set_name_const(ptr, ptr)</programlisting>
-    </refsect2>
-    <refsect2><title>char *talloc_asprintf(const void *<emphasis role="italic">t</emphasis>, const char *<emphasis role="italic">fmt</emphasis>, ...);</title>
-        <para>
-	  The talloc_asprintf() function is the talloc equivalent of the C
-	  library function asprintf(3).
-        </para>
-        <para>
-	  This function sets the name of the new pointer to the passed
-	  string. This is equivalent to:
-        </para>
-        <programlisting>talloc_set_name_const(ptr, ptr)</programlisting>
-    </refsect2>
-    <refsect2><title>char *talloc_asprintf_append(char *s, const char *fmt, ...);</title>
-        <para>
-	  The talloc_asprintf_append() function appends the given formatted
-	  string to the given string.
-        </para>
-        <para>
-	  This function sets the name of the new pointer to the new
-	  string. This is equivalent to:
-        </para>
-        <programlisting>talloc_set_name_const(ptr, ptr)</programlisting>
-    </refsect2>
-    <refsect2><title>(type *)talloc_array(const void *ctx, type, unsigned int count);</title>
-        <para>
-	  The talloc_array() macro is equivalent to:
-        </para>
-        <programlisting>(type *)talloc_size(ctx, sizeof(type) * count);</programlisting>
-        <para>
-	  except that it provides integer overflow protection for the
-	  multiply, returning NULL if the multiply overflows.
-        </para>
-    </refsect2>
-    <refsect2><title>void *talloc_array_size(const void *ctx, size_t size, unsigned int count);</title>
-        <para>
-	  The talloc_array_size() function is useful when the type is not
-	  known. It operates in the same way as talloc_array(), but takes a
-	  size instead of a type.
-        </para>
-    </refsect2>
-    <refsect2><title>(typeof(ptr)) talloc_array_ptrtype(const void *ctx, ptr, unsigned int count);</title>
-        <para>
-	  The talloc_ptrtype() macro should be used when you have a pointer to an array
-	  and want to allocate memory of an array to point at with this pointer. When compiling
-	  with gcc >= 3 it is typesafe. Note this is a wrapper of talloc_array_size()
-	  and talloc_get_name() will return the current location in the source file.
-	  and not the type.
-        </para>
-    </refsect2>
-    <refsect2><title>void *talloc_realloc_fn(const void *ctx, void *ptr, size_t size)</title>
-        <para>
-	  This is a non-macro version of talloc_realloc(), which is useful
-	  as libraries sometimes want a realloc function pointer.  A
-	  realloc(3) implementation encapsulates the functionality of
-	  malloc(3), free(3) and realloc(3) in one call, which is why it is
-	  useful to be able to pass around a single function pointer.
-        </para>
-    </refsect2>
-    <refsect2><title>void *talloc_autofree_context(void);</title>
-        <para>
-	  This is a handy utility function that returns a talloc context
-	  which will be automatically freed on program exit.  This can be
-	  used to reduce the noise in memory leak reports.
-        </para>
-    </refsect2>
-    <refsect2><title>void *talloc_check_name(const void *ptr, const char *name);</title>
-        <para>
-	  This function checks if a pointer has the specified <emphasis
-	  role="italic">name</emphasis>.  If it does then the pointer is
-	  returned.  It it doesn't then NULL is returned.
-        </para>
-    </refsect2>
-    <refsect2><title>(type *)talloc_get_type(const void *ptr, type);</title>
-        <para>
-	  This macro allows you to do type checking on talloc pointers.  It
-	  is particularly useful for void* private pointers.  It is
-	  equivalent to this:
-        </para>
-        <programlisting>(type *)talloc_check_name(ptr, #type)</programlisting>
-    </refsect2>
-    <refsect2><title>talloc_set_type(const void *ptr, type);</title>
-        <para>
-	  This macro allows you to force the name of a pointer to be a
-	  particular <emphasis>type</emphasis>.  This can be
-	  used in conjunction with talloc_get_type() to do type checking on
-	  void* pointers.
-        </para>
-        <para>
-	  It is equivalent to this:
-        </para>
-        <programlisting>talloc_set_name_const(ptr, #type)</programlisting>
-    </refsect2>
-    <refsect2><title>talloc_set_log_fn(void (*log_fn)(const char *message));</title>
-        <para>
-	  This function sets a logging function that talloc will use for
-	  warnings and errors. By default talloc will not print any warnings or
-	  errors.
-	</para>
-    </refsect2>
-    <refsect2><title>talloc_set_log_stderr(void);</title>
-        <para>
-	  This sets the talloc log function to write log messages to stderr
-	</para>
-    </refsect2>
-  </refsect1>
-  <refsect1><title>PERFORMANCE</title>
-    <para>
-      All the additional features of talloc(3) over malloc(3) do come at a
-      price.  We have a simple performance test in Samba4 that measures
-      talloc() versus malloc() performance, and it seems that talloc() is
-      about 10% slower than malloc() on my x86 Debian Linux box.  For
-      Samba, the great reduction in code complexity that we get by using
-      talloc makes this worthwhile, especially as the total overhead of
-      talloc/malloc in Samba is already quite small.
-    </para>
-  </refsect1>
-  <refsect1><title>SEE ALSO</title>
-    <para>
-      malloc(3), strndup(3), vasprintf(3), asprintf(3), 
-      <ulink url="http://talloc.samba.org/"/>
-    </para>
-  </refsect1>
-  <refsect1><title>COPYRIGHT/LICENSE</title>
-    <para>
-      Copyright (C) Andrew Tridgell 2004
-    </para>
-    <para>
-      This program is free software; you can redistribute it and/or modify
-      it under the terms of the GNU Lesser General Public License as
-      published by the Free Software Foundation; either version 3 of the
-      License, or (at your option) any later version.
-    </para>
-    <para>
-      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.
-    </para>
-    <para>
-      You should have received a copy of the GNU General Public License
-      along with this program; if not, see http://www.gnu.org/licenses/.
-    </para>
-  </refsect1>
-</refentry>
diff --git a/lib/talloc/talloc.c b/lib/talloc/talloc.c
deleted file mode 100644
index 3622934..0000000
--- a/lib/talloc/talloc.c
+++ /dev/null
@@ -1,2370 +0,0 @@
-/* 
-   Samba Unix SMB/CIFS implementation.
-
-   Samba trivial allocation library - new interface
-
-   NOTE: Please read talloc_guide.txt for full documentation
-
-   Copyright (C) Andrew Tridgell 2004
-   Copyright (C) Stefan Metzmacher 2006
-   
-     ** NOTE! The following LGPL license applies to the talloc
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-   
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-
-/*
-  inspired by http://swapped.cc/halloc/
-*/
-
-#include "replace.h"
-#include "talloc.h"
-
-#ifdef TALLOC_BUILD_VERSION_MAJOR
-#if (TALLOC_VERSION_MAJOR != TALLOC_BUILD_VERSION_MAJOR)
-#error "TALLOC_VERSION_MAJOR != TALLOC_BUILD_VERSION_MAJOR"
-#endif
-#endif
-
-#ifdef TALLOC_BUILD_VERSION_MINOR
-#if (TALLOC_VERSION_MINOR != TALLOC_BUILD_VERSION_MINOR)
-#error "TALLOC_VERSION_MINOR != TALLOC_BUILD_VERSION_MINOR"
-#endif
-#endif
-
-/* Special macros that are no-ops except when run under Valgrind on
- * x86.  They've moved a little bit from valgrind 1.0.4 to 1.9.4 */
-#ifdef HAVE_VALGRIND_MEMCHECK_H
-        /* memcheck.h includes valgrind.h */
-#include <valgrind/memcheck.h>
-#elif defined(HAVE_VALGRIND_H)
-#include <valgrind.h>
-#endif
-
-/* use this to force every realloc to change the pointer, to stress test
-   code that might not cope */
-#define ALWAYS_REALLOC 0
-
-
-#define MAX_TALLOC_SIZE 0x10000000
-#define TALLOC_MAGIC_BASE 0xe814ec70
-#define TALLOC_MAGIC ( \
-	TALLOC_MAGIC_BASE + \
-	(TALLOC_VERSION_MAJOR << 12) + \
-	(TALLOC_VERSION_MINOR << 4) \
-)
-
-#define TALLOC_FLAG_FREE 0x01
-#define TALLOC_FLAG_LOOP 0x02
-#define TALLOC_FLAG_POOL 0x04		/* This is a talloc pool */
-#define TALLOC_FLAG_POOLMEM 0x08	/* This is allocated in a pool */
-#define TALLOC_MAGIC_REFERENCE ((const char *)1)
-
-/* by default we abort when given a bad pointer (such as when talloc_free() is called 
-   on a pointer that came from malloc() */
-#ifndef TALLOC_ABORT
-#define TALLOC_ABORT(reason) abort()
-#endif
-
-#ifndef discard_const_p
-#if defined(__intptr_t_defined) || defined(HAVE_INTPTR_T)
-# define discard_const_p(type, ptr) ((type *)((intptr_t)(ptr)))
-#else
-# define discard_const_p(type, ptr) ((type *)(ptr))
-#endif
-#endif
-
-/* these macros gain us a few percent of speed on gcc */
-#if (__GNUC__ >= 3)
-/* the strange !! is to ensure that __builtin_expect() takes either 0 or 1
-   as its first argument */
-#ifndef likely
-#define likely(x)   __builtin_expect(!!(x), 1)
-#endif
-#ifndef unlikely
-#define unlikely(x) __builtin_expect(!!(x), 0)
-#endif
-#else
-#ifndef likely
-#define likely(x) (x)
-#endif
-#ifndef unlikely
-#define unlikely(x) (x)
-#endif
-#endif
-
-/* this null_context is only used if talloc_enable_leak_report() or
-   talloc_enable_leak_report_full() is called, otherwise it remains
-   NULL
-*/
-static void *null_context;
-static void *autofree_context;
-
-/* used to enable fill of memory on free, which can be useful for
- * catching use after free errors when valgrind is too slow
- */
-static struct {
-	bool initialised;
-	bool enabled;
-	uint8_t fill_value;
-} talloc_fill;
-
-#define TALLOC_FILL_ENV "TALLOC_FREE_FILL"
-
-/*
- * do not wipe the header, to allow the
- * double-free logic to still work
- */
-#define TC_INVALIDATE_FULL_FILL_CHUNK(_tc) do { \
-	if (unlikely(talloc_fill.enabled)) { \
-		size_t _flen = (_tc)->size; \
-		char *_fptr = (char *)TC_PTR_FROM_CHUNK(_tc); \
-		memset(_fptr, talloc_fill.fill_value, _flen); \
-	} \
-} while (0)
-
-#if defined(DEVELOPER) && defined(VALGRIND_MAKE_MEM_NOACCESS)
-/* Mark the whole chunk as not accessable */
-#define TC_INVALIDATE_FULL_VALGRIND_CHUNK(_tc) do { \
-	size_t _flen = TC_HDR_SIZE + (_tc)->size; \
-	char *_fptr = (char *)(_tc); \
-	VALGRIND_MAKE_MEM_NOACCESS(_fptr, _flen); \
-} while(0)
-#else
-#define TC_INVALIDATE_FULL_VALGRIND_CHUNK(_tc) do { } while (0)
-#endif
-
-#define TC_INVALIDATE_FULL_CHUNK(_tc) do { \
-	TC_INVALIDATE_FULL_FILL_CHUNK(_tc); \
-	TC_INVALIDATE_FULL_VALGRIND_CHUNK(_tc); \
-} while (0)
-
-#define TC_INVALIDATE_SHRINK_FILL_CHUNK(_tc, _new_size) do { \
-	if (unlikely(talloc_fill.enabled)) { \
-		size_t _flen = (_tc)->size - (_new_size); \
-		char *_fptr = (char *)TC_PTR_FROM_CHUNK(_tc); \
-		_fptr += (_new_size); \
-		memset(_fptr, talloc_fill.fill_value, _flen); \
-	} \
-} while (0)
-
-#if defined(DEVELOPER) && defined(VALGRIND_MAKE_MEM_NOACCESS)
-/* Mark the unused bytes not accessable */
-#define TC_INVALIDATE_SHRINK_VALGRIND_CHUNK(_tc, _new_size) do { \
-	size_t _flen = (_tc)->size - (_new_size); \
-	char *_fptr = (char *)TC_PTR_FROM_CHUNK(_tc); \
-	_fptr += (_new_size); \
-	VALGRIND_MAKE_MEM_NOACCESS(_fptr, _flen); \
-} while (0)
-#else
-#define TC_INVALIDATE_SHRINK_VALGRIND_CHUNK(_tc, _new_size) do { } while (0)
-#endif
-
-#define TC_INVALIDATE_SHRINK_CHUNK(_tc, _new_size) do { \
-	TC_INVALIDATE_SHRINK_FILL_CHUNK(_tc, _new_size); \
-	TC_INVALIDATE_SHRINK_VALGRIND_CHUNK(_tc, _new_size); \
-} while (0)
-
-#define TC_UNDEFINE_SHRINK_FILL_CHUNK(_tc, _new_size) do { \
-	if (unlikely(talloc_fill.enabled)) { \
-		size_t _flen = (_tc)->size - (_new_size); \
-		char *_fptr = (char *)TC_PTR_FROM_CHUNK(_tc); \
-		_fptr += (_new_size); \
-		memset(_fptr, talloc_fill.fill_value, _flen); \
-	} \
-} while (0)
-
-#if defined(DEVELOPER) && defined(VALGRIND_MAKE_MEM_UNDEFINED)
-/* Mark the unused bytes as undefined */
-#define TC_UNDEFINE_SHRINK_VALGRIND_CHUNK(_tc, _new_size) do { \
-	size_t _flen = (_tc)->size - (_new_size); \
-	char *_fptr = (char *)TC_PTR_FROM_CHUNK(_tc); \
-	_fptr += (_new_size); \
-	VALGRIND_MAKE_MEM_UNDEFINED(_fptr, _flen); \
-} while (0)
-#else
-#define TC_UNDEFINE_SHRINK_VALGRIND_CHUNK(_tc, _new_size) do { } while (0)
-#endif
-
-#define TC_UNDEFINE_SHRINK_CHUNK(_tc, _new_size) do { \
-	TC_UNDEFINE_SHRINK_FILL_CHUNK(_tc, _new_size); \
-	TC_UNDEFINE_SHRINK_VALGRIND_CHUNK(_tc, _new_size); \
-} while (0)
-
-#if defined(DEVELOPER) && defined(VALGRIND_MAKE_MEM_UNDEFINED)
-/* Mark the new bytes as undefined */
-#define TC_UNDEFINE_GROW_VALGRIND_CHUNK(_tc, _new_size) do { \
-	size_t _old_used = TC_HDR_SIZE + (_tc)->size; \
-	size_t _new_used = TC_HDR_SIZE + (_new_size); \
-	size_t _flen = _new_used - _old_used; \
-	char *_fptr = _old_used + (char *)(_tc); \
-	VALGRIND_MAKE_MEM_UNDEFINED(_fptr, _flen); \
-} while (0)
-#else
-#define TC_UNDEFINE_GROW_VALGRIND_CHUNK(_tc, _new_size) do { } while (0)
-#endif
-
-#define TC_UNDEFINE_GROW_CHUNK(_tc, _new_size) do { \
-	TC_UNDEFINE_GROW_VALGRIND_CHUNK(_tc, _new_size); \
-} while (0)
-
-struct talloc_reference_handle {
-	struct talloc_reference_handle *next, *prev;
-	void *ptr;
-	const char *location;
-};
-
-typedef int (*talloc_destructor_t)(void *);
-
-struct talloc_chunk {
-	struct talloc_chunk *next, *prev;
-	struct talloc_chunk *parent, *child;
-	struct talloc_reference_handle *refs;
-	talloc_destructor_t destructor;
-	const char *name;
-	size_t size;
-	unsigned flags;
-
-	/*
-	 * "pool" has dual use:
-	 *
-	 * For the talloc pool itself (i.e. TALLOC_FLAG_POOL is set), "pool"
-	 * marks the end of the currently allocated area.
-	 *
-	 * For members of the pool (i.e. TALLOC_FLAG_POOLMEM is set), "pool"
-	 * is a pointer to the struct talloc_chunk of the pool that it was
-	 * allocated from. This way children can quickly find the pool to chew
-	 * from.
-	 */
-	void *pool;
-};
-
-/* 16 byte alignment seems to keep everyone happy */
-#define TC_ALIGN16(s) (((s)+15)&~15)
-#define TC_HDR_SIZE TC_ALIGN16(sizeof(struct talloc_chunk))
-#define TC_PTR_FROM_CHUNK(tc) ((void *)(TC_HDR_SIZE + (char*)tc))
-
-_PUBLIC_ int talloc_version_major(void)
-{
-	return TALLOC_VERSION_MAJOR;
-}
-
-_PUBLIC_ int talloc_version_minor(void)
-{
-	return TALLOC_VERSION_MINOR;
-}
-
-static void (*talloc_log_fn)(const char *message);
-
-_PUBLIC_ void talloc_set_log_fn(void (*log_fn)(const char *message))
-{
-	talloc_log_fn = log_fn;
-}
-
-static void talloc_log(const char *fmt, ...) PRINTF_ATTRIBUTE(1,2);
-static void talloc_log(const char *fmt, ...)
-{
-	va_list ap;
-	char *message;
-
-	if (!talloc_log_fn) {
-		return;
-	}
-
-	va_start(ap, fmt);
-	message = talloc_vasprintf(NULL, fmt, ap);
-	va_end(ap);
-
-	talloc_log_fn(message);
-	talloc_free(message);
-}
-
-static void talloc_log_stderr(const char *message)
-{
-	fprintf(stderr, "%s", message);
-}
-
-_PUBLIC_ void talloc_set_log_stderr(void)
-{
-	talloc_set_log_fn(talloc_log_stderr);
-}
-
-static void (*talloc_abort_fn)(const char *reason);
-
-_PUBLIC_ void talloc_set_abort_fn(void (*abort_fn)(const char *reason))
-{
-	talloc_abort_fn = abort_fn;
-}
-
-static void talloc_abort(const char *reason)
-{
-	talloc_log("%s\n", reason);
-
-	if (!talloc_abort_fn) {
-		TALLOC_ABORT(reason);
-	}
-
-	talloc_abort_fn(reason);
-}
-
-static void talloc_abort_magic(unsigned magic)
-{
-	unsigned striped = magic - TALLOC_MAGIC_BASE;
-	unsigned major = (striped & 0xFFFFF000) >> 12;
-	unsigned minor = (striped & 0x00000FF0) >> 4;
-	talloc_log("Bad talloc magic[0x%08X/%u/%u] expected[0x%08X/%u/%u]\n",
-		   magic, major, minor,
-		   TALLOC_MAGIC, TALLOC_VERSION_MAJOR, TALLOC_VERSION_MINOR);
-	talloc_abort("Bad talloc magic value - wrong talloc version used/mixed");
-}
-
-static void talloc_abort_access_after_free(void)
-{
-	talloc_abort("Bad talloc magic value - access after free");
-}
-
-static void talloc_abort_unknown_value(void)
-{
-	talloc_abort("Bad talloc magic value - unknown value");
-}
-
-/* panic if we get a bad magic value */
-static inline struct talloc_chunk *talloc_chunk_from_ptr(const void *ptr)
-{
-	const char *pp = (const char *)ptr;
-	struct talloc_chunk *tc = discard_const_p(struct talloc_chunk, pp - TC_HDR_SIZE);
-	if (unlikely((tc->flags & (TALLOC_FLAG_FREE | ~0xF)) != TALLOC_MAGIC)) { 
-		if ((tc->flags & (~0xFFF)) == TALLOC_MAGIC_BASE) {
-			talloc_abort_magic(tc->flags & (~0xF));
-			return NULL;
-		}
-
-		if (tc->flags & TALLOC_FLAG_FREE) {
-			talloc_log("talloc: access after free error - first free may be at %s\n", tc->name);
-			talloc_abort_access_after_free();
-			return NULL;
-		} else {
-			talloc_abort_unknown_value();
-			return NULL;
-		}
-	}
-	return tc;
-}
-
-/* hook into the front of the list */
-#define _TLIST_ADD(list, p) \
-do { \
-        if (!(list)) { \
-		(list) = (p); \
-		(p)->next = (p)->prev = NULL; \
-	} else { \
-		(list)->prev = (p); \
-		(p)->next = (list); \
-		(p)->prev = NULL; \
-		(list) = (p); \
-	}\
-} while (0)
-
-/* remove an element from a list - element doesn't have to be in list. */
-#define _TLIST_REMOVE(list, p) \
-do { \
-	if ((p) == (list)) { \
-		(list) = (p)->next; \
-		if (list) (list)->prev = NULL; \
-	} else { \
-		if ((p)->prev) (p)->prev->next = (p)->next; \
-		if ((p)->next) (p)->next->prev = (p)->prev; \
-	} \
-	if ((p) && ((p) != (list))) (p)->next = (p)->prev = NULL; \
-} while (0)
-
-
-/*
-  return the parent chunk of a pointer
-*/
-static inline struct talloc_chunk *talloc_parent_chunk(const void *ptr)
-{
-	struct talloc_chunk *tc;
-
-	if (unlikely(ptr == NULL)) {
-		return NULL;
-	}
-
-	tc = talloc_chunk_from_ptr(ptr);
-	while (tc->prev) tc=tc->prev;
-
-	return tc->parent;
-}
-
-_PUBLIC_ void *talloc_parent(const void *ptr)
-{
-	struct talloc_chunk *tc = talloc_parent_chunk(ptr);
-	return tc? TC_PTR_FROM_CHUNK(tc) : NULL;
-}
-
-/*
-  find parents name
-*/
-_PUBLIC_ const char *talloc_parent_name(const void *ptr)
-{
-	struct talloc_chunk *tc = talloc_parent_chunk(ptr);
-	return tc? tc->name : NULL;
-}
-
-/*
-  A pool carries an in-pool object count count in the first 16 bytes.
-  bytes. This is done to support talloc_steal() to a parent outside of the
-  pool. The count includes the pool itself, so a talloc_free() on a pool will
-  only destroy the pool if the count has dropped to zero. A talloc_free() of a
-  pool member will reduce the count, and eventually also call free(3) on the
-  pool memory.
-
-  The object count is not put into "struct talloc_chunk" because it is only
-  relevant for talloc pools and the alignment to 16 bytes would increase the
-  memory footprint of each talloc chunk by those 16 bytes.
-*/
-
-#define TALLOC_POOL_HDR_SIZE 16
-
-#define TC_POOL_SPACE_LEFT(_pool_tc) \
-	PTR_DIFF(TC_HDR_SIZE + (_pool_tc)->size + (char *)(_pool_tc), \
-		 (_pool_tc)->pool)
-
-#define TC_POOL_FIRST_CHUNK(_pool_tc) \
-	((void *)(TC_HDR_SIZE + TALLOC_POOL_HDR_SIZE + (char *)(_pool_tc)))
-
-#define TC_POOLMEM_CHUNK_SIZE(_tc) \
-	TC_ALIGN16(TC_HDR_SIZE + (_tc)->size)
-
-#define TC_POOLMEM_NEXT_CHUNK(_tc) \
-	((void *)(TC_POOLMEM_CHUNK_SIZE(tc) + (char*)(_tc)))
-
-/* Mark the whole remaining pool as not accessable */
-#define TC_INVALIDATE_FILL_POOL(_pool_tc) do { \
-	if (unlikely(talloc_fill.enabled)) { \
-		size_t _flen = TC_POOL_SPACE_LEFT(_pool_tc); \
-		char *_fptr = (char *)(_pool_tc)->pool; \
-		memset(_fptr, talloc_fill.fill_value, _flen); \
-	} \
-} while(0)
-
-#if defined(DEVELOPER) && defined(VALGRIND_MAKE_MEM_NOACCESS)
-/* Mark the whole remaining pool as not accessable */
-#define TC_INVALIDATE_VALGRIND_POOL(_pool_tc) do { \
-	size_t _flen = TC_POOL_SPACE_LEFT(_pool_tc); \
-	char *_fptr = (char *)(_pool_tc)->pool; \
-	VALGRIND_MAKE_MEM_NOACCESS(_fptr, _flen); \
-} while(0)
-#else
-#define TC_INVALIDATE_VALGRIND_POOL(_pool_tc) do { } while (0)
-#endif
-
-#define TC_INVALIDATE_POOL(_pool_tc) do { \
-	TC_INVALIDATE_FILL_POOL(_pool_tc); \
-	TC_INVALIDATE_VALGRIND_POOL(_pool_tc); \
-} while (0)
-
-static unsigned int *talloc_pool_objectcount(struct talloc_chunk *tc)
-{
-	return (unsigned int *)((char *)tc + TC_HDR_SIZE);
-}
-
-/*
-  Allocate from a pool
-*/
-
-static struct talloc_chunk *talloc_alloc_pool(struct talloc_chunk *parent,
-					      size_t size)
-{
-	struct talloc_chunk *pool_ctx = NULL;
-	size_t space_left;
-	struct talloc_chunk *result;
-	size_t chunk_size;
-
-	if (parent == NULL) {
-		return NULL;
-	}
-
-	if (parent->flags & TALLOC_FLAG_POOL) {
-		pool_ctx = parent;
-	}
-	else if (parent->flags & TALLOC_FLAG_POOLMEM) {
-		pool_ctx = (struct talloc_chunk *)parent->pool;
-	}
-
-	if (pool_ctx == NULL) {
-		return NULL;
-	}
-
-	space_left = TC_POOL_SPACE_LEFT(pool_ctx);
-
-	/*
-	 * Align size to 16 bytes
-	 */
-	chunk_size = TC_ALIGN16(size);
-
-	if (space_left < chunk_size) {
-		return NULL;
-	}
-
-	result = (struct talloc_chunk *)pool_ctx->pool;
-
-#if defined(DEVELOPER) && defined(VALGRIND_MAKE_MEM_UNDEFINED)
-	VALGRIND_MAKE_MEM_UNDEFINED(result, size);
-#endif
-
-	pool_ctx->pool = (void *)((char *)result + chunk_size);
-
-	result->flags = TALLOC_MAGIC | TALLOC_FLAG_POOLMEM;
-	result->pool = pool_ctx;
-
-	*talloc_pool_objectcount(pool_ctx) += 1;
-
-	return result;
-}
-
-/* 
-   Allocate a bit of memory as a child of an existing pointer
-*/
-static inline void *__talloc(const void *context, size_t size)
-{
-	struct talloc_chunk *tc = NULL;
-
-	if (unlikely(context == NULL)) {
-		context = null_context;
-	}
-
-	if (unlikely(size >= MAX_TALLOC_SIZE)) {
-		return NULL;
-	}
-
-	if (context != NULL) {
-		tc = talloc_alloc_pool(talloc_chunk_from_ptr(context),
-				       TC_HDR_SIZE+size);
-	}
-
-	if (tc == NULL) {
-		tc = (struct talloc_chunk *)malloc(TC_HDR_SIZE+size);
-		if (unlikely(tc == NULL)) return NULL;
-		tc->flags = TALLOC_MAGIC;
-		tc->pool  = NULL;
-	}
-
-	tc->size = size;
-	tc->destructor = NULL;
-	tc->child = NULL;
-	tc->name = NULL;
-	tc->refs = NULL;
-
-	if (likely(context)) {
-		struct talloc_chunk *parent = talloc_chunk_from_ptr(context);
-
-		if (parent->child) {
-			parent->child->parent = NULL;
-			tc->next = parent->child;
-			tc->next->prev = tc;
-		} else {
-			tc->next = NULL;
-		}
-		tc->parent = parent;
-		tc->prev = NULL;
-		parent->child = tc;
-	} else {
-		tc->next = tc->prev = tc->parent = NULL;
-	}
-
-	return TC_PTR_FROM_CHUNK(tc);
-}
-
-/*
- * Create a talloc pool
- */
-
-_PUBLIC_ void *talloc_pool(const void *context, size_t size)
-{
-	void *result = __talloc(context, size + TALLOC_POOL_HDR_SIZE);
-	struct talloc_chunk *tc;
-
-	if (unlikely(result == NULL)) {
-		return NULL;
-	}
-
-	tc = talloc_chunk_from_ptr(result);
-
-	tc->flags |= TALLOC_FLAG_POOL;
-	tc->pool = TC_POOL_FIRST_CHUNK(tc);
-
-	*talloc_pool_objectcount(tc) = 1;
-
-	TC_INVALIDATE_POOL(tc);
-
-	return result;
-}
-
-/*
-  setup a destructor to be called on free of a pointer
-  the destructor should return 0 on success, or -1 on failure.
-  if the destructor fails then the free is failed, and the memory can
-  be continued to be used
-*/
-_PUBLIC_ void _talloc_set_destructor(const void *ptr, int (*destructor)(void *))
-{
-	struct talloc_chunk *tc = talloc_chunk_from_ptr(ptr);
-	tc->destructor = destructor;
-}
-
-/*
-  increase the reference count on a piece of memory. 
-*/
-_PUBLIC_ int talloc_increase_ref_count(const void *ptr)
-{
-	if (unlikely(!talloc_reference(null_context, ptr))) {
-		return -1;
-	}
-	return 0;
-}
-
-/*
-  helper for talloc_reference()
-
-  this is referenced by a function pointer and should not be inline
-*/
-static int talloc_reference_destructor(struct talloc_reference_handle *handle)
-{
-	struct talloc_chunk *ptr_tc = talloc_chunk_from_ptr(handle->ptr);
-	_TLIST_REMOVE(ptr_tc->refs, handle);
-	return 0;
-}
-
-/*
-   more efficient way to add a name to a pointer - the name must point to a 
-   true string constant
-*/
-static inline void _talloc_set_name_const(const void *ptr, const char *name)
-{
-	struct talloc_chunk *tc = talloc_chunk_from_ptr(ptr);
-	tc->name = name;
-}
-
-/*
-  internal talloc_named_const()
-*/
-static inline void *_talloc_named_const(const void *context, size_t size, const char *name)
-{
-	void *ptr;
-
-	ptr = __talloc(context, size);
-	if (unlikely(ptr == NULL)) {
-		return NULL;
-	}
-
-	_talloc_set_name_const(ptr, name);
-
-	return ptr;
-}
-
-/*
-  make a secondary reference to a pointer, hanging off the given context.
-  the pointer remains valid until both the original caller and this given
-  context are freed.
-  
-  the major use for this is when two different structures need to reference the 
-  same underlying data, and you want to be able to free the two instances separately,
-  and in either order
-*/
-_PUBLIC_ void *_talloc_reference_loc(const void *context, const void *ptr, const char *location)
-{
-	struct talloc_chunk *tc;
-	struct talloc_reference_handle *handle;
-	if (unlikely(ptr == NULL)) return NULL;
-
-	tc = talloc_chunk_from_ptr(ptr);
-	handle = (struct talloc_reference_handle *)_talloc_named_const(context,
-						   sizeof(struct talloc_reference_handle),
-						   TALLOC_MAGIC_REFERENCE);
-	if (unlikely(handle == NULL)) return NULL;
-
-	/* note that we hang the destructor off the handle, not the
-	   main context as that allows the caller to still setup their
-	   own destructor on the context if they want to */
-	talloc_set_destructor(handle, talloc_reference_destructor);
-	handle->ptr = discard_const_p(void, ptr);
-	handle->location = location;
-	_TLIST_ADD(tc->refs, handle);
-	return handle->ptr;
-}
-
-static void *_talloc_steal_internal(const void *new_ctx, const void *ptr);
-
-static inline void _talloc_free_poolmem(struct talloc_chunk *tc,
-					const char *location)
-{
-	struct talloc_chunk *pool;
-	void *next_tc;
-	unsigned int *pool_object_count;
-
-	pool = (struct talloc_chunk *)tc->pool;
-	next_tc = TC_POOLMEM_NEXT_CHUNK(tc);
-
-	tc->flags |= TALLOC_FLAG_FREE;
-
-	/* we mark the freed memory with where we called the free
-	 * from. This means on a double free error we can report where
-	 * the first free came from
-	 */
-	tc->name = location;
-
-	TC_INVALIDATE_FULL_CHUNK(tc);
-
-	pool_object_count = talloc_pool_objectcount(pool);
-
-	if (unlikely(*pool_object_count == 0)) {
-		talloc_abort("Pool object count zero!");
-		return;
-	}
-
-	*pool_object_count -= 1;
-
-	if (unlikely(*pool_object_count == 1 && !(pool->flags & TALLOC_FLAG_FREE))) {
-		/*
-		 * if there is just one object left in the pool
-		 * and pool->flags does not have TALLOC_FLAG_FREE,
-		 * it means this is the pool itself and
-		 * the rest is available for new objects
-		 * again.
-		 */
-		pool->pool = TC_POOL_FIRST_CHUNK(pool);
-		TC_INVALIDATE_POOL(pool);
-	} else if (unlikely(*pool_object_count == 0)) {
-		/*
-		 * we mark the freed memory with where we called the free
-		 * from. This means on a double free error we can report where
-		 * the first free came from
-		 */
-		pool->name = location;
-
-		TC_INVALIDATE_FULL_CHUNK(pool);
-		free(pool);
-	} else if (pool->pool == next_tc) {
-		/*
-		 * if pool->pool still points to end of
-		 * 'tc' (which is stored in the 'next_tc' variable),
-		 * we can reclaim the memory of 'tc'.
-		 */
-		pool->pool = tc;
-	}
-}
-
-static inline void _talloc_free_children_internal(struct talloc_chunk *tc,
-						  void *ptr,
-						  const char *location);
-
-/* 
-   internal talloc_free call
-*/
-static inline int _talloc_free_internal(void *ptr, const char *location)
-{
-	struct talloc_chunk *tc;
-
-	if (unlikely(ptr == NULL)) {
-		return -1;
-	}
-
-	/* possibly initialised the talloc fill value */
-	if (unlikely(!talloc_fill.initialised)) {
-		const char *fill = getenv(TALLOC_FILL_ENV);
-		if (fill != NULL) {
-			talloc_fill.enabled = true;
-			talloc_fill.fill_value = strtoul(fill, NULL, 0);
-		}
-		talloc_fill.initialised = true;
-	}
-
-	tc = talloc_chunk_from_ptr(ptr);
-
-	if (unlikely(tc->refs)) {
-		int is_child;
-		/* check if this is a reference from a child or
-		 * grandchild back to it's parent or grandparent
-		 *
-		 * in that case we need to remove the reference and
-		 * call another instance of talloc_free() on the current
-		 * pointer.
-		 */
-		is_child = talloc_is_parent(tc->refs, ptr);
-		_talloc_free_internal(tc->refs, location);
-		if (is_child) {
-			return _talloc_free_internal(ptr, location);
-		}
-		return -1;
-	}
-
-	if (unlikely(tc->flags & TALLOC_FLAG_LOOP)) {
-		/* we have a free loop - stop looping */
-		return 0;
-	}
-
-	if (unlikely(tc->destructor)) {
-		talloc_destructor_t d = tc->destructor;
-		if (d == (talloc_destructor_t)-1) {
-			return -1;
-		}
-		tc->destructor = (talloc_destructor_t)-1;
-		if (d(ptr) == -1) {
-			tc->destructor = d;
-			return -1;
-		}
-		tc->destructor = NULL;
-	}
-
-	if (tc->parent) {
-		_TLIST_REMOVE(tc->parent->child, tc);
-		if (tc->parent->child) {
-			tc->parent->child->parent = tc->parent;
-		}
-	} else {
-		if (tc->prev) tc->prev->next = tc->next;
-		if (tc->next) tc->next->prev = tc->prev;
-		tc->prev = tc->next = NULL;
-	}
-
-	tc->flags |= TALLOC_FLAG_LOOP;
-
-	_talloc_free_children_internal(tc, ptr, location);
-
-	tc->flags |= TALLOC_FLAG_FREE;
-
-	/* we mark the freed memory with where we called the free
-	 * from. This means on a double free error we can report where
-	 * the first free came from
-	 */
-	tc->name = location;
-
-	if (tc->flags & TALLOC_FLAG_POOL) {
-		unsigned int *pool_object_count;
-
-		pool_object_count = talloc_pool_objectcount(tc);
-
-		if (unlikely(*pool_object_count == 0)) {
-			talloc_abort("Pool object count zero!");
-			return 0;
-		}
-
-		*pool_object_count -= 1;
-
-		if (unlikely(*pool_object_count == 0)) {
-			TC_INVALIDATE_FULL_CHUNK(tc);
-			free(tc);
-		}
-	} else if (tc->flags & TALLOC_FLAG_POOLMEM) {
-		_talloc_free_poolmem(tc, location);
-	} else {
-		TC_INVALIDATE_FULL_CHUNK(tc);
-		free(tc);
-	}
-	return 0;
-}
-
-/* 
-   move a lump of memory from one talloc context to another return the
-   ptr on success, or NULL if it could not be transferred.
-   passing NULL as ptr will always return NULL with no side effects.
-*/
-static void *_talloc_steal_internal(const void *new_ctx, const void *ptr)
-{
-	struct talloc_chunk *tc, *new_tc;
-
-	if (unlikely(!ptr)) {
-		return NULL;
-	}
-
-	if (unlikely(new_ctx == NULL)) {
-		new_ctx = null_context;
-	}
-
-	tc = talloc_chunk_from_ptr(ptr);
-
-	if (unlikely(new_ctx == NULL)) {
-		if (tc->parent) {
-			_TLIST_REMOVE(tc->parent->child, tc);
-			if (tc->parent->child) {
-				tc->parent->child->parent = tc->parent;
-			}
-		} else {
-			if (tc->prev) tc->prev->next = tc->next;
-			if (tc->next) tc->next->prev = tc->prev;
-		}
-		
-		tc->parent = tc->next = tc->prev = NULL;
-		return discard_const_p(void, ptr);
-	}
-
-	new_tc = talloc_chunk_from_ptr(new_ctx);
-
-	if (unlikely(tc == new_tc || tc->parent == new_tc)) {
-		return discard_const_p(void, ptr);
-	}
-
-	if (tc->parent) {
-		_TLIST_REMOVE(tc->parent->child, tc);
-		if (tc->parent->child) {
-			tc->parent->child->parent = tc->parent;
-		}
-	} else {
-		if (tc->prev) tc->prev->next = tc->next;
-		if (tc->next) tc->next->prev = tc->prev;
-		tc->prev = tc->next = NULL;
-	}
-
-	tc->parent = new_tc;
-	if (new_tc->child) new_tc->child->parent = NULL;
-	_TLIST_ADD(new_tc->child, tc);
-
-	return discard_const_p(void, ptr);
-}
-
-/*
-   move a lump of memory from one talloc context to another return the
-   ptr on success, or NULL if it could not be transferred.
-   passing NULL as ptr will always return NULL with no side effects.
-*/
-_PUBLIC_ void *_talloc_steal_loc(const void *new_ctx, const void *ptr, const char *location)
-{
-	struct talloc_chunk *tc;
-
-	if (unlikely(ptr == NULL)) {
-		return NULL;
-	}
-
-	tc = talloc_chunk_from_ptr(ptr);
-
-	if (unlikely(tc->refs != NULL) && talloc_parent(ptr) != new_ctx) {
-		struct talloc_reference_handle *h;
-
-		talloc_log("WARNING: talloc_steal with references at %s\n",
-			   location);
-
-		for (h=tc->refs; h; h=h->next) {
-			talloc_log("\treference at %s\n",
-				   h->location);
-		}
-	}
-
-#if 0
-	/* this test is probably too expensive to have on in the
-	   normal build, but it useful for debugging */
-	if (talloc_is_parent(new_ctx, ptr)) {
-		talloc_log("WARNING: stealing into talloc child at %s\n", location);
-	}
-#endif
-
-	return _talloc_steal_internal(new_ctx, ptr);
-}
-
-/*
-   this is like a talloc_steal(), but you must supply the old
-   parent. This resolves the ambiguity in a talloc_steal() which is
-   called on a context that has more than one parent (via references)
-
-   The old parent can be either a reference or a parent
-*/
-_PUBLIC_ void *talloc_reparent(const void *old_parent, const void *new_parent, const void *ptr)
-{
-	struct talloc_chunk *tc;
-	struct talloc_reference_handle *h;
-
-	if (unlikely(ptr == NULL)) {
-		return NULL;
-	}
-
-	if (old_parent == talloc_parent(ptr)) {
-		return _talloc_steal_internal(new_parent, ptr);
-	}
-
-	tc = talloc_chunk_from_ptr(ptr);
-	for (h=tc->refs;h;h=h->next) {
-		if (talloc_parent(h) == old_parent) {
-			if (_talloc_steal_internal(new_parent, h) != h) {
-				return NULL;
-			}
-			return discard_const_p(void, ptr);
-		}
-	}
-
-	/* it wasn't a parent */
-	return NULL;
-}
-
-/*
-  remove a secondary reference to a pointer. This undo's what
-  talloc_reference() has done. The context and pointer arguments
-  must match those given to a talloc_reference()
-*/
-static inline int talloc_unreference(const void *context, const void *ptr)
-{
-	struct talloc_chunk *tc = talloc_chunk_from_ptr(ptr);
-	struct talloc_reference_handle *h;
-
-	if (unlikely(context == NULL)) {
-		context = null_context;
-	}
-
-	for (h=tc->refs;h;h=h->next) {
-		struct talloc_chunk *p = talloc_parent_chunk(h);
-		if (p == NULL) {
-			if (context == NULL) break;
-		} else if (TC_PTR_FROM_CHUNK(p) == context) {
-			break;
-		}
-	}
-	if (h == NULL) {
-		return -1;
-	}
-
-	return _talloc_free_internal(h, __location__);
-}
-
-/*
-  remove a specific parent context from a pointer. This is a more
-  controlled variant of talloc_free()
-*/
-_PUBLIC_ int talloc_unlink(const void *context, void *ptr)
-{
-	struct talloc_chunk *tc_p, *new_p, *tc_c;
-	void *new_parent;
-
-	if (ptr == NULL) {
-		return -1;
-	}
-
-	if (context == NULL) {
-		context = null_context;
-	}
-
-	if (talloc_unreference(context, ptr) == 0) {
-		return 0;
-	}
-
-	if (context != NULL) {
-		tc_c = talloc_chunk_from_ptr(context);
-	} else {
-		tc_c = NULL;
-	}
-	if (tc_c != talloc_parent_chunk(ptr)) {
-		return -1;
-	}
-	
-	tc_p = talloc_chunk_from_ptr(ptr);
-
-	if (tc_p->refs == NULL) {
-		return _talloc_free_internal(ptr, __location__);
-	}
-
-	new_p = talloc_parent_chunk(tc_p->refs);
-	if (new_p) {
-		new_parent = TC_PTR_FROM_CHUNK(new_p);
-	} else {
-		new_parent = NULL;
-	}
-
-	if (talloc_unreference(new_parent, ptr) != 0) {
-		return -1;
-	}
-
-	_talloc_steal_internal(new_parent, ptr);
-
-	return 0;
-}
-
-/*
-  add a name to an existing pointer - va_list version
-*/
-static inline const char *talloc_set_name_v(const void *ptr, const char *fmt, va_list ap) PRINTF_ATTRIBUTE(2,0);
-
-static inline const char *talloc_set_name_v(const void *ptr, const char *fmt, va_list ap)
-{
-	struct talloc_chunk *tc = talloc_chunk_from_ptr(ptr);
-	tc->name = talloc_vasprintf(ptr, fmt, ap);
-	if (likely(tc->name)) {
-		_talloc_set_name_const(tc->name, ".name");
-	}
-	return tc->name;
-}
-
-/*
-  add a name to an existing pointer
-*/
-_PUBLIC_ const char *talloc_set_name(const void *ptr, const char *fmt, ...)
-{
-	const char *name;
-	va_list ap;
-	va_start(ap, fmt);
-	name = talloc_set_name_v(ptr, fmt, ap);
-	va_end(ap);
-	return name;
-}
-
-
-/*
-  create a named talloc pointer. Any talloc pointer can be named, and
-  talloc_named() operates just like talloc() except that it allows you
-  to name the pointer.
-*/
-_PUBLIC_ void *talloc_named(const void *context, size_t size, const char *fmt, ...)
-{
-	va_list ap;
-	void *ptr;
-	const char *name;
-
-	ptr = __talloc(context, size);
-	if (unlikely(ptr == NULL)) return NULL;
-
-	va_start(ap, fmt);
-	name = talloc_set_name_v(ptr, fmt, ap);
-	va_end(ap);
-
-	if (unlikely(name == NULL)) {
-		_talloc_free_internal(ptr, __location__);
-		return NULL;
-	}
-
-	return ptr;
-}
-
-/*
-  return the name of a talloc ptr, or "UNNAMED"
-*/
-_PUBLIC_ const char *talloc_get_name(const void *ptr)
-{
-	struct talloc_chunk *tc = talloc_chunk_from_ptr(ptr);
-	if (unlikely(tc->name == TALLOC_MAGIC_REFERENCE)) {
-		return ".reference";
-	}
-	if (likely(tc->name)) {
-		return tc->name;
-	}
-	return "UNNAMED";
-}
-
-
-/*
-  check if a pointer has the given name. If it does, return the pointer,
-  otherwise return NULL
-*/
-_PUBLIC_ void *talloc_check_name(const void *ptr, const char *name)
-{
-	const char *pname;
-	if (unlikely(ptr == NULL)) return NULL;
-	pname = talloc_get_name(ptr);
-	if (likely(pname == name || strcmp(pname, name) == 0)) {
-		return discard_const_p(void, ptr);
-	}
-	return NULL;
-}
-
-static void talloc_abort_type_mismatch(const char *location,
-					const char *name,
-					const char *expected)
-{
-	const char *reason;
-
-	reason = talloc_asprintf(NULL,
-				 "%s: Type mismatch: name[%s] expected[%s]",
-				 location,
-				 name?name:"NULL",
-				 expected);
-	if (!reason) {
-		reason = "Type mismatch";
-	}
-
-	talloc_abort(reason);
-}
-
-_PUBLIC_ void *_talloc_get_type_abort(const void *ptr, const char *name, const char *location)
-{
-	const char *pname;
-
-	if (unlikely(ptr == NULL)) {
-		talloc_abort_type_mismatch(location, NULL, name);
-		return NULL;
-	}
-
-	pname = talloc_get_name(ptr);
-	if (likely(pname == name || strcmp(pname, name) == 0)) {
-		return discard_const_p(void, ptr);
-	}
-
-	talloc_abort_type_mismatch(location, pname, name);
-	return NULL;
-}
-
-/*
-  this is for compatibility with older versions of talloc
-*/
-_PUBLIC_ void *talloc_init(const char *fmt, ...)
-{
-	va_list ap;
-	void *ptr;
-	const char *name;
-
-	ptr = __talloc(NULL, 0);
-	if (unlikely(ptr == NULL)) return NULL;
-
-	va_start(ap, fmt);
-	name = talloc_set_name_v(ptr, fmt, ap);
-	va_end(ap);
-
-	if (unlikely(name == NULL)) {
-		_talloc_free_internal(ptr, __location__);
-		return NULL;
-	}
-
-	return ptr;
-}
-
-static inline void _talloc_free_children_internal(struct talloc_chunk *tc,
-						  void *ptr,
-						  const char *location)
-{
-	while (tc->child) {
-		/* we need to work out who will own an abandoned child
-		   if it cannot be freed. In priority order, the first
-		   choice is owner of any remaining reference to this
-		   pointer, the second choice is our parent, and the
-		   final choice is the null context. */
-		void *child = TC_PTR_FROM_CHUNK(tc->child);
-		const void *new_parent = null_context;
-		if (unlikely(tc->child->refs)) {
-			struct talloc_chunk *p = talloc_parent_chunk(tc->child->refs);
-			if (p) new_parent = TC_PTR_FROM_CHUNK(p);
-		}
-		if (unlikely(_talloc_free_internal(child, location) == -1)) {
-			if (new_parent == null_context) {
-				struct talloc_chunk *p = talloc_parent_chunk(ptr);
-				if (p) new_parent = TC_PTR_FROM_CHUNK(p);
-			}
-			_talloc_steal_internal(new_parent, child);
-		}
-	}
-}
-
-/*
-  this is a replacement for the Samba3 talloc_destroy_pool functionality. It
-  should probably not be used in new code. It's in here to keep the talloc
-  code consistent across Samba 3 and 4.
-*/
-_PUBLIC_ void talloc_free_children(void *ptr)
-{
-	struct talloc_chunk *tc_name = NULL;
-	struct talloc_chunk *tc;
-
-	if (unlikely(ptr == NULL)) {
-		return;
-	}
-
-	tc = talloc_chunk_from_ptr(ptr);
-
-	/* we do not want to free the context name if it is a child .. */
-	if (likely(tc->child)) {
-		for (tc_name = tc->child; tc_name; tc_name = tc_name->next) {
-			if (tc->name == TC_PTR_FROM_CHUNK(tc_name)) break;
-		}
-		if (tc_name) {
-			_TLIST_REMOVE(tc->child, tc_name);
-			if (tc->child) {
-				tc->child->parent = tc;
-			}
-		}
-	}
-
-	_talloc_free_children_internal(tc, ptr, __location__);
-
-	/* .. so we put it back after all other children have been freed */
-	if (tc_name) {
-		if (tc->child) {
-			tc->child->parent = NULL;
-		}
-		tc_name->parent = tc;
-		_TLIST_ADD(tc->child, tc_name);
-	}
-}
-
-/* 
-   Allocate a bit of memory as a child of an existing pointer
-*/
-_PUBLIC_ void *_talloc(const void *context, size_t size)
-{
-	return __talloc(context, size);
-}
-
-/*
-  externally callable talloc_set_name_const()
-*/
-_PUBLIC_ void talloc_set_name_const(const void *ptr, const char *name)
-{
-	_talloc_set_name_const(ptr, name);
-}
-
-/*
-  create a named talloc pointer. Any talloc pointer can be named, and
-  talloc_named() operates just like talloc() except that it allows you
-  to name the pointer.
-*/
-_PUBLIC_ void *talloc_named_const(const void *context, size_t size, const char *name)
-{
-	return _talloc_named_const(context, size, name);
-}
-
-/* 
-   free a talloc pointer. This also frees all child pointers of this 
-   pointer recursively
-
-   return 0 if the memory is actually freed, otherwise -1. The memory
-   will not be freed if the ref_count is > 1 or the destructor (if
-   any) returns non-zero
-*/
-_PUBLIC_ int _talloc_free(void *ptr, const char *location)
-{
-	struct talloc_chunk *tc;
-
-	if (unlikely(ptr == NULL)) {
-		return -1;
-	}
-
-	tc = talloc_chunk_from_ptr(ptr);
-
-	if (unlikely(tc->refs != NULL)) {
-		struct talloc_reference_handle *h;
-
-		if (talloc_parent(ptr) == null_context && tc->refs->next == NULL) {
-			/* in this case we do know which parent should
-			   get this pointer, as there is really only
-			   one parent */
-			return talloc_unlink(null_context, ptr);
-		}
-
-		talloc_log("ERROR: talloc_free with references at %s\n",
-			   location);
-
-		for (h=tc->refs; h; h=h->next) {
-			talloc_log("\treference at %s\n",
-				   h->location);
-		}
-		return -1;
-	}
-
-	return _talloc_free_internal(ptr, location);
-}
-
-
-
-/*
-  A talloc version of realloc. The context argument is only used if
-  ptr is NULL
-*/
-_PUBLIC_ void *_talloc_realloc(const void *context, void *ptr, size_t size, const char *name)
-{
-	struct talloc_chunk *tc;
-	void *new_ptr;
-	bool malloced = false;
-	struct talloc_chunk *pool_tc = NULL;
-
-	/* size zero is equivalent to free() */
-	if (unlikely(size == 0)) {
-		talloc_unlink(context, ptr);
-		return NULL;
-	}
-
-	if (unlikely(size >= MAX_TALLOC_SIZE)) {
-		return NULL;
-	}
-
-	/* realloc(NULL) is equivalent to malloc() */
-	if (ptr == NULL) {
-		return _talloc_named_const(context, size, name);
-	}
-
-	tc = talloc_chunk_from_ptr(ptr);
-
-	/* don't allow realloc on referenced pointers */
-	if (unlikely(tc->refs)) {
-		return NULL;
-	}
-
-	/* don't let anybody try to realloc a talloc_pool */
-	if (unlikely(tc->flags & TALLOC_FLAG_POOL)) {
-		return NULL;
-	}
-
-	/* don't let anybody try to realloc a talloc_pool */
-	if (unlikely(tc->flags & TALLOC_FLAG_POOLMEM)) {
-		pool_tc = (struct talloc_chunk *)tc->pool;
-	}
-
-#if (ALWAYS_REALLOC == 0)
-	/* don't shrink if we have less than 1k to gain */
-	if (size < tc->size) {
-		if (pool_tc) {
-			void *next_tc = TC_POOLMEM_NEXT_CHUNK(tc);
-			TC_INVALIDATE_SHRINK_CHUNK(tc, size);
-			tc->size = size;
-			if (next_tc == pool_tc->pool) {
-				pool_tc->pool = TC_POOLMEM_NEXT_CHUNK(tc);
-			}
-			return ptr;
-		} else if ((tc->size - size) < 1024) {
-			/*
-			 * if we call TC_INVALIDATE_SHRINK_CHUNK() here
-			 * we would need to call TC_UNDEFINE_GROW_CHUNK()
-			 * after each realloc call, which slows down
-			 * testing a lot :-(.
-			 *
-			 * That is why we only mark memory as undefined here.
-			 */
-			TC_UNDEFINE_SHRINK_CHUNK(tc, size);
-
-			/* do not shrink if we have less than 1k to gain */
-			tc->size = size;
-			return ptr;
-		}
-	} else if (tc->size == size) {
-		/*
-		 * do not change the pointer if it is exactly
-		 * the same size.
-		 */
-		return ptr;
-	}
-#endif
-
-	/* by resetting magic we catch users of the old memory */
-	tc->flags |= TALLOC_FLAG_FREE;
-
-#if ALWAYS_REALLOC
-	if (pool_tc) {
-		new_ptr = talloc_alloc_pool(tc, size + TC_HDR_SIZE);
-		*talloc_pool_objectcount(pool_tc) -= 1;
-
-		if (new_ptr == NULL) {
-			new_ptr = malloc(TC_HDR_SIZE+size);
-			malloced = true;
-		}
-
-		if (new_ptr) {
-			memcpy(new_ptr, tc, MIN(tc->size,size) + TC_HDR_SIZE);
-			TC_INVALIDATE_FULL_CHUNK(tc);
-		}
-	} else {
-		new_ptr = malloc(size + TC_HDR_SIZE);
-		if (new_ptr) {
-			memcpy(new_ptr, tc, MIN(tc->size, size) + TC_HDR_SIZE);
-			free(tc);
-		}
-	}
-#else
-	if (pool_tc) {
-		void *next_tc = TC_POOLMEM_NEXT_CHUNK(tc);
-		size_t old_chunk_size = TC_POOLMEM_CHUNK_SIZE(tc);
-		size_t new_chunk_size = TC_ALIGN16(TC_HDR_SIZE + size);
-		size_t space_needed;
-		size_t space_left;
-		unsigned int chunk_count = *talloc_pool_objectcount(pool_tc);
-
-		if (!(pool_tc->flags & TALLOC_FLAG_FREE)) {
-			chunk_count -= 1;
-		}
-
-		if (chunk_count == 1) {
-			/*
-			 * optimize for the case where 'tc' is the only
-			 * chunk in the pool.
-			 */
-			space_needed = new_chunk_size;
-			space_left = pool_tc->size - TALLOC_POOL_HDR_SIZE;
-
-			if (space_left >= space_needed) {
-				size_t old_used = TC_HDR_SIZE + tc->size;
-				size_t new_used = TC_HDR_SIZE + size;
-				pool_tc->pool = TC_POOL_FIRST_CHUNK(pool_tc);
-#if defined(DEVELOPER) && defined(VALGRIND_MAKE_MEM_UNDEFINED)
-				/*
-				 * we need to prepare the memmove into
-				 * the unaccessable area.
-				 */
-				{
-					size_t diff = PTR_DIFF(tc, pool_tc->pool);
-					size_t flen = MIN(diff, old_used);
-					char *fptr = (char *)pool_tc->pool;
-					VALGRIND_MAKE_MEM_UNDEFINED(fptr, flen);
-				}
-#endif
-				memmove(pool_tc->pool, tc, old_used);
-				new_ptr = pool_tc->pool;
-
-				tc = (struct talloc_chunk *)new_ptr;
-				TC_UNDEFINE_GROW_CHUNK(tc, size);
-
-				/*
-				 * first we do not align the pool pointer
-				 * because we want to invalidate the padding
-				 * too.
-				 */
-				pool_tc->pool = new_used + (char *)new_ptr;
-				TC_INVALIDATE_POOL(pool_tc);
-
-				/* now the aligned pointer */
-				pool_tc->pool = new_chunk_size + (char *)new_ptr;
-				goto got_new_ptr;
-			}
-
-			next_tc = NULL;
-		}
-
-		if (new_chunk_size == old_chunk_size) {
-			TC_UNDEFINE_GROW_CHUNK(tc, size);
-			tc->flags &= ~TALLOC_FLAG_FREE;
-			tc->size = size;
-			return ptr;
-		}
-
-		if (next_tc == pool_tc->pool) {
-			/*
-			 * optimize for the case where 'tc' is the last
-			 * chunk in the pool.
-			 */
-			space_needed = new_chunk_size - old_chunk_size;
-			space_left = TC_POOL_SPACE_LEFT(pool_tc);
-
-			if (space_left >= space_needed) {
-				TC_UNDEFINE_GROW_CHUNK(tc, size);
-				tc->flags &= ~TALLOC_FLAG_FREE;
-				tc->size = size;
-				pool_tc->pool = TC_POOLMEM_NEXT_CHUNK(tc);
-				return ptr;
-			}
-		}
-
-		new_ptr = talloc_alloc_pool(tc, size + TC_HDR_SIZE);
-
-		if (new_ptr == NULL) {
-			new_ptr = malloc(TC_HDR_SIZE+size);
-			malloced = true;
-		}
-
-		if (new_ptr) {
-			memcpy(new_ptr, tc, MIN(tc->size,size) + TC_HDR_SIZE);
-
-			_talloc_free_poolmem(tc, __location__ "_talloc_realloc");
-		}
-	}
-	else {
-		new_ptr = realloc(tc, size + TC_HDR_SIZE);
-	}
-got_new_ptr:
-#endif
-	if (unlikely(!new_ptr)) {	
-		tc->flags &= ~TALLOC_FLAG_FREE; 
-		return NULL; 
-	}
-
-	tc = (struct talloc_chunk *)new_ptr;
-	tc->flags &= ~TALLOC_FLAG_FREE;
-	if (malloced) {
-		tc->flags &= ~TALLOC_FLAG_POOLMEM;
-	}
-	if (tc->parent) {
-		tc->parent->child = tc;
-	}
-	if (tc->child) {
-		tc->child->parent = tc;
-	}
-
-	if (tc->prev) {
-		tc->prev->next = tc;
-	}
-	if (tc->next) {
-		tc->next->prev = tc;
-	}
-
-	tc->size = size;
-	_talloc_set_name_const(TC_PTR_FROM_CHUNK(tc), name);
-
-	return TC_PTR_FROM_CHUNK(tc);
-}
-
-/*
-  a wrapper around talloc_steal() for situations where you are moving a pointer
-  between two structures, and want the old pointer to be set to NULL
-*/
-_PUBLIC_ void *_talloc_move(const void *new_ctx, const void *_pptr)
-{
-	const void **pptr = discard_const_p(const void *,_pptr);
-	void *ret = talloc_steal(new_ctx, discard_const_p(void, *pptr));
-	(*pptr) = NULL;
-	return ret;
-}
-
-/*
-  return the total size of a talloc pool (subtree)
-*/
-_PUBLIC_ size_t talloc_total_size(const void *ptr)
-{
-	size_t total = 0;
-	struct talloc_chunk *c, *tc;
-
-	if (ptr == NULL) {
-		ptr = null_context;
-	}
-	if (ptr == NULL) {
-		return 0;
-	}
-
-	tc = talloc_chunk_from_ptr(ptr);
-
-	if (tc->flags & TALLOC_FLAG_LOOP) {
-		return 0;
-	}
-
-	tc->flags |= TALLOC_FLAG_LOOP;
-
-	if (likely(tc->name != TALLOC_MAGIC_REFERENCE)) {
-		total = tc->size;
-	}
-	for (c=tc->child;c;c=c->next) {
-		total += talloc_total_size(TC_PTR_FROM_CHUNK(c));
-	}
-
-	tc->flags &= ~TALLOC_FLAG_LOOP;
-
-	return total;
-}
-
-/*
-  return the total number of blocks in a talloc pool (subtree)
-*/
-_PUBLIC_ size_t talloc_total_blocks(const void *ptr)
-{
-	size_t total = 0;
-	struct talloc_chunk *c, *tc;
-
-	if (ptr == NULL) {
-		ptr = null_context;
-	}
-	if (ptr == NULL) {
-		return 0;
-	}
-
-	tc = talloc_chunk_from_ptr(ptr);
-
-	if (tc->flags & TALLOC_FLAG_LOOP) {
-		return 0;
-	}
-
-	tc->flags |= TALLOC_FLAG_LOOP;
-
-	total++;
-	for (c=tc->child;c;c=c->next) {
-		total += talloc_total_blocks(TC_PTR_FROM_CHUNK(c));
-	}
-
-	tc->flags &= ~TALLOC_FLAG_LOOP;
-
-	return total;
-}
-
-/*
-  return the number of external references to a pointer
-*/
-_PUBLIC_ size_t talloc_reference_count(const void *ptr)
-{
-	struct talloc_chunk *tc = talloc_chunk_from_ptr(ptr);
-	struct talloc_reference_handle *h;
-	size_t ret = 0;
-
-	for (h=tc->refs;h;h=h->next) {
-		ret++;
-	}
-	return ret;
-}
-
-/*
-  report on memory usage by all children of a pointer, giving a full tree view
-*/
-_PUBLIC_ void talloc_report_depth_cb(const void *ptr, int depth, int max_depth,
-			    void (*callback)(const void *ptr,
-			  		     int depth, int max_depth,
-					     int is_ref,
-					     void *private_data),
-			    void *private_data)
-{
-	struct talloc_chunk *c, *tc;
-
-	if (ptr == NULL) {
-		ptr = null_context;
-	}
-	if (ptr == NULL) return;
-
-	tc = talloc_chunk_from_ptr(ptr);
-
-	if (tc->flags & TALLOC_FLAG_LOOP) {
-		return;
-	}
-
-	callback(ptr, depth, max_depth, 0, private_data);
-
-	if (max_depth >= 0 && depth >= max_depth) {
-		return;
-	}
-
-	tc->flags |= TALLOC_FLAG_LOOP;
-	for (c=tc->child;c;c=c->next) {
-		if (c->name == TALLOC_MAGIC_REFERENCE) {
-			struct talloc_reference_handle *h = (struct talloc_reference_handle *)TC_PTR_FROM_CHUNK(c);
-			callback(h->ptr, depth + 1, max_depth, 1, private_data);
-		} else {
-			talloc_report_depth_cb(TC_PTR_FROM_CHUNK(c), depth + 1, max_depth, callback, private_data);
-		}
-	}
-	tc->flags &= ~TALLOC_FLAG_LOOP;
-}
-
-static void talloc_report_depth_FILE_helper(const void *ptr, int depth, int max_depth, int is_ref, void *_f)
-{
-	const char *name = talloc_get_name(ptr);
-	FILE *f = (FILE *)_f;
-
-	if (is_ref) {
-		fprintf(f, "%*sreference to: %s\n", depth*4, "", name);
-		return;
-	}
-
-	if (depth == 0) {
-		fprintf(f,"%stalloc report on '%s' (total %6lu bytes in %3lu blocks)\n", 
-			(max_depth < 0 ? "full " :""), name,
-			(unsigned long)talloc_total_size(ptr),
-			(unsigned long)talloc_total_blocks(ptr));
-		return;
-	}
-
-	fprintf(f, "%*s%-30s contains %6lu bytes in %3lu blocks (ref %d) %p\n", 
-		depth*4, "",
-		name,
-		(unsigned long)talloc_total_size(ptr),
-		(unsigned long)talloc_total_blocks(ptr),
-		(int)talloc_reference_count(ptr), ptr);
-
-#if 0
-	fprintf(f, "content: ");
-	if (talloc_total_size(ptr)) {
-		int tot = talloc_total_size(ptr);
-		int i;
-
-		for (i = 0; i < tot; i++) {
-			if ((((char *)ptr)[i] > 31) && (((char *)ptr)[i] < 126)) {
-				fprintf(f, "%c", ((char *)ptr)[i]);
-			} else {
-				fprintf(f, "~%02x", ((char *)ptr)[i]);
-			}
-		}
-	}
-	fprintf(f, "\n");
-#endif
-}
-
-/*
-  report on memory usage by all children of a pointer, giving a full tree view
-*/
-_PUBLIC_ void talloc_report_depth_file(const void *ptr, int depth, int max_depth, FILE *f)
-{
-	if (f) {
-		talloc_report_depth_cb(ptr, depth, max_depth, talloc_report_depth_FILE_helper, f);
-		fflush(f);
-	}
-}
-
-/*
-  report on memory usage by all children of a pointer, giving a full tree view
-*/
-_PUBLIC_ void talloc_report_full(const void *ptr, FILE *f)
-{
-	talloc_report_depth_file(ptr, 0, -1, f);
-}
-
-/*
-  report on memory usage by all children of a pointer
-*/
-_PUBLIC_ void talloc_report(const void *ptr, FILE *f)
-{
-	talloc_report_depth_file(ptr, 0, 1, f);
-}
-
-/*
-  report on any memory hanging off the null context
-*/
-static void talloc_report_null(void)
-{
-	if (talloc_total_size(null_context) != 0) {
-		talloc_report(null_context, stderr);
-	}
-}
-
-/*
-  report on any memory hanging off the null context
-*/
-static void talloc_report_null_full(void)
-{
-	if (talloc_total_size(null_context) != 0) {
-		talloc_report_full(null_context, stderr);
-	}
-}
-
-/*
-  enable tracking of the NULL context
-*/
-_PUBLIC_ void talloc_enable_null_tracking(void)
-{
-	if (null_context == NULL) {
-		null_context = _talloc_named_const(NULL, 0, "null_context");
-		if (autofree_context != NULL) {
-			talloc_reparent(NULL, null_context, autofree_context);
-		}
-	}
-}
-
-/*
-  enable tracking of the NULL context, not moving the autofree context
-  into the NULL context. This is needed for the talloc testsuite
-*/
-_PUBLIC_ void talloc_enable_null_tracking_no_autofree(void)
-{
-	if (null_context == NULL) {
-		null_context = _talloc_named_const(NULL, 0, "null_context");
-	}
-}
-
-/*
-  disable tracking of the NULL context
-*/
-_PUBLIC_ void talloc_disable_null_tracking(void)
-{
-	if (null_context != NULL) {
-		/* we have to move any children onto the real NULL
-		   context */
-		struct talloc_chunk *tc, *tc2;
-		tc = talloc_chunk_from_ptr(null_context);
-		for (tc2 = tc->child; tc2; tc2=tc2->next) {
-			if (tc2->parent == tc) tc2->parent = NULL;
-			if (tc2->prev == tc) tc2->prev = NULL;
-		}
-		for (tc2 = tc->next; tc2; tc2=tc2->next) {
-			if (tc2->parent == tc) tc2->parent = NULL;
-			if (tc2->prev == tc) tc2->prev = NULL;
-		}
-		tc->child = NULL;
-		tc->next = NULL;
-	}
-	talloc_free(null_context);
-	null_context = NULL;
-}
-
-/*
-  enable leak reporting on exit
-*/
-_PUBLIC_ void talloc_enable_leak_report(void)
-{
-	talloc_enable_null_tracking();
-	atexit(talloc_report_null);
-}
-
-/*
-  enable full leak reporting on exit
-*/
-_PUBLIC_ void talloc_enable_leak_report_full(void)
-{
-	talloc_enable_null_tracking();
-	atexit(talloc_report_null_full);
-}
-
-/* 
-   talloc and zero memory. 
-*/
-_PUBLIC_ void *_talloc_zero(const void *ctx, size_t size, const char *name)
-{
-	void *p = _talloc_named_const(ctx, size, name);
-
-	if (p) {
-		memset(p, '\0', size);
-	}
-
-	return p;
-}
-
-/*
-  memdup with a talloc. 
-*/
-_PUBLIC_ void *_talloc_memdup(const void *t, const void *p, size_t size, const char *name)
-{
-	void *newp = _talloc_named_const(t, size, name);
-
-	if (likely(newp)) {
-		memcpy(newp, p, size);
-	}
-
-	return newp;
-}
-
-static inline char *__talloc_strlendup(const void *t, const char *p, size_t len)
-{
-	char *ret;
-
-	ret = (char *)__talloc(t, len + 1);
-	if (unlikely(!ret)) return NULL;
-
-	memcpy(ret, p, len);
-	ret[len] = 0;
-
-	_talloc_set_name_const(ret, ret);
-	return ret;
-}
-
-/*
-  strdup with a talloc
-*/
-_PUBLIC_ char *talloc_strdup(const void *t, const char *p)
-{
-	if (unlikely(!p)) return NULL;
-	return __talloc_strlendup(t, p, strlen(p));
-}
-
-/*
-  strndup with a talloc
-*/
-_PUBLIC_ char *talloc_strndup(const void *t, const char *p, size_t n)
-{
-	if (unlikely(!p)) return NULL;
-	return __talloc_strlendup(t, p, strnlen(p, n));
-}
-
-static inline char *__talloc_strlendup_append(char *s, size_t slen,
-					      const char *a, size_t alen)
-{
-	char *ret;
-
-	ret = talloc_realloc(NULL, s, char, slen + alen + 1);
-	if (unlikely(!ret)) return NULL;
-
-	/* append the string and the trailing \0 */
-	memcpy(&ret[slen], a, alen);
-	ret[slen+alen] = 0;
-
-	_talloc_set_name_const(ret, ret);
-	return ret;
-}
-
-/*
- * Appends at the end of the string.
- */
-_PUBLIC_ char *talloc_strdup_append(char *s, const char *a)
-{
-	if (unlikely(!s)) {
-		return talloc_strdup(NULL, a);
-	}
-
-	if (unlikely(!a)) {
-		return s;
-	}
-
-	return __talloc_strlendup_append(s, strlen(s), a, strlen(a));
-}
-
-/*
- * Appends at the end of the talloc'ed buffer,
- * not the end of the string.
- */
-_PUBLIC_ char *talloc_strdup_append_buffer(char *s, const char *a)
-{
-	size_t slen;
-
-	if (unlikely(!s)) {
-		return talloc_strdup(NULL, a);
-	}
-
-	if (unlikely(!a)) {
-		return s;
-	}
-
-	slen = talloc_get_size(s);
-	if (likely(slen > 0)) {
-		slen--;
-	}
-
-	return __talloc_strlendup_append(s, slen, a, strlen(a));
-}
-
-/*
- * Appends at the end of the string.
- */
-_PUBLIC_ char *talloc_strndup_append(char *s, const char *a, size_t n)
-{
-	if (unlikely(!s)) {
-		return talloc_strdup(NULL, a);
-	}
-
-	if (unlikely(!a)) {
-		return s;
-	}
-
-	return __talloc_strlendup_append(s, strlen(s), a, strnlen(a, n));
-}
-
-/*
- * Appends at the end of the talloc'ed buffer,
- * not the end of the string.
- */
-_PUBLIC_ char *talloc_strndup_append_buffer(char *s, const char *a, size_t n)
-{
-	size_t slen;
-
-	if (unlikely(!s)) {
-		return talloc_strdup(NULL, a);
-	}
-
-	if (unlikely(!a)) {
-		return s;
-	}
-
-	slen = talloc_get_size(s);
-	if (likely(slen > 0)) {
-		slen--;
-	}
-
-	return __talloc_strlendup_append(s, slen, a, strnlen(a, n));
-}
-
-#ifndef HAVE_VA_COPY
-#ifdef HAVE___VA_COPY
-#define va_copy(dest, src) __va_copy(dest, src)
-#else
-#define va_copy(dest, src) (dest) = (src)
-#endif
-#endif
-
-_PUBLIC_ char *talloc_vasprintf(const void *t, const char *fmt, va_list ap)
-{
-	int len;
-	char *ret;
-	va_list ap2;
-	char c;
-
-	/* this call looks strange, but it makes it work on older solaris boxes */
-	va_copy(ap2, ap);
-	len = vsnprintf(&c, 1, fmt, ap2);
-	va_end(ap2);
-	if (unlikely(len < 0)) {
-		return NULL;
-	}
-
-	ret = (char *)__talloc(t, len+1);
-	if (unlikely(!ret)) return NULL;
-
-	va_copy(ap2, ap);
-	vsnprintf(ret, len+1, fmt, ap2);
-	va_end(ap2);
-
-	_talloc_set_name_const(ret, ret);
-	return ret;
-}
-
-
-/*
-  Perform string formatting, and return a pointer to newly allocated
-  memory holding the result, inside a memory pool.
- */
-_PUBLIC_ char *talloc_asprintf(const void *t, const char *fmt, ...)
-{
-	va_list ap;
-	char *ret;
-
-	va_start(ap, fmt);
-	ret = talloc_vasprintf(t, fmt, ap);
-	va_end(ap);
-	return ret;
-}
-
-static inline char *__talloc_vaslenprintf_append(char *s, size_t slen,
-						 const char *fmt, va_list ap)
-						 PRINTF_ATTRIBUTE(3,0);
-
-static inline char *__talloc_vaslenprintf_append(char *s, size_t slen,
-						 const char *fmt, va_list ap)
-{
-	ssize_t alen;
-	va_list ap2;
-	char c;
-
-	va_copy(ap2, ap);
-	alen = vsnprintf(&c, 1, fmt, ap2);
-	va_end(ap2);
-
-	if (alen <= 0) {
-		/* Either the vsnprintf failed or the format resulted in
-		 * no characters being formatted. In the former case, we
-		 * ought to return NULL, in the latter we ought to return
-		 * the original string. Most current callers of this
-		 * function expect it to never return NULL.
-		 */
-		return s;
-	}
-
-	s = talloc_realloc(NULL, s, char, slen + alen + 1);
-	if (!s) return NULL;
-
-	va_copy(ap2, ap);
-	vsnprintf(s + slen, alen + 1, fmt, ap2);
-	va_end(ap2);
-
-	_talloc_set_name_const(s, s);
-	return s;
-}
-
-/**
- * Realloc @p s to append the formatted result of @p fmt and @p ap,
- * and return @p s, which may have moved.  Good for gradually
- * accumulating output into a string buffer. Appends at the end
- * of the string.
- **/
-_PUBLIC_ char *talloc_vasprintf_append(char *s, const char *fmt, va_list ap)
-{
-	if (unlikely(!s)) {
-		return talloc_vasprintf(NULL, fmt, ap);
-	}
-
-	return __talloc_vaslenprintf_append(s, strlen(s), fmt, ap);
-}
-
-/**
- * Realloc @p s to append the formatted result of @p fmt and @p ap,
- * and return @p s, which may have moved. Always appends at the
- * end of the talloc'ed buffer, not the end of the string.
- **/
-_PUBLIC_ char *talloc_vasprintf_append_buffer(char *s, const char *fmt, va_list ap)
-{
-	size_t slen;
-
-	if (unlikely(!s)) {
-		return talloc_vasprintf(NULL, fmt, ap);
-	}
-
-	slen = talloc_get_size(s);
-	if (likely(slen > 0)) {
-		slen--;
-	}
-
-	return __talloc_vaslenprintf_append(s, slen, fmt, ap);
-}
-
-/*
-  Realloc @p s to append the formatted result of @p fmt and return @p
-  s, which may have moved.  Good for gradually accumulating output
-  into a string buffer.
- */
-_PUBLIC_ char *talloc_asprintf_append(char *s, const char *fmt, ...)
-{
-	va_list ap;
-
-	va_start(ap, fmt);
-	s = talloc_vasprintf_append(s, fmt, ap);
-	va_end(ap);
-	return s;
-}
-
-/*
-  Realloc @p s to append the formatted result of @p fmt and return @p
-  s, which may have moved.  Good for gradually accumulating output
-  into a buffer.
- */
-_PUBLIC_ char *talloc_asprintf_append_buffer(char *s, const char *fmt, ...)
-{
-	va_list ap;
-
-	va_start(ap, fmt);
-	s = talloc_vasprintf_append_buffer(s, fmt, ap);
-	va_end(ap);
-	return s;
-}
-
-/*
-  alloc an array, checking for integer overflow in the array size
-*/
-_PUBLIC_ void *_talloc_array(const void *ctx, size_t el_size, unsigned count, const char *name)
-{
-	if (count >= MAX_TALLOC_SIZE/el_size) {
-		return NULL;
-	}
-	return _talloc_named_const(ctx, el_size * count, name);
-}
-
-/*
-  alloc an zero array, checking for integer overflow in the array size
-*/
-_PUBLIC_ void *_talloc_zero_array(const void *ctx, size_t el_size, unsigned count, const char *name)
-{
-	if (count >= MAX_TALLOC_SIZE/el_size) {
-		return NULL;
-	}
-	return _talloc_zero(ctx, el_size * count, name);
-}
-
-/*
-  realloc an array, checking for integer overflow in the array size
-*/
-_PUBLIC_ void *_talloc_realloc_array(const void *ctx, void *ptr, size_t el_size, unsigned count, const char *name)
-{
-	if (count >= MAX_TALLOC_SIZE/el_size) {
-		return NULL;
-	}
-	return _talloc_realloc(ctx, ptr, el_size * count, name);
-}
-
-/*
-  a function version of talloc_realloc(), so it can be passed as a function pointer
-  to libraries that want a realloc function (a realloc function encapsulates
-  all the basic capabilities of an allocation library, which is why this is useful)
-*/
-_PUBLIC_ void *talloc_realloc_fn(const void *context, void *ptr, size_t size)
-{
-	return _talloc_realloc(context, ptr, size, NULL);
-}
-
-
-static int talloc_autofree_destructor(void *ptr)
-{
-	autofree_context = NULL;
-	return 0;
-}
-
-static void talloc_autofree(void)
-{
-	talloc_free(autofree_context);
-}
-
-/*
-  return a context which will be auto-freed on exit
-  this is useful for reducing the noise in leak reports
-*/
-_PUBLIC_ void *talloc_autofree_context(void)
-{
-	if (autofree_context == NULL) {
-		autofree_context = _talloc_named_const(NULL, 0, "autofree_context");
-		talloc_set_destructor(autofree_context, talloc_autofree_destructor);
-		atexit(talloc_autofree);
-	}
-	return autofree_context;
-}
-
-_PUBLIC_ size_t talloc_get_size(const void *context)
-{
-	struct talloc_chunk *tc;
-
-	if (context == NULL) {
-		context = null_context;
-	}
-	if (context == NULL) {
-		return 0;
-	}
-
-	tc = talloc_chunk_from_ptr(context);
-
-	return tc->size;
-}
-
-/*
-  find a parent of this context that has the given name, if any
-*/
-_PUBLIC_ void *talloc_find_parent_byname(const void *context, const char *name)
-{
-	struct talloc_chunk *tc;
-
-	if (context == NULL) {
-		return NULL;
-	}
-
-	tc = talloc_chunk_from_ptr(context);
-	while (tc) {
-		if (tc->name && strcmp(tc->name, name) == 0) {
-			return TC_PTR_FROM_CHUNK(tc);
-		}
-		while (tc && tc->prev) tc = tc->prev;
-		if (tc) {
-			tc = tc->parent;
-		}
-	}
-	return NULL;
-}
-
-/*
-  show the parentage of a context
-*/
-_PUBLIC_ void talloc_show_parents(const void *context, FILE *file)
-{
-	struct talloc_chunk *tc;
-
-	if (context == NULL) {
-		fprintf(file, "talloc no parents for NULL\n");
-		return;
-	}
-
-	tc = talloc_chunk_from_ptr(context);
-	fprintf(file, "talloc parents of '%s'\n", talloc_get_name(context));
-	while (tc) {
-		fprintf(file, "\t'%s'\n", talloc_get_name(TC_PTR_FROM_CHUNK(tc)));
-		while (tc && tc->prev) tc = tc->prev;
-		if (tc) {
-			tc = tc->parent;
-		}
-	}
-	fflush(file);
-}
-
-/*
-  return 1 if ptr is a parent of context
-*/
-static int _talloc_is_parent(const void *context, const void *ptr, int depth)
-{
-	struct talloc_chunk *tc;
-
-	if (context == NULL) {
-		return 0;
-	}
-
-	tc = talloc_chunk_from_ptr(context);
-	while (tc && depth > 0) {
-		if (TC_PTR_FROM_CHUNK(tc) == ptr) return 1;
-		while (tc && tc->prev) tc = tc->prev;
-		if (tc) {
-			tc = tc->parent;
-			depth--;
-		}
-	}
-	return 0;
-}
-
-/*
-  return 1 if ptr is a parent of context
-*/
-_PUBLIC_ int talloc_is_parent(const void *context, const void *ptr)
-{
-	return _talloc_is_parent(context, ptr, TALLOC_MAX_DEPTH);
-}
diff --git a/lib/talloc/talloc.h b/lib/talloc/talloc.h
deleted file mode 100644
index 96c7e24..0000000
--- a/lib/talloc/talloc.h
+++ /dev/null
@@ -1,1711 +0,0 @@
-#ifndef _TALLOC_H_
-#define _TALLOC_H_
-/* 
-   Unix SMB/CIFS implementation.
-   Samba temporary memory allocation functions
-
-   Copyright (C) Andrew Tridgell 2004-2005
-   Copyright (C) Stefan Metzmacher 2006
-   
-     ** NOTE! The following LGPL license applies to the talloc
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-   
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-
-#include <stdlib.h>
-#include <stdio.h>
-#include <stdarg.h>
-
-#ifdef __cplusplus
-extern "C" {
-#endif
-
-/**
- * @defgroup talloc The talloc API
- *
- * talloc is a hierarchical, reference counted memory pool system with
- * destructors. It is the core memory allocator used in Samba.
- *
- * @{
- */
-
-#define TALLOC_VERSION_MAJOR 2
-#define TALLOC_VERSION_MINOR 0
-
-int talloc_version_major(void);
-int talloc_version_minor(void);
-
-/**
- * @brief Define a talloc parent type
- *
- * As talloc is a hierarchial memory allocator, every talloc chunk is a
- * potential parent to other talloc chunks. So defining a separate type for a
- * talloc chunk is not strictly necessary. TALLOC_CTX is defined nevertheless,
- * as it provides an indicator for function arguments. You will frequently
- * write code like
- *
- * @code
- *      struct foo *foo_create(TALLOC_CTX *mem_ctx)
- *      {
- *              struct foo *result;
- *              result = talloc(mem_ctx, struct foo);
- *              if (result == NULL) return NULL;
- *                      ... initialize foo ...
- *              return result;
- *      }
- * @endcode
- *
- * In this type of allocating functions it is handy to have a general
- * TALLOC_CTX type to indicate which parent to put allocated structures on.
- */
-typedef void TALLOC_CTX;
-
-/*
-  this uses a little trick to allow __LINE__ to be stringified
-*/
-#ifndef __location__
-#define __TALLOC_STRING_LINE1__(s)    #s
-#define __TALLOC_STRING_LINE2__(s)   __TALLOC_STRING_LINE1__(s)
-#define __TALLOC_STRING_LINE3__  __TALLOC_STRING_LINE2__(__LINE__)
-#define __location__ __FILE__ ":" __TALLOC_STRING_LINE3__
-#endif
-
-#ifndef TALLOC_DEPRECATED
-#define TALLOC_DEPRECATED 0
-#endif
-
-#ifndef PRINTF_ATTRIBUTE
-#if (__GNUC__ >= 3)
-/** Use gcc attribute to check printf fns.  a1 is the 1-based index of
- * the parameter containing the format, and a2 the index of the first
- * argument. Note that some gcc 2.x versions don't handle this
- * properly **/
-#define PRINTF_ATTRIBUTE(a1, a2) __attribute__ ((format (__printf__, a1, a2)))
-#else
-#define PRINTF_ATTRIBUTE(a1, a2)
-#endif
-#endif
-
-#ifdef DOXYGEN
-/**
- * @brief Create a new talloc context.
- *
- * The talloc() macro is the core of the talloc library. It takes a memory
- * context and a type, and returns a pointer to a new area of memory of the
- * given type.
- *
- * The returned pointer is itself a talloc context, so you can use it as the
- * context argument to more calls to talloc if you wish.
- *
- * The returned pointer is a "child" of the supplied context. This means that if
- * you talloc_free() the context then the new child disappears as well.
- * Alternatively you can free just the child.
- *
- * @param[in]  ctx      A talloc context to create a new reference on or NULL to
- *                      create a new top level context.
- *
- * @param[in]  type     The type of memory to allocate.
- *
- * @return              A type casted talloc context or NULL on error.
- *
- * @code
- *      unsigned int *a, *b;
- *
- *      a = talloc(NULL, unsigned int);
- *      b = talloc(a, unsigned int);
- * @endcode
- *
- * @see talloc_zero
- * @see talloc_array
- * @see talloc_steal
- * @see talloc_free
- */
-void *talloc(const void *ctx, #type);
-#else
-#define talloc(ctx, type) (type *)talloc_named_const(ctx, sizeof(type), #type)
-void *_talloc(const void *context, size_t size);
-#endif
-
-/**
- * @brief Create a new top level talloc context.
- *
- * This function creates a zero length named talloc context as a top level
- * context. It is equivalent to:
- *
- * @code
- *      talloc_named(NULL, 0, fmt, ...);
- * @endcode
- * @param[in]  fmt      Format string for the name.
- *
- * @param[in]  ...      Additional printf-style arguments.
- *
- * @return              The allocated memory chunk, NULL on error.
- *
- * @see talloc_named()
- */
-void *talloc_init(const char *fmt, ...) PRINTF_ATTRIBUTE(1,2);
-
-#ifdef DOXYGEN
-/**
- * @brief Free a chunk of talloc memory.
- *
- * The talloc_free() function frees a piece of talloc memory, and all its
- * children. You can call talloc_free() on any pointer returned by
- * talloc().
- *
- * The return value of talloc_free() indicates success or failure, with 0
- * returned for success and -1 for failure. A possible failure condition
- * is if the pointer had a destructor attached to it and the destructor
- * returned -1. See talloc_set_destructor() for details on
- * destructors. Likewise, if "ptr" is NULL, then the function will make
- * no modifications and return -1.
- *
- * From version 2.0 and onwards, as a special case, talloc_free() is
- * refused on pointers that have more than one parent associated, as talloc
- * would have no way of knowing which parent should be removed. This is
- * different from older versions in the sense that always the reference to
- * the most recently established parent has been destroyed. Hence to free a
- * pointer that has more than one parent please use talloc_unlink().
- *
- * To help you find problems in your code caused by this behaviour, if
- * you do try and free a pointer with more than one parent then the
- * talloc logging function will be called to give output like this:
- *
- * @code
- *   ERROR: talloc_free with references at some_dir/source/foo.c:123
- *     reference at some_dir/source/other.c:325
- *     reference at some_dir/source/third.c:121
- * @endcode
- *
- * Please see the documentation for talloc_set_log_fn() and
- * talloc_set_log_stderr() for more information on talloc logging
- * functions.
- *
- * talloc_free() operates recursively on its children.
- *
- * @param[in]  ptr      The chunk to be freed.
- *
- * @return              Returns 0 on success and -1 on error. A possible
- *                      failure condition is if the pointer had a destructor
- *                      attached to it and the destructor returned -1. Likewise,
- *                      if "ptr" is NULL, then the function will make no
- *                      modifications and returns -1.
- *
- * Example:
- * @code
- *      unsigned int *a, *b;
- *      a = talloc(NULL, unsigned int);
- *      b = talloc(a, unsigned int);
- *
- *      talloc_free(a); // Frees a and b
- * @endcode
- *
- * @see talloc_set_destructor()
- * @see talloc_unlink()
- */
-int talloc_free(void *ptr);
-#else
-#define talloc_free(ctx) _talloc_free(ctx, __location__)
-int _talloc_free(void *ptr, const char *location);
-#endif
-
-/**
- * @brief Free a talloc chunk's children.
- *
- * The function walks along the list of all children of a talloc context and
- * talloc_free()s only the children, not the context itself.
- *
- * A NULL argument is handled as no-op.
- *
- * @param[in]  ptr      The chunk that you want to free the children of
- *                      (NULL is allowed too)
- */
-void talloc_free_children(void *ptr);
-
-#ifdef DOXYGEN
-/**
- * @brief Assign a destructor function to be called when a chunk is freed.
- *
- * The function talloc_set_destructor() sets the "destructor" for the pointer
- * "ptr". A destructor is a function that is called when the memory used by a
- * pointer is about to be released. The destructor receives the pointer as an
- * argument, and should return 0 for success and -1 for failure.
- *
- * The destructor can do anything it wants to, including freeing other pieces
- * of memory. A common use for destructors is to clean up operating system
- * resources (such as open file descriptors) contained in the structure the
- * destructor is placed on.
- *
- * You can only place one destructor on a pointer. If you need more than one
- * destructor then you can create a zero-length child of the pointer and place
- * an additional destructor on that.
- *
- * To remove a destructor call talloc_set_destructor() with NULL for the
- * destructor.
- *
- * If your destructor attempts to talloc_free() the pointer that it is the
- * destructor for then talloc_free() will return -1 and the free will be
- * ignored. This would be a pointless operation anyway, as the destructor is
- * only called when the memory is just about to go away.
- *
- * @param[in]  ptr      The talloc chunk to add a destructor to.
- *
- * @param[in]  destructor  The destructor function to be called. NULL to remove
- *                         it.
- *
- * Example:
- * @code
- *      static int destroy_fd(int *fd) {
- *              close(*fd);
- *              return 0;
- *      }
- *
- *      int *open_file(const char *filename) {
- *              int *fd = talloc(NULL, int);
- *              *fd = open(filename, O_RDONLY);
- *              if (*fd < 0) {
- *                      talloc_free(fd);
- *                      return NULL;
- *              }
- *              // Whenever they free this, we close the file.
- *              talloc_set_destructor(fd, destroy_fd);
- *              return fd;
- *      }
- * @endcode
- *
- * @see talloc()
- * @see talloc_free()
- */
-void talloc_set_destructor(const void *ptr, int (*destructor)(void *));
-
-/**
- * @brief Change a talloc chunk's parent.
- *
- * The talloc_steal() function changes the parent context of a talloc
- * pointer. It is typically used when the context that the pointer is
- * currently a child of is going to be freed and you wish to keep the
- * memory for a longer time.
- *
- * To make the changed hierarchy less error-prone, you might consider to use
- * talloc_move().
- *
- * If you try and call talloc_steal() on a pointer that has more than one
- * parent then the result is ambiguous. Talloc will choose to remove the
- * parent that is currently indicated by talloc_parent() and replace it with
- * the chosen parent. You will also get a message like this via the talloc
- * logging functions:
- *
- * @code
- *   WARNING: talloc_steal with references at some_dir/source/foo.c:123
- *     reference at some_dir/source/other.c:325
- *     reference at some_dir/source/third.c:121
- * @endcode
- *
- * To unambiguously change the parent of a pointer please see the function
- * talloc_reparent(). See the talloc_set_log_fn() documentation for more
- * information on talloc logging.
- *
- * @param[in]  new_ctx  The new parent context.
- *
- * @param[in]  ptr      The talloc chunk to move.
- *
- * @return              Returns the pointer that you pass it. It does not have
- *                      any failure modes.
- *
- * @note It is possible to produce loops in the parent/child relationship
- * if you are not careful with talloc_steal(). No guarantees are provided
- * as to your sanity or the safety of your data if you do this.
- */
-void *talloc_steal(const void *new_ctx, const void *ptr);
-#else /* DOXYGEN */
-/* try to make talloc_set_destructor() and talloc_steal() type safe,
-   if we have a recent gcc */
-#if (__GNUC__ >= 3)
-#define _TALLOC_TYPEOF(ptr) __typeof__(ptr)
-#define talloc_set_destructor(ptr, function)				      \
-	do {								      \
-		int (*_talloc_destructor_fn)(_TALLOC_TYPEOF(ptr)) = (function);	      \
-		_talloc_set_destructor((ptr), (int (*)(void *))_talloc_destructor_fn); \
-	} while(0)
-/* this extremely strange macro is to avoid some braindamaged warning
-   stupidity in gcc 4.1.x */
-#define talloc_steal(ctx, ptr) ({ _TALLOC_TYPEOF(ptr) __talloc_steal_ret = (_TALLOC_TYPEOF(ptr))_talloc_steal_loc((ctx),(ptr), __location__); __talloc_steal_ret; })
-#else /* __GNUC__ >= 3 */
-#define talloc_set_destructor(ptr, function) \
-	_talloc_set_destructor((ptr), (int (*)(void *))(function))
-#define _TALLOC_TYPEOF(ptr) void *
-#define talloc_steal(ctx, ptr) (_TALLOC_TYPEOF(ptr))_talloc_steal_loc((ctx),(ptr), __location__)
-#endif /* __GNUC__ >= 3 */
-void _talloc_set_destructor(const void *ptr, int (*_destructor)(void *));
-void *_talloc_steal_loc(const void *new_ctx, const void *ptr, const char *location);
-#endif /* DOXYGEN */
-
-/**
- * @brief Assign a name to a talloc chunk.
- *
- * Each talloc pointer has a "name". The name is used principally for
- * debugging purposes, although it is also possible to set and get the name on
- * a pointer in as a way of "marking" pointers in your code.
- *
- * The main use for names on pointer is for "talloc reports". See
- * talloc_report() and talloc_report_full() for details. Also see
- * talloc_enable_leak_report() and talloc_enable_leak_report_full().
- *
- * The talloc_set_name() function allocates memory as a child of the
- * pointer. It is logically equivalent to:
- *
- * @code
- *      talloc_set_name_const(ptr, talloc_asprintf(ptr, fmt, ...));
- * @endcode
- *
- * @param[in]  ptr      The talloc chunk to assign a name to.
- *
- * @param[in]  fmt      Format string for the name.
- *
- * @param[in]  ...      Add printf-style additional arguments.
- *
- * @return              The assigned name, NULL on error.
- *
- * @note Multiple calls to talloc_set_name() will allocate more memory without
- * releasing the name. All of the memory is released when the ptr is freed
- * using talloc_free().
- */
-const char *talloc_set_name(const void *ptr, const char *fmt, ...) PRINTF_ATTRIBUTE(2,3);
-
-#ifdef DOXYGEN
-/**
- * @brief Change a talloc chunk's parent.
- *
- * This function has the same effect as talloc_steal(), and additionally sets
- * the source pointer to NULL. You would use it like this:
- *
- * @code
- *      struct foo *X = talloc(tmp_ctx, struct foo);
- *      struct foo *Y;
- *      Y = talloc_move(new_ctx, &X);
- * @endcode
- *
- * @param[in]  new_ctx  The new parent context.
- *
- * @param[in]  pptr     Pointer to the talloc chunk to move.
- *
- * @return              The pointer of the talloc chunk it has been moved to,
- *                      NULL on error.
- */
-void *talloc_move(const void *new_ctx, void **pptr);
-#else
-#define talloc_move(ctx, pptr) (_TALLOC_TYPEOF(*(pptr)))_talloc_move((ctx),(void *)(pptr))
-void *_talloc_move(const void *new_ctx, const void *pptr);
-#endif
-
-/**
- * @brief Assign a name to a talloc chunk.
- *
- * The function is just like talloc_set_name(), but it takes a string constant,
- * and is much faster. It is extensively used by the "auto naming" macros, such
- * as talloc_p().
- *
- * This function does not allocate any memory. It just copies the supplied
- * pointer into the internal representation of the talloc ptr. This means you
- * must not pass a name pointer to memory that will disappear before the ptr
- * is freed with talloc_free().
- *
- * @param[in]  ptr      The talloc chunk to assign a name to.
- *
- * @param[in]  name     Format string for the name.
- */
-void talloc_set_name_const(const void *ptr, const char *name);
-
-/**
- * @brief Create a named talloc chunk.
- *
- * The talloc_named() function creates a named talloc pointer. It is
- * equivalent to:
- *
- * @code
- *      ptr = talloc_size(context, size);
- *      talloc_set_name(ptr, fmt, ....);
- * @endcode
- *
- * @param[in]  context  The talloc context to hang the result off.
- *
- * @param[in]  size     Number of char's that you want to allocate.
- *
- * @param[in]  fmt      Format string for the name.
- *
- * @param[in]  ...      Additional printf-style arguments.
- *
- * @return              The allocated memory chunk, NULL on error.
- *
- * @see talloc_set_name()
- */
-void *talloc_named(const void *context, size_t size,
-		   const char *fmt, ...) PRINTF_ATTRIBUTE(3,4);
-
-/**
- * @brief Basic routine to allocate a chunk of memory.
- *
- * This is equivalent to:
- *
- * @code
- *      ptr = talloc_size(context, size);
- *      talloc_set_name_const(ptr, name);
- * @endcode
- *
- * @param[in]  context  The parent context.
- *
- * @param[in]  size     The number of char's that we want to allocate.
- *
- * @param[in]  name     The name the talloc block has.
- *
- * @return             The allocated memory chunk, NULL on error.
- */
-void *talloc_named_const(const void *context, size_t size, const char *name);
-
-#ifdef DOXYGEN
-/**
- * @brief Untyped allocation.
- *
- * The function should be used when you don't have a convenient type to pass to
- * talloc(). Unlike talloc(), it is not type safe (as it returns a void *), so
- * you are on your own for type checking.
- *
- * Best to use talloc() or talloc_array() instead.
- *
- * @param[in]  ctx     The talloc context to hang the result off.
- *
- * @param[in]  size    Number of char's that you want to allocate.
- *
- * @return             The allocated memory chunk, NULL on error.
- *
- * Example:
- * @code
- *      void *mem = talloc_size(NULL, 100);
- * @endcode
- */
-void *talloc_size(const void *ctx, size_t size);
-#else
-#define talloc_size(ctx, size) talloc_named_const(ctx, size, __location__)
-#endif
-
-#ifdef DOXYGEN
-/**
- * @brief Allocate into a typed pointer.
- *
- * The talloc_ptrtype() macro should be used when you have a pointer and want
- * to allocate memory to point at with this pointer. When compiling with
- * gcc >= 3 it is typesafe. Note this is a wrapper of talloc_size() and
- * talloc_get_name() will return the current location in the source file and
- * not the type.
- *
- * @param[in]  ctx      The talloc context to hang the result off.
- *
- * @param[in]  type     The pointer you want to assign the result to.
- *
- * @return              The properly casted allocated memory chunk, NULL on
- *                      error.
- *
- * Example:
- * @code
- *       unsigned int *a = talloc_ptrtype(NULL, a);
- * @endcode
- */
-void *talloc_ptrtype(const void *ctx, #type);
-#else
-#define talloc_ptrtype(ctx, ptr) (_TALLOC_TYPEOF(ptr))talloc_size(ctx, sizeof(*(ptr)))
-#endif
-
-#ifdef DOXYGEN
-/**
- * @brief Allocate a new 0-sized talloc chunk.
- *
- * This is a utility macro that creates a new memory context hanging off an
- * existing context, automatically naming it "talloc_new: __location__" where
- * __location__ is the source line it is called from. It is particularly
- * useful for creating a new temporary working context.
- *
- * @param[in]  ctx      The talloc parent context.
- *
- * @return              A new talloc chunk, NULL on error.
- */
-void *talloc_new(const void *ctx);
-#else
-#define talloc_new(ctx) talloc_named_const(ctx, 0, "talloc_new: " __location__)
-#endif
-
-#ifdef DOXYGEN
-/**
- * @brief Allocate a 0-initizialized structure.
- *
- * The macro is equivalent to:
- *
- * @code
- *      ptr = talloc(ctx, type);
- *      if (ptr) memset(ptr, 0, sizeof(type));
- * @endcode
- *
- * @param[in]  ctx      The talloc context to hang the result off.
- *
- * @param[in]  type     The type that we want to allocate.
- *
- * @return              Pointer to a piece of memory, properly cast to 'type *',
- *                      NULL on error.
- *
- * Example:
- * @code
- *      unsigned int *a, *b;
- *      a = talloc_zero(NULL, unsigned int);
- *      b = talloc_zero(a, unsigned int);
- * @endcode
- *
- * @see talloc()
- * @see talloc_zero_size()
- * @see talloc_zero_array()
- */
-void *talloc_zero(const void *ctx, #type);
-
-/**
- * @brief Allocate untyped, 0-initialized memory.
- *
- * @param[in]  ctx      The talloc context to hang the result off.
- *
- * @param[in]  size     Number of char's that you want to allocate.
- *
- * @return              The allocated memory chunk.
- */
-void *talloc_zero_size(const void *ctx, size_t size);
-#else
-#define talloc_zero(ctx, type) (type *)_talloc_zero(ctx, sizeof(type), #type)
-#define talloc_zero_size(ctx, size) _talloc_zero(ctx, size, __location__)
-void *_talloc_zero(const void *ctx, size_t size, const char *name);
-#endif
-
-/**
- * @brief Return the name of a talloc chunk.
- *
- * @param[in]  ptr      The talloc chunk.
- *
- * @return              The current name for the given talloc pointer.
- *
- * @see talloc_set_name()
- */
-const char *talloc_get_name(const void *ptr);
-
-/**
- * @brief Verify that a talloc chunk carries a specified name.
- *
- * This function checks if a pointer has the specified name. If it does
- * then the pointer is returned.
- *
- * @param[in]  ptr       The talloc chunk to check.
- *
- * @param[in]  name      The name to check against.
- *
- * @return               The pointer if the name matches, NULL if it doesn't.
- */
-void *talloc_check_name(const void *ptr, const char *name);
-
-/**
- * @brief Get the parent chunk of a pointer.
- *
- * @param[in]  ptr      The talloc pointer to inspect.
- *
- * @return              The talloc parent of ptr, NULL on error.
- */
-void *talloc_parent(const void *ptr);
-
-/**
- * @brief Get a talloc chunk's parent name.
- *
- * @param[in]  ptr      The talloc pointer to inspect.
- *
- * @return              The name of ptr's parent chunk.
- */
-const char *talloc_parent_name(const void *ptr);
-
-/**
- * @brief Get the total size of a talloc chunk including its children.
- *
- * The function returns the total size in bytes used by this pointer and all
- * child pointers. Mostly useful for debugging.
- *
- * Passing NULL is allowed, but it will only give a meaningful result if
- * talloc_enable_leak_report() or talloc_enable_leak_report_full() has
- * been called.
- *
- * @param[in]  ptr      The talloc chunk.
- *
- * @return              The total size.
- */
-size_t talloc_total_size(const void *ptr);
-
-/**
- * @brief Get the number of talloc chunks hanging off a chunk.
- *
- * The talloc_total_blocks() function returns the total memory block
- * count used by this pointer and all child pointers. Mostly useful for
- * debugging.
- *
- * Passing NULL is allowed, but it will only give a meaningful result if
- * talloc_enable_leak_report() or talloc_enable_leak_report_full() has
- * been called.
- *
- * @param[in]  ptr      The talloc chunk.
- *
- * @return              The total size.
- */
-size_t talloc_total_blocks(const void *ptr);
-
-#ifdef DOXYGEN
-/**
- * @brief Duplicate a memory area into a talloc chunk.
- *
- * The function is equivalent to:
- *
- * @code
- *      ptr = talloc_size(ctx, size);
- *      if (ptr) memcpy(ptr, p, size);
- * @endcode
- *
- * @param[in]  t        The talloc context to hang the result off.
- *
- * @param[in]  p        The memory chunk you want to duplicate.
- *
- * @param[in]  size     Number of char's that you want copy.
- *
- * @return              The allocated memory chunk.
- *
- * @see talloc_size()
- */
-void *talloc_memdup(const void *t, const void *p, size_t size);
-#else
-#define talloc_memdup(t, p, size) _talloc_memdup(t, p, size, __location__)
-void *_talloc_memdup(const void *t, const void *p, size_t size, const char *name);
-#endif
-
-#ifdef DOXYGEN
-/**
- * @brief Assign a type to a talloc chunk.
- *
- * This macro allows you to force the name of a pointer to be of a particular
- * type. This can be used in conjunction with talloc_get_type() to do type
- * checking on void* pointers.
- *
- * It is equivalent to this:
- *
- * @code
- *      talloc_set_name_const(ptr, #type)
- * @endcode
- *
- * @param[in]  ptr      The talloc chunk to assign the type to.
- *
- * @param[in]  type     The type to assign.
- */
-void talloc_set_type(const char *ptr, #type);
-
-/**
- * @brief Get a typed pointer out of a talloc pointer.
- *
- * This macro allows you to do type checking on talloc pointers. It is
- * particularly useful for void* private pointers. It is equivalent to
- * this:
- *
- * @code
- *      (type *)talloc_check_name(ptr, #type)
- * @endcode
- *
- * @param[in]  ptr      The talloc pointer to check.
- *
- * @param[in]  type     The type to check against.
- *
- * @return              The properly casted pointer given by ptr, NULL on error.
- */
-type *talloc_get_type(const void *ptr, #type);
-#else
-#define talloc_set_type(ptr, type) talloc_set_name_const(ptr, #type)
-#define talloc_get_type(ptr, type) (type *)talloc_check_name(ptr, #type)
-#endif
-
-#ifdef DOXYGEN
-/**
- * @brief Safely turn a void pointer into a typed pointer.
- *
- * This macro is used together with talloc(mem_ctx, struct foo). If you had to
- * assing the talloc chunk pointer to some void pointer variable,
- * talloc_get_type_abort() is the recommended way to get the convert the void
- * pointer back to a typed pointer.
- *
- * @param[in]  ptr      The void pointer to convert.
- *
- * @param[in]  type     The type that this chunk contains
- *
- * @return              The same value as ptr, type-checked and properly cast.
- */
-void *talloc_get_type_abort(const void *ptr, #type);
-#else
-#define talloc_get_type_abort(ptr, type) (type *)_talloc_get_type_abort(ptr, #type, __location__)
-void *_talloc_get_type_abort(const void *ptr, const char *name, const char *location);
-#endif
-
-/**
- * @brief Find a parent context by name.
- *
- * Find a parent memory context of the current context that has the given
- * name. This can be very useful in complex programs where it may be
- * difficult to pass all information down to the level you need, but you
- * know the structure you want is a parent of another context.
- *
- * @param[in]  ctx      The talloc chunk to start from.
- *
- * @param[in]  name     The name of the parent we look for.
- *
- * @return              The memory context we are looking for, NULL if not
- *                      found.
- */
-void *talloc_find_parent_byname(const void *ctx, const char *name);
-
-#ifdef DOXYGEN
-/**
- * @brief Find a parent context by type.
- *
- * Find a parent memory context of the current context that has the given
- * name. This can be very useful in complex programs where it may be
- * difficult to pass all information down to the level you need, but you
- * know the structure you want is a parent of another context.
- *
- * Like talloc_find_parent_byname() but takes a type, making it typesafe.
- *
- * @param[in]  ptr      The talloc chunk to start from.
- *
- * @param[in]  type     The type of the parent to look for.
- *
- * @return              The memory context we are looking for, NULL if not
- *                      found.
- */
-void *talloc_find_parent_bytype(const void *ptr, #type);
-#else
-#define talloc_find_parent_bytype(ptr, type) (type *)talloc_find_parent_byname(ptr, #type)
-#endif
-
-/**
- * @brief Allocate a talloc pool.
- *
- * A talloc pool is a pure optimization for specific situations. In the
- * release process for Samba 3.2 we found out that we had become considerably
- * slower than Samba 3.0 was. Profiling showed that malloc(3) was a large CPU
- * consumer in benchmarks. For Samba 3.2 we have internally converted many
- * static buffers to dynamically allocated ones, so malloc(3) being beaten
- * more was no surprise. But it made us slower.
- *
- * talloc_pool() is an optimization to call malloc(3) a lot less for the use
- * pattern Samba has: The SMB protocol is mainly a request/response protocol
- * where we have to allocate a certain amount of memory per request and free
- * that after the SMB reply is sent to the client.
- *
- * talloc_pool() creates a talloc chunk that you can use as a talloc parent
- * exactly as you would use any other ::TALLOC_CTX. The difference is that
- * when you talloc a child of this pool, no malloc(3) is done. Instead, talloc
- * just increments a pointer inside the talloc_pool. This also works
- * recursively. If you use the child of the talloc pool as a parent for
- * grand-children, their memory is also taken from the talloc pool.
- *
- * If you talloc_free() children of a talloc pool, the memory is not given
- * back to the system. Instead, free(3) is only called if the talloc_pool()
- * itself is released with talloc_free().
- *
- * The downside of a talloc pool is that if you talloc_move() a child of a
- * talloc pool to a talloc parent outside the pool, the whole pool memory is
- * not free(3)'ed until that moved chunk is also talloc_free()ed.
- *
- * @param[in]  context  The talloc context to hang the result off.
- *
- * @param[in]  size     Size of the talloc pool.
- *
- * @return              The allocated talloc pool, NULL on error.
- */
-void *talloc_pool(const void *context, size_t size);
-
-/**
- * @brief Free a talloc chunk and NULL out the pointer.
- *
- * TALLOC_FREE() frees a pointer and sets it to NULL. Use this if you want
- * immediate feedback (i.e. crash) if you use a pointer after having free'ed
- * it.
- *
- * @param[in]  ctx      The chunk to be freed.
- */
-#define TALLOC_FREE(ctx) do { talloc_free(ctx); ctx=NULL; } while(0)
-
-/* @} ******************************************************************/
-
-/**
- * \defgroup talloc_ref The talloc reference function.
- * @ingroup talloc
- *
- * This module contains the definitions around talloc references
- *
- * @{
- */
-
-/**
- * @brief Increase the reference count of a talloc chunk.
- *
- * The talloc_increase_ref_count(ptr) function is exactly equivalent to:
- *
- * @code
- *      talloc_reference(NULL, ptr);
- * @endcode
- *
- * You can use either syntax, depending on which you think is clearer in
- * your code.
- *
- * @param[in]  ptr      The pointer to increase the reference count.
- *
- * @return              0 on success, -1 on error.
- */
-int talloc_increase_ref_count(const void *ptr);
-
-/**
- * @brief Get the number of references to a talloc chunk.
- *
- * @param[in]  ptr      The pointer to retrieve the reference count from.
- *
- * @return              The number of references.
- */
-size_t talloc_reference_count(const void *ptr);
-
-#ifdef DOXYGEN
-/**
- * @brief Create an additional talloc parent to a pointer.
- *
- * The talloc_reference() function makes "context" an additional parent of
- * ptr. Each additional reference consumes around 48 bytes of memory on intel
- * x86 platforms.
- *
- * If ptr is NULL, then the function is a no-op, and simply returns NULL.
- *
- * After creating a reference you can free it in one of the following ways:
- *
- * - you can talloc_free() any parent of the original pointer. That
- *   will reduce the number of parents of this pointer by 1, and will
- *   cause this pointer to be freed if it runs out of parents.
- *
- * - you can talloc_free() the pointer itself if it has at maximum one
- *   parent. This behaviour has been changed since the release of version
- *   2.0. Further informations in the description of "talloc_free".
- *
- * For more control on which parent to remove, see talloc_unlink()
- * @param[in]  ctx      The additional parent.
- *
- * @param[in]  ptr      The pointer you want to create an additional parent for.
- *
- * @return              The original pointer 'ptr', NULL if talloc ran out of
- *                      memory in creating the reference.
- *
- * Example:
- * @code
- *      unsigned int *a, *b, *c;
- *      a = talloc(NULL, unsigned int);
- *      b = talloc(NULL, unsigned int);
- *      c = talloc(a, unsigned int);
- *      // b also serves as a parent of c.
- *      talloc_reference(b, c);
- * @endcode
- *
- * @see talloc_unlink()
- */
-void *talloc_reference(const void *ctx, const void *ptr);
-#else
-#define talloc_reference(ctx, ptr) (_TALLOC_TYPEOF(ptr))_talloc_reference_loc((ctx),(ptr), __location__)
-void *_talloc_reference_loc(const void *context, const void *ptr, const char *location);
-#endif
-
-/**
- * @brief Remove a specific parent from a talloc chunk.
- *
- * The function removes a specific parent from ptr. The context passed must
- * either be a context used in talloc_reference() with this pointer, or must be
- * a direct parent of ptr.
- *
- * You can just use talloc_free() instead of talloc_unlink() if there
- * is at maximum one parent. This behaviour has been changed since the
- * release of version 2.0. Further informations in the description of
- * "talloc_free".
- *
- * @param[in]  context  The talloc parent to remove.
- *
- * @param[in]  ptr      The talloc ptr you want to remove the parent from.
- *
- * @return              0 on success, -1 on error.
- *
- * @note If the parent has already been removed using talloc_free() then
- * this function will fail and will return -1.  Likewise, if ptr is NULL,
- * then the function will make no modifications and return -1.
- *
- * Example:
- * @code
- *      unsigned int *a, *b, *c;
- *      a = talloc(NULL, unsigned int);
- *      b = talloc(NULL, unsigned int);
- *      c = talloc(a, unsigned int);
- *      // b also serves as a parent of c.
- *      talloc_reference(b, c);
- *      talloc_unlink(b, c);
- * @endcode
- */
-int talloc_unlink(const void *context, void *ptr);
-
-/**
- * @brief Provide a talloc context that is freed at program exit.
- *
- * This is a handy utility function that returns a talloc context
- * which will be automatically freed on program exit. This can be used
- * to reduce the noise in memory leak reports.
- *
- * Never use this in code that might be used in objects loaded with
- * dlopen and unloaded with dlclose. talloc_autofree_context()
- * internally uses atexit(3). Some platforms like modern Linux handles
- * this fine, but for example FreeBSD does not deal well with dlopen()
- * and atexit() used simultaneously: dlclose() does not clean up the
- * list of atexit-handlers, so when the program exits the code that
- * was registered from within talloc_autofree_context() is gone, the
- * program crashes at exit.
- *
- * @return              A talloc context, NULL on error.
- */
-void *talloc_autofree_context(void);
-
-/**
- * @brief Get the size of a talloc chunk.
- *
- * This function lets you know the amount of memory allocated so far by
- * this context. It does NOT account for subcontext memory.
- * This can be used to calculate the size of an array.
- *
- * @param[in]  ctx      The talloc chunk.
- *
- * @return              The size of the talloc chunk.
- */
-size_t talloc_get_size(const void *ctx);
-
-/**
- * @brief Show the parentage of a context.
- *
- * @param[in]  context            The talloc context to look at.
- *
- * @param[in]  file               The output to use, a file, stdout or stderr.
- */
-void talloc_show_parents(const void *context, FILE *file);
-
-/**
- * @brief Check if a context is parent of a talloc chunk.
- *
- * This checks if context is referenced in the talloc hierarchy above ptr.
- *
- * @param[in]  context  The assumed talloc context.
- *
- * @param[in]  ptr      The talloc chunk to check.
- *
- * @return              Return 1 if this is the case, 0 if not.
- */
-int talloc_is_parent(const void *context, const void *ptr);
-
-/**
- * @brief Change the parent context of a talloc pointer.
- *
- * The function changes the parent context of a talloc pointer. It is typically
- * used when the context that the pointer is currently a child of is going to be
- * freed and you wish to keep the memory for a longer time.
- *
- * The difference between talloc_reparent() and talloc_steal() is that
- * talloc_reparent() can specify which parent you wish to change. This is
- * useful when a pointer has multiple parents via references.
- *
- * @param[in]  old_parent
- * @param[in]  new_parent
- * @param[in]  ptr
- *
- * @return              Return the pointer you passed. It does not have any
- *                      failure modes.
- */
-void *talloc_reparent(const void *old_parent, const void *new_parent, const void *ptr);
-
-/* @} ******************************************************************/
-
-/**
- * @defgroup talloc_array The talloc array functions
- * @ingroup talloc
- *
- * Talloc contains some handy helpers for handling Arrays conveniently
- *
- * @{
- */
-
-#ifdef DOXYGEN
-/**
- * @brief Allocate an array.
- *
- * The macro is equivalent to:
- *
- * @code
- *      (type *)talloc_size(ctx, sizeof(type) * count);
- * @endcode
- *
- * except that it provides integer overflow protection for the multiply,
- * returning NULL if the multiply overflows.
- *
- * @param[in]  ctx      The talloc context to hang the result off.
- *
- * @param[in]  type     The type that we want to allocate.
- *
- * @param[in]  count    The number of 'type' elements you want to allocate.
- *
- * @return              The allocated result, properly cast to 'type *', NULL on
- *                      error.
- *
- * Example:
- * @code
- *      unsigned int *a, *b;
- *      a = talloc_zero(NULL, unsigned int);
- *      b = talloc_array(a, unsigned int, 100);
- * @endcode
- *
- * @see talloc()
- * @see talloc_zero_array()
- */
-void *talloc_array(const void *ctx, #type, unsigned count);
-#else
-#define talloc_array(ctx, type, count) (type *)_talloc_array(ctx, sizeof(type), count, #type)
-void *_talloc_array(const void *ctx, size_t el_size, unsigned count, const char *name);
-#endif
-
-#ifdef DOXYGEN
-/**
- * @brief Allocate an array.
- *
- * @param[in]  ctx      The talloc context to hang the result off.
- *
- * @param[in]  size     The size of an array element.
- *
- * @param[in]  count    The number of elements you want to allocate.
- *
- * @return              The allocated result, NULL on error.
- */
-void *talloc_array_size(const void *ctx, size_t size, unsigned count);
-#else
-#define talloc_array_size(ctx, size, count) _talloc_array(ctx, size, count, __location__)
-#endif
-
-#ifdef DOXYGEN
-/**
- * @brief Allocate an array into a typed pointer.
- *
- * The macro should be used when you have a pointer to an array and want to
- * allocate memory of an array to point at with this pointer. When compiling
- * with gcc >= 3 it is typesafe. Note this is a wrapper of talloc_array_size()
- * and talloc_get_name() will return the current location in the source file
- * and not the type.
- *
- * @param[in]  ctx      The talloc context to hang the result off.
- *
- * @param[in]  ptr      The pointer you want to assign the result to.
- *
- * @param[in]  count    The number of elements you want to allocate.
- *
- * @return              The allocated memory chunk, properly casted. NULL on
- *                      error.
- */
-void *talloc_array_ptrtype(const void *ctx, const void *ptr, unsigned count);
-#else
-#define talloc_array_ptrtype(ctx, ptr, count) (_TALLOC_TYPEOF(ptr))talloc_array_size(ctx, sizeof(*(ptr)), count)
-#endif
-
-#ifdef DOXYGEN
-/**
- * @brief Get the number of elements in a talloc'ed array.
- *
- * A talloc chunk carries its own size, so for talloc'ed arrays it is not
- * necessary to store the number of elements explicitly.
- *
- * @param[in]  ctx      The allocated array.
- *
- * @return              The number of elements in ctx.
- */
-size_t talloc_array_length(const void *ctx);
-#else
-#define talloc_array_length(ctx) (talloc_get_size(ctx)/sizeof(*ctx))
-#endif
-
-#ifdef DOXYGEN
-/**
- * @brief Allocate a zero-initialized array
- *
- * @param[in]  ctx      The talloc context to hang the result off.
- *
- * @param[in]  type     The type that we want to allocate.
- *
- * @param[in]  count    The number of "type" elements you want to allocate.
- *
- * @return              The allocated result casted to "type *", NULL on error.
- *
- * The talloc_zero_array() macro is equivalent to:
- *
- * @code
- *     ptr = talloc_array(ctx, type, count);
- *     if (ptr) memset(ptr, sizeof(type) * count);
- * @endcode
- */
-void *talloc_zero_array(const void *ctx, #type, unsigned count);
-#else
-#define talloc_zero_array(ctx, type, count) (type *)_talloc_zero_array(ctx, sizeof(type), count, #type)
-void *_talloc_zero_array(const void *ctx,
-			 size_t el_size,
-			 unsigned count,
-			 const char *name);
-#endif
-
-#ifdef DOXYGEN
-/**
- * @brief Change the size of a talloc array.
- *
- * The macro changes the size of a talloc pointer. The 'count' argument is the
- * number of elements of type 'type' that you want the resulting pointer to
- * hold.
- *
- * talloc_realloc() has the following equivalences:
- *
- * @code
- *      talloc_realloc(ctx, NULL, type, 1) ==> talloc(ctx, type);
- *      talloc_realloc(ctx, NULL, type, N) ==> talloc_array(ctx, type, N);
- *      talloc_realloc(ctx, ptr, type, 0)  ==> talloc_free(ptr);
- * @endcode
- *
- * The "context" argument is only used if "ptr" is NULL, otherwise it is
- * ignored.
- *
- * @param[in]  ctx      The parent context used if ptr is NULL.
- *
- * @param[in]  ptr      The chunk to be resized.
- *
- * @param[in]  type     The type of the array element inside ptr.
- *
- * @param[in]  count    The intended number of array elements.
- *
- * @return              The new array, NULL on error. The call will fail either
- *                      due to a lack of memory, or because the pointer has more
- *                      than one parent (see talloc_reference()).
- */
-void *talloc_realloc(const void *ctx, void *ptr, #type, size_t count);
-#else
-#define talloc_realloc(ctx, p, type, count) (type *)_talloc_realloc_array(ctx, p, sizeof(type), count, #type)
-void *_talloc_realloc_array(const void *ctx, void *ptr, size_t el_size, unsigned count, const char *name);
-#endif
-
-#ifdef DOXYGEN
-/**
- * @brief Untyped realloc to change the size of a talloc array.
- *
- * The macro is useful when the type is not known so the typesafe
- * talloc_realloc() cannot be used.
- *
- * @param[in]  ctx      The parent context used if 'ptr' is NULL.
- *
- * @param[in]  ptr      The chunk to be resized.
- *
- * @param[in]  size     The new chunk size.
- *
- * @return              The new array, NULL on error.
- */
-void *talloc_realloc_size(const void *ctx, void *ptr, size_t size);
-#else
-#define talloc_realloc_size(ctx, ptr, size) _talloc_realloc(ctx, ptr, size, __location__)
-void *_talloc_realloc(const void *context, void *ptr, size_t size, const char *name);
-#endif
-
-/**
- * @brief Provide a function version of talloc_realloc_size.
- *
- * This is a non-macro version of talloc_realloc(), which is useful as
- * libraries sometimes want a ralloc function pointer. A realloc()
- * implementation encapsulates the functionality of malloc(), free() and
- * realloc() in one call, which is why it is useful to be able to pass around
- * a single function pointer.
- *
- * @param[in]  context  The parent context used if ptr is NULL.
- *
- * @param[in]  ptr      The chunk to be resized.
- *
- * @param[in]  size     The new chunk size.
- *
- * @return              The new chunk, NULL on error.
- */
-void *talloc_realloc_fn(const void *context, void *ptr, size_t size);
-
-/* @} ******************************************************************/
-
-/**
- * @defgroup talloc_string The talloc string functions.
- * @ingroup talloc
- *
- * talloc string allocation and manipulation functions.
- * @{
- */
-
-/**
- * @brief Duplicate a string into a talloc chunk.
- *
- * This function is equivalent to:
- *
- * @code
- *      ptr = talloc_size(ctx, strlen(p)+1);
- *      if (ptr) memcpy(ptr, p, strlen(p)+1);
- * @endcode
- *
- * This functions sets the name of the new pointer to the passed
- * string. This is equivalent to:
- *
- * @code
- *      talloc_set_name_const(ptr, ptr)
- * @endcode
- *
- * @param[in]  t        The talloc context to hang the result off.
- *
- * @param[in]  p        The string you want to duplicate.
- *
- * @return              The duplicated string, NULL on error.
- */
-char *talloc_strdup(const void *t, const char *p);
-
-/**
- * @brief Append a string to given string and duplicate the result.
- *
- * @param[in]  s        The destination to append to.
- *
- * @param[in]  a        The string you want to append.
- *
- * @return              The duplicated string, NULL on error.
- *
- * @see talloc_strdup()
- */
-char *talloc_strdup_append(char *s, const char *a);
-
-/**
- * @brief Append a string to a given buffer and duplicate the result.
- *
- * @param[in]  s        The destination buffer to append to.
- *
- * @param[in]  a        The string you want to append.
- *
- * @return              The duplicated string, NULL on error.
- *
- * @see talloc_strdup()
- */
-char *talloc_strdup_append_buffer(char *s, const char *a);
-
-/**
- * @brief Duplicate a length-limited string into a talloc chunk.
- *
- * This function is the talloc equivalent of the C library function strndup(3).
- *
- * This functions sets the name of the new pointer to the passed string. This is
- * equivalent to:
- *
- * @code
- *      talloc_set_name_const(ptr, ptr)
- * @endcode
- *
- * @param[in]  t        The talloc context to hang the result off.
- *
- * @param[in]  p        The string you want to duplicate.
- *
- * @param[in]  n        The maximum string length to duplicate.
- *
- * @return              The duplicated string, NULL on error.
- */
-char *talloc_strndup(const void *t, const char *p, size_t n);
-
-/**
- * @brief Append at most n characters of a string to given string and duplicate
- *        the result.
- *
- * @param[in]  s        The destination string to append to.
- *
- * @param[in]  a        The source string you want to append.
- *
- * @param[in]  n        The number of characters you want to append from the
- *                      string.
- *
- * @return              The duplicated string, NULL on error.
- *
- * @see talloc_strndup()
- */
-char *talloc_strndup_append(char *s, const char *a, size_t n);
-
-/**
- * @brief Append at most n characters of a string to given buffer and duplicate
- *        the result.
- *
- * @param[in]  s        The destination buffer to append to.
- *
- * @param[in]  a        The source string you want to append.
- *
- * @param[in]  n        The number of characters you want to append from the
- *                      string.
- *
- * @return              The duplicated string, NULL on error.
- *
- * @see talloc_strndup()
- */
-char *talloc_strndup_append_buffer(char *s, const char *a, size_t n);
-
-/**
- * @brief Format a string given a va_list.
- *
- * This function is the talloc equivalent of the C library function
- * vasprintf(3).
- *
- * This functions sets the name of the new pointer to the new string. This is
- * equivalent to:
- *
- * @code
- *      talloc_set_name_const(ptr, ptr)
- * @endcode
- *
- * @param[in]  t        The talloc context to hang the result off.
- *
- * @param[in]  fmt      The format string.
- *
- * @param[in]  ap       The parameters used to fill fmt.
- *
- * @return              The formatted string, NULL on error.
- */
-char *talloc_vasprintf(const void *t, const char *fmt, va_list ap) PRINTF_ATTRIBUTE(2,0);
-
-/**
- * @brief Format a string given a va_list and append it to the given destination
- *        string.
- *
- * @param[in]  s        The destination string to append to.
- *
- * @param[in]  fmt      The format string.
- *
- * @param[in]  ap       The parameters used to fill fmt.
- *
- * @return              The formatted string, NULL on error.
- *
- * @see talloc_vasprintf()
- */
-char *talloc_vasprintf_append(char *s, const char *fmt, va_list ap) PRINTF_ATTRIBUTE(2,0);
-
-/**
- * @brief Format a string given a va_list and append it to the given destination
- *        buffer.
- *
- * @param[in]  s        The destination buffer to append to.
- *
- * @param[in]  fmt      The format string.
- *
- * @param[in]  ap       The parameters used to fill fmt.
- *
- * @return              The formatted string, NULL on error.
- *
- * @see talloc_vasprintf()
- */
-char *talloc_vasprintf_append_buffer(char *s, const char *fmt, va_list ap) PRINTF_ATTRIBUTE(2,0);
-
-/**
- * @brief Format a string.
- *
- * This function is the talloc equivalent of the C library function asprintf(3).
- *
- * This functions sets the name of the new pointer to the new string. This is
- * equivalent to:
- *
- * @code
- *      talloc_set_name_const(ptr, ptr)
- * @endcode
- *
- * @param[in]  t        The talloc context to hang the result off.
- *
- * @param[in]  fmt      The format string.
- *
- * @param[in]  ...      The parameters used to fill fmt.
- *
- * @return              The formatted string, NULL on error.
- */
-char *talloc_asprintf(const void *t, const char *fmt, ...) PRINTF_ATTRIBUTE(2,3);
-
-/**
- * @brief Append a formatted string to another string.
- *
- * This function appends the given formatted string to the given string. Use
- * this variant when the string in the current talloc buffer may have been
- * truncated in length.
- *
- * This functions sets the name of the new pointer to the new
- * string. This is equivalent to:
- *
- * @code
- *      talloc_set_name_const(ptr, ptr)
- * @endcode
- *
- * @param[in]  s        The string to append to.
- *
- * @param[in]  fmt      The format string.
- *
- * @param[in]  ...      The parameters used to fill fmt.
- *
- * @return              The formatted string, NULL on error.
- */
-char *talloc_asprintf_append(char *s, const char *fmt, ...) PRINTF_ATTRIBUTE(2,3);
-
-/**
- * @brief Append a formatted string to another string.
- *
- * @param[in]  s        The string to append to
- *
- * @param[in]  fmt      The format string.
- *
- * @param[in]  ...      The parameters used to fill fmt.
- *
- * @return              The formatted string, NULL on error.
- */
-char *talloc_asprintf_append_buffer(char *s, const char *fmt, ...) PRINTF_ATTRIBUTE(2,3);
-
-/* @} ******************************************************************/
-
-/**
- * @defgroup talloc_debug The talloc debugging support functions
- * @ingroup talloc
- *
- * To aid memory debugging, talloc contains routines to inspect the currently
- * allocated memory hierarchy.
- *
- * @{
- */
-
-/**
- * @brief Walk a complete talloc hierarchy.
- *
- * This provides a more flexible reports than talloc_report(). It
- * will recursively call the callback for the entire tree of memory
- * referenced by the pointer. References in the tree are passed with
- * is_ref = 1 and the pointer that is referenced.
- *
- * You can pass NULL for the pointer, in which case a report is
- * printed for the top level memory context, but only if
- * talloc_enable_leak_report() or talloc_enable_leak_report_full()
- * has been called.
- *
- * The recursion is stopped when depth >= max_depth.
- * max_depth = -1 means only stop at leaf nodes.
- *
- * @param[in]  ptr      The talloc chunk.
- *
- * @param[in]  depth    Internal parameter to control recursion. Call with 0.
- *
- * @param[in]  max_depth  Maximum recursion level.
- *
- * @param[in]  callback  Function to be called on every chunk.
- *
- * @param[in]  private_data  Private pointer passed to callback.
- */
-void talloc_report_depth_cb(const void *ptr, int depth, int max_depth,
-			    void (*callback)(const void *ptr,
-					     int depth, int max_depth,
-					     int is_ref,
-					     void *private_data),
-			    void *private_data);
-
-/**
- * @brief Print a talloc hierarchy.
- *
- * This provides a more flexible reports than talloc_report(). It
- * will let you specify the depth and max_depth.
- *
- * @param[in]  ptr      The talloc chunk.
- *
- * @param[in]  depth    Internal parameter to control recursion. Call with 0.
- *
- * @param[in]  max_depth  Maximum recursion level.
- *
- * @param[in]  f        The file handle to print to.
- */
-void talloc_report_depth_file(const void *ptr, int depth, int max_depth, FILE *f);
-
-/**
- * @brief Print a summary report of all memory used by ptr.
- *
- * This provides a more detailed report than talloc_report(). It will
- * recursively print the entire tree of memory referenced by the
- * pointer. References in the tree are shown by giving the name of the
- * pointer that is referenced.
- *
- * You can pass NULL for the pointer, in which case a report is printed
- * for the top level memory context, but only if
- * talloc_enable_leak_report() or talloc_enable_leak_report_full() has
- * been called.
- *
- * @param[in]  ptr      The talloc chunk.
- *
- * @param[in]  f        The file handle to print to.
- *
- * Example:
- * @code
- *      unsigned int *a, *b;
- *      a = talloc(NULL, unsigned int);
- *      b = talloc(a, unsigned int);
- *      fprintf(stderr, "Dumping memory tree for a:\n");
- *      talloc_report_full(a, stderr);
- * @endcode
- *
- * @see talloc_report()
- */
-void talloc_report_full(const void *ptr, FILE *f);
-
-/**
- * @brief Print a summary report of all memory used by ptr.
- *
- * This function prints a summary report of all memory used by ptr. One line of
- * report is printed for each immediate child of ptr, showing the total memory
- * and number of blocks used by that child.
- *
- * You can pass NULL for the pointer, in which case a report is printed
- * for the top level memory context, but only if talloc_enable_leak_report()
- * or talloc_enable_leak_report_full() has been called.
- *
- * @param[in]  ptr      The talloc chunk.
- *
- * @param[in]  f        The file handle to print to.
- *
- * Example:
- * @code
- *      unsigned int *a, *b;
- *      a = talloc(NULL, unsigned int);
- *      b = talloc(a, unsigned int);
- *      fprintf(stderr, "Summary of memory tree for a:\n");
- *      talloc_report(a, stderr);
- * @endcode
- *
- * @see talloc_report_full()
- */
-void talloc_report(const void *ptr, FILE *f);
-
-/**
- * @brief Enable tracking the use of NULL memory contexts.
- *
- * This enables tracking of the NULL memory context without enabling leak
- * reporting on exit. Useful for when you want to do your own leak
- * reporting call via talloc_report_null_full();
- */
-void talloc_enable_null_tracking(void);
-
-/**
- * @brief Enable tracking the use of NULL memory contexts.
- *
- * This enables tracking of the NULL memory context without enabling leak
- * reporting on exit. Useful for when you want to do your own leak
- * reporting call via talloc_report_null_full();
- */
-void talloc_enable_null_tracking_no_autofree(void);
-
-/**
- * @brief Disable tracking of the NULL memory context.
- *
- * This disables tracking of the NULL memory context.
- */
-void talloc_disable_null_tracking(void);
-
-/**
- * @brief Enable leak report when a program exits.
- *
- * This enables calling of talloc_report(NULL, stderr) when the program
- * exits. In Samba4 this is enabled by using the --leak-report command
- * line option.
- *
- * For it to be useful, this function must be called before any other
- * talloc function as it establishes a "null context" that acts as the
- * top of the tree. If you don't call this function first then passing
- * NULL to talloc_report() or talloc_report_full() won't give you the
- * full tree printout.
- *
- * Here is a typical talloc report:
- *
- * @code
- * talloc report on 'null_context' (total 267 bytes in 15 blocks)
- *      libcli/auth/spnego_parse.c:55  contains     31 bytes in   2 blocks
- *      libcli/auth/spnego_parse.c:55  contains     31 bytes in   2 blocks
- *      iconv(UTF8,CP850)              contains     42 bytes in   2 blocks
- *      libcli/auth/spnego_parse.c:55  contains     31 bytes in   2 blocks
- *      iconv(CP850,UTF8)              contains     42 bytes in   2 blocks
- *      iconv(UTF8,UTF-16LE)           contains     45 bytes in   2 blocks
- *      iconv(UTF-16LE,UTF8)           contains     45 bytes in   2 blocks
- * @endcode
- */
-void talloc_enable_leak_report(void);
-
-/**
- * @brief Enable full leak report when a program exits.
- *
- * This enables calling of talloc_report_full(NULL, stderr) when the
- * program exits. In Samba4 this is enabled by using the
- * --leak-report-full command line option.
- *
- * For it to be useful, this function must be called before any other
- * talloc function as it establishes a "null context" that acts as the
- * top of the tree. If you don't call this function first then passing
- * NULL to talloc_report() or talloc_report_full() won't give you the
- * full tree printout.
- *
- * Here is a typical full report:
- *
- * @code
- * full talloc report on 'root' (total 18 bytes in 8 blocks)
- *      p1                             contains     18 bytes in   7 blocks (ref 0)
- *      r1                             contains     13 bytes in   2 blocks (ref 0)
- *      reference to: p2
- *      p2                             contains      1 bytes in   1 blocks (ref 1)
- *      x3                             contains      1 bytes in   1 blocks (ref 0)
- *      x2                             contains      1 bytes in   1 blocks (ref 0)
- *      x1                             contains      1 bytes in   1 blocks (ref 0)
- * @endcode
- */
-void talloc_enable_leak_report_full(void);
-
-/* @} ******************************************************************/
-
-void talloc_set_abort_fn(void (*abort_fn)(const char *reason));
-void talloc_set_log_fn(void (*log_fn)(const char *message));
-void talloc_set_log_stderr(void);
-
-#if TALLOC_DEPRECATED
-#define talloc_zero_p(ctx, type) talloc_zero(ctx, type)
-#define talloc_p(ctx, type) talloc(ctx, type)
-#define talloc_array_p(ctx, type, count) talloc_array(ctx, type, count)
-#define talloc_realloc_p(ctx, p, type, count) talloc_realloc(ctx, p, type, count)
-#define talloc_destroy(ctx) talloc_free(ctx)
-#define talloc_append_string(c, s, a) (s?talloc_strdup_append(s,a):talloc_strdup(c, a))
-#endif
-
-#ifndef TALLOC_MAX_DEPTH
-#define TALLOC_MAX_DEPTH 10000
-#endif
-
-#ifdef __cplusplus
-} /* end of extern "C" */
-#endif
-
-#endif
diff --git a/lib/talloc/talloc.pc.in b/lib/talloc/talloc.pc.in
deleted file mode 100644
index 5ce2109..0000000
--- a/lib/talloc/talloc.pc.in
+++ /dev/null
@@ -1,11 +0,0 @@
-prefix=@prefix@
-exec_prefix=@exec_prefix@
-libdir=@libdir@
-includedir=@includedir@
-
-Name: talloc 
-Description: A hierarchical pool based memory system with destructors
-Version: @TALLOC_VERSION@
-Libs: -L${libdir} -ltalloc
-Cflags: -I${includedir} 
-URL: http://talloc.samba.org/
diff --git a/lib/talloc/talloc_guide.txt b/lib/talloc/talloc_guide.txt
deleted file mode 100644
index 8164ffc..0000000
--- a/lib/talloc/talloc_guide.txt
+++ /dev/null
@@ -1,767 +0,0 @@
-Using talloc in Samba4
-======================
-
-.. contents::
-
-Andrew Tridgell
-August 2009
-
-The most current version of this document is available at
-   http://samba.org/ftp/unpacked/talloc/talloc_guide.txt
-
-If you are used to the "old" talloc from Samba3 before 3.0.20 then please read
-this carefully, as talloc has changed a lot. With 3.0.20 (or 3.0.14?) the
-Samba4 talloc has been ported back to Samba3, so this guide applies to both.
-
-The new talloc is a hierarchical, reference counted memory pool system
-with destructors. Quite a mouthful really, but not too bad once you
-get used to it.
-
-Perhaps the biggest change from Samba3 is that there is no distinction
-between a "talloc context" and a "talloc pointer". Any pointer
-returned from talloc() is itself a valid talloc context. This means
-you can do this::
-
-  struct foo *X = talloc(mem_ctx, struct foo);
-  X->name = talloc_strdup(X, "foo");
-
-and the pointer X->name would be a "child" of the talloc context "X"
-which is itself a child of "mem_ctx". So if you do talloc_free(mem_ctx)
-then it is all destroyed, whereas if you do talloc_free(X) then just X
-and X->name are destroyed, and if you do talloc_free(X->name) then
-just the name element of X is destroyed.
-
-If you think about this, then what this effectively gives you is an
-n-ary tree, where you can free any part of the tree with
-talloc_free().
-
-If you find this confusing, then I suggest you run the testsuite to
-watch talloc in action. You may also like to add your own tests to
-testsuite.c to clarify how some particular situation is handled.
-
-
-Performance
------------
-
-All the additional features of talloc() over malloc() do come at a
-price. We have a simple performance test in Samba4 that measures
-talloc() versus malloc() performance, and it seems that talloc() is
-about 4% slower than malloc() on my x86 Debian Linux box. For Samba,
-the great reduction in code complexity that we get by using talloc
-makes this worthwhile, especially as the total overhead of
-talloc/malloc in Samba is already quite small.
-
-
-talloc API
-----------
-
-The following is a complete guide to the talloc API. Read it all at
-least twice.
-
-Multi-threading
----------------
-
-talloc itself does not deal with threads. It is thread-safe (assuming  
-the underlying "malloc" is), as long as each thread uses different  
-memory contexts.
-If two threads use the same context then they need to synchronize in
-order to be safe. In particular:
-- when using talloc_enable_leak_report(), giving directly NULL as a  
-parent context implicitly refers to a hidden "null context" global  
-variable, so this should not be used in a multi-threaded environment  
-without proper synchronization ;
-- the context returned by talloc_autofree_context() is also global so  
-shouldn't be used by several threads simultaneously without  
-synchronization.
-
-talloc and shared objects
--------------------------
-
-talloc can be used in shared objects. Special care needs to be taken
-to never use talloc_autofree_context() in code that might be loaded
-with dlopen() and unloaded with dlclose(), as talloc_autofree_context()
-internally uses atexit(3). Some platforms like modern Linux handles
-this fine, but for example FreeBSD does not deal well with dlopen()
-and atexit() used simultaneously: dlclose() does not clean up the list
-of atexit-handlers, so when the program exits the code that was
-registered from within talloc_autofree_context() is gone, the program
-crashes at exit.
-
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-(type *)talloc(const void *context, type);
-
-The talloc() macro is the core of the talloc library. It takes a
-memory context and a type, and returns a pointer to a new area of
-memory of the given type.
-
-The returned pointer is itself a talloc context, so you can use it as
-the context argument to more calls to talloc if you wish.
-
-The returned pointer is a "child" of the supplied context. This means
-that if you talloc_free() the context then the new child disappears as
-well. Alternatively you can free just the child.
-
-The context argument to talloc() can be NULL, in which case a new top
-level context is created. 
-
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-void *talloc_size(const void *context, size_t size);
-
-The function talloc_size() should be used when you don't have a
-convenient type to pass to talloc(). Unlike talloc(), it is not type
-safe (as it returns a void *), so you are on your own for type checking.
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-(typeof(ptr)) talloc_ptrtype(const void *ctx, ptr);
-
-The talloc_ptrtype() macro should be used when you have a pointer and
-want to allocate memory to point at with this pointer. When compiling
-with gcc >= 3 it is typesafe. Note this is a wrapper of talloc_size()
-and talloc_get_name() will return the current location in the source file.
-and not the type.
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-int talloc_free(void *ptr);
-
-The talloc_free() function frees a piece of talloc memory, and all its
-children. You can call talloc_free() on any pointer returned by
-talloc().
-
-The return value of talloc_free() indicates success or failure, with 0
-returned for success and -1 for failure. A possible failure condition
-is if the pointer had a destructor attached to it and the destructor
-returned -1. See talloc_set_destructor() for details on
-destructors. Likewise, if "ptr" is NULL, then the function will make
-no modifications and returns -1.
-
-From version 2.0 and onwards, as a special case, talloc_free() is
-refused on pointers that have more than one parent associated, as talloc
-would have no way of knowing which parent should be removed. This is
-different from older versions in the sense that always the reference to
-the most recently established parent has been destroyed. Hence to free a
-pointer that has more than one parent please use talloc_unlink().
-
-To help you find problems in your code caused by this behaviour, if
-you do try and free a pointer with more than one parent then the
-talloc logging function will be called to give output like this:
-
-  ERROR: talloc_free with references at some_dir/source/foo.c:123
-	reference at some_dir/source/other.c:325
-	reference at some_dir/source/third.c:121
-
-Please see the documentation for talloc_set_log_fn() and
-talloc_set_log_stderr() for more information on talloc logging
-functions.
-
-talloc_free() operates recursively on its children.
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-void talloc_free_children(void *ptr);
-
-The talloc_free_children() walks along the list of all children of a
-talloc context and talloc_free()s only the children, not the context
-itself.
-
-A NULL argument is handled as no-op.
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-void *talloc_reference(const void *context, const void *ptr);
-
-The talloc_reference() function makes "context" an additional parent
-of "ptr".
-
-The return value of talloc_reference() is always the original pointer
-"ptr", unless talloc ran out of memory in creating the reference in
-which case it will return NULL (each additional reference consumes
-around 48 bytes of memory on intel x86 platforms).
-
-If "ptr" is NULL, then the function is a no-op, and simply returns NULL.
-
-After creating a reference you can free it in one of the following
-ways:
-
-  - you can talloc_free() any parent of the original pointer. That
-    will reduce the number of parents of this pointer by 1, and will
-    cause this pointer to be freed if it runs out of parents.
-
-  - you can talloc_free() the pointer itself if it has at maximum one
-    parent. This behaviour has been changed since the release of version
-    2.0. Further informations in the description of "talloc_free".
-
-For more control on which parent to remove, see talloc_unlink()
-
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-int talloc_unlink(const void *context, const void *ptr);
-
-The talloc_unlink() function removes a specific parent from ptr. The
-context passed must either be a context used in talloc_reference()
-with this pointer, or must be a direct parent of ptr. 
-
-Note that if the parent has already been removed using talloc_free()
-then this function will fail and will return -1.  Likewise, if "ptr"
-is NULL, then the function will make no modifications and return -1.
-
-You can just use talloc_free() instead of talloc_unlink() if there
-is at maximum one parent. This behaviour has been changed since the
-release of version 2.0. Further informations in the description of
-"talloc_free".
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-void talloc_set_destructor(const void *ptr, int (*destructor)(void *));
-
-The function talloc_set_destructor() sets the "destructor" for the
-pointer "ptr". A destructor is a function that is called when the
-memory used by a pointer is about to be released. The destructor
-receives the pointer as an argument, and should return 0 for success
-and -1 for failure.
-
-The destructor can do anything it wants to, including freeing other
-pieces of memory. A common use for destructors is to clean up
-operating system resources (such as open file descriptors) contained
-in the structure the destructor is placed on.
-
-You can only place one destructor on a pointer. If you need more than
-one destructor then you can create a zero-length child of the pointer
-and place an additional destructor on that.
-
-To remove a destructor call talloc_set_destructor() with NULL for the
-destructor.
-
-If your destructor attempts to talloc_free() the pointer that it is
-the destructor for then talloc_free() will return -1 and the free will
-be ignored. This would be a pointless operation anyway, as the
-destructor is only called when the memory is just about to go away.
-
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-int talloc_increase_ref_count(const void *ptr);
-
-The talloc_increase_ref_count(ptr) function is exactly equivalent to:
-
-  talloc_reference(NULL, ptr);
-
-You can use either syntax, depending on which you think is clearer in
-your code.
-
-It returns 0 on success and -1 on failure.
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-size_t talloc_reference_count(const void *ptr);
-
-Return the number of references to the pointer.
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-void talloc_set_name(const void *ptr, const char *fmt, ...);
-
-Each talloc pointer has a "name". The name is used principally for
-debugging purposes, although it is also possible to set and get the
-name on a pointer in as a way of "marking" pointers in your code.
-
-The main use for names on pointer is for "talloc reports". See
-talloc_report() and talloc_report_full() for details. Also see
-talloc_enable_leak_report() and talloc_enable_leak_report_full().
-
-The talloc_set_name() function allocates memory as a child of the
-pointer. It is logically equivalent to:
-  talloc_set_name_const(ptr, talloc_asprintf(ptr, fmt, ...));
-
-Note that multiple calls to talloc_set_name() will allocate more
-memory without releasing the name. All of the memory is released when
-the ptr is freed using talloc_free().
-
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-void talloc_set_name_const(const void *ptr, const char *name);
-
-The function talloc_set_name_const() is just like talloc_set_name(),
-but it takes a string constant, and is much faster. It is extensively
-used by the "auto naming" macros, such as talloc_p().
-
-This function does not allocate any memory. It just copies the
-supplied pointer into the internal representation of the talloc
-ptr. This means you must not pass a name pointer to memory that will
-disappear before the ptr is freed with talloc_free().
-
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-void *talloc_named(const void *context, size_t size, const char *fmt, ...);
-
-The talloc_named() function creates a named talloc pointer. It is
-equivalent to:
-
-   ptr = talloc_size(context, size);
-   talloc_set_name(ptr, fmt, ....);
-
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-void *talloc_named_const(const void *context, size_t size, const char *name);
-
-This is equivalent to::
-
-   ptr = talloc_size(context, size);
-   talloc_set_name_const(ptr, name);
-
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-const char *talloc_get_name(const void *ptr);
-
-This returns the current name for the given talloc pointer. See
-talloc_set_name() for details.
-
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-void *talloc_init(const char *fmt, ...);
-
-This function creates a zero length named talloc context as a top
-level context. It is equivalent to::
-
-  talloc_named(NULL, 0, fmt, ...);
-
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-void *talloc_new(void *ctx);
-
-This is a utility macro that creates a new memory context hanging
-off an exiting context, automatically naming it "talloc_new: __location__"
-where __location__ is the source line it is called from. It is
-particularly useful for creating a new temporary working context.
-
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-(type *)talloc_realloc(const void *context, void *ptr, type, count);
-
-The talloc_realloc() macro changes the size of a talloc
-pointer. The "count" argument is the number of elements of type "type"
-that you want the resulting pointer to hold. 
-
-talloc_realloc() has the following equivalences::
-
-  talloc_realloc(context, NULL, type, 1) ==> talloc(context, type);
-  talloc_realloc(context, NULL, type, N) ==> talloc_array(context, type, N);
-  talloc_realloc(context, ptr, type, 0)  ==> talloc_free(ptr);
-
-The "context" argument is only used if "ptr" is NULL, otherwise it is
-ignored.
-
-talloc_realloc() returns the new pointer, or NULL on failure. The call
-will fail either due to a lack of memory, or because the pointer has
-more than one parent (see talloc_reference()).
-
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-void *talloc_realloc_size(const void *context, void *ptr, size_t size);
-
-the talloc_realloc_size() function is useful when the type is not 
-known so the typesafe talloc_realloc() cannot be used.
-
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-void *talloc_steal(const void *new_ctx, const void *ptr);
-
-The talloc_steal() function changes the parent context of a talloc
-pointer. It is typically used when the context that the pointer is
-currently a child of is going to be freed and you wish to keep the
-memory for a longer time. 
-
-The talloc_steal() function returns the pointer that you pass it. It
-does not have any failure modes.
-
-NOTE: It is possible to produce loops in the parent/child relationship
-if you are not careful with talloc_steal(). No guarantees are provided
-as to your sanity or the safety of your data if you do this.
-
-talloc_steal (new_ctx, NULL) will return NULL with no sideeffects.
-
-Note that if you try and call talloc_steal() on a pointer that has
-more than one parent then the result is ambiguous. Talloc will choose
-to remove the parent that is currently indicated by talloc_parent()
-and replace it with the chosen parent. You will also get a message
-like this via the talloc logging functions:
-
-  WARNING: talloc_steal with references at some_dir/source/foo.c:123
-	reference at some_dir/source/other.c:325
-	reference at some_dir/source/third.c:121
-
-To unambiguously change the parent of a pointer please see the
-function talloc_reparent(). See the talloc_set_log_fn() documentation
-for more information on talloc logging.
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-void *talloc_reparent(const void *old_parent, const void *new_parent, const void *ptr);
-
-The talloc_reparent() function changes the parent context of a talloc
-pointer. It is typically used when the context that the pointer is
-currently a child of is going to be freed and you wish to keep the
-memory for a longer time.
-
-The talloc_reparent() function returns the pointer that you pass it. It
-does not have any failure modes.
-
-The difference between talloc_reparent() and talloc_steal() is that
-talloc_reparent() can specify which parent you wish to change. This is
-useful when a pointer has multiple parents via references.
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-void *talloc_parent(const void *ptr);
-
-The talloc_parent() function returns the current talloc parent. This
-is usually the pointer under which this memory was originally created,
-but it may have changed due to a talloc_steal() or talloc_reparent()
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-size_t talloc_total_size(const void *ptr);
-
-The talloc_total_size() function returns the total size in bytes used
-by this pointer and all child pointers. Mostly useful for debugging.
-
-Passing NULL is allowed, but it will only give a meaningful result if
-talloc_enable_leak_report() or talloc_enable_leak_report_full() has
-been called.
-
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-size_t talloc_total_blocks(const void *ptr);
-
-The talloc_total_blocks() function returns the total memory block
-count used by this pointer and all child pointers. Mostly useful for
-debugging.
-
-Passing NULL is allowed, but it will only give a meaningful result if
-talloc_enable_leak_report() or talloc_enable_leak_report_full() has
-been called.
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-void talloc_report_depth_cb(const void *ptr, int depth, int max_depth,
-			    void (*callback)(const void *ptr,
-			    		     int depth, int max_depth,
-					     int is_ref,
-					     void *priv),
-			    void *priv);
-
-This provides a more flexible reports than talloc_report(). It
-will recursively call the callback for the entire tree of memory
-referenced by the pointer. References in the tree are passed with
-is_ref = 1 and the pointer that is referenced.
-
-You can pass NULL for the pointer, in which case a report is
-printed for the top level memory context, but only if
-talloc_enable_leak_report() or talloc_enable_leak_report_full()
-has been called.
-
-The recursion is stopped when depth >= max_depth.
-max_depth = -1 means only stop at leaf nodes.
-
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-void talloc_report_depth_file(const void *ptr, int depth, int max_depth, FILE *f);
-
-This provides a more flexible reports than talloc_report(). It
-will let you specify the depth and max_depth.
-
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-void talloc_report(const void *ptr, FILE *f);
-
-The talloc_report() function prints a summary report of all memory
-used by ptr. One line of report is printed for each immediate child of
-ptr, showing the total memory and number of blocks used by that child.
-
-You can pass NULL for the pointer, in which case a report is printed
-for the top level memory context, but only if
-talloc_enable_leak_report() or talloc_enable_leak_report_full() has
-been called.
-
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-void talloc_report_full(const void *ptr, FILE *f);
-
-This provides a more detailed report than talloc_report(). It will
-recursively print the entire tree of memory referenced by the
-pointer. References in the tree are shown by giving the name of the
-pointer that is referenced.
-
-You can pass NULL for the pointer, in which case a report is printed
-for the top level memory context, but only if
-talloc_enable_leak_report() or talloc_enable_leak_report_full() has
-been called.
-
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-void talloc_enable_leak_report(void);
-
-This enables calling of talloc_report(NULL, stderr) when the program
-exits. In Samba4 this is enabled by using the --leak-report command
-line option.
-
-For it to be useful, this function must be called before any other
-talloc function as it establishes a "null context" that acts as the
-top of the tree. If you don't call this function first then passing
-NULL to talloc_report() or talloc_report_full() won't give you the
-full tree printout.
-
-Here is a typical talloc report:
-
-talloc report on 'null_context' (total 267 bytes in 15 blocks)
-        libcli/auth/spnego_parse.c:55  contains     31 bytes in   2 blocks
-        libcli/auth/spnego_parse.c:55  contains     31 bytes in   2 blocks
-        iconv(UTF8,CP850)              contains     42 bytes in   2 blocks
-        libcli/auth/spnego_parse.c:55  contains     31 bytes in   2 blocks
-        iconv(CP850,UTF8)              contains     42 bytes in   2 blocks
-        iconv(UTF8,UTF-16LE)           contains     45 bytes in   2 blocks
-        iconv(UTF-16LE,UTF8)           contains     45 bytes in   2 blocks
-
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-void talloc_enable_leak_report_full(void);
-
-This enables calling of talloc_report_full(NULL, stderr) when the
-program exits. In Samba4 this is enabled by using the
---leak-report-full command line option.
-
-For it to be useful, this function must be called before any other
-talloc function as it establishes a "null context" that acts as the
-top of the tree. If you don't call this function first then passing
-NULL to talloc_report() or talloc_report_full() won't give you the
-full tree printout.
-
-Here is a typical full report:
-
-full talloc report on 'root' (total 18 bytes in 8 blocks)
-    p1                             contains     18 bytes in   7 blocks (ref 0)
-        r1                             contains     13 bytes in   2 blocks (ref 0)
-            reference to: p2
-        p2                             contains      1 bytes in   1 blocks (ref 1)
-        x3                             contains      1 bytes in   1 blocks (ref 0)
-        x2                             contains      1 bytes in   1 blocks (ref 0)
-        x1                             contains      1 bytes in   1 blocks (ref 0)
-
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-void talloc_enable_null_tracking(void);
-
-This enables tracking of the NULL memory context without enabling leak
-reporting on exit. Useful for when you want to do your own leak
-reporting call via talloc_report_null_full();
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-void talloc_disable_null_tracking(void);
-
-This disables tracking of the NULL memory context.
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-(type *)talloc_zero(const void *ctx, type);
-
-The talloc_zero() macro is equivalent to::
-
-  ptr = talloc(ctx, type);
-  if (ptr) memset(ptr, 0, sizeof(type));
-
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-void *talloc_zero_size(const void *ctx, size_t size)
-
-The talloc_zero_size() function is useful when you don't have a known type
-
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-void *talloc_memdup(const void *ctx, const void *p, size_t size);
-
-The talloc_memdup() function is equivalent to::
-
-  ptr = talloc_size(ctx, size);
-  if (ptr) memcpy(ptr, p, size);
-
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-char *talloc_strdup(const void *ctx, const char *p);
-
-The talloc_strdup() function is equivalent to::
-
-  ptr = talloc_size(ctx, strlen(p)+1);
-  if (ptr) memcpy(ptr, p, strlen(p)+1);
-
-This functions sets the name of the new pointer to the passed
-string. This is equivalent to::
-
-   talloc_set_name_const(ptr, ptr)
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-char *talloc_strndup(const void *t, const char *p, size_t n);
-
-The talloc_strndup() function is the talloc equivalent of the C
-library function strndup()
-
-This functions sets the name of the new pointer to the passed
-string. This is equivalent to:
-   talloc_set_name_const(ptr, ptr)
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-char *talloc_append_string(const void *t, char *orig, const char *append);
-
-The talloc_append_string() function appends the given formatted
-string to the given string.
-
-This function sets the name of the new pointer to the new
-string. This is equivalent to::
-
-   talloc_set_name_const(ptr, ptr)
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-char *talloc_vasprintf(const void *t, const char *fmt, va_list ap);
-
-The talloc_vasprintf() function is the talloc equivalent of the C
-library function vasprintf()
-
-This functions sets the name of the new pointer to the new
-string. This is equivalent to::
-
-   talloc_set_name_const(ptr, ptr)
-
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-char *talloc_asprintf(const void *t, const char *fmt, ...);
-
-The talloc_asprintf() function is the talloc equivalent of the C
-library function asprintf()
-
-This functions sets the name of the new pointer to the new
-string. This is equivalent to::
-
-   talloc_set_name_const(ptr, ptr)
-
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-char *talloc_asprintf_append(char *s, const char *fmt, ...);
-
-The talloc_asprintf_append() function appends the given formatted
-string to the given string.
-Use this variant when the string in the current talloc buffer may
-have been truncated in length.
-
-This functions sets the name of the new pointer to the new
-string. This is equivalent to::
-
-   talloc_set_name_const(ptr, ptr)
-
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-char *talloc_asprintf_append_buffer(char *s, const char *fmt, ...);
-
-The talloc_asprintf_append() function appends the given formatted 
-string to the end of the currently allocated talloc buffer.
-Use this variant when the string in the current talloc buffer has
-not been changed.
-
-This functions sets the name of the new pointer to the new
-string. This is equivalent to::
-
-   talloc_set_name_const(ptr, ptr)
-
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-((type *)talloc_array(const void *ctx, type, unsigned int count);
-
-The talloc_array() macro is equivalent to::
-
-  (type *)talloc_size(ctx, sizeof(type) * count);
-
-except that it provides integer overflow protection for the multiply,
-returning NULL if the multiply overflows.
-
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-void *talloc_array_size(const void *ctx, size_t size, unsigned int count);
-
-The talloc_array_size() function is useful when the type is not
-known. It operates in the same way as talloc_array(), but takes a size
-instead of a type.
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-(typeof(ptr)) talloc_array_ptrtype(const void *ctx, ptr, unsigned int count);
-
-The talloc_ptrtype() macro should be used when you have a pointer to an array
-and want to allocate memory of an array to point at with this pointer. When compiling
-with gcc >= 3 it is typesafe. Note this is a wrapper of talloc_array_size()
-and talloc_get_name() will return the current location in the source file.
-and not the type.
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-void *talloc_realloc_fn(const void *ctx, void *ptr, size_t size);
-
-This is a non-macro version of talloc_realloc(), which is useful 
-as libraries sometimes want a ralloc function pointer. A realloc()
-implementation encapsulates the functionality of malloc(), free() and
-realloc() in one call, which is why it is useful to be able to pass
-around a single function pointer.
-
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-void *talloc_autofree_context(void);
-
-This is a handy utility function that returns a talloc context
-which will be automatically freed on program exit. This can be used
-to reduce the noise in memory leak reports.
-
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-void *talloc_check_name(const void *ptr, const char *name);
-
-This function checks if a pointer has the specified name. If it does
-then the pointer is returned. It it doesn't then NULL is returned.
-
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-(type *)talloc_get_type(const void *ptr, type);
-
-This macro allows you to do type checking on talloc pointers. It is
-particularly useful for void* private pointers. It is equivalent to
-this::
-
-   (type *)talloc_check_name(ptr, #type)
-
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-talloc_set_type(const void *ptr, type);
-
-This macro allows you to force the name of a pointer to be of a
-particular type. This can be used in conjunction with
-talloc_get_type() to do type checking on void* pointers.
-
-It is equivalent to this::
-
-   talloc_set_name_const(ptr, #type)
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-talloc_get_size(const void *ctx);
-
-This function lets you know the amount of memory allocated so far by
-this context. It does NOT account for subcontext memory.
-This can be used to calculate the size of an array.
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-void *talloc_find_parent_byname(const void *ctx, const char *name);
-
-Find a parent memory context of the current context that has the given
-name. This can be very useful in complex programs where it may be
-difficult to pass all information down to the level you need, but you
-know the structure you want is a parent of another context.
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-(type *)talloc_find_parent_bytype(ctx, type);
-
-Like talloc_find_parent_byname() but takes a type, making it typesafe.
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-void talloc_set_log_fn(void (*log_fn)(const char *message));
-
-This function sets a logging function that talloc will use for
-warnings and errors. By default talloc will not print any warnings or
-errors.
-
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
-void talloc_set_log_stderr(void)
-
-This sets the talloc log function to write log messages to stderr.
diff --git a/lib/talloc/talloc_testsuite.h b/lib/talloc/talloc_testsuite.h
deleted file mode 100644
index acb9701..0000000
--- a/lib/talloc/talloc_testsuite.h
+++ /dev/null
@@ -1,7 +0,0 @@
-#ifndef __LIB_TALLOC_TALLOC_TESTSUITE_H__
-#define __LIB_TALLOC_TALLOC_TESTSUITE_H__
-
-struct torture_context;
-bool torture_local_talloc(struct torture_context *tctx);
-
-#endif
diff --git a/lib/talloc/testsuite.c b/lib/talloc/testsuite.c
deleted file mode 100644
index 7191703..0000000
--- a/lib/talloc/testsuite.c
+++ /dev/null
@@ -1,1430 +0,0 @@
-/* 
-   Unix SMB/CIFS implementation.
-
-   local testing of talloc routines.
-
-   Copyright (C) Andrew Tridgell 2004
-   
-     ** NOTE! The following LGPL license applies to the talloc
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-   
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-
-#include "replace.h"
-#include "system/time.h"
-#include <talloc.h>
-
-#include "talloc_testsuite.h"
-
-static struct timeval timeval_current(void)
-{
-	struct timeval tv;
-	gettimeofday(&tv, NULL);
-	return tv;
-}
-
-static double timeval_elapsed(struct timeval *tv)
-{
-	struct timeval tv2 = timeval_current();
-	return (tv2.tv_sec - tv->tv_sec) + 
-	       (tv2.tv_usec - tv->tv_usec)*1.0e-6;
-}
-
-#define torture_assert(test, expr, str) if (!(expr)) { \
-	printf("failure: %s [\n%s: Expression %s failed: %s\n]\n", \
-		test, __location__, #expr, str); \
-	return false; \
-}
-
-#define torture_assert_str_equal(test, arg1, arg2, desc) \
-	if (arg1 == NULL && arg2 == NULL) {				\
-	} else if (strcmp(arg1, arg2)) {			\
-		printf("failure: %s [\n%s: Expected %s, got %s: %s\n]\n", \
-		   test, __location__, arg1, arg2, desc); \
-		return false; \
-	}
-
-#define CHECK_SIZE(test, ptr, tsize) do { \
-	if (talloc_total_size(ptr) != (tsize)) { \
-		printf("failed: %s [\n%s: wrong '%s' tree size: got %u  expected %u\n]\n", \
-		       test, __location__, #ptr, \
-		       (unsigned)talloc_total_size(ptr), \
-		       (unsigned)tsize); \
-		talloc_report_full(ptr, stdout); \
-		return false; \
-	} \
-} while (0)
-
-#define CHECK_BLOCKS(test, ptr, tblocks) do { \
-	if (talloc_total_blocks(ptr) != (tblocks)) { \
-		printf("failed: %s [\n%s: wrong '%s' tree blocks: got %u  expected %u\n]\n", \
-		       test, __location__, #ptr, \
-		       (unsigned)talloc_total_blocks(ptr), \
-		       (unsigned)tblocks); \
-		talloc_report_full(ptr, stdout); \
-		return false; \
-	} \
-} while (0)
-
-#define CHECK_PARENT(test, ptr, parent) do { \
-	if (talloc_parent(ptr) != (parent)) { \
-		printf("failed: %s [\n%s: '%s' has wrong parent: got %p  expected %p\n]\n", \
-		       test, __location__, #ptr, \
-		       talloc_parent(ptr), \
-		       (parent)); \
-		talloc_report_full(ptr, stdout); \
-		talloc_report_full(parent, stdout); \
-		talloc_report_full(NULL, stdout); \
-		return false; \
-	} \
-} while (0)
-
-static unsigned int test_abort_count;
-
-#if 0
-static void test_abort_fn(const char *reason)
-{
-	printf("# test_abort_fn(%s)\n", reason);
-	test_abort_count++;
-}
-
-static void test_abort_start(void)
-{
-	test_abort_count = 0;
-	talloc_set_abort_fn(test_abort_fn);
-}
-#endif
-
-static void test_abort_stop(void)
-{
-	test_abort_count = 0;
-	talloc_set_abort_fn(NULL);
-}
-
-static void test_log_stdout(const char *message)
-{
-	fprintf(stdout, "%s", message);
-}
-
-/*
-  test references 
-*/
-static bool test_ref1(void)
-{
-	void *root, *p1, *p2, *ref, *r1;
-
-	printf("test: ref1\n# SINGLE REFERENCE FREE\n");
-
-	root = talloc_named_const(NULL, 0, "root");
-	p1 = talloc_named_const(root, 1, "p1");
-	p2 = talloc_named_const(p1, 1, "p2");
-	talloc_named_const(p1, 1, "x1");
-	talloc_named_const(p1, 2, "x2");
-	talloc_named_const(p1, 3, "x3");
-
-	r1 = talloc_named_const(root, 1, "r1");	
-	ref = talloc_reference(r1, p2);
-	talloc_report_full(root, stderr);
-
-	CHECK_BLOCKS("ref1", p1, 5);
-	CHECK_BLOCKS("ref1", p2, 1);
-	CHECK_BLOCKS("ref1", r1, 2);
-
-	fprintf(stderr, "Freeing p2\n");
-	talloc_unlink(r1, p2);
-	talloc_report_full(root, stderr);
-
-	CHECK_BLOCKS("ref1", p1, 5);
-	CHECK_BLOCKS("ref1", p2, 1);
-	CHECK_BLOCKS("ref1", r1, 1);
-
-	fprintf(stderr, "Freeing p1\n");
-	talloc_free(p1);
-	talloc_report_full(root, stderr);
-
-	CHECK_BLOCKS("ref1", r1, 1);
-
-	fprintf(stderr, "Freeing r1\n");
-	talloc_free(r1);
-	talloc_report_full(NULL, stderr);
-
-	fprintf(stderr, "Testing NULL\n");
-	if (talloc_reference(root, NULL)) {
-		return false;
-	}
-
-	CHECK_BLOCKS("ref1", root, 1);
-
-	CHECK_SIZE("ref1", root, 0);
-
-	talloc_free(root);
-	printf("success: ref1\n");
-	return true;
-}
-
-/*
-  test references 
-*/
-static bool test_ref2(void)
-{
-	void *root, *p1, *p2, *ref, *r1;
-
-	printf("test: ref2\n# DOUBLE REFERENCE FREE\n");
-	root = talloc_named_const(NULL, 0, "root");
-	p1 = talloc_named_const(root, 1, "p1");
-	talloc_named_const(p1, 1, "x1");
-	talloc_named_const(p1, 1, "x2");
-	talloc_named_const(p1, 1, "x3");
-	p2 = talloc_named_const(p1, 1, "p2");
-
-	r1 = talloc_named_const(root, 1, "r1");	
-	ref = talloc_reference(r1, p2);
-	talloc_report_full(root, stderr);
-
-	CHECK_BLOCKS("ref2", p1, 5);
-	CHECK_BLOCKS("ref2", p2, 1);
-	CHECK_BLOCKS("ref2", r1, 2);
-
-	fprintf(stderr, "Freeing ref\n");
-	talloc_unlink(r1, ref);
-	talloc_report_full(root, stderr);
-
-	CHECK_BLOCKS("ref2", p1, 5);
-	CHECK_BLOCKS("ref2", p2, 1);
-	CHECK_BLOCKS("ref2", r1, 1);
-
-	fprintf(stderr, "Freeing p2\n");
-	talloc_free(p2);
-	talloc_report_full(root, stderr);
-
-	CHECK_BLOCKS("ref2", p1, 4);
-	CHECK_BLOCKS("ref2", r1, 1);
-
-	fprintf(stderr, "Freeing p1\n");
-	talloc_free(p1);
-	talloc_report_full(root, stderr);
-
-	CHECK_BLOCKS("ref2", r1, 1);
-
-	fprintf(stderr, "Freeing r1\n");
-	talloc_free(r1);
-	talloc_report_full(root, stderr);
-
-	CHECK_SIZE("ref2", root, 0);
-
-	talloc_free(root);
-	printf("success: ref2\n");
-	return true;
-}
-
-/*
-  test references 
-*/
-static bool test_ref3(void)
-{
-	void *root, *p1, *p2, *ref, *r1;
-
-	printf("test: ref3\n# PARENT REFERENCE FREE\n");
-
-	root = talloc_named_const(NULL, 0, "root");
-	p1 = talloc_named_const(root, 1, "p1");
-	p2 = talloc_named_const(root, 1, "p2");
-	r1 = talloc_named_const(p1, 1, "r1");
-	ref = talloc_reference(p2, r1);
-	talloc_report_full(root, stderr);
-
-	CHECK_BLOCKS("ref3", p1, 2);
-	CHECK_BLOCKS("ref3", p2, 2);
-	CHECK_BLOCKS("ref3", r1, 1);
-
-	fprintf(stderr, "Freeing p1\n");
-	talloc_free(p1);
-	talloc_report_full(root, stderr);
-
-	CHECK_BLOCKS("ref3", p2, 2);
-	CHECK_BLOCKS("ref3", r1, 1);
-
-	fprintf(stderr, "Freeing p2\n");
-	talloc_free(p2);
-	talloc_report_full(root, stderr);
-
-	CHECK_SIZE("ref3", root, 0);
-
-	talloc_free(root);
-
-	printf("success: ref3\n");
-	return true;
-}
-
-/*
-  test references 
-*/
-static bool test_ref4(void)
-{
-	void *root, *p1, *p2, *ref, *r1;
-
-	printf("test: ref4\n# REFERRER REFERENCE FREE\n");
-
-	root = talloc_named_const(NULL, 0, "root");
-	p1 = talloc_named_const(root, 1, "p1");
-	talloc_named_const(p1, 1, "x1");
-	talloc_named_const(p1, 1, "x2");
-	talloc_named_const(p1, 1, "x3");
-	p2 = talloc_named_const(p1, 1, "p2");
-
-	r1 = talloc_named_const(root, 1, "r1");	
-	ref = talloc_reference(r1, p2);
-	talloc_report_full(root, stderr);
-
-	CHECK_BLOCKS("ref4", p1, 5);
-	CHECK_BLOCKS("ref4", p2, 1);
-	CHECK_BLOCKS("ref4", r1, 2);
-
-	fprintf(stderr, "Freeing r1\n");
-	talloc_free(r1);
-	talloc_report_full(root, stderr);
-
-	CHECK_BLOCKS("ref4", p1, 5);
-	CHECK_BLOCKS("ref4", p2, 1);
-
-	fprintf(stderr, "Freeing p2\n");
-	talloc_free(p2);
-	talloc_report_full(root, stderr);
-
-	CHECK_BLOCKS("ref4", p1, 4);
-
-	fprintf(stderr, "Freeing p1\n");
-	talloc_free(p1);
-	talloc_report_full(root, stderr);
-
-	CHECK_SIZE("ref4", root, 0);
-
-	talloc_free(root);
-
-	printf("success: ref4\n");
-	return true;
-}
-
-
-/*
-  test references 
-*/
-static bool test_unlink1(void)
-{
-	void *root, *p1, *p2, *ref, *r1;
-
-	printf("test: unlink\n# UNLINK\n");
-
-	root = talloc_named_const(NULL, 0, "root");
-	p1 = talloc_named_const(root, 1, "p1");
-	talloc_named_const(p1, 1, "x1");
-	talloc_named_const(p1, 1, "x2");
-	talloc_named_const(p1, 1, "x3");
-	p2 = talloc_named_const(p1, 1, "p2");
-
-	r1 = talloc_named_const(p1, 1, "r1");	
-	ref = talloc_reference(r1, p2);
-	talloc_report_full(root, stderr);
-
-	CHECK_BLOCKS("unlink", p1, 7);
-	CHECK_BLOCKS("unlink", p2, 1);
-	CHECK_BLOCKS("unlink", r1, 2);
-
-	fprintf(stderr, "Unreferencing r1\n");
-	talloc_unlink(r1, p2);
-	talloc_report_full(root, stderr);
-
-	CHECK_BLOCKS("unlink", p1, 6);
-	CHECK_BLOCKS("unlink", p2, 1);
-	CHECK_BLOCKS("unlink", r1, 1);
-
-	fprintf(stderr, "Freeing p1\n");
-	talloc_free(p1);
-	talloc_report_full(root, stderr);
-
-	CHECK_SIZE("unlink", root, 0);
-
-	talloc_free(root);
-
-	printf("success: unlink\n");
-	return true;
-}
-
-static int fail_destructor(void *ptr)
-{
-	return -1;
-}
-
-/*
-  miscellaneous tests to try to get a higher test coverage percentage
-*/
-static bool test_misc(void)
-{
-	void *root, *p1;
-	char *p2;
-	double *d;
-	const char *name;
-
-	printf("test: misc\n# MISCELLANEOUS\n");
-
-	root = talloc_new(NULL);
-
-	p1 = talloc_size(root, 0x7fffffff);
-	torture_assert("misc", !p1, "failed: large talloc allowed\n");
-
-	p1 = talloc_strdup(root, "foo");
-	talloc_increase_ref_count(p1);
-	talloc_increase_ref_count(p1);
-	talloc_increase_ref_count(p1);
-	CHECK_BLOCKS("misc", p1, 1);
-	CHECK_BLOCKS("misc", root, 2);
-	talloc_unlink(NULL, p1);
-	CHECK_BLOCKS("misc", p1, 1);
-	CHECK_BLOCKS("misc", root, 2);
-	talloc_unlink(NULL, p1);
-	CHECK_BLOCKS("misc", p1, 1);
-	CHECK_BLOCKS("misc", root, 2);
-	p2 = talloc_strdup(p1, "foo");
-	torture_assert("misc", talloc_unlink(root, p2) == -1,
-				   "failed: talloc_unlink() of non-reference context should return -1\n");
-	torture_assert("misc", talloc_unlink(p1, p2) == 0,
-		"failed: talloc_unlink() of parent should succeed\n");
-	talloc_unlink(NULL, p1);
-	CHECK_BLOCKS("misc", p1, 1);
-	CHECK_BLOCKS("misc", root, 2);
-
-	name = talloc_set_name(p1, "my name is %s", "foo");
-	torture_assert_str_equal("misc", talloc_get_name(p1), "my name is foo",
-		"failed: wrong name after talloc_set_name(my name is foo)");
-	CHECK_BLOCKS("misc", p1, 2);
-	CHECK_BLOCKS("misc", root, 3);
-
-	talloc_set_name_const(p1, NULL);
-	torture_assert_str_equal ("misc", talloc_get_name(p1), "UNNAMED",
-		"failed: wrong name after talloc_set_name(NULL)");
-	CHECK_BLOCKS("misc", p1, 2);
-	CHECK_BLOCKS("misc", root, 3);
-
-	torture_assert("misc", talloc_free(NULL) == -1, 
-				   "talloc_free(NULL) should give -1\n");
-
-	talloc_set_destructor(p1, fail_destructor);
-	torture_assert("misc", talloc_free(p1) == -1, 
-		"Failed destructor should cause talloc_free to fail\n");
-	talloc_set_destructor(p1, NULL);
-
-	talloc_report(root, stderr);
-
-
-	p2 = (char *)talloc_zero_size(p1, 20);
-	torture_assert("misc", p2[19] == 0, "Failed to give zero memory\n");
-	talloc_free(p2);
-
-	torture_assert("misc", talloc_strdup(root, NULL) == NULL,
-		"failed: strdup on NULL should give NULL\n");
-
-	p2 = talloc_strndup(p1, "foo", 2);
-	torture_assert("misc", strcmp("fo", p2) == 0, 
-				   "strndup doesn't work\n");
-	p2 = talloc_asprintf_append_buffer(p2, "o%c", 'd');
-	torture_assert("misc", strcmp("food", p2) == 0, 
-				   "talloc_asprintf_append_buffer doesn't work\n");
-	CHECK_BLOCKS("misc", p2, 1);
-	CHECK_BLOCKS("misc", p1, 3);
-
-	p2 = talloc_asprintf_append_buffer(NULL, "hello %s", "world");
-	torture_assert("misc", strcmp("hello world", p2) == 0,
-		"talloc_asprintf_append_buffer doesn't work\n");
-	CHECK_BLOCKS("misc", p2, 1);
-	CHECK_BLOCKS("misc", p1, 3);
-	talloc_free(p2);
-
-	d = talloc_array(p1, double, 0x20000000);
-	torture_assert("misc", !d, "failed: integer overflow not detected\n");
-
-	d = talloc_realloc(p1, d, double, 0x20000000);
-	torture_assert("misc", !d, "failed: integer overflow not detected\n");
-
-	talloc_free(p1);
-	CHECK_BLOCKS("misc", root, 1);
-
-	p1 = talloc_named(root, 100, "%d bytes", 100);
-	CHECK_BLOCKS("misc", p1, 2);
-	CHECK_BLOCKS("misc", root, 3);
-	talloc_unlink(root, p1);
-
-	p1 = talloc_init("%d bytes", 200);
-	p2 = talloc_asprintf(p1, "my test '%s'", "string");
-	torture_assert_str_equal("misc", p2, "my test 'string'",
-		"failed: talloc_asprintf(\"my test '%%s'\", \"string\") gave: \"%s\"");
-	CHECK_BLOCKS("misc", p1, 3);
-	CHECK_SIZE("misc", p2, 17);
-	CHECK_BLOCKS("misc", root, 1);
-	talloc_unlink(NULL, p1);
-
-	p1 = talloc_named_const(root, 10, "p1");
-	p2 = (char *)talloc_named_const(root, 20, "p2");
-	(void)talloc_reference(p1, p2);
-	talloc_report_full(root, stderr);
-	talloc_unlink(root, p2);
-	talloc_report_full(root, stderr);
-	CHECK_BLOCKS("misc", p2, 1);
-	CHECK_BLOCKS("misc", p1, 2);
-	CHECK_BLOCKS("misc", root, 3);
-	talloc_unlink(p1, p2);
-	talloc_unlink(root, p1);
-
-	p1 = talloc_named_const(root, 10, "p1");
-	p2 = (char *)talloc_named_const(root, 20, "p2");
-	(void)talloc_reference(NULL, p2);
-	talloc_report_full(root, stderr);
-	talloc_unlink(root, p2);
-	talloc_report_full(root, stderr);
-	CHECK_BLOCKS("misc", p2, 1);
-	CHECK_BLOCKS("misc", p1, 1);
-	CHECK_BLOCKS("misc", root, 2);
-	talloc_unlink(NULL, p2);
-	talloc_unlink(root, p1);
-
-	/* Test that talloc_unlink is a no-op */
-
-	torture_assert("misc", talloc_unlink(root, NULL) == -1,
-		"failed: talloc_unlink(root, NULL) == -1\n");
-
-	talloc_report(root, stderr);
-	talloc_report(NULL, stderr);
-
-	CHECK_SIZE("misc", root, 0);
-
-	talloc_free(root);
-
-	CHECK_SIZE("misc", NULL, 0);
-
-	talloc_enable_null_tracking_no_autofree();
-	talloc_enable_leak_report();
-	talloc_enable_leak_report_full();
-
-	printf("success: misc\n");
-
-	return true;
-}
-
-
-/*
-  test realloc
-*/
-static bool test_realloc(void)
-{
-	void *root, *p1, *p2;
-
-	printf("test: realloc\n# REALLOC\n");
-
-	root = talloc_new(NULL);
-
-	p1 = talloc_size(root, 10);
-	CHECK_SIZE("realloc", p1, 10);
-
-	p1 = talloc_realloc_size(NULL, p1, 20);
-	CHECK_SIZE("realloc", p1, 20);
-
-	talloc_new(p1);
-
-	p2 = talloc_realloc_size(p1, NULL, 30);
-
-	talloc_new(p1);
-
-	p2 = talloc_realloc_size(p1, p2, 40);
-
-	CHECK_SIZE("realloc", p2, 40);
-	CHECK_SIZE("realloc", root, 60);
-	CHECK_BLOCKS("realloc", p1, 4);
-
-	p1 = talloc_realloc_size(NULL, p1, 20);
-	CHECK_SIZE("realloc", p1, 60);
-
-	talloc_increase_ref_count(p2);
-	torture_assert("realloc", talloc_realloc_size(NULL, p2, 5) == NULL,
-		"failed: talloc_realloc() on a referenced pointer should fail\n");
-	CHECK_BLOCKS("realloc", p1, 4);
-
-	talloc_realloc_size(NULL, p2, 0);
-	talloc_realloc_size(NULL, p2, 0);
-	CHECK_BLOCKS("realloc", p1, 4);
-	talloc_realloc_size(p1, p2, 0);
-	CHECK_BLOCKS("realloc", p1, 3);
-
-	torture_assert("realloc", talloc_realloc_size(NULL, p1, 0x7fffffff) == NULL,
-		"failed: oversize talloc should fail\n");
-
-	talloc_realloc_size(NULL, p1, 0);
-	CHECK_BLOCKS("realloc", root, 4);
-	talloc_realloc_size(root, p1, 0);
-	CHECK_BLOCKS("realloc", root, 1);
-
-	CHECK_SIZE("realloc", root, 0);
-
-	talloc_free(root);
-
-	printf("success: realloc\n");
-
-	return true;
-}
-
-/*
-  test realloc with a child
-*/
-static bool test_realloc_child(void)
-{
-	void *root;
-	struct el2 {
-		const char *name;
-	} *el2;	
-	struct el1 {
-		int count;
-		struct el2 **list, **list2, **list3;
-	} *el1;
-
-	printf("test: REALLOC WITH CHILD\n");
-
-	root = talloc_new(NULL);
-
-	el1 = talloc(root, struct el1);
-	el1->list = talloc(el1, struct el2 *);
-	el1->list[0] = talloc(el1->list, struct el2);
-	el1->list[0]->name = talloc_strdup(el1->list[0], "testing");
-
-	el1->list2 = talloc(el1, struct el2 *);
-	el1->list2[0] = talloc(el1->list2, struct el2);
-	el1->list2[0]->name = talloc_strdup(el1->list2[0], "testing2");
-
-	el1->list3 = talloc(el1, struct el2 *);
-	el1->list3[0] = talloc(el1->list3, struct el2);
-	el1->list3[0]->name = talloc_strdup(el1->list3[0], "testing2");
-	
-	el2 = talloc(el1->list, struct el2);
-	el2 = talloc(el1->list2, struct el2);
-	el2 = talloc(el1->list3, struct el2);
-
-	el1->list = talloc_realloc(el1, el1->list, struct el2 *, 100);
-	el1->list2 = talloc_realloc(el1, el1->list2, struct el2 *, 200);
-	el1->list3 = talloc_realloc(el1, el1->list3, struct el2 *, 300);
-
-	talloc_free(root);
-
-	printf("success: REALLOC WITH CHILD\n");
-	return true;
-}
-
-/*
-  test type checking
-*/
-static bool test_type(void)
-{
-	void *root;
-	struct el1 {
-		int count;
-	};
-	struct el2 {
-		int count;
-	};
-	struct el1 *el1;
-
-	printf("test: type\n# talloc type checking\n");
-
-	root = talloc_new(NULL);
-
-	el1 = talloc(root, struct el1);
-
-	el1->count = 1;
-
-	torture_assert("type", talloc_get_type(el1, struct el1) == el1,
-		"type check failed on el1\n");
-	torture_assert("type", talloc_get_type(el1, struct el2) == NULL,
-		"type check failed on el1 with el2\n");
-	talloc_set_type(el1, struct el2);
-	torture_assert("type", talloc_get_type(el1, struct el2) == (struct el2 *)el1,
-		"type set failed on el1 with el2\n");
-
-	talloc_free(root);
-
-	printf("success: type\n");
-	return true;
-}
-
-/*
-  test steal
-*/
-static bool test_steal(void)
-{
-	void *root, *p1, *p2;
-
-	printf("test: steal\n# STEAL\n");
-
-	root = talloc_new(NULL);
-
-	p1 = talloc_array(root, char, 10);
-	CHECK_SIZE("steal", p1, 10);
-
-	p2 = talloc_realloc(root, NULL, char, 20);
-	CHECK_SIZE("steal", p1, 10);
-	CHECK_SIZE("steal", root, 30);
-
-	torture_assert("steal", talloc_steal(p1, NULL) == NULL,
-		"failed: stealing NULL should give NULL\n");
-
-	torture_assert("steal", talloc_steal(p1, p1) == p1,
-		"failed: stealing to ourselves is a nop\n");
-	CHECK_BLOCKS("steal", root, 3);
-	CHECK_SIZE("steal", root, 30);
-
-	talloc_steal(NULL, p1);
-	talloc_steal(NULL, p2);
-	CHECK_BLOCKS("steal", root, 1);
-	CHECK_SIZE("steal", root, 0);
-
-	talloc_free(p1);
-	talloc_steal(root, p2);
-	CHECK_BLOCKS("steal", root, 2);
-	CHECK_SIZE("steal", root, 20);
-	
-	talloc_free(p2);
-
-	CHECK_BLOCKS("steal", root, 1);
-	CHECK_SIZE("steal", root, 0);
-
-	talloc_free(root);
-
-	p1 = talloc_size(NULL, 3);
-	talloc_report_full(NULL, stderr);
-	CHECK_SIZE("steal", NULL, 3);
-	talloc_free(p1);
-
-	printf("success: steal\n");
-	return true;
-}
-
-/*
-  test move
-*/
-static bool test_move(void)
-{
-	void *root;
-	struct t_move {
-		char *p;
-		int *x;
-	} *t1, *t2;
-
-	printf("test: move\n# MOVE\n");
-
-	root = talloc_new(NULL);
-
-	t1 = talloc(root, struct t_move);
-	t2 = talloc(root, struct t_move);
-	t1->p = talloc_strdup(t1, "foo");
-	t1->x = talloc(t1, int);
-	*t1->x = 42;
-
-	t2->p = talloc_move(t2, &t1->p);
-	t2->x = talloc_move(t2, &t1->x);
-	torture_assert("move", t1->p == NULL && t1->x == NULL &&
-	    strcmp(t2->p, "foo") == 0 && *t2->x == 42,
-		"talloc move failed");
-
-	talloc_free(root);
-
-	printf("success: move\n");
-
-	return true;
-}
-
-/*
-  test talloc_realloc_fn
-*/
-static bool test_realloc_fn(void)
-{
-	void *root, *p1;
-
-	printf("test: realloc_fn\n# talloc_realloc_fn\n");
-
-	root = talloc_new(NULL);
-
-	p1 = talloc_realloc_fn(root, NULL, 10);
-	CHECK_BLOCKS("realloc_fn", root, 2);
-	CHECK_SIZE("realloc_fn", root, 10);
-	p1 = talloc_realloc_fn(root, p1, 20);
-	CHECK_BLOCKS("realloc_fn", root, 2);
-	CHECK_SIZE("realloc_fn", root, 20);
-	p1 = talloc_realloc_fn(root, p1, 0);
-	CHECK_BLOCKS("realloc_fn", root, 1);
-	CHECK_SIZE("realloc_fn", root, 0);
-
-	talloc_free(root);
-
-	printf("success: realloc_fn\n");
-	return true;
-}
-
-
-static bool test_unref_reparent(void)
-{
-	void *root, *p1, *p2, *c1;
-
-	printf("test: unref_reparent\n# UNREFERENCE AFTER PARENT FREED\n");
-
-	root = talloc_named_const(NULL, 0, "root");
-	p1 = talloc_named_const(root, 1, "orig parent");
-	p2 = talloc_named_const(root, 1, "parent by reference");
-
-	c1 = talloc_named_const(p1, 1, "child");
-	talloc_reference(p2, c1);
-
-	CHECK_PARENT("unref_reparent", c1, p1);
-
-	talloc_free(p1);
-
-	CHECK_PARENT("unref_reparent", c1, p2);
-
-	talloc_unlink(p2, c1);
-
-	CHECK_SIZE("unref_reparent", root, 1);
-
-	talloc_free(p2);
-	talloc_free(root);
-
-	printf("success: unref_reparent\n");
-	return true;
-}
-
-/*
-  measure the speed of talloc versus malloc
-*/
-static bool test_speed(void)
-{
-	void *ctx = talloc_new(NULL);
-	unsigned count;
-	const int loop = 1000;
-	int i;
-	struct timeval tv;
-
-	printf("test: speed\n# TALLOC VS MALLOC SPEED\n");
-
-	tv = timeval_current();
-	count = 0;
-	do {
-		void *p1, *p2, *p3;
-		for (i=0;i<loop;i++) {
-			p1 = talloc_size(ctx, loop % 100);
-			p2 = talloc_strdup(p1, "foo bar");
-			p3 = talloc_size(p1, 300);
-			talloc_free(p1);
-		}
-		count += 3 * loop;
-	} while (timeval_elapsed(&tv) < 5.0);
-
-	fprintf(stderr, "talloc: %.0f ops/sec\n", count/timeval_elapsed(&tv));
-
-	talloc_free(ctx);
-
-	ctx = talloc_pool(NULL, 1024);
-
-	tv = timeval_current();
-	count = 0;
-	do {
-		void *p1, *p2, *p3;
-		for (i=0;i<loop;i++) {
-			p1 = talloc_size(ctx, loop % 100);
-			p2 = talloc_strdup(p1, "foo bar");
-			p3 = talloc_size(p1, 300);
-			talloc_free_children(ctx);
-		}
-		count += 3 * loop;
-	} while (timeval_elapsed(&tv) < 5.0);
-
-	talloc_free(ctx);
-
-	fprintf(stderr, "talloc_pool: %.0f ops/sec\n", count/timeval_elapsed(&tv));
-
-	tv = timeval_current();
-	count = 0;
-	do {
-		void *p1, *p2, *p3;
-		for (i=0;i<loop;i++) {
-			p1 = malloc(loop % 100);
-			p2 = strdup("foo bar");
-			p3 = malloc(300);
-			free(p1);
-			free(p2);
-			free(p3);
-		}
-		count += 3 * loop;
-	} while (timeval_elapsed(&tv) < 5.0);
-	fprintf(stderr, "malloc: %.0f ops/sec\n", count/timeval_elapsed(&tv));
-
-	printf("success: speed\n");
-
-	return true;
-}
-
-static bool test_lifeless(void)
-{
-	void *top = talloc_new(NULL);
-	char *parent, *child; 
-	void *child_owner = talloc_new(NULL);
-
-	printf("test: lifeless\n# TALLOC_UNLINK LOOP\n");
-
-	parent = talloc_strdup(top, "parent");
-	child = talloc_strdup(parent, "child");  
-	(void)talloc_reference(child, parent);
-	(void)talloc_reference(child_owner, child); 
-	talloc_report_full(top, stderr);
-	talloc_unlink(top, parent);
-	talloc_unlink(top, child);
-	talloc_report_full(top, stderr);
-	talloc_free(top);
-	talloc_free(child_owner);
-	talloc_free(child);
-
-	printf("success: lifeless\n");
-	return true;
-}
-
-static int loop_destructor_count;
-
-static int test_loop_destructor(char *ptr)
-{
-	loop_destructor_count++;
-	return 0;
-}
-
-static bool test_loop(void)
-{
-	void *top = talloc_new(NULL);
-	char *parent;
-	struct req1 {
-		char *req2, *req3;
-	} *req1;
-
-	printf("test: loop\n# TALLOC LOOP DESTRUCTION\n");
-
-	parent = talloc_strdup(top, "parent");
-	req1 = talloc(parent, struct req1);
-	req1->req2 = talloc_strdup(req1, "req2");  
-	talloc_set_destructor(req1->req2, test_loop_destructor);
-	req1->req3 = talloc_strdup(req1, "req3");
-	(void)talloc_reference(req1->req3, req1);
-	talloc_report_full(top, stderr);
-	talloc_free(parent);
-	talloc_report_full(top, stderr);
-	talloc_report_full(NULL, stderr);
-	talloc_free(top);
-
-	torture_assert("loop", loop_destructor_count == 1, 
-				   "FAILED TO FIRE LOOP DESTRUCTOR\n");
-	loop_destructor_count = 0;
-
-	printf("success: loop\n");
-	return true;
-}
-
-static int fail_destructor_str(char *ptr)
-{
-	return -1;
-}
-
-static bool test_free_parent_deny_child(void)
-{
-	void *top = talloc_new(NULL);
-	char *level1;
-	char *level2;
-	char *level3;
-
-	printf("test: free_parent_deny_child\n# TALLOC FREE PARENT DENY CHILD\n");
-
-	level1 = talloc_strdup(top, "level1");
-	level2 = talloc_strdup(level1, "level2");
-	level3 = talloc_strdup(level2, "level3");
-
-	talloc_set_destructor(level3, fail_destructor_str);
-	talloc_free(level1);
-	talloc_set_destructor(level3, NULL);
-
-	CHECK_PARENT("free_parent_deny_child", level3, top);
-
-	talloc_free(top);
-
-	printf("success: free_parent_deny_child\n");
-	return true;
-}
-
-static bool test_talloc_ptrtype(void)
-{
-	void *top = talloc_new(NULL);
-	struct struct1 {
-		int foo;
-		int bar;
-	} *s1, *s2, **s3, ***s4;
-	const char *location1;
-	const char *location2;
-	const char *location3;
-	const char *location4;
-
-	printf("test: ptrtype\n# TALLOC PTRTYPE\n");
-
-	s1 = talloc_ptrtype(top, s1);location1 = __location__;
-
-	if (talloc_get_size(s1) != sizeof(struct struct1)) {
-		printf("failure: ptrtype [\n"
-		  "talloc_ptrtype() allocated the wrong size %lu (should be %lu)\n"
-		  "]\n", (unsigned long)talloc_get_size(s1),
-		           (unsigned long)sizeof(struct struct1));
-		return false;
-	}
-
-	if (strcmp(location1, talloc_get_name(s1)) != 0) {
-		printf("failure: ptrtype [\n"
-		  "talloc_ptrtype() sets the wrong name '%s' (should be '%s')\n]\n",
-			talloc_get_name(s1), location1);
-		return false;
-	}
-
-	s2 = talloc_array_ptrtype(top, s2, 10);location2 = __location__;
-
-	if (talloc_get_size(s2) != (sizeof(struct struct1) * 10)) {
-		printf("failure: ptrtype [\n"
-			   "talloc_array_ptrtype() allocated the wrong size "
-		       "%lu (should be %lu)\n]\n",
-			(unsigned long)talloc_get_size(s2),
-		    (unsigned long)(sizeof(struct struct1)*10));
-		return false;
-	}
-
-	if (strcmp(location2, talloc_get_name(s2)) != 0) {
-		printf("failure: ptrtype [\n"
-		"talloc_array_ptrtype() sets the wrong name '%s' (should be '%s')\n]\n",
-			talloc_get_name(s2), location2);
-		return false;
-	}
-
-	s3 = talloc_array_ptrtype(top, s3, 10);location3 = __location__;
-
-	if (talloc_get_size(s3) != (sizeof(struct struct1 *) * 10)) {
-		printf("failure: ptrtype [\n"
-			   "talloc_array_ptrtype() allocated the wrong size "
-		       "%lu (should be %lu)\n]\n",
-			   (unsigned long)talloc_get_size(s3),
-		       (unsigned long)(sizeof(struct struct1 *)*10));
-		return false;
-	}
-
-	torture_assert_str_equal("ptrtype", location3, talloc_get_name(s3),
-		"talloc_array_ptrtype() sets the wrong name");
-
-	s4 = talloc_array_ptrtype(top, s4, 10);location4 = __location__;
-
-	if (talloc_get_size(s4) != (sizeof(struct struct1 **) * 10)) {
-		printf("failure: ptrtype [\n"
-		      "talloc_array_ptrtype() allocated the wrong size "
-		       "%lu (should be %lu)\n]\n",
-			   (unsigned long)talloc_get_size(s4),
-		       (unsigned long)(sizeof(struct struct1 **)*10));
-		return false;
-	}
-
-	torture_assert_str_equal("ptrtype", location4, talloc_get_name(s4),
-		"talloc_array_ptrtype() sets the wrong name");
-
-	talloc_free(top);
-
-	printf("success: ptrtype\n");
-	return true;
-}
-
-static int _test_talloc_free_in_destructor(void **ptr)
-{
-	talloc_free(*ptr);
-	return 0;
-}
-
-static bool test_talloc_free_in_destructor(void)
-{
-	void *level0;
-	void *level1;
-	void *level2;
-	void *level3;
-	void *level4;
-	void **level5;
-
-	printf("test: free_in_destructor\n# TALLOC FREE IN DESTRUCTOR\n");
-
-	level0 = talloc_new(NULL);
-	level1 = talloc_new(level0);
-	level2 = talloc_new(level1);
-	level3 = talloc_new(level2);
-	level4 = talloc_new(level3);
-	level5 = talloc(level4, void *);
-
-	*level5 = level3;
-	(void)talloc_reference(level0, level3);
-	(void)talloc_reference(level3, level3);
-	(void)talloc_reference(level5, level3);
-
-	talloc_set_destructor(level5, _test_talloc_free_in_destructor);
-
-	talloc_free(level1);
-
-	talloc_free(level0);
-
-	printf("success: free_in_destructor\n");
-	return true;
-}
-
-static bool test_autofree(void)
-{
-#if _SAMBA_BUILD_ < 4
-	/* autofree test would kill smbtorture */
-	void *p;
-	printf("test: autofree\n# TALLOC AUTOFREE CONTEXT\n");
-
-	p = talloc_autofree_context();
-	talloc_free(p);
-
-	p = talloc_autofree_context();
-	talloc_free(p);
-
-	printf("success: autofree\n");
-#endif
-	return true;
-}
-
-static bool test_pool(void)
-{
-	void *pool;
-	void *p1, *p2, *p3, *p4;
-	void *p2_2;
-
-	pool = talloc_pool(NULL, 1024);
-
-	p1 = talloc_size(pool, 80);
-	memset(p1, 0x11, talloc_get_size(p1));
-	p2 = talloc_size(pool, 20);
-	memset(p2, 0x11, talloc_get_size(p2));
-	p3 = talloc_size(p1, 50);
-	memset(p3, 0x11, talloc_get_size(p3));
-	p4 = talloc_size(p3, 1000);
-	memset(p4, 0x11, talloc_get_size(p4));
-
-#if 1 /* this relies on ALWAYS_REALLOC == 0 in talloc.c */
-	p2_2 = talloc_realloc_size(pool, p2, 20+1);
-	torture_assert("pool realloc 20+1", p2_2 == p2, "failed: pointer changed");
-	memset(p2, 0x11, talloc_get_size(p2));
-	p2_2 = talloc_realloc_size(pool, p2, 20-1);
-	torture_assert("pool realloc 20-1", p2_2 == p2, "failed: pointer changed");
-	memset(p2, 0x11, talloc_get_size(p2));
-	p2_2 = talloc_realloc_size(pool, p2, 20-1);
-	torture_assert("pool realloc 20-1", p2_2 == p2, "failed: pointer changed");
-	memset(p2, 0x11, talloc_get_size(p2));
-
-	talloc_free(p3);
-
-	/* this should reclaim the memory of p4 and p3 */
-	p2_2 = talloc_realloc_size(pool, p2, 400);
-	torture_assert("pool realloc 400", p2_2 == p2, "failed: pointer changed");
-	memset(p2, 0x11, talloc_get_size(p2));
-
-	talloc_free(p1);
-
-	/* this should reclaim the memory of p1 */
-	p2_2 = talloc_realloc_size(pool, p2, 800);
-	torture_assert("pool realloc 800", p2_2 == p1, "failed: pointer not changed");
-	p2 = p2_2;
-	memset(p2, 0x11, talloc_get_size(p2));
-
-	/* this should do a malloc */
-	p2_2 = talloc_realloc_size(pool, p2, 1800);
-	torture_assert("pool realloc 1800", p2_2 != p2, "failed: pointer not changed");
-	p2 = p2_2;
-	memset(p2, 0x11, talloc_get_size(p2));
-
-	/* this should reclaim the memory from the pool */
-	p3 = talloc_size(pool, 80);
-	torture_assert("pool alloc 80", p3 == p1, "failed: pointer changed");
-	memset(p3, 0x11, talloc_get_size(p3));
-
-	talloc_free(p2);
-	talloc_free(p3);
-
-	p1 = talloc_size(pool, 80);
-	memset(p1, 0x11, talloc_get_size(p1));
-	p2 = talloc_size(pool, 20);
-	memset(p2, 0x11, talloc_get_size(p2));
-
-	talloc_free(p1);
-
-	p2_2 = talloc_realloc_size(pool, p2, 20-1);
-	torture_assert("pool realloc 20-1", p2_2 == p2, "failed: pointer changed");
-	memset(p2, 0x11, talloc_get_size(p2));
-	p2_2 = talloc_realloc_size(pool, p2, 20-1);
-	torture_assert("pool realloc 20-1", p2_2 == p2, "failed: pointer changed");
-	memset(p2, 0x11, talloc_get_size(p2));
-
-	/* this should do a malloc */
-	p2_2 = talloc_realloc_size(pool, p2, 1800);
-	torture_assert("pool realloc 1800", p2_2 != p2, "failed: pointer not changed");
-	p2 = p2_2;
-	memset(p2, 0x11, talloc_get_size(p2));
-
-	/* this should reclaim the memory from the pool */
-	p3 = talloc_size(pool, 800);
-	torture_assert("pool alloc 800", p3 == p1, "failed: pointer changed");
-	memset(p3, 0x11, talloc_get_size(p3));
-
-#endif /* this relies on ALWAYS_REALLOC == 0 in talloc.c */
-
-	talloc_free(pool);
-
-	return true;
-}
-
-static bool test_pool_steal(void)
-{
-	void *root;
-	void *pool;
-	void *p1, *p2;
-	void *p1_2, *p2_2;
-	size_t hdr;
-	size_t ofs1, ofs2;
-
-	root = talloc_new(NULL);
-	pool = talloc_pool(root, 1024);
-
-	p1 = talloc_size(pool, 4 * 16);
-	torture_assert("pool allocate 4 * 16", p1 != NULL, "failed ");
-	memset(p1, 0x11, talloc_get_size(p1));
-	p2 = talloc_size(pool, 4 * 16);
-	torture_assert("pool allocate 4 * 16", p2 > p1, "failed: !(p2 > p1) ");
-	memset(p2, 0x11, talloc_get_size(p2));
-
-	ofs1 = PTR_DIFF(p2, p1);
-	hdr = ofs1 - talloc_get_size(p1);
-
-	talloc_steal(root, p1);
-	talloc_steal(root, p2);
-
-	talloc_free(pool);
-
-	p1_2 = p1;
-
-#if 1 /* this relies on ALWAYS_REALLOC == 0 in talloc.c */
-	p1_2 = talloc_realloc_size(root, p1, 5 * 16);
-	torture_assert("pool realloc 5 * 16", p1_2 > p2, "failed: pointer not changed");
-	memset(p1_2, 0x11, talloc_get_size(p1_2));
-	ofs1 = PTR_DIFF(p1_2, p2);
-	ofs2 = talloc_get_size(p2) + hdr;
-
-	torture_assert("pool realloc ", ofs1 == ofs2, "failed: pointer offset unexpected");
-
-	p2_2 = talloc_realloc_size(root, p2, 3 * 16);
-	torture_assert("pool realloc 5 * 16", p2_2 == p2, "failed: pointer changed");
-	memset(p2_2, 0x11, talloc_get_size(p2_2));
-#endif /* this relies on ALWAYS_REALLOC == 0 in talloc.c */
-
-	talloc_free(p1_2);
-
-	p2_2 = p2;
-
-#if 1 /* this relies on ALWAYS_REALLOC == 0 in talloc.c */
-	/* now we should reclaim the full pool */
-	p2_2 = talloc_realloc_size(root, p2, 8 * 16);
-	torture_assert("pool realloc 8 * 16", p2_2 == p1, "failed: pointer not expected");
-	p2 = p2_2;
-	memset(p2_2, 0x11, talloc_get_size(p2_2));
-
-	/* now we malloc and free the full pool space */
-	p2_2 = talloc_realloc_size(root, p2, 2 * 1024);
-	torture_assert("pool realloc 2 * 1024", p2_2 != p1, "failed: pointer not expected");
-	memset(p2_2, 0x11, talloc_get_size(p2_2));
-
-#endif /* this relies on ALWAYS_REALLOC == 0 in talloc.c */
-
-	talloc_free(p2_2);
-
-	talloc_free(root);
-
-	return true;
-}
-
-static bool test_free_ref_null_context(void)
-{
-	void *p1, *p2, *p3;
-	int ret;
-
-	talloc_disable_null_tracking();
-	p1 = talloc_new(NULL);
-	p2 = talloc_new(NULL);
-
-	p3 = talloc_reference(p2, p1);
-	torture_assert("reference", p3 == p1, "failed: reference on null");
-
-	ret = talloc_free(p1);
-	torture_assert("ref free with null parent", ret == 0, "failed: free with null parent");
-	talloc_free(p2);
-
-	talloc_enable_null_tracking_no_autofree();
-	p1 = talloc_new(NULL);
-	p2 = talloc_new(NULL);
-
-	p3 = talloc_reference(p2, p1);
-	torture_assert("reference", p3 == p1, "failed: reference on null");
-
-	ret = talloc_free(p1);
-	torture_assert("ref free with null tracked parent", ret == 0, "failed: free with null parent");
-	talloc_free(p2);
-
-	return true;
-}
-
-static bool test_rusty(void)
-{
-	void *root;
-	const char *p1;
-
-	talloc_enable_null_tracking();
-	root = talloc_new(NULL);
-	p1 = talloc_strdup(root, "foo");
-	talloc_increase_ref_count(p1);
-	talloc_report_full(root, stdout);
-	talloc_free(root);
-	CHECK_BLOCKS("null_context", NULL, 2);
-	return true;
-}
-
-static bool test_free_children(void)
-{
-	void *root;
-	char *p1, *p2;
-	const char *name, *name2;
-
-	talloc_enable_null_tracking();
-	root = talloc_new(NULL);
-	p1 = talloc_strdup(root, "foo1");
-	p2 = talloc_strdup(p1, "foo2");
-
-	talloc_set_name(p1, "%s", "testname");
-	talloc_free_children(p1);
-	/* check its still a valid talloc ptr */
-	talloc_get_size(talloc_get_name(p1));
-	if (strcmp(talloc_get_name(p1), "testname") != 0) {
-		return false;
-	}
-
-	talloc_set_name(p1, "%s", "testname");
-	name = talloc_get_name(p1);
-	talloc_free_children(p1);
-	/* check its still a valid talloc ptr */
-	talloc_get_size(talloc_get_name(p1));
-	torture_assert("name", name == talloc_get_name(p1), "name ptr changed");
-	torture_assert("namecheck", strcmp(talloc_get_name(p1), "testname") == 0,
-		       "wrong name");
-	CHECK_BLOCKS("name1", p1, 2);
-
-	/* note that this does not free the old child name */
-	talloc_set_name_const(p1, "testname2");
-	name2 = talloc_get_name(p1);
-	/* but this does */
-	talloc_free_children(p1);
-	torture_assert("namecheck", strcmp(talloc_get_name(p1), "testname2") == 0,
-		       "wrong name");
-	CHECK_BLOCKS("name1", p1, 1);
-
-	talloc_report_full(root, stdout);
-	talloc_free(root);
-	return true;
-}
-
-
-static void test_reset(void)
-{
-	talloc_set_log_fn(test_log_stdout);
-	test_abort_stop();
-	talloc_disable_null_tracking();
-	talloc_enable_null_tracking_no_autofree();
-}
-
-bool torture_local_talloc(struct torture_context *tctx)
-{
-	bool ret = true;
-
-	setlinebuf(stdout);
-
-	test_reset();
-	ret &= test_ref1();
-	test_reset();
-	ret &= test_ref2();
-	test_reset();
-	ret &= test_ref3();
-	test_reset();
-	ret &= test_ref4();
-	test_reset();
-	ret &= test_unlink1(); 
-	test_reset();
-	ret &= test_misc();
-	test_reset();
-	ret &= test_realloc();
-	test_reset();
-	ret &= test_realloc_child(); 
-	test_reset();
-	ret &= test_steal(); 
-	test_reset();
-	ret &= test_move(); 
-	test_reset();
-	ret &= test_unref_reparent();
-	test_reset();
-	ret &= test_realloc_fn(); 
-	test_reset();
-	ret &= test_type();
-	test_reset();
-	ret &= test_lifeless(); 
-	test_reset();
-	ret &= test_loop();
-	test_reset();
-	ret &= test_free_parent_deny_child(); 
-	test_reset();
-	ret &= test_talloc_ptrtype();
-	test_reset();
-	ret &= test_talloc_free_in_destructor();
-	test_reset();
-	ret &= test_pool();
-	test_reset();
-	ret &= test_pool_steal();
-	test_reset();
-	ret &= test_free_ref_null_context();
-	test_reset();
-	ret &= test_rusty();
-	test_reset();
-	ret &= test_free_children();
-
-	if (ret) {
-		test_reset();
-		ret &= test_speed();
-	}
-	test_reset();
-	ret &= test_autofree();
-
-	test_reset();
-	talloc_disable_null_tracking();
-	return ret;
-}
diff --git a/lib/talloc/testsuite_main.c b/lib/talloc/testsuite_main.c
deleted file mode 100644
index 50ce0f8..0000000
--- a/lib/talloc/testsuite_main.c
+++ /dev/null
@@ -1,36 +0,0 @@
-/*
-   Unix SMB/CIFS implementation.
-
-   local testing of talloc routines.
-
-   Copyright (C) Andrew Tridgell 2004
-
-     ** NOTE! The following LGPL license applies to the talloc
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-
-#include "replace.h"
-
-#include "talloc_testsuite.h"
-
-int main(void)
-{
-	bool ret = torture_local_talloc(NULL);
-	if (!ret)
-		return -1;
-	return 0;
-}
diff --git a/lib/talloc/web/index.html b/lib/talloc/web/index.html
deleted file mode 100644
index 388ec2c..0000000
--- a/lib/talloc/web/index.html
+++ /dev/null
@@ -1,51 +0,0 @@
-<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 3.2//EN">
-<HTML>
-<HEAD>
-<TITLE>talloc</TITLE>
-</HEAD>
-<BODY BGCOLOR="#ffffff" TEXT="#000000" VLINK="#292555" LINK="#292555" ALINK="#cc0033">
-
-<h1>talloc</h1>
-
-talloc is a hierarchical pool based memory allocator with
-destructors. It is the core memory allocator used in Samba, and has
-made a huge difference in many aspects of Samba4 development.<p>
-
-To get started with talloc, I would recommend you read the <a
-href="http://samba.org/ftp/unpacked/talloc/talloc_guide.txt">talloc guide</a>.
-
-<h2>Download</h2>
-You can download the latest releases of talloc from the <a
-href="http://samba.org/ftp/talloc">talloc directory</a> on the samba public
-source archive.
-
-<h2>Discussion and bug reports</h2>
-
-talloc does not currently have its own mailing list or bug tracking
-system. For now, please use the <a
-href="https://lists.samba.org/mailman/listinfo/samba-technical">samba-technical</a>
-mailing list, and the <a href="http://bugzilla.samba.org/">Samba
-bugzilla</a> bug tracking system.
-
-<h2>Development</h2>
-
-You can download the latest code either via git or rsync.<br>
-<br>
-To fetch via git see the following guide:<br>
-<a href="http://wiki.samba.org/index.php/Using_Git_for_Samba_Development">Using Git for Samba Development</a><br>
-Once you have cloned the tree switch to the master branch and cd into the lib/talloc directory.<br>
-<br>
-To fetch via rsync use this command:
-
-<pre>
-  rsync -Pavz samba.org::ftp/unpacked/standalone_projects/lib/talloc .
-</pre>
-
-<hr>
-<tiny>
-<a href="http://samba.org/~tridge/">Andrew Tridgell</a><br>
-talloc AT tridgell.net
-</tiny>
-
-</BODY>
-</HTML>
diff --git a/lib/tdb/ABI/tdb-1.2.10.sigs b/lib/tdb/ABI/tdb-1.2.10.sigs
deleted file mode 100644
index 61f6c19..0000000
--- a/lib/tdb/ABI/tdb-1.2.10.sigs
+++ /dev/null
@@ -1,66 +0,0 @@
-tdb_add_flags: void (struct tdb_context *, unsigned int)
-tdb_append: int (struct tdb_context *, TDB_DATA, TDB_DATA)
-tdb_chainlock: int (struct tdb_context *, TDB_DATA)
-tdb_chainlock_mark: int (struct tdb_context *, TDB_DATA)
-tdb_chainlock_nonblock: int (struct tdb_context *, TDB_DATA)
-tdb_chainlock_read: int (struct tdb_context *, TDB_DATA)
-tdb_chainlock_unmark: int (struct tdb_context *, TDB_DATA)
-tdb_chainunlock: int (struct tdb_context *, TDB_DATA)
-tdb_chainunlock_read: int (struct tdb_context *, TDB_DATA)
-tdb_check: int (struct tdb_context *, int (*)(TDB_DATA, TDB_DATA, void *), void *)
-tdb_close: int (struct tdb_context *)
-tdb_delete: int (struct tdb_context *, TDB_DATA)
-tdb_dump_all: void (struct tdb_context *)
-tdb_enable_seqnum: void (struct tdb_context *)
-tdb_error: enum TDB_ERROR (struct tdb_context *)
-tdb_errorstr: const char *(struct tdb_context *)
-tdb_exists: int (struct tdb_context *, TDB_DATA)
-tdb_fd: int (struct tdb_context *)
-tdb_fetch: TDB_DATA (struct tdb_context *, TDB_DATA)
-tdb_firstkey: TDB_DATA (struct tdb_context *)
-tdb_freelist_size: int (struct tdb_context *)
-tdb_get_flags: int (struct tdb_context *)
-tdb_get_logging_private: void *(struct tdb_context *)
-tdb_get_seqnum: int (struct tdb_context *)
-tdb_hash_size: int (struct tdb_context *)
-tdb_increment_seqnum_nonblock: void (struct tdb_context *)
-tdb_jenkins_hash: unsigned int (TDB_DATA *)
-tdb_lock_nonblock: int (struct tdb_context *, int, int)
-tdb_lockall: int (struct tdb_context *)
-tdb_lockall_mark: int (struct tdb_context *)
-tdb_lockall_nonblock: int (struct tdb_context *)
-tdb_lockall_read: int (struct tdb_context *)
-tdb_lockall_read_nonblock: int (struct tdb_context *)
-tdb_lockall_unmark: int (struct tdb_context *)
-tdb_log_fn: tdb_log_func (struct tdb_context *)
-tdb_map_size: size_t (struct tdb_context *)
-tdb_name: const char *(struct tdb_context *)
-tdb_nextkey: TDB_DATA (struct tdb_context *, TDB_DATA)
-tdb_null: dptr = 0xXXXX, dsize = 0
-tdb_open: struct tdb_context *(const char *, int, int, int, mode_t)
-tdb_open_ex: struct tdb_context *(const char *, int, int, int, mode_t, const struct tdb_logging_context *, tdb_hash_func)
-tdb_parse_record: int (struct tdb_context *, TDB_DATA, int (*)(TDB_DATA, TDB_DATA, void *), void *)
-tdb_printfreelist: int (struct tdb_context *)
-tdb_remove_flags: void (struct tdb_context *, unsigned int)
-tdb_reopen: int (struct tdb_context *)
-tdb_reopen_all: int (int)
-tdb_repack: int (struct tdb_context *)
-tdb_set_logging_function: void (struct tdb_context *, const struct tdb_logging_context *)
-tdb_set_max_dead: void (struct tdb_context *, int)
-tdb_setalarm_sigptr: void (struct tdb_context *, volatile sig_atomic_t *)
-tdb_store: int (struct tdb_context *, TDB_DATA, TDB_DATA, int)
-tdb_summary: char *(struct tdb_context *)
-tdb_transaction_cancel: int (struct tdb_context *)
-tdb_transaction_commit: int (struct tdb_context *)
-tdb_transaction_prepare_commit: int (struct tdb_context *)
-tdb_transaction_start: int (struct tdb_context *)
-tdb_transaction_start_nonblock: int (struct tdb_context *)
-tdb_transaction_write_lock_mark: int (struct tdb_context *)
-tdb_transaction_write_lock_unmark: int (struct tdb_context *)
-tdb_traverse: int (struct tdb_context *, tdb_traverse_func, void *)
-tdb_traverse_read: int (struct tdb_context *, tdb_traverse_func, void *)
-tdb_unlock: int (struct tdb_context *, int, int)
-tdb_unlockall: int (struct tdb_context *)
-tdb_unlockall_read: int (struct tdb_context *)
-tdb_validate_freelist: int (struct tdb_context *, int *)
-tdb_wipe_all: int (struct tdb_context *)
diff --git a/lib/tdb/common/check.c b/lib/tdb/common/check.c
deleted file mode 100644
index 313f55c..0000000
--- a/lib/tdb/common/check.c
+++ /dev/null
@@ -1,472 +0,0 @@
- /*
-   Unix SMB/CIFS implementation.
-
-   trivial database library
-
-   Copyright (C) Rusty Russell		   2009
-
-     ** NOTE! The following LGPL license applies to the tdb
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-#include "tdb_private.h"
-
-/* Since we opened it, these shouldn't fail unless it's recent corruption. */
-static bool tdb_check_header(struct tdb_context *tdb, tdb_off_t *recovery)
-{
-	struct tdb_header hdr;
-	uint32_t h1, h2;
-
-	if (tdb->methods->tdb_read(tdb, 0, &hdr, sizeof(hdr), 0) == -1)
-		return false;
-	if (strcmp(hdr.magic_food, TDB_MAGIC_FOOD) != 0)
-		goto corrupt;
-
-	CONVERT(hdr);
-	if (hdr.version != TDB_VERSION)
-		goto corrupt;
-
-	if (hdr.rwlocks != 0 && hdr.rwlocks != TDB_HASH_RWLOCK_MAGIC)
-		goto corrupt;
-
-	tdb_header_hash(tdb, &h1, &h2);
-	if (hdr.magic1_hash && hdr.magic2_hash &&
-	    (hdr.magic1_hash != h1 || hdr.magic2_hash != h2))
-		goto corrupt;
-
-	if (hdr.hash_size == 0)
-		goto corrupt;
-
-	if (hdr.hash_size != tdb->header.hash_size)
-		goto corrupt;
-
-	if (hdr.recovery_start != 0 &&
-	    hdr.recovery_start < TDB_DATA_START(tdb->header.hash_size))
-		goto corrupt;
-
-	*recovery = hdr.recovery_start;
-	return true;
-
-corrupt:
-	tdb->ecode = TDB_ERR_CORRUPT;
-	TDB_LOG((tdb, TDB_DEBUG_ERROR, "Header is corrupt\n"));
-	return false;
-}
-
-/* Generic record header check. */
-static bool tdb_check_record(struct tdb_context *tdb,
-			     tdb_off_t off,
-			     const struct tdb_record *rec)
-{
-	tdb_off_t tailer;
-
-	/* Check rec->next: 0 or points to record offset, aligned. */
-	if (rec->next > 0 && rec->next < TDB_DATA_START(tdb->header.hash_size)){
-		TDB_LOG((tdb, TDB_DEBUG_ERROR,
-			 "Record offset %d too small next %d\n",
-			 off, rec->next));
-		goto corrupt;
-	}
-	if (rec->next + sizeof(*rec) < rec->next) {
-		TDB_LOG((tdb, TDB_DEBUG_ERROR,
-			 "Record offset %d too large next %d\n",
-			 off, rec->next));
-		goto corrupt;
-	}
-	if ((rec->next % TDB_ALIGNMENT) != 0) {
-		TDB_LOG((tdb, TDB_DEBUG_ERROR,
-			 "Record offset %d misaligned next %d\n",
-			 off, rec->next));
-		goto corrupt;
-	}
-	if (tdb->methods->tdb_oob(tdb, rec->next, sizeof(*rec), 0))
-		goto corrupt;
-
-	/* Check rec_len: similar to rec->next, implies next record. */
-	if ((rec->rec_len % TDB_ALIGNMENT) != 0) {
-		TDB_LOG((tdb, TDB_DEBUG_ERROR,
-			 "Record offset %d misaligned length %d\n",
-			 off, rec->rec_len));
-		goto corrupt;
-	}
-	/* Must fit tailer. */
-	if (rec->rec_len < sizeof(tailer)) {
-		TDB_LOG((tdb, TDB_DEBUG_ERROR,
-			 "Record offset %d too short length %d\n",
-			 off, rec->rec_len));
-		goto corrupt;
-	}
-	/* OOB allows "right at the end" access, so this works for last rec. */
-	if (tdb->methods->tdb_oob(tdb, off, sizeof(*rec)+rec->rec_len, 0))
-		goto corrupt;
-
-	/* Check tailer. */
-	if (tdb_ofs_read(tdb, off+sizeof(*rec)+rec->rec_len-sizeof(tailer),
-			 &tailer) == -1)
-		goto corrupt;
-	if (tailer != sizeof(*rec) + rec->rec_len) {
-		TDB_LOG((tdb, TDB_DEBUG_ERROR,
-			 "Record offset %d invalid tailer\n", off));
-		goto corrupt;
-	}
-
-	return true;
-
-corrupt:
-	tdb->ecode = TDB_ERR_CORRUPT;
-	return false;
-}
-
-/* Grab some bytes: may copy if can't use mmap.
-   Caller has already done bounds check. */
-static TDB_DATA get_bytes(struct tdb_context *tdb,
-			  tdb_off_t off, tdb_len_t len)
-{
-	TDB_DATA d;
-
-	d.dsize = len;
-
-	if (tdb->transaction == NULL && tdb->map_ptr != NULL)
-		d.dptr = (unsigned char *)tdb->map_ptr + off;
-	else
-		d.dptr = tdb_alloc_read(tdb, off, d.dsize);
-	return d;
-}
-
-/* Frees data if we're not able to simply use mmap. */
-static void put_bytes(struct tdb_context *tdb, TDB_DATA d)
-{
-	if (tdb->transaction == NULL && tdb->map_ptr != NULL)
-		return;
-	free(d.dptr);
-}
-
-/* We use the excellent Jenkins lookup3 hash; this is based on hash_word2.
- * See: http://burtleburtle.net/bob/c/lookup3.c
- */
-#define rot(x,k) (((x)<<(k)) | ((x)>>(32-(k))))
-static void hash(uint32_t key, uint32_t *pc, uint32_t *pb)
-{
-	uint32_t a,b,c;
-
-	/* Set up the internal state */
-	a = b = c = 0xdeadbeef + *pc;
-	c += *pb;
-	a += key;
-	c ^= b; c -= rot(b,14);
-	a ^= c; a -= rot(c,11);
-	b ^= a; b -= rot(a,25);
-	c ^= b; c -= rot(b,16);
-	a ^= c; a -= rot(c,4);
-	b ^= a; b -= rot(a,14);
-	c ^= b; c -= rot(b,24);
-	*pc=c; *pb=b;
-}
-
-/*
-  We want to check that all free records are in the free list
-  (only once), and all free list entries are free records.  Similarly
-  for each hash chain of used records.
-
-  Doing that naively (without walking hash chains, since we want to be
-  linear) means keeping a list of records which have been seen in each
-  hash chain, and another of records pointed to (ie. next pointers
-  from records and the initial hash chain heads).  These two lists
-  should be equal.  This will take 8 bytes per record, and require
-  sorting at the end.
-
-  So instead, we record each offset in a bitmap such a way that
-  recording it twice will cancel out.  Since each offset should appear
-  exactly twice, the bitmap should be zero at the end.
-
-  The approach was inspired by Bloom Filters (see Wikipedia).  For
-  each value, we flip K bits in a bitmap of size N.  The number of
-  distinct arrangements is:
-
-	N! / (K! * (N-K)!)
-
-  Of course, not all arrangements are actually distinct, but testing
-  shows this formula to be close enough.
-
-  So, if K == 8 and N == 256, the probability of two things flipping the same
-  bits is 1 in 409,663,695,276,000.
-
-  Given that ldb uses a hash size of 10000, using 32 bytes per hash chain
-  (320k) seems reasonable.
-*/
-#define NUM_HASHES 8
-#define BITMAP_BITS 256
-
-static void bit_flip(unsigned char bits[], unsigned int idx)
-{
-	bits[idx / CHAR_BIT] ^= (1 << (idx % CHAR_BIT));
-}
-
-/* We record offsets in a bitmap for the particular chain it should be in.  */
-static void record_offset(unsigned char bits[], tdb_off_t off)
-{
-	uint32_t h1 = off, h2 = 0;
-	unsigned int i;
-
-	/* We get two good hash values out of jhash2, so we use both.  Then
-	 * we keep going to produce further hash values. */
-	for (i = 0; i < NUM_HASHES / 2; i++) {
-		hash(off, &h1, &h2);
-		bit_flip(bits, h1 % BITMAP_BITS);
-		bit_flip(bits, h2 % BITMAP_BITS);
-		h2++;
-	}
-}
-
-/* Check that an in-use record is valid. */
-static bool tdb_check_used_record(struct tdb_context *tdb,
-				  tdb_off_t off,
-				  const struct tdb_record *rec,
-				  unsigned char **hashes,
-				  int (*check)(TDB_DATA, TDB_DATA, void *),
-				  void *private_data)
-{
-	TDB_DATA key, data;
-
-	if (!tdb_check_record(tdb, off, rec))
-		return false;
-
-	/* key + data + tailer must fit in record */
-	if (rec->key_len + rec->data_len + sizeof(tdb_off_t) > rec->rec_len) {
-		TDB_LOG((tdb, TDB_DEBUG_ERROR,
-			 "Record offset %d too short for contents\n", off));
-		return false;
-	}
-
-	key = get_bytes(tdb, off + sizeof(*rec), rec->key_len);
-	if (!key.dptr)
-		return false;
-
-	if (tdb->hash_fn(&key) != rec->full_hash) {
-		TDB_LOG((tdb, TDB_DEBUG_ERROR,
-			 "Record offset %d has incorrect hash\n", off));
-		goto fail_put_key;
-	}
-
-	/* Mark this offset as a known value for this hash bucket. */
-	record_offset(hashes[BUCKET(rec->full_hash)+1], off);
-	/* And similarly if the next pointer is valid. */
-	if (rec->next)
-		record_offset(hashes[BUCKET(rec->full_hash)+1], rec->next);
-
-	/* If they supply a check function and this record isn't dead,
-	   get data and feed it. */
-	if (check && rec->magic != TDB_DEAD_MAGIC) {
-		data = get_bytes(tdb, off + sizeof(*rec) + rec->key_len,
-				 rec->data_len);
-		if (!data.dptr)
-			goto fail_put_key;
-
-		if (check(key, data, private_data) == -1)
-			goto fail_put_data;
-		put_bytes(tdb, data);
-	}
-
-	put_bytes(tdb, key);
-	return true;
-
-fail_put_data:
-	put_bytes(tdb, data);
-fail_put_key:
-	put_bytes(tdb, key);
-	return false;
-}
-
-/* Check that an unused record is valid. */
-static bool tdb_check_free_record(struct tdb_context *tdb,
-				  tdb_off_t off,
-				  const struct tdb_record *rec,
-				  unsigned char **hashes)
-{
-	if (!tdb_check_record(tdb, off, rec))
-		return false;
-
-	/* Mark this offset as a known value for the free list. */
-	record_offset(hashes[0], off);
-	/* And similarly if the next pointer is valid. */
-	if (rec->next)
-		record_offset(hashes[0], rec->next);
-	return true;
-}
-
-/* Slow, but should be very rare. */
-size_t tdb_dead_space(struct tdb_context *tdb, tdb_off_t off)
-{
-	size_t len;
-
-	for (len = 0; off + len < tdb->map_size; len++) {
-		char c;
-		if (tdb->methods->tdb_read(tdb, off, &c, 1, 0))
-			return 0;
-		if (c != 0 && c != 0x42)
-			break;
-	}
-	return len;
-}
-
-_PUBLIC_ int tdb_check(struct tdb_context *tdb,
-	      int (*check)(TDB_DATA key, TDB_DATA data, void *private_data),
-	      void *private_data)
-{
-	unsigned int h;
-	unsigned char **hashes;
-	tdb_off_t off, recovery_start;
-	struct tdb_record rec;
-	bool found_recovery = false;
-	tdb_len_t dead;
-	bool locked;
-
-	/* Read-only databases use no locking at all: it's best-effort.
-	 * We may have a write lock already, so skip that case too. */
-	if (tdb->read_only || tdb->allrecord_lock.count != 0) {
-		locked = false;
-	} else {
-		if (tdb_lockall_read(tdb) == -1)
-			return -1;
-		locked = true;
-	}
-
-	/* Make sure we know true size of the underlying file. */
-	tdb->methods->tdb_oob(tdb, tdb->map_size, 1, 1);
-
-	/* Header must be OK: also gets us the recovery ptr, if any. */
-	if (!tdb_check_header(tdb, &recovery_start))
-		goto unlock;
-
-	/* We should have the whole header, too. */
-	if (tdb->map_size < TDB_DATA_START(tdb->header.hash_size)) {
-		tdb->ecode = TDB_ERR_CORRUPT;
-		TDB_LOG((tdb, TDB_DEBUG_ERROR, "File too short for hashes\n"));
-		goto unlock;
-	}
-
-	/* One big malloc: pointers then bit arrays. */
-	hashes = (unsigned char **)calloc(
-			1, sizeof(hashes[0]) * (1+tdb->header.hash_size)
-			+ BITMAP_BITS / CHAR_BIT * (1+tdb->header.hash_size));
-	if (!hashes) {
-		tdb->ecode = TDB_ERR_OOM;
-		goto unlock;
-	}
-
-	/* Initialize pointers */
-	hashes[0] = (unsigned char *)(&hashes[1+tdb->header.hash_size]);
-	for (h = 1; h < 1+tdb->header.hash_size; h++)
-		hashes[h] = hashes[h-1] + BITMAP_BITS / CHAR_BIT;
-
-	/* Freelist and hash headers are all in a row: read them. */
-	for (h = 0; h < 1+tdb->header.hash_size; h++) {
-		if (tdb_ofs_read(tdb, FREELIST_TOP + h*sizeof(tdb_off_t),
-				 &off) == -1)
-			goto free;
-		if (off)
-			record_offset(hashes[h], off);
-	}
-
-	/* For each record, read it in and check it's ok. */
-	for (off = TDB_DATA_START(tdb->header.hash_size);
-	     off < tdb->map_size;
-	     off += sizeof(rec) + rec.rec_len) {
-		if (tdb->methods->tdb_read(tdb, off, &rec, sizeof(rec),
-					   DOCONV()) == -1)
-			goto free;
-		switch (rec.magic) {
-		case TDB_MAGIC:
-		case TDB_DEAD_MAGIC:
-			if (!tdb_check_used_record(tdb, off, &rec, hashes,
-						   check, private_data))
-				goto free;
-			break;
-		case TDB_FREE_MAGIC:
-			if (!tdb_check_free_record(tdb, off, &rec, hashes))
-				goto free;
-			break;
-		/* If we crash after ftruncate, we can get zeroes or fill. */
-		case TDB_RECOVERY_INVALID_MAGIC:
-		case 0x42424242:
-			if (recovery_start == off) {
-				found_recovery = true;
-				break;
-			}
-			dead = tdb_dead_space(tdb, off);
-			if (dead < sizeof(rec))
-				goto corrupt;
-
-			TDB_LOG((tdb, TDB_DEBUG_ERROR,
-				 "Dead space at %d-%d (of %u)\n",
-				 off, off + dead, tdb->map_size));
-			rec.rec_len = dead - sizeof(rec);
-			break;
-		case TDB_RECOVERY_MAGIC:
-			if (recovery_start != off) {
-				TDB_LOG((tdb, TDB_DEBUG_ERROR,
-					 "Unexpected recovery record at offset %d\n",
-					 off));
-				goto free;
-			}
-			found_recovery = true;
-			break;
-		default: ;
-		corrupt:
-			tdb->ecode = TDB_ERR_CORRUPT;
-			TDB_LOG((tdb, TDB_DEBUG_ERROR,
-				 "Bad magic 0x%x at offset %d\n",
-				 rec.magic, off));
-			goto free;
-		}
-	}
-
-	/* Now, hashes should all be empty: each record exists and is referred
-	 * to by one other. */
-	for (h = 0; h < 1+tdb->header.hash_size; h++) {
-		unsigned int i;
-		for (i = 0; i < BITMAP_BITS / CHAR_BIT; i++) {
-			if (hashes[h][i] != 0) {
-				tdb->ecode = TDB_ERR_CORRUPT;
-				TDB_LOG((tdb, TDB_DEBUG_ERROR,
-					 "Hashes do not match records\n"));
-				goto free;
-			}
-		}
-	}
-
-	/* We must have found recovery area if there was one. */
-	if (recovery_start != 0 && !found_recovery) {
-		TDB_LOG((tdb, TDB_DEBUG_ERROR,
-			 "Expected a recovery area at %u\n",
-			 recovery_start));
-		goto free;
-	}
-
-	free(hashes);
-	if (locked) {
-		tdb_unlockall_read(tdb);
-	}
-	return 0;
-
-free:
-	free(hashes);
-unlock:
-	if (locked) {
-		tdb_unlockall_read(tdb);
-	}
-	return -1;
-}
diff --git a/lib/tdb/common/dump.c b/lib/tdb/common/dump.c
deleted file mode 100644
index 67de04e..0000000
--- a/lib/tdb/common/dump.c
+++ /dev/null
@@ -1,137 +0,0 @@
- /* 
-   Unix SMB/CIFS implementation.
-
-   trivial database library
-
-   Copyright (C) Andrew Tridgell              1999-2005
-   Copyright (C) Paul `Rusty' Russell		   2000
-   Copyright (C) Jeremy Allison			   2000-2003
-
-     ** NOTE! The following LGPL license applies to the tdb
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-
-#include "tdb_private.h"
-
-static tdb_off_t tdb_dump_record(struct tdb_context *tdb, int hash,
-				 tdb_off_t offset)
-{
-	struct tdb_record rec;
-	tdb_off_t tailer_ofs, tailer;
-
-	if (tdb->methods->tdb_read(tdb, offset, (char *)&rec, 
-				   sizeof(rec), DOCONV()) == -1) {
-		printf("ERROR: failed to read record at %u\n", offset);
-		return 0;
-	}
-
-	printf(" rec: hash=%d offset=0x%08x next=0x%08x rec_len=%d "
-	       "key_len=%d data_len=%d full_hash=0x%x magic=0x%x\n",
-	       hash, offset, rec.next, rec.rec_len, rec.key_len, rec.data_len,
-	       rec.full_hash, rec.magic);
-
-	tailer_ofs = offset + sizeof(rec) + rec.rec_len - sizeof(tdb_off_t);
-
-	if (tdb_ofs_read(tdb, tailer_ofs, &tailer) == -1) {
-		printf("ERROR: failed to read tailer at %u\n", tailer_ofs);
-		return rec.next;
-	}
-
-	if (tailer != rec.rec_len + sizeof(rec)) {
-		printf("ERROR: tailer does not match record! tailer=%u totalsize=%u\n",
-				(unsigned int)tailer, (unsigned int)(rec.rec_len + sizeof(rec)));
-	}
-	return rec.next;
-}
-
-static int tdb_dump_chain(struct tdb_context *tdb, int i)
-{
-	tdb_off_t rec_ptr, top;
-
-	top = TDB_HASH_TOP(i);
-
-	if (tdb_lock(tdb, i, F_WRLCK) != 0)
-		return -1;
-
-	if (tdb_ofs_read(tdb, top, &rec_ptr) == -1)
-		return tdb_unlock(tdb, i, F_WRLCK);
-
-	if (rec_ptr)
-		printf("hash=%d\n", i);
-
-	while (rec_ptr) {
-		rec_ptr = tdb_dump_record(tdb, i, rec_ptr);
-	}
-
-	return tdb_unlock(tdb, i, F_WRLCK);
-}
-
-_PUBLIC_ void tdb_dump_all(struct tdb_context *tdb)
-{
-	int i;
-	for (i=0;i<tdb->header.hash_size;i++) {
-		tdb_dump_chain(tdb, i);
-	}
-	printf("freelist:\n");
-	tdb_dump_chain(tdb, -1);
-}
-
-_PUBLIC_ int tdb_printfreelist(struct tdb_context *tdb)
-{
-	int ret;
-	long total_free = 0;
-	tdb_off_t offset, rec_ptr;
-	struct tdb_record rec;
-
-	if ((ret = tdb_lock(tdb, -1, F_WRLCK)) != 0)
-		return ret;
-
-	offset = FREELIST_TOP;
-
-	/* read in the freelist top */
-	if (tdb_ofs_read(tdb, offset, &rec_ptr) == -1) {
-		tdb_unlock(tdb, -1, F_WRLCK);
-		return 0;
-	}
-
-	printf("freelist top=[0x%08x]\n", rec_ptr );
-	while (rec_ptr) {
-		if (tdb->methods->tdb_read(tdb, rec_ptr, (char *)&rec, 
-					   sizeof(rec), DOCONV()) == -1) {
-			tdb_unlock(tdb, -1, F_WRLCK);
-			return -1;
-		}
-
-		if (rec.magic != TDB_FREE_MAGIC) {
-			printf("bad magic 0x%08x in free list\n", rec.magic);
-			tdb_unlock(tdb, -1, F_WRLCK);
-			return -1;
-		}
-
-		printf("entry offset=[0x%08x], rec.rec_len = [0x%08x (%d)] (end = 0x%08x)\n", 
-		       rec_ptr, rec.rec_len, rec.rec_len, rec_ptr + rec.rec_len);
-		total_free += rec.rec_len;
-
-		/* move to the next record */
-		rec_ptr = rec.next;
-	}
-	printf("total rec_len = [0x%08x (%d)]\n", (int)total_free, 
-               (int)total_free);
-
-	return tdb_unlock(tdb, -1, F_WRLCK);
-}
-
diff --git a/lib/tdb/common/error.c b/lib/tdb/common/error.c
deleted file mode 100644
index 2aaaa81..0000000
--- a/lib/tdb/common/error.c
+++ /dev/null
@@ -1,57 +0,0 @@
- /* 
-   Unix SMB/CIFS implementation.
-
-   trivial database library
-
-   Copyright (C) Andrew Tridgell              1999-2005
-   Copyright (C) Paul `Rusty' Russell		   2000
-   Copyright (C) Jeremy Allison			   2000-2003
-
-     ** NOTE! The following LGPL license applies to the tdb
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-
-#include "tdb_private.h"
-
-_PUBLIC_ enum TDB_ERROR tdb_error(struct tdb_context *tdb)
-{
-	return tdb->ecode;
-}
-
-static struct tdb_errname {
-	enum TDB_ERROR ecode; const char *estring;
-} emap[] = { {TDB_SUCCESS, "Success"},
-	     {TDB_ERR_CORRUPT, "Corrupt database"},
-	     {TDB_ERR_IO, "IO Error"},
-	     {TDB_ERR_LOCK, "Locking error"},
-	     {TDB_ERR_OOM, "Out of memory"},
-	     {TDB_ERR_EXISTS, "Record exists"},
-	     {TDB_ERR_NOLOCK, "Lock exists on other keys"},
-	     {TDB_ERR_EINVAL, "Invalid parameter"},
-	     {TDB_ERR_NOEXIST, "Record does not exist"},
-	     {TDB_ERR_RDONLY, "write not permitted"} };
-
-/* Error string for the last tdb error */
-_PUBLIC_ const char *tdb_errorstr(struct tdb_context *tdb)
-{
-	uint32_t i;
-	for (i = 0; i < sizeof(emap) / sizeof(struct tdb_errname); i++)
-		if (tdb->ecode == emap[i].ecode)
-			return emap[i].estring;
-	return "Invalid error code";
-}
-
diff --git a/lib/tdb/common/freelist.c b/lib/tdb/common/freelist.c
deleted file mode 100644
index 6358f64..0000000
--- a/lib/tdb/common/freelist.c
+++ /dev/null
@@ -1,386 +0,0 @@
- /* 
-   Unix SMB/CIFS implementation.
-
-   trivial database library
-
-   Copyright (C) Andrew Tridgell              1999-2005
-   Copyright (C) Paul `Rusty' Russell		   2000
-   Copyright (C) Jeremy Allison			   2000-2003
-
-     ** NOTE! The following LGPL license applies to the tdb
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-
-#include "tdb_private.h"
-
-/* 'right' merges can involve O(n^2) cost when combined with a
-   traverse, so they are disabled until we find a way to do them in 
-   O(1) time
-*/
-#define USE_RIGHT_MERGES 0
-
-/* read a freelist record and check for simple errors */
-int tdb_rec_free_read(struct tdb_context *tdb, tdb_off_t off, struct tdb_record *rec)
-{
-	if (tdb->methods->tdb_read(tdb, off, rec, sizeof(*rec),DOCONV()) == -1)
-		return -1;
-
-	if (rec->magic == TDB_MAGIC) {
-		/* this happens when a app is showdown while deleting a record - we should
-		   not completely fail when this happens */
-		TDB_LOG((tdb, TDB_DEBUG_WARNING, "tdb_rec_free_read non-free magic 0x%x at offset=%d - fixing\n", 
-			 rec->magic, off));
-		rec->magic = TDB_FREE_MAGIC;
-		if (tdb->methods->tdb_write(tdb, off, rec, sizeof(*rec)) == -1)
-			return -1;
-	}
-
-	if (rec->magic != TDB_FREE_MAGIC) {
-		/* Ensure ecode is set for log fn. */
-		tdb->ecode = TDB_ERR_CORRUPT;
-		TDB_LOG((tdb, TDB_DEBUG_WARNING, "tdb_rec_free_read bad magic 0x%x at offset=%d\n", 
-			   rec->magic, off));
-		return -1;
-	}
-	if (tdb->methods->tdb_oob(tdb, rec->next, sizeof(*rec), 0) != 0)
-		return -1;
-	return 0;
-}
-
-
-#if USE_RIGHT_MERGES
-/* Remove an element from the freelist.  Must have alloc lock. */
-static int remove_from_freelist(struct tdb_context *tdb, tdb_off_t off, tdb_off_t next)
-{
-	tdb_off_t last_ptr, i;
-
-	/* read in the freelist top */
-	last_ptr = FREELIST_TOP;
-	while (tdb_ofs_read(tdb, last_ptr, &i) != -1 && i != 0) {
-		if (i == off) {
-			/* We've found it! */
-			return tdb_ofs_write(tdb, last_ptr, &next);
-		}
-		/* Follow chain (next offset is at start of record) */
-		last_ptr = i;
-	}
-	tdb->ecode = TDB_ERR_CORRUPT;
-	TDB_LOG((tdb, TDB_DEBUG_FATAL,"remove_from_freelist: not on list at off=%d\n", off));
-	return -1;
-}
-#endif
-
-
-/* update a record tailer (must hold allocation lock) */
-static int update_tailer(struct tdb_context *tdb, tdb_off_t offset,
-			 const struct tdb_record *rec)
-{
-	tdb_off_t totalsize;
-
-	/* Offset of tailer from record header */
-	totalsize = sizeof(*rec) + rec->rec_len;
-	return tdb_ofs_write(tdb, offset + totalsize - sizeof(tdb_off_t),
-			 &totalsize);
-}
-
-/* Add an element into the freelist. Merge adjacent records if
-   necessary. */
-int tdb_free(struct tdb_context *tdb, tdb_off_t offset, struct tdb_record *rec)
-{
-	/* Allocation and tailer lock */
-	if (tdb_lock(tdb, -1, F_WRLCK) != 0)
-		return -1;
-
-	/* set an initial tailer, so if we fail we don't leave a bogus record */
-	if (update_tailer(tdb, offset, rec) != 0) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_free: update_tailer failed!\n"));
-		goto fail;
-	}
-
-#if USE_RIGHT_MERGES
-	/* Look right first (I'm an Australian, dammit) */
-	if (offset + sizeof(*rec) + rec->rec_len + sizeof(*rec) <= tdb->map_size) {
-		tdb_off_t right = offset + sizeof(*rec) + rec->rec_len;
-		struct tdb_record r;
-
-		if (tdb->methods->tdb_read(tdb, right, &r, sizeof(r), DOCONV()) == -1) {
-			TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_free: right read failed at %u\n", right));
-			goto left;
-		}
-
-		/* If it's free, expand to include it. */
-		if (r.magic == TDB_FREE_MAGIC) {
-			if (remove_from_freelist(tdb, right, r.next) == -1) {
-				TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_free: right free failed at %u\n", right));
-				goto left;
-			}
-			rec->rec_len += sizeof(r) + r.rec_len;
-			if (update_tailer(tdb, offset, rec) == -1) {
-				TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_free: update_tailer failed at %u\n", offset));
-				goto fail;
-			}
-		}
-	}
-left:
-#endif
-
-	/* Look left */
-	if (offset - sizeof(tdb_off_t) > TDB_DATA_START(tdb->header.hash_size)) {
-		tdb_off_t left = offset - sizeof(tdb_off_t);
-		struct tdb_record l;
-		tdb_off_t leftsize;
-
-		/* Read in tailer and jump back to header */
-		if (tdb_ofs_read(tdb, left, &leftsize) == -1) {
-			TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_free: left offset read failed at %u\n", left));
-			goto update;
-		}
-
-		/* it could be uninitialised data */
-		if (leftsize == 0 || leftsize == TDB_PAD_U32) {
-			goto update;
-		}
-
-		left = offset - leftsize;
-
-		if (leftsize > offset ||
-		    left < TDB_DATA_START(tdb->header.hash_size)) {
-			goto update;
-		}
-
-		/* Now read in the left record */
-		if (tdb->methods->tdb_read(tdb, left, &l, sizeof(l), DOCONV()) == -1) {
-			TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_free: left read failed at %u (%u)\n", left, leftsize));
-			goto update;
-		}
-
-		/* If it's free, expand to include it. */
-		if (l.magic == TDB_FREE_MAGIC) {
-			/* we now merge the new record into the left record, rather than the other 
-			   way around. This makes the operation O(1) instead of O(n). This change
-			   prevents traverse from being O(n^2) after a lot of deletes */
-			l.rec_len += sizeof(*rec) + rec->rec_len;
-			if (tdb_rec_write(tdb, left, &l) == -1) {
-				TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_free: update_left failed at %u\n", left));
-				goto fail;
-			}
-			if (update_tailer(tdb, left, &l) == -1) {
-				TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_free: update_tailer failed at %u\n", offset));
-				goto fail;
-			}
-			tdb_unlock(tdb, -1, F_WRLCK);
-			return 0;
-		}
-	}
-
-update:
-
-	/* Now, prepend to free list */
-	rec->magic = TDB_FREE_MAGIC;
-
-	if (tdb_ofs_read(tdb, FREELIST_TOP, &rec->next) == -1 ||
-	    tdb_rec_write(tdb, offset, rec) == -1 ||
-	    tdb_ofs_write(tdb, FREELIST_TOP, &offset) == -1) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_free record write failed at offset=%d\n", offset));
-		goto fail;
-	}
-
-	/* And we're done. */
-	tdb_unlock(tdb, -1, F_WRLCK);
-	return 0;
-
- fail:
-	tdb_unlock(tdb, -1, F_WRLCK);
-	return -1;
-}
-
-
-
-/* 
-   the core of tdb_allocate - called when we have decided which
-   free list entry to use
-
-   Note that we try to allocate by grabbing data from the end of an existing record,
-   not the beginning. This is so the left merge in a free is more likely to be
-   able to free up the record without fragmentation
- */
-static tdb_off_t tdb_allocate_ofs(struct tdb_context *tdb, 
-				  tdb_len_t length, tdb_off_t rec_ptr,
-				  struct tdb_record *rec, tdb_off_t last_ptr)
-{
-#define MIN_REC_SIZE (sizeof(struct tdb_record) + sizeof(tdb_off_t) + 8)
-
-	if (rec->rec_len < length + MIN_REC_SIZE) {
-		/* we have to grab the whole record */
-
-		/* unlink it from the previous record */
-		if (tdb_ofs_write(tdb, last_ptr, &rec->next) == -1) {
-			return 0;
-		}
-
-		/* mark it not free */
-		rec->magic = TDB_MAGIC;
-		if (tdb_rec_write(tdb, rec_ptr, rec) == -1) {
-			return 0;
-		}
-		return rec_ptr;
-	}
-
-	/* we're going to just shorten the existing record */
-	rec->rec_len -= (length + sizeof(*rec));
-	if (tdb_rec_write(tdb, rec_ptr, rec) == -1) {
-		return 0;
-	}
-	if (update_tailer(tdb, rec_ptr, rec) == -1) {
-		return 0;
-	}
-
-	/* and setup the new record */
-	rec_ptr += sizeof(*rec) + rec->rec_len;	
-
-	memset(rec, '\0', sizeof(*rec));
-	rec->rec_len = length;
-	rec->magic = TDB_MAGIC;
-
-	if (tdb_rec_write(tdb, rec_ptr, rec) == -1) {
-		return 0;
-	}
-
-	if (update_tailer(tdb, rec_ptr, rec) == -1) {
-		return 0;
-	}
-
-	return rec_ptr;
-}
-
-/* allocate some space from the free list. The offset returned points
-   to a unconnected tdb_record within the database with room for at
-   least length bytes of total data
-
-   0 is returned if the space could not be allocated
- */
-tdb_off_t tdb_allocate(struct tdb_context *tdb, tdb_len_t length, struct tdb_record *rec)
-{
-	tdb_off_t rec_ptr, last_ptr, newrec_ptr;
-	struct {
-		tdb_off_t rec_ptr, last_ptr;
-		tdb_len_t rec_len;
-	} bestfit;
-	float multiplier = 1.0;
-
-	if (tdb_lock(tdb, -1, F_WRLCK) == -1)
-		return 0;
-
-	/* over-allocate to reduce fragmentation */
-	length *= 1.25;
-
-	/* Extra bytes required for tailer */
-	length += sizeof(tdb_off_t);
-	length = TDB_ALIGN(length, TDB_ALIGNMENT);
-
- again:
-	last_ptr = FREELIST_TOP;
-
-	/* read in the freelist top */
-	if (tdb_ofs_read(tdb, FREELIST_TOP, &rec_ptr) == -1)
-		goto fail;
-
-	bestfit.rec_ptr = 0;
-	bestfit.last_ptr = 0;
-	bestfit.rec_len = 0;
-
-	/* 
-	   this is a best fit allocation strategy. Originally we used
-	   a first fit strategy, but it suffered from massive fragmentation
-	   issues when faced with a slowly increasing record size.
-	 */
-	while (rec_ptr) {
-		if (tdb_rec_free_read(tdb, rec_ptr, rec) == -1) {
-			goto fail;
-		}
-
-		if (rec->rec_len >= length) {
-			if (bestfit.rec_ptr == 0 ||
-			    rec->rec_len < bestfit.rec_len) {
-				bestfit.rec_len = rec->rec_len;
-				bestfit.rec_ptr = rec_ptr;
-				bestfit.last_ptr = last_ptr;
-			}
-		}
-
-		/* move to the next record */
-		last_ptr = rec_ptr;
-		rec_ptr = rec->next;
-
-		/* if we've found a record that is big enough, then
-		   stop searching if its also not too big. The
-		   definition of 'too big' changes as we scan
-		   through */
-		if (bestfit.rec_len > 0 &&
-		    bestfit.rec_len < length * multiplier) {
-			break;
-		}
-
-		/* this multiplier means we only extremely rarely
-		   search more than 50 or so records. At 50 records we
-		   accept records up to 11 times larger than what we
-		   want */
-		multiplier *= 1.05;
-	}
-
-	if (bestfit.rec_ptr != 0) {
-		if (tdb_rec_free_read(tdb, bestfit.rec_ptr, rec) == -1) {
-			goto fail;
-		}
-
-		newrec_ptr = tdb_allocate_ofs(tdb, length, bestfit.rec_ptr, 
-					      rec, bestfit.last_ptr);
-		tdb_unlock(tdb, -1, F_WRLCK);
-		return newrec_ptr;
-	}
-
-	/* we didn't find enough space. See if we can expand the
-	   database and if we can then try again */
-	if (tdb_expand(tdb, length + sizeof(*rec)) == 0)
-		goto again;
- fail:
-	tdb_unlock(tdb, -1, F_WRLCK);
-	return 0;
-}
-
-
-
-/* 
-   return the size of the freelist - used to decide if we should repack 
-*/
-_PUBLIC_ int tdb_freelist_size(struct tdb_context *tdb)
-{
-	tdb_off_t ptr;
-	int count=0;
-
-	if (tdb_lock(tdb, -1, F_RDLCK) == -1) {
-		return -1;
-	}
-
-	ptr = FREELIST_TOP;
-	while (tdb_ofs_read(tdb, ptr, &ptr) == 0 && ptr != 0) {
-		count++;
-	}
-
-	tdb_unlock(tdb, -1, F_RDLCK);
-	return count;
-}
diff --git a/lib/tdb/common/freelistcheck.c b/lib/tdb/common/freelistcheck.c
deleted file mode 100644
index ab6e78f..0000000
--- a/lib/tdb/common/freelistcheck.c
+++ /dev/null
@@ -1,109 +0,0 @@
-/*
-   Unix SMB/CIFS implementation.
-
-   trivial database library
-
-   Copyright (C) Jeremy Allison                    2006
-
-     ** NOTE! The following LGPL license applies to the tdb
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-
-#include "tdb_private.h"
-
-/* Check the freelist is good and contains no loops.
-   Very memory intensive - only do this as a consistency
-   checker. Heh heh - uses an in memory tdb as the storage
-   for the "seen" record list. For some reason this strikes
-   me as extremely clever as I don't have to write another tree
-   data structure implementation :-).
- */
-
-static int seen_insert(struct tdb_context *mem_tdb, tdb_off_t rec_ptr)
-{
-	TDB_DATA key, data;
-
-	memset(&data, '\0', sizeof(data));
-	key.dptr = (unsigned char *)&rec_ptr;
-	key.dsize = sizeof(rec_ptr);
-	return tdb_store(mem_tdb, key, data, TDB_INSERT);
-}
-
-_PUBLIC_ int tdb_validate_freelist(struct tdb_context *tdb, int *pnum_entries)
-{
-	struct tdb_context *mem_tdb = NULL;
-	struct tdb_record rec;
-	tdb_off_t rec_ptr, last_ptr;
-	int ret = -1;
-
-	*pnum_entries = 0;
-
-	mem_tdb = tdb_open("flval", tdb->header.hash_size,
-				TDB_INTERNAL, O_RDWR, 0600);
-	if (!mem_tdb) {
-		return -1;
-	}
-
-	if (tdb_lock(tdb, -1, F_WRLCK) == -1) {
-		tdb_close(mem_tdb);
-		return 0;
-	}
-
-	last_ptr = FREELIST_TOP;
-
-	/* Store the FREELIST_TOP record. */
-	if (seen_insert(mem_tdb, last_ptr) == -1) {
-		tdb->ecode = TDB_ERR_CORRUPT;
-		ret = -1;
-		goto fail;
-	}
-
-	/* read in the freelist top */
-	if (tdb_ofs_read(tdb, FREELIST_TOP, &rec_ptr) == -1) {
-		goto fail;
-	}
-
-	while (rec_ptr) {
-
-		/* If we can't store this record (we've seen it
-		   before) then the free list has a loop and must
-		   be corrupt. */
-
-		if (seen_insert(mem_tdb, rec_ptr)) {
-			tdb->ecode = TDB_ERR_CORRUPT;
-			ret = -1;
-			goto fail;
-		}
-
-		if (tdb_rec_free_read(tdb, rec_ptr, &rec) == -1) {
-			goto fail;
-		}
-
-		/* move to the next record */
-		last_ptr = rec_ptr;
-		rec_ptr = rec.next;
-		*pnum_entries += 1;
-	}
-
-	ret = 0;
-
-  fail:
-
-	tdb_close(mem_tdb);
-	tdb_unlock(tdb, -1, F_WRLCK);
-	return ret;
-}
diff --git a/lib/tdb/common/hash.c b/lib/tdb/common/hash.c
deleted file mode 100644
index 1eed722..0000000
--- a/lib/tdb/common/hash.c
+++ /dev/null
@@ -1,345 +0,0 @@
- /*
-   Unix SMB/CIFS implementation.
-
-   trivial database library
-
-   Copyright (C) Rusty Russell		   2010
-
-     ** NOTE! The following LGPL license applies to the tdb
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-#include "tdb_private.h"
-
-/* This is based on the hash algorithm from gdbm */
-unsigned int tdb_old_hash(TDB_DATA *key)
-{
-	uint32_t value;	/* Used to compute the hash value.  */
-	uint32_t   i;	/* Used to cycle through random values. */
-
-	/* Set the initial value from the key size. */
-	for (value = 0x238F13AF * key->dsize, i=0; i < key->dsize; i++)
-		value = (value + (key->dptr[i] << (i*5 % 24)));
-
-	return (1103515243 * value + 12345);
-}
-
-#ifndef WORDS_BIGENDIAN
-# define HASH_LITTLE_ENDIAN 1
-# define HASH_BIG_ENDIAN 0
-#else
-# define HASH_LITTLE_ENDIAN 0
-# define HASH_BIG_ENDIAN 1
-#endif
-
-/*
--------------------------------------------------------------------------------
-lookup3.c, by Bob Jenkins, May 2006, Public Domain.
-
-These are functions for producing 32-bit hashes for hash table lookup.
-hash_word(), hashlittle(), hashlittle2(), hashbig(), mix(), and final()
-are externally useful functions.  Routines to test the hash are included
-if SELF_TEST is defined.  You can use this free for any purpose.  It's in
-the public domain.  It has no warranty.
-
-You probably want to use hashlittle().  hashlittle() and hashbig()
-hash byte arrays.  hashlittle() is is faster than hashbig() on
-little-endian machines.  Intel and AMD are little-endian machines.
-On second thought, you probably want hashlittle2(), which is identical to
-hashlittle() except it returns two 32-bit hashes for the price of one.
-You could implement hashbig2() if you wanted but I haven't bothered here.
-
-If you want to find a hash of, say, exactly 7 integers, do
-  a = i1;  b = i2;  c = i3;
-  mix(a,b,c);
-  a += i4; b += i5; c += i6;
-  mix(a,b,c);
-  a += i7;
-  final(a,b,c);
-then use c as the hash value.  If you have a variable length array of
-4-byte integers to hash, use hash_word().  If you have a byte array (like
-a character string), use hashlittle().  If you have several byte arrays, or
-a mix of things, see the comments above hashlittle().
-
-Why is this so big?  I read 12 bytes at a time into 3 4-byte integers,
-then mix those integers.  This is fast (you can do a lot more thorough
-mixing with 12*3 instructions on 3 integers than you can with 3 instructions
-on 1 byte), but shoehorning those bytes into integers efficiently is messy.
-*/
-
-#define hashsize(n) ((uint32_t)1<<(n))
-#define hashmask(n) (hashsize(n)-1)
-#define rot(x,k) (((x)<<(k)) | ((x)>>(32-(k))))
-
-/*
--------------------------------------------------------------------------------
-mix -- mix 3 32-bit values reversibly.
-
-This is reversible, so any information in (a,b,c) before mix() is
-still in (a,b,c) after mix().
-
-If four pairs of (a,b,c) inputs are run through mix(), or through
-mix() in reverse, there are at least 32 bits of the output that
-are sometimes the same for one pair and different for another pair.
-This was tested for:
-* pairs that differed by one bit, by two bits, in any combination
-  of top bits of (a,b,c), or in any combination of bottom bits of
-  (a,b,c).
-* "differ" is defined as +, -, ^, or ~^.  For + and -, I transformed
-  the output delta to a Gray code (a^(a>>1)) so a string of 1's (as
-  is commonly produced by subtraction) look like a single 1-bit
-  difference.
-* the base values were pseudorandom, all zero but one bit set, or
-  all zero plus a counter that starts at zero.
-
-Some k values for my "a-=c; a^=rot(c,k); c+=b;" arrangement that
-satisfy this are
-    4  6  8 16 19  4
-    9 15  3 18 27 15
-   14  9  3  7 17  3
-Well, "9 15 3 18 27 15" didn't quite get 32 bits diffing
-for "differ" defined as + with a one-bit base and a two-bit delta.  I
-used http://burtleburtle.net/bob/hash/avalanche.html to choose
-the operations, constants, and arrangements of the variables.
-
-This does not achieve avalanche.  There are input bits of (a,b,c)
-that fail to affect some output bits of (a,b,c), especially of a.  The
-most thoroughly mixed value is c, but it doesn't really even achieve
-avalanche in c.
-
-This allows some parallelism.  Read-after-writes are good at doubling
-the number of bits affected, so the goal of mixing pulls in the opposite
-direction as the goal of parallelism.  I did what I could.  Rotates
-seem to cost as much as shifts on every machine I could lay my hands
-on, and rotates are much kinder to the top and bottom bits, so I used
-rotates.
--------------------------------------------------------------------------------
-*/
-#define mix(a,b,c) \
-{ \
-  a -= c;  a ^= rot(c, 4);  c += b; \
-  b -= a;  b ^= rot(a, 6);  a += c; \
-  c -= b;  c ^= rot(b, 8);  b += a; \
-  a -= c;  a ^= rot(c,16);  c += b; \
-  b -= a;  b ^= rot(a,19);  a += c; \
-  c -= b;  c ^= rot(b, 4);  b += a; \
-}
-
-/*
--------------------------------------------------------------------------------
-final -- final mixing of 3 32-bit values (a,b,c) into c
-
-Pairs of (a,b,c) values differing in only a few bits will usually
-produce values of c that look totally different.  This was tested for
-* pairs that differed by one bit, by two bits, in any combination
-  of top bits of (a,b,c), or in any combination of bottom bits of
-  (a,b,c).
-* "differ" is defined as +, -, ^, or ~^.  For + and -, I transformed
-  the output delta to a Gray code (a^(a>>1)) so a string of 1's (as
-  is commonly produced by subtraction) look like a single 1-bit
-  difference.
-* the base values were pseudorandom, all zero but one bit set, or
-  all zero plus a counter that starts at zero.
-
-These constants passed:
- 14 11 25 16 4 14 24
- 12 14 25 16 4 14 24
-and these came close:
-  4  8 15 26 3 22 24
- 10  8 15 26 3 22 24
- 11  8 15 26 3 22 24
--------------------------------------------------------------------------------
-*/
-#define final(a,b,c) \
-{ \
-  c ^= b; c -= rot(b,14); \
-  a ^= c; a -= rot(c,11); \
-  b ^= a; b -= rot(a,25); \
-  c ^= b; c -= rot(b,16); \
-  a ^= c; a -= rot(c,4);  \
-  b ^= a; b -= rot(a,14); \
-  c ^= b; c -= rot(b,24); \
-}
-
-
-/*
--------------------------------------------------------------------------------
-hashlittle() -- hash a variable-length key into a 32-bit value
-  k       : the key (the unaligned variable-length array of bytes)
-  length  : the length of the key, counting by bytes
-  val2    : IN: can be any 4-byte value OUT: second 32 bit hash.
-Returns a 32-bit value.  Every bit of the key affects every bit of
-the return value.  Two keys differing by one or two bits will have
-totally different hash values.  Note that the return value is better
-mixed than val2, so use that first.
-
-The best hash table sizes are powers of 2.  There is no need to do
-mod a prime (mod is sooo slow!).  If you need less than 32 bits,
-use a bitmask.  For example, if you need only 10 bits, do
-  h = (h & hashmask(10));
-In which case, the hash table should have hashsize(10) elements.
-
-If you are hashing n strings (uint8_t **)k, do it like this:
-  for (i=0, h=0; i<n; ++i) h = hashlittle( k[i], len[i], h);
-
-By Bob Jenkins, 2006.  bob_jenkins at burtleburtle.net.  You may use this
-code any way you wish, private, educational, or commercial.  It's free.
-
-Use for hash table lookup, or anything where one collision in 2^^32 is
-acceptable.  Do NOT use for cryptographic purposes.
--------------------------------------------------------------------------------
-*/
-
-static uint32_t hashlittle( const void *key, size_t length )
-{
-  uint32_t a,b,c;                                          /* internal state */
-  union { const void *ptr; size_t i; } u;     /* needed for Mac Powerbook G4 */
-
-  /* Set up the internal state */
-  a = b = c = 0xdeadbeef + ((uint32_t)length);
-
-  u.ptr = key;
-  if (HASH_LITTLE_ENDIAN && ((u.i & 0x3) == 0)) {
-    const uint32_t *k = (const uint32_t *)key;         /* read 32-bit chunks */
-    const uint8_t  *k8;
-
-    /*------ all but last block: aligned reads and affect 32 bits of (a,b,c) */
-    while (length > 12)
-    {
-      a += k[0];
-      b += k[1];
-      c += k[2];
-      mix(a,b,c);
-      length -= 12;
-      k += 3;
-    }
-
-    /*----------------------------- handle the last (probably partial) block */
-    k8 = (const uint8_t *)k;
-    switch(length)
-    {
-    case 12: c+=k[2]; b+=k[1]; a+=k[0]; break;
-    case 11: c+=((uint32_t)k8[10])<<16;  /* fall through */
-    case 10: c+=((uint32_t)k8[9])<<8;    /* fall through */
-    case 9 : c+=k8[8];                   /* fall through */
-    case 8 : b+=k[1]; a+=k[0]; break;
-    case 7 : b+=((uint32_t)k8[6])<<16;   /* fall through */
-    case 6 : b+=((uint32_t)k8[5])<<8;    /* fall through */
-    case 5 : b+=k8[4];                   /* fall through */
-    case 4 : a+=k[0]; break;
-    case 3 : a+=((uint32_t)k8[2])<<16;   /* fall through */
-    case 2 : a+=((uint32_t)k8[1])<<8;    /* fall through */
-    case 1 : a+=k8[0]; break;
-    case 0 : return c;
-    }
-  } else if (HASH_LITTLE_ENDIAN && ((u.i & 0x1) == 0)) {
-    const uint16_t *k = (const uint16_t *)key;         /* read 16-bit chunks */
-    const uint8_t  *k8;
-
-    /*--------------- all but last block: aligned reads and different mixing */
-    while (length > 12)
-    {
-      a += k[0] + (((uint32_t)k[1])<<16);
-      b += k[2] + (((uint32_t)k[3])<<16);
-      c += k[4] + (((uint32_t)k[5])<<16);
-      mix(a,b,c);
-      length -= 12;
-      k += 6;
-    }
-
-    /*----------------------------- handle the last (probably partial) block */
-    k8 = (const uint8_t *)k;
-    switch(length)
-    {
-    case 12: c+=k[4]+(((uint32_t)k[5])<<16);
-             b+=k[2]+(((uint32_t)k[3])<<16);
-             a+=k[0]+(((uint32_t)k[1])<<16);
-             break;
-    case 11: c+=((uint32_t)k8[10])<<16;     /* fall through */
-    case 10: c+=k[4];
-             b+=k[2]+(((uint32_t)k[3])<<16);
-             a+=k[0]+(((uint32_t)k[1])<<16);
-             break;
-    case 9 : c+=k8[8];                      /* fall through */
-    case 8 : b+=k[2]+(((uint32_t)k[3])<<16);
-             a+=k[0]+(((uint32_t)k[1])<<16);
-             break;
-    case 7 : b+=((uint32_t)k8[6])<<16;      /* fall through */
-    case 6 : b+=k[2];
-             a+=k[0]+(((uint32_t)k[1])<<16);
-             break;
-    case 5 : b+=k8[4];                      /* fall through */
-    case 4 : a+=k[0]+(((uint32_t)k[1])<<16);
-             break;
-    case 3 : a+=((uint32_t)k8[2])<<16;      /* fall through */
-    case 2 : a+=k[0];
-             break;
-    case 1 : a+=k8[0];
-             break;
-    case 0 : return c;                     /* zero length requires no mixing */
-    }
-
-  } else {                        /* need to read the key one byte at a time */
-    const uint8_t *k = (const uint8_t *)key;
-
-    /*--------------- all but the last block: affect some 32 bits of (a,b,c) */
-    while (length > 12)
-    {
-      a += k[0];
-      a += ((uint32_t)k[1])<<8;
-      a += ((uint32_t)k[2])<<16;
-      a += ((uint32_t)k[3])<<24;
-      b += k[4];
-      b += ((uint32_t)k[5])<<8;
-      b += ((uint32_t)k[6])<<16;
-      b += ((uint32_t)k[7])<<24;
-      c += k[8];
-      c += ((uint32_t)k[9])<<8;
-      c += ((uint32_t)k[10])<<16;
-      c += ((uint32_t)k[11])<<24;
-      mix(a,b,c);
-      length -= 12;
-      k += 12;
-    }
-
-    /*-------------------------------- last block: affect all 32 bits of (c) */
-    switch(length)                   /* all the case statements fall through */
-    {
-    case 12: c+=((uint32_t)k[11])<<24;
-    case 11: c+=((uint32_t)k[10])<<16;
-    case 10: c+=((uint32_t)k[9])<<8;
-    case 9 : c+=k[8];
-    case 8 : b+=((uint32_t)k[7])<<24;
-    case 7 : b+=((uint32_t)k[6])<<16;
-    case 6 : b+=((uint32_t)k[5])<<8;
-    case 5 : b+=k[4];
-    case 4 : a+=((uint32_t)k[3])<<24;
-    case 3 : a+=((uint32_t)k[2])<<16;
-    case 2 : a+=((uint32_t)k[1])<<8;
-    case 1 : a+=k[0];
-             break;
-    case 0 : return c;
-    }
-  }
-
-  final(a,b,c);
-  return c;
-}
-
-_PUBLIC_ unsigned int tdb_jenkins_hash(TDB_DATA *key)
-{
-	return hashlittle(key->dptr, key->dsize);
-}
diff --git a/lib/tdb/common/io.c b/lib/tdb/common/io.c
deleted file mode 100644
index 3131f4f..0000000
--- a/lib/tdb/common/io.c
+++ /dev/null
@@ -1,526 +0,0 @@
- /* 
-   Unix SMB/CIFS implementation.
-
-   trivial database library
-
-   Copyright (C) Andrew Tridgell              1999-2005
-   Copyright (C) Paul `Rusty' Russell		   2000
-   Copyright (C) Jeremy Allison			   2000-2003
-
-     ** NOTE! The following LGPL license applies to the tdb
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-
-
-#include "tdb_private.h"
-
-/* check for an out of bounds access - if it is out of bounds then
-   see if the database has been expanded by someone else and expand
-   if necessary 
-*/
-static int tdb_oob(struct tdb_context *tdb, tdb_off_t off, tdb_len_t len,
-		   int probe)
-{
-	struct stat st;
-	if (len + off < len) {
-		if (!probe) {
-			/* Ensure ecode is set for log fn. */
-			tdb->ecode = TDB_ERR_IO;
-			TDB_LOG((tdb, TDB_DEBUG_FATAL,"tdb_oob off %d len %d wrap\n",
-				 (int)off, (int)len));
-		}
-		return -1;
-	}
-
-	if (off + len <= tdb->map_size)
-		return 0;
-	if (tdb->flags & TDB_INTERNAL) {
-		if (!probe) {
-			/* Ensure ecode is set for log fn. */
-			tdb->ecode = TDB_ERR_IO;
-			TDB_LOG((tdb, TDB_DEBUG_FATAL,"tdb_oob len %u beyond internal malloc size %u\n",
-				 (int)(off + len), (int)tdb->map_size));
-		}
-		return -1;
-	}
-
-	if (fstat(tdb->fd, &st) == -1) {
-		tdb->ecode = TDB_ERR_IO;
-		return -1;
-	}
-
-	if (st.st_size < (size_t)off + len) {
-		if (!probe) {
-			/* Ensure ecode is set for log fn. */
-			tdb->ecode = TDB_ERR_IO;
-			TDB_LOG((tdb, TDB_DEBUG_FATAL,"tdb_oob len %u beyond eof at %u\n",
-				 (int)(off + len), (int)st.st_size));
-		}
-		return -1;
-	}
-
-	/* Beware >4G files! */
-	if ((tdb_off_t)st.st_size != st.st_size) {
-		/* Ensure ecode is set for log fn. */
-		tdb->ecode = TDB_ERR_IO;
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_oob len %llu too large!\n",
-			 (long long)st.st_size));
-		return -1;
-	}
-
-	/* Unmap, update size, remap */
-	if (tdb_munmap(tdb) == -1) {
-		tdb->ecode = TDB_ERR_IO;
-		return -1;
-	}
-	tdb->map_size = st.st_size;
-	return tdb_mmap(tdb);
-}
-
-/* write a lump of data at a specified offset */
-static int tdb_write(struct tdb_context *tdb, tdb_off_t off, 
-		     const void *buf, tdb_len_t len)
-{
-	if (len == 0) {
-		return 0;
-	}
-
-	if (tdb->read_only || tdb->traverse_read) {
-		tdb->ecode = TDB_ERR_RDONLY;
-		return -1;
-	}
-
-	if (tdb->methods->tdb_oob(tdb, off, len, 0) != 0)
-		return -1;
-
-	if (tdb->map_ptr) {
-		memcpy(off + (char *)tdb->map_ptr, buf, len);
-	} else {
-#ifdef HAVE_INCOHERENT_MMAP
-		tdb->ecode = TDB_ERR_IO;
-		return -1;
-#else
-		ssize_t written = pwrite(tdb->fd, buf, len, off);
-		if ((written != (ssize_t)len) && (written != -1)) {
-			/* try once more */
-			tdb->ecode = TDB_ERR_IO;
-			TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_write: wrote only "
-				 "%d of %d bytes at %d, trying once more\n",
-				 (int)written, len, off));
-			written = pwrite(tdb->fd, (const char *)buf+written,
-					 len-written,
-					 off+written);
-		}
-		if (written == -1) {
-			/* Ensure ecode is set for log fn. */
-			tdb->ecode = TDB_ERR_IO;
-			TDB_LOG((tdb, TDB_DEBUG_FATAL,"tdb_write failed at %d "
-				 "len=%d (%s)\n", off, len, strerror(errno)));
-			return -1;
-		} else if (written != (ssize_t)len) {
-			tdb->ecode = TDB_ERR_IO;
-			TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_write: failed to "
-				 "write %d bytes at %d in two attempts\n",
-				 len, off));
-			return -1;
-		}
-#endif
-	}
-	return 0;
-}
-
-/* Endian conversion: we only ever deal with 4 byte quantities */
-void *tdb_convert(void *buf, uint32_t size)
-{
-	uint32_t i, *p = (uint32_t *)buf;
-	for (i = 0; i < size / 4; i++)
-		p[i] = TDB_BYTEREV(p[i]);
-	return buf;
-}
-
-
-/* read a lump of data at a specified offset, maybe convert */
-static int tdb_read(struct tdb_context *tdb, tdb_off_t off, void *buf, 
-		    tdb_len_t len, int cv)
-{
-	if (tdb->methods->tdb_oob(tdb, off, len, 0) != 0) {
-		return -1;
-	}
-
-	if (tdb->map_ptr) {
-		memcpy(buf, off + (char *)tdb->map_ptr, len);
-	} else {
-#ifdef HAVE_INCOHERENT_MMAP
-		tdb->ecode = TDB_ERR_IO;
-		return -1;
-#else
-		ssize_t ret = pread(tdb->fd, buf, len, off);
-		if (ret != (ssize_t)len) {
-			/* Ensure ecode is set for log fn. */
-			tdb->ecode = TDB_ERR_IO;
-			TDB_LOG((tdb, TDB_DEBUG_FATAL,"tdb_read failed at %d "
-				 "len=%d ret=%d (%s) map_size=%d\n",
-				 (int)off, (int)len, (int)ret, strerror(errno),
-				 (int)tdb->map_size));
-			return -1;
-		}
-#endif
-	}
-	if (cv) {
-		tdb_convert(buf, len);
-	}
-	return 0;
-}
-
-
-
-/*
-  do an unlocked scan of the hash table heads to find the next non-zero head. The value
-  will then be confirmed with the lock held
-*/		
-static void tdb_next_hash_chain(struct tdb_context *tdb, uint32_t *chain)
-{
-	uint32_t h = *chain;
-	if (tdb->map_ptr) {
-		for (;h < tdb->header.hash_size;h++) {
-			if (0 != *(uint32_t *)(TDB_HASH_TOP(h) + (unsigned char *)tdb->map_ptr)) {
-				break;
-			}
-		}
-	} else {
-		uint32_t off=0;
-		for (;h < tdb->header.hash_size;h++) {
-			if (tdb_ofs_read(tdb, TDB_HASH_TOP(h), &off) != 0 || off != 0) {
-				break;
-			}
-		}
-	}
-	(*chain) = h;
-}
-
-
-int tdb_munmap(struct tdb_context *tdb)
-{
-	if (tdb->flags & TDB_INTERNAL)
-		return 0;
-
-#ifdef HAVE_MMAP
-	if (tdb->map_ptr) {
-		int ret;
-
-		ret = munmap(tdb->map_ptr, tdb->map_size);
-		if (ret != 0)
-			return ret;
-	}
-#endif
-	tdb->map_ptr = NULL;
-	return 0;
-}
-
-/* If mmap isn't coherent, *everyone* must always mmap. */
-static bool should_mmap(const struct tdb_context *tdb)
-{
-#ifdef HAVE_INCOHERENT_MMAP
-	return true;
-#else
-	return !(tdb->flags & TDB_NOMMAP);
-#endif
-}
-
-int tdb_mmap(struct tdb_context *tdb)
-{
-	if (tdb->flags & TDB_INTERNAL)
-		return 0;
-
-#ifdef HAVE_MMAP
-	if (should_mmap(tdb)) {
-		tdb->map_ptr = mmap(NULL, tdb->map_size, 
-				    PROT_READ|(tdb->read_only? 0:PROT_WRITE), 
-				    MAP_SHARED|MAP_FILE, tdb->fd, 0);
-
-		/*
-		 * NB. When mmap fails it returns MAP_FAILED *NOT* NULL !!!!
-		 */
-
-		if (tdb->map_ptr == MAP_FAILED) {
-			tdb->map_ptr = NULL;
-			TDB_LOG((tdb, TDB_DEBUG_WARNING, "tdb_mmap failed for size %d (%s)\n", 
-				 tdb->map_size, strerror(errno)));
-#ifdef HAVE_INCOHERENT_MMAP
-			tdb->ecode = TDB_ERR_IO;
-			return -1;
-#endif
-		}
-	} else {
-		tdb->map_ptr = NULL;
-	}
-#else
-	tdb->map_ptr = NULL;
-#endif
-	return 0;
-}
-
-/* expand a file.  we prefer to use ftruncate, as that is what posix
-  says to use for mmap expansion */
-static int tdb_expand_file(struct tdb_context *tdb, tdb_off_t size, tdb_off_t addition)
-{
-	char buf[8192];
-
-	if (tdb->read_only || tdb->traverse_read) {
-		tdb->ecode = TDB_ERR_RDONLY;
-		return -1;
-	}
-
-	if (ftruncate(tdb->fd, size+addition) == -1) {
-		char b = 0;
-		ssize_t written = pwrite(tdb->fd,  &b, 1, (size+addition) - 1);
-		if (written == 0) {
-			/* try once more, potentially revealing errno */
-			written = pwrite(tdb->fd,  &b, 1, (size+addition) - 1);
-		}
-		if (written == 0) {
-			/* again - give up, guessing errno */
-			errno = ENOSPC;
-		}
-		if (written != 1) {
-			TDB_LOG((tdb, TDB_DEBUG_FATAL, "expand_file to %d failed (%s)\n", 
-				 size+addition, strerror(errno)));
-			return -1;
-		}
-	}
-
-	/* now fill the file with something. This ensures that the
-	   file isn't sparse, which would be very bad if we ran out of
-	   disk. This must be done with write, not via mmap */
-	memset(buf, TDB_PAD_BYTE, sizeof(buf));
-	while (addition) {
-		size_t n = addition>sizeof(buf)?sizeof(buf):addition;
-		ssize_t written = pwrite(tdb->fd, buf, n, size);
-		if (written == 0) {
-			/* prevent infinite loops: try _once_ more */
-			written = pwrite(tdb->fd, buf, n, size);
-		}
-		if (written == 0) {
-			/* give up, trying to provide a useful errno */
-			TDB_LOG((tdb, TDB_DEBUG_FATAL, "expand_file write "
-				"returned 0 twice: giving up!\n"));
-			errno = ENOSPC;
-			return -1;
-		} else if (written == -1) {
-			TDB_LOG((tdb, TDB_DEBUG_FATAL, "expand_file write of "
-				 "%d bytes failed (%s)\n", (int)n,
-				 strerror(errno)));
-			return -1;
-		} else if (written != n) {
-			TDB_LOG((tdb, TDB_DEBUG_WARNING, "expand_file: wrote "
-				 "only %d of %d bytes - retrying\n", (int)written,
-				 (int)n));
-		}
-		addition -= written;
-		size += written;
-	}
-	return 0;
-}
-
-
-/* You need 'size', this tells you how much you should expand by. */
-tdb_off_t tdb_expand_adjust(tdb_off_t map_size, tdb_off_t size, int page_size)
-{
-	tdb_off_t new_size, top_size;
-
-	/* limit size in order to avoid using up huge amounts of memory for
-	 * in memory tdbs if an oddball huge record creeps in */
-	if (size > 100 * 1024) {
-		top_size = map_size + size * 2;
-	} else {
-		top_size = map_size + size * 100;
-	}
-
-	/* always make room for at least top_size more records, and at
-	   least 25% more space. if the DB is smaller than 100MiB,
-	   otherwise grow it by 10% only. */
-	if (map_size > 100 * 1024 * 1024) {
-		new_size = map_size * 1.10;
-	} else {
-		new_size = map_size * 1.25;
-	}
-
-	/* Round the database up to a multiple of the page size */
-	new_size = MAX(top_size, new_size);
-	return TDB_ALIGN(new_size, page_size) - map_size;
-}
-
-/* expand the database at least size bytes by expanding the underlying
-   file and doing the mmap again if necessary */
-int tdb_expand(struct tdb_context *tdb, tdb_off_t size)
-{
-	struct tdb_record rec;
-	tdb_off_t offset;
-
-	if (tdb_lock(tdb, -1, F_WRLCK) == -1) {
-		TDB_LOG((tdb, TDB_DEBUG_ERROR, "lock failed in tdb_expand\n"));
-		return -1;
-	}
-
-	/* must know about any previous expansions by another process */
-	tdb->methods->tdb_oob(tdb, tdb->map_size, 1, 1);
-
-	size = tdb_expand_adjust(tdb->map_size, size, tdb->page_size);
-
-	/* expand the file itself */
-	if (!(tdb->flags & TDB_INTERNAL)) {
-		if (tdb->methods->tdb_expand_file(tdb, tdb->map_size, size) != 0)
-			goto fail;
-	}
-
-	/* form a new freelist record */
-	offset = tdb->map_size;
-	memset(&rec,'\0',sizeof(rec));
-	rec.rec_len = size - sizeof(rec);
-
-	if (tdb->flags & TDB_INTERNAL) {
-		char *new_map_ptr = (char *)realloc(tdb->map_ptr,
-						    tdb->map_size + size);
-		if (!new_map_ptr) {
-			goto fail;
-		}
-		tdb->map_ptr = new_map_ptr;
-		tdb->map_size += size;
-	} else {
-		/* Explicitly remap: if we're in a transaction, this won't
-		 * happen automatically! */
-		tdb_munmap(tdb);
-		tdb->map_size += size;
-		if (tdb_mmap(tdb) != 0) {
-			goto fail;
-		}
-	}
-
-	/* link it into the free list */
-	if (tdb_free(tdb, offset, &rec) == -1)
-		goto fail;
-
-	tdb_unlock(tdb, -1, F_WRLCK);
-	return 0;
- fail:
-	tdb_unlock(tdb, -1, F_WRLCK);
-	return -1;
-}
-
-/* read/write a tdb_off_t */
-int tdb_ofs_read(struct tdb_context *tdb, tdb_off_t offset, tdb_off_t *d)
-{
-	return tdb->methods->tdb_read(tdb, offset, (char*)d, sizeof(*d), DOCONV());
-}
-
-int tdb_ofs_write(struct tdb_context *tdb, tdb_off_t offset, tdb_off_t *d)
-{
-	tdb_off_t off = *d;
-	return tdb->methods->tdb_write(tdb, offset, CONVERT(off), sizeof(*d));
-}
-
-
-/* read a lump of data, allocating the space for it */
-unsigned char *tdb_alloc_read(struct tdb_context *tdb, tdb_off_t offset, tdb_len_t len)
-{
-	unsigned char *buf;
-
-	/* some systems don't like zero length malloc */
-
-	if (!(buf = (unsigned char *)malloc(len ? len : 1))) {
-		/* Ensure ecode is set for log fn. */
-		tdb->ecode = TDB_ERR_OOM;
-		TDB_LOG((tdb, TDB_DEBUG_ERROR,"tdb_alloc_read malloc failed len=%d (%s)\n",
-			   len, strerror(errno)));
-		return NULL;
-	}
-	if (tdb->methods->tdb_read(tdb, offset, buf, len, 0) == -1) {
-		SAFE_FREE(buf);
-		return NULL;
-	}
-	return buf;
-}
-
-/* Give a piece of tdb data to a parser */
-
-int tdb_parse_data(struct tdb_context *tdb, TDB_DATA key,
-		   tdb_off_t offset, tdb_len_t len,
-		   int (*parser)(TDB_DATA key, TDB_DATA data,
-				 void *private_data),
-		   void *private_data)
-{
-	TDB_DATA data;
-	int result;
-
-	data.dsize = len;
-
-	if ((tdb->transaction == NULL) && (tdb->map_ptr != NULL)) {
-		/*
-		 * Optimize by avoiding the malloc/memcpy/free, point the
-		 * parser directly at the mmap area.
-		 */
-		if (tdb->methods->tdb_oob(tdb, offset, len, 0) != 0) {
-			return -1;
-		}
-		data.dptr = offset + (unsigned char *)tdb->map_ptr;
-		return parser(key, data, private_data);
-	}
-
-	if (!(data.dptr = tdb_alloc_read(tdb, offset, len))) {
-		return -1;
-	}
-
-	result = parser(key, data, private_data);
-	free(data.dptr);
-	return result;
-}
-
-/* read/write a record */
-int tdb_rec_read(struct tdb_context *tdb, tdb_off_t offset, struct tdb_record *rec)
-{
-	if (tdb->methods->tdb_read(tdb, offset, rec, sizeof(*rec),DOCONV()) == -1)
-		return -1;
-	if (TDB_BAD_MAGIC(rec)) {
-		/* Ensure ecode is set for log fn. */
-		tdb->ecode = TDB_ERR_CORRUPT;
-		TDB_LOG((tdb, TDB_DEBUG_FATAL,"tdb_rec_read bad magic 0x%x at offset=%d\n", rec->magic, offset));
-		return -1;
-	}
-	return tdb->methods->tdb_oob(tdb, rec->next, sizeof(*rec), 0);
-}
-
-int tdb_rec_write(struct tdb_context *tdb, tdb_off_t offset, struct tdb_record *rec)
-{
-	struct tdb_record r = *rec;
-	return tdb->methods->tdb_write(tdb, offset, CONVERT(r), sizeof(r));
-}
-
-static const struct tdb_methods io_methods = {
-	tdb_read,
-	tdb_write,
-	tdb_next_hash_chain,
-	tdb_oob,
-	tdb_expand_file,
-};
-
-/*
-  initialise the default methods table
-*/
-void tdb_io_init(struct tdb_context *tdb)
-{
-	tdb->methods = &io_methods;
-}
diff --git a/lib/tdb/common/lock.c b/lib/tdb/common/lock.c
deleted file mode 100644
index 88a52e9..0000000
--- a/lib/tdb/common/lock.c
+++ /dev/null
@@ -1,875 +0,0 @@
- /* 
-   Unix SMB/CIFS implementation.
-
-   trivial database library
-
-   Copyright (C) Andrew Tridgell              1999-2005
-   Copyright (C) Paul `Rusty' Russell		   2000
-   Copyright (C) Jeremy Allison			   2000-2003
-
-     ** NOTE! The following LGPL license applies to the tdb
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-
-#include "tdb_private.h"
-
-_PUBLIC_ void tdb_setalarm_sigptr(struct tdb_context *tdb, volatile sig_atomic_t *ptr)
-{
-	tdb->interrupt_sig_ptr = ptr;
-}
-
-static int fcntl_lock(struct tdb_context *tdb,
-		      int rw, off_t off, off_t len, bool waitflag)
-{
-	struct flock fl;
-
-	fl.l_type = rw;
-	fl.l_whence = SEEK_SET;
-	fl.l_start = off;
-	fl.l_len = len;
-	fl.l_pid = 0;
-
-	if (waitflag)
-		return fcntl(tdb->fd, F_SETLKW, &fl);
-	else
-		return fcntl(tdb->fd, F_SETLK, &fl);
-}
-
-static int fcntl_unlock(struct tdb_context *tdb, int rw, off_t off, off_t len)
-{
-	struct flock fl;
-#if 0 /* Check they matched up locks and unlocks correctly. */
-	char line[80];
-	FILE *locks;
-	bool found = false;
-
-	locks = fopen("/proc/locks", "r");
-
-	while (fgets(line, 80, locks)) {
-		char *p;
-		int type, start, l;
-
-		/* eg. 1: FLOCK  ADVISORY  WRITE 2440 08:01:2180826 0 EOF */
-		p = strchr(line, ':') + 1;
-		if (strncmp(p, " POSIX  ADVISORY  ", strlen(" POSIX  ADVISORY  ")))
-			continue;
-		p += strlen(" FLOCK  ADVISORY  ");
-		if (strncmp(p, "READ  ", strlen("READ  ")) == 0)
-			type = F_RDLCK;
-		else if (strncmp(p, "WRITE ", strlen("WRITE ")) == 0)
-			type = F_WRLCK;
-		else
-			abort();
-		p += 6;
-		if (atoi(p) != getpid())
-			continue;
-		p = strchr(strchr(p, ' ') + 1, ' ') + 1;
-		start = atoi(p);
-		p = strchr(p, ' ') + 1;
-		if (strncmp(p, "EOF", 3) == 0)
-			l = 0;
-		else
-			l = atoi(p) - start + 1;
-
-		if (off == start) {
-			if (len != l) {
-				fprintf(stderr, "Len %u should be %u: %s",
-					(int)len, l, line);
-				abort();
-			}
-			if (type != rw) {
-				fprintf(stderr, "Type %s wrong: %s",
-					rw == F_RDLCK ? "READ" : "WRITE", line);
-				abort();
-			}
-			found = true;
-			break;
-		}
-	}
-
-	if (!found) {
-		fprintf(stderr, "Unlock on %u@%u not found!\n",
-			(int)off, (int)len);
-		abort();
-	}
-
-	fclose(locks);
-#endif
-
-	fl.l_type = F_UNLCK;
-	fl.l_whence = SEEK_SET;
-	fl.l_start = off;
-	fl.l_len = len;
-	fl.l_pid = 0;
-
-	return fcntl(tdb->fd, F_SETLKW, &fl);
-}
-
-/* list -1 is the alloc list, otherwise a hash chain. */
-static tdb_off_t lock_offset(int list)
-{
-	return FREELIST_TOP + 4*list;
-}
-
-/* a byte range locking function - return 0 on success
-   this functions locks/unlocks 1 byte at the specified offset.
-
-   On error, errno is also set so that errors are passed back properly
-   through tdb_open(). 
-
-   note that a len of zero means lock to end of file
-*/
-int tdb_brlock(struct tdb_context *tdb,
-	       int rw_type, tdb_off_t offset, size_t len,
-	       enum tdb_lock_flags flags)
-{
-	int ret;
-
-	if (tdb->flags & TDB_NOLOCK) {
-		return 0;
-	}
-
-	if (flags & TDB_LOCK_MARK_ONLY) {
-		return 0;
-	}
-
-	if ((rw_type == F_WRLCK) && (tdb->read_only || tdb->traverse_read)) {
-		tdb->ecode = TDB_ERR_RDONLY;
-		return -1;
-	}
-
-	do {
-		ret = fcntl_lock(tdb, rw_type, offset, len,
-				 flags & TDB_LOCK_WAIT);
-		/* Check for a sigalarm break. */
-		if (ret == -1 && errno == EINTR &&
-				tdb->interrupt_sig_ptr &&
-				*tdb->interrupt_sig_ptr) {
-			break;
-		}
-	} while (ret == -1 && errno == EINTR);
-
-	if (ret == -1) {
-		tdb->ecode = TDB_ERR_LOCK;
-		/* Generic lock error. errno set by fcntl.
-		 * EAGAIN is an expected return from non-blocking
-		 * locks. */
-		if (!(flags & TDB_LOCK_PROBE) && errno != EAGAIN) {
-			TDB_LOG((tdb, TDB_DEBUG_TRACE,"tdb_brlock failed (fd=%d) at offset %d rw_type=%d flags=%d len=%d\n",
-				 tdb->fd, offset, rw_type, flags, (int)len));
-		}
-		return -1;
-	}
-	return 0;
-}
-
-int tdb_brunlock(struct tdb_context *tdb,
-		 int rw_type, tdb_off_t offset, size_t len)
-{
-	int ret;
-
-	if (tdb->flags & TDB_NOLOCK) {
-		return 0;
-	}
-
-	do {
-		ret = fcntl_unlock(tdb, rw_type, offset, len);
-	} while (ret == -1 && errno == EINTR);
-
-	if (ret == -1) {
-		TDB_LOG((tdb, TDB_DEBUG_TRACE,"tdb_brunlock failed (fd=%d) at offset %d rw_type=%d len=%d\n",
-			 tdb->fd, offset, rw_type, (int)len));
-	}
-	return ret;
-}
-
-/*
-  upgrade a read lock to a write lock. This needs to be handled in a
-  special way as some OSes (such as solaris) have too conservative
-  deadlock detection and claim a deadlock when progress can be
-  made. For those OSes we may loop for a while.  
-*/
-int tdb_allrecord_upgrade(struct tdb_context *tdb)
-{
-	int count = 1000;
-
-	if (tdb->allrecord_lock.count != 1) {
-		TDB_LOG((tdb, TDB_DEBUG_ERROR,
-			 "tdb_allrecord_upgrade failed: count %u too high\n",
-			 tdb->allrecord_lock.count));
-		return -1;
-	}
-
-	if (tdb->allrecord_lock.off != 1) {
-		TDB_LOG((tdb, TDB_DEBUG_ERROR,
-			 "tdb_allrecord_upgrade failed: already upgraded?\n"));
-		return -1;
-	}
-
-	while (count--) {
-		struct timeval tv;
-		if (tdb_brlock(tdb, F_WRLCK, FREELIST_TOP, 0,
-			       TDB_LOCK_WAIT|TDB_LOCK_PROBE) == 0) {
-			tdb->allrecord_lock.ltype = F_WRLCK;
-			tdb->allrecord_lock.off = 0;
-			return 0;
-		}
-		if (errno != EDEADLK) {
-			break;
-		}
-		/* sleep for as short a time as we can - more portable than usleep() */
-		tv.tv_sec = 0;
-		tv.tv_usec = 1;
-		select(0, NULL, NULL, NULL, &tv);
-	}
-	TDB_LOG((tdb, TDB_DEBUG_TRACE,"tdb_allrecord_upgrade failed\n"));
-	return -1;
-}
-
-static struct tdb_lock_type *find_nestlock(struct tdb_context *tdb,
-					   tdb_off_t offset)
-{
-	unsigned int i;
-
-	for (i=0; i<tdb->num_lockrecs; i++) {
-		if (tdb->lockrecs[i].off == offset) {
-			return &tdb->lockrecs[i];
-		}
-	}
-	return NULL;
-}
-
-/* lock an offset in the database. */
-int tdb_nest_lock(struct tdb_context *tdb, uint32_t offset, int ltype,
-		  enum tdb_lock_flags flags)
-{
-	struct tdb_lock_type *new_lck;
-
-	if (offset >= lock_offset(tdb->header.hash_size)) {
-		tdb->ecode = TDB_ERR_LOCK;
-		TDB_LOG((tdb, TDB_DEBUG_ERROR,"tdb_lock: invalid offset %u for ltype=%d\n",
-			 offset, ltype));
-		return -1;
-	}
-	if (tdb->flags & TDB_NOLOCK)
-		return 0;
-
-	new_lck = find_nestlock(tdb, offset);
-	if (new_lck) {
-		/*
-		 * Just increment the in-memory struct, posix locks
-		 * don't stack.
-		 */
-		new_lck->count++;
-		return 0;
-	}
-
-	new_lck = (struct tdb_lock_type *)realloc(
-		tdb->lockrecs,
-		sizeof(*tdb->lockrecs) * (tdb->num_lockrecs+1));
-	if (new_lck == NULL) {
-		errno = ENOMEM;
-		return -1;
-	}
-	tdb->lockrecs = new_lck;
-
-	/* Since fcntl locks don't nest, we do a lock for the first one,
-	   and simply bump the count for future ones */
-	if (tdb_brlock(tdb, ltype, offset, 1, flags)) {
-		return -1;
-	}
-
-	tdb->lockrecs[tdb->num_lockrecs].off = offset;
-	tdb->lockrecs[tdb->num_lockrecs].count = 1;
-	tdb->lockrecs[tdb->num_lockrecs].ltype = ltype;
-	tdb->num_lockrecs++;
-
-	return 0;
-}
-
-static int tdb_lock_and_recover(struct tdb_context *tdb)
-{
-	int ret;
-
-	/* We need to match locking order in transaction commit. */
-	if (tdb_brlock(tdb, F_WRLCK, FREELIST_TOP, 0, TDB_LOCK_WAIT)) {
-		return -1;
-	}
-
-	if (tdb_brlock(tdb, F_WRLCK, OPEN_LOCK, 1, TDB_LOCK_WAIT)) {
-		tdb_brunlock(tdb, F_WRLCK, FREELIST_TOP, 0);
-		return -1;
-	}
-
-	ret = tdb_transaction_recover(tdb);
-
-	tdb_brunlock(tdb, F_WRLCK, OPEN_LOCK, 1);
-	tdb_brunlock(tdb, F_WRLCK, FREELIST_TOP, 0);
-
-	return ret;
-}
-
-static bool have_data_locks(const struct tdb_context *tdb)
-{
-	unsigned int i;
-
-	for (i = 0; i < tdb->num_lockrecs; i++) {
-		if (tdb->lockrecs[i].off >= lock_offset(-1))
-			return true;
-	}
-	return false;
-}
-
-static int tdb_lock_list(struct tdb_context *tdb, int list, int ltype,
-			 enum tdb_lock_flags waitflag)
-{
-	int ret;
-	bool check = false;
-
-	/* a allrecord lock allows us to avoid per chain locks */
-	if (tdb->allrecord_lock.count &&
-	    (ltype == tdb->allrecord_lock.ltype || ltype == F_RDLCK)) {
-		return 0;
-	}
-
-	if (tdb->allrecord_lock.count) {
-		tdb->ecode = TDB_ERR_LOCK;
-		ret = -1;
-	} else {
-		/* Only check when we grab first data lock. */
-		check = !have_data_locks(tdb);
-		ret = tdb_nest_lock(tdb, lock_offset(list), ltype, waitflag);
-
-		if (ret == 0 && check && tdb_needs_recovery(tdb)) {
-			tdb_nest_unlock(tdb, lock_offset(list), ltype, false);
-
-			if (tdb_lock_and_recover(tdb) == -1) {
-				return -1;
-			}
-			return tdb_lock_list(tdb, list, ltype, waitflag);
-		}
-	}
-	return ret;
-}
-
-/* lock a list in the database. list -1 is the alloc list */
-int tdb_lock(struct tdb_context *tdb, int list, int ltype)
-{
-	int ret;
-
-	ret = tdb_lock_list(tdb, list, ltype, TDB_LOCK_WAIT);
-	if (ret) {
-		TDB_LOG((tdb, TDB_DEBUG_ERROR, "tdb_lock failed on list %d "
-			 "ltype=%d (%s)\n",  list, ltype, strerror(errno)));
-	}
-	return ret;
-}
-
-/* lock a list in the database. list -1 is the alloc list. non-blocking lock */
-_PUBLIC_ int tdb_lock_nonblock(struct tdb_context *tdb, int list, int ltype)
-{
-	return tdb_lock_list(tdb, list, ltype, TDB_LOCK_NOWAIT);
-}
-
-
-int tdb_nest_unlock(struct tdb_context *tdb, uint32_t offset, int ltype,
-		    bool mark_lock)
-{
-	int ret = -1;
-	struct tdb_lock_type *lck;
-
-	if (tdb->flags & TDB_NOLOCK)
-		return 0;
-
-	/* Sanity checks */
-	if (offset >= lock_offset(tdb->header.hash_size)) {
-		TDB_LOG((tdb, TDB_DEBUG_ERROR, "tdb_unlock: offset %u invalid (%d)\n", offset, tdb->header.hash_size));
-		return ret;
-	}
-
-	lck = find_nestlock(tdb, offset);
-	if ((lck == NULL) || (lck->count == 0)) {
-		TDB_LOG((tdb, TDB_DEBUG_ERROR, "tdb_unlock: count is 0\n"));
-		return -1;
-	}
-
-	if (lck->count > 1) {
-		lck->count--;
-		return 0;
-	}
-
-	/*
-	 * This lock has count==1 left, so we need to unlock it in the
-	 * kernel. We don't bother with decrementing the in-memory array
-	 * element, we're about to overwrite it with the last array element
-	 * anyway.
-	 */
-
-	if (mark_lock) {
-		ret = 0;
-	} else {
-		ret = tdb_brunlock(tdb, ltype, offset, 1);
-	}
-
-	/*
-	 * Shrink the array by overwriting the element just unlocked with the
-	 * last array element.
-	 */
-	*lck = tdb->lockrecs[--tdb->num_lockrecs];
-
-	/*
-	 * We don't bother with realloc when the array shrinks, but if we have
-	 * a completely idle tdb we should get rid of the locked array.
-	 */
-
-	if (tdb->num_lockrecs == 0) {
-		SAFE_FREE(tdb->lockrecs);
-	}
-
-	if (ret)
-		TDB_LOG((tdb, TDB_DEBUG_ERROR, "tdb_unlock: An error occurred unlocking!\n")); 
-	return ret;
-}
-
-_PUBLIC_ int tdb_unlock(struct tdb_context *tdb, int list, int ltype)
-{
-	/* a global lock allows us to avoid per chain locks */
-	if (tdb->allrecord_lock.count &&
-	    (ltype == tdb->allrecord_lock.ltype || ltype == F_RDLCK)) {
-		return 0;
-	}
-
-	if (tdb->allrecord_lock.count) {
-		tdb->ecode = TDB_ERR_LOCK;
-		return -1;
-	}
-
-	return tdb_nest_unlock(tdb, lock_offset(list), ltype, false);
-}
-
-/*
-  get the transaction lock
- */
-int tdb_transaction_lock(struct tdb_context *tdb, int ltype,
-			 enum tdb_lock_flags lockflags)
-{
-	return tdb_nest_lock(tdb, TRANSACTION_LOCK, ltype, lockflags);
-}
-
-/*
-  release the transaction lock
- */
-int tdb_transaction_unlock(struct tdb_context *tdb, int ltype)
-{
-	return tdb_nest_unlock(tdb, TRANSACTION_LOCK, ltype, false);
-}
-
-/* Returns 0 if all done, -1 if error, 1 if ok. */
-static int tdb_allrecord_check(struct tdb_context *tdb, int ltype,
-			       enum tdb_lock_flags flags, bool upgradable)
-{
-	/* There are no locks on read-only dbs */
-	if (tdb->read_only || tdb->traverse_read) {
-		tdb->ecode = TDB_ERR_LOCK;
-		return -1;
-	}
-
-	if (tdb->allrecord_lock.count && tdb->allrecord_lock.ltype == ltype) {
-		tdb->allrecord_lock.count++;
-		return 0;
-	}
-
-	if (tdb->allrecord_lock.count) {
-		/* a global lock of a different type exists */
-		tdb->ecode = TDB_ERR_LOCK;
-		return -1;
-	}
-
-	if (tdb_have_extra_locks(tdb)) {
-		/* can't combine global and chain locks */
-		tdb->ecode = TDB_ERR_LOCK;
-		return -1;
-	}
-
-	if (upgradable && ltype != F_RDLCK) {
-		/* tdb error: you can't upgrade a write lock! */
-		tdb->ecode = TDB_ERR_LOCK;
-		return -1;
-	}
-	return 1;
-}
-
-/* We only need to lock individual bytes, but Linux merges consecutive locks
- * so we lock in contiguous ranges. */
-static int tdb_chainlock_gradual(struct tdb_context *tdb,
-				 int ltype, enum tdb_lock_flags flags,
-				 size_t off, size_t len)
-{
-	int ret;
-	enum tdb_lock_flags nb_flags = (flags & ~TDB_LOCK_WAIT);
-
-	if (len <= 4) {
-		/* Single record.  Just do blocking lock. */
-		return tdb_brlock(tdb, ltype, off, len, flags);
-	}
-
-	/* First we try non-blocking. */
-	ret = tdb_brlock(tdb, ltype, off, len, nb_flags);
-	if (ret == 0) {
-		return 0;
-	}
-
-	/* Try locking first half, then second. */
-	ret = tdb_chainlock_gradual(tdb, ltype, flags, off, len / 2);
-	if (ret == -1)
-		return -1;
-
-	ret = tdb_chainlock_gradual(tdb, ltype, flags,
-				    off + len / 2, len - len / 2);
-	if (ret == -1) {
-		tdb_brunlock(tdb, ltype, off, len / 2);
-		return -1;
-	}
-	return 0;
-}
-
-/* lock/unlock entire database.  It can only be upgradable if you have some
- * other way of guaranteeing exclusivity (ie. transaction write lock).
- * We do the locking gradually to avoid being starved by smaller locks. */
-int tdb_allrecord_lock(struct tdb_context *tdb, int ltype,
-		       enum tdb_lock_flags flags, bool upgradable)
-{
-	switch (tdb_allrecord_check(tdb, ltype, flags, upgradable)) {
-	case -1:
-		return -1;
-	case 0:
-		return 0;
-	}
-
-	/* We cover two kinds of locks:
-	 * 1) Normal chain locks.  Taken for almost all operations.
-	 * 3) Individual records locks.  Taken after normal or free
-	 *    chain locks.
-	 *
-	 * It is (1) which cause the starvation problem, so we're only
-	 * gradual for that. */
-	if (tdb_chainlock_gradual(tdb, ltype, flags, FREELIST_TOP,
-				  tdb->header.hash_size * 4) == -1) {
-		return -1;
-	}
-
-	/* Grab individual record locks. */
-	if (tdb_brlock(tdb, ltype, lock_offset(tdb->header.hash_size), 0,
-		       flags) == -1) {
-		tdb_brunlock(tdb, ltype, FREELIST_TOP,
-			     tdb->header.hash_size * 4);
-		return -1;
-	}
-
-	tdb->allrecord_lock.count = 1;
-	/* If it's upgradable, it's actually exclusive so we can treat
-	 * it as a write lock. */
-	tdb->allrecord_lock.ltype = upgradable ? F_WRLCK : ltype;
-	tdb->allrecord_lock.off = upgradable;
-
-	if (tdb_needs_recovery(tdb)) {
-		bool mark = flags & TDB_LOCK_MARK_ONLY;
-		tdb_allrecord_unlock(tdb, ltype, mark);
-		if (mark) {
-			tdb->ecode = TDB_ERR_LOCK;
-			TDB_LOG((tdb, TDB_DEBUG_ERROR,
-				 "tdb_lockall_mark cannot do recovery\n"));
-			return -1;
-		}
-		if (tdb_lock_and_recover(tdb) == -1) {
-			return -1;
-		}
-		return tdb_allrecord_lock(tdb, ltype, flags, upgradable);
-	}
-
-	return 0;
-}
-
-
-
-/* unlock entire db */
-int tdb_allrecord_unlock(struct tdb_context *tdb, int ltype, bool mark_lock)
-{
-	/* There are no locks on read-only dbs */
-	if (tdb->read_only || tdb->traverse_read) {
-		tdb->ecode = TDB_ERR_LOCK;
-		return -1;
-	}
-
-	if (tdb->allrecord_lock.count == 0) {
-		tdb->ecode = TDB_ERR_LOCK;
-		return -1;
-	}
-
-	/* Upgradable locks are marked as write locks. */
-	if (tdb->allrecord_lock.ltype != ltype
-	    && (!tdb->allrecord_lock.off || ltype != F_RDLCK)) {
-		tdb->ecode = TDB_ERR_LOCK;
-		return -1;
-	}
-
-	if (tdb->allrecord_lock.count > 1) {
-		tdb->allrecord_lock.count--;
-		return 0;
-	}
-
-	if (!mark_lock && tdb_brunlock(tdb, ltype, FREELIST_TOP, 0)) {
-		TDB_LOG((tdb, TDB_DEBUG_ERROR, "tdb_unlockall failed (%s)\n", strerror(errno)));
-		return -1;
-	}
-
-	tdb->allrecord_lock.count = 0;
-	tdb->allrecord_lock.ltype = 0;
-
-	return 0;
-}
-
-/* lock entire database with write lock */
-_PUBLIC_ int tdb_lockall(struct tdb_context *tdb)
-{
-	tdb_trace(tdb, "tdb_lockall");
-	return tdb_allrecord_lock(tdb, F_WRLCK, TDB_LOCK_WAIT, false);
-}
-
-/* lock entire database with write lock - mark only */
-_PUBLIC_ int tdb_lockall_mark(struct tdb_context *tdb)
-{
-	tdb_trace(tdb, "tdb_lockall_mark");
-	return tdb_allrecord_lock(tdb, F_WRLCK, TDB_LOCK_MARK_ONLY, false);
-}
-
-/* unlock entire database with write lock - unmark only */
-_PUBLIC_ int tdb_lockall_unmark(struct tdb_context *tdb)
-{
-	tdb_trace(tdb, "tdb_lockall_unmark");
-	return tdb_allrecord_unlock(tdb, F_WRLCK, true);
-}
-
-/* lock entire database with write lock - nonblocking varient */
-_PUBLIC_ int tdb_lockall_nonblock(struct tdb_context *tdb)
-{
-	int ret = tdb_allrecord_lock(tdb, F_WRLCK, TDB_LOCK_NOWAIT, false);
-	tdb_trace_ret(tdb, "tdb_lockall_nonblock", ret);
-	return ret;
-}
-
-/* unlock entire database with write lock */
-_PUBLIC_ int tdb_unlockall(struct tdb_context *tdb)
-{
-	tdb_trace(tdb, "tdb_unlockall");
-	return tdb_allrecord_unlock(tdb, F_WRLCK, false);
-}
-
-/* lock entire database with read lock */
-_PUBLIC_ int tdb_lockall_read(struct tdb_context *tdb)
-{
-	tdb_trace(tdb, "tdb_lockall_read");
-	return tdb_allrecord_lock(tdb, F_RDLCK, TDB_LOCK_WAIT, false);
-}
-
-/* lock entire database with read lock - nonblock varient */
-_PUBLIC_ int tdb_lockall_read_nonblock(struct tdb_context *tdb)
-{
-	int ret = tdb_allrecord_lock(tdb, F_RDLCK, TDB_LOCK_NOWAIT, false);
-	tdb_trace_ret(tdb, "tdb_lockall_read_nonblock", ret);
-	return ret;
-}
-
-/* unlock entire database with read lock */
-_PUBLIC_ int tdb_unlockall_read(struct tdb_context *tdb)
-{
-	tdb_trace(tdb, "tdb_unlockall_read");
-	return tdb_allrecord_unlock(tdb, F_RDLCK, false);
-}
-
-/* lock/unlock one hash chain. This is meant to be used to reduce
-   contention - it cannot guarantee how many records will be locked */
-_PUBLIC_ int tdb_chainlock(struct tdb_context *tdb, TDB_DATA key)
-{
-	int ret = tdb_lock(tdb, BUCKET(tdb->hash_fn(&key)), F_WRLCK);
-	tdb_trace_1rec(tdb, "tdb_chainlock", key);
-	return ret;
-}
-
-/* lock/unlock one hash chain, non-blocking. This is meant to be used
-   to reduce contention - it cannot guarantee how many records will be
-   locked */
-_PUBLIC_ int tdb_chainlock_nonblock(struct tdb_context *tdb, TDB_DATA key)
-{
-	int ret = tdb_lock_nonblock(tdb, BUCKET(tdb->hash_fn(&key)), F_WRLCK);
-	tdb_trace_1rec_ret(tdb, "tdb_chainlock_nonblock", key, ret);
-	return ret;
-}
-
-/* mark a chain as locked without actually locking it. Warning! use with great caution! */
-_PUBLIC_ int tdb_chainlock_mark(struct tdb_context *tdb, TDB_DATA key)
-{
-	int ret = tdb_nest_lock(tdb, lock_offset(BUCKET(tdb->hash_fn(&key))),
-				F_WRLCK, TDB_LOCK_MARK_ONLY);
-	tdb_trace_1rec(tdb, "tdb_chainlock_mark", key);
-	return ret;
-}
-
-/* unmark a chain as locked without actually locking it. Warning! use with great caution! */
-_PUBLIC_ int tdb_chainlock_unmark(struct tdb_context *tdb, TDB_DATA key)
-{
-	tdb_trace_1rec(tdb, "tdb_chainlock_unmark", key);
-	return tdb_nest_unlock(tdb, lock_offset(BUCKET(tdb->hash_fn(&key))),
-			       F_WRLCK, true);
-}
-
-_PUBLIC_ int tdb_chainunlock(struct tdb_context *tdb, TDB_DATA key)
-{
-	tdb_trace_1rec(tdb, "tdb_chainunlock", key);
-	return tdb_unlock(tdb, BUCKET(tdb->hash_fn(&key)), F_WRLCK);
-}
-
-_PUBLIC_ int tdb_chainlock_read(struct tdb_context *tdb, TDB_DATA key)
-{
-	int ret;
-	ret = tdb_lock(tdb, BUCKET(tdb->hash_fn(&key)), F_RDLCK);
-	tdb_trace_1rec(tdb, "tdb_chainlock_read", key);
-	return ret;
-}
-
-_PUBLIC_ int tdb_chainunlock_read(struct tdb_context *tdb, TDB_DATA key)
-{
-	tdb_trace_1rec(tdb, "tdb_chainunlock_read", key);
-	return tdb_unlock(tdb, BUCKET(tdb->hash_fn(&key)), F_RDLCK);
-}
-
-/* record lock stops delete underneath */
-int tdb_lock_record(struct tdb_context *tdb, tdb_off_t off)
-{
-	if (tdb->allrecord_lock.count) {
-		return 0;
-	}
-	return off ? tdb_brlock(tdb, F_RDLCK, off, 1, TDB_LOCK_WAIT) : 0;
-}
-
-/*
-  Write locks override our own fcntl readlocks, so check it here.
-  Note this is meant to be F_SETLK, *not* F_SETLKW, as it's not
-  an error to fail to get the lock here.
-*/
-int tdb_write_lock_record(struct tdb_context *tdb, tdb_off_t off)
-{
-	struct tdb_traverse_lock *i;
-	for (i = &tdb->travlocks; i; i = i->next)
-		if (i->off == off)
-			return -1;
-	if (tdb->allrecord_lock.count) {
-		if (tdb->allrecord_lock.ltype == F_WRLCK) {
-			return 0;
-		}
-		return -1;
-	}
-	return tdb_brlock(tdb, F_WRLCK, off, 1, TDB_LOCK_NOWAIT|TDB_LOCK_PROBE);
-}
-
-int tdb_write_unlock_record(struct tdb_context *tdb, tdb_off_t off)
-{
-	if (tdb->allrecord_lock.count) {
-		return 0;
-	}
-	return tdb_brunlock(tdb, F_WRLCK, off, 1);
-}
-
-/* fcntl locks don't stack: avoid unlocking someone else's */
-int tdb_unlock_record(struct tdb_context *tdb, tdb_off_t off)
-{
-	struct tdb_traverse_lock *i;
-	uint32_t count = 0;
-
-	if (tdb->allrecord_lock.count) {
-		return 0;
-	}
-
-	if (off == 0)
-		return 0;
-	for (i = &tdb->travlocks; i; i = i->next)
-		if (i->off == off)
-			count++;
-	return (count == 1 ? tdb_brunlock(tdb, F_RDLCK, off, 1) : 0);
-}
-
-bool tdb_have_extra_locks(struct tdb_context *tdb)
-{
-	unsigned int extra = tdb->num_lockrecs;
-
-	/* A transaction holds the lock for all records. */
-	if (!tdb->transaction && tdb->allrecord_lock.count) {
-		return true;
-	}
-
-	/* We always hold the active lock if CLEAR_IF_FIRST. */
-	if (find_nestlock(tdb, ACTIVE_LOCK)) {
-		extra--;
-	}
-
-	/* In a transaction, we expect to hold the transaction lock */
-	if (tdb->transaction && find_nestlock(tdb, TRANSACTION_LOCK)) {
-		extra--;
-	}
-
-	return extra;
-}
-
-/* The transaction code uses this to remove all locks. */
-void tdb_release_transaction_locks(struct tdb_context *tdb)
-{
-	unsigned int i, active = 0;
-
-	if (tdb->allrecord_lock.count != 0) {
-		tdb_brunlock(tdb, tdb->allrecord_lock.ltype, FREELIST_TOP, 0);
-		tdb->allrecord_lock.count = 0;
-	}
-
-	for (i=0;i<tdb->num_lockrecs;i++) {
-		struct tdb_lock_type *lck = &tdb->lockrecs[i];
-
-		/* Don't release the active lock!  Copy it to first entry. */
-		if (lck->off == ACTIVE_LOCK) {
-			tdb->lockrecs[active++] = *lck;
-		} else {
-			tdb_brunlock(tdb, lck->ltype, lck->off, 1);
-		}
-	}
-	tdb->num_lockrecs = active;
-	if (tdb->num_lockrecs == 0) {
-		SAFE_FREE(tdb->lockrecs);
-	}
-}
-
-/* Following functions are added specifically to support CTDB. */
-
-/* Don't do actual fcntl locking, just mark tdb locked */
-_PUBLIC_ int tdb_transaction_write_lock_mark(struct tdb_context *tdb)
-{
-	return tdb_transaction_lock(tdb, F_WRLCK, TDB_LOCK_MARK_ONLY);
-}
-
-/* Don't do actual fcntl unlocking, just mark tdb unlocked */
-_PUBLIC_ int tdb_transaction_write_lock_unmark(struct tdb_context *tdb)
-{
-	return tdb_nest_unlock(tdb, TRANSACTION_LOCK, F_WRLCK, true);
-}
diff --git a/lib/tdb/common/open.c b/lib/tdb/common/open.c
deleted file mode 100644
index 8836f84..0000000
--- a/lib/tdb/common/open.c
+++ /dev/null
@@ -1,647 +0,0 @@
- /* 
-   Unix SMB/CIFS implementation.
-
-   trivial database library
-
-   Copyright (C) Andrew Tridgell              1999-2005
-   Copyright (C) Paul `Rusty' Russell		   2000
-   Copyright (C) Jeremy Allison			   2000-2003
-
-     ** NOTE! The following LGPL license applies to the tdb
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-
-#include "tdb_private.h"
-
-/* all contexts, to ensure no double-opens (fcntl locks don't nest!) */
-static struct tdb_context *tdbs = NULL;
-
-/* We use two hashes to double-check they're using the right hash function. */
-void tdb_header_hash(struct tdb_context *tdb,
-		     uint32_t *magic1_hash, uint32_t *magic2_hash)
-{
-	TDB_DATA hash_key;
-	uint32_t tdb_magic = TDB_MAGIC;
-
-	hash_key.dptr = discard_const_p(unsigned char, TDB_MAGIC_FOOD);
-	hash_key.dsize = sizeof(TDB_MAGIC_FOOD);
-	*magic1_hash = tdb->hash_fn(&hash_key);
-
-	hash_key.dptr = (unsigned char *)CONVERT(tdb_magic);
-	hash_key.dsize = sizeof(tdb_magic);
-	*magic2_hash = tdb->hash_fn(&hash_key);
-
-	/* Make sure at least one hash is non-zero! */
-	if (*magic1_hash == 0 && *magic2_hash == 0)
-		*magic1_hash = 1;
-}
-
-/* initialise a new database with a specified hash size */
-static int tdb_new_database(struct tdb_context *tdb, int hash_size)
-{
-	struct tdb_header *newdb;
-	size_t size;
-	int ret = -1;
-
-	/* We make it up in memory, then write it out if not internal */
-	size = sizeof(struct tdb_header) + (hash_size+1)*sizeof(tdb_off_t);
-	if (!(newdb = (struct tdb_header *)calloc(size, 1))) {
-		tdb->ecode = TDB_ERR_OOM;
-		return -1;
-	}
-
-	/* Fill in the header */
-	newdb->version = TDB_VERSION;
-	newdb->hash_size = hash_size;
-
-	tdb_header_hash(tdb, &newdb->magic1_hash, &newdb->magic2_hash);
-
-	/* Make sure older tdbs (which don't check the magic hash fields)
-	 * will refuse to open this TDB. */
-	if (tdb->flags & TDB_INCOMPATIBLE_HASH)
-		newdb->rwlocks = TDB_HASH_RWLOCK_MAGIC;
-
-	if (tdb->flags & TDB_INTERNAL) {
-		tdb->map_size = size;
-		tdb->map_ptr = (char *)newdb;
-		memcpy(&tdb->header, newdb, sizeof(tdb->header));
-		/* Convert the `ondisk' version if asked. */
-		CONVERT(*newdb);
-		return 0;
-	}
-	if (lseek(tdb->fd, 0, SEEK_SET) == -1)
-		goto fail;
-
-	if (ftruncate(tdb->fd, 0) == -1)
-		goto fail;
-
-	/* This creates an endian-converted header, as if read from disk */
-	CONVERT(*newdb);
-	memcpy(&tdb->header, newdb, sizeof(tdb->header));
-	/* Don't endian-convert the magic food! */
-	memcpy(newdb->magic_food, TDB_MAGIC_FOOD, strlen(TDB_MAGIC_FOOD)+1);
-	/* we still have "ret == -1" here */
-	if (tdb_write_all(tdb->fd, newdb, size))
-		ret = 0;
-
-  fail:
-	SAFE_FREE(newdb);
-	return ret;
-}
-
-
-
-static int tdb_already_open(dev_t device,
-			    ino_t ino)
-{
-	struct tdb_context *i;
-
-	for (i = tdbs; i; i = i->next) {
-		if (i->device == device && i->inode == ino) {
-			return 1;
-		}
-	}
-
-	return 0;
-}
-
-/* open the database, creating it if necessary 
-
-   The open_flags and mode are passed straight to the open call on the
-   database file. A flags value of O_WRONLY is invalid. The hash size
-   is advisory, use zero for a default value.
-
-   Return is NULL on error, in which case errno is also set.  Don't 
-   try to call tdb_error or tdb_errname, just do strerror(errno).
-
-   @param name may be NULL for internal databases. */
-_PUBLIC_ struct tdb_context *tdb_open(const char *name, int hash_size, int tdb_flags,
-		      int open_flags, mode_t mode)
-{
-	return tdb_open_ex(name, hash_size, tdb_flags, open_flags, mode, NULL, NULL);
-}
-
-/* a default logging function */
-static void null_log_fn(struct tdb_context *tdb, enum tdb_debug_level level, const char *fmt, ...) PRINTF_ATTRIBUTE(3, 4);
-static void null_log_fn(struct tdb_context *tdb, enum tdb_debug_level level, const char *fmt, ...)
-{
-}
-
-static bool check_header_hash(struct tdb_context *tdb,
-			      bool default_hash, uint32_t *m1, uint32_t *m2)
-{
-	tdb_header_hash(tdb, m1, m2);
-	if (tdb->header.magic1_hash == *m1 &&
-	    tdb->header.magic2_hash == *m2) {
-		return true;
-	}
-
-	/* If they explicitly set a hash, always respect it. */
-	if (!default_hash)
-		return false;
-
-	/* Otherwise, try the other inbuilt hash. */
-	if (tdb->hash_fn == tdb_old_hash)
-		tdb->hash_fn = tdb_jenkins_hash;
-	else
-		tdb->hash_fn = tdb_old_hash;
-	return check_header_hash(tdb, false, m1, m2);
-}
-
-_PUBLIC_ struct tdb_context *tdb_open_ex(const char *name, int hash_size, int tdb_flags,
-				int open_flags, mode_t mode,
-				const struct tdb_logging_context *log_ctx,
-				tdb_hash_func hash_fn)
-{
-	struct tdb_context *tdb;
-	struct stat st;
-	int rev = 0, locked = 0;
-	unsigned char *vp;
-	uint32_t vertest;
-	unsigned v;
-	const char *hash_alg;
-	uint32_t magic1, magic2;
-
-	if (!(tdb = (struct tdb_context *)calloc(1, sizeof *tdb))) {
-		/* Can't log this */
-		errno = ENOMEM;
-		goto fail;
-	}
-	tdb_io_init(tdb);
-	tdb->fd = -1;
-#ifdef TDB_TRACE
-	tdb->tracefd = -1;
-#endif
-	tdb->name = NULL;
-	tdb->map_ptr = NULL;
-	tdb->flags = tdb_flags;
-	tdb->open_flags = open_flags;
-	if (log_ctx) {
-		tdb->log = *log_ctx;
-	} else {
-		tdb->log.log_fn = null_log_fn;
-		tdb->log.log_private = NULL;
-	}
-
-	if (name == NULL && (tdb_flags & TDB_INTERNAL)) {
-		name = "__TDB_INTERNAL__";
-	}
-
-	if (name == NULL) {
-		tdb->name = discard_const_p(char, "__NULL__");
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_open_ex: called with name == NULL\n"));
-		tdb->name = NULL;
-		errno = EINVAL;
-		goto fail;
-	}
-
-	/* now make a copy of the name, as the caller memory might went away */
-	if (!(tdb->name = (char *)strdup(name))) {
-		/*
-		 * set the name as the given string, so that tdb_name() will
-		 * work in case of an error.
-		 */
-		tdb->name = discard_const_p(char, name);
-		TDB_LOG((tdb, TDB_DEBUG_ERROR, "tdb_open_ex: can't strdup(%s)\n",
-			 name));
-		tdb->name = NULL;
-		errno = ENOMEM;
-		goto fail;
-	}
-
-	if (hash_fn) {
-		tdb->hash_fn = hash_fn;
-		hash_alg = "the user defined";
-	} else {
-		/* This controls what we use when creating a tdb. */
-		if (tdb->flags & TDB_INCOMPATIBLE_HASH) {
-			tdb->hash_fn = tdb_jenkins_hash;
-		} else {
-			tdb->hash_fn = tdb_old_hash;
-		}
-		hash_alg = "either default";
-	}
-
-	/* cache the page size */
-	tdb->page_size = getpagesize();
-	if (tdb->page_size <= 0) {
-		tdb->page_size = 0x2000;
-	}
-
-	tdb->max_dead_records = (tdb_flags & TDB_VOLATILE) ? 5 : 0;
-
-	if ((open_flags & O_ACCMODE) == O_WRONLY) {
-		TDB_LOG((tdb, TDB_DEBUG_ERROR, "tdb_open_ex: can't open tdb %s write-only\n",
-			 name));
-		errno = EINVAL;
-		goto fail;
-	}
-
-	if (hash_size == 0)
-		hash_size = DEFAULT_HASH_SIZE;
-	if ((open_flags & O_ACCMODE) == O_RDONLY) {
-		tdb->read_only = 1;
-		/* read only databases don't do locking or clear if first */
-		tdb->flags |= TDB_NOLOCK;
-		tdb->flags &= ~TDB_CLEAR_IF_FIRST;
-	}
-
-	if ((tdb->flags & TDB_ALLOW_NESTING) &&
-	    (tdb->flags & TDB_DISALLOW_NESTING)) {
-		tdb->ecode = TDB_ERR_NESTING;
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_open_ex: "
-			"allow_nesting and disallow_nesting are not allowed together!"));
-		errno = EINVAL;
-		goto fail;
-	}
-
-	if (getenv("TDB_NO_FSYNC")) {
-		tdb->flags |= TDB_NOSYNC;
-	}
-
-	/*
-	 * TDB_ALLOW_NESTING is the default behavior.
-	 * Note: this may change in future versions!
-	 */
-	if (!(tdb->flags & TDB_DISALLOW_NESTING)) {
-		tdb->flags |= TDB_ALLOW_NESTING;
-	}
-
-	/* internal databases don't mmap or lock, and start off cleared */
-	if (tdb->flags & TDB_INTERNAL) {
-		tdb->flags |= (TDB_NOLOCK | TDB_NOMMAP);
-		tdb->flags &= ~TDB_CLEAR_IF_FIRST;
-		if (tdb_new_database(tdb, hash_size) != 0) {
-			TDB_LOG((tdb, TDB_DEBUG_ERROR, "tdb_open_ex: tdb_new_database failed!"));
-			goto fail;
-		}
-		goto internal;
-	}
-
-	if ((tdb->fd = open(name, open_flags, mode)) == -1) {
-		TDB_LOG((tdb, TDB_DEBUG_WARNING, "tdb_open_ex: could not open file %s: %s\n",
-			 name, strerror(errno)));
-		goto fail;	/* errno set by open(2) */
-	}
-
-	/* on exec, don't inherit the fd */
-	v = fcntl(tdb->fd, F_GETFD, 0);
-        fcntl(tdb->fd, F_SETFD, v | FD_CLOEXEC);
-
-	/* ensure there is only one process initialising at once */
-	if (tdb_nest_lock(tdb, OPEN_LOCK, F_WRLCK, TDB_LOCK_WAIT) == -1) {
-		TDB_LOG((tdb, TDB_DEBUG_ERROR, "tdb_open_ex: failed to get open lock on %s: %s\n",
-			 name, strerror(errno)));
-		goto fail;	/* errno set by tdb_brlock */
-	}
-
-	/* we need to zero database if we are the only one with it open */
-	if ((tdb_flags & TDB_CLEAR_IF_FIRST) &&
-	    (!tdb->read_only) &&
-	    (locked = (tdb_nest_lock(tdb, ACTIVE_LOCK, F_WRLCK, TDB_LOCK_NOWAIT|TDB_LOCK_PROBE) == 0))) {
-		open_flags |= O_CREAT;
-		if (ftruncate(tdb->fd, 0) == -1) {
-			TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_open_ex: "
-				 "failed to truncate %s: %s\n",
-				 name, strerror(errno)));
-			goto fail; /* errno set by ftruncate */
-		}
-	}
-
-	errno = 0;
-	if (read(tdb->fd, &tdb->header, sizeof(tdb->header)) != sizeof(tdb->header)
-	    || strcmp(tdb->header.magic_food, TDB_MAGIC_FOOD) != 0) {
-		if (!(open_flags & O_CREAT) || tdb_new_database(tdb, hash_size) == -1) {
-			if (errno == 0) {
-				errno = EIO; /* ie bad format or something */
-			}
-			goto fail;
-		}
-		rev = (tdb->flags & TDB_CONVERT);
-	} else if (tdb->header.version != TDB_VERSION
-		   && !(rev = (tdb->header.version==TDB_BYTEREV(TDB_VERSION)))) {
-		/* wrong version */
-		errno = EIO;
-		goto fail;
-	}
-	vp = (unsigned char *)&tdb->header.version;
-	vertest = (((uint32_t)vp[0]) << 24) | (((uint32_t)vp[1]) << 16) |
-		  (((uint32_t)vp[2]) << 8) | (uint32_t)vp[3];
-	tdb->flags |= (vertest==TDB_VERSION) ? TDB_BIGENDIAN : 0;
-	if (!rev)
-		tdb->flags &= ~TDB_CONVERT;
-	else {
-		tdb->flags |= TDB_CONVERT;
-		tdb_convert(&tdb->header, sizeof(tdb->header));
-	}
-	if (fstat(tdb->fd, &st) == -1)
-		goto fail;
-
-	if (tdb->header.rwlocks != 0 &&
-	    tdb->header.rwlocks != TDB_HASH_RWLOCK_MAGIC) {
-		TDB_LOG((tdb, TDB_DEBUG_ERROR, "tdb_open_ex: spinlocks no longer supported\n"));
-		goto fail;
-	}
-
-	if ((tdb->header.magic1_hash == 0) && (tdb->header.magic2_hash == 0)) {
-		/* older TDB without magic hash references */
-		tdb->hash_fn = tdb_old_hash;
-	} else if (!check_header_hash(tdb, !hash_fn, &magic1, &magic2)) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_open_ex: "
-			 "%s was not created with %s hash function we are using\n"
-			 "magic1_hash[0x%08X %s 0x%08X] "
-			 "magic2_hash[0x%08X %s 0x%08X]\n",
-			 name, hash_alg,
-			 tdb->header.magic1_hash,
-			 (tdb->header.magic1_hash == magic1) ? "==" : "!=",
-			 magic1,
-			 tdb->header.magic2_hash,
-			 (tdb->header.magic2_hash == magic2) ? "==" : "!=",
-			 magic2));
-		errno = EINVAL;
-		goto fail;
-	}
-
-	/* Is it already in the open list?  If so, fail. */
-	if (tdb_already_open(st.st_dev, st.st_ino)) {
-		TDB_LOG((tdb, TDB_DEBUG_ERROR, "tdb_open_ex: "
-			 "%s (%d,%d) is already open in this process\n",
-			 name, (int)st.st_dev, (int)st.st_ino));
-		errno = EBUSY;
-		goto fail;
-	}
-
-	/* Beware truncation! */
-	tdb->map_size = st.st_size;
-	if (tdb->map_size != st.st_size) {
-		/* Ensure ecode is set for log fn. */
-		tdb->ecode = TDB_ERR_IO;
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_open_ex: "
-			 "len %llu too large!\n", (long long)st.st_size));
-		errno = EIO;
-		goto fail;
-	}
-
-	tdb->device = st.st_dev;
-	tdb->inode = st.st_ino;
-	tdb_mmap(tdb);
-	if (locked) {
-		if (tdb_nest_unlock(tdb, ACTIVE_LOCK, F_WRLCK, false) == -1) {
-			TDB_LOG((tdb, TDB_DEBUG_ERROR, "tdb_open_ex: "
-				 "failed to release ACTIVE_LOCK on %s: %s\n",
-				 name, strerror(errno)));
-			goto fail;
-		}
-
-	}
-
-	/* We always need to do this if the CLEAR_IF_FIRST flag is set, even if
-	   we didn't get the initial exclusive lock as we need to let all other
-	   users know we're using it. */
-
-	if (tdb_flags & TDB_CLEAR_IF_FIRST) {
-		/* leave this lock in place to indicate it's in use */
-		if (tdb_nest_lock(tdb, ACTIVE_LOCK, F_RDLCK, TDB_LOCK_WAIT) == -1) {
-			goto fail;
-		}
-	}
-
-	/* if needed, run recovery */
-	if (tdb_transaction_recover(tdb) == -1) {
-		goto fail;
-	}
-
-#ifdef TDB_TRACE
-	{
-		char tracefile[strlen(name) + 32];
-
-		snprintf(tracefile, sizeof(tracefile),
-			 "%s.trace.%li", name, (long)getpid());
-		tdb->tracefd = open(tracefile, O_WRONLY|O_CREAT|O_EXCL, 0600);
-		if (tdb->tracefd >= 0) {
-			tdb_enable_seqnum(tdb);
-			tdb_trace_open(tdb, "tdb_open", hash_size, tdb_flags,
-				       open_flags);
-		} else
-			TDB_LOG((tdb, TDB_DEBUG_ERROR, "tdb_open_ex: failed to open trace file %s!\n", tracefile));
-	}
-#endif
-
- internal:
-	/* Internal (memory-only) databases skip all the code above to
-	 * do with disk files, and resume here by releasing their
-	 * open lock and hooking into the active list. */
-	if (tdb_nest_unlock(tdb, OPEN_LOCK, F_WRLCK, false) == -1) {
-		goto fail;
-	}
-	tdb->next = tdbs;
-	tdbs = tdb;
-	return tdb;
-
- fail:
-	{ int save_errno = errno;
-
-	if (!tdb)
-		return NULL;
-
-#ifdef TDB_TRACE
-	close(tdb->tracefd);
-#endif
-	if (tdb->map_ptr) {
-		if (tdb->flags & TDB_INTERNAL)
-			SAFE_FREE(tdb->map_ptr);
-		else
-			tdb_munmap(tdb);
-	}
-	if (tdb->fd != -1)
-		if (close(tdb->fd) != 0)
-			TDB_LOG((tdb, TDB_DEBUG_ERROR, "tdb_open_ex: failed to close tdb->fd on error!\n"));
-	SAFE_FREE(tdb->lockrecs);
-	SAFE_FREE(tdb->name);
-	SAFE_FREE(tdb);
-	errno = save_errno;
-	return NULL;
-	}
-}
-
-/*
- * Set the maximum number of dead records per hash chain
- */
-
-_PUBLIC_ void tdb_set_max_dead(struct tdb_context *tdb, int max_dead)
-{
-	tdb->max_dead_records = max_dead;
-}
-
-/**
- * Close a database.
- *
- * @returns -1 for error; 0 for success.
- **/
-_PUBLIC_ int tdb_close(struct tdb_context *tdb)
-{
-	struct tdb_context **i;
-	int ret = 0;
-
-	if (tdb->transaction) {
-		tdb_transaction_cancel(tdb);
-	}
-	tdb_trace(tdb, "tdb_close");
-
-	if (tdb->map_ptr) {
-		if (tdb->flags & TDB_INTERNAL)
-			SAFE_FREE(tdb->map_ptr);
-		else
-			tdb_munmap(tdb);
-	}
-	SAFE_FREE(tdb->name);
-	if (tdb->fd != -1) {
-		ret = close(tdb->fd);
-		tdb->fd = -1;
-	}
-	SAFE_FREE(tdb->lockrecs);
-
-	/* Remove from contexts list */
-	for (i = &tdbs; *i; i = &(*i)->next) {
-		if (*i == tdb) {
-			*i = tdb->next;
-			break;
-		}
-	}
-
-#ifdef TDB_TRACE
-	close(tdb->tracefd);
-#endif
-	memset(tdb, 0, sizeof(*tdb));
-	SAFE_FREE(tdb);
-
-	return ret;
-}
-
-/* register a loging function */
-_PUBLIC_ void tdb_set_logging_function(struct tdb_context *tdb,
-                                       const struct tdb_logging_context *log_ctx)
-{
-        tdb->log = *log_ctx;
-}
-
-_PUBLIC_ void *tdb_get_logging_private(struct tdb_context *tdb)
-{
-	return tdb->log.log_private;
-}
-
-static int tdb_reopen_internal(struct tdb_context *tdb, bool active_lock)
-{
-#if !defined(LIBREPLACE_PREAD_NOT_REPLACED) || \
-	!defined(LIBREPLACE_PWRITE_NOT_REPLACED)
-	struct stat st;
-#endif
-
-	if (tdb->flags & TDB_INTERNAL) {
-		return 0; /* Nothing to do. */
-	}
-
-	if (tdb_have_extra_locks(tdb)) {
-		TDB_LOG((tdb, TDB_DEBUG_ERROR, "tdb_reopen: reopen not allowed with locks held\n"));
-		goto fail;
-	}
-
-	if (tdb->transaction != 0) {
-		TDB_LOG((tdb, TDB_DEBUG_ERROR, "tdb_reopen: reopen not allowed inside a transaction\n"));
-		goto fail;
-	}
-
-/* If we have real pread & pwrite, we can skip reopen. */
-#if !defined(LIBREPLACE_PREAD_NOT_REPLACED) || \
-	!defined(LIBREPLACE_PWRITE_NOT_REPLACED)
-	if (tdb_munmap(tdb) != 0) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_reopen: munmap failed (%s)\n", strerror(errno)));
-		goto fail;
-	}
-	if (close(tdb->fd) != 0)
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_reopen: WARNING closing tdb->fd failed!\n"));
-	tdb->fd = open(tdb->name, tdb->open_flags & ~(O_CREAT|O_TRUNC), 0);
-	if (tdb->fd == -1) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_reopen: open failed (%s)\n", strerror(errno)));
-		goto fail;
-	}
-	if (fstat(tdb->fd, &st) != 0) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_reopen: fstat failed (%s)\n", strerror(errno)));
-		goto fail;
-	}
-	if (st.st_ino != tdb->inode || st.st_dev != tdb->device) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_reopen: file dev/inode has changed!\n"));
-		goto fail;
-	}
-	if (tdb_mmap(tdb) != 0) {
-		goto fail;
-	}
-#endif /* fake pread or pwrite */
-
-	/* We may still think we hold the active lock. */
-	tdb->num_lockrecs = 0;
-	SAFE_FREE(tdb->lockrecs);
-
-	if (active_lock && tdb_nest_lock(tdb, ACTIVE_LOCK, F_RDLCK, TDB_LOCK_WAIT) == -1) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_reopen: failed to obtain active lock\n"));
-		goto fail;
-	}
-
-	return 0;
-
-fail:
-	tdb_close(tdb);
-	return -1;
-}
-
-/* reopen a tdb - this can be used after a fork to ensure that we have an independent
-   seek pointer from our parent and to re-establish locks */
-_PUBLIC_ int tdb_reopen(struct tdb_context *tdb)
-{
-	return tdb_reopen_internal(tdb, tdb->flags & TDB_CLEAR_IF_FIRST);
-}
-
-/* reopen all tdb's */
-_PUBLIC_ int tdb_reopen_all(int parent_longlived)
-{
-	struct tdb_context *tdb;
-
-	for (tdb=tdbs; tdb; tdb = tdb->next) {
-		bool active_lock = (tdb->flags & TDB_CLEAR_IF_FIRST);
-
-		/*
-		 * If the parent is longlived (ie. a
-		 * parent daemon architecture), we know
-		 * it will keep it's active lock on a
-		 * tdb opened with CLEAR_IF_FIRST. Thus
-		 * for child processes we don't have to
-		 * add an active lock. This is essential
-		 * to improve performance on systems that
-		 * keep POSIX locks as a non-scalable data
-		 * structure in the kernel.
-		 */
-		if (parent_longlived) {
-			/* Ensure no clear-if-first. */
-			active_lock = false;
-		}
-
-		if (tdb_reopen_internal(tdb, active_lock) != 0)
-			return -1;
-	}
-
-	return 0;
-}
diff --git a/lib/tdb/common/summary.c b/lib/tdb/common/summary.c
deleted file mode 100644
index 171a1a2..0000000
--- a/lib/tdb/common/summary.c
+++ /dev/null
@@ -1,201 +0,0 @@
- /* 
-   Trivial Database: human-readable summary code
-   Copyright (C) Rusty Russell 2010
-   
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-#include "tdb_private.h"
-
-#define SUMMARY_FORMAT \
-	"Size of file/data: %u/%zu\n" \
-	"Number of records: %zu\n" \
-	"Smallest/average/largest keys: %zu/%zu/%zu\n" \
-	"Smallest/average/largest data: %zu/%zu/%zu\n" \
-	"Smallest/average/largest padding: %zu/%zu/%zu\n" \
-	"Number of dead records: %zu\n" \
-	"Smallest/average/largest dead records: %zu/%zu/%zu\n" \
-	"Number of free records: %zu\n" \
-	"Smallest/average/largest free records: %zu/%zu/%zu\n" \
-	"Number of hash chains: %zu\n" \
-	"Smallest/average/largest hash chains: %zu/%zu/%zu\n" \
-	"Number of uncoalesced records: %zu\n" \
-	"Smallest/average/largest uncoalesced runs: %zu/%zu/%zu\n" \
-	"Percentage keys/data/padding/free/dead/rechdrs&tailers/hashes: %.0f/%.0f/%.0f/%.0f/%.0f/%.0f/%.0f\n"
-
-/* We don't use tally module, to keep upstream happy. */
-struct tally {
-	size_t min, max, total;
-	size_t num;
-};
-
-static void tally_init(struct tally *tally)
-{
-	tally->total = 0;
-	tally->num = 0;
-	tally->min = tally->max = 0;
-}
-
-static void tally_add(struct tally *tally, size_t len)
-{
-	if (tally->num == 0)
-		tally->max = tally->min = len;
-	else if (len > tally->max)
-		tally->max = len;
-	else if (len < tally->min)
-		tally->min = len;
-	tally->num++;
-	tally->total += len;
-}
-
-static size_t tally_mean(const struct tally *tally)
-{
-	if (!tally->num)
-		return 0;
-	return tally->total / tally->num;
-}
-
-static size_t get_hash_length(struct tdb_context *tdb, unsigned int i)
-{
-	tdb_off_t rec_ptr;
-	size_t count = 0;
-
-	if (tdb_ofs_read(tdb, TDB_HASH_TOP(i), &rec_ptr) == -1)
-		return 0;
-
-	/* keep looking until we find the right record */
-	while (rec_ptr) {
-		struct tdb_record r;
-		++count;
-		if (tdb_rec_read(tdb, rec_ptr, &r) == -1)
-			return 0;
-		rec_ptr = r.next;
-	}
-	return count;
-}
-
-_PUBLIC_ char *tdb_summary(struct tdb_context *tdb)
-{
-	tdb_off_t off, rec_off;
-	struct tally freet, keys, data, dead, extra, hash, uncoal;
-	struct tdb_record rec;
-	char *ret = NULL;
-	bool locked;
-	size_t len, unc = 0;
-	struct tdb_record recovery;
-
-	/* Read-only databases use no locking at all: it's best-effort.
-	 * We may have a write lock already, so skip that case too. */
-	if (tdb->read_only || tdb->allrecord_lock.count != 0) {
-		locked = false;
-	} else {
-		if (tdb_lockall_read(tdb) == -1)
-			return NULL;
-		locked = true;
-	}
-
-	if (tdb_recovery_area(tdb, tdb->methods, &rec_off, &recovery) != 0) {
-		goto unlock;
-	}
-
-	tally_init(&freet);
-	tally_init(&keys);
-	tally_init(&data);
-	tally_init(&dead);
-	tally_init(&extra);
-	tally_init(&hash);
-	tally_init(&uncoal);
-
-	for (off = TDB_DATA_START(tdb->header.hash_size);
-	     off < tdb->map_size - 1;
-	     off += sizeof(rec) + rec.rec_len) {
-		if (tdb->methods->tdb_read(tdb, off, &rec, sizeof(rec),
-					   DOCONV()) == -1)
-			goto unlock;
-		switch (rec.magic) {
-		case TDB_MAGIC:
-			tally_add(&keys, rec.key_len);
-			tally_add(&data, rec.data_len);
-			tally_add(&extra, rec.rec_len - (rec.key_len
-							 + rec.data_len));
-			if (unc > 1)
-				tally_add(&uncoal, unc - 1);
-			unc = 0;
-			break;
-		case TDB_FREE_MAGIC:
-			tally_add(&freet, rec.rec_len);
-			unc++;
-			break;
-		/* If we crash after ftruncate, we can get zeroes or fill. */
-		case TDB_RECOVERY_INVALID_MAGIC:
-		case 0x42424242:
-			unc++;
-			/* If it's a valid recovery, we can trust rec_len. */
-			if (off != rec_off) {
-				rec.rec_len = tdb_dead_space(tdb, off)
-					- sizeof(rec);
-			}
-			/* Fall through */
-		case TDB_DEAD_MAGIC:
-			tally_add(&dead, rec.rec_len);
-			break;
-		default:
-			TDB_LOG((tdb, TDB_DEBUG_ERROR,
-				 "Unexpected record magic 0x%x at offset %d\n",
-				 rec.magic, off));
-			goto unlock;
-		}
-	}
-	if (unc > 1)
-		tally_add(&uncoal, unc - 1);
-
-	for (off = 0; off < tdb->header.hash_size; off++)
-		tally_add(&hash, get_hash_length(tdb, off));
-
-	/* 20 is max length of a %zu. */
-	len = strlen(SUMMARY_FORMAT) + 35*20 + 1;
-	ret = (char *)malloc(len);
-	if (!ret)
-		goto unlock;
-
-	snprintf(ret, len, SUMMARY_FORMAT,
-		 tdb->map_size, keys.total+data.total,
-		 keys.num,
-		 keys.min, tally_mean(&keys), keys.max,
-		 data.min, tally_mean(&data), data.max,
-		 extra.min, tally_mean(&extra), extra.max,
-		 dead.num,
-		 dead.min, tally_mean(&dead), dead.max,
-		 freet.num,
-		 freet.min, tally_mean(&freet), freet.max,
-		 hash.num,
-		 hash.min, tally_mean(&hash), hash.max,
-		 uncoal.total,
-		 uncoal.min, tally_mean(&uncoal), uncoal.max,
-		 keys.total * 100.0 / tdb->map_size,
-		 data.total * 100.0 / tdb->map_size,
-		 extra.total * 100.0 / tdb->map_size,
-		 freet.total * 100.0 / tdb->map_size,
-		 dead.total * 100.0 / tdb->map_size,
-		 (keys.num + freet.num + dead.num)
-		 * (sizeof(struct tdb_record) + sizeof(uint32_t))
-		 * 100.0 / tdb->map_size,
-		 tdb->header.hash_size * sizeof(tdb_off_t)
-		 * 100.0 / tdb->map_size);
-
-unlock:
-	if (locked) {
-		tdb_unlockall_read(tdb);
-	}
-	return ret;
-}
diff --git a/lib/tdb/common/tdb.c b/lib/tdb/common/tdb.c
deleted file mode 100644
index fc1f560..0000000
--- a/lib/tdb/common/tdb.c
+++ /dev/null
@@ -1,1154 +0,0 @@
- /* 
-   Unix SMB/CIFS implementation.
-
-   trivial database library
-
-   Copyright (C) Andrew Tridgell              1999-2005
-   Copyright (C) Paul `Rusty' Russell		   2000
-   Copyright (C) Jeremy Allison			   2000-2003
-
-     ** NOTE! The following LGPL license applies to the tdb
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-
-#include "tdb_private.h"
-
-_PUBLIC_ TDB_DATA tdb_null;
-
-/*
-  non-blocking increment of the tdb sequence number if the tdb has been opened using
-  the TDB_SEQNUM flag
-*/
-_PUBLIC_ void tdb_increment_seqnum_nonblock(struct tdb_context *tdb)
-{
-	tdb_off_t seqnum=0;
-
-	if (!(tdb->flags & TDB_SEQNUM)) {
-		return;
-	}
-
-	/* we ignore errors from this, as we have no sane way of
-	   dealing with them.
-	*/
-	tdb_ofs_read(tdb, TDB_SEQNUM_OFS, &seqnum);
-	seqnum++;
-	tdb_ofs_write(tdb, TDB_SEQNUM_OFS, &seqnum);
-}
-
-/*
-  increment the tdb sequence number if the tdb has been opened using
-  the TDB_SEQNUM flag
-*/
-static void tdb_increment_seqnum(struct tdb_context *tdb)
-{
-	if (!(tdb->flags & TDB_SEQNUM)) {
-		return;
-	}
-
-	if (tdb_nest_lock(tdb, TDB_SEQNUM_OFS, F_WRLCK,
-			  TDB_LOCK_WAIT|TDB_LOCK_PROBE) != 0) {
-		return;
-	}
-
-	tdb_increment_seqnum_nonblock(tdb);
-
-	tdb_nest_unlock(tdb, TDB_SEQNUM_OFS, F_WRLCK, false);
-}
-
-static int tdb_key_compare(TDB_DATA key, TDB_DATA data, void *private_data)
-{
-	return memcmp(data.dptr, key.dptr, data.dsize);
-}
-
-/* Returns 0 on fail.  On success, return offset of record, and fills
-   in rec */
-static tdb_off_t tdb_find(struct tdb_context *tdb, TDB_DATA key, uint32_t hash,
-			struct tdb_record *r)
-{
-	tdb_off_t rec_ptr;
-
-	/* read in the hash top */
-	if (tdb_ofs_read(tdb, TDB_HASH_TOP(hash), &rec_ptr) == -1)
-		return 0;
-
-	/* keep looking until we find the right record */
-	while (rec_ptr) {
-		if (tdb_rec_read(tdb, rec_ptr, r) == -1)
-			return 0;
-
-		if (!TDB_DEAD(r) && hash==r->full_hash
-		    && key.dsize==r->key_len
-		    && tdb_parse_data(tdb, key, rec_ptr + sizeof(*r),
-				      r->key_len, tdb_key_compare,
-				      NULL) == 0) {
-			return rec_ptr;
-		}
-		/* detect tight infinite loop */
-		if (rec_ptr == r->next) {
-			tdb->ecode = TDB_ERR_CORRUPT;
-			TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_find: loop detected.\n"));
-			return 0;
-		}
-		rec_ptr = r->next;
-	}
-	tdb->ecode = TDB_ERR_NOEXIST;
-	return 0;
-}
-
-/* As tdb_find, but if you succeed, keep the lock */
-tdb_off_t tdb_find_lock_hash(struct tdb_context *tdb, TDB_DATA key, uint32_t hash, int locktype,
-			   struct tdb_record *rec)
-{
-	uint32_t rec_ptr;
-
-	if (tdb_lock(tdb, BUCKET(hash), locktype) == -1)
-		return 0;
-	if (!(rec_ptr = tdb_find(tdb, key, hash, rec)))
-		tdb_unlock(tdb, BUCKET(hash), locktype);
-	return rec_ptr;
-}
-
-static TDB_DATA _tdb_fetch(struct tdb_context *tdb, TDB_DATA key);
-
-static int tdb_update_hash_cmp(TDB_DATA key, TDB_DATA data, void *private_data)
-{
-	TDB_DATA *dbuf = (TDB_DATA *)private_data;
-
-	if (dbuf->dsize != data.dsize) {
-		return -1;
-	}
-	if (memcmp(dbuf->dptr, data.dptr, data.dsize) != 0) {
-		return -1;
-	}
-	return 0;
-}
-
-/* update an entry in place - this only works if the new data size
-   is <= the old data size and the key exists.
-   on failure return -1.
-*/
-static int tdb_update_hash(struct tdb_context *tdb, TDB_DATA key, uint32_t hash, TDB_DATA dbuf)
-{
-	struct tdb_record rec;
-	tdb_off_t rec_ptr;
-
-	/* find entry */
-	if (!(rec_ptr = tdb_find(tdb, key, hash, &rec)))
-		return -1;
-
-	/* it could be an exact duplicate of what is there - this is
-	 * surprisingly common (eg. with a ldb re-index). */
-	if (rec.key_len == key.dsize && 
-	    rec.data_len == dbuf.dsize &&
-	    rec.full_hash == hash &&
-	    tdb_parse_record(tdb, key, tdb_update_hash_cmp, &dbuf) == 0) {
-		return 0;
-	}
-
-	/* must be long enough key, data and tailer */
-	if (rec.rec_len < key.dsize + dbuf.dsize + sizeof(tdb_off_t)) {
-		tdb->ecode = TDB_SUCCESS; /* Not really an error */
-		return -1;
-	}
-
-	if (tdb->methods->tdb_write(tdb, rec_ptr + sizeof(rec) + rec.key_len,
-		      dbuf.dptr, dbuf.dsize) == -1)
-		return -1;
-
-	if (dbuf.dsize != rec.data_len) {
-		/* update size */
-		rec.data_len = dbuf.dsize;
-		return tdb_rec_write(tdb, rec_ptr, &rec);
-	}
-
-	return 0;
-}
-
-/* find an entry in the database given a key */
-/* If an entry doesn't exist tdb_err will be set to
- * TDB_ERR_NOEXIST. If a key has no data attached
- * then the TDB_DATA will have zero length but
- * a non-zero pointer
- */
-static TDB_DATA _tdb_fetch(struct tdb_context *tdb, TDB_DATA key)
-{
-	tdb_off_t rec_ptr;
-	struct tdb_record rec;
-	TDB_DATA ret;
-	uint32_t hash;
-
-	/* find which hash bucket it is in */
-	hash = tdb->hash_fn(&key);
-	if (!(rec_ptr = tdb_find_lock_hash(tdb,key,hash,F_RDLCK,&rec)))
-		return tdb_null;
-
-	ret.dptr = tdb_alloc_read(tdb, rec_ptr + sizeof(rec) + rec.key_len,
-				  rec.data_len);
-	ret.dsize = rec.data_len;
-	tdb_unlock(tdb, BUCKET(rec.full_hash), F_RDLCK);
-	return ret;
-}
-
-_PUBLIC_ TDB_DATA tdb_fetch(struct tdb_context *tdb, TDB_DATA key)
-{
-	TDB_DATA ret = _tdb_fetch(tdb, key);
-
-	tdb_trace_1rec_retrec(tdb, "tdb_fetch", key, ret);
-	return ret;
-}
-
-/*
- * Find an entry in the database and hand the record's data to a parsing
- * function. The parsing function is executed under the chain read lock, so it
- * should be fast and should not block on other syscalls.
- *
- * DON'T CALL OTHER TDB CALLS FROM THE PARSER, THIS MIGHT LEAD TO SEGFAULTS.
- *
- * For mmapped tdb's that do not have a transaction open it points the parsing
- * function directly at the mmap area, it avoids the malloc/memcpy in this
- * case. If a transaction is open or no mmap is available, it has to do
- * malloc/read/parse/free.
- *
- * This is interesting for all readers of potentially large data structures in
- * the tdb records, ldb indexes being one example.
- *
- * Return -1 if the record was not found.
- */
-
-_PUBLIC_ int tdb_parse_record(struct tdb_context *tdb, TDB_DATA key,
-		     int (*parser)(TDB_DATA key, TDB_DATA data,
-				   void *private_data),
-		     void *private_data)
-{
-	tdb_off_t rec_ptr;
-	struct tdb_record rec;
-	int ret;
-	uint32_t hash;
-
-	/* find which hash bucket it is in */
-	hash = tdb->hash_fn(&key);
-
-	if (!(rec_ptr = tdb_find_lock_hash(tdb,key,hash,F_RDLCK,&rec))) {
-		/* record not found */
-		tdb_trace_1rec_ret(tdb, "tdb_parse_record", key, -1);
-		tdb->ecode = TDB_ERR_NOEXIST;
-		return -1;
-	}
-	tdb_trace_1rec_ret(tdb, "tdb_parse_record", key, 0);
-
-	ret = tdb_parse_data(tdb, key, rec_ptr + sizeof(rec) + rec.key_len,
-			     rec.data_len, parser, private_data);
-
-	tdb_unlock(tdb, BUCKET(rec.full_hash), F_RDLCK);
-
-	return ret;
-}
-
-/* check if an entry in the database exists 
-
-   note that 1 is returned if the key is found and 0 is returned if not found
-   this doesn't match the conventions in the rest of this module, but is
-   compatible with gdbm
-*/
-static int tdb_exists_hash(struct tdb_context *tdb, TDB_DATA key, uint32_t hash)
-{
-	struct tdb_record rec;
-
-	if (tdb_find_lock_hash(tdb, key, hash, F_RDLCK, &rec) == 0)
-		return 0;
-	tdb_unlock(tdb, BUCKET(rec.full_hash), F_RDLCK);
-	return 1;
-}
-
-_PUBLIC_ int tdb_exists(struct tdb_context *tdb, TDB_DATA key)
-{
-	uint32_t hash = tdb->hash_fn(&key);
-	int ret;
-
-	ret = tdb_exists_hash(tdb, key, hash);
-	tdb_trace_1rec_ret(tdb, "tdb_exists", key, ret);
-	return ret;
-}
-
-/* actually delete an entry in the database given the offset */
-int tdb_do_delete(struct tdb_context *tdb, tdb_off_t rec_ptr, struct tdb_record *rec)
-{
-	tdb_off_t last_ptr, i;
-	struct tdb_record lastrec;
-
-	if (tdb->read_only || tdb->traverse_read) return -1;
-
-	if (((tdb->traverse_write != 0) && (!TDB_DEAD(rec))) ||
-	    tdb_write_lock_record(tdb, rec_ptr) == -1) {
-		/* Someone traversing here: mark it as dead */
-		rec->magic = TDB_DEAD_MAGIC;
-		return tdb_rec_write(tdb, rec_ptr, rec);
-	}
-	if (tdb_write_unlock_record(tdb, rec_ptr) != 0)
-		return -1;
-
-	/* find previous record in hash chain */
-	if (tdb_ofs_read(tdb, TDB_HASH_TOP(rec->full_hash), &i) == -1)
-		return -1;
-	for (last_ptr = 0; i != rec_ptr; last_ptr = i, i = lastrec.next)
-		if (tdb_rec_read(tdb, i, &lastrec) == -1)
-			return -1;
-
-	/* unlink it: next ptr is at start of record. */
-	if (last_ptr == 0)
-		last_ptr = TDB_HASH_TOP(rec->full_hash);
-	if (tdb_ofs_write(tdb, last_ptr, &rec->next) == -1)
-		return -1;
-
-	/* recover the space */
-	if (tdb_free(tdb, rec_ptr, rec) == -1)
-		return -1;
-	return 0;
-}
-
-static int tdb_count_dead(struct tdb_context *tdb, uint32_t hash)
-{
-	int res = 0;
-	tdb_off_t rec_ptr;
-	struct tdb_record rec;
-
-	/* read in the hash top */
-	if (tdb_ofs_read(tdb, TDB_HASH_TOP(hash), &rec_ptr) == -1)
-		return 0;
-
-	while (rec_ptr) {
-		if (tdb_rec_read(tdb, rec_ptr, &rec) == -1)
-			return 0;
-
-		if (rec.magic == TDB_DEAD_MAGIC) {
-			res += 1;
-		}
-		rec_ptr = rec.next;
-	}
-	return res;
-}
-
-/*
- * Purge all DEAD records from a hash chain
- */
-static int tdb_purge_dead(struct tdb_context *tdb, uint32_t hash)
-{
-	int res = -1;
-	struct tdb_record rec;
-	tdb_off_t rec_ptr;
-
-	if (tdb_lock(tdb, -1, F_WRLCK) == -1) {
-		return -1;
-	}
-
-	/* read in the hash top */
-	if (tdb_ofs_read(tdb, TDB_HASH_TOP(hash), &rec_ptr) == -1)
-		goto fail;
-
-	while (rec_ptr) {
-		tdb_off_t next;
-
-		if (tdb_rec_read(tdb, rec_ptr, &rec) == -1) {
-			goto fail;
-		}
-
-		next = rec.next;
-
-		if (rec.magic == TDB_DEAD_MAGIC
-		    && tdb_do_delete(tdb, rec_ptr, &rec) == -1) {
-			goto fail;
-		}
-		rec_ptr = next;
-	}
-	res = 0;
- fail:
-	tdb_unlock(tdb, -1, F_WRLCK);
-	return res;
-}
-
-/* delete an entry in the database given a key */
-static int tdb_delete_hash(struct tdb_context *tdb, TDB_DATA key, uint32_t hash)
-{
-	tdb_off_t rec_ptr;
-	struct tdb_record rec;
-	int ret;
-
-	if (tdb->max_dead_records != 0) {
-
-		/*
-		 * Allow for some dead records per hash chain, mainly for
-		 * tdb's with a very high create/delete rate like locking.tdb.
-		 */
-
-		if (tdb_lock(tdb, BUCKET(hash), F_WRLCK) == -1)
-			return -1;
-
-		if (tdb_count_dead(tdb, hash) >= tdb->max_dead_records) {
-			/*
-			 * Don't let the per-chain freelist grow too large,
-			 * delete all existing dead records
-			 */
-			tdb_purge_dead(tdb, hash);
-		}
-
-		if (!(rec_ptr = tdb_find(tdb, key, hash, &rec))) {
-			tdb_unlock(tdb, BUCKET(hash), F_WRLCK);
-			return -1;
-		}
-
-		/*
-		 * Just mark the record as dead.
-		 */
-		rec.magic = TDB_DEAD_MAGIC;
-		ret = tdb_rec_write(tdb, rec_ptr, &rec);
-	}
-	else {
-		if (!(rec_ptr = tdb_find_lock_hash(tdb, key, hash, F_WRLCK,
-						   &rec)))
-			return -1;
-
-		ret = tdb_do_delete(tdb, rec_ptr, &rec);
-	}
-
-	if (ret == 0) {
-		tdb_increment_seqnum(tdb);
-	}
-
-	if (tdb_unlock(tdb, BUCKET(rec.full_hash), F_WRLCK) != 0)
-		TDB_LOG((tdb, TDB_DEBUG_WARNING, "tdb_delete: WARNING tdb_unlock failed!\n"));
-	return ret;
-}
-
-_PUBLIC_ int tdb_delete(struct tdb_context *tdb, TDB_DATA key)
-{
-	uint32_t hash = tdb->hash_fn(&key);
-	int ret;
-
-	ret = tdb_delete_hash(tdb, key, hash);
-	tdb_trace_1rec_ret(tdb, "tdb_delete", key, ret);
-	return ret;
-}
-
-/*
- * See if we have a dead record around with enough space
- */
-static tdb_off_t tdb_find_dead(struct tdb_context *tdb, uint32_t hash,
-			       struct tdb_record *r, tdb_len_t length)
-{
-	tdb_off_t rec_ptr;
-
-	/* read in the hash top */
-	if (tdb_ofs_read(tdb, TDB_HASH_TOP(hash), &rec_ptr) == -1)
-		return 0;
-
-	/* keep looking until we find the right record */
-	while (rec_ptr) {
-		if (tdb_rec_read(tdb, rec_ptr, r) == -1)
-			return 0;
-
-		if (TDB_DEAD(r) && r->rec_len >= length) {
-			/*
-			 * First fit for simple coding, TODO: change to best
-			 * fit
-			 */
-			return rec_ptr;
-		}
-		rec_ptr = r->next;
-	}
-	return 0;
-}
-
-static int _tdb_store(struct tdb_context *tdb, TDB_DATA key,
-		       TDB_DATA dbuf, int flag, uint32_t hash)
-{
-	struct tdb_record rec;
-	tdb_off_t rec_ptr;
-	int ret = -1;
-
-	/* check for it existing, on insert. */
-	if (flag == TDB_INSERT) {
-		if (tdb_exists_hash(tdb, key, hash)) {
-			tdb->ecode = TDB_ERR_EXISTS;
-			goto fail;
-		}
-	} else {
-		/* first try in-place update, on modify or replace. */
-		if (tdb_update_hash(tdb, key, hash, dbuf) == 0) {
-			goto done;
-		}
-		if (tdb->ecode == TDB_ERR_NOEXIST &&
-		    flag == TDB_MODIFY) {
-			/* if the record doesn't exist and we are in TDB_MODIFY mode then
-			 we should fail the store */
-			goto fail;
-		}
-	}
-	/* reset the error code potentially set by the tdb_update() */
-	tdb->ecode = TDB_SUCCESS;
-
-	/* delete any existing record - if it doesn't exist we don't
-           care.  Doing this first reduces fragmentation, and avoids
-           coalescing with `allocated' block before it's updated. */
-	if (flag != TDB_INSERT)
-		tdb_delete_hash(tdb, key, hash);
-
-	if (tdb->max_dead_records != 0) {
-		/*
-		 * Allow for some dead records per hash chain, look if we can
-		 * find one that can hold the new record. We need enough space
-		 * for key, data and tailer. If we find one, we don't have to
-		 * consult the central freelist.
-		 */
-		rec_ptr = tdb_find_dead(
-			tdb, hash, &rec,
-			key.dsize + dbuf.dsize + sizeof(tdb_off_t));
-
-		if (rec_ptr != 0) {
-			rec.key_len = key.dsize;
-			rec.data_len = dbuf.dsize;
-			rec.full_hash = hash;
-			rec.magic = TDB_MAGIC;
-			if (tdb_rec_write(tdb, rec_ptr, &rec) == -1
-			    || tdb->methods->tdb_write(
-				    tdb, rec_ptr + sizeof(rec),
-				    key.dptr, key.dsize) == -1
-			    || tdb->methods->tdb_write(
-				    tdb, rec_ptr + sizeof(rec) + key.dsize,
-				    dbuf.dptr, dbuf.dsize) == -1) {
-				goto fail;
-			}
-			goto done;
-		}
-	}
-
-	/*
-	 * We have to allocate some space from the freelist, so this means we
-	 * have to lock it. Use the chance to purge all the DEAD records from
-	 * the hash chain under the freelist lock.
-	 */
-
-	if (tdb_lock(tdb, -1, F_WRLCK) == -1) {
-		goto fail;
-	}
-
-	if ((tdb->max_dead_records != 0)
-	    && (tdb_purge_dead(tdb, hash) == -1)) {
-		tdb_unlock(tdb, -1, F_WRLCK);
-		goto fail;
-	}
-
-	/* we have to allocate some space */
-	rec_ptr = tdb_allocate(tdb, key.dsize + dbuf.dsize, &rec);
-
-	tdb_unlock(tdb, -1, F_WRLCK);
-
-	if (rec_ptr == 0) {
-		goto fail;
-	}
-
-	/* Read hash top into next ptr */
-	if (tdb_ofs_read(tdb, TDB_HASH_TOP(hash), &rec.next) == -1)
-		goto fail;
-
-	rec.key_len = key.dsize;
-	rec.data_len = dbuf.dsize;
-	rec.full_hash = hash;
-	rec.magic = TDB_MAGIC;
-
-	/* write out and point the top of the hash chain at it */
-	if (tdb_rec_write(tdb, rec_ptr, &rec) == -1
-	    || tdb->methods->tdb_write(tdb, rec_ptr+sizeof(rec),
-				       key.dptr, key.dsize) == -1
-	    || tdb->methods->tdb_write(tdb, rec_ptr+sizeof(rec)+key.dsize,
-				       dbuf.dptr, dbuf.dsize) == -1
-	    || tdb_ofs_write(tdb, TDB_HASH_TOP(hash), &rec_ptr) == -1) {
-		/* Need to tdb_unallocate() here */
-		goto fail;
-	}
-
- done:
-	ret = 0;
- fail:
-	if (ret == 0) {
-		tdb_increment_seqnum(tdb);
-	}
-	return ret;
-}
-
-/* store an element in the database, replacing any existing element
-   with the same key
-
-   return 0 on success, -1 on failure
-*/
-_PUBLIC_ int tdb_store(struct tdb_context *tdb, TDB_DATA key, TDB_DATA dbuf, int flag)
-{
-	uint32_t hash;
-	int ret;
-
-	if (tdb->read_only || tdb->traverse_read) {
-		tdb->ecode = TDB_ERR_RDONLY;
-		tdb_trace_2rec_flag_ret(tdb, "tdb_store", key, dbuf, flag, -1);
-		return -1;
-	}
-
-	/* find which hash bucket it is in */
-	hash = tdb->hash_fn(&key);
-	if (tdb_lock(tdb, BUCKET(hash), F_WRLCK) == -1)
-		return -1;
-
-	ret = _tdb_store(tdb, key, dbuf, flag, hash);
-	tdb_trace_2rec_flag_ret(tdb, "tdb_store", key, dbuf, flag, ret);
-	tdb_unlock(tdb, BUCKET(hash), F_WRLCK);
-	return ret;
-}
-
-/* Append to an entry. Create if not exist. */
-_PUBLIC_ int tdb_append(struct tdb_context *tdb, TDB_DATA key, TDB_DATA new_dbuf)
-{
-	uint32_t hash;
-	TDB_DATA dbuf;
-	int ret = -1;
-
-	/* find which hash bucket it is in */
-	hash = tdb->hash_fn(&key);
-	if (tdb_lock(tdb, BUCKET(hash), F_WRLCK) == -1)
-		return -1;
-
-	dbuf = _tdb_fetch(tdb, key);
-
-	if (dbuf.dptr == NULL) {
-		dbuf.dptr = (unsigned char *)malloc(new_dbuf.dsize);
-	} else {
-		unsigned int new_len = dbuf.dsize + new_dbuf.dsize;
-		unsigned char *new_dptr;
-
-		/* realloc '0' is special: don't do that. */
-		if (new_len == 0)
-			new_len = 1;
-		new_dptr = (unsigned char *)realloc(dbuf.dptr, new_len);
-		if (new_dptr == NULL) {
-			free(dbuf.dptr);
-		}
-		dbuf.dptr = new_dptr;
-	}
-
-	if (dbuf.dptr == NULL) {
-		tdb->ecode = TDB_ERR_OOM;
-		goto failed;
-	}
-
-	memcpy(dbuf.dptr + dbuf.dsize, new_dbuf.dptr, new_dbuf.dsize);
-	dbuf.dsize += new_dbuf.dsize;
-
-	ret = _tdb_store(tdb, key, dbuf, 0, hash);
-	tdb_trace_2rec_retrec(tdb, "tdb_append", key, new_dbuf, dbuf);
-
-failed:
-	tdb_unlock(tdb, BUCKET(hash), F_WRLCK);
-	SAFE_FREE(dbuf.dptr);
-	return ret;
-}
-
-
-/*
-  return the name of the current tdb file
-  useful for external logging functions
-*/
-_PUBLIC_ const char *tdb_name(struct tdb_context *tdb)
-{
-	return tdb->name;
-}
-
-/*
-  return the underlying file descriptor being used by tdb, or -1
-  useful for external routines that want to check the device/inode
-  of the fd
-*/
-_PUBLIC_ int tdb_fd(struct tdb_context *tdb)
-{
-	return tdb->fd;
-}
-
-/*
-  return the current logging function
-  useful for external tdb routines that wish to log tdb errors
-*/
-_PUBLIC_ tdb_log_func tdb_log_fn(struct tdb_context *tdb)
-{
-	return tdb->log.log_fn;
-}
-
-
-/*
-  get the tdb sequence number. Only makes sense if the writers opened
-  with TDB_SEQNUM set. Note that this sequence number will wrap quite
-  quickly, so it should only be used for a 'has something changed'
-  test, not for code that relies on the count of the number of changes
-  made. If you want a counter then use a tdb record.
-
-  The aim of this sequence number is to allow for a very lightweight
-  test of a possible tdb change.
-*/
-_PUBLIC_ int tdb_get_seqnum(struct tdb_context *tdb)
-{
-	tdb_off_t seqnum=0;
-
-	tdb_ofs_read(tdb, TDB_SEQNUM_OFS, &seqnum);
-	return seqnum;
-}
-
-_PUBLIC_ int tdb_hash_size(struct tdb_context *tdb)
-{
-	return tdb->header.hash_size;
-}
-
-_PUBLIC_ size_t tdb_map_size(struct tdb_context *tdb)
-{
-	return tdb->map_size;
-}
-
-_PUBLIC_ int tdb_get_flags(struct tdb_context *tdb)
-{
-	return tdb->flags;
-}
-
-_PUBLIC_ void tdb_add_flags(struct tdb_context *tdb, unsigned flags)
-{
-	if ((flags & TDB_ALLOW_NESTING) &&
-	    (flags & TDB_DISALLOW_NESTING)) {
-		tdb->ecode = TDB_ERR_NESTING;
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_add_flags: "
-			"allow_nesting and disallow_nesting are not allowed together!"));
-		return;
-	}
-
-	if (flags & TDB_ALLOW_NESTING) {
-		tdb->flags &= ~TDB_DISALLOW_NESTING;
-	}
-	if (flags & TDB_DISALLOW_NESTING) {
-		tdb->flags &= ~TDB_ALLOW_NESTING;
-	}
-
-	tdb->flags |= flags;
-}
-
-_PUBLIC_ void tdb_remove_flags(struct tdb_context *tdb, unsigned flags)
-{
-	if ((flags & TDB_ALLOW_NESTING) &&
-	    (flags & TDB_DISALLOW_NESTING)) {
-		tdb->ecode = TDB_ERR_NESTING;
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_remove_flags: "
-			"allow_nesting and disallow_nesting are not allowed together!"));
-		return;
-	}
-
-	if (flags & TDB_ALLOW_NESTING) {
-		tdb->flags |= TDB_DISALLOW_NESTING;
-	}
-	if (flags & TDB_DISALLOW_NESTING) {
-		tdb->flags |= TDB_ALLOW_NESTING;
-	}
-
-	tdb->flags &= ~flags;
-}
-
-
-/*
-  enable sequence number handling on an open tdb
-*/
-_PUBLIC_ void tdb_enable_seqnum(struct tdb_context *tdb)
-{
-	tdb->flags |= TDB_SEQNUM;
-}
-
-
-/*
-  add a region of the file to the freelist. Length is the size of the region in bytes, 
-  which includes the free list header that needs to be added
- */
-static int tdb_free_region(struct tdb_context *tdb, tdb_off_t offset, ssize_t length)
-{
-	struct tdb_record rec;
-	if (length <= sizeof(rec)) {
-		/* the region is not worth adding */
-		return 0;
-	}
-	if (length + offset > tdb->map_size) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL,"tdb_free_region: adding region beyond end of file\n"));
-		return -1;		
-	}
-	memset(&rec,'\0',sizeof(rec));
-	rec.rec_len = length - sizeof(rec);
-	if (tdb_free(tdb, offset, &rec) == -1) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL,"tdb_free_region: failed to add free record\n"));
-		return -1;
-	}
-	return 0;
-}
-
-/*
-  wipe the entire database, deleting all records. This can be done
-  very fast by using a allrecord lock. The entire data portion of the
-  file becomes a single entry in the freelist.
-
-  This code carefully steps around the recovery area, leaving it alone
- */
-_PUBLIC_ int tdb_wipe_all(struct tdb_context *tdb)
-{
-	int i;
-	tdb_off_t offset = 0;
-	ssize_t data_len;
-	tdb_off_t recovery_head;
-	tdb_len_t recovery_size = 0;
-
-	if (tdb_lockall(tdb) != 0) {
-		return -1;
-	}
-
-	tdb_trace(tdb, "tdb_wipe_all");
-
-	/* see if the tdb has a recovery area, and remember its size
-	   if so. We don't want to lose this as otherwise each
-	   tdb_wipe_all() in a transaction will increase the size of
-	   the tdb by the size of the recovery area */
-	if (tdb_ofs_read(tdb, TDB_RECOVERY_HEAD, &recovery_head) == -1) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_wipe_all: failed to read recovery head\n"));
-		goto failed;
-	}
-
-	if (recovery_head != 0) {
-		struct tdb_record rec;
-		if (tdb->methods->tdb_read(tdb, recovery_head, &rec, sizeof(rec), DOCONV()) == -1) {
-			TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_wipe_all: failed to read recovery record\n"));
-			return -1;
-		}	
-		recovery_size = rec.rec_len + sizeof(rec);
-	}
-
-	/* wipe the hashes */
-	for (i=0;i<tdb->header.hash_size;i++) {
-		if (tdb_ofs_write(tdb, TDB_HASH_TOP(i), &offset) == -1) {
-			TDB_LOG((tdb, TDB_DEBUG_FATAL,"tdb_wipe_all: failed to write hash %d\n", i));
-			goto failed;
-		}
-	}
-
-	/* wipe the freelist */
-	if (tdb_ofs_write(tdb, FREELIST_TOP, &offset) == -1) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL,"tdb_wipe_all: failed to write freelist\n"));
-		goto failed;
-	}
-
-	/* add all the rest of the file to the freelist, possibly leaving a gap 
-	   for the recovery area */
-	if (recovery_size == 0) {
-		/* the simple case - the whole file can be used as a freelist */
-		data_len = (tdb->map_size - TDB_DATA_START(tdb->header.hash_size));
-		if (tdb_free_region(tdb, TDB_DATA_START(tdb->header.hash_size), data_len) != 0) {
-			goto failed;
-		}
-	} else {
-		/* we need to add two freelist entries - one on either
-		   side of the recovery area 
-
-		   Note that we cannot shift the recovery area during
-		   this operation. Only the transaction.c code may
-		   move the recovery area or we risk subtle data
-		   corruption
-		*/
-		data_len = (recovery_head - TDB_DATA_START(tdb->header.hash_size));
-		if (tdb_free_region(tdb, TDB_DATA_START(tdb->header.hash_size), data_len) != 0) {
-			goto failed;
-		}
-		/* and the 2nd free list entry after the recovery area - if any */
-		data_len = tdb->map_size - (recovery_head+recovery_size);
-		if (tdb_free_region(tdb, recovery_head+recovery_size, data_len) != 0) {
-			goto failed;
-		}
-	}
-
-	tdb_increment_seqnum_nonblock(tdb);
-
-	if (tdb_unlockall(tdb) != 0) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL,"tdb_wipe_all: failed to unlock\n"));
-		goto failed;
-	}
-
-	return 0;
-
-failed:
-	tdb_unlockall(tdb);
-	return -1;
-}
-
-struct traverse_state {
-	bool error;
-	struct tdb_context *dest_db;
-};
-
-/*
-  traverse function for repacking
- */
-static int repack_traverse(struct tdb_context *tdb, TDB_DATA key, TDB_DATA data, void *private_data)
-{
-	struct traverse_state *state = (struct traverse_state *)private_data;
-	if (tdb_store(state->dest_db, key, data, TDB_INSERT) != 0) {
-		state->error = true;
-		return -1;
-	}
-	return 0;
-}
-
-/*
-  repack a tdb
- */
-_PUBLIC_ int tdb_repack(struct tdb_context *tdb)
-{
-	struct tdb_context *tmp_db;
-	struct traverse_state state;
-
-	tdb_trace(tdb, "tdb_repack");
-
-	if (tdb_transaction_start(tdb) != 0) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, __location__ " Failed to start transaction\n"));
-		return -1;
-	}
-
-	tmp_db = tdb_open("tmpdb", tdb_hash_size(tdb), TDB_INTERNAL, O_RDWR|O_CREAT, 0);
-	if (tmp_db == NULL) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, __location__ " Failed to create tmp_db\n"));
-		tdb_transaction_cancel(tdb);
-		return -1;
-	}
-
-	state.error = false;
-	state.dest_db = tmp_db;
-
-	if (tdb_traverse_read(tdb, repack_traverse, &state) == -1) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, __location__ " Failed to traverse copying out\n"));
-		tdb_transaction_cancel(tdb);
-		tdb_close(tmp_db);
-		return -1;		
-	}
-
-	if (state.error) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, __location__ " Error during traversal\n"));
-		tdb_transaction_cancel(tdb);
-		tdb_close(tmp_db);
-		return -1;
-	}
-
-	if (tdb_wipe_all(tdb) != 0) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, __location__ " Failed to wipe database\n"));
-		tdb_transaction_cancel(tdb);
-		tdb_close(tmp_db);
-		return -1;
-	}
-
-	state.error = false;
-	state.dest_db = tdb;
-
-	if (tdb_traverse_read(tmp_db, repack_traverse, &state) == -1) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, __location__ " Failed to traverse copying back\n"));
-		tdb_transaction_cancel(tdb);
-		tdb_close(tmp_db);
-		return -1;		
-	}
-
-	if (state.error) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, __location__ " Error during second traversal\n"));
-		tdb_transaction_cancel(tdb);
-		tdb_close(tmp_db);
-		return -1;
-	}
-
-	tdb_close(tmp_db);
-
-	if (tdb_transaction_commit(tdb) != 0) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, __location__ " Failed to commit\n"));
-		return -1;
-	}
-
-	return 0;
-}
-
-/* Even on files, we can get partial writes due to signals. */
-bool tdb_write_all(int fd, const void *buf, size_t count)
-{
-	while (count) {
-		ssize_t ret;
-		ret = write(fd, buf, count);
-		if (ret < 0)
-			return false;
-		buf = (const char *)buf + ret;
-		count -= ret;
-	}
-	return true;
-}
-
-#ifdef TDB_TRACE
-static void tdb_trace_write(struct tdb_context *tdb, const char *str)
-{
-	if (!tdb_write_all(tdb->tracefd, str, strlen(str))) {
-		close(tdb->tracefd);
-		tdb->tracefd = -1;
-	}
-}
-
-static void tdb_trace_start(struct tdb_context *tdb)
-{
-	tdb_off_t seqnum=0;
-	char msg[sizeof(tdb_off_t) * 4 + 1];
-
-	tdb_ofs_read(tdb, TDB_SEQNUM_OFS, &seqnum);
-	snprintf(msg, sizeof(msg), "%u ", seqnum);
-	tdb_trace_write(tdb, msg);
-}
-
-static void tdb_trace_end(struct tdb_context *tdb)
-{
-	tdb_trace_write(tdb, "\n");
-}
-
-static void tdb_trace_end_ret(struct tdb_context *tdb, int ret)
-{
-	char msg[sizeof(ret) * 4 + 4];
-	snprintf(msg, sizeof(msg), " = %i\n", ret);
-	tdb_trace_write(tdb, msg);
-}
-
-static void tdb_trace_record(struct tdb_context *tdb, TDB_DATA rec)
-{
-	char msg[20 + rec.dsize*2], *p;
-	unsigned int i;
-
-	/* We differentiate zero-length records from non-existent ones. */
-	if (rec.dptr == NULL) {
-		tdb_trace_write(tdb, " NULL");
-		return;
-	}
-
-	/* snprintf here is purely cargo-cult programming. */
-	p = msg;
-	p += snprintf(p, sizeof(msg), " %zu:", rec.dsize);
-	for (i = 0; i < rec.dsize; i++)
-		p += snprintf(p, 2, "%02x", rec.dptr[i]);
-
-	tdb_trace_write(tdb, msg);
-}
-
-void tdb_trace(struct tdb_context *tdb, const char *op)
-{
-	tdb_trace_start(tdb);
-	tdb_trace_write(tdb, op);
-	tdb_trace_end(tdb);
-}
-
-void tdb_trace_seqnum(struct tdb_context *tdb, uint32_t seqnum, const char *op)
-{
-	char msg[sizeof(tdb_off_t) * 4 + 1];
-
-	snprintf(msg, sizeof(msg), "%u ", seqnum);
-	tdb_trace_write(tdb, msg);
-	tdb_trace_write(tdb, op);
-	tdb_trace_end(tdb);
-}
-
-void tdb_trace_open(struct tdb_context *tdb, const char *op,
-		    unsigned hash_size, unsigned tdb_flags, unsigned open_flags)
-{
-	char msg[128];
-
-	snprintf(msg, sizeof(msg),
-		 "%s %u 0x%x 0x%x", op, hash_size, tdb_flags, open_flags);
-	tdb_trace_start(tdb);
-	tdb_trace_write(tdb, msg);
-	tdb_trace_end(tdb);
-}
-
-void tdb_trace_ret(struct tdb_context *tdb, const char *op, int ret)
-{
-	tdb_trace_start(tdb);
-	tdb_trace_write(tdb, op);
-	tdb_trace_end_ret(tdb, ret);
-}
-
-void tdb_trace_retrec(struct tdb_context *tdb, const char *op, TDB_DATA ret)
-{
-	tdb_trace_start(tdb);
-	tdb_trace_write(tdb, op);
-	tdb_trace_write(tdb, " =");
-	tdb_trace_record(tdb, ret);
-	tdb_trace_end(tdb);
-}
-
-void tdb_trace_1rec(struct tdb_context *tdb, const char *op,
-		    TDB_DATA rec)
-{
-	tdb_trace_start(tdb);
-	tdb_trace_write(tdb, op);
-	tdb_trace_record(tdb, rec);
-	tdb_trace_end(tdb);
-}
-
-void tdb_trace_1rec_ret(struct tdb_context *tdb, const char *op,
-			TDB_DATA rec, int ret)
-{
-	tdb_trace_start(tdb);
-	tdb_trace_write(tdb, op);
-	tdb_trace_record(tdb, rec);
-	tdb_trace_end_ret(tdb, ret);
-}
-
-void tdb_trace_1rec_retrec(struct tdb_context *tdb, const char *op,
-			   TDB_DATA rec, TDB_DATA ret)
-{
-	tdb_trace_start(tdb);
-	tdb_trace_write(tdb, op);
-	tdb_trace_record(tdb, rec);
-	tdb_trace_write(tdb, " =");
-	tdb_trace_record(tdb, ret);
-	tdb_trace_end(tdb);
-}
-
-void tdb_trace_2rec_flag_ret(struct tdb_context *tdb, const char *op,
-			     TDB_DATA rec1, TDB_DATA rec2, unsigned flag,
-			     int ret)
-{
-	char msg[1 + sizeof(ret) * 4];
-
-	snprintf(msg, sizeof(msg), " %#x", flag);
-	tdb_trace_start(tdb);
-	tdb_trace_write(tdb, op);
-	tdb_trace_record(tdb, rec1);
-	tdb_trace_record(tdb, rec2);
-	tdb_trace_write(tdb, msg);
-	tdb_trace_end_ret(tdb, ret);
-}
-
-void tdb_trace_2rec_retrec(struct tdb_context *tdb, const char *op,
-			   TDB_DATA rec1, TDB_DATA rec2, TDB_DATA ret)
-{
-	tdb_trace_start(tdb);
-	tdb_trace_write(tdb, op);
-	tdb_trace_record(tdb, rec1);
-	tdb_trace_record(tdb, rec2);
-	tdb_trace_write(tdb, " =");
-	tdb_trace_record(tdb, ret);
-	tdb_trace_end(tdb);
-}
-#endif
diff --git a/lib/tdb/common/tdb_private.h b/lib/tdb/common/tdb_private.h
deleted file mode 100644
index 0441fb2..0000000
--- a/lib/tdb/common/tdb_private.h
+++ /dev/null
@@ -1,285 +0,0 @@
-#ifndef TDB_PRIVATE_H
-#define TDB_PRIVATE_H
- /* 
-   Unix SMB/CIFS implementation.
-
-   trivial database library - private includes
-
-   Copyright (C) Andrew Tridgell              2005
-
-     ** NOTE! The following LGPL license applies to the tdb
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-
-#include "replace.h"
-#include "system/filesys.h"
-#include "system/time.h"
-#include "system/shmem.h"
-#include "system/select.h"
-#include "system/wait.h"
-#include "tdb.h"
-
-/* #define TDB_TRACE 1 */
-#ifndef HAVE_GETPAGESIZE
-#define getpagesize() 0x2000
-#endif
-
-typedef uint32_t tdb_len_t;
-typedef uint32_t tdb_off_t;
-
-#ifndef offsetof
-#define offsetof(t,f) ((unsigned int)&((t *)0)->f)
-#endif
-
-#define TDB_MAGIC_FOOD "TDB file\n"
-#define TDB_VERSION (0x26011967 + 6)
-#define TDB_MAGIC (0x26011999U)
-#define TDB_FREE_MAGIC (~TDB_MAGIC)
-#define TDB_DEAD_MAGIC (0xFEE1DEAD)
-#define TDB_RECOVERY_MAGIC (0xf53bc0e7U)
-#define TDB_RECOVERY_INVALID_MAGIC (0x0)
-#define TDB_HASH_RWLOCK_MAGIC (0xbad1a51U)
-#define TDB_ALIGNMENT 4
-#define DEFAULT_HASH_SIZE 131
-#define FREELIST_TOP (sizeof(struct tdb_header))
-#define TDB_ALIGN(x,a) (((x) + (a)-1) & ~((a)-1))
-#define TDB_BYTEREV(x) (((((x)&0xff)<<24)|((x)&0xFF00)<<8)|(((x)>>8)&0xFF00)|((x)>>24))
-#define TDB_DEAD(r) ((r)->magic == TDB_DEAD_MAGIC)
-#define TDB_BAD_MAGIC(r) ((r)->magic != TDB_MAGIC && !TDB_DEAD(r))
-#define TDB_HASH_TOP(hash) (FREELIST_TOP + (BUCKET(hash)+1)*sizeof(tdb_off_t))
-#define TDB_HASHTABLE_SIZE(tdb) ((tdb->header.hash_size+1)*sizeof(tdb_off_t))
-#define TDB_DATA_START(hash_size) (TDB_HASH_TOP(hash_size-1) + sizeof(tdb_off_t))
-#define TDB_RECOVERY_HEAD offsetof(struct tdb_header, recovery_start)
-#define TDB_SEQNUM_OFS    offsetof(struct tdb_header, sequence_number)
-#define TDB_PAD_BYTE 0x42
-#define TDB_PAD_U32  0x42424242
-
-/* NB assumes there is a local variable called "tdb" that is the
- * current context, also takes doubly-parenthesized print-style
- * argument. */
-#define TDB_LOG(x) tdb->log.log_fn x
-
-#ifdef TDB_TRACE
-void tdb_trace(struct tdb_context *tdb, const char *op);
-void tdb_trace_seqnum(struct tdb_context *tdb, uint32_t seqnum, const char *op);
-void tdb_trace_open(struct tdb_context *tdb, const char *op,
-		    unsigned hash_size, unsigned tdb_flags, unsigned open_flags);
-void tdb_trace_ret(struct tdb_context *tdb, const char *op, int ret);
-void tdb_trace_retrec(struct tdb_context *tdb, const char *op, TDB_DATA ret);
-void tdb_trace_1rec(struct tdb_context *tdb, const char *op,
-		    TDB_DATA rec);
-void tdb_trace_1rec_ret(struct tdb_context *tdb, const char *op,
-			TDB_DATA rec, int ret);
-void tdb_trace_1rec_retrec(struct tdb_context *tdb, const char *op,
-			   TDB_DATA rec, TDB_DATA ret);
-void tdb_trace_2rec_flag_ret(struct tdb_context *tdb, const char *op,
-			     TDB_DATA rec1, TDB_DATA rec2, unsigned flag,
-			     int ret);
-void tdb_trace_2rec_retrec(struct tdb_context *tdb, const char *op,
-			   TDB_DATA rec1, TDB_DATA rec2, TDB_DATA ret);
-#else
-#define tdb_trace(tdb, op)
-#define tdb_trace_seqnum(tdb, seqnum, op)
-#define tdb_trace_open(tdb, op, hash_size, tdb_flags, open_flags)
-#define tdb_trace_ret(tdb, op, ret)
-#define tdb_trace_retrec(tdb, op, ret)
-#define tdb_trace_1rec(tdb, op, rec)
-#define tdb_trace_1rec_ret(tdb, op, rec, ret)
-#define tdb_trace_1rec_retrec(tdb, op, rec, ret)
-#define tdb_trace_2rec_flag_ret(tdb, op, rec1, rec2, flag, ret)
-#define tdb_trace_2rec_retrec(tdb, op, rec1, rec2, ret)
-#endif /* !TDB_TRACE */
-
-/* lock offsets */
-#define OPEN_LOCK        0
-#define ACTIVE_LOCK      4
-#define TRANSACTION_LOCK 8
-
-/* free memory if the pointer is valid and zero the pointer */
-#ifndef SAFE_FREE
-#define SAFE_FREE(x) do { if ((x) != NULL) {free(x); (x)=NULL;} } while(0)
-#endif
-
-#define BUCKET(hash) ((hash) % tdb->header.hash_size)
-
-#define DOCONV() (tdb->flags & TDB_CONVERT)
-#define CONVERT(x) (DOCONV() ? tdb_convert(&x, sizeof(x)) : &x)
-
-
-/* the body of the database is made of one tdb_record for the free space
-   plus a separate data list for each hash value */
-struct tdb_record {
-	tdb_off_t next; /* offset of the next record in the list */
-	tdb_len_t rec_len; /* total byte length of record */
-	tdb_len_t key_len; /* byte length of key */
-	tdb_len_t data_len; /* byte length of data */
-	uint32_t full_hash; /* the full 32 bit hash of the key */
-	uint32_t magic;   /* try to catch errors */
-	/* the following union is implied:
-		union {
-			char record[rec_len];
-			struct {
-				char key[key_len];
-				char data[data_len];
-			}
-			uint32_t totalsize; (tailer)
-		}
-	*/
-};
-
-
-/* this is stored at the front of every database */
-struct tdb_header {
-	char magic_food[32]; /* for /etc/magic */
-	uint32_t version; /* version of the code */
-	uint32_t hash_size; /* number of hash entries */
-	tdb_off_t rwlocks; /* obsolete - kept to detect old formats */
-	tdb_off_t recovery_start; /* offset of transaction recovery region */
-	tdb_off_t sequence_number; /* used when TDB_SEQNUM is set */
-	uint32_t magic1_hash; /* hash of TDB_MAGIC_FOOD. */
-	uint32_t magic2_hash; /* hash of TDB_MAGIC. */
-	tdb_off_t reserved[27];
-};
-
-struct tdb_lock_type {
-	uint32_t off;
-	uint32_t count;
-	uint32_t ltype;
-};
-
-struct tdb_traverse_lock {
-	struct tdb_traverse_lock *next;
-	uint32_t off;
-	uint32_t hash;
-	int lock_rw;
-};
-
-enum tdb_lock_flags {
-	/* WAIT == F_SETLKW, NOWAIT == F_SETLK */
-	TDB_LOCK_NOWAIT = 0,
-	TDB_LOCK_WAIT = 1,
-	/* If set, don't log an error on failure. */
-	TDB_LOCK_PROBE = 2,
-	/* If set, don't actually lock at all. */
-	TDB_LOCK_MARK_ONLY = 4,
-};
-
-struct tdb_methods {
-	int (*tdb_read)(struct tdb_context *, tdb_off_t , void *, tdb_len_t , int );
-	int (*tdb_write)(struct tdb_context *, tdb_off_t, const void *, tdb_len_t);
-	void (*next_hash_chain)(struct tdb_context *, uint32_t *);
-	int (*tdb_oob)(struct tdb_context *, tdb_off_t , tdb_len_t, int );
-	int (*tdb_expand_file)(struct tdb_context *, tdb_off_t , tdb_off_t );
-};
-
-struct tdb_context {
-	char *name; /* the name of the database */
-	void *map_ptr; /* where it is currently mapped */
-	int fd; /* open file descriptor for the database */
-	tdb_len_t map_size; /* how much space has been mapped */
-	int read_only; /* opened read-only */
-	int traverse_read; /* read-only traversal */
-	int traverse_write; /* read-write traversal */
-	struct tdb_lock_type allrecord_lock; /* .offset == upgradable */
-	int num_lockrecs;
-	struct tdb_lock_type *lockrecs; /* only real locks, all with count>0 */
-	enum TDB_ERROR ecode; /* error code for last tdb error */
-	struct tdb_header header; /* a cached copy of the header */
-	uint32_t flags; /* the flags passed to tdb_open */
-	struct tdb_traverse_lock travlocks; /* current traversal locks */
-	struct tdb_context *next; /* all tdbs to avoid multiple opens */
-	dev_t device;	/* uniquely identifies this tdb */
-	ino_t inode;	/* uniquely identifies this tdb */
-	struct tdb_logging_context log;
-	unsigned int (*hash_fn)(TDB_DATA *key);
-	int open_flags; /* flags used in the open - needed by reopen */
-	const struct tdb_methods *methods;
-	struct tdb_transaction *transaction;
-	int page_size;
-	int max_dead_records;
-#ifdef TDB_TRACE
-	int tracefd;
-#endif
-	volatile sig_atomic_t *interrupt_sig_ptr;
-};
-
-
-/*
-  internal prototypes
-*/
-int tdb_munmap(struct tdb_context *tdb);
-int tdb_mmap(struct tdb_context *tdb);
-int tdb_lock(struct tdb_context *tdb, int list, int ltype);
-int tdb_lock_nonblock(struct tdb_context *tdb, int list, int ltype);
-int tdb_nest_lock(struct tdb_context *tdb, uint32_t offset, int ltype,
-		  enum tdb_lock_flags flags);
-int tdb_nest_unlock(struct tdb_context *tdb, uint32_t offset, int ltype,
-		    bool mark_lock);
-int tdb_unlock(struct tdb_context *tdb, int list, int ltype);
-int tdb_brlock(struct tdb_context *tdb,
-	       int rw_type, tdb_off_t offset, size_t len,
-	       enum tdb_lock_flags flags);
-int tdb_brunlock(struct tdb_context *tdb,
-		 int rw_type, tdb_off_t offset, size_t len);
-bool tdb_have_extra_locks(struct tdb_context *tdb);
-void tdb_release_transaction_locks(struct tdb_context *tdb);
-int tdb_transaction_lock(struct tdb_context *tdb, int ltype,
-			 enum tdb_lock_flags lockflags);
-int tdb_transaction_unlock(struct tdb_context *tdb, int ltype);
-int tdb_recovery_area(struct tdb_context *tdb,
-		      const struct tdb_methods *methods,
-		      tdb_off_t *recovery_offset,
-		      struct tdb_record *rec);
-int tdb_allrecord_lock(struct tdb_context *tdb, int ltype,
-		       enum tdb_lock_flags flags, bool upgradable);
-int tdb_allrecord_unlock(struct tdb_context *tdb, int ltype, bool mark_lock);
-int tdb_allrecord_upgrade(struct tdb_context *tdb);
-int tdb_write_lock_record(struct tdb_context *tdb, tdb_off_t off);
-int tdb_write_unlock_record(struct tdb_context *tdb, tdb_off_t off);
-int tdb_ofs_read(struct tdb_context *tdb, tdb_off_t offset, tdb_off_t *d);
-int tdb_ofs_write(struct tdb_context *tdb, tdb_off_t offset, tdb_off_t *d);
-void *tdb_convert(void *buf, uint32_t size);
-int tdb_free(struct tdb_context *tdb, tdb_off_t offset, struct tdb_record *rec);
-tdb_off_t tdb_allocate(struct tdb_context *tdb, tdb_len_t length, struct tdb_record *rec);
-int tdb_ofs_read(struct tdb_context *tdb, tdb_off_t offset, tdb_off_t *d);
-int tdb_ofs_write(struct tdb_context *tdb, tdb_off_t offset, tdb_off_t *d);
-int tdb_lock_record(struct tdb_context *tdb, tdb_off_t off);
-int tdb_unlock_record(struct tdb_context *tdb, tdb_off_t off);
-bool tdb_needs_recovery(struct tdb_context *tdb);
-int tdb_rec_read(struct tdb_context *tdb, tdb_off_t offset, struct tdb_record *rec);
-int tdb_rec_write(struct tdb_context *tdb, tdb_off_t offset, struct tdb_record *rec);
-int tdb_do_delete(struct tdb_context *tdb, tdb_off_t rec_ptr, struct tdb_record *rec);
-unsigned char *tdb_alloc_read(struct tdb_context *tdb, tdb_off_t offset, tdb_len_t len);
-int tdb_parse_data(struct tdb_context *tdb, TDB_DATA key,
-		   tdb_off_t offset, tdb_len_t len,
-		   int (*parser)(TDB_DATA key, TDB_DATA data,
-				 void *private_data),
-		   void *private_data);
-tdb_off_t tdb_find_lock_hash(struct tdb_context *tdb, TDB_DATA key, uint32_t hash, int locktype,
-			   struct tdb_record *rec);
-void tdb_io_init(struct tdb_context *tdb);
-int tdb_expand(struct tdb_context *tdb, tdb_off_t size);
-tdb_off_t tdb_expand_adjust(tdb_off_t map_size, tdb_off_t size, int page_size);
-int tdb_rec_free_read(struct tdb_context *tdb, tdb_off_t off,
-		      struct tdb_record *rec);
-bool tdb_write_all(int fd, const void *buf, size_t count);
-int tdb_transaction_recover(struct tdb_context *tdb);
-void tdb_header_hash(struct tdb_context *tdb,
-		     uint32_t *magic1_hash, uint32_t *magic2_hash);
-unsigned int tdb_old_hash(TDB_DATA *key);
-size_t tdb_dead_space(struct tdb_context *tdb, tdb_off_t off);
-#endif /* TDB_PRIVATE_H */
diff --git a/lib/tdb/common/transaction.c b/lib/tdb/common/transaction.c
deleted file mode 100644
index c3477eb..0000000
--- a/lib/tdb/common/transaction.c
+++ /dev/null
@@ -1,1295 +0,0 @@
- /* 
-   Unix SMB/CIFS implementation.
-
-   trivial database library
-
-   Copyright (C) Andrew Tridgell              2005
-
-     ** NOTE! The following LGPL license applies to the tdb
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-
-#include "tdb_private.h"
-
-/*
-  transaction design:
-
-  - only allow a single transaction at a time per database. This makes
-    using the transaction API simpler, as otherwise the caller would
-    have to cope with temporary failures in transactions that conflict
-    with other current transactions
-
-  - keep the transaction recovery information in the same file as the
-    database, using a special 'transaction recovery' record pointed at
-    by the header. This removes the need for extra journal files as
-    used by some other databases
-
-  - dynamically allocated the transaction recover record, re-using it
-    for subsequent transactions. If a larger record is needed then
-    tdb_free() the old record to place it on the normal tdb freelist
-    before allocating the new record
-
-  - during transactions, keep a linked list of writes all that have
-    been performed by intercepting all tdb_write() calls. The hooked
-    transaction versions of tdb_read() and tdb_write() check this
-    linked list and try to use the elements of the list in preference
-    to the real database.
-
-  - don't allow any locks to be held when a transaction starts,
-    otherwise we can end up with deadlock (plus lack of lock nesting
-    in posix locks would mean the lock is lost)
-
-  - if the caller gains a lock during the transaction but doesn't
-    release it then fail the commit
-
-  - allow for nested calls to tdb_transaction_start(), re-using the
-    existing transaction record. If the inner transaction is cancelled
-    then a subsequent commit will fail
-
-  - keep a mirrored copy of the tdb hash chain heads to allow for the
-    fast hash heads scan on traverse, updating the mirrored copy in
-    the transaction version of tdb_write
-
-  - allow callers to mix transaction and non-transaction use of tdb,
-    although once a transaction is started then an exclusive lock is
-    gained until the transaction is committed or cancelled
-
-  - the commit stategy involves first saving away all modified data
-    into a linearised buffer in the transaction recovery area, then
-    marking the transaction recovery area with a magic value to
-    indicate a valid recovery record. In total 4 fsync/msync calls are
-    needed per commit to prevent race conditions. It might be possible
-    to reduce this to 3 or even 2 with some more work.
-
-  - check for a valid recovery record on open of the tdb, while the
-    open lock is held. Automatically recover from the transaction
-    recovery area if needed, then continue with the open as
-    usual. This allows for smooth crash recovery with no administrator
-    intervention.
-
-  - if TDB_NOSYNC is passed to flags in tdb_open then transactions are
-    still available, but no transaction recovery area is used and no
-    fsync/msync calls are made.
-
-  - if TDB_ALLOW_NESTING is passed to flags in tdb open, or added using
-    tdb_add_flags() transaction nesting is enabled.
-    It resets the TDB_DISALLOW_NESTING flag, as both cannot be used together.
-    The default is that transaction nesting is allowed.
-    Note: this default may change in future versions of tdb.
-
-    Beware. when transactions are nested a transaction successfully
-    completed with tdb_transaction_commit() can be silently unrolled later.
-
-  - if TDB_DISALLOW_NESTING is passed to flags in tdb open, or added using
-    tdb_add_flags() transaction nesting is disabled.
-    It resets the TDB_ALLOW_NESTING flag, as both cannot be used together.
-    An attempt create a nested transaction will fail with TDB_ERR_NESTING.
-    The default is that transaction nesting is allowed.
-    Note: this default may change in future versions of tdb.
-*/
-
-
-/*
-  hold the context of any current transaction
-*/
-struct tdb_transaction {
-	/* we keep a mirrored copy of the tdb hash heads here so
-	   tdb_next_hash_chain() can operate efficiently */
-	uint32_t *hash_heads;
-
-	/* the original io methods - used to do IOs to the real db */
-	const struct tdb_methods *io_methods;
-
-	/* the list of transaction blocks. When a block is first
-	   written to, it gets created in this list */
-	uint8_t **blocks;
-	uint32_t num_blocks;
-	uint32_t block_size;      /* bytes in each block */
-	uint32_t last_block_size; /* number of valid bytes in the last block */
-
-	/* non-zero when an internal transaction error has
-	   occurred. All write operations will then fail until the
-	   transaction is ended */
-	int transaction_error;
-
-	/* when inside a transaction we need to keep track of any
-	   nested tdb_transaction_start() calls, as these are allowed,
-	   but don't create a new transaction */
-	int nesting;
-
-	/* set when a prepare has already occurred */
-	bool prepared;
-	tdb_off_t magic_offset;
-
-	/* old file size before transaction */
-	tdb_len_t old_map_size;
-
-	/* did we expand in this transaction */
-	bool expanded;
-};
-
-
-/*
-  read while in a transaction. We need to check first if the data is in our list
-  of transaction elements, then if not do a real read
-*/
-static int transaction_read(struct tdb_context *tdb, tdb_off_t off, void *buf, 
-			    tdb_len_t len, int cv)
-{
-	uint32_t blk;
-
-	/* break it down into block sized ops */
-	while (len + (off % tdb->transaction->block_size) > tdb->transaction->block_size) {
-		tdb_len_t len2 = tdb->transaction->block_size - (off % tdb->transaction->block_size);
-		if (transaction_read(tdb, off, buf, len2, cv) != 0) {
-			return -1;
-		}
-		len -= len2;
-		off += len2;
-		buf = (void *)(len2 + (char *)buf);
-	}
-
-	if (len == 0) {
-		return 0;
-	}
-
-	blk = off / tdb->transaction->block_size;
-
-	/* see if we have it in the block list */
-	if (tdb->transaction->num_blocks <= blk ||
-	    tdb->transaction->blocks[blk] == NULL) {
-		/* nope, do a real read */
-		if (tdb->transaction->io_methods->tdb_read(tdb, off, buf, len, cv) != 0) {
-			goto fail;
-		}
-		return 0;
-	}
-
-	/* it is in the block list. Now check for the last block */
-	if (blk == tdb->transaction->num_blocks-1) {
-		if (len > tdb->transaction->last_block_size) {
-			goto fail;
-		}
-	}
-
-	/* now copy it out of this block */
-	memcpy(buf, tdb->transaction->blocks[blk] + (off % tdb->transaction->block_size), len);
-	if (cv) {
-		tdb_convert(buf, len);
-	}
-	return 0;
-
-fail:
-	TDB_LOG((tdb, TDB_DEBUG_FATAL, "transaction_read: failed at off=%d len=%d\n", off, len));
-	tdb->ecode = TDB_ERR_IO;
-	tdb->transaction->transaction_error = 1;
-	return -1;
-}
-
-
-/*
-  write while in a transaction
-*/
-static int transaction_write(struct tdb_context *tdb, tdb_off_t off, 
-			     const void *buf, tdb_len_t len)
-{
-	uint32_t blk;
-
-	/* Only a commit is allowed on a prepared transaction */
-	if (tdb->transaction->prepared) {
-		tdb->ecode = TDB_ERR_EINVAL;
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "transaction_write: transaction already prepared, write not allowed\n"));
-		tdb->transaction->transaction_error = 1;
-		return -1;
-	}
-
-	/* if the write is to a hash head, then update the transaction
-	   hash heads */
-	if (len == sizeof(tdb_off_t) && off >= FREELIST_TOP &&
-	    off < FREELIST_TOP+TDB_HASHTABLE_SIZE(tdb)) {
-		uint32_t chain = (off-FREELIST_TOP) / sizeof(tdb_off_t);
-		memcpy(&tdb->transaction->hash_heads[chain], buf, len);
-	}
-
-	/* break it up into block sized chunks */
-	while (len + (off % tdb->transaction->block_size) > tdb->transaction->block_size) {
-		tdb_len_t len2 = tdb->transaction->block_size - (off % tdb->transaction->block_size);
-		if (transaction_write(tdb, off, buf, len2) != 0) {
-			return -1;
-		}
-		len -= len2;
-		off += len2;
-		if (buf != NULL) {
-			buf = (const void *)(len2 + (const char *)buf);
-		}
-	}
-
-	if (len == 0) {
-		return 0;
-	}
-
-	blk = off / tdb->transaction->block_size;
-	off = off % tdb->transaction->block_size;
-
-	if (tdb->transaction->num_blocks <= blk) {
-		uint8_t **new_blocks;
-		/* expand the blocks array */
-		if (tdb->transaction->blocks == NULL) {
-			new_blocks = (uint8_t **)malloc(
-				(blk+1)*sizeof(uint8_t *));
-		} else {
-			new_blocks = (uint8_t **)realloc(
-				tdb->transaction->blocks,
-				(blk+1)*sizeof(uint8_t *));
-		}
-		if (new_blocks == NULL) {
-			tdb->ecode = TDB_ERR_OOM;
-			goto fail;
-		}
-		memset(&new_blocks[tdb->transaction->num_blocks], 0, 
-		       (1+(blk - tdb->transaction->num_blocks))*sizeof(uint8_t *));
-		tdb->transaction->blocks = new_blocks;
-		tdb->transaction->num_blocks = blk+1;
-		tdb->transaction->last_block_size = 0;
-	}
-
-	/* allocate and fill a block? */
-	if (tdb->transaction->blocks[blk] == NULL) {
-		tdb->transaction->blocks[blk] = (uint8_t *)calloc(tdb->transaction->block_size, 1);
-		if (tdb->transaction->blocks[blk] == NULL) {
-			tdb->ecode = TDB_ERR_OOM;
-			tdb->transaction->transaction_error = 1;
-			return -1;			
-		}
-		if (tdb->transaction->old_map_size > blk * tdb->transaction->block_size) {
-			tdb_len_t len2 = tdb->transaction->block_size;
-			if (len2 + (blk * tdb->transaction->block_size) > tdb->transaction->old_map_size) {
-				len2 = tdb->transaction->old_map_size - (blk * tdb->transaction->block_size);
-			}
-			if (tdb->transaction->io_methods->tdb_read(tdb, blk * tdb->transaction->block_size, 
-								   tdb->transaction->blocks[blk], 
-								   len2, 0) != 0) {
-				SAFE_FREE(tdb->transaction->blocks[blk]);				
-				tdb->ecode = TDB_ERR_IO;
-				goto fail;
-			}
-			if (blk == tdb->transaction->num_blocks-1) {
-				tdb->transaction->last_block_size = len2;
-			}			
-		}
-	}
-
-	/* overwrite part of an existing block */
-	if (buf == NULL) {
-		memset(tdb->transaction->blocks[blk] + off, 0, len);
-	} else {
-		memcpy(tdb->transaction->blocks[blk] + off, buf, len);
-	}
-	if (blk == tdb->transaction->num_blocks-1) {
-		if (len + off > tdb->transaction->last_block_size) {
-			tdb->transaction->last_block_size = len + off;
-		}
-	}
-
-	return 0;
-
-fail:
-	TDB_LOG((tdb, TDB_DEBUG_FATAL, "transaction_write: failed at off=%d len=%d\n", 
-		 (blk*tdb->transaction->block_size) + off, len));
-	tdb->transaction->transaction_error = 1;
-	return -1;
-}
-
-
-/*
-  write while in a transaction - this varient never expands the transaction blocks, it only
-  updates existing blocks. This means it cannot change the recovery size
-*/
-static int transaction_write_existing(struct tdb_context *tdb, tdb_off_t off, 
-				      const void *buf, tdb_len_t len)
-{
-	uint32_t blk;
-
-	/* break it up into block sized chunks */
-	while (len + (off % tdb->transaction->block_size) > tdb->transaction->block_size) {
-		tdb_len_t len2 = tdb->transaction->block_size - (off % tdb->transaction->block_size);
-		if (transaction_write_existing(tdb, off, buf, len2) != 0) {
-			return -1;
-		}
-		len -= len2;
-		off += len2;
-		if (buf != NULL) {
-			buf = (const void *)(len2 + (const char *)buf);
-		}
-	}
-
-	if (len == 0) {
-		return 0;
-	}
-
-	blk = off / tdb->transaction->block_size;
-	off = off % tdb->transaction->block_size;
-
-	if (tdb->transaction->num_blocks <= blk ||
-	    tdb->transaction->blocks[blk] == NULL) {
-		return 0;
-	}
-
-	if (blk == tdb->transaction->num_blocks-1 &&
-	    off + len > tdb->transaction->last_block_size) {
-		if (off >= tdb->transaction->last_block_size) {
-			return 0;
-		}
-		len = tdb->transaction->last_block_size - off;
-	}
-
-	/* overwrite part of an existing block */
-	memcpy(tdb->transaction->blocks[blk] + off, buf, len);
-
-	return 0;
-}
-
-
-/*
-  accelerated hash chain head search, using the cached hash heads
-*/
-static void transaction_next_hash_chain(struct tdb_context *tdb, uint32_t *chain)
-{
-	uint32_t h = *chain;
-	for (;h < tdb->header.hash_size;h++) {
-		/* the +1 takes account of the freelist */
-		if (0 != tdb->transaction->hash_heads[h+1]) {
-			break;
-		}
-	}
-	(*chain) = h;
-}
-
-/*
-  out of bounds check during a transaction
-*/
-static int transaction_oob(struct tdb_context *tdb, tdb_off_t off,
-			   tdb_len_t len, int probe)
-{
-	if (off + len >= off && off + len <= tdb->map_size) {
-		return 0;
-	}
-	tdb->ecode = TDB_ERR_IO;
-	return -1;
-}
-
-/*
-  transaction version of tdb_expand().
-*/
-static int transaction_expand_file(struct tdb_context *tdb, tdb_off_t size, 
-				   tdb_off_t addition)
-{
-	/* add a write to the transaction elements, so subsequent
-	   reads see the zero data */
-	if (transaction_write(tdb, size, NULL, addition) != 0) {
-		return -1;
-	}
-
-	tdb->transaction->expanded = true;
-
-	return 0;
-}
-
-static const struct tdb_methods transaction_methods = {
-	transaction_read,
-	transaction_write,
-	transaction_next_hash_chain,
-	transaction_oob,
-	transaction_expand_file,
-};
-
-
-/*
-  start a tdb transaction. No token is returned, as only a single
-  transaction is allowed to be pending per tdb_context
-*/
-static int _tdb_transaction_start(struct tdb_context *tdb,
-				  enum tdb_lock_flags lockflags)
-{
-	/* some sanity checks */
-	if (tdb->read_only || (tdb->flags & TDB_INTERNAL) || tdb->traverse_read) {
-		TDB_LOG((tdb, TDB_DEBUG_ERROR, "tdb_transaction_start: cannot start a transaction on a read-only or internal db\n"));
-		tdb->ecode = TDB_ERR_EINVAL;
-		return -1;
-	}
-
-	/* cope with nested tdb_transaction_start() calls */
-	if (tdb->transaction != NULL) {
-		if (!(tdb->flags & TDB_ALLOW_NESTING)) {
-			tdb->ecode = TDB_ERR_NESTING;
-			return -1;
-		}
-		tdb->transaction->nesting++;
-		TDB_LOG((tdb, TDB_DEBUG_TRACE, "tdb_transaction_start: nesting %d\n", 
-			 tdb->transaction->nesting));
-		return 0;
-	}
-
-	if (tdb_have_extra_locks(tdb)) {
-		/* the caller must not have any locks when starting a
-		   transaction as otherwise we'll be screwed by lack
-		   of nested locks in posix */
-		TDB_LOG((tdb, TDB_DEBUG_ERROR, "tdb_transaction_start: cannot start a transaction with locks held\n"));
-		tdb->ecode = TDB_ERR_LOCK;
-		return -1;
-	}
-
-	if (tdb->travlocks.next != NULL) {
-		/* you cannot use transactions inside a traverse (although you can use
-		   traverse inside a transaction) as otherwise you can end up with
-		   deadlock */
-		TDB_LOG((tdb, TDB_DEBUG_ERROR, "tdb_transaction_start: cannot start a transaction within a traverse\n"));
-		tdb->ecode = TDB_ERR_LOCK;
-		return -1;
-	}
-
-	tdb->transaction = (struct tdb_transaction *)
-		calloc(sizeof(struct tdb_transaction), 1);
-	if (tdb->transaction == NULL) {
-		tdb->ecode = TDB_ERR_OOM;
-		return -1;
-	}
-
-	/* a page at a time seems like a reasonable compromise between compactness and efficiency */
-	tdb->transaction->block_size = tdb->page_size;
-
-	/* get the transaction write lock. This is a blocking lock. As
-	   discussed with Volker, there are a number of ways we could
-	   make this async, which we will probably do in the future */
-	if (tdb_transaction_lock(tdb, F_WRLCK, lockflags) == -1) {
-		SAFE_FREE(tdb->transaction->blocks);
-		SAFE_FREE(tdb->transaction);
-		if ((lockflags & TDB_LOCK_WAIT) == 0) {
-			tdb->ecode = TDB_ERR_NOLOCK;
-		}
-		return -1;
-	}
-
-	/* get a read lock from the freelist to the end of file. This
-	   is upgraded to a write lock during the commit */
-	if (tdb_allrecord_lock(tdb, F_RDLCK, TDB_LOCK_WAIT, true) == -1) {
-		TDB_LOG((tdb, TDB_DEBUG_ERROR, "tdb_transaction_start: failed to get hash locks\n"));
-		goto fail_allrecord_lock;
-	}
-
-	/* setup a copy of the hash table heads so the hash scan in
-	   traverse can be fast */
-	tdb->transaction->hash_heads = (uint32_t *)
-		calloc(tdb->header.hash_size+1, sizeof(uint32_t));
-	if (tdb->transaction->hash_heads == NULL) {
-		tdb->ecode = TDB_ERR_OOM;
-		goto fail;
-	}
-	if (tdb->methods->tdb_read(tdb, FREELIST_TOP, tdb->transaction->hash_heads,
-				   TDB_HASHTABLE_SIZE(tdb), 0) != 0) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_transaction_start: failed to read hash heads\n"));
-		tdb->ecode = TDB_ERR_IO;
-		goto fail;
-	}
-
-	/* make sure we know about any file expansions already done by
-	   anyone else */
-	tdb->methods->tdb_oob(tdb, tdb->map_size, 1, 1);
-	tdb->transaction->old_map_size = tdb->map_size;
-
-	/* finally hook the io methods, replacing them with
-	   transaction specific methods */
-	tdb->transaction->io_methods = tdb->methods;
-	tdb->methods = &transaction_methods;
-
-	/* Trace at the end, so we get sequence number correct. */
-	tdb_trace(tdb, "tdb_transaction_start");
-	return 0;
-
-fail:
-	tdb_allrecord_unlock(tdb, F_RDLCK, false);
-fail_allrecord_lock:
-	tdb_transaction_unlock(tdb, F_WRLCK);
-	SAFE_FREE(tdb->transaction->blocks);
-	SAFE_FREE(tdb->transaction->hash_heads);
-	SAFE_FREE(tdb->transaction);
-	return -1;
-}
-
-_PUBLIC_ int tdb_transaction_start(struct tdb_context *tdb)
-{
-	return _tdb_transaction_start(tdb, TDB_LOCK_WAIT);
-}
-
-_PUBLIC_ int tdb_transaction_start_nonblock(struct tdb_context *tdb)
-{
-	return _tdb_transaction_start(tdb, TDB_LOCK_NOWAIT|TDB_LOCK_PROBE);
-}
-
-/*
-  sync to disk
-*/
-static int transaction_sync(struct tdb_context *tdb, tdb_off_t offset, tdb_len_t length)
-{	
-	if (tdb->flags & TDB_NOSYNC) {
-		return 0;
-	}
-
-#ifdef HAVE_FDATASYNC
-	if (fdatasync(tdb->fd) != 0) {
-#else
-	if (fsync(tdb->fd) != 0) {
-#endif
-		tdb->ecode = TDB_ERR_IO;
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_transaction: fsync failed\n"));
-		return -1;
-	}
-#ifdef HAVE_MMAP
-	if (tdb->map_ptr) {
-		tdb_off_t moffset = offset & ~(tdb->page_size-1);
-		if (msync(moffset + (char *)tdb->map_ptr, 
-			  length + (offset - moffset), MS_SYNC) != 0) {
-			tdb->ecode = TDB_ERR_IO;
-			TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_transaction: msync failed - %s\n",
-				 strerror(errno)));
-			return -1;
-		}
-	}
-#endif
-	return 0;
-}
-
-
-static int _tdb_transaction_cancel(struct tdb_context *tdb)
-{	
-	int i, ret = 0;
-
-	if (tdb->transaction == NULL) {
-		TDB_LOG((tdb, TDB_DEBUG_ERROR, "tdb_transaction_cancel: no transaction\n"));
-		return -1;
-	}
-
-	if (tdb->transaction->nesting != 0) {
-		tdb->transaction->transaction_error = 1;
-		tdb->transaction->nesting--;
-		return 0;
-	}		
-
-	tdb->map_size = tdb->transaction->old_map_size;
-
-	/* free all the transaction blocks */
-	for (i=0;i<tdb->transaction->num_blocks;i++) {
-		if (tdb->transaction->blocks[i] != NULL) {
-			free(tdb->transaction->blocks[i]);
-		}
-	}
-	SAFE_FREE(tdb->transaction->blocks);
-
-	if (tdb->transaction->magic_offset) {
-		const struct tdb_methods *methods = tdb->transaction->io_methods;
-		const uint32_t invalid = TDB_RECOVERY_INVALID_MAGIC;
-
-		/* remove the recovery marker */
-		if (methods->tdb_write(tdb, tdb->transaction->magic_offset, &invalid, 4) == -1 ||
-		transaction_sync(tdb, tdb->transaction->magic_offset, 4) == -1) {
-			TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_transaction_cancel: failed to remove recovery magic\n"));
-			ret = -1;
-		}
-	}
-
-	/* This also removes the OPEN_LOCK, if we have it. */
-	tdb_release_transaction_locks(tdb);
-
-	/* restore the normal io methods */
-	tdb->methods = tdb->transaction->io_methods;
-
-	SAFE_FREE(tdb->transaction->hash_heads);
-	SAFE_FREE(tdb->transaction);
-
-	return ret;
-}
-
-/*
-  cancel the current transaction
-*/
-_PUBLIC_ int tdb_transaction_cancel(struct tdb_context *tdb)
-{
-	tdb_trace(tdb, "tdb_transaction_cancel");
-	return _tdb_transaction_cancel(tdb);
-}
-
-/*
-  work out how much space the linearised recovery data will consume
-*/
-static tdb_len_t tdb_recovery_size(struct tdb_context *tdb)
-{
-	tdb_len_t recovery_size = 0;
-	int i;
-
-	recovery_size = sizeof(uint32_t);
-	for (i=0;i<tdb->transaction->num_blocks;i++) {
-		if (i * tdb->transaction->block_size >= tdb->transaction->old_map_size) {
-			break;
-		}
-		if (tdb->transaction->blocks[i] == NULL) {
-			continue;
-		}
-		recovery_size += 2*sizeof(tdb_off_t);
-		if (i == tdb->transaction->num_blocks-1) {
-			recovery_size += tdb->transaction->last_block_size;
-		} else {
-			recovery_size += tdb->transaction->block_size;
-		}
-	}	
-
-	return recovery_size;
-}
-
-int tdb_recovery_area(struct tdb_context *tdb,
-		      const struct tdb_methods *methods,
-		      tdb_off_t *recovery_offset,
-		      struct tdb_record *rec)
-{
-	if (tdb_ofs_read(tdb, TDB_RECOVERY_HEAD, recovery_offset) == -1) {
-		return -1;
-	}
-
-	if (*recovery_offset == 0) {
-		rec->rec_len = 0;
-		return 0;
-	}
-
-	if (methods->tdb_read(tdb, *recovery_offset, rec, sizeof(*rec),
-			      DOCONV()) == -1) {
-		return -1;
-	}
-
-	/* ignore invalid recovery regions: can happen in crash */
-	if (rec->magic != TDB_RECOVERY_MAGIC &&
-	    rec->magic != TDB_RECOVERY_INVALID_MAGIC) {
-		*recovery_offset = 0;
-		rec->rec_len = 0;
-	}
-	return 0;
-}
-
-/*
-  allocate the recovery area, or use an existing recovery area if it is
-  large enough
-*/
-static int tdb_recovery_allocate(struct tdb_context *tdb, 
-				 tdb_len_t *recovery_size,
-				 tdb_off_t *recovery_offset,
-				 tdb_len_t *recovery_max_size)
-{
-	struct tdb_record rec;
-	const struct tdb_methods *methods = tdb->transaction->io_methods;
-	tdb_off_t recovery_head, new_end;
-
-	if (tdb_recovery_area(tdb, methods, &recovery_head, &rec) == -1) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_recovery_allocate: failed to read recovery head\n"));
-		return -1;
-	}
-
-	*recovery_size = tdb_recovery_size(tdb);
-
-	/* Existing recovery area? */
-	if (recovery_head != 0 && *recovery_size <= rec.rec_len) {
-		/* it fits in the existing area */
-		*recovery_max_size = rec.rec_len;
-		*recovery_offset = recovery_head;
-		return 0;
-	}
-
-	/* If recovery area in middle of file, we need a new one. */
-	if (recovery_head == 0
-	    || recovery_head + sizeof(rec) + rec.rec_len != tdb->map_size) {
-		/* we need to free up the old recovery area, then allocate a
-		   new one at the end of the file. Note that we cannot use
-		   tdb_allocate() to allocate the new one as that might return
-		   us an area that is being currently used (as of the start of
-		   the transaction) */
-		if (recovery_head) {
-			if (tdb_free(tdb, recovery_head, &rec) == -1) {
-				TDB_LOG((tdb, TDB_DEBUG_FATAL,
-					 "tdb_recovery_allocate: failed to"
-					 " free previous recovery area\n"));
-				return -1;
-			}
-
-			/* the tdb_free() call might have increased
-			 * the recovery size */
-			*recovery_size = tdb_recovery_size(tdb);
-		}
-
-		/* New head will be at end of file. */
-		recovery_head = tdb->map_size;
-	}
-
-	/* Now we know where it will be. */
-	*recovery_offset = recovery_head;
-
-	/* Expand by more than we need, so we don't do it often. */
-	*recovery_max_size = tdb_expand_adjust(tdb->map_size,
-					       *recovery_size,
-					       tdb->page_size)
-		- sizeof(rec);
-
-	new_end = recovery_head + sizeof(rec) + *recovery_max_size;
-
-	if (methods->tdb_expand_file(tdb, tdb->transaction->old_map_size, 
-				     new_end - tdb->transaction->old_map_size)
-	    == -1) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_recovery_allocate: failed to create recovery area\n"));
-		return -1;
-	}
-
-	/* remap the file (if using mmap) */
-	methods->tdb_oob(tdb, tdb->map_size, 1, 1);
-
-	/* we have to reset the old map size so that we don't try to expand the file
-	   again in the transaction commit, which would destroy the recovery area */
-	tdb->transaction->old_map_size = tdb->map_size;
-
-	/* write the recovery header offset and sync - we can sync without a race here
-	   as the magic ptr in the recovery record has not been set */
-	CONVERT(recovery_head);
-	if (methods->tdb_write(tdb, TDB_RECOVERY_HEAD, 
-			       &recovery_head, sizeof(tdb_off_t)) == -1) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_recovery_allocate: failed to write recovery head\n"));
-		return -1;
-	}
-	if (transaction_write_existing(tdb, TDB_RECOVERY_HEAD, &recovery_head, sizeof(tdb_off_t)) == -1) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_recovery_allocate: failed to write recovery head\n"));
-		return -1;
-	}
-
-	return 0;
-}
-
-
-/*
-  setup the recovery data that will be used on a crash during commit
-*/
-static int transaction_setup_recovery(struct tdb_context *tdb, 
-				      tdb_off_t *magic_offset)
-{
-	tdb_len_t recovery_size;
-	unsigned char *data, *p;
-	const struct tdb_methods *methods = tdb->transaction->io_methods;
-	struct tdb_record *rec;
-	tdb_off_t recovery_offset, recovery_max_size;
-	tdb_off_t old_map_size = tdb->transaction->old_map_size;
-	uint32_t magic, tailer;
-	int i;
-
-	/*
-	  check that the recovery area has enough space
-	*/
-	if (tdb_recovery_allocate(tdb, &recovery_size, 
-				  &recovery_offset, &recovery_max_size) == -1) {
-		return -1;
-	}
-
-	data = (unsigned char *)malloc(recovery_size + sizeof(*rec));
-	if (data == NULL) {
-		tdb->ecode = TDB_ERR_OOM;
-		return -1;
-	}
-
-	rec = (struct tdb_record *)data;
-	memset(rec, 0, sizeof(*rec));
-
-	rec->magic    = TDB_RECOVERY_INVALID_MAGIC;
-	rec->data_len = recovery_size;
-	rec->rec_len  = recovery_max_size;
-	rec->key_len  = old_map_size;
-	CONVERT(*rec);
-
-	/* build the recovery data into a single blob to allow us to do a single
-	   large write, which should be more efficient */
-	p = data + sizeof(*rec);
-	for (i=0;i<tdb->transaction->num_blocks;i++) {
-		tdb_off_t offset;
-		tdb_len_t length;
-
-		if (tdb->transaction->blocks[i] == NULL) {
-			continue;
-		}
-
-		offset = i * tdb->transaction->block_size;
-		length = tdb->transaction->block_size;
-		if (i == tdb->transaction->num_blocks-1) {
-			length = tdb->transaction->last_block_size;
-		}
-
-		if (offset >= old_map_size) {
-			continue;
-		}
-		if (offset + length > tdb->transaction->old_map_size) {
-			TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_transaction_setup_recovery: transaction data over new region boundary\n"));
-			free(data);
-			tdb->ecode = TDB_ERR_CORRUPT;
-			return -1;
-		}
-		memcpy(p, &offset, 4);
-		memcpy(p+4, &length, 4);
-		if (DOCONV()) {
-			tdb_convert(p, 8);
-		}
-		/* the recovery area contains the old data, not the
-		   new data, so we have to call the original tdb_read
-		   method to get it */
-		if (methods->tdb_read(tdb, offset, p + 8, length, 0) != 0) {
-			free(data);
-			tdb->ecode = TDB_ERR_IO;
-			return -1;
-		}
-		p += 8 + length;
-	}
-
-	/* and the tailer */
-	tailer = sizeof(*rec) + recovery_max_size;
-	memcpy(p, &tailer, 4);
-	if (DOCONV()) {
-		tdb_convert(p, 4);
-	}
-
-	/* write the recovery data to the recovery area */
-	if (methods->tdb_write(tdb, recovery_offset, data, sizeof(*rec) + recovery_size) == -1) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_transaction_setup_recovery: failed to write recovery data\n"));
-		free(data);
-		tdb->ecode = TDB_ERR_IO;
-		return -1;
-	}
-	if (transaction_write_existing(tdb, recovery_offset, data, sizeof(*rec) + recovery_size) == -1) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_transaction_setup_recovery: failed to write secondary recovery data\n"));
-		free(data);
-		tdb->ecode = TDB_ERR_IO;
-		return -1;
-	}
-
-	/* as we don't have ordered writes, we have to sync the recovery
-	   data before we update the magic to indicate that the recovery
-	   data is present */
-	if (transaction_sync(tdb, recovery_offset, sizeof(*rec) + recovery_size) == -1) {
-		free(data);
-		return -1;
-	}
-
-	free(data);
-
-	magic = TDB_RECOVERY_MAGIC;
-	CONVERT(magic);
-
-	*magic_offset = recovery_offset + offsetof(struct tdb_record, magic);
-
-	if (methods->tdb_write(tdb, *magic_offset, &magic, sizeof(magic)) == -1) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_transaction_setup_recovery: failed to write recovery magic\n"));
-		tdb->ecode = TDB_ERR_IO;
-		return -1;
-	}
-	if (transaction_write_existing(tdb, *magic_offset, &magic, sizeof(magic)) == -1) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_transaction_setup_recovery: failed to write secondary recovery magic\n"));
-		tdb->ecode = TDB_ERR_IO;
-		return -1;
-	}
-
-	/* ensure the recovery magic marker is on disk */
-	if (transaction_sync(tdb, *magic_offset, sizeof(magic)) == -1) {
-		return -1;
-	}
-
-	return 0;
-}
-
-static int _tdb_transaction_prepare_commit(struct tdb_context *tdb)
-{	
-	const struct tdb_methods *methods;
-
-	if (tdb->transaction == NULL) {
-		TDB_LOG((tdb, TDB_DEBUG_ERROR, "tdb_transaction_prepare_commit: no transaction\n"));
-		return -1;
-	}
-
-	if (tdb->transaction->prepared) {
-		tdb->ecode = TDB_ERR_EINVAL;
-		_tdb_transaction_cancel(tdb);
-		TDB_LOG((tdb, TDB_DEBUG_ERROR, "tdb_transaction_prepare_commit: transaction already prepared\n"));
-		return -1;
-	}
-
-	if (tdb->transaction->transaction_error) {
-		tdb->ecode = TDB_ERR_IO;
-		_tdb_transaction_cancel(tdb);
-		TDB_LOG((tdb, TDB_DEBUG_ERROR, "tdb_transaction_prepare_commit: transaction error pending\n"));
-		return -1;
-	}
-
-
-	if (tdb->transaction->nesting != 0) {
-		return 0;
-	}		
-
-	/* check for a null transaction */
-	if (tdb->transaction->blocks == NULL) {
-		return 0;
-	}
-
-	methods = tdb->transaction->io_methods;
-
-	/* if there are any locks pending then the caller has not
-	   nested their locks properly, so fail the transaction */
-	if (tdb_have_extra_locks(tdb)) {
-		tdb->ecode = TDB_ERR_LOCK;
-		TDB_LOG((tdb, TDB_DEBUG_ERROR, "tdb_transaction_prepare_commit: locks pending on commit\n"));
-		_tdb_transaction_cancel(tdb);
-		return -1;
-	}
-
-	/* upgrade the main transaction lock region to a write lock */
-	if (tdb_allrecord_upgrade(tdb) == -1) {
-		TDB_LOG((tdb, TDB_DEBUG_ERROR, "tdb_transaction_prepare_commit: failed to upgrade hash locks\n"));
-		_tdb_transaction_cancel(tdb);
-		return -1;
-	}
-
-	/* get the open lock - this prevents new users attaching to the database
-	   during the commit */
-	if (tdb_nest_lock(tdb, OPEN_LOCK, F_WRLCK, TDB_LOCK_WAIT) == -1) {
-		TDB_LOG((tdb, TDB_DEBUG_ERROR, "tdb_transaction_prepare_commit: failed to get open lock\n"));
-		_tdb_transaction_cancel(tdb);
-		return -1;
-	}
-
-	if (!(tdb->flags & TDB_NOSYNC)) {
-		/* write the recovery data to the end of the file */
-		if (transaction_setup_recovery(tdb, &tdb->transaction->magic_offset) == -1) {
-			TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_transaction_prepare_commit: failed to setup recovery data\n"));
-			_tdb_transaction_cancel(tdb);
-			return -1;
-		}
-	}
-
-	tdb->transaction->prepared = true;
-
-	/* expand the file to the new size if needed */
-	if (tdb->map_size != tdb->transaction->old_map_size) {
-		if (methods->tdb_expand_file(tdb, tdb->transaction->old_map_size, 
-					     tdb->map_size - 
-					     tdb->transaction->old_map_size) == -1) {
-			tdb->ecode = TDB_ERR_IO;
-			TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_transaction_prepare_commit: expansion failed\n"));
-			_tdb_transaction_cancel(tdb);
-			return -1;
-		}
-		tdb->map_size = tdb->transaction->old_map_size;
-		methods->tdb_oob(tdb, tdb->map_size, 1, 1);
-	}
-
-	/* Keep the open lock until the actual commit */
-
-	return 0;
-}
-
-/*
-   prepare to commit the current transaction
-*/
-_PUBLIC_ int tdb_transaction_prepare_commit(struct tdb_context *tdb)
-{
-	tdb_trace(tdb, "tdb_transaction_prepare_commit");
-	return _tdb_transaction_prepare_commit(tdb);
-}
-
-/* A repack is worthwhile if the largest is less than half total free. */
-static bool repack_worthwhile(struct tdb_context *tdb)
-{
-	tdb_off_t ptr;
-	struct tdb_record rec;
-	tdb_len_t total = 0, largest = 0;
-
-	if (tdb_ofs_read(tdb, FREELIST_TOP, &ptr) == -1) {
-		return false;
-	}
-
-	while (ptr != 0 && tdb_rec_free_read(tdb, ptr, &rec) == 0) {
-		total += rec.rec_len;
-		if (rec.rec_len > largest) {
-			largest = rec.rec_len;
-		}
-		ptr = rec.next;
-	}
-
-	return total > largest * 2;
-}
-
-/*
-  commit the current transaction
-*/
-_PUBLIC_ int tdb_transaction_commit(struct tdb_context *tdb)
-{
-	const struct tdb_methods *methods;
-	int i;
-	bool need_repack = false;
-
-	if (tdb->transaction == NULL) {
-		TDB_LOG((tdb, TDB_DEBUG_ERROR, "tdb_transaction_commit: no transaction\n"));
-		return -1;
-	}
-
-	tdb_trace(tdb, "tdb_transaction_commit");
-
-	if (tdb->transaction->transaction_error) {
-		tdb->ecode = TDB_ERR_IO;
-		_tdb_transaction_cancel(tdb);
-		TDB_LOG((tdb, TDB_DEBUG_ERROR, "tdb_transaction_commit: transaction error pending\n"));
-		return -1;
-	}
-
-
-	if (tdb->transaction->nesting != 0) {
-		tdb->transaction->nesting--;
-		return 0;
-	}
-
-	/* check for a null transaction */
-	if (tdb->transaction->blocks == NULL) {
-		_tdb_transaction_cancel(tdb);
-		return 0;
-	}
-
-	if (!tdb->transaction->prepared) {
-		int ret = _tdb_transaction_prepare_commit(tdb);
-		if (ret)
-			return ret;
-	}
-
-	methods = tdb->transaction->io_methods;
-
-	/* perform all the writes */
-	for (i=0;i<tdb->transaction->num_blocks;i++) {
-		tdb_off_t offset;
-		tdb_len_t length;
-
-		if (tdb->transaction->blocks[i] == NULL) {
-			continue;
-		}
-
-		offset = i * tdb->transaction->block_size;
-		length = tdb->transaction->block_size;
-		if (i == tdb->transaction->num_blocks-1) {
-			length = tdb->transaction->last_block_size;
-		}
-
-		if (methods->tdb_write(tdb, offset, tdb->transaction->blocks[i], length) == -1) {
-			TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_transaction_commit: write failed during commit\n"));
-
-			/* we've overwritten part of the data and
-			   possibly expanded the file, so we need to
-			   run the crash recovery code */
-			tdb->methods = methods;
-			tdb_transaction_recover(tdb); 
-
-			_tdb_transaction_cancel(tdb);
-
-			TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_transaction_commit: write failed\n"));
-			return -1;
-		}
-		SAFE_FREE(tdb->transaction->blocks[i]);
-	} 
-
-	/* Do this before we drop lock or blocks. */
-	if (tdb->transaction->expanded) {
-		need_repack = repack_worthwhile(tdb);
-	}
-
-	SAFE_FREE(tdb->transaction->blocks);
-	tdb->transaction->num_blocks = 0;
-
-	/* ensure the new data is on disk */
-	if (transaction_sync(tdb, 0, tdb->map_size) == -1) {
-		return -1;
-	}
-
-	/*
-	  TODO: maybe write to some dummy hdr field, or write to magic
-	  offset without mmap, before the last sync, instead of the
-	  utime() call
-	*/
-
-	/* on some systems (like Linux 2.6.x) changes via mmap/msync
-	   don't change the mtime of the file, this means the file may
-	   not be backed up (as tdb rounding to block sizes means that
-	   file size changes are quite rare too). The following forces
-	   mtime changes when a transaction completes */
-#ifdef HAVE_UTIME
-	utime(tdb->name, NULL);
-#endif
-
-	/* use a transaction cancel to free memory and remove the
-	   transaction locks */
-	_tdb_transaction_cancel(tdb);
-
-	if (need_repack) {
-		return tdb_repack(tdb);
-	}
-
-	return 0;
-}
-
-
-/*
-  recover from an aborted transaction. Must be called with exclusive
-  database write access already established (including the open
-  lock to prevent new processes attaching)
-*/
-int tdb_transaction_recover(struct tdb_context *tdb)
-{
-	tdb_off_t recovery_head, recovery_eof;
-	unsigned char *data, *p;
-	uint32_t zero = 0;
-	struct tdb_record rec;
-
-	/* find the recovery area */
-	if (tdb_ofs_read(tdb, TDB_RECOVERY_HEAD, &recovery_head) == -1) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_transaction_recover: failed to read recovery head\n"));
-		tdb->ecode = TDB_ERR_IO;
-		return -1;
-	}
-
-	if (recovery_head == 0) {
-		/* we have never allocated a recovery record */
-		return 0;
-	}
-
-	/* read the recovery record */
-	if (tdb->methods->tdb_read(tdb, recovery_head, &rec, 
-				   sizeof(rec), DOCONV()) == -1) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_transaction_recover: failed to read recovery record\n"));		
-		tdb->ecode = TDB_ERR_IO;
-		return -1;
-	}
-
-	if (rec.magic != TDB_RECOVERY_MAGIC) {
-		/* there is no valid recovery data */
-		return 0;
-	}
-
-	if (tdb->read_only) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_transaction_recover: attempt to recover read only database\n"));
-		tdb->ecode = TDB_ERR_CORRUPT;
-		return -1;
-	}
-
-	recovery_eof = rec.key_len;
-
-	data = (unsigned char *)malloc(rec.data_len);
-	if (data == NULL) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_transaction_recover: failed to allocate recovery data\n"));		
-		tdb->ecode = TDB_ERR_OOM;
-		return -1;
-	}
-
-	/* read the full recovery data */
-	if (tdb->methods->tdb_read(tdb, recovery_head + sizeof(rec), data,
-				   rec.data_len, 0) == -1) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_transaction_recover: failed to read recovery data\n"));		
-		tdb->ecode = TDB_ERR_IO;
-		return -1;
-	}
-
-	/* recover the file data */
-	p = data;
-	while (p+8 < data + rec.data_len) {
-		uint32_t ofs, len;
-		if (DOCONV()) {
-			tdb_convert(p, 8);
-		}
-		memcpy(&ofs, p, 4);
-		memcpy(&len, p+4, 4);
-
-		if (tdb->methods->tdb_write(tdb, ofs, p+8, len) == -1) {
-			free(data);
-			TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_transaction_recover: failed to recover %d bytes at offset %d\n", len, ofs));
-			tdb->ecode = TDB_ERR_IO;
-			return -1;
-		}
-		p += 8 + len;
-	}
-
-	free(data);
-
-	if (transaction_sync(tdb, 0, tdb->map_size) == -1) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_transaction_recover: failed to sync recovery\n"));
-		tdb->ecode = TDB_ERR_IO;
-		return -1;
-	}
-
-	/* if the recovery area is after the recovered eof then remove it */
-	if (recovery_eof <= recovery_head) {
-		if (tdb_ofs_write(tdb, TDB_RECOVERY_HEAD, &zero) == -1) {
-			TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_transaction_recover: failed to remove recovery head\n"));
-			tdb->ecode = TDB_ERR_IO;
-			return -1;			
-		}
-	}
-
-	/* remove the recovery magic */
-	if (tdb_ofs_write(tdb, recovery_head + offsetof(struct tdb_record, magic),
-			  &zero) == -1) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_transaction_recover: failed to remove recovery magic\n"));
-		tdb->ecode = TDB_ERR_IO;
-		return -1;			
-	}
-
-	if (transaction_sync(tdb, 0, recovery_eof) == -1) {
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_transaction_recover: failed to sync2 recovery\n"));
-		tdb->ecode = TDB_ERR_IO;
-		return -1;
-	}
-
-	TDB_LOG((tdb, TDB_DEBUG_TRACE, "tdb_transaction_recover: recovered %d byte database\n", 
-		 recovery_eof));
-
-	/* all done */
-	return 0;
-}
-
-/* Any I/O failures we say "needs recovery". */
-bool tdb_needs_recovery(struct tdb_context *tdb)
-{
-	tdb_off_t recovery_head;
-	struct tdb_record rec;
-
-	/* find the recovery area */
-	if (tdb_ofs_read(tdb, TDB_RECOVERY_HEAD, &recovery_head) == -1) {
-		return true;
-	}
-
-	if (recovery_head == 0) {
-		/* we have never allocated a recovery record */
-		return false;
-	}
-
-	/* read the recovery record */
-	if (tdb->methods->tdb_read(tdb, recovery_head, &rec,
-				   sizeof(rec), DOCONV()) == -1) {
-		return true;
-	}
-
-	return (rec.magic == TDB_RECOVERY_MAGIC);
-}
diff --git a/lib/tdb/common/traverse.c b/lib/tdb/common/traverse.c
deleted file mode 100644
index 517fecb..0000000
--- a/lib/tdb/common/traverse.c
+++ /dev/null
@@ -1,366 +0,0 @@
- /* 
-   Unix SMB/CIFS implementation.
-
-   trivial database library
-
-   Copyright (C) Andrew Tridgell              1999-2005
-   Copyright (C) Paul `Rusty' Russell		   2000
-   Copyright (C) Jeremy Allison			   2000-2003
-
-     ** NOTE! The following LGPL license applies to the tdb
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-
-#include "tdb_private.h"
-
-#define TDB_NEXT_LOCK_ERR ((tdb_off_t)-1)
-
-/* Uses traverse lock: 0 = finish, TDB_NEXT_LOCK_ERR = error,
-   other = record offset */
-static tdb_off_t tdb_next_lock(struct tdb_context *tdb, struct tdb_traverse_lock *tlock,
-			 struct tdb_record *rec)
-{
-	int want_next = (tlock->off != 0);
-
-	/* Lock each chain from the start one. */
-	for (; tlock->hash < tdb->header.hash_size; tlock->hash++) {
-		if (!tlock->off && tlock->hash != 0) {
-			/* this is an optimisation for the common case where
-			   the hash chain is empty, which is particularly
-			   common for the use of tdb with ldb, where large
-			   hashes are used. In that case we spend most of our
-			   time in tdb_brlock(), locking empty hash chains.
-
-			   To avoid this, we do an unlocked pre-check to see
-			   if the hash chain is empty before starting to look
-			   inside it. If it is empty then we can avoid that
-			   hash chain. If it isn't empty then we can't believe
-			   the value we get back, as we read it without a
-			   lock, so instead we get the lock and re-fetch the
-			   value below.
-
-			   Notice that not doing this optimisation on the
-			   first hash chain is critical. We must guarantee
-			   that we have done at least one fcntl lock at the
-			   start of a search to guarantee that memory is
-			   coherent on SMP systems. If records are added by
-			   others during the search then thats OK, and we
-			   could possibly miss those with this trick, but we
-			   could miss them anyway without this trick, so the
-			   semantics don't change.
-
-			   With a non-indexed ldb search this trick gains us a
-			   factor of around 80 in speed on a linux 2.6.x
-			   system (testing using ldbtest).
-			*/
-			tdb->methods->next_hash_chain(tdb, &tlock->hash);
-			if (tlock->hash == tdb->header.hash_size) {
-				continue;
-			}
-		}
-
-		if (tdb_lock(tdb, tlock->hash, tlock->lock_rw) == -1)
-			return TDB_NEXT_LOCK_ERR;
-
-		/* No previous record?  Start at top of chain. */
-		if (!tlock->off) {
-			if (tdb_ofs_read(tdb, TDB_HASH_TOP(tlock->hash),
-				     &tlock->off) == -1)
-				goto fail;
-		} else {
-			/* Otherwise unlock the previous record. */
-			if (tdb_unlock_record(tdb, tlock->off) != 0)
-				goto fail;
-		}
-
-		if (want_next) {
-			/* We have offset of old record: grab next */
-			if (tdb_rec_read(tdb, tlock->off, rec) == -1)
-				goto fail;
-			tlock->off = rec->next;
-		}
-
-		/* Iterate through chain */
-		while( tlock->off) {
-			tdb_off_t current;
-			if (tdb_rec_read(tdb, tlock->off, rec) == -1)
-				goto fail;
-
-			/* Detect infinite loops. From "Shlomi Yaakobovich" <Shlomi at exanet.com>. */
-			if (tlock->off == rec->next) {
-				tdb->ecode = TDB_ERR_CORRUPT;
-				TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_next_lock: loop detected.\n"));
-				goto fail;
-			}
-
-			if (!TDB_DEAD(rec)) {
-				/* Woohoo: we found one! */
-				if (tdb_lock_record(tdb, tlock->off) != 0)
-					goto fail;
-				return tlock->off;
-			}
-
-			/* Try to clean dead ones from old traverses */
-			current = tlock->off;
-			tlock->off = rec->next;
-			if (!(tdb->read_only || tdb->traverse_read) && 
-			    tdb_do_delete(tdb, current, rec) != 0)
-				goto fail;
-		}
-		tdb_unlock(tdb, tlock->hash, tlock->lock_rw);
-		want_next = 0;
-	}
-	/* We finished iteration without finding anything */
-	tdb->ecode = TDB_SUCCESS;
-	return 0;
-
- fail:
-	tlock->off = 0;
-	if (tdb_unlock(tdb, tlock->hash, tlock->lock_rw) != 0)
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_next_lock: On error unlock failed!\n"));
-	return TDB_NEXT_LOCK_ERR;
-}
-
-/* traverse the entire database - calling fn(tdb, key, data) on each element.
-   return -1 on error or the record count traversed
-   if fn is NULL then it is not called
-   a non-zero return value from fn() indicates that the traversal should stop
-  */
-static int tdb_traverse_internal(struct tdb_context *tdb, 
-				 tdb_traverse_func fn, void *private_data,
-				 struct tdb_traverse_lock *tl)
-{
-	TDB_DATA key, dbuf;
-	struct tdb_record rec;
-	int ret = 0, count = 0;
-	tdb_off_t off;
-
-	/* This was in the initializaton, above, but the IRIX compiler
-	 * did not like it.  crh
-	 */
-	tl->next = tdb->travlocks.next;
-
-	/* fcntl locks don't stack: beware traverse inside traverse */
-	tdb->travlocks.next = tl;
-
-	/* tdb_next_lock places locks on the record returned, and its chain */
-	while ((off = tdb_next_lock(tdb, tl, &rec)) != 0) {
-		if (off == TDB_NEXT_LOCK_ERR) {
-			ret = -1;
-			goto out;
-		}
-		count++;
-		/* now read the full record */
-		key.dptr = tdb_alloc_read(tdb, tl->off + sizeof(rec), 
-					  rec.key_len + rec.data_len);
-		if (!key.dptr) {
-			ret = -1;
-			if (tdb_unlock(tdb, tl->hash, tl->lock_rw) != 0)
-				goto out;
-			if (tdb_unlock_record(tdb, tl->off) != 0)
-				TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_traverse: key.dptr == NULL and unlock_record failed!\n"));
-			goto out;
-		}
-		key.dsize = rec.key_len;
-		dbuf.dptr = key.dptr + rec.key_len;
-		dbuf.dsize = rec.data_len;
-
-		tdb_trace_1rec_retrec(tdb, "traverse", key, dbuf);
-
-		/* Drop chain lock, call out */
-		if (tdb_unlock(tdb, tl->hash, tl->lock_rw) != 0) {
-			ret = -1;
-			SAFE_FREE(key.dptr);
-			goto out;
-		}
-		if (fn && fn(tdb, key, dbuf, private_data)) {
-			/* They want us to terminate traversal */
-			tdb_trace_ret(tdb, "tdb_traverse_end", count);
-			if (tdb_unlock_record(tdb, tl->off) != 0) {
-				TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_traverse: unlock_record failed!\n"));;
-				ret = -1;
-			}
-			SAFE_FREE(key.dptr);
-			goto out;
-		}
-		SAFE_FREE(key.dptr);
-	}
-	tdb_trace(tdb, "tdb_traverse_end");
-out:
-	tdb->travlocks.next = tl->next;
-	if (ret < 0)
-		return -1;
-	else
-		return count;
-}
-
-
-/*
-  a write style traverse - temporarily marks the db read only
-*/
-_PUBLIC_ int tdb_traverse_read(struct tdb_context *tdb, 
-		      tdb_traverse_func fn, void *private_data)
-{
-	struct tdb_traverse_lock tl = { NULL, 0, 0, F_RDLCK };
-	int ret;
-
-	/* we need to get a read lock on the transaction lock here to
-	   cope with the lock ordering semantics of solaris10 */
-	if (tdb_transaction_lock(tdb, F_RDLCK, TDB_LOCK_WAIT)) {
-		return -1;
-	}
-
-	tdb->traverse_read++;
-	tdb_trace(tdb, "tdb_traverse_read_start");
-	ret = tdb_traverse_internal(tdb, fn, private_data, &tl);
-	tdb->traverse_read--;
-
-	tdb_transaction_unlock(tdb, F_RDLCK);
-
-	return ret;
-}
-
-/*
-  a write style traverse - needs to get the transaction lock to
-  prevent deadlocks
-
-  WARNING: The data buffer given to the callback fn does NOT meet the
-  alignment restrictions malloc gives you.
-*/
-_PUBLIC_ int tdb_traverse(struct tdb_context *tdb, 
-		 tdb_traverse_func fn, void *private_data)
-{
-	struct tdb_traverse_lock tl = { NULL, 0, 0, F_WRLCK };
-	int ret;
-
-	if (tdb->read_only || tdb->traverse_read) {
-		return tdb_traverse_read(tdb, fn, private_data);
-	}
-
-	if (tdb_transaction_lock(tdb, F_WRLCK, TDB_LOCK_WAIT)) {
-		return -1;
-	}
-
-	tdb->traverse_write++;
-	tdb_trace(tdb, "tdb_traverse_start");
-	ret = tdb_traverse_internal(tdb, fn, private_data, &tl);
-	tdb->traverse_write--;
-
-	tdb_transaction_unlock(tdb, F_WRLCK);
-
-	return ret;
-}
-
-
-/* find the first entry in the database and return its key */
-_PUBLIC_ TDB_DATA tdb_firstkey(struct tdb_context *tdb)
-{
-	TDB_DATA key;
-	struct tdb_record rec;
-	tdb_off_t off;
-
-	/* release any old lock */
-	if (tdb_unlock_record(tdb, tdb->travlocks.off) != 0)
-		return tdb_null;
-	tdb->travlocks.off = tdb->travlocks.hash = 0;
-	tdb->travlocks.lock_rw = F_RDLCK;
-
-	/* Grab first record: locks chain and returned record. */
-	off = tdb_next_lock(tdb, &tdb->travlocks, &rec);
-	if (off == 0 || off == TDB_NEXT_LOCK_ERR) {
-		tdb_trace_retrec(tdb, "tdb_firstkey", tdb_null);
-		return tdb_null;
-	}
-	/* now read the key */
-	key.dsize = rec.key_len;
-	key.dptr =tdb_alloc_read(tdb,tdb->travlocks.off+sizeof(rec),key.dsize);
-
-	tdb_trace_retrec(tdb, "tdb_firstkey", key);
-
-	/* Unlock the hash chain of the record we just read. */
-	if (tdb_unlock(tdb, tdb->travlocks.hash, tdb->travlocks.lock_rw) != 0)
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_firstkey: error occurred while tdb_unlocking!\n"));
-	return key;
-}
-
-/* find the next entry in the database, returning its key */
-_PUBLIC_ TDB_DATA tdb_nextkey(struct tdb_context *tdb, TDB_DATA oldkey)
-{
-	uint32_t oldhash;
-	TDB_DATA key = tdb_null;
-	struct tdb_record rec;
-	unsigned char *k = NULL;
-	tdb_off_t off;
-
-	/* Is locked key the old key?  If so, traverse will be reliable. */
-	if (tdb->travlocks.off) {
-		if (tdb_lock(tdb,tdb->travlocks.hash,tdb->travlocks.lock_rw))
-			return tdb_null;
-		if (tdb_rec_read(tdb, tdb->travlocks.off, &rec) == -1
-		    || !(k = tdb_alloc_read(tdb,tdb->travlocks.off+sizeof(rec),
-					    rec.key_len))
-		    || memcmp(k, oldkey.dptr, oldkey.dsize) != 0) {
-			/* No, it wasn't: unlock it and start from scratch */
-			if (tdb_unlock_record(tdb, tdb->travlocks.off) != 0) {
-				tdb_trace_1rec_retrec(tdb, "tdb_nextkey",
-						      oldkey, tdb_null);
-				SAFE_FREE(k);
-				return tdb_null;
-			}
-			if (tdb_unlock(tdb, tdb->travlocks.hash, tdb->travlocks.lock_rw) != 0) {
-				SAFE_FREE(k);
-				return tdb_null;
-			}
-			tdb->travlocks.off = 0;
-		}
-
-		SAFE_FREE(k);
-	}
-
-	if (!tdb->travlocks.off) {
-		/* No previous element: do normal find, and lock record */
-		tdb->travlocks.off = tdb_find_lock_hash(tdb, oldkey, tdb->hash_fn(&oldkey), tdb->travlocks.lock_rw, &rec);
-		if (!tdb->travlocks.off) {
-			tdb_trace_1rec_retrec(tdb, "tdb_nextkey", oldkey, tdb_null);
-			return tdb_null;
-		}
-		tdb->travlocks.hash = BUCKET(rec.full_hash);
-		if (tdb_lock_record(tdb, tdb->travlocks.off) != 0) {
-			TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_nextkey: lock_record failed (%s)!\n", strerror(errno)));
-			return tdb_null;
-		}
-	}
-	oldhash = tdb->travlocks.hash;
-
-	/* Grab next record: locks chain and returned record,
-	   unlocks old record */
-	off = tdb_next_lock(tdb, &tdb->travlocks, &rec);
-	if (off != TDB_NEXT_LOCK_ERR && off != 0) {
-		key.dsize = rec.key_len;
-		key.dptr = tdb_alloc_read(tdb, tdb->travlocks.off+sizeof(rec),
-					  key.dsize);
-		/* Unlock the chain of this new record */
-		if (tdb_unlock(tdb, tdb->travlocks.hash, tdb->travlocks.lock_rw) != 0)
-			TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_nextkey: WARNING tdb_unlock failed!\n"));
-	}
-	/* Unlock the chain of old record */
-	if (tdb_unlock(tdb, BUCKET(oldhash), tdb->travlocks.lock_rw) != 0)
-		TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_nextkey: WARNING tdb_unlock failed!\n"));
-	tdb_trace_1rec_retrec(tdb, "tdb_nextkey", oldkey, key);
-	return key;
-}
-
diff --git a/lib/tdb/docs/README b/lib/tdb/docs/README
deleted file mode 100644
index fe0e258..0000000
--- a/lib/tdb/docs/README
+++ /dev/null
@@ -1,273 +0,0 @@
-tdb - a trivial database system
-tridge at linuxcare.com December 1999
-==================================
-
-This is a simple database API. It was inspired by the realisation that
-in Samba we have several ad-hoc bits of code that essentially
-implement small databases for sharing structures between parts of
-Samba. As I was about to add another I realised that a generic
-database module was called for to replace all the ad-hoc bits.
-
-I based the interface on gdbm. I couldn't use gdbm as we need to be
-able to have multiple writers to the databases at one time.
-
-Compilation
------------
-
-add HAVE_MMAP=1 to use mmap instead of read/write
-add NOLOCK=1 to disable locking code
-
-Testing
--------
-
-Compile tdbtest.c and link with gdbm for testing. tdbtest will perform
-identical operations via tdb and gdbm then make sure the result is the
-same
-
-Also included is tdbtool, which allows simple database manipulation
-on the commandline.
-
-tdbtest and tdbtool are not built as part of Samba, but are included
-for completeness.
-
-Interface
----------
-
-The interface is very similar to gdbm except for the following:
-
-- different open interface. The tdb_open call is more similar to a
-  traditional open()
-- no tdbm_reorganise() function
-- no tdbm_sync() function. No operations are cached in the library anyway
-- added a tdb_traverse() function for traversing the whole database
-- added transactions support
-
-A general rule for using tdb is that the caller frees any returned
-TDB_DATA structures. Just call free(p.dptr) to free a TDB_DATA
-return value called p. This is the same as gdbm.
-
-here is a full list of tdb functions with brief descriptions.
-
-
-----------------------------------------------------------------------
-TDB_CONTEXT *tdb_open(char *name, int hash_size, int tdb_flags,
-		      int open_flags, mode_t mode)
-
-   open the database, creating it if necessary 
-
-   The open_flags and mode are passed straight to the open call on the database
-   file. A flags value of O_WRONLY is invalid
-
-   The hash size is advisory, use zero for a default value. 
-
-   return is NULL on error
-
-   possible tdb_flags are:
-    TDB_CLEAR_IF_FIRST - clear database if we are the only one with it open
-    TDB_INTERNAL - don't use a file, instaed store the data in
-                   memory. The filename is ignored in this case.
-    TDB_NOLOCK - don't do any locking
-    TDB_NOMMAP - don't use mmap
-    TDB_NOSYNC - don't synchronise transactions to disk
-    TDB_SEQNUM - maintain a sequence number
-    TDB_VOLATILE - activate the per-hashchain freelist, default 5
-    TDB_ALLOW_NESTING - allow transactions to nest
-    TDB_DISALLOW_NESTING - disallow transactions to nest
-
-----------------------------------------------------------------------
-TDB_CONTEXT *tdb_open_ex(char *name, int hash_size, int tdb_flags,
-		         int open_flags, mode_t mode,
-			 const struct tdb_logging_context *log_ctx,
-			 tdb_hash_func hash_fn)
-
-This is like tdb_open(), but allows you to pass an initial logging and
-hash function. Be careful when passing a hash function - all users of
-the database must use the same hash function or you will get data
-corruption.
-
-
-----------------------------------------------------------------------
-char *tdb_error(TDB_CONTEXT *tdb);
-
-     return a error string for the last tdb error
-
-----------------------------------------------------------------------
-int tdb_close(TDB_CONTEXT *tdb);
-
-   close a database
-
-----------------------------------------------------------------------
-TDB_DATA tdb_fetch(TDB_CONTEXT *tdb, TDB_DATA key);
-
-   fetch an entry in the database given a key 
-   if the return value has a null dptr then a error occurred
-
-   caller must free the resulting data
-
-----------------------------------------------------------------------
-int tdb_parse_record(struct tdb_context *tdb, TDB_DATA key,
-		     int (*parser)(TDB_DATA key, TDB_DATA data,
-				   void *private_data),
-		     void *private_data);
-
-   Hand a record to a parser function without allocating it.
-
-   This function is meant as a fast tdb_fetch alternative for large records
-   that are frequently read. The "key" and "data" arguments point directly
-   into the tdb shared memory, they are not aligned at any boundary.
-
-   WARNING: The parser is called while tdb holds a lock on the record. DO NOT
-   call other tdb routines from within the parser. Also, for good performance
-   you should make the parser fast to allow parallel operations.
-
-   tdb_parse_record returns -1 if the record was not found.  If the record was
-   found, the return value of "parser" is passed up to the caller.
-
-----------------------------------------------------------------------
-int tdb_exists(TDB_CONTEXT *tdb, TDB_DATA key);
-
-   check if an entry in the database exists 
-
-   note that 1 is returned if the key is found and 0 is returned if not found
-   this doesn't match the conventions in the rest of this module, but is
-   compatible with gdbm
-
-----------------------------------------------------------------------
-int tdb_traverse(TDB_CONTEXT *tdb, int (*fn)(TDB_CONTEXT *tdb,
-                 TDB_DATA key, TDB_DATA dbuf, void *state), void *state);
-
-   traverse the entire database - calling fn(tdb, key, data, state) on each 
-   element.
-
-   return -1 on error or the record count traversed
-
-   if fn is NULL then it is not called
-
-   a non-zero return value from fn() indicates that the traversal
-   should stop. Traversal callbacks may not start transactions.
-
-   WARNING: The data buffer given to the callback fn does NOT meet the
-   alignment restrictions malloc gives you.
-
-----------------------------------------------------------------------
-int tdb_traverse_read(TDB_CONTEXT *tdb, int (*fn)(TDB_CONTEXT *tdb,
-                     TDB_DATA key, TDB_DATA dbuf, void *state), void *state);
-
-   traverse the entire database - calling fn(tdb, key, data, state) on
-   each element, but marking the database read only during the
-   traversal, so any write operations will fail. This allows tdb to
-   use read locks, which increases the parallelism possible during the
-   traversal.
-
-   return -1 on error or the record count traversed
-
-   if fn is NULL then it is not called
-
-   a non-zero return value from fn() indicates that the traversal
-   should stop. Traversal callbacks may not start transactions.
-
-----------------------------------------------------------------------
-TDB_DATA tdb_firstkey(TDB_CONTEXT *tdb);
-
-   find the first entry in the database and return its key
-
-   the caller must free the returned data
-
-----------------------------------------------------------------------
-TDB_DATA tdb_nextkey(TDB_CONTEXT *tdb, TDB_DATA key);
-
-   find the next entry in the database, returning its key
-
-   the caller must free the returned data
-
-----------------------------------------------------------------------
-int tdb_delete(TDB_CONTEXT *tdb, TDB_DATA key);
-
-   delete an entry in the database given a key
-
-----------------------------------------------------------------------
-int tdb_store(TDB_CONTEXT *tdb, TDB_DATA key, TDB_DATA dbuf, int flag);
-
-   store an element in the database, replacing any existing element
-   with the same key 
-
-   If flag==TDB_INSERT then don't overwrite an existing entry
-   If flag==TDB_MODIFY then don't create a new entry
-
-   return 0 on success, -1 on failure
-
-----------------------------------------------------------------------
-int tdb_writelock(TDB_CONTEXT *tdb);
-
-   lock the database. If we already have it locked then don't do anything
-
-----------------------------------------------------------------------
-int tdb_writeunlock(TDB_CONTEXT *tdb);
-   unlock the database
-
-----------------------------------------------------------------------
-int tdb_lockchain(TDB_CONTEXT *tdb, TDB_DATA key);
-
-   lock one hash chain. This is meant to be used to reduce locking
-   contention - it cannot guarantee how many records will be locked
-
-----------------------------------------------------------------------
-int tdb_unlockchain(TDB_CONTEXT *tdb, TDB_DATA key);
-
-   unlock one hash chain
-
-----------------------------------------------------------------------
-int tdb_transaction_start(TDB_CONTEXT *tdb)
-
-   start a transaction. All operations after the transaction start can
-   either be committed with tdb_transaction_commit() or cancelled with
-   tdb_transaction_cancel(). 
-
-   If you call tdb_transaction_start() again on the same tdb context
-   while a transaction is in progress, then the same transaction
-   buffer is re-used. The number of tdb_transaction_{commit,cancel}
-   operations must match the number of successful
-   tdb_transaction_start() calls.
-
-   Note that transactions are by default disk synchronous, and use a
-   recover area in the database to automatically recover the database
-   on the next open if the system crashes during a transaction. You
-   can disable the synchronous transaction recovery setup using the
-   TDB_NOSYNC flag, which will greatly speed up operations at the risk
-   of corrupting your database if the system crashes.
-
-   Operations made within a transaction are not visible to other users
-   of the database until a successful commit.
-
-----------------------------------------------------------------------
-int tdb_transaction_cancel(TDB_CONTEXT *tdb)
-
-   cancel a current transaction, discarding all write and lock
-   operations that have been made since the transaction started.
-
-
-----------------------------------------------------------------------
-int tdb_transaction_commit(TDB_CONTEXT *tdb)
-
-   commit a current transaction, updating the database and releasing
-   the transaction locks.
-
-----------------------------------------------------------------------
-int tdb_transaction_prepare_commit(TDB_CONTEXT *tdb)
-
-   prepare to commit a current transaction, for two-phase commits.
-   Once prepared for commit, the only allowed calls are
-   tdb_transaction_commit() or tdb_transaction_cancel(). Preparing
-   allocates disk space for the pending updates, so a subsequent
-   commit should succeed (barring any hardware failures).
-
-----------------------------------------------------------------------
-int tdb_check(TDB_CONTEXT *tdb,
-	      int (*check)(TDB_DATA key, TDB_DATA data, void *private_data),
-	      void *private_data);)
-
-   check the consistency of the database, calling back the check function
-   (if non-NULL) with each record.  If some consistency check fails, or
-   the supplied check function returns -1, tdb_check returns -1, otherwise
-   0.  Note that logging function (if set) will be called with additional
-   information on the corruption found.
diff --git a/lib/tdb/docs/mainpage.dox b/lib/tdb/docs/mainpage.dox
deleted file mode 100644
index d130769..0000000
--- a/lib/tdb/docs/mainpage.dox
+++ /dev/null
@@ -1,61 +0,0 @@
-/**
-
- at mainpage
-
-This is a simple database API. It was inspired by the realisation that in Samba
-we have several ad-hoc bits of code that essentially implement small databases
-for sharing structures between parts of Samba.
-
-The interface is based on gdbm. gdbm couldn't be use as we needed to be able to
-have multiple writers to the databases at one time.
-
- at section tdb_download Download
-
-You can download the latest releases of tdb from the
-<a href="http://samba.org/ftp/tdb">tdb directory</a> on the samba public source
-archive.
-
-You can download the latest code either via git or rsync.
-
-To fetch via git see the following guide:
-
-<a href="http://wiki.samba.org/index.php/Using_Git_for_Samba_Development">Using Git for Samba Development</a>
-Once you have cloned the tree switch to the master branch and cd into the source/lib/tdb directory.
-
-To fetch via rsync use these commands:
-
-<pre>
-  rsync -Pavz samba.org::ftp/unpacked/standalone_projects/lib/tdb .
-  rsync -Pavz samba.org::ftp/unpacked/standalone_projects/lib/replace .
-</pre>
-
-and build in tdb. It will find the replace library in the directory above
-automatically.
-
- at section tdb_bugs Discussion and bug reports
-
-tdb does not currently have its own mailing list or bug tracking system. For now,
-please use the
-<a href="https://lists.samba.org/mailman/listinfo/samba-technical">samba-technical</a>
-mailing list, and the <a href="http://bugzilla.samba.org/">Samba bugzilla</a> bug
-tracking system.
-
-
- at section tdb_compilation Compilation
-
-add HAVE_MMAP=1 to use mmap instead of read/write
-add NOLOCK=1 to disable locking code
-
- at section tdb_testing Testing
-
-Compile tdbtest.c and link with gdbm for testing. tdbtest will perform
-identical operations via tdb and gdbm then make sure the result is the
-same
-
-Also included is tdbtool, which allows simple database manipulation
-on the commandline.
-
-tdbtest and tdbtool are not built as part of Samba, but are included
-for completeness.
-
-*/
diff --git a/lib/tdb/docs/tdb.magic b/lib/tdb/docs/tdb.magic
deleted file mode 100644
index f5619e7..0000000
--- a/lib/tdb/docs/tdb.magic
+++ /dev/null
@@ -1,10 +0,0 @@
-# Magic file(1) information about tdb files.
-#
-# Install this into /etc/magic or the corresponding location for your
-# system, or pass as a -m argument to file(1).
-
-# You may use and redistribute this file without restriction.
-
-0	string	TDB\ file		TDB database
->32	lelong	=0x2601196D		version 6, little-endian
->>36	lelong	x			hash size %d bytes
diff --git a/lib/tdb/docs/tracing.txt b/lib/tdb/docs/tracing.txt
deleted file mode 100644
index 98c5db9..0000000
--- a/lib/tdb/docs/tracing.txt
+++ /dev/null
@@ -1,46 +0,0 @@
-How And Why To Use TDB Tracing
-==============================
-
-You can trace all TDB operations, using TDB_TRACE.  It is not complete
-(error conditions which expect to the logged will not always be traced
-correctly, so you should set up a logging function too), but is designed
-to collect benchmark-style traces to allow us to optimize TDB.
-
-Note: tracing is not efficient, and the trace files are huge: a
-traverse of the database is particularly large!  But they compress very
-well with rzip (http://rzip.samba.org)
-
-How to gather trace files:
---------------------------
-1) Uncomment /* #define TDB_TRACE 1 */ in tdb_private.h.
-2) Rebuild TDB, and everything that uses it.
-3) Run something.
-
-Your trace files will be called <tdbname>.trace.<pid>.  These files
-will not be overwritten: if the same process reopens the same TDB, an
-error will be logged and tracing will be disabled.
-
-How to replay trace files:
---------------------------
-1) For benchmarking, remember to rebuild tdb with #define TDB_TRACE commented
-   out again!
-2) Grab the latest "replace_trace.c" from CCAN's tdb module (tools/ dir):
-	http://ccan.ozlabs.org/tarballs/tdb.tar.bz2
-3) Compile up replay_trace, munging as necessary.
-4) Run replay_trace <scratch-tdb-name> <tracefiles>...
-
-If given more than one trace file (presumably from the same tdb)
-replay_trace will try to figure out the dependencies between the operations
-and fire off a child to run each trace.  Occasionally it gets stuck, in
-which case it will add another dependency and retry.  Eventually it will
-give a speed value.
-
-replay_trace can intuit the existence of previous data in the tdb (ie.
-activity prior to the trace(s) supplied) and will prepopulate as
-neccessary.
-
-You can run --quiet for straight benchmark results, and -n to run multiple
-times (this saves time, since it need only calculate dependencies once).
-
-Good luck!
-Rusty Russell <rusty at rustcorp.com.au>
diff --git a/lib/tdb/include/tdb.h b/lib/tdb/include/tdb.h
deleted file mode 100644
index 5eb9562..0000000
--- a/lib/tdb/include/tdb.h
+++ /dev/null
@@ -1,847 +0,0 @@
-#ifndef __TDB_H__
-#define __TDB_H__
-
-/* 
-   Unix SMB/CIFS implementation.
-
-   trivial database library
-
-   Copyright (C) Andrew Tridgell 1999-2004
-   
-     ** NOTE! The following LGPL license applies to the tdb
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-   
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-
-#ifdef  __cplusplus
-extern "C" {
-#endif
-
-#include <signal.h>
-
-/**
- * @defgroup tdb The tdb API
- *
- * tdb is a Trivial database. In concept, it is very much like GDBM, and BSD's
- * DB except that it allows multiple simultaneous writers and uses locking
- * internally to keep writers from trampling on each other. tdb is also
- * extremely small.
- *
- * @section tdb_interface Interface
- *
- * The interface is very similar to gdbm except for the following:
- *
- * <ul>
- * <li>different open interface. The tdb_open call is more similar to a
- * traditional open()</li>
- * <li>no tdbm_reorganise() function</li>
- * <li>no tdbm_sync() function. No operations are cached in the library
- *     anyway</li>
- * <li>added a tdb_traverse() function for traversing the whole database</li>
- * <li>added transactions support</li>
- * </ul>
- *
- * A general rule for using tdb is that the caller frees any returned TDB_DATA
- * structures. Just call free(p.dptr) to free a TDB_DATA return value called p.
- * This is the same as gdbm.
- *
- * @{
- */
-
-/** Flags to tdb_store() */
-#define TDB_REPLACE 1		/** Unused */
-#define TDB_INSERT 2 		/** Don't overwrite an existing entry */
-#define TDB_MODIFY 3		/** Don't create an existing entry    */
-
-/** Flags for tdb_open() */
-#define TDB_DEFAULT 0 /** just a readability place holder */
-#define TDB_CLEAR_IF_FIRST 1 /** If this is the first open, wipe the db */
-#define TDB_INTERNAL 2 /** Don't store on disk */
-#define TDB_NOLOCK   4 /** Don't do any locking */
-#define TDB_NOMMAP   8 /** Don't use mmap */
-#define TDB_CONVERT 16 /** Convert endian (internal use) */
-#define TDB_BIGENDIAN 32 /** Header is big-endian (internal use) */
-#define TDB_NOSYNC   64 /** Don't use synchronous transactions */
-#define TDB_SEQNUM   128 /** Maintain a sequence number */
-#define TDB_VOLATILE   256 /** Activate the per-hashchain freelist, default 5 */
-#define TDB_ALLOW_NESTING 512 /** Allow transactions to nest */
-#define TDB_DISALLOW_NESTING 1024 /** Disallow transactions to nest */
-#define TDB_INCOMPATIBLE_HASH 2048 /** Better hashing: can't be opened by tdb < 1.2.6. */
-
-/** The tdb error codes */
-enum TDB_ERROR {TDB_SUCCESS=0, TDB_ERR_CORRUPT, TDB_ERR_IO, TDB_ERR_LOCK, 
-		TDB_ERR_OOM, TDB_ERR_EXISTS, TDB_ERR_NOLOCK, TDB_ERR_LOCK_TIMEOUT,
-		TDB_ERR_NOEXIST, TDB_ERR_EINVAL, TDB_ERR_RDONLY,
-		TDB_ERR_NESTING};
-
-/** Debugging uses one of the following levels */
-enum tdb_debug_level {TDB_DEBUG_FATAL = 0, TDB_DEBUG_ERROR, 
-		      TDB_DEBUG_WARNING, TDB_DEBUG_TRACE};
-
-/** The tdb data structure */
-typedef struct TDB_DATA {
-	unsigned char *dptr;
-	size_t dsize;
-} TDB_DATA;
-
-#ifndef PRINTF_ATTRIBUTE
-#if (__GNUC__ >= 3)
-/** Use gcc attribute to check printf fns.  a1 is the 1-based index of
- * the parameter containing the format, and a2 the index of the first
- * argument. Note that some gcc 2.x versions don't handle this
- * properly **/
-#define PRINTF_ATTRIBUTE(a1, a2) __attribute__ ((format (__printf__, a1, a2)))
-#else
-#define PRINTF_ATTRIBUTE(a1, a2)
-#endif
-#endif
-
-/** This is the context structure that is returned from a db open. */
-typedef struct tdb_context TDB_CONTEXT;
-
-typedef int (*tdb_traverse_func)(struct tdb_context *, TDB_DATA, TDB_DATA, void *);
-typedef void (*tdb_log_func)(struct tdb_context *, enum tdb_debug_level, const char *, ...) PRINTF_ATTRIBUTE(3, 4);
-typedef unsigned int (*tdb_hash_func)(TDB_DATA *key);
-
-struct tdb_logging_context {
-        tdb_log_func log_fn;
-        void *log_private;
-};
-
-/**
- * @brief Open the database and creating it if necessary.
- *
- * @param[in]  name     The name of the db to open.
- *
- * @param[in]  hash_size The hash size is advisory, use zero for a default
- *                       value.
- *
- * @param[in]  tdb_flags The flags to use to open the db:\n\n
- *                         TDB_CLEAR_IF_FIRST - Clear database if we are the
- *                                              only one with it open\n
- *                         TDB_INTERNAL - Don't use a file, instaed store the
- *                                        data in memory. The filename is
- *                                        ignored in this case.\n
- *                         TDB_NOLOCK - Don't do any locking\n
- *                         TDB_NOMMAP - Don't use mmap\n
- *                         TDB_NOSYNC - Don't synchronise transactions to disk\n
- *                         TDB_SEQNUM - Maintain a sequence number\n
- *                         TDB_VOLATILE - activate the per-hashchain freelist,
- *                                        default 5.\n
- *                         TDB_ALLOW_NESTING - Allow transactions to nest.\n
- *                         TDB_DISALLOW_NESTING - Disallow transactions to nest.\n
- *
- * @param[in]  open_flags Flags for the open(2) function.
- *
- * @param[in]  mode     The mode for the open(2) function.
- *
- * @return              A tdb context structure, NULL on error.
- */
-struct tdb_context *tdb_open(const char *name, int hash_size, int tdb_flags,
-		      int open_flags, mode_t mode);
-
-/**
- * @brief Open the database and creating it if necessary.
- *
- * This is like tdb_open(), but allows you to pass an initial logging and
- * hash function. Be careful when passing a hash function - all users of the
- * database must use the same hash function or you will get data corruption.
- *
- * @param[in]  name     The name of the db to open.
- *
- * @param[in]  hash_size The hash size is advisory, use zero for a default
- *                       value.
- *
- * @param[in]  tdb_flags The flags to use to open the db:\n\n
- *                         TDB_CLEAR_IF_FIRST - Clear database if we are the
- *                                              only one with it open\n
- *                         TDB_INTERNAL - Don't use a file, instaed store the
- *                                        data in memory. The filename is
- *                                        ignored in this case.\n
- *                         TDB_NOLOCK - Don't do any locking\n
- *                         TDB_NOMMAP - Don't use mmap\n
- *                         TDB_NOSYNC - Don't synchronise transactions to disk\n
- *                         TDB_SEQNUM - Maintain a sequence number\n
- *                         TDB_VOLATILE - activate the per-hashchain freelist,
- *                                        default 5.\n
- *                         TDB_ALLOW_NESTING - Allow transactions to nest.\n
- *                         TDB_DISALLOW_NESTING - Disallow transactions to nest.\n
- *
- * @param[in]  open_flags Flags for the open(2) function.
- *
- * @param[in]  mode     The mode for the open(2) function.
- *
- * @param[in]  log_ctx  The logging function to use.
- *
- * @param[in]  hash_fn  The hash function you want to use.
- *
- * @return              A tdb context structure, NULL on error.
- *
- * @see tdb_open()
- */
-struct tdb_context *tdb_open_ex(const char *name, int hash_size, int tdb_flags,
-			 int open_flags, mode_t mode,
-			 const struct tdb_logging_context *log_ctx,
-			 tdb_hash_func hash_fn);
-
-/**
- * @brief Set the maximum number of dead records per hash chain.
- *
- * @param[in]  tdb      The database handle to set the maximum.
- *
- * @param[in]  max_dead The maximum number of dead records per hash chain.
- */
-void tdb_set_max_dead(struct tdb_context *tdb, int max_dead);
-
-/**
- * @brief Reopen a tdb.
- *
- * This can be used after a fork to ensure that we have an independent seek
- * pointer from our parent and to re-establish locks.
- *
- * @param[in]  tdb      The database to reopen.
- *
- * @return              0 on success, -1 on error.
- */
-int tdb_reopen(struct tdb_context *tdb);
-
-/**
- * @brief Reopen all tdb's
- *
- * If the parent is longlived (ie. a parent daemon architecture), we know it
- * will keep it's active lock on a tdb opened with CLEAR_IF_FIRST. Thus for
- * child processes we don't have to add an active lock. This is essential to
- * improve performance on systems that keep POSIX locks as a non-scalable data
- * structure in the kernel.
- *
- * @param[in]  parent_longlived Wether the parent is longlived or not.
- *
- * @return              0 on success, -1 on error.
- */
-int tdb_reopen_all(int parent_longlived);
-
-/**
- * @brief Set a different tdb logging function.
- *
- * @param[in]  tdb      The tdb to set the logging function.
- *
- * @param[in]  log_ctx  The logging function to set.
- */
-void tdb_set_logging_function(struct tdb_context *tdb, const struct tdb_logging_context *log_ctx);
-
-/**
- * @brief Get the tdb last error code.
- *
- * @param[in]  tdb      The tdb to get the error code from.
- *
- * @return              A TDB_ERROR code.
- *
- * @see TDB_ERROR
- */
-enum TDB_ERROR tdb_error(struct tdb_context *tdb);
-
-/**
- * @brief Get a error string for the last tdb error
- *
- * @param[in]  tdb      The tdb to get the error code from.
- *
- * @return              An error string.
- */
-const char *tdb_errorstr(struct tdb_context *tdb);
-
-/**
- * @brief Fetch an entry in the database given a key.
- *
- * The caller must free the resulting data.
- *
- * @param[in]  tdb      The tdb to fetch the key.
- *
- * @param[in]  key      The key to fetch.
- *
- * @return              The key entry found in the database, NULL on error with
- *                      TDB_ERROR set.
- *
- * @see tdb_error()
- * @see tdb_errorstr()
- */
-TDB_DATA tdb_fetch(struct tdb_context *tdb, TDB_DATA key);
-
-/**
- * @brief Hand a record to a parser function without allocating it.
- *
- * This function is meant as a fast tdb_fetch alternative for large records
- * that are frequently read. The "key" and "data" arguments point directly
- * into the tdb shared memory, they are not aligned at any boundary.
- *
- * @warning The parser is called while tdb holds a lock on the record. DO NOT
- * call other tdb routines from within the parser. Also, for good performance
- * you should make the parser fast to allow parallel operations.
- *
- * @param[in]  tdb      The tdb to parse the record.
- *
- * @param[in]  key      The key to parse.
- *
- * @param[in]  parser   The parser to use to parse the data.
- *
- * @param[in]  private_data A private data pointer which is passed to the parser
- *                          function.
- *
- * @return              -1 if the record was not found. If the record was found,
- *                      the return value of "parser" is passed up to the caller.
- */
-int tdb_parse_record(struct tdb_context *tdb, TDB_DATA key,
-			      int (*parser)(TDB_DATA key, TDB_DATA data,
-					    void *private_data),
-			      void *private_data);
-
-/**
- * @brief Delete an entry in the database given a key.
- *
- * @param[in]  tdb      The tdb to delete the key.
- *
- * @param[in]  key      The key to delete.
- *
- * @return              0 on success, -1 if the key doesn't exist.
- */
-int tdb_delete(struct tdb_context *tdb, TDB_DATA key);
-
-/**
- * @brief Store an element in the database.
- *
- * This replaces any existing element with the same key.
- *
- * @param[in]  tdb      The tdb to store the entry.
- *
- * @param[in]  key      The key to use to store the entry.
- *
- * @param[in]  dbuf     The data to store under the key.
- *
- * @param[in]  flag     The flags to store the key:\n\n
- *                      TDB_INSERT: Don't overwrite an existing entry.\n
- *                      TDB_MODIFY: Don't create a new entry\n
- *
- * @return              0 on success, -1 on error with error code set.
- *
- * @see tdb_error()
- * @see tdb_errorstr()
- */
-int tdb_store(struct tdb_context *tdb, TDB_DATA key, TDB_DATA dbuf, int flag);
-
-/**
- * @brief Append data to an entry.
- *
- * If the entry doesn't exist, it will create a new one.
- *
- * @param[in]  tdb      The database to use.
- *
- * @param[in]  key      The key to append the data.
- *
- * @param[in]  new_dbuf The data to append to the key.
- *
- * @return              0 on success, -1 on error with error code set.
- *
- * @see tdb_error()
- * @see tdb_errorstr()
- */
-int tdb_append(struct tdb_context *tdb, TDB_DATA key, TDB_DATA new_dbuf);
-
-/**
- * @brief Close a database.
- *
- * @param[in]  tdb      The database to close.
- *
- * @return              0 for success, -1 on error.
- */
-int tdb_close(struct tdb_context *tdb);
-
-/**
- * @brief Find the first entry in the database and return its key.
- *
- * The caller must free the returned data.
- *
- * @param[in]  tdb      The database to use.
- *
- * @return              The first entry of the database, an empty TDB_DATA entry
- *                      if the database is empty.
- */
-TDB_DATA tdb_firstkey(struct tdb_context *tdb);
-
-/**
- * @brief Find the next entry in the database, returning its key.
- *
- * The caller must free the returned data.
- *
- * @param[in]  tdb      The database to use.
- *
- * @param[in]  key      The key from which you want the next key.
- *
- * @return              The next entry of the current key, an empty TDB_DATA
- *                      entry if there is no entry.
- */
-TDB_DATA tdb_nextkey(struct tdb_context *tdb, TDB_DATA key);
-
-/**
- * @brief Traverse the entire database.
- *
- * While travering the function fn(tdb, key, data, state) is called on each
- * element. If fn is NULL then it is not called. A non-zero return value from
- * fn() indicates that the traversal should stop. Traversal callbacks may not
- * start transactions.
- *
- * @warning The data buffer given to the callback fn does NOT meet the alignment
- * restrictions malloc gives you.
- *
- * @param[in]  tdb      The database to traverse.
- *
- * @param[in]  fn       The function to call on each entry.
- *
- * @param[in]  private_data The private data which should be passed to the
- *                          traversing function.
- *
- * @return              The record count traversed, -1 on error.
- */
-int tdb_traverse(struct tdb_context *tdb, tdb_traverse_func fn, void *private_data);
-
-/**
- * @brief Traverse the entire database.
- *
- * While traversing the database the function fn(tdb, key, data, state) is
- * called on each element, but marking the database read only during the
- * traversal, so any write operations will fail. This allows tdb to use read
- * locks, which increases the parallelism possible during the traversal.
- *
- * @param[in]  tdb      The database to traverse.
- *
- * @param[in]  fn       The function to call on each entry.
- *
- * @param[in]  private_data The private data which should be passed to the
- *                          traversing function.
- *
- * @return              The record count traversed, -1 on error.
- */
-int tdb_traverse_read(struct tdb_context *tdb, tdb_traverse_func fn, void *private_data);
-
-/**
- * @brief Check if an entry in the database exists.
- *
- * @note 1 is returned if the key is found and 0 is returned if not found this
- * doesn't match the conventions in the rest of this module, but is compatible
- * with gdbm.
- *
- * @param[in]  tdb      The database to check if the entry exists.
- *
- * @param[in]  key      The key to check if the entry exists.
- *
- * @return              1 if the key is found, 0 if not.
- */
-int tdb_exists(struct tdb_context *tdb, TDB_DATA key);
-
-/**
- * @brief Lock entire database with a write lock.
- *
- * @param[in]  tdb      The database to lock.
- *
- * @return              0 on success, -1 on error with error code set.
- *
- * @see tdb_error()
- * @see tdb_errorstr()
- */
-int tdb_lockall(struct tdb_context *tdb);
-
-/**
- * @brief Lock entire database with a write lock.
- *
- * This is the non-blocking call.
- *
- * @param[in]  tdb      The database to lock.
- *
- * @return              0 on success, -1 on error with error code set.
- *
- * @see tdb_lockall()
- * @see tdb_error()
- * @see tdb_errorstr()
- */
-int tdb_lockall_nonblock(struct tdb_context *tdb);
-
-/**
- * @brief Unlock entire database with write lock.
- *
- * @param[in]  tdb      The database to unlock.
- *
- * @return              0 on success, -1 on error with error code set.
- *
- * @see tdb_lockall()
- * @see tdb_error()
- * @see tdb_errorstr()
- */
-int tdb_unlockall(struct tdb_context *tdb);
-
-/**
- * @brief Lock entire database with a read lock.
- *
- * @param[in]  tdb      The database to lock.
- *
- * @return              0 on success, -1 on error with error code set.
- *
- * @see tdb_error()
- * @see tdb_errorstr()
- */
-int tdb_lockall_read(struct tdb_context *tdb);
-
-/**
- * @brief Lock entire database with a read lock.
- *
- * This is the non-blocking call.
- *
- * @param[in]  tdb      The database to lock.
- *
- * @return              0 on success, -1 on error with error code set.
- *
- * @see tdb_lockall_read()
- * @see tdb_error()
- * @see tdb_errorstr()
- */
-int tdb_lockall_read_nonblock(struct tdb_context *tdb);
-
-/**
- * @brief Unlock entire database with read lock.
- *
- * @param[in]  tdb      The database to unlock.
- *
- * @return              0 on success, -1 on error with error code set.
- *
- * @see tdb_lockall_read()
- * @see tdb_error()
- * @see tdb_errorstr()
- */
-int tdb_unlockall_read(struct tdb_context *tdb);
-
-/**
- * @brief Lock entire database with write lock - mark only.
- *
- * @todo Add more details.
- *
- * @param[in]  tdb      The database to mark.
- *
- * @return              0 on success, -1 on error with error code set.
- *
- * @see tdb_error()
- * @see tdb_errorstr()
- */
-int tdb_lockall_mark(struct tdb_context *tdb);
-
-/**
- * @brief Lock entire database with write lock - unmark only.
- *
- * @todo Add more details.
- *
- * @param[in]  tdb      The database to mark.
- *
- * @return              0 on success, -1 on error with error code set.
- *
- * @see tdb_error()
- * @see tdb_errorstr()
- */
-int tdb_lockall_unmark(struct tdb_context *tdb);
-
-/**
- * @brief Get the name of the current tdb file.
- *
- * This is useful for external logging functions.
- *
- * @param[in]  tdb      The database to get the name from.
- *
- * @return              The name of the database.
- */
-const char *tdb_name(struct tdb_context *tdb);
-
-/**
- * @brief Get the underlying file descriptor being used by tdb.
- *
- * This is useful for external routines that want to check the device/inode
- * of the fd.
- *
- * @param[in]  tdb      The database to get the fd from.
- *
- * @return              The file descriptor or -1.
- */
-int tdb_fd(struct tdb_context *tdb);
-
-/**
- * @brief Get the current logging function.
- *
- * This is useful for external tdb routines that wish to log tdb errors.
- *
- * @param[in]  tdb      The database to get the logging function from.
- *
- * @return              The logging function of the database.
- *
- * @see tdb_get_logging_private()
- */
-tdb_log_func tdb_log_fn(struct tdb_context *tdb);
-
-/**
- * @brief Get the private data of the logging function.
- *
- * @param[in]  tdb      The database to get the data from.
- *
- * @return              The private data pointer of the logging function.
- *
- * @see tdb_log_fn()
- */
-void *tdb_get_logging_private(struct tdb_context *tdb);
-
-/**
- * @brief Start a transaction.
- *
- * All operations after the transaction start can either be committed with
- * tdb_transaction_commit() or cancelled with tdb_transaction_cancel().
- *
- * If you call tdb_transaction_start() again on the same tdb context while a
- * transaction is in progress, then the same transaction buffer is re-used. The
- * number of tdb_transaction_{commit,cancel} operations must match the number
- * of successful tdb_transaction_start() calls.
- *
- * Note that transactions are by default disk synchronous, and use a recover
- * area in the database to automatically recover the database on the next open
- * if the system crashes during a transaction. You can disable the synchronous
- * transaction recovery setup using the TDB_NOSYNC flag, which will greatly
- * speed up operations at the risk of corrupting your database if the system
- * crashes.
- *
- * Operations made within a transaction are not visible to other users of the
- * database until a successful commit.
- *
- * @param[in]  tdb      The database to start the transaction.
- *
- * @return              0 on success, -1 on error with error code set.
- *
- * @see tdb_error()
- * @see tdb_errorstr()
- */
-int tdb_transaction_start(struct tdb_context *tdb);
-
-/**
- * @brief Start a transaction, non-blocking.
- *
- * @param[in]  tdb      The database to start the transaction.
- *
- * @return              0 on success, -1 on error with error code set.
- *
- * @see tdb_error()
- * @see tdb_errorstr()
- * @see tdb_transaction_start()
- */
-int tdb_transaction_start_nonblock(struct tdb_context *tdb);
-
-/**
- * @brief Prepare to commit a current transaction, for two-phase commits.
- *
- * Once prepared for commit, the only allowed calls are tdb_transaction_commit()
- * or tdb_transaction_cancel(). Preparing allocates disk space for the pending
- * updates, so a subsequent commit should succeed (barring any hardware
- * failures).
- *
- * @param[in]  tdb      The database to prepare the commit.
- *
- * @return              0 on success, -1 on error with error code set.
- *
- * @see tdb_error()
- * @see tdb_errorstr()
- */
-int tdb_transaction_prepare_commit(struct tdb_context *tdb);
-
-/**
- * @brief Commit a current transaction.
- *
- * This updates the database and releases the current transaction locks.
- *
- * @param[in]  tdb      The database to commit the transaction.
- *
- * @return              0 on success, -1 on error with error code set.
- *
- * @see tdb_error()
- * @see tdb_errorstr()
- */
-int tdb_transaction_commit(struct tdb_context *tdb);
-
-/**
- * @brief Cancel a current transaction.
- *
- * This discards all write and lock operations that have been made since the
- * transaction started.
- *
- * @param[in]  tdb      The tdb to cancel the transaction on.
- *
- * @return              0 on success, -1 on error with error code set.
- *
- * @see tdb_error()
- * @see tdb_errorstr()
- */
-int tdb_transaction_cancel(struct tdb_context *tdb);
-
-/**
- * @brief Get the tdb sequence number.
- *
- * Only makes sense if the writers opened with TDB_SEQNUM set. Note that this
- * sequence number will wrap quite quickly, so it should only be used for a
- * 'has something changed' test, not for code that relies on the count of the
- * number of changes made. If you want a counter then use a tdb record.
- *
- * The aim of this sequence number is to allow for a very lightweight test of a
- * possible tdb change.
- *
- * @param[in]  tdb      The database to get the sequence number from.
- *
- * @return              The sequence number or 0.
- *
- * @see tdb_open()
- * @see tdb_enable_seqnum()
- */
-int tdb_get_seqnum(struct tdb_context *tdb);
-
-/**
- * @brief Get the hash size.
- *
- * @param[in]  tdb      The database to get the hash size from.
- *
- * @return              The hash size.
- */
-int tdb_hash_size(struct tdb_context *tdb);
-
-/**
- * @brief Get the map size.
- *
- * @param[in]  tdb     The database to get the map size from.
- *
- * @return             The map size.
- */
-size_t tdb_map_size(struct tdb_context *tdb);
-
-/**
- * @brief Get the tdb flags set during open.
- *
- * @param[in]  tdb      The database to get the flags form.
- *
- * @return              The flags set to on the database.
- */
-int tdb_get_flags(struct tdb_context *tdb);
-
-/**
- * @brief Add flags to the database.
- *
- * @param[in]  tdb      The database to add the flags.
- *
- * @param[in]  flag     The tdb flags to add.
- */
-void tdb_add_flags(struct tdb_context *tdb, unsigned flag);
-
-/**
- * @brief Remove flags from the database.
- *
- * @param[in]  tdb      The database to remove the flags.
- *
- * @param[in]  flag     The tdb flags to remove.
- */
-void tdb_remove_flags(struct tdb_context *tdb, unsigned flag);
-
-/**
- * @brief Enable sequence number handling on an open tdb.
- *
- * @param[in]  tdb      The database to enable sequence number handling.
- *
- * @see tdb_get_seqnum()
- */
-void tdb_enable_seqnum(struct tdb_context *tdb);
-
-/**
- * @brief Increment the tdb sequence number.
- *
- * This only works if the tdb has been opened using the TDB_SEQNUM flag or
- * enabled useing tdb_enable_seqnum().
- *
- * @param[in]  tdb      The database to increment the sequence number.
- *
- * @see tdb_enable_seqnum()
- * @see tdb_get_seqnum()
- */
-void tdb_increment_seqnum_nonblock(struct tdb_context *tdb);
-
-/**
- * @brief Create a hash of the key.
- *
- * @param[in]  key      The key to hash
- *
- * @return              The hash.
- */
-unsigned int tdb_jenkins_hash(TDB_DATA *key);
-
-/**
- * @brief Check the consistency of the database.
- *
- * This check the consistency of the database calling back the check function
- * (if non-NULL) on each record.  If some consistency check fails, or the
- * supplied check function returns -1, tdb_check returns -1, otherwise 0.
- *
- * @note The logging function (if set) will be called with additional
- * information on the corruption found.
- *
- * @param[in]  tdb      The database to check.
- *
- * @param[in]  check    The check function to use.
- *
- * @param[in]  private_data the private data to pass to the check function.
- *
- * @return              0 on success, -1 on error with error code set.
- *
- * @see tdb_error()
- * @see tdb_errorstr()
- */
-int tdb_check(struct tdb_context *tdb,
-	      int (*check) (TDB_DATA key, TDB_DATA data, void *private_data),
-	      void *private_data);
-
-/* @} ******************************************************************/
-
-/* Low level locking functions: use with care */
-int tdb_chainlock(struct tdb_context *tdb, TDB_DATA key);
-int tdb_chainlock_nonblock(struct tdb_context *tdb, TDB_DATA key);
-int tdb_chainunlock(struct tdb_context *tdb, TDB_DATA key);
-int tdb_chainlock_read(struct tdb_context *tdb, TDB_DATA key);
-int tdb_chainunlock_read(struct tdb_context *tdb, TDB_DATA key);
-int tdb_chainlock_mark(struct tdb_context *tdb, TDB_DATA key);
-int tdb_chainlock_unmark(struct tdb_context *tdb, TDB_DATA key);
-
-void tdb_setalarm_sigptr(struct tdb_context *tdb, volatile sig_atomic_t *sigptr);
-
-/* wipe and repack */
-int tdb_wipe_all(struct tdb_context *tdb);
-int tdb_repack(struct tdb_context *tdb);
-
-/* Debug functions. Not used in production. */
-void tdb_dump_all(struct tdb_context *tdb);
-int tdb_printfreelist(struct tdb_context *tdb);
-int tdb_validate_freelist(struct tdb_context *tdb, int *pnum_entries);
-int tdb_freelist_size(struct tdb_context *tdb);
-char *tdb_summary(struct tdb_context *tdb);
-
-extern TDB_DATA tdb_null;
-
-#ifdef  __cplusplus
-}
-#endif
-
-#endif /* tdb.h */
diff --git a/lib/tdb/libtdb.m4 b/lib/tdb/libtdb.m4
deleted file mode 100644
index dde4e0d..0000000
--- a/lib/tdb/libtdb.m4
+++ /dev/null
@@ -1,59 +0,0 @@
-dnl Check to see if we should use the included tdb
-
-INCLUDED_TDB=auto
-AC_ARG_WITH(included-tdb,
-    [AC_HELP_STRING([--with-included-tdb], [use bundled tdb library, not from system])],
-    [ INCLUDED_TDB=$withval ])
-
-AC_SUBST(TDB_LIBS)
-AC_SUBST(TDB_CFLAGS)
-
-if test x"$INCLUDED_TDB" != x"yes" ; then
-    AC_CHECK_HEADERS(tdb.h)
-    AC_CHECK_LIB(tdb, tdb_transaction_write_lock_mark, [ TDB_LIBS="-ltdb" ])
-    if test x"$ac_cv_header_tdb_h" = x"no" -o x"$ac_cv_lib_tdb_tdb_transaction_write_lock_mark" = x"no" ; then
-        INCLUDED_TDB=yes
-        TDB_CFLAGS=""
-    else
-        INCLUDED_TDB=no
-    fi
-fi
-
-AC_MSG_CHECKING(whether to use included tdb)
-AC_MSG_RESULT($INCLUDED_TDB)
-if test x"$INCLUDED_TDB" != x"no" ; then
-    dnl find the tdb sources. This is meant to work both for 
-    dnl tdb standalone builds, and builds of packages using tdb
-    tdbdir=""
-    tdbpaths=". lib/tdb tdb ../tdb ../lib/tdb"
-    for d in $tdbpaths; do
-    	if test -f "$srcdir/$d/common/tdb.c"; then
-    		tdbdir="$d"		
-    		AC_SUBST(tdbdir)
-    		break;
-    	fi
-    done
-    if test x"$tdbdir" = "x"; then
-       AC_MSG_ERROR([cannot find tdb source in $tdbpaths])
-    fi
-    TDB_OBJ="common/tdb.o common/dump.o common/transaction.o common/error.o common/traverse.o"
-    TDB_OBJ="$TDB_OBJ common/freelist.o common/freelistcheck.o common/io.o common/lock.o common/open.o common/check.o common/hash.o"
-    AC_SUBST(TDB_OBJ)
-
-    TDB_LIBS=""
-    AC_SUBST(TDB_LIBS)
-
-    TDB_CFLAGS="-I$tdbdir/include"
-    AC_SUBST(TDB_CFLAGS)
-fi
-
-AC_CHECK_FUNCS(mmap pread pwrite getpagesize utime)
-AC_CHECK_HEADERS(getopt.h sys/select.h sys/time.h)
-
-AC_HAVE_DECL(pread, [#include <unistd.h>])
-AC_HAVE_DECL(pwrite, [#include <unistd.h>])
-
-if test x"$VERSIONSCRIPT" != "x"; then
-    EXPORTSFILE=tdb.exports
-    AC_SUBST(EXPORTSFILE)
-fi
diff --git a/lib/tdb/pytdb.c b/lib/tdb/pytdb.c
deleted file mode 100644
index 4892752..0000000
--- a/lib/tdb/pytdb.c
+++ /dev/null
@@ -1,603 +0,0 @@
-/* 
-   Unix SMB/CIFS implementation.
-
-   Python interface to tdb.
-
-   Copyright (C) 2004-2006 Tim Potter <tpot at samba.org>
-   Copyright (C) 2007-2008 Jelmer Vernooij <jelmer at samba.org>
-
-     ** NOTE! The following LGPL license applies to the tdb
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-
-#include <Python.h>
-#include "replace.h"
-#include "system/filesys.h"
-
-#ifndef Py_RETURN_NONE
-#define Py_RETURN_NONE return Py_INCREF(Py_None), Py_None
-#endif
-
-/* Include tdb headers */
-#include <tdb.h>
-
-typedef struct {
-	PyObject_HEAD
-	TDB_CONTEXT *ctx;
-	bool closed;
-} PyTdbObject;
-
-staticforward PyTypeObject PyTdb;
-
-static void PyErr_SetTDBError(TDB_CONTEXT *tdb)
-{
-	PyErr_SetObject(PyExc_RuntimeError, 
-		Py_BuildValue("(i,s)", tdb_error(tdb), tdb_errorstr(tdb)));
-}
-
-static TDB_DATA PyString_AsTDB_DATA(PyObject *data)
-{
-	TDB_DATA ret;
-	ret.dptr = (unsigned char *)PyString_AsString(data);
-	ret.dsize = PyString_Size(data);
-	return ret;
-}
-
-static PyObject *PyString_FromTDB_DATA(TDB_DATA data)
-{
-	if (data.dptr == NULL && data.dsize == 0) {
-		Py_RETURN_NONE;
-	} else {
-		PyObject *ret = PyString_FromStringAndSize((const char *)data.dptr, 
-												   data.dsize);
-		free(data.dptr);
-		return ret;
-    }
-}
-
-#define PyErr_TDB_ERROR_IS_ERR_RAISE(ret, tdb) \
-	if (ret != 0) { \
-		PyErr_SetTDBError(tdb); \
-		return NULL; \
-	}
-
-static PyObject *py_tdb_open(PyTypeObject *type, PyObject *args, PyObject *kwargs)
-{
-	char *name = NULL;
-	int hash_size = 0, tdb_flags = TDB_DEFAULT, flags = O_RDWR, mode = 0600;
-	TDB_CONTEXT *ctx;
-	PyTdbObject *ret;
-	const char *kwnames[] = { "name", "hash_size", "tdb_flags", "flags", "mode", NULL };
-
-	if (!PyArg_ParseTupleAndKeywords(args, kwargs, "|siiii", (char **)kwnames, &name, &hash_size, &tdb_flags, &flags, &mode))
-		return NULL;
-
-	if (name == NULL) {
-		tdb_flags |= TDB_INTERNAL;
-	}
-
-	ctx = tdb_open(name, hash_size, tdb_flags, flags, mode);
-	if (ctx == NULL) {
-		PyErr_SetFromErrno(PyExc_IOError);
-		return NULL;
-	}
-
-	ret = PyObject_New(PyTdbObject, &PyTdb);
-	if (!ret) {
-		tdb_close(ctx);
-		return NULL;
-	}
-
-	ret->ctx = ctx;
-	ret->closed = false;
-	return (PyObject *)ret;
-}
-
-static PyObject *obj_transaction_cancel(PyTdbObject *self)
-{
-	int ret = tdb_transaction_cancel(self->ctx);
-	PyErr_TDB_ERROR_IS_ERR_RAISE(ret, self->ctx);
-	Py_RETURN_NONE;
-}
-
-static PyObject *obj_transaction_commit(PyTdbObject *self)
-{
-	int ret = tdb_transaction_commit(self->ctx);
-	PyErr_TDB_ERROR_IS_ERR_RAISE(ret, self->ctx);
-	Py_RETURN_NONE;
-}
-
-static PyObject *obj_transaction_prepare_commit(PyTdbObject *self)
-{
-	int ret = tdb_transaction_prepare_commit(self->ctx);
-	PyErr_TDB_ERROR_IS_ERR_RAISE(ret, self->ctx);
-	Py_RETURN_NONE;
-}
-
-static PyObject *obj_transaction_start(PyTdbObject *self)
-{
-	int ret = tdb_transaction_start(self->ctx);
-	PyErr_TDB_ERROR_IS_ERR_RAISE(ret, self->ctx);
-	Py_RETURN_NONE;
-}
-
-static PyObject *obj_reopen(PyTdbObject *self)
-{
-	int ret = tdb_reopen(self->ctx);
-	PyErr_TDB_ERROR_IS_ERR_RAISE(ret, self->ctx);
-	Py_RETURN_NONE;
-}
-
-static PyObject *obj_lockall(PyTdbObject *self)
-{
-	int ret = tdb_lockall(self->ctx);
-	PyErr_TDB_ERROR_IS_ERR_RAISE(ret, self->ctx);
-	Py_RETURN_NONE;
-}
-
-static PyObject *obj_unlockall(PyTdbObject *self)
-{
-	int ret = tdb_unlockall(self->ctx);
-	PyErr_TDB_ERROR_IS_ERR_RAISE(ret, self->ctx);
-	Py_RETURN_NONE;
-}
-
-static PyObject *obj_lockall_read(PyTdbObject *self)
-{
-	int ret = tdb_lockall_read(self->ctx);
-	PyErr_TDB_ERROR_IS_ERR_RAISE(ret, self->ctx);
-	Py_RETURN_NONE;
-}
-
-static PyObject *obj_unlockall_read(PyTdbObject *self)
-{
-	int ret = tdb_unlockall_read(self->ctx);
-	PyErr_TDB_ERROR_IS_ERR_RAISE(ret, self->ctx);
-	Py_RETURN_NONE;
-}
-
-static PyObject *obj_close(PyTdbObject *self)
-{
-	int ret;
-	if (self->closed)
-		Py_RETURN_NONE;
-	ret = tdb_close(self->ctx);
-	self->closed = true;
-	PyErr_TDB_ERROR_IS_ERR_RAISE(ret, self->ctx);
-	Py_RETURN_NONE;
-}
-
-static PyObject *obj_get(PyTdbObject *self, PyObject *args)
-{
-	TDB_DATA key;
-	PyObject *py_key;
-	if (!PyArg_ParseTuple(args, "O", &py_key))
-		return NULL;
-
-	key = PyString_AsTDB_DATA(py_key);
-
-	return PyString_FromTDB_DATA(tdb_fetch(self->ctx, key));
-}
-
-static PyObject *obj_append(PyTdbObject *self, PyObject *args)
-{
-	TDB_DATA key, data;
-	PyObject *py_key, *py_data;
-	int ret;
-	if (!PyArg_ParseTuple(args, "OO", &py_key, &py_data))
-		return NULL;
-
-	key = PyString_AsTDB_DATA(py_key);
-	data = PyString_AsTDB_DATA(py_data);
-
-	ret = tdb_append(self->ctx, key, data);
-	PyErr_TDB_ERROR_IS_ERR_RAISE(ret, self->ctx);
-	Py_RETURN_NONE;
-}
-
-static PyObject *obj_firstkey(PyTdbObject *self)
-{
-	return PyString_FromTDB_DATA(tdb_firstkey(self->ctx));
-}
-
-static PyObject *obj_nextkey(PyTdbObject *self, PyObject *args)
-{
-	TDB_DATA key;
-	PyObject *py_key;
-	if (!PyArg_ParseTuple(args, "O", &py_key))
-		return NULL;
-
-	key = PyString_AsTDB_DATA(py_key);
-	
-	return PyString_FromTDB_DATA(tdb_nextkey(self->ctx, key));
-}
-
-static PyObject *obj_delete(PyTdbObject *self, PyObject *args)
-{
-	TDB_DATA key;
-	PyObject *py_key;
-	int ret;
-	if (!PyArg_ParseTuple(args, "O", &py_key))
-		return NULL;
-
-	key = PyString_AsTDB_DATA(py_key);
-	ret = tdb_delete(self->ctx, key);
-	PyErr_TDB_ERROR_IS_ERR_RAISE(ret, self->ctx);
-	Py_RETURN_NONE;
-}
-
-static PyObject *obj_has_key(PyTdbObject *self, PyObject *args)
-{
-	TDB_DATA key;
-	int ret;
-	PyObject *py_key;
-	if (!PyArg_ParseTuple(args, "O", &py_key))
-		return NULL;
-
-	key = PyString_AsTDB_DATA(py_key);
-	ret = tdb_exists(self->ctx, key);
-	if (ret != TDB_ERR_NOEXIST) {
-		PyErr_TDB_ERROR_IS_ERR_RAISE(ret, self->ctx);
-	}
-
-	return (ret == TDB_ERR_NOEXIST)?Py_False:Py_True;
-}
-
-static PyObject *obj_store(PyTdbObject *self, PyObject *args)
-{
-	TDB_DATA key, value;
-	int ret;
-	int flag = TDB_REPLACE;
-	PyObject *py_key, *py_value;
-
-	if (!PyArg_ParseTuple(args, "OO|i", &py_key, &py_value, &flag))
-		return NULL;
-
-	key = PyString_AsTDB_DATA(py_key);
-	value = PyString_AsTDB_DATA(py_value);
-
-	ret = tdb_store(self->ctx, key, value, flag);
-	PyErr_TDB_ERROR_IS_ERR_RAISE(ret, self->ctx);
-	Py_RETURN_NONE;
-}
-
-static PyObject *obj_add_flags(PyTdbObject *self, PyObject *args)
-{
-	unsigned flags;
-
-	if (!PyArg_ParseTuple(args, "I", &flags))
-		return NULL;
-
-	tdb_add_flags(self->ctx, flags);
-	Py_RETURN_NONE;
-}
-
-static PyObject *obj_remove_flags(PyTdbObject *self, PyObject *args)
-{
-	unsigned flags;
-
-	if (!PyArg_ParseTuple(args, "I", &flags))
-		return NULL;
-
-	tdb_remove_flags(self->ctx, flags);
-	Py_RETURN_NONE;
-}
-
-typedef struct {
-	PyObject_HEAD
-	TDB_DATA current;
-	PyTdbObject *iteratee;
-} PyTdbIteratorObject;
-
-static PyObject *tdb_iter_next(PyTdbIteratorObject *self)
-{
-	TDB_DATA current;
-	PyObject *ret;
-	if (self->current.dptr == NULL && self->current.dsize == 0)
-		return NULL;
-	current = self->current;
-	self->current = tdb_nextkey(self->iteratee->ctx, self->current);
-	ret = PyString_FromTDB_DATA(current);
-	return ret;
-}
-
-static void tdb_iter_dealloc(PyTdbIteratorObject *self)
-{
-	Py_DECREF(self->iteratee);
-	PyObject_Del(self);
-}
-
-PyTypeObject PyTdbIterator = {
-	.tp_name = "Iterator",
-	.tp_basicsize = sizeof(PyTdbIteratorObject),
-	.tp_iternext = (iternextfunc)tdb_iter_next,
-	.tp_dealloc = (destructor)tdb_iter_dealloc,
-	.tp_flags = Py_TPFLAGS_DEFAULT,
-	.tp_iter = PyObject_SelfIter,
-};
-
-static PyObject *tdb_object_iter(PyTdbObject *self)
-{
-	PyTdbIteratorObject *ret;	
-
-	ret = PyObject_New(PyTdbIteratorObject, &PyTdbIterator);
-	if (!ret)
-		return NULL;
-	ret->current = tdb_firstkey(self->ctx);
-	ret->iteratee = self;
-	Py_INCREF(self);
-	return (PyObject *)ret;
-}
-
-static PyObject *obj_clear(PyTdbObject *self)
-{
-	int ret = tdb_wipe_all(self->ctx);
-	PyErr_TDB_ERROR_IS_ERR_RAISE(ret, self->ctx);
-	Py_RETURN_NONE;
-}
-
-static PyObject *obj_repack(PyTdbObject *self)
-{
-	int ret = tdb_repack(self->ctx);
-	PyErr_TDB_ERROR_IS_ERR_RAISE(ret, self->ctx);
-	Py_RETURN_NONE;
-}
-
-static PyObject *obj_enable_seqnum(PyTdbObject *self)
-{
-	tdb_enable_seqnum(self->ctx);
-	Py_RETURN_NONE;
-}
-
-static PyObject *obj_increment_seqnum_nonblock(PyTdbObject *self)
-{
-	tdb_increment_seqnum_nonblock(self->ctx);
-	Py_RETURN_NONE;
-}
-
-static PyMethodDef tdb_object_methods[] = {
-	{ "transaction_cancel", (PyCFunction)obj_transaction_cancel, METH_NOARGS, 
-		"S.transaction_cancel() -> None\n"
-		"Cancel the currently active transaction." },
-	{ "transaction_commit", (PyCFunction)obj_transaction_commit, METH_NOARGS,
-		"S.transaction_commit() -> None\n"
-		"Commit the currently active transaction." },
-	{ "transaction_prepare_commit", (PyCFunction)obj_transaction_prepare_commit, METH_NOARGS,
-		"S.transaction_prepare_commit() -> None\n"
-		"Prepare to commit the currently active transaction" },
-	{ "transaction_start", (PyCFunction)obj_transaction_start, METH_NOARGS,
-		"S.transaction_start() -> None\n"
-		"Start a new transaction." },
-	{ "reopen", (PyCFunction)obj_reopen, METH_NOARGS, "Reopen this file." },
-	{ "lock_all", (PyCFunction)obj_lockall, METH_NOARGS, NULL },
-	{ "unlock_all", (PyCFunction)obj_unlockall, METH_NOARGS, NULL },
-	{ "read_lock_all", (PyCFunction)obj_lockall_read, METH_NOARGS, NULL },
-	{ "read_unlock_all", (PyCFunction)obj_unlockall_read, METH_NOARGS, NULL },
-	{ "close", (PyCFunction)obj_close, METH_NOARGS, NULL },
-	{ "get", (PyCFunction)obj_get, METH_VARARGS, "S.get(key) -> value\n"
-		"Fetch a value." },
-	{ "append", (PyCFunction)obj_append, METH_VARARGS, "S.append(key, value) -> None\n"
-		"Append data to an existing key." },
-	{ "firstkey", (PyCFunction)obj_firstkey, METH_NOARGS, "S.firstkey() -> data\n"
-		"Return the first key in this database." },
-	{ "nextkey", (PyCFunction)obj_nextkey, METH_NOARGS, "S.nextkey(key) -> data\n"
-		"Return the next key in this database." },
-	{ "delete", (PyCFunction)obj_delete, METH_VARARGS, "S.delete(key) -> None\n"
-		"Delete an entry." },
-	{ "has_key", (PyCFunction)obj_has_key, METH_VARARGS, "S.has_key(key) -> None\n"
-		"Check whether key exists in this database." },
-	{ "store", (PyCFunction)obj_store, METH_VARARGS, "S.store(key, data, flag=REPLACE) -> None"
-		"Store data." },
-	{ "add_flags", (PyCFunction)obj_add_flags, METH_VARARGS, "S.add_flags(flags) -> None" },
-	{ "remove_flags", (PyCFunction)obj_remove_flags, METH_VARARGS, "S.remove_flags(flags) -> None" },
-	{ "iterkeys", (PyCFunction)tdb_object_iter, METH_NOARGS, "S.iterkeys() -> iterator" },
-	{ "clear", (PyCFunction)obj_clear, METH_NOARGS, "S.clear() -> None\n"
-		"Wipe the entire database." },
-	{ "repack", (PyCFunction)obj_repack, METH_NOARGS, "S.repack() -> None\n"
-		"Repack the entire database." },
-	{ "enable_seqnum", (PyCFunction)obj_enable_seqnum, METH_NOARGS,
-		"S.enable_seqnum() -> None" },
-	{ "increment_seqnum_nonblock", (PyCFunction)obj_increment_seqnum_nonblock, METH_NOARGS,
-		"S.increment_seqnum_nonblock() -> None" },
-	{ NULL }
-};
-
-static PyObject *obj_get_hash_size(PyTdbObject *self, void *closure)
-{
-	return PyInt_FromLong(tdb_hash_size(self->ctx));
-}
-
-static int obj_set_max_dead(PyTdbObject *self, PyObject *max_dead, void *closure)
-{
-	if (!PyInt_Check(max_dead))
-		return -1;
-	tdb_set_max_dead(self->ctx, PyInt_AsLong(max_dead));
-	return 0;
-}
-
-static PyObject *obj_get_map_size(PyTdbObject *self, void *closure)
-{
-	return PyInt_FromLong(tdb_map_size(self->ctx));
-}
-
-static PyObject *obj_get_freelist_size(PyTdbObject *self, void *closure)
-{
-	return PyInt_FromLong(tdb_freelist_size(self->ctx));
-}
-
-static PyObject *obj_get_flags(PyTdbObject *self, void *closure)
-{
-	return PyInt_FromLong(tdb_get_flags(self->ctx));
-}
-
-static PyObject *obj_get_filename(PyTdbObject *self, void *closure)
-{
-	return PyString_FromString(tdb_name(self->ctx));
-}
-
-static PyObject *obj_get_seqnum(PyTdbObject *self, void *closure)
-{
-	return PyInt_FromLong(tdb_get_seqnum(self->ctx));
-}
-
-
-static PyGetSetDef tdb_object_getsetters[] = {
-	{ (char *)"hash_size", (getter)obj_get_hash_size, NULL, NULL },
-	{ (char *)"map_size", (getter)obj_get_map_size, NULL, NULL },
-	{ (char *)"freelist_size", (getter)obj_get_freelist_size, NULL, NULL },
-	{ (char *)"flags", (getter)obj_get_flags, NULL, NULL },
-	{ (char *)"max_dead", NULL, (setter)obj_set_max_dead, NULL },
-	{ (char *)"filename", (getter)obj_get_filename, NULL, (char *)"The filename of this TDB file."},
-	{ (char *)"seqnum", (getter)obj_get_seqnum, NULL, NULL },
-	{ NULL }
-};
-
-static PyObject *tdb_object_repr(PyTdbObject *self)
-{
-	if (tdb_get_flags(self->ctx) & TDB_INTERNAL) {
-		return PyString_FromString("Tdb(<internal>)");
-	} else {
-		return PyString_FromFormat("Tdb('%s')", tdb_name(self->ctx));
-	}
-}
-
-static void tdb_object_dealloc(PyTdbObject *self)
-{
-	if (!self->closed)
-		tdb_close(self->ctx);
-	self->ob_type->tp_free(self);
-}
-
-static PyObject *obj_getitem(PyTdbObject *self, PyObject *key)
-{
-	TDB_DATA tkey, val;
-	if (!PyString_Check(key)) {
-		PyErr_SetString(PyExc_TypeError, "Expected string as key");
-		return NULL;
-	}
-
-	tkey.dptr = (unsigned char *)PyString_AsString(key);
-	tkey.dsize = PyString_Size(key);
-
-	val = tdb_fetch(self->ctx, tkey);
-	if (val.dptr == NULL) {
-		PyErr_SetString(PyExc_KeyError, "No such TDB entry");
-		return NULL;
-	} else {
-		return PyString_FromTDB_DATA(val);
-	}
-}
-
-static int obj_setitem(PyTdbObject *self, PyObject *key, PyObject *value)
-{
-	TDB_DATA tkey, tval;
-	int ret;
-	if (!PyString_Check(key)) {
-		PyErr_SetString(PyExc_TypeError, "Expected string as key");
-		return -1;
-	}
-
-	tkey = PyString_AsTDB_DATA(key);
-
-	if (value == NULL) { 
-		ret = tdb_delete(self->ctx, tkey);
-	} else { 
-		if (!PyString_Check(value)) {
-			PyErr_SetString(PyExc_TypeError, "Expected string as value");
-			return -1;
-		}
-
-		tval = PyString_AsTDB_DATA(value);
-
-		ret = tdb_store(self->ctx, tkey, tval, TDB_REPLACE);
-	}
-
-	if (ret != 0) {
-		PyErr_SetTDBError(self->ctx);
-		return -1;
-	} 
-
-	return ret;
-}
-
-static PyMappingMethods tdb_object_mapping = {
-	.mp_subscript = (binaryfunc)obj_getitem,
-	.mp_ass_subscript = (objobjargproc)obj_setitem,
-};
-static PyTypeObject PyTdb = {
-	.tp_name = "tdb.Tdb",
-	.tp_basicsize = sizeof(PyTdbObject),
-	.tp_methods = tdb_object_methods,
-	.tp_getset = tdb_object_getsetters,
-	.tp_new = py_tdb_open,
-	.tp_doc = "A TDB file",
-	.tp_repr = (reprfunc)tdb_object_repr,
-	.tp_dealloc = (destructor)tdb_object_dealloc,
-	.tp_as_mapping = &tdb_object_mapping,
-	.tp_flags = Py_TPFLAGS_DEFAULT|Py_TPFLAGS_BASETYPE|Py_TPFLAGS_HAVE_ITER,
-	.tp_iter = (getiterfunc)tdb_object_iter,
-};
-
-static PyMethodDef tdb_methods[] = {
-	{ "open", (PyCFunction)py_tdb_open, METH_VARARGS|METH_KEYWORDS, "open(name, hash_size=0, tdb_flags=TDB_DEFAULT, flags=O_RDWR, mode=0600)\n"
-		"Open a TDB file." },
-	{ NULL }
-};
-
-void inittdb(void);
-void inittdb(void)
-{
-	PyObject *m;
-
-	if (PyType_Ready(&PyTdb) < 0)
-		return;
-
-	if (PyType_Ready(&PyTdbIterator) < 0)
-		return;
-
-	m = Py_InitModule3("tdb", tdb_methods,
-		"simple key-value database that supports multiple writers.");
-	if (m == NULL)
-		return;
-
-	PyModule_AddObject(m, "REPLACE", PyInt_FromLong(TDB_REPLACE));
-	PyModule_AddObject(m, "INSERT", PyInt_FromLong(TDB_INSERT));
-	PyModule_AddObject(m, "MODIFY", PyInt_FromLong(TDB_MODIFY));
-
-	PyModule_AddObject(m, "DEFAULT", PyInt_FromLong(TDB_DEFAULT));
-	PyModule_AddObject(m, "CLEAR_IF_FIRST", PyInt_FromLong(TDB_CLEAR_IF_FIRST));
-	PyModule_AddObject(m, "INTERNAL", PyInt_FromLong(TDB_INTERNAL));
-	PyModule_AddObject(m, "NOLOCK", PyInt_FromLong(TDB_NOLOCK));
-	PyModule_AddObject(m, "NOMMAP", PyInt_FromLong(TDB_NOMMAP));
-	PyModule_AddObject(m, "CONVERT", PyInt_FromLong(TDB_CONVERT));
-	PyModule_AddObject(m, "BIGENDIAN", PyInt_FromLong(TDB_BIGENDIAN));
-	PyModule_AddObject(m, "NOSYNC", PyInt_FromLong(TDB_NOSYNC));
-	PyModule_AddObject(m, "SEQNUM", PyInt_FromLong(TDB_SEQNUM));
-	PyModule_AddObject(m, "VOLATILE", PyInt_FromLong(TDB_VOLATILE));
-	PyModule_AddObject(m, "ALLOW_NESTING", PyInt_FromLong(TDB_ALLOW_NESTING));
-	PyModule_AddObject(m, "DISALLOW_NESTING", PyInt_FromLong(TDB_DISALLOW_NESTING));
-	PyModule_AddObject(m, "INCOMPATIBLE_HASH", PyInt_FromLong(TDB_INCOMPATIBLE_HASH));
-
-	PyModule_AddObject(m, "__docformat__", PyString_FromString("restructuredText"));
-
-	PyModule_AddObject(m, "__version__", PyString_FromString(PACKAGE_VERSION));
-
-	Py_INCREF(&PyTdb);
-	PyModule_AddObject(m, "Tdb", (PyObject *)&PyTdb);
-
-	Py_INCREF(&PyTdbIterator);
-}
diff --git a/lib/tdb/python/tdbdump.py b/lib/tdb/python/tdbdump.py
deleted file mode 100644
index 01859eb..0000000
--- a/lib/tdb/python/tdbdump.py
+++ /dev/null
@@ -1,12 +0,0 @@
-#!/usr/bin/env python
-# Trivial reimplementation of tdbdump in Python
-
-import tdb, sys
-
-if len(sys.argv) < 2:
-    print "Usage: tdbdump.py <tdb-file>"
-    sys.exit(1)
-
-db = tdb.Tdb(sys.argv[1])
-for (k, v) in db.iteritems():
-    print "{\nkey(%d) = %r\ndata(%d) = %r\n}" % (len(k), k, len(v), v)
diff --git a/lib/tdb/python/tests/simple.py b/lib/tdb/python/tests/simple.py
deleted file mode 100644
index 2877092..0000000
--- a/lib/tdb/python/tests/simple.py
+++ /dev/null
@@ -1,199 +0,0 @@
-#!/usr/bin/env python
-# Some simple tests for the Python bindings for TDB
-# Note that this tests the interface of the Python bindings
-# It does not test tdb itself.
-#
-# Copyright (C) 2007-2008 Jelmer Vernooij <jelmer at samba.org>
-# Published under the GNU LGPLv3 or later
-
-import tdb
-from unittest import TestCase
-import os, tempfile
-
-
-class OpenTdbTests(TestCase):
-
-    def test_nonexistant_read(self):
-        self.assertRaises(IOError, tdb.Tdb, "/some/nonexistant/file", 0,
-                tdb.DEFAULT, os.O_RDWR)
-
-class CloseTdbTests(TestCase):
-
-    def test_double_close(self):
-        # No hash size in tdb2.
-        if tdb.__version__.startswith("2"):
-            self.tdb = tdb.Tdb(tempfile.mkstemp()[1], tdb.DEFAULT,
-                               os.O_CREAT|os.O_RDWR)
-        else:
-            self.tdb = tdb.Tdb(tempfile.mkstemp()[1], 0, tdb.DEFAULT,
-                               os.O_CREAT|os.O_RDWR)
-        self.assertNotEqual(None, self.tdb)
-
-        # ensure that double close does not crash python
-        self.tdb.close()
-        self.tdb.close()
-
-
-class InternalTdbTests(TestCase):
-
-    def test_repr(self):
-        self.tdb = tdb.Tdb()
-
-        # repr used to crash on internal db
-        self.assertEquals(repr(self.tdb), "Tdb(<internal>)")
-
-
-class SimpleTdbTests(TestCase):
-
-    def setUp(self):
-        super(SimpleTdbTests, self).setUp()
-        if tdb.__version__.startswith("2"):
-            self.tdb = tdb.Tdb(tempfile.mkstemp()[1], tdb.DEFAULT,
-                               os.O_CREAT|os.O_RDWR)
-        else:
-            self.tdb = tdb.Tdb(tempfile.mkstemp()[1], 0, tdb.DEFAULT,
-                               os.O_CREAT|os.O_RDWR)
-        self.assertNotEqual(None, self.tdb)
-
-    def tearDown(self):
-        del self.tdb
-
-    def test_repr(self):
-        self.assertTrue(repr(self.tdb).startswith("Tdb('"))
-
-    def test_lockall(self):
-        self.tdb.lock_all()
-
-    def test_max_dead(self):
-        if not tdb.__version__.startswith("2"):
-            self.tdb.max_dead = 20
-
-    def test_unlockall(self):
-        self.tdb.lock_all()
-        self.tdb.unlock_all()
-
-    def test_lockall_read(self):
-        self.tdb.read_lock_all()
-        self.tdb.read_unlock_all()
-
-    def test_reopen(self):
-        if not tdb.__version__.startswith("2"):
-            self.tdb.reopen()
-
-    def test_store(self):
-        self.tdb.store("bar", "bla")
-        self.assertEquals("bla", self.tdb.get("bar"))
-
-    def test_getitem(self):
-        self.tdb["bar"] = "foo"
-        if not tdb.__version__.startswith("2"):
-            self.tdb.reopen()
-        self.assertEquals("foo", self.tdb["bar"])
-
-    def test_delete(self):
-        self.tdb["bar"] = "foo"
-        del self.tdb["bar"]
-        self.assertRaises(KeyError, lambda: self.tdb["bar"])
-    
-    def test_contains(self):
-        self.tdb["bla"] = "bloe"
-        self.assertTrue("bla" in self.tdb)
-
-    def test_keyerror(self):
-        self.assertRaises(KeyError, lambda: self.tdb["bla"])
-
-    def test_hash_size(self):
-        if not tdb.__version__.startswith("2"):
-            self.tdb.hash_size
-
-    def test_map_size(self):
-        if not tdb.__version__.startswith("2"):
-            self.tdb.map_size
-
-    def test_freelist_size(self):
-        if not tdb.__version__.startswith("2"):
-            self.tdb.freelist_size
-
-    def test_name(self):
-        self.tdb.filename
-
-    def test_iterator(self):
-        self.tdb["bla"] = "1"
-        self.tdb["brainslug"] = "2"
-        l = list(self.tdb)
-        l.sort()
-        self.assertEquals(["bla", "brainslug"], l)
-
-    def test_transaction_cancel(self):
-        self.tdb["bloe"] = "2"
-        self.tdb.transaction_start()
-        self.tdb["bloe"] = "1"
-        self.tdb.transaction_cancel()
-        self.assertEquals("2", self.tdb["bloe"])
-
-    def test_transaction_commit(self):
-        self.tdb["bloe"] = "2"
-        self.tdb.transaction_start()
-        self.tdb["bloe"] = "1"
-        self.tdb.transaction_commit()
-        self.assertEquals("1", self.tdb["bloe"])
-
-    def test_transaction_prepare_commit(self):
-        self.tdb["bloe"] = "2"
-        self.tdb.transaction_start()
-        self.tdb["bloe"] = "1"
-        self.tdb.transaction_prepare_commit()
-        self.tdb.transaction_commit()
-        self.assertEquals("1", self.tdb["bloe"])
-
-    def test_iterkeys(self):
-        self.tdb["bloe"] = "2"
-        self.tdb["bla"] = "25"
-        i = self.tdb.iterkeys()
-        self.assertEquals(set(["bloe", "bla"]), set([i.next(), i.next()]))
-
-    def test_clear(self):
-        self.tdb["bloe"] = "2"
-        self.tdb["bla"] = "25"
-        self.assertEquals(2, len(list(self.tdb)))
-        self.tdb.clear()
-        self.assertEquals(0, len(list(self.tdb)))
-
-    def test_repack(self):
-        if not tdb.__version__.startswith("2"):
-            self.tdb["foo"] = "abc"
-            self.tdb["bar"] = "def"
-            del self.tdb["foo"]
-            self.tdb.repack()
-
-    def test_seqnum(self):
-        if not tdb.__version__.startswith("2"):
-            self.tdb.enable_seqnum()
-            seq1 = self.tdb.seqnum
-            self.tdb.increment_seqnum_nonblock()
-            seq2 = self.tdb.seqnum
-            self.assertEquals(seq2-seq1, 1)
-
-    def test_len(self):
-        self.assertEquals(0, len(list(self.tdb)))
-        self.tdb["entry"] = "value"
-        self.assertEquals(1, len(list(self.tdb)))
-
-    def test_add_flags(self):
-        if tdb.__version__.startswith("2"):
-            self.tdb.add_flag(tdb.NOMMAP)
-            self.tdb.remove_flag(tdb.NOMMAP)
-        else:
-            self.tdb.add_flags(tdb.NOMMAP)
-            self.tdb.remove_flags(tdb.NOMMAP)
-
-
-class VersionTests(TestCase):
-
-    def test_present(self):
-        self.assertTrue(isinstance(tdb.__version__, str))
-
-
-if __name__ == '__main__':
-    import unittest
-    unittest.TestProgram()
diff --git a/lib/tdb/tdb.pc.in b/lib/tdb/tdb.pc.in
deleted file mode 100644
index 6f8f553..0000000
--- a/lib/tdb/tdb.pc.in
+++ /dev/null
@@ -1,11 +0,0 @@
-prefix=@prefix@
-exec_prefix=@exec_prefix@
-libdir=@libdir@
-includedir=@includedir@
-
-Name: tdb
-Description: A trivial database
-Version: @PACKAGE_VERSION@
-Libs: -L${libdir} -ltdb
-Cflags: -I${includedir} 
-URL: http://tdb.samba.org/
diff --git a/lib/tdb/tools/tdbbackup.c b/lib/tdb/tools/tdbbackup.c
deleted file mode 100644
index 11ecaa0..0000000
--- a/lib/tdb/tools/tdbbackup.c
+++ /dev/null
@@ -1,342 +0,0 @@
-/* 
-   Unix SMB/CIFS implementation.
-   low level tdb backup and restore utility
-   Copyright (C) Andrew Tridgell              2002
-
-   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 3 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, see <http://www.gnu.org/licenses/>.
-*/
-
-/*
-
-  This program is meant for backup/restore of tdb databases. Typical usage would be:
-     tdbbackup *.tdb
-  when Samba shuts down cleanly, which will make a backup of all the local databases
-  to *.bak files. Then on Samba startup you would use:
-     tdbbackup -v *.tdb
-  and this will check the databases for corruption and if corruption is detected then
-  the backup will be restored.
-
-  You may also like to do a backup on a regular basis while Samba is
-  running, perhaps using cron.
-
-  The reason this program is needed is to cope with power failures
-  while Samba is running. A power failure could lead to database
-  corruption and Samba will then not start correctly.
-
-  Note that many of the databases in Samba are transient and thus
-  don't need to be backed up, so you can optimise the above a little
-  by only running the backup on the critical databases.
-
- */
-
-#include "replace.h"
-#include "system/locale.h"
-#include "system/time.h"
-#include "system/filesys.h"
-#include "system/wait.h"
-#include "tdb.h"
-
-#ifdef HAVE_GETOPT_H
-#include <getopt.h>
-#endif
-
-static int failed;
-
-static struct tdb_logging_context log_ctx;
-
-#ifdef PRINTF_ATTRIBUTE
-static void tdb_log(struct tdb_context *tdb, enum tdb_debug_level level, const char *format, ...) PRINTF_ATTRIBUTE(3,4);
-#endif
-static void tdb_log(struct tdb_context *tdb, enum tdb_debug_level level, const char *format, ...)
-{
-	va_list ap;
-    
-	va_start(ap, format);
-	vfprintf(stdout, format, ap);
-	va_end(ap);
-	fflush(stdout);
-}
-
-static char *add_suffix(const char *name, const char *suffix)
-{
-	char *ret;
-	int len = strlen(name) + strlen(suffix) + 1;
-	ret = (char *)malloc(len);
-	if (!ret) {
-		fprintf(stderr,"Out of memory!\n");
-		exit(1);
-	}
-	snprintf(ret, len, "%s%s", name, suffix);
-	return ret;
-}
-
-static int copy_fn(TDB_CONTEXT *tdb, TDB_DATA key, TDB_DATA dbuf, void *state)
-{
-	TDB_CONTEXT *tdb_new = (TDB_CONTEXT *)state;
-
-	if (tdb_store(tdb_new, key, dbuf, TDB_INSERT) != 0) {
-		fprintf(stderr,"Failed to insert into %s\n", tdb_name(tdb_new));
-		failed = 1;
-		return 1;
-	}
-	return 0;
-}
-
-
-static int test_fn(TDB_CONTEXT *tdb, TDB_DATA key, TDB_DATA dbuf, void *state)
-{
-	return 0;
-}
-
-/*
-  carefully backup a tdb, validating the contents and
-  only doing the backup if its OK
-  this function is also used for restore
-*/
-static int backup_tdb(const char *old_name, const char *new_name, int hash_size)
-{
-	TDB_CONTEXT *tdb;
-	TDB_CONTEXT *tdb_new;
-	char *tmp_name;
-	struct stat st;
-	int count1, count2;
-
-	tmp_name = add_suffix(new_name, ".tmp");
-
-	/* stat the old tdb to find its permissions */
-	if (stat(old_name, &st) != 0) {
-		perror(old_name);
-		free(tmp_name);
-		return 1;
-	}
-
-	/* open the old tdb */
-	tdb = tdb_open_ex(old_name, 0, 0, 
-			  O_RDWR, 0, &log_ctx, NULL);
-	if (!tdb) {
-		printf("Failed to open %s\n", old_name);
-		free(tmp_name);
-		return 1;
-	}
-
-	/* create the new tdb */
-	unlink(tmp_name);
-	tdb_new = tdb_open_ex(tmp_name, 
-			      hash_size ? hash_size : tdb_hash_size(tdb), 
-			      TDB_DEFAULT, 
-			      O_RDWR|O_CREAT|O_EXCL, st.st_mode & 0777, 
-			      &log_ctx, NULL);
-	if (!tdb_new) {
-		perror(tmp_name);
-		free(tmp_name);
-		return 1;
-	}
-
-	if (tdb_transaction_start(tdb) != 0) {
-		printf("Failed to start transaction on old tdb\n");
-		tdb_close(tdb);
-		tdb_close(tdb_new);
-		unlink(tmp_name);
-		free(tmp_name);
-		return 1;
-	}
-
-	/* lock the backup tdb so that nobody else can change it */
-	if (tdb_lockall(tdb_new) != 0) {
-		printf("Failed to lock backup tdb\n");
-		tdb_close(tdb);
-		tdb_close(tdb_new);
-		unlink(tmp_name);
-		free(tmp_name);
-		return 1;
-	}
-
-	failed = 0;
-
-	/* traverse and copy */
-	count1 = tdb_traverse(tdb, copy_fn, (void *)tdb_new);
-	if (count1 < 0 || failed) {
-		fprintf(stderr,"failed to copy %s\n", old_name);
-		tdb_close(tdb);
-		tdb_close(tdb_new);
-		unlink(tmp_name);
-		free(tmp_name);
-		return 1;
-	}
-
-	/* close the old tdb */
-	tdb_close(tdb);
-
-	/* copy done, unlock the backup tdb */
-	tdb_unlockall(tdb_new);
-
-#ifdef HAVE_FDATASYNC
-	if (fdatasync(tdb_fd(tdb_new)) != 0) {
-#else
-	if (fsync(tdb_fd(tdb_new)) != 0) {
-#endif
-		/* not fatal */
-		fprintf(stderr, "failed to fsync backup file\n");
-	}
-
-	/* close the new tdb and re-open read-only */
-	tdb_close(tdb_new);
-	tdb_new = tdb_open_ex(tmp_name, 
-			      0,
-			      TDB_DEFAULT, 
-			      O_RDONLY, 0,
-			      &log_ctx, NULL);
-	if (!tdb_new) {
-		fprintf(stderr,"failed to reopen %s\n", tmp_name);
-		unlink(tmp_name);
-		perror(tmp_name);
-		free(tmp_name);
-		return 1;
-	}
-	
-	/* traverse the new tdb to confirm */
-	count2 = tdb_traverse(tdb_new, test_fn, NULL);
-	if (count2 != count1) {
-		fprintf(stderr,"failed to copy %s\n", old_name);
-		tdb_close(tdb_new);
-		unlink(tmp_name);
-		free(tmp_name);
-		return 1;
-	}
-
-	/* close the new tdb and rename it to .bak */
-	tdb_close(tdb_new);
-	if (rename(tmp_name, new_name) != 0) {
-		perror(new_name);
-		free(tmp_name);
-		return 1;
-	}
-
-	free(tmp_name);
-
-	return 0;
-}
-
-/*
-  verify a tdb and if it is corrupt then restore from *.bak
-*/
-static int verify_tdb(const char *fname, const char *bak_name)
-{
-	TDB_CONTEXT *tdb;
-	int count = -1;
-
-	/* open the tdb */
-	tdb = tdb_open_ex(fname, 0, 0, 
-			  O_RDONLY, 0, &log_ctx, NULL);
-
-	/* traverse the tdb, then close it */
-	if (tdb) {
-		count = tdb_traverse(tdb, test_fn, NULL);
-		tdb_close(tdb);
-	}
-
-	/* count is < 0 means an error */
-	if (count < 0) {
-		printf("restoring %s\n", fname);
-		return backup_tdb(bak_name, fname, 0);
-	}
-
-	printf("%s : %d records\n", fname, count);
-
-	return 0;
-}
-
-/*
-  see if one file is newer than another
-*/
-static int file_newer(const char *fname1, const char *fname2)
-{
-	struct stat st1, st2;
-	if (stat(fname1, &st1) != 0) {
-		return 0;
-	}
-	if (stat(fname2, &st2) != 0) {
-		return 1;
-	}
-	return (st1.st_mtime > st2.st_mtime);
-}
-
-static void usage(void)
-{
-	printf("Usage: tdbbackup [options] <fname...>\n\n");
-	printf("   -h            this help message\n");
-	printf("   -s suffix     set the backup suffix\n");
-	printf("   -v            verify mode (restore if corrupt)\n");
-	printf("   -n hashsize   set the new hash size for the backup\n");
-}
-		
-
- int main(int argc, char *argv[])
-{
-	int i;
-	int ret = 0;
-	int c;
-	int verify = 0;
-	int hashsize = 0;
-	const char *suffix = ".bak";
-
-	log_ctx.log_fn = tdb_log;
-
-	while ((c = getopt(argc, argv, "vhs:n:")) != -1) {
-		switch (c) {
-		case 'h':
-			usage();
-			exit(0);
-		case 'v':
-			verify = 1;
-			break;
-		case 's':
-			suffix = optarg;
-			break;
-		case 'n':
-			hashsize = atoi(optarg);
-			break;
-		}
-	}
-
-	argc -= optind;
-	argv += optind;
-
-	if (argc < 1) {
-		usage();
-		exit(1);
-	}
-
-	for (i=0; i<argc; i++) {
-		const char *fname = argv[i];
-		char *bak_name;
-
-		bak_name = add_suffix(fname, suffix);
-
-		if (verify) {
-			if (verify_tdb(fname, bak_name) != 0) {
-				ret = 1;
-			}
-		} else {
-			if (file_newer(fname, bak_name) &&
-			    backup_tdb(fname, bak_name, hashsize) != 0) {
-				ret = 1;
-			}
-		}
-
-		free(bak_name);
-	}
-
-	return ret;
-}
diff --git a/lib/tdb/tools/tdbdump.c b/lib/tdb/tools/tdbdump.c
deleted file mode 100644
index 027fda3..0000000
--- a/lib/tdb/tools/tdbdump.c
+++ /dev/null
@@ -1,116 +0,0 @@
-/* 
-   Unix SMB/CIFS implementation.
-   simple tdb dump util
-   Copyright (C) Andrew Tridgell              2001
-
-   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 3 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, see <http://www.gnu.org/licenses/>.
-*/
-
-#include "replace.h"
-#include "system/locale.h"
-#include "system/time.h"
-#include "system/filesys.h"
-#include "system/wait.h"
-#include "tdb.h"
-
-static void print_data(TDB_DATA d)
-{
-	unsigned char *p = (unsigned char *)d.dptr;
-	int len = d.dsize;
-	while (len--) {
-		if (isprint(*p) && !strchr("\"\\", *p)) {
-			fputc(*p, stdout);
-		} else {
-			printf("\\%02X", *p);
-		}
-		p++;
-	}
-}
-
-static int traverse_fn(TDB_CONTEXT *tdb, TDB_DATA key, TDB_DATA dbuf, void *state)
-{
-	printf("{\n");
-	printf("key(%d) = \"", (int)key.dsize);
-	print_data(key);
-	printf("\"\n");
-	printf("data(%d) = \"", (int)dbuf.dsize);
-	print_data(dbuf);
-	printf("\"\n");
-	printf("}\n");
-	return 0;
-}
-
-static int dump_tdb(const char *fname, const char *keyname)
-{
-	TDB_CONTEXT *tdb;
-	TDB_DATA key, value;
-	
-	tdb = tdb_open(fname, 0, 0, O_RDONLY, 0);
-	if (!tdb) {
-		printf("Failed to open %s\n", fname);
-		return 1;
-	}
-
-	if (!keyname) {
-		tdb_traverse(tdb, traverse_fn, NULL);
-	} else {
-		key.dptr = discard_const_p(uint8_t, keyname);
-		key.dsize = strlen(keyname);
-		value = tdb_fetch(tdb, key);
-		if (!value.dptr) {
-			return 1;
-		} else {
-			print_data(value);
-			free(value.dptr);
-		}
-	}
-
-	return 0;
-}
-
-static void usage( void)
-{
-	printf( "Usage: tdbdump [options] <filename>\n\n");
-	printf( "   -h          this help message\n");
-	printf( "   -k keyname  dumps value of keyname\n");
-}
-
- int main(int argc, char *argv[])
-{
-	char *fname, *keyname=NULL;
-	int c;
-
-	if (argc < 2) {
-		printf("Usage: tdbdump <fname>\n");
-		exit(1);
-	}
-
-	while ((c = getopt( argc, argv, "hk:")) != -1) {
-		switch (c) {
-		case 'h':
-			usage();
-			exit( 0);
-		case 'k':
-			keyname = optarg;
-			break;
-		default:
-			usage();
-			exit( 1);
-		}
-	}
-
-	fname = argv[optind];
-
-	return dump_tdb(fname, keyname);
-}
diff --git a/lib/tdb/tools/tdbrestore.c b/lib/tdb/tools/tdbrestore.c
deleted file mode 100644
index 8106cf9..0000000
--- a/lib/tdb/tools/tdbrestore.c
+++ /dev/null
@@ -1,224 +0,0 @@
-/*
-   tdbrestore -- construct a tdb from tdbdump output.
-   Copyright (C) Volker Lendecke		2010
-   Copyright (C) Simon McVittie			2005
-
-   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 3 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, see <http://www.gnu.org/licenses/>.
-*/
-
-#include <assert.h>
-#include "replace.h"
-#include "system/locale.h"
-#include "system/time.h"
-#include "system/filesys.h"
-#include "system/wait.h"
-#include "tdb.h"
-
-#define debug_fprintf(file, fmt, ...) do {/*nothing*/} while (0)
-
-static int read_linehead(FILE *f)
-{
-	int i, c;
-	int num_bytes;
-	char prefix[128];
-
-	while (1) {
-		c = getc(f);
-		if (c == EOF) {
-			return -1;
-		}
-		if (c == '(') {
-			break;
-		}
-	}
-	for (i=0; i<sizeof(prefix); i++) {
-		c = getc(f);
-		if (c == EOF) {
-			return -1;
-		}
-		prefix[i] = c;
-		if (c == '"') {
-			break;
-		}
-	}
-	if (i == sizeof(prefix)) {
-		return -1;
-	}
-	prefix[i] = '\0';
-
-	if (sscanf(prefix, "%d) = ", &num_bytes) != 1) {
-		return -1;
-	}
-	return num_bytes;
-}
-
-static int read_hex(void) {
-	int c;
-	c = getchar();
-	if (c == EOF) {
-		fprintf(stderr, "Unexpected EOF in data\n");
-		return -1;
-	} else if (c == '"') {
-		fprintf(stderr, "Unexpected \\\" sequence\n");
-		return -1;
-	} else if ('0' <= c && c <= '9')  {
-		return c - '0';
-	} else if ('A' <= c && c <= 'F')  {
-		return c - 'A' + 10;
-	} else if ('a' <= c && c <= 'f')  {
-		return c - 'a' + 10;
-	} else {
-		fprintf(stderr, "Invalid hex: %c\n", c);
-		return -1;
-	}
-}
-
-static int read_data(FILE *f, TDB_DATA *d, size_t size) {
-	int c, low, high;
-	int i;
-
-	d->dptr = (unsigned char *)malloc(size);
-	if (d->dptr == NULL) {
-		return -1;
-	}
-	d->dsize = size;
-
-	for (i=0; i<size; i++) {
-		c = getc(f);
-		if (c == EOF) {
-			fprintf(stderr, "Unexpected EOF in data\n");
-			return 1;
-		} else if (c == '"') {
-			return 0;
-		} else if (c == '\\') {
-			high = read_hex();
-			if (high < 0) {
-				return -1;
-			}
-			high = high << 4;
-			assert(high == (high & 0xf0));
-			low = read_hex();
-			if (low < 0) {
-				return -1;
-			}
-			assert(low == (low & 0x0f));
-			d->dptr[i] = (low|high);
-		} else {
-			d->dptr[i] = c;
-		}
-	}
-	return 0;
-}
-
-static int swallow(FILE *f, const char *s, int *eof)
-{
-	char line[128];
-
-	if (fgets(line, sizeof(line), f) == NULL) {
-		if (eof != NULL) {
-			*eof = 1;
-		}
-		return -1;
-	}
-	if (strcmp(line, s) != 0) {
-		return -1;
-	}
-	return 0;
-}
-
-static int read_rec(FILE *f, TDB_CONTEXT *tdb, int *eof)
-{
-	int length;
-	TDB_DATA key, data;
-	int ret = -1;
-
-	key.dptr = NULL;
-	data.dptr = NULL;
-
-	if (swallow(f, "{\n", eof) == -1) {
-		goto fail;
-	}
-	length = read_linehead(f);
-	if (length == -1) {
-		goto fail;
-	}
-	if (read_data(f, &key, length) == -1) {
-		goto fail;
-	}
-	if (swallow(f, "\"\n", NULL) == -1) {
-		goto fail;
-	}
-	length = read_linehead(f);
-	if (length == -1) {
-		goto fail;
-	}
-	if (read_data(f, &data, length) == -1) {
-		goto fail;
-	}
-	if ((swallow(f, "\"\n", NULL) == -1)
-	    || (swallow(f, "}\n", NULL) == -1)) {
-		goto fail;
-	}
-	if (tdb_store(tdb, key, data, TDB_INSERT) != 0) {
-		fprintf(stderr, "TDB error: %s\n", tdb_errorstr(tdb));
-		goto fail;
-	}
-
-	ret = 0;
-fail:
-	free(key.dptr);
-	free(data.dptr);
-	return ret;
-}
-
-static int restore_tdb(const char *fname)
-{
-	TDB_CONTEXT *tdb;
-
-	tdb = tdb_open(fname, 0, 0, O_RDWR|O_CREAT|O_EXCL, 0666);
-	if (!tdb) {
-		perror("tdb_open");
-		fprintf(stderr, "Failed to open %s\n", fname);
-		return 1;
-	}
-
-	while (1) {
-		int eof = 0;
-		if (read_rec(stdin, tdb, &eof) == -1) {
-			if (eof) {
-				break;
-			}
-			return 1;
-		}
-	}
-	if (tdb_close(tdb)) {
-		fprintf(stderr, "Error closing tdb\n");
-		return 1;
-	}
-	return 0;
-}
-
-int main(int argc, char *argv[])
-{
-	char *fname;
-
-	if (argc < 2) {
-		printf("Usage: %s dbname < tdbdump_output\n", argv[0]);
-		exit(1);
-	}
-
-	fname = argv[1];
-
-	return restore_tdb(fname);
-}
diff --git a/lib/tdb/tools/tdbtest.c b/lib/tdb/tools/tdbtest.c
deleted file mode 100644
index 44c78ef..0000000
--- a/lib/tdb/tools/tdbtest.c
+++ /dev/null
@@ -1,290 +0,0 @@
-/* a test program for tdb - the trivial database */
-
-#include "replace.h"
-#include "tdb.h"
-#include "system/filesys.h"
-#include "system/time.h"
-
-#include <gdbm.h>
-
-
-#define DELETE_PROB 7
-#define STORE_PROB 5
-
-static struct tdb_context *db;
-static GDBM_FILE gdbm;
-
-struct timeval tp1,tp2;
-
-static void _start_timer(void)
-{
-	gettimeofday(&tp1,NULL);
-}
-
-static double _end_timer(void)
-{
-	gettimeofday(&tp2,NULL);
-	return((tp2.tv_sec - tp1.tv_sec) + 
-	       (tp2.tv_usec - tp1.tv_usec)*1.0e-6);
-}
-
-static void fatal(const char *why)
-{
-	perror(why);
-	exit(1);
-}
-
-#ifdef PRINTF_ATTRIBUTE
-static void tdb_log(struct tdb_context *tdb, int level, const char *format, ...) PRINTF_ATTRIBUTE(3,4);
-#endif
-static void tdb_log(struct tdb_context *tdb, int level, const char *format, ...)
-{
-	va_list ap;
-    
-	va_start(ap, format);
-	vfprintf(stdout, format, ap);
-	va_end(ap);
-	fflush(stdout);
-}
-
-static void compare_db(void)
-{
-	TDB_DATA d, key, nextkey;
-	datum gd, gkey, gnextkey;
-
-	key = tdb_firstkey(db);
-	while (key.dptr) {
-		d = tdb_fetch(db, key);
-		gkey.dptr = key.dptr;
-		gkey.dsize = key.dsize;
-
-		gd = gdbm_fetch(gdbm, gkey);
-
-		if (!gd.dptr) fatal("key not in gdbm");
-		if (gd.dsize != d.dsize) fatal("data sizes differ");
-		if (memcmp(gd.dptr, d.dptr, d.dsize)) {
-			fatal("data differs");
-		}
-
-		nextkey = tdb_nextkey(db, key);
-		free(key.dptr);
-		free(d.dptr);
-		free(gd.dptr);
-		key = nextkey;
-	}
-
-	gkey = gdbm_firstkey(gdbm);
-	while (gkey.dptr) {
-		gd = gdbm_fetch(gdbm, gkey);
-		key.dptr = gkey.dptr;
-		key.dsize = gkey.dsize;
-
-		d = tdb_fetch(db, key);
-
-		if (!d.dptr) fatal("key not in db");
-		if (d.dsize != gd.dsize) fatal("data sizes differ");
-		if (memcmp(d.dptr, gd.dptr, gd.dsize)) {
-			fatal("data differs");
-		}
-
-		gnextkey = gdbm_nextkey(gdbm, gkey);
-		free(gkey.dptr);
-		free(gd.dptr);
-		free(d.dptr);
-		gkey = gnextkey;
-	}
-}
-
-static char *randbuf(int len)
-{
-	char *buf;
-	int i;
-	buf = (char *)malloc(len+1);
-
-	for (i=0;i<len;i++) {
-		buf[i] = 'a' + (rand() % 26);
-	}
-	buf[i] = 0;
-	return buf;
-}
-
-static void addrec_db(void)
-{
-	int klen, dlen;
-	char *k, *d;
-	TDB_DATA key, data;
-
-	klen = 1 + (rand() % 4);
-	dlen = 1 + (rand() % 100);
-
-	k = randbuf(klen);
-	d = randbuf(dlen);
-
-	key.dptr = k;
-	key.dsize = klen+1;
-
-	data.dptr = d;
-	data.dsize = dlen+1;
-
-	if (rand() % DELETE_PROB == 0) {
-		tdb_delete(db, key);
-	} else if (rand() % STORE_PROB == 0) {
-		if (tdb_store(db, key, data, TDB_REPLACE) != 0) {
-			fatal("tdb_store failed");
-		}
-	} else {
-		data = tdb_fetch(db, key);
-		if (data.dptr) free(data.dptr);
-	}
-
-	free(k);
-	free(d);
-}
-
-static void addrec_gdbm(void)
-{
-	int klen, dlen;
-	char *k, *d;
-	datum key, data;
-
-	klen = 1 + (rand() % 4);
-	dlen = 1 + (rand() % 100);
-
-	k = randbuf(klen);
-	d = randbuf(dlen);
-
-	key.dptr = k;
-	key.dsize = klen+1;
-
-	data.dptr = d;
-	data.dsize = dlen+1;
-
-	if (rand() % DELETE_PROB == 0) {
-		gdbm_delete(gdbm, key);
-	} else if (rand() % STORE_PROB == 0) {
-		if (gdbm_store(gdbm, key, data, GDBM_REPLACE) != 0) {
-			fatal("gdbm_store failed");
-		}
-	} else {
-		data = gdbm_fetch(gdbm, key);
-		if (data.dptr) free(data.dptr);
-	}
-
-	free(k);
-	free(d);
-}
-
-static int traverse_fn(struct tdb_context *tdb, TDB_DATA key, TDB_DATA dbuf, void *state)
-{
-#if 0
-	printf("[%s] [%s]\n", key.dptr, dbuf.dptr);
-#endif
-	tdb_delete(tdb, key);
-	return 0;
-}
-
-static void merge_test(void)
-{
-	int i;
-	char keys[5][2];
-	char tdata[] = "test";
-	TDB_DATA key, data;
-	
-	for (i = 0; i < 5; i++) {
-		snprintf(keys[i],2, "%d", i);
-		key.dptr = keys[i];
-		key.dsize = 2;
-		
-		data.dptr = tdata;
-		data.dsize = 4;
-		
-		if (tdb_store(db, key, data, TDB_REPLACE) != 0) {
-			fatal("tdb_store failed");
-		}
-	}
-
-	key.dptr = keys[0];
-	tdb_delete(db, key);
-	key.dptr = keys[4];
-	tdb_delete(db, key);
-	key.dptr = keys[2];
-	tdb_delete(db, key);
-	key.dptr = keys[1];
-	tdb_delete(db, key);
-	key.dptr = keys[3];
-	tdb_delete(db, key);
-}
-
-static char *test_path(const char *filename)
-{
-	const char *prefix = getenv("TEST_DATA_PREFIX");
-
-	if (prefix) {
-		char *path = NULL;
-		int ret;
-
-		ret = asprintf(&path, "%s/%s", prefix, filename);
-		if (ret == -1) {
-			return NULL;
-		}
-		return path;
-	}
-
-	return strdup(filename);
-}
-
- int main(int argc, const char *argv[])
-{
-	int i, seed=0;
-	int loops = 10000;
-	int num_entries;
-	char test_gdbm[1] = "test.gdbm";
-	char *test_tdb;
-
-	test_gdbm[0] = test_path("test.gdbm");
-	test_tdb = test_path("test.tdb");
-
-	unlink(test_gdbm[0]);
-
-	db = tdb_open(test_tdb, 0, TDB_CLEAR_IF_FIRST,
-		      O_RDWR | O_CREAT | O_TRUNC, 0600);
-	gdbm = gdbm_open(test_gdbm, 512, GDBM_WRITER|GDBM_NEWDB|GDBM_FAST, 
-			 0600, NULL);
-
-	if (!db || !gdbm) {
-		fatal("db open failed");
-	}
-
-#if 1
-	srand(seed);
-	_start_timer();
-	for (i=0;i<loops;i++) addrec_gdbm();
-	printf("gdbm got %.2f ops/sec\n", i/_end_timer());
-#endif
-
-	merge_test();
-
-	srand(seed);
-	_start_timer();
-	for (i=0;i<loops;i++) addrec_db();
-	printf("tdb got %.2f ops/sec\n", i/_end_timer());
-
-	if (tdb_validate_freelist(db, &num_entries) == -1) {
-		printf("tdb freelist is corrupt\n");
-	} else {
-		printf("tdb freelist is good (%d entries)\n", num_entries);
-	}
-
-	compare_db();
-
-	printf("traversed %d records\n", tdb_traverse(db, traverse_fn, NULL));
-	printf("traversed %d records\n", tdb_traverse(db, traverse_fn, NULL));
-
-	tdb_close(db);
-	gdbm_close(gdbm);
-
-	free(test_gdbm[0]);
-	free(test_tdb);
-
-	return 0;
-}
diff --git a/lib/tdb/tools/tdbtool.c b/lib/tdb/tools/tdbtool.c
deleted file mode 100644
index dc5747f..0000000
--- a/lib/tdb/tools/tdbtool.c
+++ /dev/null
@@ -1,785 +0,0 @@
-/* 
-   Unix SMB/CIFS implementation.
-   Samba database functions
-   Copyright (C) Andrew Tridgell              1999-2000
-   Copyright (C) Paul `Rusty' Russell		   2000
-   Copyright (C) Jeremy Allison			   2000
-   Copyright (C) Andrew Esh                        2001
-
-   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 3 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, see <http://www.gnu.org/licenses/>.
-*/
-
-#include "replace.h"
-#include "system/locale.h"
-#include "system/time.h"
-#include "system/filesys.h"
-#include "system/wait.h"
-#include "tdb.h"
-
-static int do_command(void);
-const char *cmdname;
-char *arg1, *arg2;
-size_t arg1len, arg2len;
-int bIterate = 0;
-char *line;
-TDB_DATA iterate_kbuf;
-char cmdline[1024];
-static int disable_mmap;
-
-enum commands {
-	CMD_CREATE_TDB,
-	CMD_OPEN_TDB,
-	CMD_TRANSACTION_START,
-	CMD_TRANSACTION_COMMIT,
-	CMD_TRANSACTION_CANCEL,
-	CMD_ERASE,
-	CMD_DUMP,
-	CMD_INSERT,
-	CMD_MOVE,
-	CMD_STORE,
-	CMD_SHOW,
-	CMD_KEYS,
-	CMD_HEXKEYS,
-	CMD_DELETE,
-	CMD_LIST_HASH_FREE,
-	CMD_LIST_FREE,
-	CMD_INFO,
-	CMD_MMAP,
-	CMD_SPEED,
-	CMD_FIRST,
-	CMD_NEXT,
-	CMD_SYSTEM,
-	CMD_CHECK,
-	CMD_REPACK,
-	CMD_QUIT,
-	CMD_HELP
-};
-
-typedef struct {
-	const char *name;
-	enum commands cmd;
-} COMMAND_TABLE;
-
-COMMAND_TABLE cmd_table[] = {
-	{"create",	CMD_CREATE_TDB},
-	{"open",	CMD_OPEN_TDB},
-	{"transaction_start",	CMD_TRANSACTION_START},
-	{"transaction_commit",	CMD_TRANSACTION_COMMIT},
-	{"transaction_cancel",	CMD_TRANSACTION_CANCEL},
-	{"erase",	CMD_ERASE},
-	{"dump",	CMD_DUMP},
-	{"insert",	CMD_INSERT},
-	{"move",	CMD_MOVE},
-	{"store",	CMD_STORE},
-	{"show",	CMD_SHOW},
-	{"keys",	CMD_KEYS},
-	{"hexkeys",	CMD_HEXKEYS},
-	{"delete",	CMD_DELETE},
-	{"list",	CMD_LIST_HASH_FREE},
-	{"free",	CMD_LIST_FREE},
-	{"info",	CMD_INFO},
-	{"speed",	CMD_SPEED},
-	{"mmap",	CMD_MMAP},
-	{"first",	CMD_FIRST},
-	{"1",		CMD_FIRST},
-	{"next",	CMD_NEXT},
-	{"n",		CMD_NEXT},
-	{"check",	CMD_CHECK},
-	{"quit",	CMD_QUIT},
-	{"q",		CMD_QUIT},
-	{"!",		CMD_SYSTEM},
-	{"repack",	CMD_REPACK},
-	{NULL,		CMD_HELP}
-};
-
-struct timeval tp1,tp2;
-
-static void _start_timer(void)
-{
-	gettimeofday(&tp1,NULL);
-}
-
-static double _end_timer(void)
-{
-	gettimeofday(&tp2,NULL);
-	return((tp2.tv_sec - tp1.tv_sec) + 
-	       (tp2.tv_usec - tp1.tv_usec)*1.0e-6);
-}
-
-#ifdef PRINTF_ATTRIBUTE
-static void tdb_log(struct tdb_context *tdb, enum tdb_debug_level level, const char *format, ...) PRINTF_ATTRIBUTE(3,4);
-#endif
-static void tdb_log(struct tdb_context *tdb, enum tdb_debug_level level, const char *format, ...)
-{
-	va_list ap;
-
-	va_start(ap, format);
-	vfprintf(stderr, format, ap);
-	va_end(ap);
-}
-
-/* a tdb tool for manipulating a tdb database */
-
-static TDB_CONTEXT *tdb;
-
-static int print_rec(TDB_CONTEXT *the_tdb, TDB_DATA key, TDB_DATA dbuf, void *state);
-static int print_key(TDB_CONTEXT *the_tdb, TDB_DATA key, TDB_DATA dbuf, void *state);
-static int print_hexkey(TDB_CONTEXT *the_tdb, TDB_DATA key, TDB_DATA dbuf, void *state);
-
-static void print_asc(const char *buf,int len)
-{
-	int i;
-
-	/* We're probably printing ASCII strings so don't try to display
-	   the trailing NULL character. */
-
-	if (buf[len - 1] == 0)
-	        len--;
-
-	for (i=0;i<len;i++)
-		printf("%c",isprint(buf[i])?buf[i]:'.');
-}
-
-static void print_data(const char *buf,int len)
-{
-	int i=0;
-	if (len<=0) return;
-	printf("[%03X] ",i);
-	for (i=0;i<len;) {
-		printf("%02X ",(int)((unsigned char)buf[i]));
-		i++;
-		if (i%8 == 0) printf(" ");
-		if (i%16 == 0) {      
-			print_asc(&buf[i-16],8); printf(" ");
-			print_asc(&buf[i-8],8); printf("\n");
-			if (i<len) printf("[%03X] ",i);
-		}
-	}
-	if (i%16) {
-		int n;
-		
-		n = 16 - (i%16);
-		printf(" ");
-		if (n>8) printf(" ");
-		while (n--) printf("   ");
-		
-		n = i%16;
-		if (n > 8) n = 8;
-		print_asc(&buf[i-(i%16)],n); printf(" ");
-		n = (i%16) - n;
-		if (n>0) print_asc(&buf[i-n],n); 
-		printf("\n");    
-	}
-}
-
-static void help(void)
-{
-	printf("\n"
-"tdbtool: \n"
-"  create    dbname     : create a database\n"
-"  open      dbname     : open an existing database\n"
-"  transaction_start    : start a transaction\n"
-"  transaction_commit   : commit a transaction\n"
-"  transaction_cancel   : cancel a transaction\n"
-"  erase                : erase the database\n"
-"  dump                 : dump the database as strings\n"
-"  keys                 : dump the database keys as strings\n"
-"  hexkeys              : dump the database keys as hex values\n"
-"  info                 : print summary info about the database\n"
-"  insert    key  data  : insert a record\n"
-"  move      key  file  : move a record to a destination tdb\n"
-"  store     key  data  : store a record (replace)\n"
-"  show      key        : show a record by key\n"
-"  delete    key        : delete a record by key\n"
-"  list                 : print the database hash table and freelist\n"
-"  free                 : print the database freelist\n"
-"  check                : check the integrity of an opened database\n"
-"  repack               : repack the database\n"
-"  speed                : perform speed tests on the database\n"
-"  ! command            : execute system command\n"
-"  1 | first            : print the first record\n"
-"  n | next             : print the next record\n"
-"  q | quit             : terminate\n"
-"  \\n                   : repeat 'next' command\n"
-"\n");
-}
-
-static void terror(const char *why)
-{
-	printf("%s\n", why);
-}
-
-static void create_tdb(const char *tdbname)
-{
-	struct tdb_logging_context log_ctx;
-	log_ctx.log_fn = tdb_log;
-
-	if (tdb) tdb_close(tdb);
-	tdb = tdb_open_ex(tdbname, 0, TDB_CLEAR_IF_FIRST | (disable_mmap?TDB_NOMMAP:0),
-			  O_RDWR | O_CREAT | O_TRUNC, 0600, &log_ctx, NULL);
-	if (!tdb) {
-		printf("Could not create %s: %s\n", tdbname, strerror(errno));
-	}
-}
-
-static void open_tdb(const char *tdbname)
-{
-	struct tdb_logging_context log_ctx;
-	log_ctx.log_fn = tdb_log;
-
-	if (tdb) tdb_close(tdb);
-	tdb = tdb_open_ex(tdbname, 0, disable_mmap?TDB_NOMMAP:0, O_RDWR, 0600,
-			  &log_ctx, NULL);
-	if (!tdb) {
-		printf("Could not open %s: %s\n", tdbname, strerror(errno));
-	}
-}
-
-static void insert_tdb(char *keyname, size_t keylen, char* data, size_t datalen)
-{
-	TDB_DATA key, dbuf;
-
-	if ((keyname == NULL) || (keylen == 0)) {
-		terror("need key");
-		return;
-	}
-
-	key.dptr = (unsigned char *)keyname;
-	key.dsize = keylen;
-	dbuf.dptr = (unsigned char *)data;
-	dbuf.dsize = datalen;
-
-	if (tdb_store(tdb, key, dbuf, TDB_INSERT) != 0) {
-		terror("insert failed");
-	}
-}
-
-static void store_tdb(char *keyname, size_t keylen, char* data, size_t datalen)
-{
-	TDB_DATA key, dbuf;
-
-	if ((keyname == NULL) || (keylen == 0)) {
-		terror("need key");
-		return;
-	}
-
-	if ((data == NULL) || (datalen == 0)) {
-		terror("need data");
-		return;
-	}
-
-	key.dptr = (unsigned char *)keyname;
-	key.dsize = keylen;
-	dbuf.dptr = (unsigned char *)data;
-	dbuf.dsize = datalen;
-
-	printf("Storing key:\n");
-	print_rec(tdb, key, dbuf, NULL);
-
-	if (tdb_store(tdb, key, dbuf, TDB_REPLACE) != 0) {
-		terror("store failed");
-	}
-}
-
-static void show_tdb(char *keyname, size_t keylen)
-{
-	TDB_DATA key, dbuf;
-
-	if ((keyname == NULL) || (keylen == 0)) {
-		terror("need key");
-		return;
-	}
-
-	key.dptr = (unsigned char *)keyname;
-	key.dsize = keylen;
-
-	dbuf = tdb_fetch(tdb, key);
-	if (!dbuf.dptr) {
-	    terror("fetch failed");
-	    return;
-	}
-	
-	print_rec(tdb, key, dbuf, NULL);
-	
-	free( dbuf.dptr );
-	
-	return;
-}
-
-static void delete_tdb(char *keyname, size_t keylen)
-{
-	TDB_DATA key;
-
-	if ((keyname == NULL) || (keylen == 0)) {
-		terror("need key");
-		return;
-	}
-
-	key.dptr = (unsigned char *)keyname;
-	key.dsize = keylen;
-
-	if (tdb_delete(tdb, key) != 0) {
-		terror("delete failed");
-	}
-}
-
-static void move_rec(char *keyname, size_t keylen, char* tdbname)
-{
-	TDB_DATA key, dbuf;
-	TDB_CONTEXT *dst_tdb;
-
-	if ((keyname == NULL) || (keylen == 0)) {
-		terror("need key");
-		return;
-	}
-
-	if ( !tdbname ) {
-		terror("need destination tdb name");
-		return;
-	}
-
-	key.dptr = (unsigned char *)keyname;
-	key.dsize = keylen;
-
-	dbuf = tdb_fetch(tdb, key);
-	if (!dbuf.dptr) {
-		terror("fetch failed");
-		return;
-	}
-	
-	print_rec(tdb, key, dbuf, NULL);
-	
-	dst_tdb = tdb_open(tdbname, 0, 0, O_RDWR, 0600);
-	if ( !dst_tdb ) {
-		terror("unable to open destination tdb");
-		return;
-	}
-	
-	if (tdb_store( dst_tdb, key, dbuf, TDB_REPLACE ) != 0) {
-		terror("failed to move record");
-	}
-	else
-		printf("record moved\n");
-	
-	tdb_close( dst_tdb );
-	
-	return;
-}
-
-static int print_rec(TDB_CONTEXT *the_tdb, TDB_DATA key, TDB_DATA dbuf, void *state)
-{
-	printf("\nkey %d bytes\n", (int)key.dsize);
-	print_asc((const char *)key.dptr, key.dsize);
-	printf("\ndata %d bytes\n", (int)dbuf.dsize);
-	print_data((const char *)dbuf.dptr, dbuf.dsize);
-	return 0;
-}
-
-static int print_key(TDB_CONTEXT *the_tdb, TDB_DATA key, TDB_DATA dbuf, void *state)
-{
-	printf("key %d bytes: ", (int)key.dsize);
-	print_asc((const char *)key.dptr, key.dsize);
-	printf("\n");
-	return 0;
-}
-
-static int print_hexkey(TDB_CONTEXT *the_tdb, TDB_DATA key, TDB_DATA dbuf, void *state)
-{
-	printf("key %d bytes\n", (int)key.dsize);
-	print_data((const char *)key.dptr, key.dsize);
-	printf("\n");
-	return 0;
-}
-
-static int total_bytes;
-
-static int traverse_fn(TDB_CONTEXT *the_tdb, TDB_DATA key, TDB_DATA dbuf, void *state)
-{
-	total_bytes += dbuf.dsize;
-	return 0;
-}
-
-static void info_tdb(void)
-{
-	char *summary = tdb_summary(tdb);
-
-	if (!summary) {
-		printf("Error = %s\n", tdb_errorstr(tdb));
-	} else {
-		printf("%s", summary);
-		free(summary);
-	}
-}
-
-static void speed_tdb(const char *tlimit)
-{
-	const char *str = "store test", *str2 = "transaction test";
-	unsigned timelimit = tlimit?atoi(tlimit):0;
-	double t;
-	int ops;
-	if (timelimit == 0) timelimit = 5;
-
-	ops = 0;
-	printf("Testing store speed for %u seconds\n", timelimit);
-	_start_timer();
-	do {
-		long int r = random();
-		TDB_DATA key, dbuf;
-		key.dptr = discard_const_p(uint8_t, str);
-		key.dsize = strlen((char *)key.dptr);
-		dbuf.dptr = (uint8_t *) &r;
-		dbuf.dsize = sizeof(r);
-		tdb_store(tdb, key, dbuf, TDB_REPLACE);
-		t = _end_timer();
-		ops++;
-	} while (t < timelimit);
-	printf("%10.3f ops/sec\n", ops/t);
-
-	ops = 0;
-	printf("Testing fetch speed for %u seconds\n", timelimit);
-	_start_timer();
-	do {
-		TDB_DATA key;
-		key.dptr = discard_const_p(uint8_t, str);
-		key.dsize = strlen((char *)key.dptr);
-		tdb_fetch(tdb, key);
-		t = _end_timer();
-		ops++;
-	} while (t < timelimit);
-	printf("%10.3f ops/sec\n", ops/t);
-
-	ops = 0;
-	printf("Testing transaction speed for %u seconds\n", timelimit);
-	_start_timer();
-	do {
-		long int r = random();
-		TDB_DATA key, dbuf;
-		key.dptr = discard_const_p(uint8_t, str2);
-		key.dsize = strlen((char *)key.dptr);
-		dbuf.dptr = (uint8_t *) &r;
-		dbuf.dsize = sizeof(r);
-		tdb_transaction_start(tdb);
-		tdb_store(tdb, key, dbuf, TDB_REPLACE);
-		tdb_transaction_commit(tdb);
-		t = _end_timer();
-		ops++;
-	} while (t < timelimit);
-	printf("%10.3f ops/sec\n", ops/t);
-
-	ops = 0;
-	printf("Testing traverse speed for %u seconds\n", timelimit);
-	_start_timer();
-	do {
-		tdb_traverse(tdb, traverse_fn, NULL);
-		t = _end_timer();
-		ops++;
-	} while (t < timelimit);
-	printf("%10.3f ops/sec\n", ops/t);
-}
-
-static void toggle_mmap(void)
-{
-	disable_mmap = !disable_mmap;
-	if (disable_mmap) {
-		printf("mmap is disabled\n");
-	} else {
-		printf("mmap is enabled\n");
-	}
-}
-
-static char *tdb_getline(const char *prompt)
-{
-	static char thisline[1024];
-	char *p;
-	fputs(prompt, stdout);
-	thisline[0] = 0;
-	p = fgets(thisline, sizeof(thisline)-1, stdin);
-	if (p) p = strchr(p, '\n');
-	if (p) *p = 0;
-	return p?thisline:NULL;
-}
-
-static int do_delete_fn(TDB_CONTEXT *the_tdb, TDB_DATA key, TDB_DATA dbuf,
-                     void *state)
-{
-    return tdb_delete(the_tdb, key);
-}
-
-static void first_record(TDB_CONTEXT *the_tdb, TDB_DATA *pkey)
-{
-	TDB_DATA dbuf;
-	*pkey = tdb_firstkey(the_tdb);
-	
-	dbuf = tdb_fetch(the_tdb, *pkey);
-	if (!dbuf.dptr) terror("fetch failed");
-	else {
-		print_rec(the_tdb, *pkey, dbuf, NULL);
-	}
-}
-
-static void next_record(TDB_CONTEXT *the_tdb, TDB_DATA *pkey)
-{
-	TDB_DATA dbuf;
-	*pkey = tdb_nextkey(the_tdb, *pkey);
-	
-	dbuf = tdb_fetch(the_tdb, *pkey);
-	if (!dbuf.dptr) 
-		terror("fetch failed");
-	else
-		print_rec(the_tdb, *pkey, dbuf, NULL);
-}
-
-static int count(TDB_DATA key, TDB_DATA data, void *private_data)
-{
-	(*(unsigned int *)private_data)++;
-	return 0;
-}
-
-static void check_db(TDB_CONTEXT *the_tdb)
-{
-	int tdbcount = 0;
-	if (!the_tdb)
-		printf("Error: No database opened!\n");
-	else if (tdb_check(the_tdb, count, &tdbcount) == -1)
-		printf("Integrity check for the opened database failed.\n");
-	else
-		printf("Database integrity is OK and has %d records.\n",
-		       tdbcount);
-}
-
-static int do_command(void)
-{
-	COMMAND_TABLE *ctp = cmd_table;
-	enum commands mycmd = CMD_HELP;
-	int cmd_len;
-
-	if (cmdname && strlen(cmdname) == 0) {
-		mycmd = CMD_NEXT;
-	} else {
-		while (ctp->name) {
-			cmd_len = strlen(ctp->name);
-			if (strncmp(ctp->name,cmdname,cmd_len) == 0) {
-				mycmd = ctp->cmd;
-				break;
-			}
-			ctp++;
-		}
-	}
-
-	switch (mycmd) {
-	case CMD_CREATE_TDB:
-		bIterate = 0;
-		create_tdb(arg1);
-		return 0;
-	case CMD_OPEN_TDB:
-		bIterate = 0;
-		open_tdb(arg1);
-		return 0;
-	case CMD_SYSTEM:
-		/* Shell command */
-		if (system(arg1) == -1) {
-			terror("system() call failed\n");
-		}
-		return 0;
-	case CMD_QUIT:
-		return 1;
-	default:
-		/* all the rest require a open database */
-		if (!tdb) {
-			bIterate = 0;
-			terror("database not open");
-			help();
-			return 0;
-		}
-		switch (mycmd) {
-		case CMD_TRANSACTION_START:
-			bIterate = 0;
-			tdb_transaction_start(tdb);
-			return 0;
-		case CMD_TRANSACTION_COMMIT:
-			bIterate = 0;
-			tdb_transaction_commit(tdb);
-			return 0;
-		case CMD_REPACK:
-			bIterate = 0;
-			tdb_repack(tdb);
-			return 0;
-		case CMD_TRANSACTION_CANCEL:
-			bIterate = 0;
-			tdb_transaction_cancel(tdb);
-			return 0;
-		case CMD_ERASE:
-			bIterate = 0;
-			tdb_traverse(tdb, do_delete_fn, NULL);
-			return 0;
-		case CMD_DUMP:
-			bIterate = 0;
-			tdb_traverse(tdb, print_rec, NULL);
-			return 0;
-		case CMD_INSERT:
-			bIterate = 0;
-			insert_tdb(arg1, arg1len,arg2,arg2len);
-			return 0;
-		case CMD_MOVE:
-			bIterate = 0;
-			move_rec(arg1,arg1len,arg2);
-			return 0;
-		case CMD_STORE:
-			bIterate = 0;
-			store_tdb(arg1,arg1len,arg2,arg2len);
-			return 0;
-		case CMD_SHOW:
-			bIterate = 0;
-			show_tdb(arg1, arg1len);
-			return 0;
-		case CMD_KEYS:
-			tdb_traverse(tdb, print_key, NULL);
-			return 0;
-		case CMD_HEXKEYS:
-			tdb_traverse(tdb, print_hexkey, NULL);
-			return 0;
-		case CMD_DELETE:
-			bIterate = 0;
-			delete_tdb(arg1,arg1len);
-			return 0;
-		case CMD_LIST_HASH_FREE:
-			tdb_dump_all(tdb);
-			return 0;
-		case CMD_LIST_FREE:
-			tdb_printfreelist(tdb);
-			return 0;
-		case CMD_INFO:
-			info_tdb();
-			return 0;
-		case CMD_SPEED:
-			speed_tdb(arg1);
-			return 0;
-		case CMD_MMAP:
-			toggle_mmap();
-			return 0;
-		case CMD_FIRST:
-			bIterate = 1;
-			first_record(tdb, &iterate_kbuf);
-			return 0;
-		case CMD_NEXT:
-			if (bIterate)
-				next_record(tdb, &iterate_kbuf);
-			return 0;
-		case CMD_CHECK:
-			check_db(tdb);
-			return 0;
-		case CMD_HELP:
-			help();
-			return 0;
-		case CMD_CREATE_TDB:
-		case CMD_OPEN_TDB:
-		case CMD_SYSTEM:
-		case CMD_QUIT:
-			/*
-			 * unhandled commands.  cases included here to avoid compiler
-			 * warnings.
-			 */
-			return 0;
-		}
-	}
-
-	return 0;
-}
-
-static char *tdb_convert_string(char *instring, size_t *sizep)
-{
-	size_t length = 0;
-	char *outp, *inp;
-	char temp[3];
-
-	outp = inp = instring;
-
-	while (*inp) {
-		if (*inp == '\\') {
-			inp++;
-			if (*inp && strchr("0123456789abcdefABCDEF",(int)*inp)) {
-				temp[0] = *inp++;
-				temp[1] = '\0';
-				if (*inp && strchr("0123456789abcdefABCDEF",(int)*inp)) {
-					temp[1] = *inp++;
-					temp[2] = '\0';
-				}
-				*outp++ = (char)strtol((const char *)temp,NULL,16);
-			} else {
-				*outp++ = *inp++;
-			}
-		} else {
-			*outp++ = *inp++;
-		}
-		length++;
-	}
-	*sizep = length;
-	return instring;
-}
-
-int main(int argc, char *argv[])
-{
-	cmdname = "";
-	arg1 = NULL;
-	arg1len = 0;
-	arg2 = NULL;
-	arg2len = 0;
-
-	if (argv[1]) {
-		cmdname = "open";
-		arg1 = argv[1];
-		do_command();
-		cmdname =  "";
-		arg1 = NULL;
-	}
-
-	switch (argc) {
-	case 1:
-	case 2:
-		/* Interactive mode */
-		while ((cmdname = tdb_getline("tdb> "))) {
-			arg2 = arg1 = NULL;
-			if ((arg1 = strchr((const char *)cmdname,' ')) != NULL) {
-				arg1++;
-				arg2 = arg1;
-				while (*arg2) {
-					if (*arg2 == ' ') {
-						*arg2++ = '\0';
-						break;
-					}
-					if ((*arg2++ == '\\') && (*arg2 == ' ')) {
-						arg2++;
-					}
-				}
-			}
-			if (arg1) arg1 = tdb_convert_string(arg1,&arg1len);
-			if (arg2) arg2 = tdb_convert_string(arg2,&arg2len);
-			if (do_command()) break;
-		}
-		break;
-	case 5:
-		arg2 = tdb_convert_string(argv[4],&arg2len);
-	case 4:
-		arg1 = tdb_convert_string(argv[3],&arg1len);
-	case 3:
-		cmdname = argv[2];
-	default:
-		do_command();
-		break;
-	}
-
-	if (tdb) tdb_close(tdb);
-
-	return 0;
-}
diff --git a/lib/tdb/tools/tdbtorture.c b/lib/tdb/tools/tdbtorture.c
deleted file mode 100644
index 64c5043..0000000
--- a/lib/tdb/tools/tdbtorture.c
+++ /dev/null
@@ -1,453 +0,0 @@
-/* this tests tdb by doing lots of ops from several simultaneous
-   writers - that stresses the locking code. 
-*/
-
-#include "replace.h"
-#include "system/time.h"
-#include "system/wait.h"
-#include "system/filesys.h"
-#include "tdb.h"
-
-#ifdef HAVE_GETOPT_H
-#include <getopt.h>
-#endif
-
-
-#define REOPEN_PROB 30
-#define DELETE_PROB 8
-#define STORE_PROB 4
-#define APPEND_PROB 6
-#define TRANSACTION_PROB 10
-#define TRANSACTION_PREPARE_PROB 2
-#define LOCKSTORE_PROB 5
-#define TRAVERSE_PROB 20
-#define TRAVERSE_READ_PROB 20
-#define CULL_PROB 100
-#define KEYLEN 3
-#define DATALEN 100
-
-static struct tdb_context *db;
-static int in_transaction;
-static int error_count;
-static int always_transaction = 0;
-static int hash_size = 2;
-static int loopnum;
-static int count_pipe;
-static struct tdb_logging_context log_ctx;
-
-#ifdef PRINTF_ATTRIBUTE
-static void tdb_log(struct tdb_context *tdb, enum tdb_debug_level level, const char *format, ...) PRINTF_ATTRIBUTE(3,4);
-#endif
-static void tdb_log(struct tdb_context *tdb, enum tdb_debug_level level, const char *format, ...)
-{
-	va_list ap;
-
-	/* trace level messages do not indicate an error */
-	if (level != TDB_DEBUG_TRACE) {
-		error_count++;
-	}
-
-	va_start(ap, format);
-	vfprintf(stdout, format, ap);
-	va_end(ap);
-	fflush(stdout);
-#if 0
-	if (level != TDB_DEBUG_TRACE) {
-		char *ptr;
-		signal(SIGUSR1, SIG_IGN);
-		asprintf(&ptr,"xterm -e gdb /proc/%d/exe %d", getpid(), getpid());
-		system(ptr);
-		free(ptr);
-	}
-#endif	
-}
-
-static void fatal(const char *why)
-{
-	perror(why);
-	error_count++;
-}
-
-static char *randbuf(int len)
-{
-	char *buf;
-	int i;
-	buf = (char *)malloc(len+1);
-
-	for (i=0;i<len;i++) {
-		buf[i] = 'a' + (rand() % 26);
-	}
-	buf[i] = 0;
-	return buf;
-}
-
-static int cull_traverse(struct tdb_context *tdb, TDB_DATA key, TDB_DATA dbuf,
-			 void *state)
-{
-#if CULL_PROB
-	if (random() % CULL_PROB == 0) {
-		tdb_delete(tdb, key);
-	}
-#endif
-	return 0;
-}
-
-static void addrec_db(void)
-{
-	int klen, dlen;
-	char *k, *d;
-	TDB_DATA key, data;
-
-	klen = 1 + (rand() % KEYLEN);
-	dlen = 1 + (rand() % DATALEN);
-
-	k = randbuf(klen);
-	d = randbuf(dlen);
-
-	key.dptr = (unsigned char *)k;
-	key.dsize = klen+1;
-
-	data.dptr = (unsigned char *)d;
-	data.dsize = dlen+1;
-
-#if REOPEN_PROB
-	if (in_transaction == 0 && random() % REOPEN_PROB == 0) {
-		tdb_reopen_all(0);
-		goto next;
-	}
-#endif
-
-#if TRANSACTION_PROB
-	if (in_transaction == 0 &&
-	    (always_transaction || random() % TRANSACTION_PROB == 0)) {
-		if (tdb_transaction_start(db) != 0) {
-			fatal("tdb_transaction_start failed");
-		}
-		in_transaction++;
-		goto next;
-	}
-	if (in_transaction && random() % TRANSACTION_PROB == 0) {
-		if (random() % TRANSACTION_PREPARE_PROB == 0) {
-			if (tdb_transaction_prepare_commit(db) != 0) {
-				fatal("tdb_transaction_prepare_commit failed");
-			}
-		}
-		if (tdb_transaction_commit(db) != 0) {
-			fatal("tdb_transaction_commit failed");
-		}
-		in_transaction--;
-		goto next;
-	}
-	if (in_transaction && random() % TRANSACTION_PROB == 0) {
-		if (tdb_transaction_cancel(db) != 0) {
-			fatal("tdb_transaction_cancel failed");
-		}
-		in_transaction--;
-		goto next;
-	}
-#endif
-
-#if DELETE_PROB
-	if (random() % DELETE_PROB == 0) {
-		tdb_delete(db, key);
-		goto next;
-	}
-#endif
-
-#if STORE_PROB
-	if (random() % STORE_PROB == 0) {
-		if (tdb_store(db, key, data, TDB_REPLACE) != 0) {
-			fatal("tdb_store failed");
-		}
-		goto next;
-	}
-#endif
-
-#if APPEND_PROB
-	if (random() % APPEND_PROB == 0) {
-		if (tdb_append(db, key, data) != 0) {
-			fatal("tdb_append failed");
-		}
-		goto next;
-	}
-#endif
-
-#if LOCKSTORE_PROB
-	if (random() % LOCKSTORE_PROB == 0) {
-		tdb_chainlock(db, key);
-		data = tdb_fetch(db, key);
-		if (tdb_store(db, key, data, TDB_REPLACE) != 0) {
-			fatal("tdb_store failed");
-		}
-		if (data.dptr) free(data.dptr);
-		tdb_chainunlock(db, key);
-		goto next;
-	} 
-#endif
-
-#if TRAVERSE_PROB
-	if (random() % TRAVERSE_PROB == 0) {
-		tdb_traverse(db, cull_traverse, NULL);
-		goto next;
-	}
-#endif
-
-#if TRAVERSE_READ_PROB
-	if (random() % TRAVERSE_READ_PROB == 0) {
-		tdb_traverse_read(db, NULL, NULL);
-		goto next;
-	}
-#endif
-
-	data = tdb_fetch(db, key);
-	if (data.dptr) free(data.dptr);
-
-next:
-	free(k);
-	free(d);
-}
-
-static int traverse_fn(struct tdb_context *tdb, TDB_DATA key, TDB_DATA dbuf,
-                       void *state)
-{
-	tdb_delete(tdb, key);
-	return 0;
-}
-
-static void usage(void)
-{
-	printf("Usage: tdbtorture [-t] [-k] [-n NUM_PROCS] [-l NUM_LOOPS] [-s SEED] [-H HASH_SIZE]\n");
-	exit(0);
-}
-
-static void send_count_and_suicide(int sig)
-{
-	/* This ensures our successor can continue where we left off. */
-	write(count_pipe, &loopnum, sizeof(loopnum));
-	/* This gives a unique signature. */
-	kill(getpid(), SIGUSR2);
-}
-
-static int run_child(const char *filename, int i, int seed, unsigned num_loops, unsigned start)
-{
-	db = tdb_open_ex(filename, hash_size, TDB_DEFAULT,
-			 O_RDWR | O_CREAT, 0600, &log_ctx, NULL);
-	if (!db) {
-		fatal("db open failed");
-	}
-
-	srand(seed + i);
-	srandom(seed + i);
-
-	/* Set global, then we're ready to handle being killed. */
-	loopnum = start;
-	signal(SIGUSR1, send_count_and_suicide);
-
-	for (;loopnum<num_loops && error_count == 0;loopnum++) {
-		addrec_db();
-	}
-
-	if (error_count == 0) {
-		tdb_traverse_read(db, NULL, NULL);
-		if (always_transaction) {
-			while (in_transaction) {
-				tdb_transaction_cancel(db);
-				in_transaction--;
-			}
-			if (tdb_transaction_start(db) != 0)
-				fatal("tdb_transaction_start failed");
-		}
-		tdb_traverse(db, traverse_fn, NULL);
-		tdb_traverse(db, traverse_fn, NULL);
-		if (always_transaction) {
-			if (tdb_transaction_commit(db) != 0)
-				fatal("tdb_transaction_commit failed");
-		}
-	}
-
-	tdb_close(db);
-
-	return (error_count < 100 ? error_count : 100);
-}
-
-static char *test_path(const char *filename)
-{
-	const char *prefix = getenv("TEST_DATA_PREFIX");
-
-	if (prefix) {
-		char *path = NULL;
-		int ret;
-
-		ret = asprintf(&path, "%s/%s", prefix, filename);
-		if (ret == -1) {
-			return NULL;
-		}
-		return path;
-	}
-
-	return strdup(filename);
-}
-
-int main(int argc, char * const *argv)
-{
-	int i, seed = -1;
-	int num_loops = 5000;
-	int num_procs = 3;
-	int c, pfds[2];
-	extern char *optarg;
-	pid_t *pids;
-	int kill_random = 0;
-	int *done;
-	char *test_tdb;
-
-	log_ctx.log_fn = tdb_log;
-
-	while ((c = getopt(argc, argv, "n:l:s:H:thk")) != -1) {
-		switch (c) {
-		case 'n':
-			num_procs = strtol(optarg, NULL, 0);
-			break;
-		case 'l':
-			num_loops = strtol(optarg, NULL, 0);
-			break;
-		case 'H':
-			hash_size = strtol(optarg, NULL, 0);
-			break;
-		case 's':
-			seed = strtol(optarg, NULL, 0);
-			break;
-		case 't':
-			always_transaction = 1;
-			break;
-		case 'k':
-			kill_random = 1;
-			break;
-		default:
-			usage();
-		}
-	}
-
-	test_tdb = test_path("torture.tdb");
-
-	unlink(test_tdb);
-
-	if (seed == -1) {
-		seed = (getpid() + time(NULL)) & 0x7FFFFFFF;
-	}
-
-	if (num_procs == 1 && !kill_random) {
-		/* Don't fork for this case, makes debugging easier. */
-		error_count = run_child(test_tdb, 0, seed, num_loops, 0);
-		goto done;
-	}
-
-	pids = (pid_t *)calloc(sizeof(pid_t), num_procs);
-	done = (int *)calloc(sizeof(int), num_procs);
-
-	if (pipe(pfds) != 0) {
-		perror("Creating pipe");
-		exit(1);
-	}
-	count_pipe = pfds[1];
-
-	for (i=0;i<num_procs;i++) {
-		if ((pids[i]=fork()) == 0) {
-			close(pfds[0]);
-			if (i == 0) {
-				printf("Testing with %d processes, %d loops, %d hash_size, seed=%d%s\n",
-				       num_procs, num_loops, hash_size, seed, always_transaction ? " (all within transactions)" : "");
-			}
-			exit(run_child(test_tdb, i, seed, num_loops, 0));
-		}
-	}
-
-	while (num_procs) {
-		int status, j;
-		pid_t pid;
-
-		if (error_count != 0) {
-			/* try and stop the test on any failure */
-			for (j=0;j<num_procs;j++) {
-				if (pids[j] != 0) {
-					kill(pids[j], SIGTERM);
-				}
-			}
-		}
-
-		pid = waitpid(-1, &status, kill_random ? WNOHANG : 0);
-		if (pid == 0) {
-			struct timeval tv;
-
-			/* Sleep for 1/10 second. */
-			tv.tv_sec = 0;
-			tv.tv_usec = 100000;
-			select(0, NULL, NULL, NULL, &tv);
-
-			/* Kill someone. */
-			kill(pids[random() % num_procs], SIGUSR1);
-			continue;
-		}
-
-		if (pid == -1) {
-			perror("failed to wait for child\n");
-			exit(1);
-		}
-
-		for (j=0;j<num_procs;j++) {
-			if (pids[j] == pid) break;
-		}
-		if (j == num_procs) {
-			printf("unknown child %d exited!?\n", (int)pid);
-			exit(1);
-		}
-		if (WIFSIGNALED(status)) {
-			if (WTERMSIG(status) == SIGUSR2
-			    || WTERMSIG(status) == SIGUSR1) {
-				/* SIGUSR2 means they wrote to pipe. */
-				if (WTERMSIG(status) == SIGUSR2) {
-					read(pfds[0], &done[j],
-					     sizeof(done[j]));
-				}
-				pids[j] = fork();
-				if (pids[j] == 0)
-					exit(run_child(test_tdb, j, seed,
-						       num_loops, done[j]));
-				printf("Restarting child %i for %u-%u\n",
-				       j, done[j], num_loops);
-				continue;
-			}
-			printf("child %d exited with signal %d\n",
-			       (int)pid, WTERMSIG(status));
-			error_count++;
-		} else {
-			if (WEXITSTATUS(status) != 0) {
-				printf("child %d exited with status %d\n",
-				       (int)pid, WEXITSTATUS(status));
-				error_count++;
-			}
-		}
-		memmove(&pids[j], &pids[j+1],
-			(num_procs - j - 1)*sizeof(pids[0]));
-		num_procs--;
-	}
-
-	free(pids);
-
-done:
-	if (error_count == 0) {
-		db = tdb_open_ex(test_tdb, hash_size, TDB_DEFAULT,
-				 O_RDWR, 0, &log_ctx, NULL);
-		if (!db) {
-			fatal("db open failed");
-		}
-		if (tdb_check(db, NULL, NULL) == -1) {
-			printf("db check failed");
-			exit(1);
-		}
-		tdb_close(db);
-		printf("OK\n");
-	}
-
-	free(test_tdb);
-	return error_count;
-}
diff --git a/lib/tdb/web/index.html b/lib/tdb/web/index.html
deleted file mode 100644
index 99e8a2f..0000000
--- a/lib/tdb/web/index.html
+++ /dev/null
@@ -1,48 +0,0 @@
-<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 3.2//EN">
-<HTML>
-<HEAD>
-<TITLE>ldb</TITLE>
-</HEAD>
-<BODY BGCOLOR="#ffffff" TEXT="#000000" VLINK="#292555" LINK="#292555" ALINK="#cc0033">
-
-<h1>tdb</h1>
-
-TDB is a Trivial Database. In concept, it is very much like GDBM, and BSD's DB 
-except that it allows multiple simultaneous writers and uses locking 
-internally to keep writers from trampling on each other. TDB is also extremely 
-small.
-
-<h2>Download</h2>
-You can download the latest releases of tdb from the <a
-href="http://samba.org/ftp/tdb">tdb directory</a> on the samba public
-source archive.
-
-
-<h2>Discussion and bug reports</h2>
-
-tdb does not currently have its own mailing list or bug tracking
-system. For now, please use the <a
-href="https://lists.samba.org/mailman/listinfo/samba-technical">samba-technical</a>
-mailing list, and the <a href="http://bugzilla.samba.org/">Samba
-bugzilla</a> bug tracking system.
-
-<h2>Download</h2>
-
-You can download the latest code either via git or rsync.<br>
-<br>
-To fetch via git see the following guide:<br>
-<a href="http://wiki.samba.org/index.php/Using_Git_for_Samba_Development">Using Git for Samba Development</a><br>
-Once you have cloned the tree switch to the master branch and cd into the source/lib/tdb directory.<br>
-<br>
-To fetch via rsync use these commands:
-
-<pre>
-  rsync -Pavz samba.org::ftp/unpacked/standalone_projects/lib/tdb .
-  rsync -Pavz samba.org::ftp/unpacked/standalone_projects/lib/replace .
-</pre>
-
-and build in tdb. It will find the replace library in the directory
-above automatically.
-
-</BODY>
-</HTML>
diff --git a/lib/tevent/ABI/tevent-0.9.15.sigs b/lib/tevent/ABI/tevent-0.9.15.sigs
deleted file mode 100644
index 13c461c..0000000
--- a/lib/tevent/ABI/tevent-0.9.15.sigs
+++ /dev/null
@@ -1,78 +0,0 @@
-_tevent_add_fd: struct tevent_fd *(struct tevent_context *, TALLOC_CTX *, int, uint16_t, tevent_fd_handler_t, void *, const char *, const char *)
-_tevent_add_signal: struct tevent_signal *(struct tevent_context *, TALLOC_CTX *, int, int, tevent_signal_handler_t, void *, const char *, const char *)
-_tevent_add_timer: struct tevent_timer *(struct tevent_context *, TALLOC_CTX *, struct timeval, tevent_timer_handler_t, void *, const char *, const char *)
-_tevent_create_immediate: struct tevent_immediate *(TALLOC_CTX *, const char *)
-_tevent_loop_once: int (struct tevent_context *, const char *)
-_tevent_loop_until: int (struct tevent_context *, bool (*)(void *), void *, const char *)
-_tevent_loop_wait: int (struct tevent_context *, const char *)
-_tevent_queue_create: struct tevent_queue *(TALLOC_CTX *, const char *, const char *)
-_tevent_req_callback_data: void *(struct tevent_req *)
-_tevent_req_cancel: bool (struct tevent_req *, const char *)
-_tevent_req_create: struct tevent_req *(TALLOC_CTX *, void *, size_t, const char *, const char *)
-_tevent_req_data: void *(struct tevent_req *)
-_tevent_req_done: void (struct tevent_req *, const char *)
-_tevent_req_error: bool (struct tevent_req *, uint64_t, const char *)
-_tevent_req_nomem: bool (const void *, struct tevent_req *, const char *)
-_tevent_req_notify_callback: void (struct tevent_req *, const char *)
-_tevent_req_oom: void (struct tevent_req *, const char *)
-_tevent_schedule_immediate: void (struct tevent_immediate *, struct tevent_context *, tevent_immediate_handler_t, void *, const char *, const char *)
-tevent_backend_list: const char **(TALLOC_CTX *)
-tevent_cleanup_pending_signal_handlers: void (struct tevent_signal *)
-tevent_common_add_fd: struct tevent_fd *(struct tevent_context *, TALLOC_CTX *, int, uint16_t, tevent_fd_handler_t, void *, const char *, const char *)
-tevent_common_add_signal: struct tevent_signal *(struct tevent_context *, TALLOC_CTX *, int, int, tevent_signal_handler_t, void *, const char *, const char *)
-tevent_common_add_timer: struct tevent_timer *(struct tevent_context *, TALLOC_CTX *, struct timeval, tevent_timer_handler_t, void *, const char *, const char *)
-tevent_common_check_signal: int (struct tevent_context *)
-tevent_common_context_destructor: int (struct tevent_context *)
-tevent_common_fd_destructor: int (struct tevent_fd *)
-tevent_common_fd_get_flags: uint16_t (struct tevent_fd *)
-tevent_common_fd_set_close_fn: void (struct tevent_fd *, tevent_fd_close_fn_t)
-tevent_common_fd_set_flags: void (struct tevent_fd *, uint16_t)
-tevent_common_loop_immediate: bool (struct tevent_context *)
-tevent_common_loop_timer_delay: struct timeval (struct tevent_context *)
-tevent_common_loop_wait: int (struct tevent_context *, const char *)
-tevent_common_schedule_immediate: void (struct tevent_immediate *, struct tevent_context *, tevent_immediate_handler_t, void *, const char *, const char *)
-tevent_context_init: struct tevent_context *(TALLOC_CTX *)
-tevent_context_init_byname: struct tevent_context *(TALLOC_CTX *, const char *)
-tevent_debug: void (struct tevent_context *, enum tevent_debug_level, const char *, ...)
-tevent_fd_get_flags: uint16_t (struct tevent_fd *)
-tevent_fd_set_auto_close: void (struct tevent_fd *)
-tevent_fd_set_close_fn: void (struct tevent_fd *, tevent_fd_close_fn_t)
-tevent_fd_set_flags: void (struct tevent_fd *, uint16_t)
-tevent_loop_allow_nesting: void (struct tevent_context *)
-tevent_loop_set_nesting_hook: void (struct tevent_context *, tevent_nesting_hook, void *)
-tevent_queue_add: bool (struct tevent_queue *, struct tevent_context *, struct tevent_req *, tevent_queue_trigger_fn_t, void *)
-tevent_queue_add_entry: struct tevent_queue_entry *(struct tevent_queue *, struct tevent_context *, struct tevent_req *, tevent_queue_trigger_fn_t, void *)
-tevent_queue_add_optimize_empty: struct tevent_queue_entry *(struct tevent_queue *, struct tevent_context *, struct tevent_req *, tevent_queue_trigger_fn_t, void *)
-tevent_queue_length: size_t (struct tevent_queue *)
-tevent_queue_running: bool (struct tevent_queue *)
-tevent_queue_start: void (struct tevent_queue *)
-tevent_queue_stop: void (struct tevent_queue *)
-tevent_re_initialise: int (struct tevent_context *)
-tevent_register_backend: bool (const char *, const struct tevent_ops *)
-tevent_req_default_print: char *(struct tevent_req *, TALLOC_CTX *)
-tevent_req_defer_callback: void (struct tevent_req *, struct tevent_context *)
-tevent_req_is_error: bool (struct tevent_req *, enum tevent_req_state *, uint64_t *)
-tevent_req_is_in_progress: bool (struct tevent_req *)
-tevent_req_poll: bool (struct tevent_req *, struct tevent_context *)
-tevent_req_post: struct tevent_req *(struct tevent_req *, struct tevent_context *)
-tevent_req_print: char *(TALLOC_CTX *, struct tevent_req *)
-tevent_req_received: void (struct tevent_req *)
-tevent_req_set_callback: void (struct tevent_req *, tevent_req_fn, void *)
-tevent_req_set_cancel_fn: void (struct tevent_req *, tevent_req_cancel_fn)
-tevent_req_set_endtime: bool (struct tevent_req *, struct tevent_context *, struct timeval)
-tevent_req_set_print_fn: void (struct tevent_req *, tevent_req_print_fn)
-tevent_set_abort_fn: void (void (*)(const char *))
-tevent_set_debug: int (struct tevent_context *, void (*)(void *, enum tevent_debug_level, const char *, va_list), void *)
-tevent_set_debug_stderr: int (struct tevent_context *)
-tevent_set_default_backend: void (const char *)
-tevent_signal_support: bool (struct tevent_context *)
-tevent_timeval_add: struct timeval (const struct timeval *, uint32_t, uint32_t)
-tevent_timeval_compare: int (const struct timeval *, const struct timeval *)
-tevent_timeval_current: struct timeval (void)
-tevent_timeval_current_ofs: struct timeval (uint32_t, uint32_t)
-tevent_timeval_is_zero: bool (const struct timeval *)
-tevent_timeval_set: struct timeval (uint32_t, uint32_t)
-tevent_timeval_until: struct timeval (const struct timeval *, const struct timeval *)
-tevent_timeval_zero: struct timeval (void)
-tevent_wakeup_recv: bool (struct tevent_req *)
-tevent_wakeup_send: struct tevent_req *(TALLOC_CTX *, struct tevent_context *, struct timeval)
diff --git a/lib/tevent/ABI/tevent-0.9.16.sigs b/lib/tevent/ABI/tevent-0.9.16.sigs
deleted file mode 100644
index ea7f944..0000000
--- a/lib/tevent/ABI/tevent-0.9.16.sigs
+++ /dev/null
@@ -1,82 +0,0 @@
-_tevent_add_fd: struct tevent_fd *(struct tevent_context *, TALLOC_CTX *, int, uint16_t, tevent_fd_handler_t, void *, const char *, const char *)
-_tevent_add_signal: struct tevent_signal *(struct tevent_context *, TALLOC_CTX *, int, int, tevent_signal_handler_t, void *, const char *, const char *)
-_tevent_add_timer: struct tevent_timer *(struct tevent_context *, TALLOC_CTX *, struct timeval, tevent_timer_handler_t, void *, const char *, const char *)
-_tevent_create_immediate: struct tevent_immediate *(TALLOC_CTX *, const char *)
-_tevent_loop_once: int (struct tevent_context *, const char *)
-_tevent_loop_until: int (struct tevent_context *, bool (*)(void *), void *, const char *)
-_tevent_loop_wait: int (struct tevent_context *, const char *)
-_tevent_queue_create: struct tevent_queue *(TALLOC_CTX *, const char *, const char *)
-_tevent_req_callback_data: void *(struct tevent_req *)
-_tevent_req_cancel: bool (struct tevent_req *, const char *)
-_tevent_req_create: struct tevent_req *(TALLOC_CTX *, void *, size_t, const char *, const char *)
-_tevent_req_data: void *(struct tevent_req *)
-_tevent_req_done: void (struct tevent_req *, const char *)
-_tevent_req_error: bool (struct tevent_req *, uint64_t, const char *)
-_tevent_req_nomem: bool (const void *, struct tevent_req *, const char *)
-_tevent_req_notify_callback: void (struct tevent_req *, const char *)
-_tevent_req_oom: void (struct tevent_req *, const char *)
-_tevent_schedule_immediate: void (struct tevent_immediate *, struct tevent_context *, tevent_immediate_handler_t, void *, const char *, const char *)
-tevent_backend_list: const char **(TALLOC_CTX *)
-tevent_cleanup_pending_signal_handlers: void (struct tevent_signal *)
-tevent_common_add_fd: struct tevent_fd *(struct tevent_context *, TALLOC_CTX *, int, uint16_t, tevent_fd_handler_t, void *, const char *, const char *)
-tevent_common_add_signal: struct tevent_signal *(struct tevent_context *, TALLOC_CTX *, int, int, tevent_signal_handler_t, void *, const char *, const char *)
-tevent_common_add_timer: struct tevent_timer *(struct tevent_context *, TALLOC_CTX *, struct timeval, tevent_timer_handler_t, void *, const char *, const char *)
-tevent_common_check_signal: int (struct tevent_context *)
-tevent_common_context_destructor: int (struct tevent_context *)
-tevent_common_fd_destructor: int (struct tevent_fd *)
-tevent_common_fd_get_flags: uint16_t (struct tevent_fd *)
-tevent_common_fd_set_close_fn: void (struct tevent_fd *, tevent_fd_close_fn_t)
-tevent_common_fd_set_flags: void (struct tevent_fd *, uint16_t)
-tevent_common_loop_immediate: bool (struct tevent_context *)
-tevent_common_loop_timer_delay: struct timeval (struct tevent_context *)
-tevent_common_loop_wait: int (struct tevent_context *, const char *)
-tevent_common_schedule_immediate: void (struct tevent_immediate *, struct tevent_context *, tevent_immediate_handler_t, void *, const char *, const char *)
-tevent_context_init: struct tevent_context *(TALLOC_CTX *)
-tevent_context_init_byname: struct tevent_context *(TALLOC_CTX *, const char *)
-tevent_context_init_ops: struct tevent_context *(TALLOC_CTX *, const struct tevent_ops *, void *)
-tevent_debug: void (struct tevent_context *, enum tevent_debug_level, const char *, ...)
-tevent_fd_get_flags: uint16_t (struct tevent_fd *)
-tevent_fd_set_auto_close: void (struct tevent_fd *)
-tevent_fd_set_close_fn: void (struct tevent_fd *, tevent_fd_close_fn_t)
-tevent_fd_set_flags: void (struct tevent_fd *, uint16_t)
-tevent_get_trace_callback: void (struct tevent_context *, tevent_trace_callback_t *, void *)
-tevent_loop_allow_nesting: void (struct tevent_context *)
-tevent_loop_set_nesting_hook: void (struct tevent_context *, tevent_nesting_hook, void *)
-tevent_queue_add: bool (struct tevent_queue *, struct tevent_context *, struct tevent_req *, tevent_queue_trigger_fn_t, void *)
-tevent_queue_add_entry: struct tevent_queue_entry *(struct tevent_queue *, struct tevent_context *, struct tevent_req *, tevent_queue_trigger_fn_t, void *)
-tevent_queue_add_optimize_empty: struct tevent_queue_entry *(struct tevent_queue *, struct tevent_context *, struct tevent_req *, tevent_queue_trigger_fn_t, void *)
-tevent_queue_length: size_t (struct tevent_queue *)
-tevent_queue_running: bool (struct tevent_queue *)
-tevent_queue_start: void (struct tevent_queue *)
-tevent_queue_stop: void (struct tevent_queue *)
-tevent_re_initialise: int (struct tevent_context *)
-tevent_register_backend: bool (const char *, const struct tevent_ops *)
-tevent_req_default_print: char *(struct tevent_req *, TALLOC_CTX *)
-tevent_req_defer_callback: void (struct tevent_req *, struct tevent_context *)
-tevent_req_is_error: bool (struct tevent_req *, enum tevent_req_state *, uint64_t *)
-tevent_req_is_in_progress: bool (struct tevent_req *)
-tevent_req_poll: bool (struct tevent_req *, struct tevent_context *)
-tevent_req_post: struct tevent_req *(struct tevent_req *, struct tevent_context *)
-tevent_req_print: char *(TALLOC_CTX *, struct tevent_req *)
-tevent_req_received: void (struct tevent_req *)
-tevent_req_set_callback: void (struct tevent_req *, tevent_req_fn, void *)
-tevent_req_set_cancel_fn: void (struct tevent_req *, tevent_req_cancel_fn)
-tevent_req_set_endtime: bool (struct tevent_req *, struct tevent_context *, struct timeval)
-tevent_req_set_print_fn: void (struct tevent_req *, tevent_req_print_fn)
-tevent_set_abort_fn: void (void (*)(const char *))
-tevent_set_debug: int (struct tevent_context *, void (*)(void *, enum tevent_debug_level, const char *, va_list), void *)
-tevent_set_debug_stderr: int (struct tevent_context *)
-tevent_set_default_backend: void (const char *)
-tevent_set_trace_callback: void (struct tevent_context *, tevent_trace_callback_t, void *)
-tevent_signal_support: bool (struct tevent_context *)
-tevent_timeval_add: struct timeval (const struct timeval *, uint32_t, uint32_t)
-tevent_timeval_compare: int (const struct timeval *, const struct timeval *)
-tevent_timeval_current: struct timeval (void)
-tevent_timeval_current_ofs: struct timeval (uint32_t, uint32_t)
-tevent_timeval_is_zero: bool (const struct timeval *)
-tevent_timeval_set: struct timeval (uint32_t, uint32_t)
-tevent_timeval_until: struct timeval (const struct timeval *, const struct timeval *)
-tevent_timeval_zero: struct timeval (void)
-tevent_trace_point_callback: void (struct tevent_context *, enum tevent_trace_point)
-tevent_wakeup_recv: bool (struct tevent_req *)
-tevent_wakeup_send: struct tevent_req *(TALLOC_CTX *, struct tevent_context *, struct timeval)
diff --git a/lib/tevent/doc/mainpage.dox b/lib/tevent/doc/mainpage.dox
deleted file mode 100644
index e2f986e..0000000
--- a/lib/tevent/doc/mainpage.dox
+++ /dev/null
@@ -1,42 +0,0 @@
-/**
- * @mainpage
- *
- * Tevent is an event system based on the talloc memory management library. It
- * is the core event system used in Samba.
- *
- * The low level tevent has support for many event types, including timers,
- * signals, and the classic file descriptor events.
- *
- * Tevent also provide helpers to deal with asynchronous code providing the
- * tevent_req (tevent request) functions.
- *
- * @section tevent_download Download
- *
- * You can download the latest releases of tevent from the
- * <a href="http://samba.org/ftp/tevent" target="_blank">tevent directory</a>
- * on the samba public source archive.
- *
- * @section tevent_bugs Discussion and bug reports
- *
- * tevent does not currently have its own mailing list or bug tracking system.
- * For now, please use the
- * <a href="https://lists.samba.org/mailman/listinfo/samba-technical" target="_blank">samba-technical</a>
- * mailing list, and the
- * <a href="http://bugzilla.samba.org/" target="_blank">Samba bugzilla</a>
- * bug tracking system.
- *
- * @section tevent_devel Development
- * You can download the latest code either via git or rsync.
- *
- * To fetch via git see the following guide:
- *
- * <a href="http://wiki.samba.org/index.php/Using_Git_for_Samba_Development" target="_blank">Using Git for Samba Development</a>
- *
- * Once you have cloned the tree switch to the master branch and cd into the
- * lib/tevent directory.
- *
- * To fetch via rsync use this command:
- *
- *   rsync -Pavz samba.org::ftp/unpacked/standalone_projects/lib/tevent .
- *
- */
diff --git a/lib/tevent/doc/tutorials.dox b/lib/tevent/doc/tutorials.dox
deleted file mode 100644
index e8beed7..0000000
--- a/lib/tevent/doc/tutorials.dox
+++ /dev/null
@@ -1,43 +0,0 @@
-/**
- * @page tevent_queue_tutorial The tevent_queue tutorial
- *
- * @section Introduction
- *
- * A tevent_queue is used to queue up async requests that must be
- * serialized. For example writing buffers into a socket must be
- * serialized. Writing a large lump of data into a socket can require
- * multiple write(2) or send(2) system calls. If more than one async
- * request is outstanding to write large buffers into a socket, every
- * request must individually be completed before the next one begins,
- * even if multiple syscalls are required.
- *
- * To do this, every socket gets assigned a tevent_queue struct.
- *
- * Creating a serialized async request follows the usual convention to
- * return a tevent_req structure with an embedded state structure. To
- * serialize the work the requests is about to so, instead of directly
- * starting or doing that work, tevent_queue_add must be called. When it
- * is time for the serialized async request to do its work, the trigger
- * callback function tevent_queue_add was given is called. In the example
- * of writing to a socket, the trigger is called when the write request
- * can begin accessing the socket.
- *
- * How does this engine work behind the scenes? When the queue is empty,
- * tevent_queue_add schedules an immediate call to the trigger
- * callback. The trigger callback starts its work, likely by starting
- * other async subrequests. While these async subrequests are working,
- * more requests can accumulate in the queue by tevent_queue_add. While
- * there is no function to explicitly trigger the next waiter in line, it
- * still works: When the active request in the queue is done, it will be
- * destroyed by talloc_free. Talloc_free of an serialized async request
- * that had been added to a queue will trigger the next request in the
- * queue via a talloc destructor attached to a child of the serialized
- * request. This way the queue will be kept busy when an async request
- * finishes.
- *
- * @section Example
- *
- * @code
- *      Metze: Please add a code example here.
- * @endcode
- */
diff --git a/lib/tevent/doxy.config b/lib/tevent/doxy.config
deleted file mode 100644
index 578ecaf..0000000
--- a/lib/tevent/doxy.config
+++ /dev/null
@@ -1,1538 +0,0 @@
-# Doxyfile 1.6.1
-
-# This file describes the settings to be used by the documentation system
-# doxygen (www.doxygen.org) for a project
-#
-# All text after a hash (#) is considered a comment and will be ignored
-# The format is:
-#       TAG = value [value, ...]
-# For lists items can also be appended using:
-#       TAG += value [value, ...]
-# Values that contain spaces should be placed between quotes (" ")
-
-#---------------------------------------------------------------------------
-# Project related configuration options
-#---------------------------------------------------------------------------
-
-# This tag specifies the encoding used for all characters in the config file
-# that follow. The default is UTF-8 which is also the encoding used for all
-# text before the first occurrence of this tag. Doxygen uses libiconv (or the
-# iconv built into libc) for the transcoding. See
-# http://www.gnu.org/software/libiconv for the list of possible encodings.
-
-DOXYFILE_ENCODING      = UTF-8
-
-# The PROJECT_NAME tag is a single word (or a sequence of words surrounded
-# by quotes) that should identify the project.
-
-PROJECT_NAME           = tevent
-
-# The PROJECT_NUMBER tag can be used to enter a project or revision number.
-# This could be handy for archiving the generated documentation or
-# if some version control system is used.
-
-PROJECT_NUMBER         = 0.9.8
-
-# The OUTPUT_DIRECTORY tag is used to specify the (relative or absolute)
-# base path where the generated documentation will be put.
-# If a relative path is entered, it will be relative to the location
-# where doxygen was started. If left blank the current directory will be used.
-
-OUTPUT_DIRECTORY       = doc
-
-# If the CREATE_SUBDIRS tag is set to YES, then doxygen will create
-# 4096 sub-directories (in 2 levels) under the output directory of each output
-# format and will distribute the generated files over these directories.
-# Enabling this option can be useful when feeding doxygen a huge amount of
-# source files, where putting all generated files in the same directory would
-# otherwise cause performance problems for the file system.
-
-CREATE_SUBDIRS         = NO
-
-# The OUTPUT_LANGUAGE tag is used to specify the language in which all
-# documentation generated by doxygen is written. Doxygen will use this
-# information to generate all constant output in the proper language.
-# The default language is English, other supported languages are:
-# Afrikaans, Arabic, Brazilian, Catalan, Chinese, Chinese-Traditional,
-# Croatian, Czech, Danish, Dutch, Esperanto, Farsi, Finnish, French, German,
-# Greek, Hungarian, Italian, Japanese, Japanese-en (Japanese with English
-# messages), Korean, Korean-en, Lithuanian, Norwegian, Macedonian, Persian,
-# Polish, Portuguese, Romanian, Russian, Serbian, Serbian-Cyrilic, Slovak,
-# Slovene, Spanish, Swedish, Ukrainian, and Vietnamese.
-
-OUTPUT_LANGUAGE        = English
-
-# If the BRIEF_MEMBER_DESC tag is set to YES (the default) Doxygen will
-# include brief member descriptions after the members that are listed in
-# the file and class documentation (similar to JavaDoc).
-# Set to NO to disable this.
-
-BRIEF_MEMBER_DESC      = YES
-
-# If the REPEAT_BRIEF tag is set to YES (the default) Doxygen will prepend
-# the brief description of a member or function before the detailed description.
-# Note: if both HIDE_UNDOC_MEMBERS and BRIEF_MEMBER_DESC are set to NO, the
-# brief descriptions will be completely suppressed.
-
-REPEAT_BRIEF           = YES
-
-# This tag implements a quasi-intelligent brief description abbreviator
-# that is used to form the text in various listings. Each string
-# in this list, if found as the leading text of the brief description, will be
-# stripped from the text and the result after processing the whole list, is
-# used as the annotated text. Otherwise, the brief description is used as-is.
-# If left blank, the following values are used ("$name" is automatically
-# replaced with the name of the entity): "The $name class" "The $name widget"
-# "The $name file" "is" "provides" "specifies" "contains"
-# "represents" "a" "an" "the"
-
-ABBREVIATE_BRIEF       = "The $name class" \
-                         "The $name widget" \
-                         "The $name file" \
-                         is \
-                         provides \
-                         specifies \
-                         contains \
-                         represents \
-                         a \
-                         an \
-                         the
-
-# If the ALWAYS_DETAILED_SEC and REPEAT_BRIEF tags are both set to YES then
-# Doxygen will generate a detailed section even if there is only a brief
-# description.
-
-ALWAYS_DETAILED_SEC    = NO
-
-# If the INLINE_INHERITED_MEMB tag is set to YES, doxygen will show all
-# inherited members of a class in the documentation of that class as if those
-# members were ordinary class members. Constructors, destructors and assignment
-# operators of the base classes will not be shown.
-
-INLINE_INHERITED_MEMB  = NO
-
-# If the FULL_PATH_NAMES tag is set to YES then Doxygen will prepend the full
-# path before files name in the file list and in the header files. If set
-# to NO the shortest path that makes the file name unique will be used.
-
-FULL_PATH_NAMES        = YES
-
-# If the FULL_PATH_NAMES tag is set to YES then the STRIP_FROM_PATH tag
-# can be used to strip a user-defined part of the path. Stripping is
-# only done if one of the specified strings matches the left-hand part of
-# the path. The tag can be used to show relative paths in the file list.
-# If left blank the directory from which doxygen is run is used as the
-# path to strip.
-
-STRIP_FROM_PATH        =
-
-# The STRIP_FROM_INC_PATH tag can be used to strip a user-defined part of
-# the path mentioned in the documentation of a class, which tells
-# the reader which header file to include in order to use a class.
-# If left blank only the name of the header file containing the class
-# definition is used. Otherwise one should specify the include paths that
-# are normally passed to the compiler using the -I flag.
-
-STRIP_FROM_INC_PATH    =
-
-# If the SHORT_NAMES tag is set to YES, doxygen will generate much shorter
-# (but less readable) file names. This can be useful is your file systems
-# doesn't support long names like on DOS, Mac, or CD-ROM.
-
-SHORT_NAMES            = NO
-
-# If the JAVADOC_AUTOBRIEF tag is set to YES then Doxygen
-# will interpret the first line (until the first dot) of a JavaDoc-style
-# comment as the brief description. If set to NO, the JavaDoc
-# comments will behave just like regular Qt-style comments
-# (thus requiring an explicit @brief command for a brief description.)
-
-JAVADOC_AUTOBRIEF      = YES
-
-# If the QT_AUTOBRIEF tag is set to YES then Doxygen will
-# interpret the first line (until the first dot) of a Qt-style
-# comment as the brief description. If set to NO, the comments
-# will behave just like regular Qt-style comments (thus requiring
-# an explicit \brief command for a brief description.)
-
-QT_AUTOBRIEF           = NO
-
-# The MULTILINE_CPP_IS_BRIEF tag can be set to YES to make Doxygen
-# treat a multi-line C++ special comment block (i.e. a block of //! or ///
-# comments) as a brief description. This used to be the default behaviour.
-# The new default is to treat a multi-line C++ comment block as a detailed
-# description. Set this tag to YES if you prefer the old behaviour instead.
-
-MULTILINE_CPP_IS_BRIEF = NO
-
-# If the INHERIT_DOCS tag is set to YES (the default) then an undocumented
-# member inherits the documentation from any documented member that it
-# re-implements.
-
-INHERIT_DOCS           = YES
-
-# If the SEPARATE_MEMBER_PAGES tag is set to YES, then doxygen will produce
-# a new page for each member. If set to NO, the documentation of a member will
-# be part of the file/class/namespace that contains it.
-
-SEPARATE_MEMBER_PAGES  = NO
-
-# The TAB_SIZE tag can be used to set the number of spaces in a tab.
-# Doxygen uses this value to replace tabs by spaces in code fragments.
-
-TAB_SIZE               = 8
-
-# This tag can be used to specify a number of aliases that acts
-# as commands in the documentation. An alias has the form "name=value".
-# For example adding "sideeffect=\par Side Effects:\n" will allow you to
-# put the command \sideeffect (or @sideeffect) in the documentation, which
-# will result in a user-defined paragraph with heading "Side Effects:".
-# You can put \n's in the value part of an alias to insert newlines.
-
-ALIASES                =
-
-# Set the OPTIMIZE_OUTPUT_FOR_C tag to YES if your project consists of C
-# sources only. Doxygen will then generate output that is more tailored for C.
-# For instance, some of the names that are used will be different. The list
-# of all members will be omitted, etc.
-
-OPTIMIZE_OUTPUT_FOR_C  = YES
-
-# Set the OPTIMIZE_OUTPUT_JAVA tag to YES if your project consists of Java
-# sources only. Doxygen will then generate output that is more tailored for
-# Java. For instance, namespaces will be presented as packages, qualified
-# scopes will look different, etc.
-
-OPTIMIZE_OUTPUT_JAVA   = NO
-
-# Set the OPTIMIZE_FOR_FORTRAN tag to YES if your project consists of Fortran
-# sources only. Doxygen will then generate output that is more tailored for
-# Fortran.
-
-OPTIMIZE_FOR_FORTRAN   = NO
-
-# Set the OPTIMIZE_OUTPUT_VHDL tag to YES if your project consists of VHDL
-# sources. Doxygen will then generate output that is tailored for
-# VHDL.
-
-OPTIMIZE_OUTPUT_VHDL   = NO
-
-# Doxygen selects the parser to use depending on the extension of the files it parses.
-# With this tag you can assign which parser to use for a given extension.
-# Doxygen has a built-in mapping, but you can override or extend it using this tag.
-# The format is ext=language, where ext is a file extension, and language is one of
-# the parsers supported by doxygen: IDL, Java, Javascript, C#, C, C++, D, PHP,
-# Objective-C, Python, Fortran, VHDL, C, C++. For instance to make doxygen treat
-# .inc files as Fortran files (default is PHP), and .f files as C (default is Fortran),
-# use: inc=Fortran f=C. Note that for custom extensions you also need to set FILE_PATTERNS otherwise the files are not read by doxygen.
-
-EXTENSION_MAPPING      =
-
-# If you use STL classes (i.e. std::string, std::vector, etc.) but do not want
-# to include (a tag file for) the STL sources as input, then you should
-# set this tag to YES in order to let doxygen match functions declarations and
-# definitions whose arguments contain STL classes (e.g. func(std::string); v.s.
-# func(std::string) {}). This also make the inheritance and collaboration
-# diagrams that involve STL classes more complete and accurate.
-
-BUILTIN_STL_SUPPORT    = NO
-
-# If you use Microsoft's C++/CLI language, you should set this option to YES to
-# enable parsing support.
-
-CPP_CLI_SUPPORT        = NO
-
-# Set the SIP_SUPPORT tag to YES if your project consists of sip sources only.
-# Doxygen will parse them like normal C++ but will assume all classes use public
-# instead of private inheritance when no explicit protection keyword is present.
-
-SIP_SUPPORT            = NO
-
-# For Microsoft's IDL there are propget and propput attributes to indicate getter
-# and setter methods for a property. Setting this option to YES (the default)
-# will make doxygen to replace the get and set methods by a property in the
-# documentation. This will only work if the methods are indeed getting or
-# setting a simple type. If this is not the case, or you want to show the
-# methods anyway, you should set this option to NO.
-
-IDL_PROPERTY_SUPPORT   = YES
-
-# If member grouping is used in the documentation and the DISTRIBUTE_GROUP_DOC
-# tag is set to YES, then doxygen will reuse the documentation of the first
-# member in the group (if any) for the other members of the group. By default
-# all members of a group must be documented explicitly.
-
-DISTRIBUTE_GROUP_DOC   = NO
-
-# Set the SUBGROUPING tag to YES (the default) to allow class member groups of
-# the same type (for instance a group of public functions) to be put as a
-# subgroup of that type (e.g. under the Public Functions section). Set it to
-# NO to prevent subgrouping. Alternatively, this can be done per class using
-# the \nosubgrouping command.
-
-SUBGROUPING            = YES
-
-# When TYPEDEF_HIDES_STRUCT is enabled, a typedef of a struct, union, or enum
-# is documented as struct, union, or enum with the name of the typedef. So
-# typedef struct TypeS {} TypeT, will appear in the documentation as a struct
-# with name TypeT. When disabled the typedef will appear as a member of a file,
-# namespace, or class. And the struct will be named TypeS. This can typically
-# be useful for C code in case the coding convention dictates that all compound
-# types are typedef'ed and only the typedef is referenced, never the tag name.
-
-TYPEDEF_HIDES_STRUCT   = NO
-
-# The SYMBOL_CACHE_SIZE determines the size of the internal cache use to
-# determine which symbols to keep in memory and which to flush to disk.
-# When the cache is full, less often used symbols will be written to disk.
-# For small to medium size projects (<1000 input files) the default value is
-# probably good enough. For larger projects a too small cache size can cause
-# doxygen to be busy swapping symbols to and from disk most of the time
-# causing a significant performance penality.
-# If the system has enough physical memory increasing the cache will improve the
-# performance by keeping more symbols in memory. Note that the value works on
-# a logarithmic scale so increasing the size by one will rougly double the
-# memory usage. The cache size is given by this formula:
-# 2^(16+SYMBOL_CACHE_SIZE). The valid range is 0..9, the default is 0,
-# corresponding to a cache size of 2^16 = 65536 symbols
-
-SYMBOL_CACHE_SIZE      = 0
-
-#---------------------------------------------------------------------------
-# Build related configuration options
-#---------------------------------------------------------------------------
-
-# If the EXTRACT_ALL tag is set to YES doxygen will assume all entities in
-# documentation are documented, even if no documentation was available.
-# Private class members and static file members will be hidden unless
-# the EXTRACT_PRIVATE and EXTRACT_STATIC tags are set to YES
-
-EXTRACT_ALL            = NO
-
-# If the EXTRACT_PRIVATE tag is set to YES all private members of a class
-# will be included in the documentation.
-
-EXTRACT_PRIVATE        = NO
-
-# If the EXTRACT_STATIC tag is set to YES all static members of a file
-# will be included in the documentation.
-
-EXTRACT_STATIC         = NO
-
-# If the EXTRACT_LOCAL_CLASSES tag is set to YES classes (and structs)
-# defined locally in source files will be included in the documentation.
-# If set to NO only classes defined in header files are included.
-
-EXTRACT_LOCAL_CLASSES  = NO
-
-# This flag is only useful for Objective-C code. When set to YES local
-# methods, which are defined in the implementation section but not in
-# the interface are included in the documentation.
-# If set to NO (the default) only methods in the interface are included.
-
-EXTRACT_LOCAL_METHODS  = NO
-
-# If this flag is set to YES, the members of anonymous namespaces will be
-# extracted and appear in the documentation as a namespace called
-# 'anonymous_namespace{file}', where file will be replaced with the base
-# name of the file that contains the anonymous namespace. By default
-# anonymous namespace are hidden.
-
-EXTRACT_ANON_NSPACES   = NO
-
-# If the HIDE_UNDOC_MEMBERS tag is set to YES, Doxygen will hide all
-# undocumented members of documented classes, files or namespaces.
-# If set to NO (the default) these members will be included in the
-# various overviews, but no documentation section is generated.
-# This option has no effect if EXTRACT_ALL is enabled.
-
-HIDE_UNDOC_MEMBERS     = YES
-
-# If the HIDE_UNDOC_CLASSES tag is set to YES, Doxygen will hide all
-# undocumented classes that are normally visible in the class hierarchy.
-# If set to NO (the default) these classes will be included in the various
-# overviews. This option has no effect if EXTRACT_ALL is enabled.
-
-HIDE_UNDOC_CLASSES     = YES
-
-# If the HIDE_FRIEND_COMPOUNDS tag is set to YES, Doxygen will hide all
-# friend (class|struct|union) declarations.
-# If set to NO (the default) these declarations will be included in the
-# documentation.
-
-HIDE_FRIEND_COMPOUNDS  = NO
-
-# If the HIDE_IN_BODY_DOCS tag is set to YES, Doxygen will hide any
-# documentation blocks found inside the body of a function.
-# If set to NO (the default) these blocks will be appended to the
-# function's detailed documentation block.
-
-HIDE_IN_BODY_DOCS      = NO
-
-# The INTERNAL_DOCS tag determines if documentation
-# that is typed after a \internal command is included. If the tag is set
-# to NO (the default) then the documentation will be excluded.
-# Set it to YES to include the internal documentation.
-
-INTERNAL_DOCS          = NO
-
-# If the CASE_SENSE_NAMES tag is set to NO then Doxygen will only generate
-# file names in lower-case letters. If set to YES upper-case letters are also
-# allowed. This is useful if you have classes or files whose names only differ
-# in case and if your file system supports case sensitive file names. Windows
-# and Mac users are advised to set this option to NO.
-
-CASE_SENSE_NAMES       = YES
-
-# If the HIDE_SCOPE_NAMES tag is set to NO (the default) then Doxygen
-# will show members with their full class and namespace scopes in the
-# documentation. If set to YES the scope will be hidden.
-
-HIDE_SCOPE_NAMES       = NO
-
-# If the SHOW_INCLUDE_FILES tag is set to YES (the default) then Doxygen
-# will put a list of the files that are included by a file in the documentation
-# of that file.
-
-SHOW_INCLUDE_FILES     = YES
-
-# If the INLINE_INFO tag is set to YES (the default) then a tag [inline]
-# is inserted in the documentation for inline members.
-
-INLINE_INFO            = YES
-
-# If the SORT_MEMBER_DOCS tag is set to YES (the default) then doxygen
-# will sort the (detailed) documentation of file and class members
-# alphabetically by member name. If set to NO the members will appear in
-# declaration order.
-
-SORT_MEMBER_DOCS       = YES
-
-# If the SORT_BRIEF_DOCS tag is set to YES then doxygen will sort the
-# brief documentation of file, namespace and class members alphabetically
-# by member name. If set to NO (the default) the members will appear in
-# declaration order.
-
-SORT_BRIEF_DOCS        = NO
-
-# If the SORT_MEMBERS_CTORS_1ST tag is set to YES then doxygen will sort the (brief and detailed) documentation of class members so that constructors and destructors are listed first. If set to NO (the default) the constructors will appear in the respective orders defined by SORT_MEMBER_DOCS and SORT_BRIEF_DOCS. This tag will be ignored for brief docs if SORT_BRIEF_DOCS is set to NO and ignored for detailed docs if SORT_MEMBER_DOCS is set to NO.
-
-SORT_MEMBERS_CTORS_1ST = NO
-
-# If the SORT_GROUP_NAMES tag is set to YES then doxygen will sort the
-# hierarchy of group names into alphabetical order. If set to NO (the default)
-# the group names will appear in their defined order.
-
-SORT_GROUP_NAMES       = NO
-
-# If the SORT_BY_SCOPE_NAME tag is set to YES, the class list will be
-# sorted by fully-qualified names, including namespaces. If set to
-# NO (the default), the class list will be sorted only by class name,
-# not including the namespace part.
-# Note: This option is not very useful if HIDE_SCOPE_NAMES is set to YES.
-# Note: This option applies only to the class list, not to the
-# alphabetical list.
-
-SORT_BY_SCOPE_NAME     = NO
-
-# The GENERATE_TODOLIST tag can be used to enable (YES) or
-# disable (NO) the todo list. This list is created by putting \todo
-# commands in the documentation.
-
-GENERATE_TODOLIST      = YES
-
-# The GENERATE_TESTLIST tag can be used to enable (YES) or
-# disable (NO) the test list. This list is created by putting \test
-# commands in the documentation.
-
-GENERATE_TESTLIST      = YES
-
-# The GENERATE_BUGLIST tag can be used to enable (YES) or
-# disable (NO) the bug list. This list is created by putting \bug
-# commands in the documentation.
-
-GENERATE_BUGLIST       = YES
-
-# The GENERATE_DEPRECATEDLIST tag can be used to enable (YES) or
-# disable (NO) the deprecated list. This list is created by putting
-# \deprecated commands in the documentation.
-
-GENERATE_DEPRECATEDLIST= YES
-
-# The ENABLED_SECTIONS tag can be used to enable conditional
-# documentation sections, marked by \if sectionname ... \endif.
-
-ENABLED_SECTIONS       =
-
-# The MAX_INITIALIZER_LINES tag determines the maximum number of lines
-# the initial value of a variable or define consists of for it to appear in
-# the documentation. If the initializer consists of more lines than specified
-# here it will be hidden. Use a value of 0 to hide initializers completely.
-# The appearance of the initializer of individual variables and defines in the
-# documentation can be controlled using \showinitializer or \hideinitializer
-# command in the documentation regardless of this setting.
-
-MAX_INITIALIZER_LINES  = 30
-
-# Set the SHOW_USED_FILES tag to NO to disable the list of files generated
-# at the bottom of the documentation of classes and structs. If set to YES the
-# list will mention the files that were used to generate the documentation.
-
-SHOW_USED_FILES        = YES
-
-# If the sources in your project are distributed over multiple directories
-# then setting the SHOW_DIRECTORIES tag to YES will show the directory hierarchy
-# in the documentation. The default is NO.
-
-SHOW_DIRECTORIES       = NO
-
-# Set the SHOW_FILES tag to NO to disable the generation of the Files page.
-# This will remove the Files entry from the Quick Index and from the
-# Folder Tree View (if specified). The default is YES.
-
-SHOW_FILES             = YES
-
-# Set the SHOW_NAMESPACES tag to NO to disable the generation of the
-# Namespaces page.
-# This will remove the Namespaces entry from the Quick Index
-# and from the Folder Tree View (if specified). The default is YES.
-
-SHOW_NAMESPACES        = YES
-
-# The FILE_VERSION_FILTER tag can be used to specify a program or script that
-# doxygen should invoke to get the current version for each file (typically from
-# the version control system). Doxygen will invoke the program by executing (via
-# popen()) the command <command> <input-file>, where <command> is the value of
-# the FILE_VERSION_FILTER tag, and <input-file> is the name of an input file
-# provided by doxygen. Whatever the program writes to standard output
-# is used as the file version. See the manual for examples.
-
-FILE_VERSION_FILTER    =
-
-# The LAYOUT_FILE tag can be used to specify a layout file which will be parsed by
-# doxygen. The layout file controls the global structure of the generated output files
-# in an output format independent way. The create the layout file that represents
-# doxygen's defaults, run doxygen with the -l option. You can optionally specify a
-# file name after the option, if omitted DoxygenLayout.xml will be used as the name
-# of the layout file.
-
-LAYOUT_FILE            =
-
-#---------------------------------------------------------------------------
-# configuration options related to warning and progress messages
-#---------------------------------------------------------------------------
-
-# The QUIET tag can be used to turn on/off the messages that are generated
-# by doxygen. Possible values are YES and NO. If left blank NO is used.
-
-QUIET                  = NO
-
-# The WARNINGS tag can be used to turn on/off the warning messages that are
-# generated by doxygen. Possible values are YES and NO. If left blank
-# NO is used.
-
-WARNINGS               = YES
-
-# If WARN_IF_UNDOCUMENTED is set to YES, then doxygen will generate warnings
-# for undocumented members. If EXTRACT_ALL is set to YES then this flag will
-# automatically be disabled.
-
-WARN_IF_UNDOCUMENTED   = YES
-
-# If WARN_IF_DOC_ERROR is set to YES, doxygen will generate warnings for
-# potential errors in the documentation, such as not documenting some
-# parameters in a documented function, or documenting parameters that
-# don't exist or using markup commands wrongly.
-
-WARN_IF_DOC_ERROR      = YES
-
-# This WARN_NO_PARAMDOC option can be abled to get warnings for
-# functions that are documented, but have no documentation for their parameters
-# or return value. If set to NO (the default) doxygen will only warn about
-# wrong or incomplete parameter documentation, but not about the absence of
-# documentation.
-
-WARN_NO_PARAMDOC       = NO
-
-# The WARN_FORMAT tag determines the format of the warning messages that
-# doxygen can produce. The string should contain the $file, $line, and $text
-# tags, which will be replaced by the file and line number from which the
-# warning originated and the warning text. Optionally the format may contain
-# $version, which will be replaced by the version of the file (if it could
-# be obtained via FILE_VERSION_FILTER)
-
-WARN_FORMAT            = "$file:$line: $text"
-
-# The WARN_LOGFILE tag can be used to specify a file to which warning
-# and error messages should be written. If left blank the output is written
-# to stderr.
-
-WARN_LOGFILE           =
-
-#---------------------------------------------------------------------------
-# configuration options related to the input files
-#---------------------------------------------------------------------------
-
-# The INPUT tag can be used to specify the files and/or directories that contain
-# documented source files. You may enter file names like "myfile.cpp" or
-# directories like "/usr/src/myproject". Separate the files or directories
-# with spaces.
-
-INPUT                  = . doc
-
-# This tag can be used to specify the character encoding of the source files
-# that doxygen parses. Internally doxygen uses the UTF-8 encoding, which is
-# also the default input encoding. Doxygen uses libiconv (or the iconv built
-# into libc) for the transcoding. See http://www.gnu.org/software/libiconv for
-# the list of possible encodings.
-
-INPUT_ENCODING         = UTF-8
-
-# If the value of the INPUT tag contains directories, you can use the
-# FILE_PATTERNS tag to specify one or more wildcard pattern (like *.cpp
-# and *.h) to filter out the source-files in the directories. If left
-# blank the following patterns are tested:
-# *.c *.cc *.cxx *.cpp *.c++ *.java *.ii *.ixx *.ipp *.i++ *.inl *.h *.hh *.hxx
-# *.hpp *.h++ *.idl *.odl *.cs *.php *.php3 *.inc *.m *.mm *.py *.f90
-
-FILE_PATTERNS          = *.cpp \
-                         *.cc \
-                         *.c \
-                         *.h \
-                         *.hh \
-                         *.hpp \
-                         *.dox
-
-# The RECURSIVE tag can be used to turn specify whether or not subdirectories
-# should be searched for input files as well. Possible values are YES and NO.
-# If left blank NO is used.
-
-RECURSIVE              = NO
-
-# The EXCLUDE tag can be used to specify files and/or directories that should
-# excluded from the INPUT source files. This way you can easily exclude a
-# subdirectory from a directory tree whose root is specified with the INPUT tag.
-
-EXCLUDE                =
-
-# The EXCLUDE_SYMLINKS tag can be used select whether or not files or
-# directories that are symbolic links (a Unix filesystem feature) are excluded
-# from the input.
-
-EXCLUDE_SYMLINKS       = NO
-
-# If the value of the INPUT tag contains directories, you can use the
-# EXCLUDE_PATTERNS tag to specify one or more wildcard patterns to exclude
-# certain files from those directories. Note that the wildcards are matched
-# against the file with absolute path, so to exclude all test directories
-# for example use the pattern */test/*
-
-EXCLUDE_PATTERNS       = */.git/* \
-                         */.svn/* \
-                         */cmake/* \
-                         */build/*
-
-# The EXCLUDE_SYMBOLS tag can be used to specify one or more symbol names
-# (namespaces, classes, functions, etc.) that should be excluded from the
-# output. The symbol name can be a fully qualified name, a word, or if the
-# wildcard * is used, a substring. Examples: ANamespace, AClass,
-# AClass::ANamespace, ANamespace::*Test
-
-EXCLUDE_SYMBOLS        =
-
-# The EXAMPLE_PATH tag can be used to specify one or more files or
-# directories that contain example code fragments that are included (see
-# the \include command).
-
-EXAMPLE_PATH           =
-
-# If the value of the EXAMPLE_PATH tag contains directories, you can use the
-# EXAMPLE_PATTERNS tag to specify one or more wildcard pattern (like *.cpp
-# and *.h) to filter out the source-files in the directories. If left
-# blank all files are included.
-
-EXAMPLE_PATTERNS       =
-
-# If the EXAMPLE_RECURSIVE tag is set to YES then subdirectories will be
-# searched for input files to be used with the \include or \dontinclude
-# commands irrespective of the value of the RECURSIVE tag.
-# Possible values are YES and NO. If left blank NO is used.
-
-EXAMPLE_RECURSIVE      = NO
-
-# The IMAGE_PATH tag can be used to specify one or more files or
-# directories that contain image that are included in the documentation (see
-# the \image command).
-
-IMAGE_PATH             =
-
-# The INPUT_FILTER tag can be used to specify a program that doxygen should
-# invoke to filter for each input file. Doxygen will invoke the filter program
-# by executing (via popen()) the command <filter> <input-file>, where <filter>
-# is the value of the INPUT_FILTER tag, and <input-file> is the name of an
-# input file. Doxygen will then use the output that the filter program writes
-# to standard output.
-# If FILTER_PATTERNS is specified, this tag will be
-# ignored.
-
-INPUT_FILTER           =
-
-# The FILTER_PATTERNS tag can be used to specify filters on a per file pattern
-# basis.
-# Doxygen will compare the file name with each pattern and apply the
-# filter if there is a match.
-# The filters are a list of the form:
-# pattern=filter (like *.cpp=my_cpp_filter). See INPUT_FILTER for further
-# info on how filters are used. If FILTER_PATTERNS is empty, INPUT_FILTER
-# is applied to all files.
-
-FILTER_PATTERNS        =
-
-# If the FILTER_SOURCE_FILES tag is set to YES, the input filter (if set using
-# INPUT_FILTER) will be used to filter the input files when producing source
-# files to browse (i.e. when SOURCE_BROWSER is set to YES).
-
-FILTER_SOURCE_FILES    = NO
-
-#---------------------------------------------------------------------------
-# configuration options related to source browsing
-#---------------------------------------------------------------------------
-
-# If the SOURCE_BROWSER tag is set to YES then a list of source files will
-# be generated. Documented entities will be cross-referenced with these sources.
-# Note: To get rid of all source code in the generated output, make sure also
-# VERBATIM_HEADERS is set to NO.
-
-SOURCE_BROWSER         = NO
-
-# Setting the INLINE_SOURCES tag to YES will include the body
-# of functions and classes directly in the documentation.
-
-INLINE_SOURCES         = NO
-
-# Setting the STRIP_CODE_COMMENTS tag to YES (the default) will instruct
-# doxygen to hide any special comment blocks from generated source code
-# fragments. Normal C and C++ comments will always remain visible.
-
-STRIP_CODE_COMMENTS    = YES
-
-# If the REFERENCED_BY_RELATION tag is set to YES
-# then for each documented function all documented
-# functions referencing it will be listed.
-
-REFERENCED_BY_RELATION = NO
-
-# If the REFERENCES_RELATION tag is set to YES
-# then for each documented function all documented entities
-# called/used by that function will be listed.
-
-REFERENCES_RELATION    = NO
-
-# If the REFERENCES_LINK_SOURCE tag is set to YES (the default)
-# and SOURCE_BROWSER tag is set to YES, then the hyperlinks from
-# functions in REFERENCES_RELATION and REFERENCED_BY_RELATION lists will
-# link to the source code.
-# Otherwise they will link to the documentation.
-
-REFERENCES_LINK_SOURCE = YES
-
-# If the USE_HTAGS tag is set to YES then the references to source code
-# will point to the HTML generated by the htags(1) tool instead of doxygen
-# built-in source browser. The htags tool is part of GNU's global source
-# tagging system (see http://www.gnu.org/software/global/global.html). You
-# will need version 4.8.6 or higher.
-
-USE_HTAGS              = NO
-
-# If the VERBATIM_HEADERS tag is set to YES (the default) then Doxygen
-# will generate a verbatim copy of the header file for each class for
-# which an include is specified. Set to NO to disable this.
-
-VERBATIM_HEADERS       = YES
-
-#---------------------------------------------------------------------------
-# configuration options related to the alphabetical class index
-#---------------------------------------------------------------------------
-
-# If the ALPHABETICAL_INDEX tag is set to YES, an alphabetical index
-# of all compounds will be generated. Enable this if the project
-# contains a lot of classes, structs, unions or interfaces.
-
-ALPHABETICAL_INDEX     = NO
-
-# If the alphabetical index is enabled (see ALPHABETICAL_INDEX) then
-# the COLS_IN_ALPHA_INDEX tag can be used to specify the number of columns
-# in which this list will be split (can be a number in the range [1..20])
-
-COLS_IN_ALPHA_INDEX    = 5
-
-# In case all classes in a project start with a common prefix, all
-# classes will be put under the same header in the alphabetical index.
-# The IGNORE_PREFIX tag can be used to specify one or more prefixes that
-# should be ignored while generating the index headers.
-
-IGNORE_PREFIX          =
-
-#---------------------------------------------------------------------------
-# configuration options related to the HTML output
-#---------------------------------------------------------------------------
-
-# If the GENERATE_HTML tag is set to YES (the default) Doxygen will
-# generate HTML output.
-
-GENERATE_HTML          = YES
-
-# If the HTML_FOOTER_DESCRIPTION tag is set to YES, Doxygen will
-# add generated date, project name and doxygen version to HTML footer.
-
-HTML_FOOTER_DESCRIPTION= NO
-
-# The HTML_OUTPUT tag is used to specify where the HTML docs will be put.
-# If a relative path is entered the value of OUTPUT_DIRECTORY will be
-# put in front of it. If left blank `html' will be used as the default path.
-
-HTML_OUTPUT            = html
-
-# The HTML_FILE_EXTENSION tag can be used to specify the file extension for
-# each generated HTML page (for example: .htm,.php,.asp). If it is left blank
-# doxygen will generate files with .html extension.
-
-HTML_FILE_EXTENSION    = .html
-
-# The HTML_HEADER tag can be used to specify a personal HTML header for
-# each generated HTML page. If it is left blank doxygen will generate a
-# standard header.
-
-HTML_HEADER            =
-
-# The HTML_FOOTER tag can be used to specify a personal HTML footer for
-# each generated HTML page. If it is left blank doxygen will generate a
-# standard footer.
-
-HTML_FOOTER            =
-
-# The HTML_STYLESHEET tag can be used to specify a user-defined cascading
-# style sheet that is used by each HTML page. It can be used to
-# fine-tune the look of the HTML output. If the tag is left blank doxygen
-# will generate a default style sheet. Note that doxygen will try to copy
-# the style sheet file to the HTML output directory, so don't put your own
-# stylesheet in the HTML output directory as well, or it will be erased!
-
-HTML_STYLESHEET        =
-
-# If the HTML_ALIGN_MEMBERS tag is set to YES, the members of classes,
-# files or namespaces will be aligned in HTML using tables. If set to
-# NO a bullet list will be used.
-
-HTML_ALIGN_MEMBERS     = YES
-
-# If the HTML_DYNAMIC_SECTIONS tag is set to YES then the generated HTML
-# documentation will contain sections that can be hidden and shown after the
-# page has loaded. For this to work a browser that supports
-# JavaScript and DHTML is required (for instance Mozilla 1.0+, Firefox
-# Netscape 6.0+, Internet explorer 5.0+, Konqueror, or Safari).
-
-HTML_DYNAMIC_SECTIONS  = NO
-
-# If the GENERATE_DOCSET tag is set to YES, additional index files
-# will be generated that can be used as input for Apple's Xcode 3
-# integrated development environment, introduced with OSX 10.5 (Leopard).
-# To create a documentation set, doxygen will generate a Makefile in the
-# HTML output directory. Running make will produce the docset in that
-# directory and running "make install" will install the docset in
-# ~/Library/Developer/Shared/Documentation/DocSets so that Xcode will find
-# it at startup.
-# See http://developer.apple.com/tools/creatingdocsetswithdoxygen.html for more information.
-
-GENERATE_DOCSET        = NO
-
-# When GENERATE_DOCSET tag is set to YES, this tag determines the name of the
-# feed. A documentation feed provides an umbrella under which multiple
-# documentation sets from a single provider (such as a company or product suite)
-# can be grouped.
-
-DOCSET_FEEDNAME        = "Doxygen generated docs"
-
-# When GENERATE_DOCSET tag is set to YES, this tag specifies a string that
-# should uniquely identify the documentation set bundle. This should be a
-# reverse domain-name style string, e.g. com.mycompany.MyDocSet. Doxygen
-# will append .docset to the name.
-
-DOCSET_BUNDLE_ID       = org.doxygen.Project
-
-# If the GENERATE_HTMLHELP tag is set to YES, additional index files
-# will be generated that can be used as input for tools like the
-# Microsoft HTML help workshop to generate a compiled HTML help file (.chm)
-# of the generated HTML documentation.
-
-GENERATE_HTMLHELP      = NO
-
-# If the GENERATE_HTMLHELP tag is set to YES, the CHM_FILE tag can
-# be used to specify the file name of the resulting .chm file. You
-# can add a path in front of the file if the result should not be
-# written to the html output directory.
-
-CHM_FILE               =
-
-# If the GENERATE_HTMLHELP tag is set to YES, the HHC_LOCATION tag can
-# be used to specify the location (absolute path including file name) of
-# the HTML help compiler (hhc.exe). If non-empty doxygen will try to run
-# the HTML help compiler on the generated index.hhp.
-
-HHC_LOCATION           =
-
-# If the GENERATE_HTMLHELP tag is set to YES, the GENERATE_CHI flag
-# controls if a separate .chi index file is generated (YES) or that
-# it should be included in the master .chm file (NO).
-
-GENERATE_CHI           = NO
-
-# If the GENERATE_HTMLHELP tag is set to YES, the CHM_INDEX_ENCODING
-# is used to encode HtmlHelp index (hhk), content (hhc) and project file
-# content.
-
-CHM_INDEX_ENCODING     =
-
-# If the GENERATE_HTMLHELP tag is set to YES, the BINARY_TOC flag
-# controls whether a binary table of contents is generated (YES) or a
-# normal table of contents (NO) in the .chm file.
-
-BINARY_TOC             = NO
-
-# The TOC_EXPAND flag can be set to YES to add extra items for group members
-# to the contents of the HTML help documentation and to the tree view.
-
-TOC_EXPAND             = NO
-
-# If the GENERATE_QHP tag is set to YES and both QHP_NAMESPACE and QHP_VIRTUAL_FOLDER
-# are set, an additional index file will be generated that can be used as input for
-# Qt's qhelpgenerator to generate a Qt Compressed Help (.qch) of the generated
-# HTML documentation.
-
-GENERATE_QHP           = NO
-
-# If the QHG_LOCATION tag is specified, the QCH_FILE tag can
-# be used to specify the file name of the resulting .qch file.
-# The path specified is relative to the HTML output folder.
-
-QCH_FILE               =
-
-# The QHP_NAMESPACE tag specifies the namespace to use when generating
-# Qt Help Project output. For more information please see
-# http://doc.trolltech.com/qthelpproject.html#namespace
-
-QHP_NAMESPACE          =
-
-# The QHP_VIRTUAL_FOLDER tag specifies the namespace to use when generating
-# Qt Help Project output. For more information please see
-# http://doc.trolltech.com/qthelpproject.html#virtual-folders
-
-QHP_VIRTUAL_FOLDER     = doc
-
-# If QHP_CUST_FILTER_NAME is set, it specifies the name of a custom filter to add.
-# For more information please see
-# http://doc.trolltech.com/qthelpproject.html#custom-filters
-
-QHP_CUST_FILTER_NAME   =
-
-# The QHP_CUST_FILT_ATTRS tag specifies the list of the attributes of the custom filter to add.For more information please see
-# <a href="http://doc.trolltech.com/qthelpproject.html#custom-filters">Qt Help Project / Custom Filters</a>.
-
-QHP_CUST_FILTER_ATTRS  =
-
-# The QHP_SECT_FILTER_ATTRS tag specifies the list of the attributes this project's
-# filter section matches.
-# <a href="http://doc.trolltech.com/qthelpproject.html#filter-attributes">Qt Help Project / Filter Attributes</a>.
-
-QHP_SECT_FILTER_ATTRS  =
-
-# If the GENERATE_QHP tag is set to YES, the QHG_LOCATION tag can
-# be used to specify the location of Qt's qhelpgenerator.
-# If non-empty doxygen will try to run qhelpgenerator on the generated
-# .qhp file.
-
-QHG_LOCATION           =
-
-# The DISABLE_INDEX tag can be used to turn on/off the condensed index at
-# top of each HTML page. The value NO (the default) enables the index and
-# the value YES disables it.
-
-DISABLE_INDEX          = NO
-
-# This tag can be used to set the number of enum values (range [1..20])
-# that doxygen will group on one line in the generated HTML documentation.
-
-ENUM_VALUES_PER_LINE   = 4
-
-# The GENERATE_TREEVIEW tag is used to specify whether a tree-like index
-# structure should be generated to display hierarchical information.
-# If the tag value is set to YES, a side panel will be generated
-# containing a tree-like index structure (just like the one that
-# is generated for HTML Help). For this to work a browser that supports
-# JavaScript, DHTML, CSS and frames is required (i.e. any modern browser).
-# Windows users are probably better off using the HTML help feature.
-
-GENERATE_TREEVIEW      = NONE
-
-# By enabling USE_INLINE_TREES, doxygen will generate the Groups, Directories,
-# and Class Hierarchy pages using a tree view instead of an ordered list.
-
-USE_INLINE_TREES       = NO
-
-# If the treeview is enabled (see GENERATE_TREEVIEW) then this tag can be
-# used to set the initial width (in pixels) of the frame in which the tree
-# is shown.
-
-TREEVIEW_WIDTH         = 250
-
-# Use this tag to change the font size of Latex formulas included
-# as images in the HTML documentation. The default is 10. Note that
-# when you change the font size after a successful doxygen run you need
-# to manually remove any form_*.png images from the HTML output directory
-# to force them to be regenerated.
-
-FORMULA_FONTSIZE       = 10
-
-# When the SEARCHENGINE tag is enable doxygen will generate a search box for the HTML output. The underlying search engine uses javascript
-# and DHTML and should work on any modern browser. Note that when using HTML help (GENERATE_HTMLHELP) or Qt help (GENERATE_QHP)
-# there is already a search function so this one should typically
-# be disabled.
-
-SEARCHENGINE           = NO
-
-#---------------------------------------------------------------------------
-# configuration options related to the LaTeX output
-#---------------------------------------------------------------------------
-
-# If the GENERATE_LATEX tag is set to YES (the default) Doxygen will
-# generate Latex output.
-
-GENERATE_LATEX         = YES
-
-# The LATEX_OUTPUT tag is used to specify where the LaTeX docs will be put.
-# If a relative path is entered the value of OUTPUT_DIRECTORY will be
-# put in front of it. If left blank `latex' will be used as the default path.
-
-LATEX_OUTPUT           = latex
-
-# The LATEX_CMD_NAME tag can be used to specify the LaTeX command name to be
-# invoked. If left blank `latex' will be used as the default command name.
-
-LATEX_CMD_NAME         = latex
-
-# The MAKEINDEX_CMD_NAME tag can be used to specify the command name to
-# generate index for LaTeX. If left blank `makeindex' will be used as the
-# default command name.
-
-MAKEINDEX_CMD_NAME     = makeindex
-
-# If the COMPACT_LATEX tag is set to YES Doxygen generates more compact
-# LaTeX documents. This may be useful for small projects and may help to
-# save some trees in general.
-
-COMPACT_LATEX          = NO
-
-# The PAPER_TYPE tag can be used to set the paper type that is used
-# by the printer. Possible values are: a4, a4wide, letter, legal and
-# executive. If left blank a4wide will be used.
-
-PAPER_TYPE             = a4wide
-
-# The EXTRA_PACKAGES tag can be to specify one or more names of LaTeX
-# packages that should be included in the LaTeX output.
-
-EXTRA_PACKAGES         =
-
-# The LATEX_HEADER tag can be used to specify a personal LaTeX header for
-# the generated latex document. The header should contain everything until
-# the first chapter. If it is left blank doxygen will generate a
-# standard header. Notice: only use this tag if you know what you are doing!
-
-LATEX_HEADER           =
-
-# If the PDF_HYPERLINKS tag is set to YES, the LaTeX that is generated
-# is prepared for conversion to pdf (using ps2pdf). The pdf file will
-# contain links (just like the HTML output) instead of page references
-# This makes the output suitable for online browsing using a pdf viewer.
-
-PDF_HYPERLINKS         = YES
-
-# If the USE_PDFLATEX tag is set to YES, pdflatex will be used instead of
-# plain latex in the generated Makefile. Set this option to YES to get a
-# higher quality PDF documentation.
-
-USE_PDFLATEX           = YES
-
-# If the LATEX_BATCHMODE tag is set to YES, doxygen will add the \\batchmode.
-# command to the generated LaTeX files. This will instruct LaTeX to keep
-# running if errors occur, instead of asking the user for help.
-# This option is also used when generating formulas in HTML.
-
-LATEX_BATCHMODE        = NO
-
-# If LATEX_HIDE_INDICES is set to YES then doxygen will not
-# include the index chapters (such as File Index, Compound Index, etc.)
-# in the output.
-
-LATEX_HIDE_INDICES     = NO
-
-# If LATEX_SOURCE_CODE is set to YES then doxygen will include source code with syntax highlighting in the LaTeX output. Note that which sources are shown also depends on other settings such as SOURCE_BROWSER.
-
-LATEX_SOURCE_CODE      = NO
-
-#---------------------------------------------------------------------------
-# configuration options related to the RTF output
-#---------------------------------------------------------------------------
-
-# If the GENERATE_RTF tag is set to YES Doxygen will generate RTF output
-# The RTF output is optimized for Word 97 and may not look very pretty with
-# other RTF readers or editors.
-
-GENERATE_RTF           = NO
-
-# The RTF_OUTPUT tag is used to specify where the RTF docs will be put.
-# If a relative path is entered the value of OUTPUT_DIRECTORY will be
-# put in front of it. If left blank `rtf' will be used as the default path.
-
-RTF_OUTPUT             = rtf
-
-# If the COMPACT_RTF tag is set to YES Doxygen generates more compact
-# RTF documents. This may be useful for small projects and may help to
-# save some trees in general.
-
-COMPACT_RTF            = NO
-
-# If the RTF_HYPERLINKS tag is set to YES, the RTF that is generated
-# will contain hyperlink fields. The RTF file will
-# contain links (just like the HTML output) instead of page references.
-# This makes the output suitable for online browsing using WORD or other
-# programs which support those fields.
-# Note: wordpad (write) and others do not support links.
-
-RTF_HYPERLINKS         = NO
-
-# Load stylesheet definitions from file. Syntax is similar to doxygen's
-# config file, i.e. a series of assignments. You only have to provide
-# replacements, missing definitions are set to their default value.
-
-RTF_STYLESHEET_FILE    =
-
-# Set optional variables used in the generation of an rtf document.
-# Syntax is similar to doxygen's config file.
-
-RTF_EXTENSIONS_FILE    =
-
-#---------------------------------------------------------------------------
-# configuration options related to the man page output
-#---------------------------------------------------------------------------
-
-# If the GENERATE_MAN tag is set to YES (the default) Doxygen will
-# generate man pages
-
-GENERATE_MAN           = YES
-
-# The MAN_OUTPUT tag is used to specify where the man pages will be put.
-# If a relative path is entered the value of OUTPUT_DIRECTORY will be
-# put in front of it. If left blank `man' will be used as the default path.
-
-MAN_OUTPUT             = man
-
-# The MAN_EXTENSION tag determines the extension that is added to
-# the generated man pages (default is the subroutine's section .3)
-
-MAN_EXTENSION          = .3
-
-# If the MAN_LINKS tag is set to YES and Doxygen generates man output,
-# then it will generate one additional man file for each entity
-# documented in the real man page(s). These additional files
-# only source the real man page, but without them the man command
-# would be unable to find the correct page. The default is NO.
-
-MAN_LINKS              = NO
-
-#---------------------------------------------------------------------------
-# configuration options related to the XML output
-#---------------------------------------------------------------------------
-
-# If the GENERATE_XML tag is set to YES Doxygen will
-# generate an XML file that captures the structure of
-# the code including all documentation.
-
-GENERATE_XML           = NO
-
-# The XML_OUTPUT tag is used to specify where the XML pages will be put.
-# If a relative path is entered the value of OUTPUT_DIRECTORY will be
-# put in front of it. If left blank `xml' will be used as the default path.
-
-XML_OUTPUT             = xml
-
-# The XML_SCHEMA tag can be used to specify an XML schema,
-# which can be used by a validating XML parser to check the
-# syntax of the XML files.
-
-XML_SCHEMA             =
-
-# The XML_DTD tag can be used to specify an XML DTD,
-# which can be used by a validating XML parser to check the
-# syntax of the XML files.
-
-XML_DTD                =
-
-# If the XML_PROGRAMLISTING tag is set to YES Doxygen will
-# dump the program listings (including syntax highlighting
-# and cross-referencing information) to the XML output. Note that
-# enabling this will significantly increase the size of the XML output.
-
-XML_PROGRAMLISTING     = YES
-
-#---------------------------------------------------------------------------
-# configuration options for the AutoGen Definitions output
-#---------------------------------------------------------------------------
-
-# If the GENERATE_AUTOGEN_DEF tag is set to YES Doxygen will
-# generate an AutoGen Definitions (see autogen.sf.net) file
-# that captures the structure of the code including all
-# documentation. Note that this feature is still experimental
-# and incomplete at the moment.
-
-GENERATE_AUTOGEN_DEF   = NO
-
-#---------------------------------------------------------------------------
-# configuration options related to the Perl module output
-#---------------------------------------------------------------------------
-
-# If the GENERATE_PERLMOD tag is set to YES Doxygen will
-# generate a Perl module file that captures the structure of
-# the code including all documentation. Note that this
-# feature is still experimental and incomplete at the
-# moment.
-
-GENERATE_PERLMOD       = NO
-
-# If the PERLMOD_LATEX tag is set to YES Doxygen will generate
-# the necessary Makefile rules, Perl scripts and LaTeX code to be able
-# to generate PDF and DVI output from the Perl module output.
-
-PERLMOD_LATEX          = NO
-
-# If the PERLMOD_PRETTY tag is set to YES the Perl module output will be
-# nicely formatted so it can be parsed by a human reader.
-# This is useful
-# if you want to understand what is going on.
-# On the other hand, if this
-# tag is set to NO the size of the Perl module output will be much smaller
-# and Perl will parse it just the same.
-
-PERLMOD_PRETTY         = YES
-
-# The names of the make variables in the generated doxyrules.make file
-# are prefixed with the string contained in PERLMOD_MAKEVAR_PREFIX.
-# This is useful so different doxyrules.make files included by the same
-# Makefile don't overwrite each other's variables.
-
-PERLMOD_MAKEVAR_PREFIX =
-
-#---------------------------------------------------------------------------
-# Configuration options related to the preprocessor
-#---------------------------------------------------------------------------
-
-# If the ENABLE_PREPROCESSING tag is set to YES (the default) Doxygen will
-# evaluate all C-preprocessor directives found in the sources and include
-# files.
-
-ENABLE_PREPROCESSING   = YES
-
-# If the MACRO_EXPANSION tag is set to YES Doxygen will expand all macro
-# names in the source code. If set to NO (the default) only conditional
-# compilation will be performed. Macro expansion can be done in a controlled
-# way by setting EXPAND_ONLY_PREDEF to YES.
-
-MACRO_EXPANSION        = YES
-
-# If the EXPAND_ONLY_PREDEF and MACRO_EXPANSION tags are both set to YES
-# then the macro expansion is limited to the macros specified with the
-# PREDEFINED and EXPAND_AS_DEFINED tags.
-
-EXPAND_ONLY_PREDEF     = YES
-
-# If the SEARCH_INCLUDES tag is set to YES (the default) the includes files
-# in the INCLUDE_PATH (see below) will be search if a #include is found.
-
-SEARCH_INCLUDES        = YES
-
-# The INCLUDE_PATH tag can be used to specify one or more directories that
-# contain include files that are not input files but should be processed by
-# the preprocessor.
-
-INCLUDE_PATH           =
-
-# You can use the INCLUDE_FILE_PATTERNS tag to specify one or more wildcard
-# patterns (like *.h and *.hpp) to filter out the header-files in the
-# directories. If left blank, the patterns specified with FILE_PATTERNS will
-# be used.
-
-INCLUDE_FILE_PATTERNS  =
-
-# The PREDEFINED tag can be used to specify one or more macro names that
-# are defined before the preprocessor is started (similar to the -D option of
-# gcc). The argument of the tag is a list of macros of the form: name
-# or name=definition (no spaces). If the definition and the = are
-# omitted =1 is assumed. To prevent a macro definition from being
-# undefined via #undef or recursively expanded use the := operator
-# instead of the = operator.
-
-PREDEFINED             = DOXYGEN PRINTF_ATTRIBUTE(x,y)=
-
-# If the MACRO_EXPANSION and EXPAND_ONLY_PREDEF tags are set to YES then
-# this tag can be used to specify a list of macro names that should be expanded.
-# The macro definition that is found in the sources will be used.
-# Use the PREDEFINED tag if you want to use a different macro definition.
-
-EXPAND_AS_DEFINED      =
-
-# If the SKIP_FUNCTION_MACROS tag is set to YES (the default) then
-# doxygen's preprocessor will remove all function-like macros that are alone
-# on a line, have an all uppercase name, and do not end with a semicolon. Such
-# function macros are typically used for boiler-plate code, and will confuse
-# the parser if not removed.
-
-SKIP_FUNCTION_MACROS   = YES
-
-#---------------------------------------------------------------------------
-# Configuration::additions related to external references
-#---------------------------------------------------------------------------
-
-# The TAGFILES option can be used to specify one or more tagfiles.
-# Optionally an initial location of the external documentation
-# can be added for each tagfile. The format of a tag file without
-# this location is as follows:
-#
-# TAGFILES = file1 file2 ...
-# Adding location for the tag files is done as follows:
-#
-# TAGFILES = file1=loc1 "file2 = loc2" ...
-# where "loc1" and "loc2" can be relative or absolute paths or
-# URLs. If a location is present for each tag, the installdox tool
-# does not have to be run to correct the links.
-# Note that each tag file must have a unique name
-# (where the name does NOT include the path)
-# If a tag file is not located in the directory in which doxygen
-# is run, you must also specify the path to the tagfile here.
-
-TAGFILES               =
-
-# When a file name is specified after GENERATE_TAGFILE, doxygen will create
-# a tag file that is based on the input files it reads.
-
-GENERATE_TAGFILE       =
-
-# If the ALLEXTERNALS tag is set to YES all external classes will be listed
-# in the class index. If set to NO only the inherited external classes
-# will be listed.
-
-ALLEXTERNALS           = NO
-
-# If the EXTERNAL_GROUPS tag is set to YES all external groups will be listed
-# in the modules index. If set to NO, only the current project's groups will
-# be listed.
-
-EXTERNAL_GROUPS        = YES
-
-# The PERL_PATH should be the absolute path and name of the perl script
-# interpreter (i.e. the result of `which perl').
-
-PERL_PATH              = /usr/bin/perl
-
-#---------------------------------------------------------------------------
-# Configuration options related to the dot tool
-#---------------------------------------------------------------------------
-
-# If the CLASS_DIAGRAMS tag is set to YES (the default) Doxygen will
-# generate a inheritance diagram (in HTML, RTF and LaTeX) for classes with base
-# or super classes. Setting the tag to NO turns the diagrams off. Note that
-# this option is superseded by the HAVE_DOT option below. This is only a
-# fallback. It is recommended to install and use dot, since it yields more
-# powerful graphs.
-
-CLASS_DIAGRAMS         = YES
-
-# You can define message sequence charts within doxygen comments using the \msc
-# command. Doxygen will then run the mscgen tool (see
-# http://www.mcternan.me.uk/mscgen/) to produce the chart and insert it in the
-# documentation. The MSCGEN_PATH tag allows you to specify the directory where
-# the mscgen tool resides. If left empty the tool is assumed to be found in the
-# default search path.
-
-MSCGEN_PATH            =
-
-# If set to YES, the inheritance and collaboration graphs will hide
-# inheritance and usage relations if the target is undocumented
-# or is not a class.
-
-HIDE_UNDOC_RELATIONS   = YES
-
-# If you set the HAVE_DOT tag to YES then doxygen will assume the dot tool is
-# available from the path. This tool is part of Graphviz, a graph visualization
-# toolkit from AT&T and Lucent Bell Labs. The other options in this section
-# have no effect if this option is set to NO (the default)
-
-HAVE_DOT               = NO
-
-# By default doxygen will write a font called FreeSans.ttf to the output
-# directory and reference it in all dot files that doxygen generates. This
-# font does not include all possible unicode characters however, so when you need
-# these (or just want a differently looking font) you can specify the font name
-# using DOT_FONTNAME. You need need to make sure dot is able to find the font,
-# which can be done by putting it in a standard location or by setting the
-# DOTFONTPATH environment variable or by setting DOT_FONTPATH to the directory
-# containing the font.
-
-DOT_FONTNAME           = FreeSans
-
-# The DOT_FONTSIZE tag can be used to set the size of the font of dot graphs.
-# The default size is 10pt.
-
-DOT_FONTSIZE           = 10
-
-# By default doxygen will tell dot to use the output directory to look for the
-# FreeSans.ttf font (which doxygen will put there itself). If you specify a
-# different font using DOT_FONTNAME you can set the path where dot
-# can find it using this tag.
-
-DOT_FONTPATH           =
-
-# If the CLASS_GRAPH and HAVE_DOT tags are set to YES then doxygen
-# will generate a graph for each documented class showing the direct and
-# indirect inheritance relations. Setting this tag to YES will force the
-# the CLASS_DIAGRAMS tag to NO.
-
-CLASS_GRAPH            = YES
-
-# If the COLLABORATION_GRAPH and HAVE_DOT tags are set to YES then doxygen
-# will generate a graph for each documented class showing the direct and
-# indirect implementation dependencies (inheritance, containment, and
-# class references variables) of the class with other documented classes.
-
-COLLABORATION_GRAPH    = YES
-
-# If the GROUP_GRAPHS and HAVE_DOT tags are set to YES then doxygen
-# will generate a graph for groups, showing the direct groups dependencies
-
-GROUP_GRAPHS           = YES
-
-# If the UML_LOOK tag is set to YES doxygen will generate inheritance and
-# collaboration diagrams in a style similar to the OMG's Unified Modeling
-# Language.
-
-UML_LOOK               = NO
-
-# If set to YES, the inheritance and collaboration graphs will show the
-# relations between templates and their instances.
-
-TEMPLATE_RELATIONS     = NO
-
-# If the ENABLE_PREPROCESSING, SEARCH_INCLUDES, INCLUDE_GRAPH, and HAVE_DOT
-# tags are set to YES then doxygen will generate a graph for each documented
-# file showing the direct and indirect include dependencies of the file with
-# other documented files.
-
-INCLUDE_GRAPH          = YES
-
-# If the ENABLE_PREPROCESSING, SEARCH_INCLUDES, INCLUDED_BY_GRAPH, and
-# HAVE_DOT tags are set to YES then doxygen will generate a graph for each
-# documented header file showing the documented files that directly or
-# indirectly include this file.
-
-INCLUDED_BY_GRAPH      = YES
-
-# If the CALL_GRAPH and HAVE_DOT options are set to YES then
-# doxygen will generate a call dependency graph for every global function
-# or class method. Note that enabling this option will significantly increase
-# the time of a run. So in most cases it will be better to enable call graphs
-# for selected functions only using the \callgraph command.
-
-CALL_GRAPH             = NO
-
-# If the CALLER_GRAPH and HAVE_DOT tags are set to YES then
-# doxygen will generate a caller dependency graph for every global function
-# or class method. Note that enabling this option will significantly increase
-# the time of a run. So in most cases it will be better to enable caller
-# graphs for selected functions only using the \callergraph command.
-
-CALLER_GRAPH           = NO
-
-# If the GRAPHICAL_HIERARCHY and HAVE_DOT tags are set to YES then doxygen
-# will graphical hierarchy of all classes instead of a textual one.
-
-GRAPHICAL_HIERARCHY    = YES
-
-# If the DIRECTORY_GRAPH, SHOW_DIRECTORIES and HAVE_DOT tags are set to YES
-# then doxygen will show the dependencies a directory has on other directories
-# in a graphical way. The dependency relations are determined by the #include
-# relations between the files in the directories.
-
-DIRECTORY_GRAPH        = YES
-
-# The DOT_IMAGE_FORMAT tag can be used to set the image format of the images
-# generated by dot. Possible values are png, jpg, or gif
-# If left blank png will be used.
-
-DOT_IMAGE_FORMAT       = png
-
-# The tag DOT_PATH can be used to specify the path where the dot tool can be
-# found. If left blank, it is assumed the dot tool can be found in the path.
-
-DOT_PATH               =
-
-# The DOTFILE_DIRS tag can be used to specify one or more directories that
-# contain dot files that are included in the documentation (see the
-# \dotfile command).
-
-DOTFILE_DIRS           =
-
-# The DOT_GRAPH_MAX_NODES tag can be used to set the maximum number of
-# nodes that will be shown in the graph. If the number of nodes in a graph
-# becomes larger than this value, doxygen will truncate the graph, which is
-# visualized by representing a node as a red box. Note that doxygen if the
-# number of direct children of the root node in a graph is already larger than
-# DOT_GRAPH_MAX_NODES then the graph will not be shown at all. Also note
-# that the size of a graph can be further restricted by MAX_DOT_GRAPH_DEPTH.
-
-DOT_GRAPH_MAX_NODES    = 50
-
-# The MAX_DOT_GRAPH_DEPTH tag can be used to set the maximum depth of the
-# graphs generated by dot. A depth value of 3 means that only nodes reachable
-# from the root by following a path via at most 3 edges will be shown. Nodes
-# that lay further from the root node will be omitted. Note that setting this
-# option to 1 or 2 may greatly reduce the computation time needed for large
-# code bases. Also note that the size of a graph can be further restricted by
-# DOT_GRAPH_MAX_NODES. Using a depth of 0 means no depth restriction.
-
-MAX_DOT_GRAPH_DEPTH    = 0
-
-# Set the DOT_TRANSPARENT tag to YES to generate images with a transparent
-# background. This is disabled by default, because dot on Windows does not
-# seem to support this out of the box. Warning: Depending on the platform used,
-# enabling this option may lead to badly anti-aliased labels on the edges of
-# a graph (i.e. they become hard to read).
-
-DOT_TRANSPARENT        = YES
-
-# Set the DOT_MULTI_TARGETS tag to YES allow dot to generate multiple output
-# files in one run (i.e. multiple -o and -T options on the command line). This
-# makes dot run faster, but since only newer versions of dot (>1.8.10)
-# support this, this feature is disabled by default.
-
-DOT_MULTI_TARGETS      = NO
-
-# If the GENERATE_LEGEND tag is set to YES (the default) Doxygen will
-# generate a legend page explaining the meaning of the various boxes and
-# arrows in the dot generated graphs.
-
-GENERATE_LEGEND        = YES
-
-# If the DOT_CLEANUP tag is set to YES (the default) Doxygen will
-# remove the intermediate dot files that are used to generate
-# the various graphs.
-
-DOT_CLEANUP            = YES
diff --git a/lib/tevent/libtevent.m4 b/lib/tevent/libtevent.m4
deleted file mode 100644
index 2141af6..0000000
--- a/lib/tevent/libtevent.m4
+++ /dev/null
@@ -1,60 +0,0 @@
-dnl Check to see if we should use the included tevent
-
-INCLUDED_TEVENT=auto
-AC_ARG_WITH(included-tevent,
-    [AC_HELP_STRING([--with-included-tevent], [use bundled tevent library, not from system])],
-    [ INCLUDED_TEVENT=$withval ])
-
-AC_SUBST(TEVENT_LIBS)
-AC_SUBST(TEVENT_CFLAGS)
-
-if test x"$INCLUDED_TEVENT" != x"yes" ; then
-    AC_CHECK_HEADERS(tevent.h)
-    AC_CHECK_LIB(tevent, tevent_context_init, [ TEVENT_LIBS="-ltevent" ])
-    AC_CHECK_DECLS([TEVENT_TRACE_BEFORE_WAIT], [[#include <tevent.h>]])
-    if test x"$ac_cv_header_tevent_h" = x"no" -o \
-	x"$ac_cv_lib_tevent_tevent_context_init" = x"no" -o \
-	x"$ac_cv_have_decl_TEVENT_TRACE_BEFORE_WAIT" = x"no" ; then
-        INCLUDED_TEVENT=yes
-        TEVENT_CFLAGS=""
-    else
-        INCLUDED_TEVENT=no
-    fi
-fi
-
-AC_MSG_CHECKING(whether to use included tevent)
-AC_MSG_RESULT($INCLUDED_TEVENT)
-if test x"$INCLUDED_TEVENT" != x"no" ; then
-    dnl find the tevent sources. This is meant to work both for
-    dnl standalone builds, and builds of packages using libtevent
-	teventdir=""
-	teventpaths="$srcdir $srcdir/lib/tevent $srcdir/tevent $srcdir/../tevent"
-	for d in $teventpaths; do
-		if test -f "$d/tevent.c"; then
-			teventdir="$d"
-            AC_SUBST(teventdir)
-			break
-		fi
-	done
-	if test x"$teventdir" = "x"; then
-	   AC_MSG_ERROR([cannot find tevent source in $teventpaths])
-	fi
-    TEVENT_OBJ="tevent.o tevent_debug.o tevent_util.o"
-    TEVENT_OBJ="$TEVENT_OBJ tevent_fd.o tevent_timed.o tevent_immediate.o tevent_signal.o"
-    TEVENT_OBJ="$TEVENT_OBJ tevent_req.o tevent_wakeup.o tevent_queue.o"
-    TEVENT_OBJ="$TEVENT_OBJ tevent_standard.o tevent_select.o tevent_poll.o"
-    AC_SUBST(TEVENT_OBJ)
-
-    TEVENT_CFLAGS="-I$teventdir"
-    AC_SUBST(TEVENT_CFLAGS)
-
-    TEVENT_LIBS=""
-    AC_SUBST(TEVENT_LIBS)
-
-    AC_CHECK_HEADERS(sys/epoll.h)
-    AC_CHECK_FUNCS(epoll_create)
-    if test x"$ac_cv_header_sys_epoll_h" = x"yes" -a x"$ac_cv_func_epoll_create" = x"yes"; then
-        TEVENT_OBJ="$TEVENT_OBJ tevent_epoll.o"
-        AC_DEFINE(HAVE_EPOLL, 1, [Whether epoll available])
-    fi
-fi
diff --git a/lib/tevent/testsuite.c b/lib/tevent/testsuite.c
deleted file mode 100644
index 6f2851e..0000000
--- a/lib/tevent/testsuite.c
+++ /dev/null
@@ -1,162 +0,0 @@
-/*
-   Unix SMB/CIFS implementation.
-
-   testing of the events subsystem
-
-   Copyright (C) Stefan Metzmacher 2006-2009
-
-     ** NOTE! The following LGPL license applies to the tevent
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-
-#include "includes.h"
-#include "lib/events/events.h"
-#include "system/filesys.h"
-#include "torture/torture.h"
-
-static int fde_count;
-
-static void fde_handler(struct tevent_context *ev_ctx, struct tevent_fd *f,
-			uint16_t flags, void *private_data)
-{
-	int *fd = (int *)private_data;
-	char c;
-#ifdef SA_SIGINFO
-	kill(getpid(), SIGUSR1);
-#endif
-	kill(getpid(), SIGALRM);
-	read(fd[0], &c, 1);
-	write(fd[1], &c, 1);
-	fde_count++;
-}
-
-static void finished_handler(struct tevent_context *ev_ctx, struct tevent_timer *te,
-			     struct timeval tval, void *private_data)
-{
-	int *finished = (int *)private_data;
-	(*finished) = 1;
-}
-
-static void count_handler(struct tevent_context *ev_ctx, struct tevent_signal *te,
-			  int signum, int count, void *info, void *private_data)
-{
-	int *countp = (int *)private_data;
-	(*countp) += count;
-}
-
-static bool test_event_context(struct torture_context *test,
-			       const void *test_data)
-{
-	struct tevent_context *ev_ctx;
-	int fd[2] = { -1, -1 };
-	const char *backend = (const char *)test_data;
-	int alarm_count=0, info_count=0;
-	struct tevent_fd *fde;
-#ifdef SA_RESTART
-	struct tevent_signal *se1 = NULL;
-#endif
-	struct tevent_signal *se2 = NULL;
-#ifdef SA_SIGINFO
-	struct tevent_signal *se3 = NULL;
-#endif
-	int finished=0;
-	struct timeval t;
-	char c = 0;
-
-	ev_ctx = tevent_context_init_byname(test, backend);
-	if (ev_ctx == NULL) {
-		torture_comment(test, "event backend '%s' not supported\n", backend);
-		return true;
-	}
-
-	torture_comment(test, "Testing event backend '%s'\n", backend);
-
-	/* reset globals */
-	fde_count = 0;
-
-	/* create a pipe */
-	pipe(fd);
-
-	fde = tevent_add_fd(ev_ctx, ev_ctx, fd[0], TEVENT_FD_READ,
-			    fde_handler, fd);
-	tevent_fd_set_auto_close(fde);
-
-	tevent_add_timer(ev_ctx, ev_ctx, timeval_current_ofs(2,0),
-			 finished_handler, &finished);
-
-#ifdef SA_RESTART
-	se1 = tevent_add_signal(ev_ctx, ev_ctx, SIGALRM, SA_RESTART, count_handler, &alarm_count);
-#endif
-#ifdef SA_RESETHAND
-	se2 = tevent_add_signal(ev_ctx, ev_ctx, SIGALRM, SA_RESETHAND, count_handler, &alarm_count);
-#endif
-#ifdef SA_SIGINFO
-	se3 = tevent_add_signal(ev_ctx, ev_ctx, SIGUSR1, SA_SIGINFO, count_handler, &info_count);
-#endif
-
-	write(fd[1], &c, 1);
-
-	t = timeval_current();
-	while (!finished) {
-		errno = 0;
-		if (tevent_loop_once(ev_ctx) == -1) {
-			talloc_free(ev_ctx);
-			torture_fail(test, talloc_asprintf(test, "Failed event loop %s\n", strerror(errno)));
-		}
-	}
-
-	talloc_free(fde);
-	close(fd[1]);
-
-	while (alarm_count < fde_count+1) {
-		if (tevent_loop_once(ev_ctx) == -1) {
-			break;
-		}
-	}
-
-	torture_comment(test, "Got %.2f pipe events/sec\n", fde_count/timeval_elapsed(&t));
-
-#ifdef SA_RESTART
-	talloc_free(se1);
-#endif
-
-	torture_assert_int_equal(test, alarm_count, 1+fde_count, "alarm count mismatch");
-
-#ifdef SA_SIGINFO
-	talloc_free(se3);
-	torture_assert_int_equal(test, info_count, fde_count, "info count mismatch");
-#endif
-
-	talloc_free(ev_ctx);
-
-	return true;
-}
-
-struct torture_suite *torture_local_event(TALLOC_CTX *mem_ctx)
-{
-	struct torture_suite *suite = torture_suite_create(mem_ctx, "event");
-	const char **list = tevent_backend_list(suite);
-	int i;
-
-	for (i=0;list && list[i];i++) {
-		torture_suite_add_simple_tcase_const(suite, list[i],
-					       test_event_context,
-					       (const void *)list[i]);
-	}
-
-	return suite;
-}
diff --git a/lib/tevent/tevent.c b/lib/tevent/tevent.c
deleted file mode 100644
index 6c6c6e7..0000000
--- a/lib/tevent/tevent.c
+++ /dev/null
@@ -1,642 +0,0 @@
-/*
-   Unix SMB/CIFS implementation.
-   main select loop and event handling
-   Copyright (C) Andrew Tridgell 2003
-   Copyright (C) Stefan Metzmacher 2009
-
-     ** NOTE! The following LGPL license applies to the tevent
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-
-/*
-  PLEASE READ THIS BEFORE MODIFYING!
-
-  This module is a general abstraction for the main select loop and
-  event handling. Do not ever put any localised hacks in here, instead
-  register one of the possible event types and implement that event
-  somewhere else.
-
-  There are 2 types of event handling that are handled in this module:
-
-  1) a file descriptor becoming readable or writeable. This is mostly
-     used for network sockets, but can be used for any type of file
-     descriptor. You may only register one handler for each file
-     descriptor/io combination or you will get unpredictable results
-     (this means that you can have a handler for read events, and a
-     separate handler for write events, but not two handlers that are
-     both handling read events)
-
-  2) a timed event. You can register an event that happens at a
-     specific time.  You can register as many of these as you
-     like. They are single shot - add a new timed event in the event
-     handler to get another event.
-
-  To setup a set of events you first need to create a event_context
-  structure using the function tevent_context_init(); This returns a
-  'struct tevent_context' that you use in all subsequent calls.
-
-  After that you can add/remove events that you are interested in
-  using tevent_add_*() and talloc_free()
-
-  Finally, you call tevent_loop_wait_once() to block waiting for one of the
-  events to occor or tevent_loop_wait() which will loop
-  forever.
-
-*/
-#include "replace.h"
-#include "system/filesys.h"
-#define TEVENT_DEPRECATED 1
-#include "tevent.h"
-#include "tevent_internal.h"
-#include "tevent_util.h"
-
-struct tevent_ops_list {
-	struct tevent_ops_list *next, *prev;
-	const char *name;
-	const struct tevent_ops *ops;
-};
-
-/* list of registered event backends */
-static struct tevent_ops_list *tevent_backends = NULL;
-static char *tevent_default_backend = NULL;
-
-/*
-  register an events backend
-*/
-bool tevent_register_backend(const char *name, const struct tevent_ops *ops)
-{
-	struct tevent_ops_list *e;
-
-	for (e = tevent_backends; e != NULL; e = e->next) {
-		if (0 == strcmp(e->name, name)) {
-			/* already registered, skip it */
-			return true;
-		}
-	}
-
-	e = talloc(NULL, struct tevent_ops_list);
-	if (e == NULL) return false;
-
-	e->name = name;
-	e->ops = ops;
-	DLIST_ADD(tevent_backends, e);
-
-	return true;
-}
-
-/*
-  set the default event backend
- */
-void tevent_set_default_backend(const char *backend)
-{
-	talloc_free(tevent_default_backend);
-	tevent_default_backend = talloc_strdup(NULL, backend);
-}
-
-/*
-  initialise backends if not already done
-*/
-static void tevent_backend_init(void)
-{
-	tevent_select_init();
-	tevent_poll_init();
-	tevent_standard_init();
-#ifdef HAVE_EPOLL
-	tevent_epoll_init();
-#endif
-}
-
-/*
-  list available backends
-*/
-const char **tevent_backend_list(TALLOC_CTX *mem_ctx)
-{
-	const char **list = NULL;
-	struct tevent_ops_list *e;
-
-	tevent_backend_init();
-
-	for (e=tevent_backends;e;e=e->next) {
-		list = ev_str_list_add(list, e->name);
-	}
-
-	talloc_steal(mem_ctx, list);
-
-	return list;
-}
-
-int tevent_common_context_destructor(struct tevent_context *ev)
-{
-	struct tevent_fd *fd, *fn;
-	struct tevent_timer *te, *tn;
-	struct tevent_immediate *ie, *in;
-	struct tevent_signal *se, *sn;
-
-	if (ev->pipe_fde) {
-		talloc_free(ev->pipe_fde);
-		close(ev->pipe_fds[0]);
-		close(ev->pipe_fds[1]);
-		ev->pipe_fde = NULL;
-	}
-
-	for (fd = ev->fd_events; fd; fd = fn) {
-		fn = fd->next;
-		fd->event_ctx = NULL;
-		DLIST_REMOVE(ev->fd_events, fd);
-	}
-
-	for (te = ev->timer_events; te; te = tn) {
-		tn = te->next;
-		te->event_ctx = NULL;
-		DLIST_REMOVE(ev->timer_events, te);
-	}
-
-	for (ie = ev->immediate_events; ie; ie = in) {
-		in = ie->next;
-		ie->event_ctx = NULL;
-		ie->cancel_fn = NULL;
-		DLIST_REMOVE(ev->immediate_events, ie);
-	}
-
-	for (se = ev->signal_events; se; se = sn) {
-		sn = se->next;
-		se->event_ctx = NULL;
-		DLIST_REMOVE(ev->signal_events, se);
-		/*
-		 * This is important, Otherwise signals
-		 * are handled twice in child. eg, SIGHUP.
-		 * one added in parent, and another one in
-		 * the child. -- BoYang
-		 */
-		tevent_cleanup_pending_signal_handlers(se);
-	}
-
-	/* removing nesting hook or we get an abort when nesting is
-	 * not allowed. -- SSS
-	 * Note that we need to leave the allowed flag at its current
-	 * value, otherwise the use in tevent_re_initialise() will
-	 * leave the event context with allowed forced to false, which
-	 * will break users that expect nesting to be allowed
-	 */
-	ev->nesting.level = 0;
-	ev->nesting.hook_fn = NULL;
-	ev->nesting.hook_private = NULL;
-
-	return 0;
-}
-
-/*
-  create a event_context structure for a specific implemementation.
-  This must be the first events call, and all subsequent calls pass
-  this event_context as the first element. Event handlers also
-  receive this as their first argument.
-
-  This function is for allowing third-party-applications to hook in gluecode
-  to their own event loop code, so that they can make async usage of our client libs
-
-  NOTE: use tevent_context_init() inside of samba!
-*/
-struct tevent_context *tevent_context_init_ops(TALLOC_CTX *mem_ctx,
-					       const struct tevent_ops *ops,
-					       void *additional_data)
-{
-	struct tevent_context *ev;
-	int ret;
-
-	ev = talloc_zero(mem_ctx, struct tevent_context);
-	if (!ev) return NULL;
-
-	talloc_set_destructor(ev, tevent_common_context_destructor);
-
-	ev->ops = ops;
-	ev->additional_data = additional_data;
-
-	ret = ev->ops->context_init(ev);
-	if (ret != 0) {
-		talloc_free(ev);
-		return NULL;
-	}
-
-	return ev;
-}
-
-/*
-  create a event_context structure. This must be the first events
-  call, and all subsequent calls pass this event_context as the first
-  element. Event handlers also receive this as their first argument.
-*/
-struct tevent_context *tevent_context_init_byname(TALLOC_CTX *mem_ctx,
-						  const char *name)
-{
-	struct tevent_ops_list *e;
-
-	tevent_backend_init();
-
-	if (name == NULL) {
-		name = tevent_default_backend;
-	}
-	if (name == NULL) {
-		name = "standard";
-	}
-
-	for (e=tevent_backends;e;e=e->next) {
-		if (strcmp(name, e->name) == 0) {
-			return tevent_context_init_ops(mem_ctx, e->ops, NULL);
-		}
-	}
-	return NULL;
-}
-
-
-/*
-  create a event_context structure. This must be the first events
-  call, and all subsequent calls pass this event_context as the first
-  element. Event handlers also receive this as their first argument.
-*/
-struct tevent_context *tevent_context_init(TALLOC_CTX *mem_ctx)
-{
-	return tevent_context_init_byname(mem_ctx, NULL);
-}
-
-/*
-  add a fd based event
-  return NULL on failure (memory allocation error)
-*/
-struct tevent_fd *_tevent_add_fd(struct tevent_context *ev,
-				 TALLOC_CTX *mem_ctx,
-				 int fd,
-				 uint16_t flags,
-				 tevent_fd_handler_t handler,
-				 void *private_data,
-				 const char *handler_name,
-				 const char *location)
-{
-	return ev->ops->add_fd(ev, mem_ctx, fd, flags, handler, private_data,
-			       handler_name, location);
-}
-
-/*
-  set a close function on the fd event
-*/
-void tevent_fd_set_close_fn(struct tevent_fd *fde,
-			    tevent_fd_close_fn_t close_fn)
-{
-	if (!fde) return;
-	if (!fde->event_ctx) return;
-	fde->event_ctx->ops->set_fd_close_fn(fde, close_fn);
-}
-
-static void tevent_fd_auto_close_fn(struct tevent_context *ev,
-				    struct tevent_fd *fde,
-				    int fd,
-				    void *private_data)
-{
-	close(fd);
-}
-
-void tevent_fd_set_auto_close(struct tevent_fd *fde)
-{
-	tevent_fd_set_close_fn(fde, tevent_fd_auto_close_fn);
-}
-
-/*
-  return the fd event flags
-*/
-uint16_t tevent_fd_get_flags(struct tevent_fd *fde)
-{
-	if (!fde) return 0;
-	if (!fde->event_ctx) return 0;
-	return fde->event_ctx->ops->get_fd_flags(fde);
-}
-
-/*
-  set the fd event flags
-*/
-void tevent_fd_set_flags(struct tevent_fd *fde, uint16_t flags)
-{
-	if (!fde) return;
-	if (!fde->event_ctx) return;
-	fde->event_ctx->ops->set_fd_flags(fde, flags);
-}
-
-bool tevent_signal_support(struct tevent_context *ev)
-{
-	if (ev->ops->add_signal) {
-		return true;
-	}
-	return false;
-}
-
-static void (*tevent_abort_fn)(const char *reason);
-
-void tevent_set_abort_fn(void (*abort_fn)(const char *reason))
-{
-	tevent_abort_fn = abort_fn;
-}
-
-static void tevent_abort(struct tevent_context *ev, const char *reason)
-{
-	tevent_debug(ev, TEVENT_DEBUG_FATAL,
-		     "abort: %s\n", reason);
-
-	if (!tevent_abort_fn) {
-		abort();
-	}
-
-	tevent_abort_fn(reason);
-}
-
-/*
-  add a timer event
-  return NULL on failure
-*/
-struct tevent_timer *_tevent_add_timer(struct tevent_context *ev,
-				       TALLOC_CTX *mem_ctx,
-				       struct timeval next_event,
-				       tevent_timer_handler_t handler,
-				       void *private_data,
-				       const char *handler_name,
-				       const char *location)
-{
-	return ev->ops->add_timer(ev, mem_ctx, next_event, handler, private_data,
-				  handler_name, location);
-}
-
-/*
-  allocate an immediate event
-  return NULL on failure (memory allocation error)
-*/
-struct tevent_immediate *_tevent_create_immediate(TALLOC_CTX *mem_ctx,
-						  const char *location)
-{
-	struct tevent_immediate *im;
-
-	im = talloc(mem_ctx, struct tevent_immediate);
-	if (im == NULL) return NULL;
-
-	im->prev		= NULL;
-	im->next		= NULL;
-	im->event_ctx		= NULL;
-	im->create_location	= location;
-	im->handler		= NULL;
-	im->private_data	= NULL;
-	im->handler_name	= NULL;
-	im->schedule_location	= NULL;
-	im->cancel_fn		= NULL;
-	im->additional_data	= NULL;
-
-	return im;
-}
-
-/*
-  schedule an immediate event
-*/
-void _tevent_schedule_immediate(struct tevent_immediate *im,
-				struct tevent_context *ev,
-				tevent_immediate_handler_t handler,
-				void *private_data,
-				const char *handler_name,
-				const char *location)
-{
-	ev->ops->schedule_immediate(im, ev, handler, private_data,
-				    handler_name, location);
-}
-
-/*
-  add a signal event
-
-  sa_flags are flags to sigaction(2)
-
-  return NULL on failure
-*/
-struct tevent_signal *_tevent_add_signal(struct tevent_context *ev,
-					 TALLOC_CTX *mem_ctx,
-					 int signum,
-					 int sa_flags,
-					 tevent_signal_handler_t handler,
-					 void *private_data,
-					 const char *handler_name,
-					 const char *location)
-{
-	return ev->ops->add_signal(ev, mem_ctx, signum, sa_flags, handler, private_data,
-				   handler_name, location);
-}
-
-void tevent_loop_allow_nesting(struct tevent_context *ev)
-{
-	ev->nesting.allowed = true;
-}
-
-void tevent_loop_set_nesting_hook(struct tevent_context *ev,
-				  tevent_nesting_hook hook,
-				  void *private_data)
-{
-	if (ev->nesting.hook_fn &&
-	    (ev->nesting.hook_fn != hook ||
-	     ev->nesting.hook_private != private_data)) {
-		/* the way the nesting hook code is currently written
-		   we cannot support two different nesting hooks at the
-		   same time. */
-		tevent_abort(ev, "tevent: Violation of nesting hook rules\n");
-	}
-	ev->nesting.hook_fn = hook;
-	ev->nesting.hook_private = private_data;
-}
-
-static void tevent_abort_nesting(struct tevent_context *ev, const char *location)
-{
-	const char *reason;
-
-	reason = talloc_asprintf(NULL, "tevent_loop_once() nesting at %s",
-				 location);
-	if (!reason) {
-		reason = "tevent_loop_once() nesting";
-	}
-
-	tevent_abort(ev, reason);
-}
-
-/*
-  do a single event loop using the events defined in ev
-*/
-int _tevent_loop_once(struct tevent_context *ev, const char *location)
-{
-	int ret;
-	void *nesting_stack_ptr = NULL;
-
-	ev->nesting.level++;
-
-	if (ev->nesting.level > 1) {
-		if (!ev->nesting.allowed) {
-			tevent_abort_nesting(ev, location);
-			errno = ELOOP;
-			return -1;
-		}
-	}
-	if (ev->nesting.level > 0) {
-		if (ev->nesting.hook_fn) {
-			int ret2;
-			ret2 = ev->nesting.hook_fn(ev,
-						   ev->nesting.hook_private,
-						   ev->nesting.level,
-						   true,
-						   (void *)&nesting_stack_ptr,
-						   location);
-			if (ret2 != 0) {
-				ret = ret2;
-				goto done;
-			}
-		}
-	}
-
-	ret = ev->ops->loop_once(ev, location);
-
-	if (ev->nesting.level > 0) {
-		if (ev->nesting.hook_fn) {
-			int ret2;
-			ret2 = ev->nesting.hook_fn(ev,
-						   ev->nesting.hook_private,
-						   ev->nesting.level,
-						   false,
-						   (void *)&nesting_stack_ptr,
-						   location);
-			if (ret2 != 0) {
-				ret = ret2;
-				goto done;
-			}
-		}
-	}
-
-done:
-	ev->nesting.level--;
-	return ret;
-}
-
-/*
-  this is a performance optimization for the samba4 nested event loop problems
-*/
-int _tevent_loop_until(struct tevent_context *ev,
-		       bool (*finished)(void *private_data),
-		       void *private_data,
-		       const char *location)
-{
-	int ret = 0;
-	void *nesting_stack_ptr = NULL;
-
-	ev->nesting.level++;
-
-	if (ev->nesting.level > 1) {
-		if (!ev->nesting.allowed) {
-			tevent_abort_nesting(ev, location);
-			errno = ELOOP;
-			return -1;
-		}
-	}
-	if (ev->nesting.level > 0) {
-		if (ev->nesting.hook_fn) {
-			int ret2;
-			ret2 = ev->nesting.hook_fn(ev,
-						   ev->nesting.hook_private,
-						   ev->nesting.level,
-						   true,
-						   (void *)&nesting_stack_ptr,
-						   location);
-			if (ret2 != 0) {
-				ret = ret2;
-				goto done;
-			}
-		}
-	}
-
-	while (!finished(private_data)) {
-		ret = ev->ops->loop_once(ev, location);
-		if (ret != 0) {
-			break;
-		}
-	}
-
-	if (ev->nesting.level > 0) {
-		if (ev->nesting.hook_fn) {
-			int ret2;
-			ret2 = ev->nesting.hook_fn(ev,
-						   ev->nesting.hook_private,
-						   ev->nesting.level,
-						   false,
-						   (void *)&nesting_stack_ptr,
-						   location);
-			if (ret2 != 0) {
-				ret = ret2;
-				goto done;
-			}
-		}
-	}
-
-done:
-	ev->nesting.level--;
-	return ret;
-}
-
-/*
-  return on failure or (with 0) if all fd events are removed
-*/
-int tevent_common_loop_wait(struct tevent_context *ev,
-			    const char *location)
-{
-	/*
-	 * loop as long as we have events pending
-	 */
-	while (ev->fd_events ||
-	       ev->timer_events ||
-	       ev->immediate_events ||
-	       ev->signal_events) {
-		int ret;
-		ret = _tevent_loop_once(ev, location);
-		if (ret != 0) {
-			tevent_debug(ev, TEVENT_DEBUG_FATAL,
-				     "_tevent_loop_once() failed: %d - %s\n",
-				     ret, strerror(errno));
-			return ret;
-		}
-	}
-
-	tevent_debug(ev, TEVENT_DEBUG_WARNING,
-		     "tevent_common_loop_wait() out of events\n");
-	return 0;
-}
-
-/*
-  return on failure or (with 0) if all fd events are removed
-*/
-int _tevent_loop_wait(struct tevent_context *ev, const char *location)
-{
-	return ev->ops->loop_wait(ev, location);
-}
-
-
-/*
-  re-initialise a tevent context. This leaves you with the same
-  event context, but all events are wiped and the structure is
-  re-initialised. This is most useful after a fork()
-
-  zero is returned on success, non-zero on failure
-*/
-int tevent_re_initialise(struct tevent_context *ev)
-{
-	tevent_common_context_destructor(ev);
-
-	return ev->ops->context_init(ev);
-}
diff --git a/lib/tevent/tevent.h b/lib/tevent/tevent.h
deleted file mode 100644
index 60bc92a..0000000
--- a/lib/tevent/tevent.h
+++ /dev/null
@@ -1,1765 +0,0 @@
-/*
-   Unix SMB/CIFS implementation.
-
-   generalised event loop handling
-
-   Copyright (C) Andrew Tridgell 2005
-   Copyright (C) Stefan Metzmacher 2005-2009
-   Copyright (C) Volker Lendecke 2008
-
-     ** NOTE! The following LGPL license applies to the tevent
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-
-#ifndef __TEVENT_H__
-#define __TEVENT_H__
-
-#include <stdint.h>
-#include <talloc.h>
-#include <sys/time.h>
-#include <stdbool.h>
-
-struct tevent_context;
-struct tevent_ops;
-struct tevent_fd;
-struct tevent_timer;
-struct tevent_immediate;
-struct tevent_signal;
-
-/**
- * @defgroup tevent The tevent API
- *
- * The tevent low-level API
- *
- * This API provides the public interface to manage events in the tevent
- * mainloop. Functions are provided for managing low-level events such
- * as timer events, fd events and signal handling.
- *
- * @{
- */
-
-/* event handler types */
-/**
- * Called when a file descriptor monitored by tevent has
- * data to be read or written on it.
- */
-typedef void (*tevent_fd_handler_t)(struct tevent_context *ev,
-				    struct tevent_fd *fde,
-				    uint16_t flags,
-				    void *private_data);
-
-/**
- * Called when tevent is ceasing the monitoring of a file descriptor.
- */
-typedef void (*tevent_fd_close_fn_t)(struct tevent_context *ev,
-				     struct tevent_fd *fde,
-				     int fd,
-				     void *private_data);
-
-/**
- * Called when a tevent timer has fired.
- */
-typedef void (*tevent_timer_handler_t)(struct tevent_context *ev,
-				       struct tevent_timer *te,
-				       struct timeval current_time,
-				       void *private_data);
-
-/**
- * Called when a tevent immediate event is invoked.
- */
-typedef void (*tevent_immediate_handler_t)(struct tevent_context *ctx,
-					   struct tevent_immediate *im,
-					   void *private_data);
-
-/**
- * Called after tevent detects the specified signal.
- */
-typedef void (*tevent_signal_handler_t)(struct tevent_context *ev,
-					struct tevent_signal *se,
-					int signum,
-					int count,
-					void *siginfo,
-					void *private_data);
-
-/**
- * @brief Create a event_context structure.
- *
- * This must be the first events call, and all subsequent calls pass this
- * event_context as the first element. Event handlers also receive this as
- * their first argument.
- *
- * @param[in]  mem_ctx  The memory context to use.
- *
- * @return              An allocated tevent context, NULL on error.
- *
- * @see tevent_context_init()
- */
-struct tevent_context *tevent_context_init(TALLOC_CTX *mem_ctx);
-
-/**
- * @brief Create a event_context structure and select a specific backend.
- *
- * This must be the first events call, and all subsequent calls pass this
- * event_context as the first element. Event handlers also receive this as
- * their first argument.
- *
- * @param[in]  mem_ctx  The memory context to use.
- *
- * @param[in]  name     The name of the backend to use.
- *
- * @return              An allocated tevent context, NULL on error.
- */
-struct tevent_context *tevent_context_init_byname(TALLOC_CTX *mem_ctx, const char *name);
-
-/**
- * @brief Create a custom event context
- *
- * @param[in]  mem_ctx  The memory context to use.
- * @param[in]  ops      The function pointer table of the backend.
- * @param[in]  additional_data  The additional/private data to this instance
- *
- * @return              An allocated tevent context, NULL on error.
- *
- */
-struct tevent_context *tevent_context_init_ops(TALLOC_CTX *mem_ctx,
-					       const struct tevent_ops *ops,
-					       void *additional_data);
-
-/**
- * @brief List available backends.
- *
- * @param[in]  mem_ctx  The memory context to use.
- *
- * @return              A string vector with a terminating NULL element, NULL
- *                      on error.
- */
-const char **tevent_backend_list(TALLOC_CTX *mem_ctx);
-
-/**
- * @brief Set the default tevent backend.
- *
- * @param[in]  backend  The name of the backend to set.
- */
-void tevent_set_default_backend(const char *backend);
-
-#ifdef DOXYGEN
-/**
- * @brief Add a file descriptor based event.
- *
- * @param[in]  ev       The event context to work on.
- *
- * @param[in]  mem_ctx  The talloc memory context to use.
- *
- * @param[in]  fd       The file descriptor to base the event on.
- *
- * @param[in]  flags    #TEVENT_FD_READ or #TEVENT_FD_WRITE
- *
- * @param[in]  handler  The callback handler for the event.
- *
- * @param[in]  private_data  The private data passed to the callback handler.
- *
- * @return              The file descriptor based event, NULL on error.
- *
- * @note To cancel the monitoring of a file descriptor, call talloc_free()
- * on the object returned by this function.
- */
-struct tevent_fd *tevent_add_fd(struct tevent_context *ev,
-				TALLOC_CTX *mem_ctx,
-				int fd,
-				uint16_t flags,
-				tevent_fd_handler_t handler,
-				void *private_data);
-#else
-struct tevent_fd *_tevent_add_fd(struct tevent_context *ev,
-				 TALLOC_CTX *mem_ctx,
-				 int fd,
-				 uint16_t flags,
-				 tevent_fd_handler_t handler,
-				 void *private_data,
-				 const char *handler_name,
-				 const char *location);
-#define tevent_add_fd(ev, mem_ctx, fd, flags, handler, private_data) \
-	_tevent_add_fd(ev, mem_ctx, fd, flags, handler, private_data, \
-		       #handler, __location__)
-#endif
-
-#ifdef DOXYGEN
-/**
- * @brief Add a timed event
- *
- * @param[in]  ev       The event context to work on.
- *
- * @param[in]  mem_ctx  The talloc memory context to use.
- *
- * @param[in]  next_event  Timeval specifying the absolute time to fire this
- * event. This is not an offset.
- *
- * @param[in]  handler  The callback handler for the event.
- *
- * @param[in]  private_data  The private data passed to the callback handler.
- *
- * @return The newly-created timer event, or NULL on error.
- *
- * @note To cancel a timer event before it fires, call talloc_free() on the
- * event returned from this function. This event is automatically
- * talloc_free()-ed after its event handler files, if it hasn't been freed yet.
- *
- * @note Unlike some mainloops, tevent timers are one-time events. To set up
- * a recurring event, it is necessary to call tevent_add_timer() again during
- * the handler processing.
- *
- * @note Due to the internal mainloop processing, a timer set to run
- * immediately will do so after any other pending timers fire, but before
- * any further file descriptor or signal handling events fire. Callers should
- * not rely on this behavior!
- */
-struct tevent_timer *tevent_add_timer(struct tevent_context *ev,
-                                      TALLOC_CTX *mem_ctx,
-                                      struct timeval next_event,
-                                      tevent_timer_handler_t handler,
-                                      void *private_data);
-#else
-struct tevent_timer *_tevent_add_timer(struct tevent_context *ev,
-				       TALLOC_CTX *mem_ctx,
-				       struct timeval next_event,
-				       tevent_timer_handler_t handler,
-				       void *private_data,
-				       const char *handler_name,
-				       const char *location);
-#define tevent_add_timer(ev, mem_ctx, next_event, handler, private_data) \
-	_tevent_add_timer(ev, mem_ctx, next_event, handler, private_data, \
-			  #handler, __location__)
-#endif
-
-#ifdef DOXYGEN
-/**
- * Initialize an immediate event object
- *
- * This object can be used to trigger an event to occur immediately after
- * returning from the current event (before any other event occurs)
- *
- * @param[in] mem_ctx  The talloc memory context to use as the parent
- *
- * @return An empty tevent_immediate object. Use tevent_schedule_immediate
- * to populate and use it.
- *
- * @note Available as of tevent 0.9.8
- */
-struct tevent_immediate *tevent_create_immediate(TALLOC_CTX *mem_ctx);
-#else
-struct tevent_immediate *_tevent_create_immediate(TALLOC_CTX *mem_ctx,
-						  const char *location);
-#define tevent_create_immediate(mem_ctx) \
-	_tevent_create_immediate(mem_ctx, __location__)
-#endif
-
-#ifdef DOXYGEN
-
-/**
- * Schedule an event for immediate execution. This event will occur
- * immediately after returning from the current event (before any other
- * event occurs)
- *
- * @param[in] im       The tevent_immediate object to populate and use
- * @param[in] ctx      The tevent_context to run this event
- * @param[in] handler  The event handler to run when this event fires
- * @param[in] private_data  Data to pass to the event handler
- */
-void tevent_schedule_immediate(struct tevent_immediate *im,
-                struct tevent_context *ctx,
-                tevent_immediate_handler_t handler,
-                void *private_data);
-#else
-void _tevent_schedule_immediate(struct tevent_immediate *im,
-				struct tevent_context *ctx,
-				tevent_immediate_handler_t handler,
-				void *private_data,
-				const char *handler_name,
-				const char *location);
-#define tevent_schedule_immediate(im, ctx, handler, private_data) \
-	_tevent_schedule_immediate(im, ctx, handler, private_data, \
-				   #handler, __location__);
-#endif
-
-#ifdef DOXYGEN
-/**
- * @brief Add a tevent signal handler
- *
- * tevent_add_signal() creates a new event for handling a signal the next
- * time through the mainloop. It implements a very simple traditional signal
- * handler whose only purpose is to add the handler event into the mainloop.
- *
- * @param[in]  ev       The event context to work on.
- *
- * @param[in]  mem_ctx  The talloc memory context to use.
- *
- * @param[in]  signum   The signal to trap
- *
- * @param[in]  handler  The callback handler for the signal.
- *
- * @param[in]  sa_flags sigaction flags for this signal handler.
- *
- * @param[in]  private_data  The private data passed to the callback handler.
- *
- * @return The newly-created signal handler event, or NULL on error.
- *
- * @note To cancel a signal handler, call talloc_free() on the event returned
- * from this function.
- */
-struct tevent_signal *tevent_add_signal(struct tevent_context *ev,
-                     TALLOC_CTX *mem_ctx,
-                     int signum,
-                     int sa_flags,
-                     tevent_signal_handler_t handler,
-                     void *private_data);
-#else
-struct tevent_signal *_tevent_add_signal(struct tevent_context *ev,
-					 TALLOC_CTX *mem_ctx,
-					 int signum,
-					 int sa_flags,
-					 tevent_signal_handler_t handler,
-					 void *private_data,
-					 const char *handler_name,
-					 const char *location);
-#define tevent_add_signal(ev, mem_ctx, signum, sa_flags, handler, private_data) \
-	_tevent_add_signal(ev, mem_ctx, signum, sa_flags, handler, private_data, \
-			   #handler, __location__)
-#endif
-
-#ifdef DOXYGEN
-/**
- * @brief Pass a single time through the mainloop
- *
- * This will process any appropriate signal, immediate, fd and timer events
- *
- * @param[in]  ev The event context to process
- *
- * @return Zero on success, nonzero if an internal error occurred
- */
-int tevent_loop_once(struct tevent_context *ev);
-#else
-int _tevent_loop_once(struct tevent_context *ev, const char *location);
-#define tevent_loop_once(ev) \
-	_tevent_loop_once(ev, __location__)
-#endif
-
-#ifdef DOXYGEN
-/**
- * @brief Run the mainloop
- *
- * The mainloop will run until there are no events remaining to be processed
- *
- * @param[in]  ev The event context to process
- *
- * @return Zero if all events have been processed. Nonzero if an internal
- * error occurred.
- */
-int tevent_loop_wait(struct tevent_context *ev);
-#else
-int _tevent_loop_wait(struct tevent_context *ev, const char *location);
-#define tevent_loop_wait(ev) \
-	_tevent_loop_wait(ev, __location__)
-#endif
-
-
-/**
- * Assign a function to run when a tevent_fd is freed
- *
- * This function is a destructor for the tevent_fd. It does not automatically
- * close the file descriptor. If this is the desired behavior, then it must be
- * performed by the close_fn.
- *
- * @param[in] fde       File descriptor event on which to set the destructor
- * @param[in] close_fn  Destructor to execute when fde is freed
- */
-void tevent_fd_set_close_fn(struct tevent_fd *fde,
-			    tevent_fd_close_fn_t close_fn);
-
-/**
- * Automatically close the file descriptor when the tevent_fd is freed
- *
- * This function calls close(fd) internally.
- *
- * @param[in] fde  File descriptor event to auto-close
- */
-void tevent_fd_set_auto_close(struct tevent_fd *fde);
-
-/**
- * Return the flags set on this file descriptor event
- *
- * @param[in] fde  File descriptor event to query
- *
- * @return The flags set on the event. See #TEVENT_FD_READ and
- * #TEVENT_FD_WRITE
- */
-uint16_t tevent_fd_get_flags(struct tevent_fd *fde);
-
-/**
- * Set flags on a file descriptor event
- *
- * @param[in] fde    File descriptor event to set
- * @param[in] flags  Flags to set on the event. See #TEVENT_FD_READ and
- * #TEVENT_FD_WRITE
- */
-void tevent_fd_set_flags(struct tevent_fd *fde, uint16_t flags);
-
-/**
- * Query whether tevent supports signal handling
- *
- * @param[in] ev  An initialized tevent context
- *
- * @return True if this platform and tevent context support signal handling
- */
-bool tevent_signal_support(struct tevent_context *ev);
-
-void tevent_set_abort_fn(void (*abort_fn)(const char *reason));
-
-/* bits for file descriptor event flags */
-
-/**
- * Monitor a file descriptor for write availability
- */
-#define TEVENT_FD_READ 1
-/**
- * Monitor a file descriptor for data to be read
- */
-#define TEVENT_FD_WRITE 2
-
-/**
- * Convenience function for declaring a tevent_fd writable
- */
-#define TEVENT_FD_WRITEABLE(fde) \
-	tevent_fd_set_flags(fde, tevent_fd_get_flags(fde) | TEVENT_FD_WRITE)
-
-/**
- * Convenience function for declaring a tevent_fd readable
- */
-#define TEVENT_FD_READABLE(fde) \
-	tevent_fd_set_flags(fde, tevent_fd_get_flags(fde) | TEVENT_FD_READ)
-
-/**
- * Convenience function for declaring a tevent_fd non-writable
- */
-#define TEVENT_FD_NOT_WRITEABLE(fde) \
-	tevent_fd_set_flags(fde, tevent_fd_get_flags(fde) & ~TEVENT_FD_WRITE)
-
-/**
- * Convenience function for declaring a tevent_fd non-readable
- */
-#define TEVENT_FD_NOT_READABLE(fde) \
-	tevent_fd_set_flags(fde, tevent_fd_get_flags(fde) & ~TEVENT_FD_READ)
-
-/**
- * Debug level of tevent
- */
-enum tevent_debug_level {
-	TEVENT_DEBUG_FATAL,
-	TEVENT_DEBUG_ERROR,
-	TEVENT_DEBUG_WARNING,
-	TEVENT_DEBUG_TRACE
-};
-
-/**
- * @brief The tevent debug callbac.
- *
- * @param[in]  context  The memory context to use.
- *
- * @param[in]  level    The debug level.
- *
- * @param[in]  fmt      The format string.
- *
- * @param[in]  ap       The arguments for the format string.
- */
-typedef void (*tevent_debug_fn)(void *context,
-				enum tevent_debug_level level,
-				const char *fmt,
-				va_list ap) PRINTF_ATTRIBUTE(3,0);
-
-/**
- * Set destination for tevent debug messages
- *
- * @param[in] ev        Event context to debug
- * @param[in] debug     Function to handle output printing
- * @param[in] context   The context to pass to the debug function.
- *
- * @return Always returns 0 as of version 0.9.8
- *
- * @note Default is to emit no debug messages
- */
-int tevent_set_debug(struct tevent_context *ev,
-		     tevent_debug_fn debug,
-		     void *context);
-
-/**
- * Designate stderr for debug message output
- *
- * @param[in] ev     Event context to debug
- *
- * @note This function will only output TEVENT_DEBUG_FATAL, TEVENT_DEBUG_ERROR
- * and TEVENT_DEBUG_WARNING messages. For TEVENT_DEBUG_TRACE, please define a
- * function for tevent_set_debug()
- */
-int tevent_set_debug_stderr(struct tevent_context *ev);
-
-enum tevent_trace_point {
-	/**
-	 * Corresponds to a trace point just before waiting
-	 */
-	TEVENT_TRACE_BEFORE_WAIT,
-	/**
-	 * Corresponds to a trace point just after waiting
-	 */
-	TEVENT_TRACE_AFTER_WAIT,
-};
-
-typedef void (*tevent_trace_callback_t)(enum tevent_trace_point,
-					void *private_data);
-
-/**
- * Register a callback to be called at certain trace points
- *
- * @param[in] ev             Event context
- * @param[in] cb             Trace callback
- * @param[in] private_data   Data to be passed to callback
- *
- * @note The callback will be called at trace points defined by
- * tevent_trace_point.  Call with NULL to reset.
- */
-void tevent_set_trace_callback(struct tevent_context *ev,
-			       tevent_trace_callback_t cb,
-			       void *private_data);
-
-/**
- * Retrieve the current trace callback
- *
- * @param[in] ev             Event context
- * @param[out] cb            Registered trace callback
- * @param[out] private_data  Registered data to be passed to callback
- *
- * @note This can be used to allow one component that wants to
- * register a callback to respect the callback that another component
- * has already registered.
- */
-void tevent_get_trace_callback(struct tevent_context *ev,
-			       tevent_trace_callback_t *cb,
-			       void *private_data);
-
-/**
- * @}
- */
-
-/**
- * @defgroup tevent_request The tevent request functions.
- * @ingroup tevent
- *
- * A tevent_req represents an asynchronous computation.
- *
- * The tevent_req group of API calls is the recommended way of
- * programming async computations within tevent. In particular the
- * file descriptor (tevent_add_fd) and timer (tevent_add_timed) events
- * are considered too low-level to be used in larger computations. To
- * read and write from and to sockets, Samba provides two calls on top
- * of tevent_add_fd: read_packet_send/recv and writev_send/recv. These
- * requests are much easier to compose than the low-level event
- * handlers called from tevent_add_fd.
- *
- * A lot of the simplicity tevent_req has brought to the notoriously
- * hairy async programming came via a set of conventions that every
- * async computation programmed should follow. One central piece of
- * these conventions is the naming of routines and variables.
- *
- * Every async computation needs a name (sensibly called "computation"
- * down from here). From this name quite a few naming conventions are
- * derived.
- *
- * Every computation that requires local state needs a
- * @code
- * struct computation_state {
- *     int local_var;
- * };
- * @endcode
- * Even if no local variables are required, such a state struct should
- * be created containing a dummy variable. Quite a few helper
- * functions and macros (for example tevent_req_create()) assume such
- * a state struct.
- *
- * An async computation is started by a computation_send
- * function. When it is finished, its result can be received by a
- * computation_recv function. For an example how to set up an async
- * computation, see the code example in the documentation for
- * tevent_req_create() and tevent_req_post(). The prototypes for _send
- * and _recv functions should follow some conventions:
- *
- * @code
- * struct tevent_req *computation_send(TALLOC_CTX *mem_ctx,
- *                                     struct tevent_req *ev,
- *                                     ... further args);
- * int computation_recv(struct tevent_req *req, ... further output args);
- * @endcode
- *
- * The "int" result of computation_recv() depends on the result the
- * sync version of the function would have, "int" is just an example
- * here.
- *
- * Another important piece of the conventions is that the program flow
- * is interrupted as little as possible. Because a blocking
- * sub-computation requires that the flow needs to continue in a
- * separate function that is the logical sequel of some computation,
- * it should lexically follow sending off the blocking
- * sub-computation. Setting the callback function via
- * tevent_req_set_callback() requires referencing a function lexically
- * below the call to tevent_req_set_callback(), forward declarations
- * are required. A lot of the async computations thus begin with a
- * sequence of declarations such as
- *
- * @code
- * static void computation_step1_done(struct tevent_req *subreq);
- * static void computation_step2_done(struct tevent_req *subreq);
- * static void computation_step3_done(struct tevent_req *subreq);
- * @endcode
- *
- * It really helps readability a lot to do these forward declarations,
- * because the lexically sequential program flow makes the async
- * computations almost as clear to read as a normal, sync program
- * flow.
- *
- * It is up to the user of the async computation to talloc_free it
- * after it has finished. If an async computation should be aborted,
- * the tevent_req structure can be talloc_free'ed. After it has
- * finished, it should talloc_free'ed by the API user.
- *
- * @{
- */
-
-/**
- * An async request moves from TEVENT_REQ_INIT to
- * TEVENT_REQ_IN_PROGRESS. All other states are valid after a request
- * has finished.
- */
-enum tevent_req_state {
-	/**
-	 * We are creating the request
-	 */
-	TEVENT_REQ_INIT,
-	/**
-	 * We are waiting the request to complete
-	 */
-	TEVENT_REQ_IN_PROGRESS,
-	/**
-	 * The request is finished successfully
-	 */
-	TEVENT_REQ_DONE,
-	/**
-	 * A user error has occurred. The user error has been
-	 * indicated by tevent_req_error(), it can be retrieved via
-	 * tevent_req_is_error().
-	 */
-	TEVENT_REQ_USER_ERROR,
-	/**
-	 * Request timed out after the timeout set by tevent_req_set_endtime.
-	 */
-	TEVENT_REQ_TIMED_OUT,
-	/**
-	 * An internal allocation has failed, or tevent_req_nomem has
-	 * been given a NULL pointer as the first argument.
-	 */
-	TEVENT_REQ_NO_MEMORY,
-	/**
-	 * The request has been received by the caller. No further
-	 * action is valid.
-	 */
-	TEVENT_REQ_RECEIVED
-};
-
-/**
- * @brief An async request
- */
-struct tevent_req;
-
-/**
- * @brief A tevent request callback function.
- *
- * @param[in]  req      The tevent async request which executed this callback.
- */
-typedef void (*tevent_req_fn)(struct tevent_req *req);
-
-/**
- * @brief Set an async request callback.
- *
- * See the documentation of tevent_req_post() for an example how this
- * is supposed to be used.
- *
- * @param[in]  req      The async request to set the callback.
- *
- * @param[in]  fn       The callback function to set.
- *
- * @param[in]  pvt      A pointer to private data to pass to the async request
- *                      callback.
- */
-void tevent_req_set_callback(struct tevent_req *req, tevent_req_fn fn, void *pvt);
-
-#ifdef DOXYGEN
-/**
- * @brief Get the private data cast to the given type for a callback from
- *        a tevent request structure.
- *
- * @code
- * static void computation_done(struct tevent_req *subreq) {
- *     struct tevent_req *req = tevent_req_callback_data(subreq, struct tevent_req);
- *     struct computation_state *state = tevent_req_data(req, struct computation_state);
- *     .... more things, eventually maybe call tevent_req_done(req);
- * }
- * @endcode
- *
- * @param[in]  req      The structure to get the callback data from.
- *
- * @param[in]  type     The type of the private callback data to get.
- *
- * @return              The type casted private data set NULL if not set.
- */
-void *tevent_req_callback_data(struct tevent_req *req, #type);
-#else
-void *_tevent_req_callback_data(struct tevent_req *req);
-#define tevent_req_callback_data(_req, _type) \
-	talloc_get_type_abort(_tevent_req_callback_data(_req), _type)
-#endif
-
-#ifdef DOXYGEN
-/**
- * @brief Get the private data for a callback from a tevent request structure.
- *
- * @param[in]  req      The structure to get the callback data from.
- *
- * @param[in]  req      The structure to get the data from.
- *
- * @return              The private data or NULL if not set.
- */
-void *tevent_req_callback_data_void(struct tevent_req *req);
-#else
-#define tevent_req_callback_data_void(_req) \
-	_tevent_req_callback_data(_req)
-#endif
-
-#ifdef DOXYGEN
-/**
- * @brief Get the private data from a tevent request structure.
- *
- * When the tevent_req has been created by tevent_req_create, the
- * result of tevent_req_data() is the state variable created by
- * tevent_req_create() as a child of the req.
- *
- * @param[in]  req      The structure to get the private data from.
- *
- * @param[in]  type	The type of the private data
- *
- * @return              The private data or NULL if not set.
- */
-void *tevent_req_data(struct tevent_req *req, #type);
-#else
-void *_tevent_req_data(struct tevent_req *req);
-#define tevent_req_data(_req, _type) \
-	talloc_get_type_abort(_tevent_req_data(_req), _type)
-#endif
-
-/**
- * @brief The print function which can be set for a tevent async request.
- *
- * @param[in]  req      The tevent async request.
- *
- * @param[in]  ctx      A talloc memory context which can be uses to allocate
- *                      memory.
- *
- * @return              An allocated string buffer to print.
- *
- * Example:
- * @code
- *   static char *my_print(struct tevent_req *req, TALLOC_CTX *mem_ctx)
- *   {
- *     struct my_data *data = tevent_req_data(req, struct my_data);
- *     char *result;
- *
- *     result = tevent_req_default_print(mem_ctx, req);
- *     if (result == NULL) {
- *       return NULL;
- *     }
- *
- *     return talloc_asprintf_append_buffer(result, "foo=%d, bar=%d",
- *       data->foo, data->bar);
- *   }
- * @endcode
- */
-typedef char *(*tevent_req_print_fn)(struct tevent_req *req, TALLOC_CTX *ctx);
-
-/**
- * @brief This function sets a print function for the given request.
- *
- * This function can be used to setup a print function for the given request.
- * This will be triggered if the tevent_req_print() function was
- * called on the given request.
- *
- * @param[in]  req      The request to use.
- *
- * @param[in]  fn       A pointer to the print function
- *
- * @note This function should only be used for debugging.
- */
-void tevent_req_set_print_fn(struct tevent_req *req, tevent_req_print_fn fn);
-
-/**
- * @brief The default print function for creating debug messages.
- *
- * The function should not be used by users of the async API,
- * but custom print function can use it and append custom text
- * to the string.
- *
- * @param[in]  req      The request to be printed.
- *
- * @param[in]  mem_ctx  The memory context for the result.
- *
- * @return              Text representation of request.
- *
- */
-char *tevent_req_default_print(struct tevent_req *req, TALLOC_CTX *mem_ctx);
-
-/**
- * @brief Print an tevent_req structure in debug messages.
- *
- * This function should be used by callers of the async API.
- *
- * @param[in]  mem_ctx  The memory context for the result.
- *
- * @param[in] req       The request to be printed.
- *
- * @return              Text representation of request.
- */
-char *tevent_req_print(TALLOC_CTX *mem_ctx, struct tevent_req *req);
-
-/**
- * @brief A typedef for a cancel function for a tevent request.
- *
- * @param[in]  req      The tevent request calling this function.
- *
- * @return              True if the request could be canceled, false if not.
- */
-typedef bool (*tevent_req_cancel_fn)(struct tevent_req *req);
-
-/**
- * @brief This function sets a cancel function for the given tevent request.
- *
- * This function can be used to setup a cancel function for the given request.
- * This will be triggered if the tevent_req_cancel() function was
- * called on the given request.
- *
- * @param[in]  req      The request to use.
- *
- * @param[in]  fn       A pointer to the cancel function.
- */
-void tevent_req_set_cancel_fn(struct tevent_req *req, tevent_req_cancel_fn fn);
-
-#ifdef DOXYGEN
-/**
- * @brief Try to cancel the given tevent request.
- *
- * This function can be used to cancel the given request.
- *
- * It is only possible to cancel a request when the implementation
- * has registered a cancel function via the tevent_req_set_cancel_fn().
- *
- * @param[in]  req      The request to use.
- *
- * @return              This function returns true is the request is cancelable,
- *                      othererwise false is returned.
- *
- * @note Even if the function returns true, the caller need to wait
- *       for the function to complete normally.
- *       Only the _recv() function of the given request indicates
- *       if the request was really canceled.
- */
-bool tevent_req_cancel(struct tevent_req *req);
-#else
-bool _tevent_req_cancel(struct tevent_req *req, const char *location);
-#define tevent_req_cancel(req) \
-	_tevent_req_cancel(req, __location__)
-#endif
-
-#ifdef DOXYGEN
-/**
- * @brief Create an async tevent request.
- *
- * The new async request will be initialized in state TEVENT_REQ_IN_PROGRESS.
- *
- * @code
- * struct tevent_req *req;
- * struct computation_state *state;
- * req = tevent_req_create(mem_ctx, &state, struct computation_state);
- * @endcode
- *
- * Tevent_req_create() creates the state variable as a talloc child of
- * its result. The state variable should be used as the talloc parent
- * for all temporary variables that are allocated during the async
- * computation. This way, when the user of the async computation frees
- * the request, the state as a talloc child will be free'd along with
- * all the temporary variables hanging off the state.
- *
- * @param[in] mem_ctx   The memory context for the result.
- * @param[in] pstate    Pointer to the private request state.
- * @param[in] type      The name of the request.
- *
- * @return              A new async request. NULL on error.
- */
-struct tevent_req *tevent_req_create(TALLOC_CTX *mem_ctx,
-				     void **pstate, #type);
-#else
-struct tevent_req *_tevent_req_create(TALLOC_CTX *mem_ctx,
-				      void *pstate,
-				      size_t state_size,
-				      const char *type,
-				      const char *location);
-
-#define tevent_req_create(_mem_ctx, _pstate, _type) \
-	_tevent_req_create((_mem_ctx), (_pstate), sizeof(_type), \
-			   #_type, __location__)
-#endif
-
-/**
- * @brief Set a timeout for an async request.
- *
- * @param[in]  req      The request to set the timeout for.
- *
- * @param[in]  ev       The event context to use for the timer.
- *
- * @param[in]  endtime  The endtime of the request.
- *
- * @return              True if succeeded, false if not.
- */
-bool tevent_req_set_endtime(struct tevent_req *req,
-			    struct tevent_context *ev,
-			    struct timeval endtime);
-
-#ifdef DOXYGEN
-/**
- * @brief Call the notify callback of the given tevent request manually.
- *
- * @param[in]  req      The tevent request to call the notify function from.
- *
- * @see tevent_req_set_callback()
- */
-void tevent_req_notify_callback(struct tevent_req *req);
-#else
-void _tevent_req_notify_callback(struct tevent_req *req, const char *location);
-#define tevent_req_notify_callback(req)		\
-	_tevent_req_notify_callback(req, __location__)
-#endif
-
-#ifdef DOXYGEN
-/**
- * @brief An async request has successfully finished.
- *
- * This function is to be used by implementors of async requests. When a
- * request is successfully finished, this function calls the user's completion
- * function.
- *
- * @param[in]  req       The finished request.
- */
-void tevent_req_done(struct tevent_req *req);
-#else
-void _tevent_req_done(struct tevent_req *req,
-		      const char *location);
-#define tevent_req_done(req) \
-	_tevent_req_done(req, __location__)
-#endif
-
-#ifdef DOXYGEN
-/**
- * @brief An async request has seen an error.
- *
- * This function is to be used by implementors of async requests. When a
- * request can not successfully completed, the implementation should call this
- * function with the appropriate status code.
- *
- * If error is 0 the function returns false and does nothing more.
- *
- * @param[in]  req      The request with an error.
- *
- * @param[in]  error    The error code.
- *
- * @return              On success true is returned, false if error is 0.
- *
- * @code
- * int error = first_function();
- * if (tevent_req_error(req, error)) {
- *      return;
- * }
- *
- * error = second_function();
- * if (tevent_req_error(req, error)) {
- *      return;
- * }
- *
- * tevent_req_done(req);
- * return;
- * @endcode
- */
-bool tevent_req_error(struct tevent_req *req,
-		      uint64_t error);
-#else
-bool _tevent_req_error(struct tevent_req *req,
-		       uint64_t error,
-		       const char *location);
-#define tevent_req_error(req, error) \
-	_tevent_req_error(req, error, __location__)
-#endif
-
-#ifdef DOXYGEN
-/**
- * @brief Helper function for nomem check.
- *
- * Convenience helper to easily check alloc failure within a callback
- * implementing the next step of an async request.
- *
- * @param[in]  p        The pointer to be checked.
- *
- * @param[in]  req      The request being processed.
- *
- * @code
- * p = talloc(mem_ctx, bla);
- * if (tevent_req_nomem(p, req)) {
- *      return;
- * }
- * @endcode
- */
-bool tevent_req_nomem(const void *p,
-		      struct tevent_req *req);
-#else
-bool _tevent_req_nomem(const void *p,
-		       struct tevent_req *req,
-		       const char *location);
-#define tevent_req_nomem(p, req) \
-	_tevent_req_nomem(p, req, __location__)
-#endif
-
-#ifdef DOXYGEN
-/**
- * @brief Indicate out of memory to a request
- *
- * @param[in]  req      The request being processed.
- */
-void tevent_req_oom(struct tevent_req *req);
-#else
-void _tevent_req_oom(struct tevent_req *req,
-		     const char *location);
-#define tevent_req_oom(req) \
-	_tevent_req_oom(req, __location__)
-#endif
-
-/**
- * @brief Finish a request before the caller had the change to set the callback.
- *
- * An implementation of an async request might find that it can either finish
- * the request without waiting for an external event, or it can not even start
- * the engine. To present the illusion of a callback to the user of the API,
- * the implementation can call this helper function which triggers an
- * immediate event. This way the caller can use the same calling
- * conventions, independent of whether the request was actually deferred.
- *
- * @code
- * struct tevent_req *computation_send(TALLOC_CTX *mem_ctx,
- *                                     struct tevent_context *ev)
- * {
- *     struct tevent_req *req, *subreq;
- *     struct computation_state *state;
- *     req = tevent_req_create(mem_ctx, &state, struct computation_state);
- *     if (req == NULL) {
- *         return NULL;
- *     }
- *     subreq = subcomputation_send(state, ev);
- *     if (tevent_req_nomem(subreq, req)) {
- *         return tevent_req_post(req, ev);
- *     }
- *     tevent_req_set_callback(subreq, computation_done, req);
- *     return req;
- * }
- * @endcode
- *
- * @param[in]  req      The finished request.
- *
- * @param[in]  ev       The tevent_context for the immediate event.
- *
- * @return              The given request will be returned.
- */
-struct tevent_req *tevent_req_post(struct tevent_req *req,
-				   struct tevent_context *ev);
-
-/**
- * @brief Finish multiple requests within one function
- *
- * Normally tevent_req_notify_callback() and all wrappers
- * (e.g. tevent_req_done() and tevent_req_error())
- * need to be the last thing an event handler should call.
- * This is because the callback is likely to destroy the
- * context of the current function.
- *
- * If a function wants to notify more than one caller,
- * it is dangerous if it just triggers multiple callbacks
- * in a row. With tevent_req_defer_callback() it is possible
- * to set an event context that will be used to defer the callback
- * via an immediate event (similar to tevent_req_post()).
- *
- * @code
- * struct complete_state {
- *       struct tevent_context *ev;
- *
- *       struct tevent_req **reqs;
- * };
- *
- * void complete(struct complete_state *state)
- * {
- *       size_t i, c = talloc_array_length(state->reqs);
- *
- *       for (i=0; i < c; i++) {
- *            tevent_req_defer_callback(state->reqs[i], state->ev);
- *            tevent_req_done(state->reqs[i]);
- *       }
- * }
- * @endcode
- *
- * @param[in]  req      The finished request.
- *
- * @param[in]  ev       The tevent_context for the immediate event.
- *
- * @return              The given request will be returned.
- */
-void tevent_req_defer_callback(struct tevent_req *req,
-			       struct tevent_context *ev);
-
-/**
- * @brief Check if the given request is still in progress.
- *
- * It is typically used by sync wrapper functions.
- *
- * @param[in]  req      The request to poll.
- *
- * @return              The boolean form of "is in progress".
- */
-bool tevent_req_is_in_progress(struct tevent_req *req);
-
-/**
- * @brief Actively poll for the given request to finish.
- *
- * This function is typically used by sync wrapper functions.
- *
- * @param[in]  req      The request to poll.
- *
- * @param[in]  ev       The tevent_context to be used.
- *
- * @return              On success true is returned. If a critical error has
- *                      happened in the tevent loop layer false is returned.
- *                      This is not the return value of the given request!
- *
- * @note This should only be used if the given tevent context was created by the
- * caller, to avoid event loop nesting.
- *
- * @code
- * req = tstream_writev_queue_send(mem_ctx,
- *                                 ev_ctx,
- *                                 tstream,
- *                                 send_queue,
- *                                 iov, 2);
- * ok = tevent_req_poll(req, tctx->ev);
- * rc = tstream_writev_queue_recv(req, &sys_errno);
- * TALLOC_FREE(req);
- * @endcode
- */
-bool tevent_req_poll(struct tevent_req *req,
-		     struct tevent_context *ev);
-
-/**
- * @brief Get the tevent request state and the actual error set by
- * tevent_req_error.
- *
- * @code
- * int computation_recv(struct tevent_req *req, uint64_t *perr)
- * {
- *     enum tevent_req_state state;
- *     uint64_t err;
- *     if (tevent_req_is_error(req, &state, &err)) {
- *         *perr = err;
- *         return -1;
- *     }
- *     return 0;
- * }
- * @endcode
- *
- * @param[in]  req      The tevent request to get the error from.
- *
- * @param[out] state    A pointer to store the tevent request error state.
- *
- * @param[out] error    A pointer to store the error set by tevent_req_error().
- *
- * @return              True if the function could set error and state, false
- *                      otherwise.
- *
- * @see tevent_req_error()
- */
-bool tevent_req_is_error(struct tevent_req *req,
-			 enum tevent_req_state *state,
-			 uint64_t *error);
-
-/**
- * @brief Use as the last action of a _recv() function.
- *
- * This function destroys the attached private data.
- *
- * @param[in]  req      The finished request.
- */
-void tevent_req_received(struct tevent_req *req);
-
-/**
- * @brief Create a tevent subrequest at a given time.
- *
- * The idea is that always the same syntax for tevent requests.
- *
- * @param[in]  mem_ctx  The talloc memory context to use.
- *
- * @param[in]  ev       The event handle to setup the request.
- *
- * @param[in]  wakeup_time The time to wakeup and execute the request.
- *
- * @return              The new subrequest, NULL on error.
- *
- * Example:
- * @code
- *   static void my_callback_wakeup_done(tevent_req *subreq)
- *   {
- *     struct tevent_req *req = tevent_req_callback_data(subreq,
- *                              struct tevent_req);
- *     bool ok;
- *
- *     ok = tevent_wakeup_recv(subreq);
- *     TALLOC_FREE(subreq);
- *     if (!ok) {
- *         tevent_req_error(req, -1);
- *         return;
- *     }
- *     ...
- *   }
- * @endcode
- *
- * @code
- *   subreq = tevent_wakeup_send(mem_ctx, ev, wakeup_time);
- *   if (tevent_req_nomem(subreq, req)) {
- *     return false;
- *   }
- *   tevent_set_callback(subreq, my_callback_wakeup_done, req);
- * @endcode
- *
- * @see tevent_wakeup_recv()
- */
-struct tevent_req *tevent_wakeup_send(TALLOC_CTX *mem_ctx,
-				      struct tevent_context *ev,
-				      struct timeval wakeup_time);
-
-/**
- * @brief Check if the wakeup has been correctly executed.
- *
- * This function needs to be called in the callback function set after calling
- * tevent_wakeup_send().
- *
- * @param[in]  req      The tevent request to check.
- *
- * @return              True on success, false otherwise.
- *
- * @see tevent_wakeup_recv()
- */
-bool tevent_wakeup_recv(struct tevent_req *req);
-
-/* @} */
-
-/**
- * @defgroup tevent_helpers The tevent helper functiions
- * @ingroup tevent
- *
- * @todo description
- *
- * @{
- */
-
-/**
- * @brief Compare two timeval values.
- *
- * @param[in]  tv1      The first timeval value to compare.
- *
- * @param[in]  tv2      The second timeval value to compare.
- *
- * @return              0 if they are equal.
- *                      1 if the first time is greater than the second.
- *                      -1 if the first time is smaller than the second.
- */
-int tevent_timeval_compare(const struct timeval *tv1,
-			   const struct timeval *tv2);
-
-/**
- * @brief Get a zero timval value.
- *
- * @return              A zero timval value.
- */
-struct timeval tevent_timeval_zero(void);
-
-/**
- * @brief Get a timeval value for the current time.
- *
- * @return              A timval value with the current time.
- */
-struct timeval tevent_timeval_current(void);
-
-/**
- * @brief Get a timeval structure with the given values.
- *
- * @param[in]  secs     The seconds to set.
- *
- * @param[in]  usecs    The microseconds to set.
- *
- * @return              A timeval structure with the given values.
- */
-struct timeval tevent_timeval_set(uint32_t secs, uint32_t usecs);
-
-/**
- * @brief Get the difference between two timeval values.
- *
- * @param[in]  tv1      The first timeval.
- *
- * @param[in]  tv2      The second timeval.
- *
- * @return              A timeval structure with the difference between the
- *                      first and the second value.
- */
-struct timeval tevent_timeval_until(const struct timeval *tv1,
-				    const struct timeval *tv2);
-
-/**
- * @brief Check if a given timeval structure is zero.
- *
- * @param[in]  tv       The timeval to check if it is zero.
- *
- * @return              True if it is zero, false otherwise.
- */
-bool tevent_timeval_is_zero(const struct timeval *tv);
-
-/**
- * @brief Add the given amount of time to a timeval structure.
- *
- * @param[in]  tv        The timeval structure to add the time.
- *
- * @param[in]  secs      The seconds to add to the timeval.
- *
- * @param[in]  usecs     The microseconds to add to the timeval.
- *
- * @return               The timeval structure with the new time.
- */
-struct timeval tevent_timeval_add(const struct timeval *tv, uint32_t secs,
-				  uint32_t usecs);
-
-/**
- * @brief Get a timeval in the future with a specified offset from now.
- *
- * @param[in]  secs     The seconds of the offset from now.
- *
- * @param[in]  usecs    The microseconds of the offset from now.
- *
- * @return              A timval with the given offset in the future.
- */
-struct timeval tevent_timeval_current_ofs(uint32_t secs, uint32_t usecs);
-
-/* @} */
-
-
-/**
- * @defgroup tevent_queue The tevent queue functions
- * @ingroup tevent
- *
- * A tevent_queue is used to queue up async requests that must be
- * serialized. For example writing buffers into a socket must be
- * serialized. Writing a large lump of data into a socket can require
- * multiple write(2) or send(2) system calls. If more than one async
- * request is outstanding to write large buffers into a socket, every
- * request must individually be completed before the next one begins,
- * even if multiple syscalls are required.
- *
- * Take a look at @ref tevent_queue_tutorial for more details.
- * @{
- */
-
-struct tevent_queue;
-struct tevent_queue_entry;
-
-#ifdef DOXYGEN
-/**
- * @brief Create and start a tevent queue.
- *
- * @param[in]  mem_ctx  The talloc memory context to allocate the queue.
- *
- * @param[in]  name     The name to use to identify the queue.
- *
- * @return              An allocated tevent queue on success, NULL on error.
- *
- * @see tevent_queue_start()
- * @see tevent_queue_stop()
- */
-struct tevent_queue *tevent_queue_create(TALLOC_CTX *mem_ctx,
-					 const char *name);
-#else
-struct tevent_queue *_tevent_queue_create(TALLOC_CTX *mem_ctx,
-					  const char *name,
-					  const char *location);
-
-#define tevent_queue_create(_mem_ctx, _name) \
-	_tevent_queue_create((_mem_ctx), (_name), __location__)
-#endif
-
-/**
- * @brief A callback trigger function run by the queue.
- *
- * @param[in]  req      The tevent request the trigger function is executed on.
- *
- * @param[in]  private_data The private data pointer specified by
- *                          tevent_queue_add().
- *
- * @see tevent_queue_add()
- * @see tevent_queue_add_entry()
- * @see tevent_queue_add_optimize_empty()
- */
-typedef void (*tevent_queue_trigger_fn_t)(struct tevent_req *req,
-					  void *private_data);
-
-/**
- * @brief Add a tevent request to the queue.
- *
- * @param[in]  queue    The queue to add the request.
- *
- * @param[in]  ev       The event handle to use for the request.
- *
- * @param[in]  req      The tevent request to add to the queue.
- *
- * @param[in]  trigger  The function triggered by the queue when the request
- *                      is called. Since tevent 0.9.14 it's possible to
- *                      pass NULL, in order to just add a "blocker" to the
- *                      queue.
- *
- * @param[in]  private_data The private data passed to the trigger function.
- *
- * @return              True if the request has been successfully added, false
- *                      otherwise.
- */
-bool tevent_queue_add(struct tevent_queue *queue,
-		      struct tevent_context *ev,
-		      struct tevent_req *req,
-		      tevent_queue_trigger_fn_t trigger,
-		      void *private_data);
-
-/**
- * @brief Add a tevent request to the queue.
- *
- * The request can be removed from the queue by calling talloc_free()
- * (or a similar function) on the returned queue entry. This
- * is the only difference to tevent_queue_add().
- *
- * @param[in]  queue    The queue to add the request.
- *
- * @param[in]  ev       The event handle to use for the request.
- *
- * @param[in]  req      The tevent request to add to the queue.
- *
- * @param[in]  trigger  The function triggered by the queue when the request
- *                      is called. Since tevent 0.9.14 it's possible to
- *                      pass NULL, in order to just add a "blocker" to the
- *                      queue.
- *
- * @param[in]  private_data The private data passed to the trigger function.
- *
- * @return              a pointer to the tevent_queue_entry if the request
- *                      has been successfully added, NULL otherwise.
- *
- * @see tevent_queue_add()
- * @see tevent_queue_add_optimize_empty()
- */
-struct tevent_queue_entry *tevent_queue_add_entry(
-					struct tevent_queue *queue,
-					struct tevent_context *ev,
-					struct tevent_req *req,
-					tevent_queue_trigger_fn_t trigger,
-					void *private_data);
-
-/**
- * @brief Add a tevent request to the queue using a possible optimization.
- *
- * This tries to optimize for the empty queue case and may calls
- * the trigger function directly. This is the only difference compared
- * to tevent_queue_add_entry().
- *
- * The caller needs to be prepared that the trigger function has
- * already called tevent_req_notify_callback(), tevent_req_error(),
- * tevent_req_done() or a similar function.
- *
- * The request can be removed from the queue by calling talloc_free()
- * (or a similar function) on the returned queue entry.
- *
- * @param[in]  queue    The queue to add the request.
- *
- * @param[in]  ev       The event handle to use for the request.
- *
- * @param[in]  req      The tevent request to add to the queue.
- *
- * @param[in]  trigger  The function triggered by the queue when the request
- *                      is called. Since tevent 0.9.14 it's possible to
- *                      pass NULL, in order to just add a "blocker" to the
- *                      queue.
- *
- * @param[in]  private_data The private data passed to the trigger function.
- *
- * @return              a pointer to the tevent_queue_entry if the request
- *                      has been successfully added, NULL otherwise.
- *
- * @see tevent_queue_add()
- * @see tevent_queue_add_entry()
- */
-struct tevent_queue_entry *tevent_queue_add_optimize_empty(
-					struct tevent_queue *queue,
-					struct tevent_context *ev,
-					struct tevent_req *req,
-					tevent_queue_trigger_fn_t trigger,
-					void *private_data);
-
-/**
- * @brief Start a tevent queue.
- *
- * The queue is started by default.
- *
- * @param[in]  queue    The queue to start.
- */
-void tevent_queue_start(struct tevent_queue *queue);
-
-/**
- * @brief Stop a tevent queue.
- *
- * The queue is started by default.
- *
- * @param[in]  queue    The queue to stop.
- */
-void tevent_queue_stop(struct tevent_queue *queue);
-
-/**
- * @brief Get the length of the queue.
- *
- * @param[in]  queue    The queue to get the length from.
- *
- * @return              The number of elements.
- */
-size_t tevent_queue_length(struct tevent_queue *queue);
-
-/**
- * @brief Is the tevent queue running.
- *
- * The queue is started by default.
- *
- * @param[in]  queue    The queue.
- *
- * @return              Wether the queue is running or not..
- */
-bool tevent_queue_running(struct tevent_queue *queue);
-
-typedef int (*tevent_nesting_hook)(struct tevent_context *ev,
-				   void *private_data,
-				   uint32_t level,
-				   bool begin,
-				   void *stack_ptr,
-				   const char *location);
-#ifdef TEVENT_DEPRECATED
-#ifndef _DEPRECATED_
-#if (__GNUC__ >= 3) && (__GNUC_MINOR__ >= 1 )
-#define _DEPRECATED_ __attribute__ ((deprecated))
-#else
-#define _DEPRECATED_
-#endif
-#endif
-void tevent_loop_allow_nesting(struct tevent_context *ev) _DEPRECATED_;
-void tevent_loop_set_nesting_hook(struct tevent_context *ev,
-				  tevent_nesting_hook hook,
-				  void *private_data) _DEPRECATED_;
-int _tevent_loop_until(struct tevent_context *ev,
-		       bool (*finished)(void *private_data),
-		       void *private_data,
-		       const char *location) _DEPRECATED_;
-#define tevent_loop_until(ev, finished, private_data) \
-	_tevent_loop_until(ev, finished, private_data, __location__)
-#endif
-
-int tevent_re_initialise(struct tevent_context *ev);
-
-/* @} */
-
-/**
- * @defgroup tevent_ops The tevent operation functions
- * @ingroup tevent
- *
- * The following structure and registration functions are exclusively
- * needed for people writing and pluggin a different event engine.
- * There is nothing useful for normal tevent user in here.
- * @{
- */
-
-struct tevent_ops {
-	/* context init */
-	int (*context_init)(struct tevent_context *ev);
-
-	/* fd_event functions */
-	struct tevent_fd *(*add_fd)(struct tevent_context *ev,
-				    TALLOC_CTX *mem_ctx,
-				    int fd, uint16_t flags,
-				    tevent_fd_handler_t handler,
-				    void *private_data,
-				    const char *handler_name,
-				    const char *location);
-	void (*set_fd_close_fn)(struct tevent_fd *fde,
-				tevent_fd_close_fn_t close_fn);
-	uint16_t (*get_fd_flags)(struct tevent_fd *fde);
-	void (*set_fd_flags)(struct tevent_fd *fde, uint16_t flags);
-
-	/* timed_event functions */
-	struct tevent_timer *(*add_timer)(struct tevent_context *ev,
-					  TALLOC_CTX *mem_ctx,
-					  struct timeval next_event,
-					  tevent_timer_handler_t handler,
-					  void *private_data,
-					  const char *handler_name,
-					  const char *location);
-
-	/* immediate event functions */
-	void (*schedule_immediate)(struct tevent_immediate *im,
-				   struct tevent_context *ev,
-				   tevent_immediate_handler_t handler,
-				   void *private_data,
-				   const char *handler_name,
-				   const char *location);
-
-	/* signal functions */
-	struct tevent_signal *(*add_signal)(struct tevent_context *ev,
-					    TALLOC_CTX *mem_ctx,
-					    int signum, int sa_flags,
-					    tevent_signal_handler_t handler,
-					    void *private_data,
-					    const char *handler_name,
-					    const char *location);
-
-	/* loop functions */
-	int (*loop_once)(struct tevent_context *ev, const char *location);
-	int (*loop_wait)(struct tevent_context *ev, const char *location);
-};
-
-bool tevent_register_backend(const char *name, const struct tevent_ops *ops);
-
-/* @} */
-
-/**
- * @defgroup tevent_compat The tevent compatibility functions
- * @ingroup tevent
- *
- * The following definitions are usueful only for compatibility with the
- * implementation originally developed within the samba4 code and will be
- * soon removed. Please NEVER use in new code.
- *
- * @todo Ignore it?
- *
- * @{
- */
-
-#ifdef TEVENT_COMPAT_DEFINES
-
-#define event_context	tevent_context
-#define event_ops	tevent_ops
-#define fd_event	tevent_fd
-#define timed_event	tevent_timer
-#define signal_event	tevent_signal
-
-#define event_fd_handler_t	tevent_fd_handler_t
-#define event_timed_handler_t	tevent_timer_handler_t
-#define event_signal_handler_t	tevent_signal_handler_t
-
-#define event_context_init(mem_ctx) \
-	tevent_context_init(mem_ctx)
-
-#define event_context_init_byname(mem_ctx, name) \
-	tevent_context_init_byname(mem_ctx, name)
-
-#define event_backend_list(mem_ctx) \
-	tevent_backend_list(mem_ctx)
-
-#define event_set_default_backend(backend) \
-	tevent_set_default_backend(backend)
-
-#define event_add_fd(ev, mem_ctx, fd, flags, handler, private_data) \
-	tevent_add_fd(ev, mem_ctx, fd, flags, handler, private_data)
-
-#define event_add_timed(ev, mem_ctx, next_event, handler, private_data) \
-	tevent_add_timer(ev, mem_ctx, next_event, handler, private_data)
-
-#define event_add_signal(ev, mem_ctx, signum, sa_flags, handler, private_data) \
-	tevent_add_signal(ev, mem_ctx, signum, sa_flags, handler, private_data)
-
-#define event_loop_once(ev) \
-	tevent_loop_once(ev)
-
-#define event_loop_wait(ev) \
-	tevent_loop_wait(ev)
-
-#define event_get_fd_flags(fde) \
-	tevent_fd_get_flags(fde)
-
-#define event_set_fd_flags(fde, flags) \
-	tevent_fd_set_flags(fde, flags)
-
-#define EVENT_FD_READ		TEVENT_FD_READ
-#define EVENT_FD_WRITE		TEVENT_FD_WRITE
-
-#define EVENT_FD_WRITEABLE(fde) \
-	TEVENT_FD_WRITEABLE(fde)
-
-#define EVENT_FD_READABLE(fde) \
-	TEVENT_FD_READABLE(fde)
-
-#define EVENT_FD_NOT_WRITEABLE(fde) \
-	TEVENT_FD_NOT_WRITEABLE(fde)
-
-#define EVENT_FD_NOT_READABLE(fde) \
-	TEVENT_FD_NOT_READABLE(fde)
-
-#define ev_debug_level		tevent_debug_level
-
-#define EV_DEBUG_FATAL		TEVENT_DEBUG_FATAL
-#define EV_DEBUG_ERROR		TEVENT_DEBUG_ERROR
-#define EV_DEBUG_WARNING	TEVENT_DEBUG_WARNING
-#define EV_DEBUG_TRACE		TEVENT_DEBUG_TRACE
-
-#define ev_set_debug(ev, debug, context) \
-	tevent_set_debug(ev, debug, context)
-
-#define ev_set_debug_stderr(_ev) tevent_set_debug_stderr(ev)
-
-#endif /* TEVENT_COMPAT_DEFINES */
-
-/* @} */
-
-#endif /* __TEVENT_H__ */
diff --git a/lib/tevent/tevent.pc.in b/lib/tevent/tevent.pc.in
deleted file mode 100644
index 9adcffb..0000000
--- a/lib/tevent/tevent.pc.in
+++ /dev/null
@@ -1,12 +0,0 @@
-prefix=@prefix@
-exec_prefix=@exec_prefix@
-libdir=@libdir@
-includedir=@includedir@
-
-Name: tevent
-Description: An event system library
-Version: @PACKAGE_VERSION@
-Requires: talloc
-Libs: -L${libdir} -ltevent
-Cflags: -I${includedir}
-URL: http://samba.org/
diff --git a/lib/tevent/tevent_debug.c b/lib/tevent/tevent_debug.c
deleted file mode 100644
index 31da7b9..0000000
--- a/lib/tevent/tevent_debug.c
+++ /dev/null
@@ -1,119 +0,0 @@
-/*
-   Unix SMB/CIFS implementation.
-
-   Copyright (C) Andrew Tridgell 2005
-   Copyright (C) Jelmer Vernooij 2005
-
-     ** NOTE! The following LGPL license applies to the tevent
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-
-#include "replace.h"
-#include "tevent.h"
-#include "tevent_internal.h"
-
-/********************************************************************
- * Debug wrapper functions, modeled (with lot's of code copied as is)
- * after the ev debug wrapper functions
- ********************************************************************/
-
-/*
-  this allows the user to choose their own debug function
-*/
-int tevent_set_debug(struct tevent_context *ev,
-		     void (*debug)(void *context,
-				   enum tevent_debug_level level,
-				   const char *fmt,
-				   va_list ap) PRINTF_ATTRIBUTE(3,0),
-		     void *context)
-{
-	ev->debug_ops.debug = debug;
-	ev->debug_ops.context = context;
-	return 0;
-}
-
-/*
-  debug function for ev_set_debug_stderr
-*/
-static void tevent_debug_stderr(void *private_data,
-				enum tevent_debug_level level,
-				const char *fmt,
-				va_list ap) PRINTF_ATTRIBUTE(3,0);
-static void tevent_debug_stderr(void *private_data,
-				enum tevent_debug_level level,
-				const char *fmt, va_list ap)
-{
-	if (level <= TEVENT_DEBUG_WARNING) {
-		vfprintf(stderr, fmt, ap);
-	}
-}
-
-/*
-  convenience function to setup debug messages on stderr
-  messages of level TEVENT_DEBUG_WARNING and higher are printed
-*/
-int tevent_set_debug_stderr(struct tevent_context *ev)
-{
-	return tevent_set_debug(ev, tevent_debug_stderr, ev);
-}
-
-/*
- * log a message
- *
- * The default debug action is to ignore debugging messages.
- * This is the most appropriate action for a library.
- * Applications using the library must decide where to
- * redirect debugging messages
-*/
-void tevent_debug(struct tevent_context *ev, enum tevent_debug_level level,
-		  const char *fmt, ...)
-{
-	va_list ap;
-	if (!ev) {
-		return;
-	}
-	if (ev->debug_ops.debug == NULL) {
-		return;
-	}
-	va_start(ap, fmt);
-	ev->debug_ops.debug(ev->debug_ops.context, level, fmt, ap);
-	va_end(ap);
-}
-
-void tevent_set_trace_callback(struct tevent_context *ev,
-			       tevent_trace_callback_t cb,
-			       void *private_data)
-{
-	ev->tracing.callback = cb;
-	ev->tracing.private_data = private_data;
-}
-
-void tevent_get_trace_callback(struct tevent_context *ev,
-			       tevent_trace_callback_t *cb,
-			       void *private_data)
-{
-	*cb = ev->tracing.callback;
-	*(void**)private_data = ev->tracing.private_data;
-}
-
-void tevent_trace_point_callback(struct tevent_context *ev,
-				 enum tevent_trace_point tp)
-{
-	if (ev->tracing.callback != NULL) {
-		ev->tracing.callback(tp, ev->tracing.private_data);
-	}
-}
diff --git a/lib/tevent/tevent_epoll.c b/lib/tevent/tevent_epoll.c
deleted file mode 100644
index a7fb8b1..0000000
--- a/lib/tevent/tevent_epoll.c
+++ /dev/null
@@ -1,459 +0,0 @@
-/*
-   Unix SMB/CIFS implementation.
-
-   main select loop and event handling - epoll implementation
-
-   Copyright (C) Andrew Tridgell	2003-2005
-   Copyright (C) Stefan Metzmacher	2005-2009
-
-     ** NOTE! The following LGPL license applies to the tevent
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-
-#include "replace.h"
-#include "system/filesys.h"
-#include "system/select.h"
-#include "tevent.h"
-#include "tevent_internal.h"
-#include "tevent_util.h"
-
-struct epoll_event_context {
-	/* a pointer back to the generic event_context */
-	struct tevent_context *ev;
-
-	/* when using epoll this is the handle from epoll_create */
-	int epoll_fd;
-
-	pid_t pid;
-};
-
-/*
-  called when a epoll call fails
-*/
-static void epoll_panic(struct epoll_event_context *epoll_ev, const char *reason)
-{
-	tevent_debug(epoll_ev->ev, TEVENT_DEBUG_FATAL,
-		 "%s (%s) - calling abort()\n", reason, strerror(errno));
-	abort();
-}
-
-/*
-  map from TEVENT_FD_* to EPOLLIN/EPOLLOUT
-*/
-static uint32_t epoll_map_flags(uint16_t flags)
-{
-	uint32_t ret = 0;
-	if (flags & TEVENT_FD_READ) ret |= (EPOLLIN | EPOLLERR | EPOLLHUP);
-	if (flags & TEVENT_FD_WRITE) ret |= (EPOLLOUT | EPOLLERR | EPOLLHUP);
-	return ret;
-}
-
-/*
- free the epoll fd
-*/
-static int epoll_ctx_destructor(struct epoll_event_context *epoll_ev)
-{
-	close(epoll_ev->epoll_fd);
-	epoll_ev->epoll_fd = -1;
-	return 0;
-}
-
-/*
- init the epoll fd
-*/
-static int epoll_init_ctx(struct epoll_event_context *epoll_ev)
-{
-	epoll_ev->epoll_fd = epoll_create(64);
-	if (epoll_ev->epoll_fd == -1) {
-		tevent_debug(epoll_ev->ev, TEVENT_DEBUG_FATAL,
-			     "Failed to create epoll handle.\n");
-		return -1;
-	}
-
-	if (!ev_set_close_on_exec(epoll_ev->epoll_fd)) {
-		tevent_debug(epoll_ev->ev, TEVENT_DEBUG_WARNING,
-			     "Failed to set close-on-exec, file descriptor may be leaked to children.\n");
-	}
-
-	epoll_ev->pid = getpid();
-	talloc_set_destructor(epoll_ev, epoll_ctx_destructor);
-
-	return 0;
-}
-
-static void epoll_add_event(struct epoll_event_context *epoll_ev, struct tevent_fd *fde);
-
-/*
-  reopen the epoll handle when our pid changes
-  see http://junkcode.samba.org/ftp/unpacked/junkcode/epoll_fork.c for an
-  demonstration of why this is needed
- */
-static void epoll_check_reopen(struct epoll_event_context *epoll_ev)
-{
-	struct tevent_fd *fde;
-
-	if (epoll_ev->pid == getpid()) {
-		return;
-	}
-
-	close(epoll_ev->epoll_fd);
-	epoll_ev->epoll_fd = epoll_create(64);
-	if (epoll_ev->epoll_fd == -1) {
-		tevent_debug(epoll_ev->ev, TEVENT_DEBUG_FATAL,
-			     "Failed to recreate epoll handle after fork\n");
-		return;
-	}
-
-	if (!ev_set_close_on_exec(epoll_ev->epoll_fd)) {
-		tevent_debug(epoll_ev->ev, TEVENT_DEBUG_WARNING,
-			     "Failed to set close-on-exec, file descriptor may be leaked to children.\n");
-	}
-
-	epoll_ev->pid = getpid();
-	for (fde=epoll_ev->ev->fd_events;fde;fde=fde->next) {
-		epoll_add_event(epoll_ev, fde);
-	}
-}
-
-#define EPOLL_ADDITIONAL_FD_FLAG_HAS_EVENT	(1<<0)
-#define EPOLL_ADDITIONAL_FD_FLAG_REPORT_ERROR	(1<<1)
-#define EPOLL_ADDITIONAL_FD_FLAG_GOT_ERROR	(1<<2)
-
-/*
- add the epoll event to the given fd_event
-*/
-static void epoll_add_event(struct epoll_event_context *epoll_ev, struct tevent_fd *fde)
-{
-	struct epoll_event event;
-
-	if (epoll_ev->epoll_fd == -1) return;
-
-	fde->additional_flags &= ~EPOLL_ADDITIONAL_FD_FLAG_REPORT_ERROR;
-
-	/* if we don't want events yet, don't add an epoll_event */
-	if (fde->flags == 0) return;
-
-	ZERO_STRUCT(event);
-	event.events = epoll_map_flags(fde->flags);
-	event.data.ptr = fde;
-	if (epoll_ctl(epoll_ev->epoll_fd, EPOLL_CTL_ADD, fde->fd, &event) != 0) {
-		epoll_panic(epoll_ev, "EPOLL_CTL_ADD failed");
-	}
-	fde->additional_flags |= EPOLL_ADDITIONAL_FD_FLAG_HAS_EVENT;
-
-	/* only if we want to read we want to tell the event handler about errors */
-	if (fde->flags & TEVENT_FD_READ) {
-		fde->additional_flags |= EPOLL_ADDITIONAL_FD_FLAG_REPORT_ERROR;
-	}
-}
-
-/*
- delete the epoll event for given fd_event
-*/
-static void epoll_del_event(struct epoll_event_context *epoll_ev, struct tevent_fd *fde)
-{
-	struct epoll_event event;
-
-	if (epoll_ev->epoll_fd == -1) return;
-
-	fde->additional_flags &= ~EPOLL_ADDITIONAL_FD_FLAG_REPORT_ERROR;
-
-	/* if there's no epoll_event, we don't need to delete it */
-	if (!(fde->additional_flags & EPOLL_ADDITIONAL_FD_FLAG_HAS_EVENT)) return;
-
-	ZERO_STRUCT(event);
-	event.events = epoll_map_flags(fde->flags);
-	event.data.ptr = fde;
-	if (epoll_ctl(epoll_ev->epoll_fd, EPOLL_CTL_DEL, fde->fd, &event) != 0) {
-		tevent_debug(epoll_ev->ev, TEVENT_DEBUG_FATAL,
-			     "epoll_del_event failed! probable early close bug (%s)\n",
-			     strerror(errno));
-	}
-	fde->additional_flags &= ~EPOLL_ADDITIONAL_FD_FLAG_HAS_EVENT;
-}
-
-/*
- change the epoll event to the given fd_event
-*/
-static void epoll_mod_event(struct epoll_event_context *epoll_ev, struct tevent_fd *fde)
-{
-	struct epoll_event event;
-	if (epoll_ev->epoll_fd == -1) return;
-
-	fde->additional_flags &= ~EPOLL_ADDITIONAL_FD_FLAG_REPORT_ERROR;
-
-	ZERO_STRUCT(event);
-	event.events = epoll_map_flags(fde->flags);
-	event.data.ptr = fde;
-	if (epoll_ctl(epoll_ev->epoll_fd, EPOLL_CTL_MOD, fde->fd, &event) != 0) {
-		epoll_panic(epoll_ev, "EPOLL_CTL_MOD failed");
-	}
-
-	/* only if we want to read we want to tell the event handler about errors */
-	if (fde->flags & TEVENT_FD_READ) {
-		fde->additional_flags |= EPOLL_ADDITIONAL_FD_FLAG_REPORT_ERROR;
-	}
-}
-
-static void epoll_change_event(struct epoll_event_context *epoll_ev, struct tevent_fd *fde)
-{
-	bool got_error = (fde->additional_flags & EPOLL_ADDITIONAL_FD_FLAG_GOT_ERROR);
-	bool want_read = (fde->flags & TEVENT_FD_READ);
-	bool want_write= (fde->flags & TEVENT_FD_WRITE);
-
-	if (epoll_ev->epoll_fd == -1) return;
-
-	fde->additional_flags &= ~EPOLL_ADDITIONAL_FD_FLAG_REPORT_ERROR;
-
-	/* there's already an event */
-	if (fde->additional_flags & EPOLL_ADDITIONAL_FD_FLAG_HAS_EVENT) {
-		if (want_read || (want_write && !got_error)) {
-			epoll_mod_event(epoll_ev, fde);
-			return;
-		}
-		/*
-		 * if we want to match the select behavior, we need to remove the epoll_event
-		 * when the caller isn't interested in events.
-		 *
-		 * this is because epoll reports EPOLLERR and EPOLLHUP, even without asking for them
-		 */
-		epoll_del_event(epoll_ev, fde);
-		return;
-	}
-
-	/* there's no epoll_event attached to the fde */
-	if (want_read || (want_write && !got_error)) {
-		epoll_add_event(epoll_ev, fde);
-		return;
-	}
-}
-
-/*
-  event loop handling using epoll
-*/
-static int epoll_event_loop(struct epoll_event_context *epoll_ev, struct timeval *tvalp)
-{
-	int ret, i;
-#define MAXEVENTS 1
-	struct epoll_event events[MAXEVENTS];
-	int timeout = -1;
-
-	if (epoll_ev->epoll_fd == -1) return -1;
-
-	if (tvalp) {
-		/* it's better to trigger timed events a bit later than to early */
-		timeout = ((tvalp->tv_usec+999) / 1000) + (tvalp->tv_sec*1000);
-	}
-
-	if (epoll_ev->ev->signal_events &&
-	    tevent_common_check_signal(epoll_ev->ev)) {
-		return 0;
-	}
-
-	tevent_trace_point_callback(epoll_ev->ev, TEVENT_TRACE_BEFORE_WAIT);
-	ret = epoll_wait(epoll_ev->epoll_fd, events, MAXEVENTS, timeout);
-	tevent_trace_point_callback(epoll_ev->ev, TEVENT_TRACE_AFTER_WAIT);
-
-	if (ret == -1 && errno == EINTR && epoll_ev->ev->signal_events) {
-		if (tevent_common_check_signal(epoll_ev->ev)) {
-			return 0;
-		}
-	}
-
-	if (ret == -1 && errno != EINTR) {
-		epoll_panic(epoll_ev, "epoll_wait() failed");
-		return -1;
-	}
-
-	if (ret == 0 && tvalp) {
-		/* we don't care about a possible delay here */
-		tevent_common_loop_timer_delay(epoll_ev->ev);
-		return 0;
-	}
-
-	for (i=0;i<ret;i++) {
-		struct tevent_fd *fde = talloc_get_type(events[i].data.ptr,
-						       struct tevent_fd);
-		uint16_t flags = 0;
-
-		if (fde == NULL) {
-			epoll_panic(epoll_ev, "epoll_wait() gave bad data");
-			return -1;
-		}
-		if (events[i].events & (EPOLLHUP|EPOLLERR)) {
-			fde->additional_flags |= EPOLL_ADDITIONAL_FD_FLAG_GOT_ERROR;
-			/*
-			 * if we only wait for TEVENT_FD_WRITE, we should not tell the
-			 * event handler about it, and remove the epoll_event,
-			 * as we only report errors when waiting for read events,
-			 * to match the select() behavior
-			 */
-			if (!(fde->additional_flags & EPOLL_ADDITIONAL_FD_FLAG_REPORT_ERROR)) {
-				epoll_del_event(epoll_ev, fde);
-				continue;
-			}
-			flags |= TEVENT_FD_READ;
-		}
-		if (events[i].events & EPOLLIN) flags |= TEVENT_FD_READ;
-		if (events[i].events & EPOLLOUT) flags |= TEVENT_FD_WRITE;
-		if (flags) {
-			fde->handler(epoll_ev->ev, fde, flags, fde->private_data);
-			break;
-		}
-	}
-
-	return 0;
-}
-
-/*
-  create a epoll_event_context structure.
-*/
-static int epoll_event_context_init(struct tevent_context *ev)
-{
-	int ret;
-	struct epoll_event_context *epoll_ev;
-
-	epoll_ev = talloc_zero(ev, struct epoll_event_context);
-	if (!epoll_ev) return -1;
-	epoll_ev->ev = ev;
-	epoll_ev->epoll_fd = -1;
-
-	ret = epoll_init_ctx(epoll_ev);
-	if (ret != 0) {
-		talloc_free(epoll_ev);
-		return ret;
-	}
-
-	ev->additional_data = epoll_ev;
-	return 0;
-}
-
-/*
-  destroy an fd_event
-*/
-static int epoll_event_fd_destructor(struct tevent_fd *fde)
-{
-	struct tevent_context *ev = fde->event_ctx;
-	struct epoll_event_context *epoll_ev = NULL;
-
-	if (ev) {
-		epoll_ev = talloc_get_type(ev->additional_data,
-					   struct epoll_event_context);
-
-		epoll_check_reopen(epoll_ev);
-
-		epoll_del_event(epoll_ev, fde);
-	}
-
-	return tevent_common_fd_destructor(fde);
-}
-
-/*
-  add a fd based event
-  return NULL on failure (memory allocation error)
-*/
-static struct tevent_fd *epoll_event_add_fd(struct tevent_context *ev, TALLOC_CTX *mem_ctx,
-					    int fd, uint16_t flags,
-					    tevent_fd_handler_t handler,
-					    void *private_data,
-					    const char *handler_name,
-					    const char *location)
-{
-	struct epoll_event_context *epoll_ev = talloc_get_type(ev->additional_data,
-							   struct epoll_event_context);
-	struct tevent_fd *fde;
-
-	epoll_check_reopen(epoll_ev);
-
-	fde = tevent_common_add_fd(ev, mem_ctx, fd, flags,
-				   handler, private_data,
-				   handler_name, location);
-	if (!fde) return NULL;
-
-	talloc_set_destructor(fde, epoll_event_fd_destructor);
-
-	epoll_add_event(epoll_ev, fde);
-
-	return fde;
-}
-
-/*
-  set the fd event flags
-*/
-static void epoll_event_set_fd_flags(struct tevent_fd *fde, uint16_t flags)
-{
-	struct tevent_context *ev;
-	struct epoll_event_context *epoll_ev;
-
-	if (fde->flags == flags) return;
-
-	ev = fde->event_ctx;
-	epoll_ev = talloc_get_type(ev->additional_data, struct epoll_event_context);
-
-	fde->flags = flags;
-
-	epoll_check_reopen(epoll_ev);
-
-	epoll_change_event(epoll_ev, fde);
-}
-
-/*
-  do a single event loop using the events defined in ev
-*/
-static int epoll_event_loop_once(struct tevent_context *ev, const char *location)
-{
-	struct epoll_event_context *epoll_ev = talloc_get_type(ev->additional_data,
-							   struct epoll_event_context);
-	struct timeval tval;
-
-	if (ev->signal_events &&
-	    tevent_common_check_signal(ev)) {
-		return 0;
-	}
-
-	if (ev->immediate_events &&
-	    tevent_common_loop_immediate(ev)) {
-		return 0;
-	}
-
-	tval = tevent_common_loop_timer_delay(ev);
-	if (tevent_timeval_is_zero(&tval)) {
-		return 0;
-	}
-
-	epoll_check_reopen(epoll_ev);
-
-	return epoll_event_loop(epoll_ev, &tval);
-}
-
-static const struct tevent_ops epoll_event_ops = {
-	.context_init		= epoll_event_context_init,
-	.add_fd			= epoll_event_add_fd,
-	.set_fd_close_fn	= tevent_common_fd_set_close_fn,
-	.get_fd_flags		= tevent_common_fd_get_flags,
-	.set_fd_flags		= epoll_event_set_fd_flags,
-	.add_timer		= tevent_common_add_timer,
-	.schedule_immediate	= tevent_common_schedule_immediate,
-	.add_signal		= tevent_common_add_signal,
-	.loop_once		= epoll_event_loop_once,
-	.loop_wait		= tevent_common_loop_wait,
-};
-
-_PRIVATE_ bool tevent_epoll_init(void)
-{
-	return tevent_register_backend("epoll", &epoll_event_ops);
-}
diff --git a/lib/tevent/tevent_fd.c b/lib/tevent/tevent_fd.c
deleted file mode 100644
index 455961b..0000000
--- a/lib/tevent/tevent_fd.c
+++ /dev/null
@@ -1,95 +0,0 @@
-/*
-   Unix SMB/CIFS implementation.
-
-   common events code for fd events
-
-   Copyright (C) Stefan Metzmacher 2009
-
-     ** NOTE! The following LGPL license applies to the tevent
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-
-#include "replace.h"
-#include "tevent.h"
-#include "tevent_internal.h"
-#include "tevent_util.h"
-
-int tevent_common_fd_destructor(struct tevent_fd *fde)
-{
-	if (fde->event_ctx) {
-		DLIST_REMOVE(fde->event_ctx->fd_events, fde);
-	}
-
-	if (fde->close_fn) {
-		fde->close_fn(fde->event_ctx, fde, fde->fd, fde->private_data);
-		fde->fd = -1;
-	}
-
-	return 0;
-}
-
-struct tevent_fd *tevent_common_add_fd(struct tevent_context *ev, TALLOC_CTX *mem_ctx,
-				       int fd, uint16_t flags,
-				       tevent_fd_handler_t handler,
-				       void *private_data,
-				       const char *handler_name,
-				       const char *location)
-{
-	struct tevent_fd *fde;
-
-	/* tevent will crash later on select() if we save
-	 * a negative file descriptor. Better to fail here
-	 * so that consumers will be able to debug it
-	 */
-	if (fd < 0) return NULL;
-
-	fde = talloc(mem_ctx?mem_ctx:ev, struct tevent_fd);
-	if (!fde) return NULL;
-
-	fde->event_ctx		= ev;
-	fde->fd			= fd;
-	fde->flags		= flags;
-	fde->handler		= handler;
-	fde->close_fn		= NULL;
-	fde->private_data	= private_data;
-	fde->handler_name	= handler_name;
-	fde->location		= location;
-	fde->additional_flags	= 0;
-	fde->additional_data	= NULL;
-
-	DLIST_ADD(ev->fd_events, fde);
-
-	talloc_set_destructor(fde, tevent_common_fd_destructor);
-
-	return fde;
-}
-uint16_t tevent_common_fd_get_flags(struct tevent_fd *fde)
-{
-	return fde->flags;
-}
-
-void tevent_common_fd_set_flags(struct tevent_fd *fde, uint16_t flags)
-{
-	if (fde->flags == flags) return;
-	fde->flags = flags;
-}
-
-void tevent_common_fd_set_close_fn(struct tevent_fd *fde,
-				   tevent_fd_close_fn_t close_fn)
-{
-	fde->close_fn = close_fn;
-}
diff --git a/lib/tevent/tevent_immediate.c b/lib/tevent/tevent_immediate.c
deleted file mode 100644
index d5e7688..0000000
--- a/lib/tevent/tevent_immediate.c
+++ /dev/null
@@ -1,138 +0,0 @@
-/*
-   Unix SMB/CIFS implementation.
-
-   common events code for immediate events
-
-   Copyright (C) Stefan Metzmacher 2009
-
-     ** NOTE! The following LGPL license applies to the tevent
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-
-#include "replace.h"
-#include "tevent.h"
-#include "tevent_internal.h"
-#include "tevent_util.h"
-
-static void tevent_common_immediate_cancel(struct tevent_immediate *im)
-{
-	if (!im->event_ctx) {
-		return;
-	}
-
-	tevent_debug(im->event_ctx, TEVENT_DEBUG_TRACE,
-		     "Cancel immediate event %p \"%s\"\n",
-		     im, im->handler_name);
-
-	/* let the backend free im->additional_data */
-	if (im->cancel_fn) {
-		im->cancel_fn(im);
-	}
-
-	DLIST_REMOVE(im->event_ctx->immediate_events, im);
-	im->event_ctx		= NULL;
-	im->handler		= NULL;
-	im->private_data	= NULL;
-	im->handler_name	= NULL;
-	im->schedule_location	= NULL;
-	im->cancel_fn		= NULL;
-	im->additional_data	= NULL;
-
-	talloc_set_destructor(im, NULL);
-}
-
-/*
-  destroy an immediate event
-*/
-static int tevent_common_immediate_destructor(struct tevent_immediate *im)
-{
-	tevent_common_immediate_cancel(im);
-	return 0;
-}
-
-/*
- * schedule an immediate event on
- */
-void tevent_common_schedule_immediate(struct tevent_immediate *im,
-				      struct tevent_context *ev,
-				      tevent_immediate_handler_t handler,
-				      void *private_data,
-				      const char *handler_name,
-				      const char *location)
-{
-	tevent_common_immediate_cancel(im);
-
-	if (!handler) {
-		return;
-	}
-
-	im->event_ctx		= ev;
-	im->handler		= handler;
-	im->private_data	= private_data;
-	im->handler_name	= handler_name;
-	im->schedule_location	= location;
-	im->cancel_fn		= NULL;
-	im->additional_data	= NULL;
-
-	DLIST_ADD_END(ev->immediate_events, im, struct tevent_immediate *);
-	talloc_set_destructor(im, tevent_common_immediate_destructor);
-
-	tevent_debug(ev, TEVENT_DEBUG_TRACE,
-		     "Schedule immediate event \"%s\": %p\n",
-		     handler_name, im);
-}
-
-/*
-  trigger the first immediate event and return true
-  if no event was triggered return false
-*/
-bool tevent_common_loop_immediate(struct tevent_context *ev)
-{
-	struct tevent_immediate *im = ev->immediate_events;
-	tevent_immediate_handler_t handler;
-	void *private_data;
-
-	if (!im) {
-		return false;
-	}
-
-	tevent_debug(ev, TEVENT_DEBUG_TRACE,
-		     "Run immediate event \"%s\": %p\n",
-		     im->handler_name, im);
-
-	/*
-	 * remember the handler and then clear the event
-	 * the handler might reschedule the event
-	 */
-	handler = im->handler;
-	private_data = im->private_data;
-
-	DLIST_REMOVE(im->event_ctx->immediate_events, im);
-	im->event_ctx		= NULL;
-	im->handler		= NULL;
-	im->private_data	= NULL;
-	im->handler_name	= NULL;
-	im->schedule_location	= NULL;
-	im->cancel_fn		= NULL;
-	im->additional_data	= NULL;
-
-	talloc_set_destructor(im, NULL);
-
-	handler(ev, im, private_data);
-
-	return true;
-}
diff --git a/lib/tevent/tevent_internal.h b/lib/tevent/tevent_internal.h
deleted file mode 100644
index 21b5aea..0000000
--- a/lib/tevent/tevent_internal.h
+++ /dev/null
@@ -1,323 +0,0 @@
-/*
-   Unix SMB/CIFS implementation.
-
-   generalised event loop handling
-
-   INTERNAL STRUCTS. THERE ARE NO API GUARANTEES.
-   External users should only ever have to include this header when
-   implementing new tevent backends.
-
-   Copyright (C) Stefan Metzmacher 2005-2009
-
-     ** NOTE! The following LGPL license applies to the tevent
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-
-struct tevent_req {
-	/**
-	 * @brief What to do on completion
-	 *
-	 * This is used for the user of an async request, fn is called when
-	 * the request completes, either successfully or with an error.
-	 */
-	struct {
-		/**
-		 * @brief Completion function
-		 * Completion function, to be filled by the API user
-		 */
-		tevent_req_fn fn;
-		/**
-		 * @brief Private data for the completion function
-		 */
-		void *private_data;
-	} async;
-
-	/**
-	 * @brief Private state pointer for the actual implementation
-	 *
-	 * The implementation doing the work for the async request needs to
-	 * keep around current data like for example a fd event. The user of
-	 * an async request should not touch this.
-	 */
-	void *data;
-
-	/**
-	 * @brief A function to overwrite the default print function
-	 *
-	 * The implementation doing the work may want to implement a
-	 * custom function to print the text representation of the async
-	 * request.
-	 */
-	tevent_req_print_fn private_print;
-
-	/**
-	 * @brief A function to cancel the request
-	 *
-	 * The implementation might want to set a function
-	 * that is called when the tevent_req_cancel() function
-	 * was called.
-	 */
-	tevent_req_cancel_fn private_cancel;
-
-	/**
-	 * @brief Internal state of the request
-	 *
-	 * Callers should only access this via functions and never directly.
-	 */
-	struct {
-		/**
-		 * @brief The talloc type of the data pointer
-		 *
-		 * This is filled by the tevent_req_create() macro.
-		 *
-		 * This for debugging only.
-		 */
-		const char *private_type;
-
-		/**
-		 * @brief The location where the request was created
-		 *
-		 * This uses the __location__ macro via the tevent_req_create()
-		 * macro.
-		 *
-		 * This for debugging only.
-		 */
-		const char *create_location;
-
-		/**
-		 * @brief The location where the request was finished
-		 *
-		 * This uses the __location__ macro via the tevent_req_done(),
-		 * tevent_req_error() or tevent_req_nomem() macro.
-		 *
-		 * This for debugging only.
-		 */
-		const char *finish_location;
-
-		/**
-		 * @brief The location where the request was canceled
-		 *
-		 * This uses the __location__ macro via the
-		 * tevent_req_cancel() macro.
-		 *
-		 * This for debugging only.
-		 */
-		const char *cancel_location;
-
-		/**
-		 * @brief The external state - will be queried by the caller
-		 *
-		 * While the async request is being processed, state will remain in
-		 * TEVENT_REQ_IN_PROGRESS. A request is finished if
-		 * req->state>=TEVENT_REQ_DONE.
-		 */
-		enum tevent_req_state state;
-
-		/**
-		 * @brief status code when finished
-		 *
-		 * This status can be queried in the async completion function. It
-		 * will be set to 0 when everything went fine.
-		 */
-		uint64_t error;
-
-		/**
-		 * @brief the immediate event used by tevent_req_post
-		 *
-		 */
-		struct tevent_immediate *trigger;
-
-		/**
-		 * @brief An event context which will be used to
-		 *        defer the _tevent_req_notify_callback().
-		 */
-		struct tevent_context *defer_callback_ev;
-
-		/**
-		 * @brief the timer event if tevent_req_set_endtime was used
-		 *
-		 */
-		struct tevent_timer *timer;
-	} internal;
-};
-
-struct tevent_fd {
-	struct tevent_fd *prev, *next;
-	struct tevent_context *event_ctx;
-	int fd;
-	uint16_t flags; /* see TEVENT_FD_* flags */
-	tevent_fd_handler_t handler;
-	tevent_fd_close_fn_t close_fn;
-	/* this is private for the specific handler */
-	void *private_data;
-	/* this is for debugging only! */
-	const char *handler_name;
-	const char *location;
-	/* this is private for the events_ops implementation */
-	uint64_t additional_flags;
-	void *additional_data;
-};
-
-struct tevent_timer {
-	struct tevent_timer *prev, *next;
-	struct tevent_context *event_ctx;
-	struct timeval next_event;
-	tevent_timer_handler_t handler;
-	/* this is private for the specific handler */
-	void *private_data;
-	/* this is for debugging only! */
-	const char *handler_name;
-	const char *location;
-	/* this is private for the events_ops implementation */
-	void *additional_data;
-};
-
-struct tevent_immediate {
-	struct tevent_immediate *prev, *next;
-	struct tevent_context *event_ctx;
-	tevent_immediate_handler_t handler;
-	/* this is private for the specific handler */
-	void *private_data;
-	/* this is for debugging only! */
-	const char *handler_name;
-	const char *create_location;
-	const char *schedule_location;
-	/* this is private for the events_ops implementation */
-	void (*cancel_fn)(struct tevent_immediate *im);
-	void *additional_data;
-};
-
-struct tevent_signal {
-	struct tevent_signal *prev, *next;
-	struct tevent_context *event_ctx;
-	int signum;
-	int sa_flags;
-	tevent_signal_handler_t handler;
-	/* this is private for the specific handler */
-	void *private_data;
-	/* this is for debugging only! */
-	const char *handler_name;
-	const char *location;
-	/* this is private for the events_ops implementation */
-	void *additional_data;
-};
-
-struct tevent_debug_ops {
-	void (*debug)(void *context, enum tevent_debug_level level,
-		      const char *fmt, va_list ap) PRINTF_ATTRIBUTE(3,0);
-	void *context;
-};
-
-void tevent_debug(struct tevent_context *ev, enum tevent_debug_level level,
-		  const char *fmt, ...) PRINTF_ATTRIBUTE(3,4);
-
-struct tevent_context {
-	/* the specific events implementation */
-	const struct tevent_ops *ops;
-
-	/* list of fd events - used by common code */
-	struct tevent_fd *fd_events;
-
-	/* list of timed events - used by common code */
-	struct tevent_timer *timer_events;
-
-	/* list of immediate events - used by common code */
-	struct tevent_immediate *immediate_events;
-
-	/* list of signal events - used by common code */
-	struct tevent_signal *signal_events;
-
-	/* this is private for the events_ops implementation */
-	void *additional_data;
-
-	/* pipe hack used with signal handlers */
-	struct tevent_fd *pipe_fde;
-	int pipe_fds[2];
-
-	/* debugging operations */
-	struct tevent_debug_ops debug_ops;
-
-	/* info about the nesting status */
-	struct {
-		bool allowed;
-		uint32_t level;
-		tevent_nesting_hook hook_fn;
-		void *hook_private;
-	} nesting;
-
-	struct {
-		tevent_trace_callback_t callback;
-		void *private_data;
-	} tracing;
-};
-
-
-int tevent_common_context_destructor(struct tevent_context *ev);
-int tevent_common_loop_wait(struct tevent_context *ev,
-			    const char *location);
-
-int tevent_common_fd_destructor(struct tevent_fd *fde);
-struct tevent_fd *tevent_common_add_fd(struct tevent_context *ev,
-				       TALLOC_CTX *mem_ctx,
-				       int fd,
-				       uint16_t flags,
-				       tevent_fd_handler_t handler,
-				       void *private_data,
-				       const char *handler_name,
-				       const char *location);
-void tevent_common_fd_set_close_fn(struct tevent_fd *fde,
-				   tevent_fd_close_fn_t close_fn);
-uint16_t tevent_common_fd_get_flags(struct tevent_fd *fde);
-void tevent_common_fd_set_flags(struct tevent_fd *fde, uint16_t flags);
-
-struct tevent_timer *tevent_common_add_timer(struct tevent_context *ev,
-					     TALLOC_CTX *mem_ctx,
-					     struct timeval next_event,
-					     tevent_timer_handler_t handler,
-					     void *private_data,
-					     const char *handler_name,
-					     const char *location);
-struct timeval tevent_common_loop_timer_delay(struct tevent_context *);
-
-void tevent_common_schedule_immediate(struct tevent_immediate *im,
-				      struct tevent_context *ev,
-				      tevent_immediate_handler_t handler,
-				      void *private_data,
-				      const char *handler_name,
-				      const char *location);
-bool tevent_common_loop_immediate(struct tevent_context *ev);
-
-struct tevent_signal *tevent_common_add_signal(struct tevent_context *ev,
-					       TALLOC_CTX *mem_ctx,
-					       int signum,
-					       int sa_flags,
-					       tevent_signal_handler_t handler,
-					       void *private_data,
-					       const char *handler_name,
-					       const char *location);
-int tevent_common_check_signal(struct tevent_context *ev);
-void tevent_cleanup_pending_signal_handlers(struct tevent_signal *se);
-
-bool tevent_standard_init(void);
-bool tevent_select_init(void);
-bool tevent_poll_init(void);
-#ifdef HAVE_EPOLL
-bool tevent_epoll_init(void);
-#endif
-
-void tevent_trace_point_callback(struct tevent_context *ev,
-				 enum tevent_trace_point);
diff --git a/lib/tevent/tevent_liboop.c b/lib/tevent/tevent_liboop.c
deleted file mode 100644
index c8af5ab..0000000
--- a/lib/tevent/tevent_liboop.c
+++ /dev/null
@@ -1,292 +0,0 @@
-/*
-   Unix SMB/CIFS implementation.
-   main select loop and event handling
-   wrapper for http://liboop.org/
-
-   Copyright (C) Stefan Metzmacher 2005
-
-     ** NOTE! The following LGPL license applies to the tevent
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-
-#include "events.h"
-#include "events_internal.h"
-
-#include <oop.h>
-
-/*
- !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
-
- NOTE: this code compiles fine, but is completely *UNTESTED*
-       and is only committed as an example
-
- !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
-*/
-
-static int oop_event_context_destructor(struct tevent_context *ev)
-{
-	oop_source_sys *oop_sys = ev->additional_data;
-
-	oop_sys_delete(oop_sys);
-
-	return 0;
-}
-
-/*
-  create a oop_event_context structure.
-*/
-static int oop_event_context_init(struct tevent_context *ev, void *private_data)
-{
-	oop_source_sys *oop_sys = private_data;
-
-	if (!oop_sys) {
-		oop_sys = oop_sys_new();
-		if (!oop_sys) {
-			return -1;
-		}
-
-		talloc_set_destructor(ev, oop_event_context_destructor);
-	}
-
-	ev->additional_data = oop_sys;
-
-	return 0;
-}
-
-static void *oop_event_fd_handler(oop_source *oop, int fd, oop_event oop_type, void *ptr)
-{
-	struct tevent_fd *fde = ptr;
-
-	if (fd != fde->fd) return OOP_ERROR;
-
-	switch(oop_type) {
-		case OOP_READ:
-			fde->handler(fde->event_ctx, fde, EVENT_FD_READ, fde->private_data);
-			return OOP_CONTINUE;
-		case OOP_WRITE:
-			fde->handler(fde->event_ctx, fde, EVENT_FD_WRITE, fde->private_data);
-			return OOP_CONTINUE;
-		case OOP_EXCEPTION:
-			return OOP_ERROR;
-		case OOP_NUM_EVENTS:
-			return OOP_ERROR;
-	}
-
-	return OOP_ERROR;
-}
-
-/*
-  destroy an fd_event
-*/
-static int oop_event_fd_destructor(struct tevent_fd *fde)
-{
-	struct tevent_context *ev = fde->event_ctx;
-	oop_source_sys *oop_sys = ev->additional_data;
-	oop_source *oop = oop_sys_source(oop_sys);
-
-	if (fde->flags & EVENT_FD_READ)
-		oop->cancel_fd(oop, fde->fd, OOP_READ);
-	if (fde->flags & EVENT_FD_WRITE)
-		oop->cancel_fd(oop, fde->fd, OOP_WRITE);
-
-	if (fde->flags & EVENT_FD_AUTOCLOSE) {
-		close(fde->fd);
-		fde->fd = -1;
-	}
-
-	return 0;
-}
-
-/*
-  add a fd based event
-  return NULL on failure (memory allocation error)
-*/
-static struct tevent_fd *oop_event_add_fd(struct tevent_context *ev, TALLOC_CTX *mem_ctx,
-					 int fd, uint16_t flags,
-					 event_fd_handler_t handler,
-					 void *private_data)
-{
-	struct tevent_fd *fde;
-	oop_source_sys *oop_sys = ev->additional_data;
-	oop_source *oop = oop_sys_source(oop_sys);
-
-	fde = talloc(mem_ctx?mem_ctx:ev, struct tevent_fd);
-	if (!fde) return NULL;
-
-	fde->event_ctx		= ev;
-	fde->fd			= fd;
-	fde->flags		= flags;
-	fde->handler		= handler;
-	fde->private_data	= private_data;
-	fde->additional_flags	= 0;
-	fde->additional_data	= NULL;
-
-	if (fde->flags & EVENT_FD_READ)
-		oop->on_fd(oop, fde->fd, OOP_READ, oop_event_fd_handler, fde);
-	if (fde->flags & EVENT_FD_WRITE)
-		oop->on_fd(oop, fde->fd, OOP_WRITE, oop_event_fd_handler, fde);
-
-	talloc_set_destructor(fde, oop_event_fd_destructor);
-
-	return fde;
-}
-
-/*
-  return the fd event flags
-*/
-static uint16_t oop_event_get_fd_flags(struct tevent_fd *fde)
-{
-	return fde->flags;
-}
-
-/*
-  set the fd event flags
-*/
-static void oop_event_set_fd_flags(struct tevent_fd *fde, uint16_t flags)
-{
-	oop_source_sys *oop_sys;
-	oop_source *oop;
-
-	oop_sys = fde->event_ctx->additional_data;
-	oop = oop_sys_source(oop_sys);
-
-	if ((fde->flags & EVENT_FD_READ)&&(!(flags & EVENT_FD_READ)))
-		oop->cancel_fd(oop, fde->fd, OOP_READ);
-
-	if ((!(fde->flags & EVENT_FD_READ))&&(flags & EVENT_FD_READ))
-		oop->on_fd(oop, fde->fd, OOP_READ, oop_event_fd_handler, fde);
-
-	if ((fde->flags & EVENT_FD_WRITE)&&(!(flags & EVENT_FD_WRITE)))
-		oop->cancel_fd(oop, fde->fd, OOP_WRITE);
-
-	if ((!(fde->flags & EVENT_FD_WRITE))&&(flags & EVENT_FD_WRITE))
-		oop->on_fd(oop, fde->fd, OOP_WRITE, oop_event_fd_handler, fde);
-
-	fde->flags = flags;
-}
-
-static int oop_event_timed_destructor(struct tevent_timer *te);
-
-static int oop_event_timed_deny_destructor(struct tevent_timer *te)
-{
-	return -1;
-}
-
-static void *oop_event_timed_handler(oop_source *oop, struct timeval t, void *ptr)
-{
-	struct tevent_timer *te = ptr;
-
-	/* deny the handler to free the event */
-	talloc_set_destructor(te, oop_event_timed_deny_destructor);
-	te->handler(te->event_ctx, te, t, te->private_data);
-
-	talloc_set_destructor(te, oop_event_timed_destructor);
-	talloc_free(te);
-
-	return OOP_CONTINUE;
-}
-
-/*
-  destroy a timed event
-*/
-static int oop_event_timed_destructor(struct tevent_timer *te)
-{
-	struct tevent_context *ev = te->event_ctx;
-	oop_source_sys *oop_sys = ev->additional_data;
-	oop_source *oop = oop_sys_source(oop_sys);
-
-	oop->cancel_time(oop, te->next_event, oop_event_timed_handler, te);
-
-	return 0;
-}
-
-/*
-  add a timed event
-  return NULL on failure (memory allocation error)
-*/
-static struct tevent_timer *oop_event_add_timed(struct tevent_context *ev, TALLOC_CTX *mem_ctx,
-					       struct timeval next_event,
-					       event_timed_handler_t handler,
-					       void *private_data)
-{
-	oop_source_sys *oop_sys = ev->additional_data;
-	oop_source *oop = oop_sys_source(oop_sys);
-	struct tevent_timer *te;
-
-	te = talloc(mem_ctx?mem_ctx:ev, struct tevent_timer);
-	if (te == NULL) return NULL;
-
-	te->event_ctx		= ev;
-	te->next_event		= next_event;
-	te->handler		= handler;
-	te->private_data	= private_data;
-	te->additional_data	= NULL;
-
-	oop->on_time(oop, te->next_event, oop_event_timed_handler, te);
-
-	talloc_set_destructor(te, oop_event_timed_destructor);
-
-	return te;
-}
-
-/*
-  do a single event loop using the events defined in ev
-*/
-static int oop_event_loop_once(struct tevent_context *ev)
-{
-	void *oop_ret;
-	oop_source_sys *oop_sys = ev->additional_data;
-
-	oop_ret = oop_sys_run_once(oop_sys);
-	if (oop_ret == OOP_CONTINUE) {
-		return 0;
-	}
-
-	return -1;
-}
-
-/*
-  return on failure or (with 0) if all fd events are removed
-*/
-static int oop_event_loop_wait(struct tevent_context *ev)
-{
-	void *oop_ret;
-	oop_source_sys *oop_sys = ev->additional_data;
-
-	oop_ret = oop_sys_run(oop_sys);
-	if (oop_ret == OOP_CONTINUE) {
-		return 0;
-	}
-
-	return -1;
-}
-
-static const struct event_ops event_oop_ops = {
-	.context_init	= oop_event_context_init,
-	.add_fd		= oop_event_add_fd,
-	.get_fd_flags	= oop_event_get_fd_flags,
-	.set_fd_flags	= oop_event_set_fd_flags,
-	.add_timer	= oop_event_add_timed,
-	.add_signal	= common_event_add_signal,
-	.loop_once	= oop_event_loop_once,
-	.loop_wait	= oop_event_loop_wait,
-};
-
-const struct event_ops *event_liboop_get_ops(void)
-{
-	return &event_oop_ops;
-}
diff --git a/lib/tevent/tevent_poll.c b/lib/tevent/tevent_poll.c
deleted file mode 100644
index 7ae3c42..0000000
--- a/lib/tevent/tevent_poll.c
+++ /dev/null
@@ -1,318 +0,0 @@
-/*
-   Unix SMB/CIFS implementation.
-   main select loop and event handling
-   Copyright (C) Andrew Tridgell	2003-2005
-   Copyright (C) Stefan Metzmacher	2005-2009
-
-     ** NOTE! The following LGPL license applies to the tevent
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-
-#include "replace.h"
-#include "system/filesys.h"
-#include "system/select.h"
-#include "tevent.h"
-#include "tevent_util.h"
-#include "tevent_internal.h"
-
-struct poll_event_context {
-	/* a pointer back to the generic event_context */
-	struct tevent_context *ev;
-
-	/*
-	 * These two arrays are maintained together.
-	 */
-	struct pollfd *fds;
-	struct tevent_fd **fd_events;
-	uint64_t num_fds;
-
-	/* information for exiting from the event loop */
-	int exit_code;
-};
-
-/*
-  create a select_event_context structure.
-*/
-static int poll_event_context_init(struct tevent_context *ev)
-{
-	struct poll_event_context *poll_ev;
-
-	poll_ev = talloc_zero(ev, struct poll_event_context);
-	if (poll_ev == NULL) {
-		return -1;
-	}
-	poll_ev->ev = ev;
-	ev->additional_data = poll_ev;
-	return 0;
-}
-
-/*
-  destroy an fd_event
-*/
-static int poll_event_fd_destructor(struct tevent_fd *fde)
-{
-	struct tevent_context *ev = fde->event_ctx;
-	struct poll_event_context *poll_ev = NULL;
-	struct tevent_fd *moved_fde;
-	uint64_t del_idx = fde->additional_flags;
-
-	if (ev == NULL) {
-		goto done;
-	}
-
-	poll_ev = talloc_get_type_abort(
-		ev->additional_data, struct poll_event_context);
-
-	moved_fde = poll_ev->fd_events[poll_ev->num_fds-1];
-	poll_ev->fd_events[del_idx] = moved_fde;
-	poll_ev->fds[del_idx] = poll_ev->fds[poll_ev->num_fds-1];
-	moved_fde->additional_flags = del_idx;
-
-	poll_ev->num_fds -= 1;
-done:
-	return tevent_common_fd_destructor(fde);
-}
-
-/*
-  add a fd based event
-  return NULL on failure (memory allocation error)
-*/
-static struct tevent_fd *poll_event_add_fd(struct tevent_context *ev,
-					   TALLOC_CTX *mem_ctx,
-					   int fd, uint16_t flags,
-					   tevent_fd_handler_t handler,
-					   void *private_data,
-					   const char *handler_name,
-					   const char *location)
-{
-	struct poll_event_context *poll_ev = talloc_get_type_abort(
-		ev->additional_data, struct poll_event_context);
-	struct pollfd *pfd;
-	struct tevent_fd *fde;
-
-	fde = tevent_common_add_fd(ev, mem_ctx, fd, flags,
-				   handler, private_data,
-				   handler_name, location);
-	if (fde == NULL) {
-		return NULL;
-	}
-
-	/* we allocate 16 slots to avoid a lot of reallocations */
-	if (talloc_array_length(poll_ev->fds) == poll_ev->num_fds) {
-		struct pollfd *tmp_fds;
-		struct tevent_fd **tmp_fd_events;
-		tmp_fds = talloc_realloc(
-			poll_ev, poll_ev->fds, struct pollfd,
-			poll_ev->num_fds + 16);
-		if (tmp_fds == NULL) {
-			TALLOC_FREE(fde);
-			return NULL;
-		}
-		poll_ev->fds = tmp_fds;
-
-		tmp_fd_events = talloc_realloc(
-			poll_ev, poll_ev->fd_events, struct tevent_fd *,
-			poll_ev->num_fds + 16);
-		if (tmp_fd_events == NULL) {
-			TALLOC_FREE(fde);
-			return NULL;
-		}
-		poll_ev->fd_events = tmp_fd_events;
-	}
-
-	pfd = &poll_ev->fds[poll_ev->num_fds];
-
-	pfd->fd = fd;
-
-	pfd->events = 0;
-	pfd->revents = 0;
-
-	if (flags & TEVENT_FD_READ) {
-		pfd->events |= (POLLIN|POLLHUP);
-	}
-	if (flags & TEVENT_FD_WRITE) {
-		pfd->events |= (POLLOUT);
-	}
-
-	fde->additional_flags = poll_ev->num_fds;
-	poll_ev->fd_events[poll_ev->num_fds] = fde;
-
-	poll_ev->num_fds += 1;
-
-	talloc_set_destructor(fde, poll_event_fd_destructor);
-
-	return fde;
-}
-
-/*
-  set the fd event flags
-*/
-static void poll_event_set_fd_flags(struct tevent_fd *fde, uint16_t flags)
-{
-	struct poll_event_context *poll_ev = talloc_get_type_abort(
-		fde->event_ctx->additional_data, struct poll_event_context);
-	uint64_t idx = fde->additional_flags;
-	uint16_t pollflags = 0;
-
-	if (flags & TEVENT_FD_READ) {
-		pollflags |= (POLLIN|POLLHUP);
-	}
-	if (flags & TEVENT_FD_WRITE) {
-		pollflags |= (POLLOUT);
-	}
-
-	poll_ev->fds[idx].events = pollflags;
-
-	fde->flags = flags;
-}
-
-/*
-  event loop handling using poll()
-*/
-static int poll_event_loop_poll(struct tevent_context *ev,
-				struct timeval *tvalp)
-{
-	struct poll_event_context *poll_ev = talloc_get_type_abort(
-		ev->additional_data, struct poll_event_context);
-	struct tevent_fd *fde;
-	int pollrtn;
-	int timeout = -1;
-
-	if (ev->signal_events && tevent_common_check_signal(ev)) {
-		return 0;
-	}
-
-	if (tvalp != NULL) {
-		timeout = tvalp->tv_sec * 1000;
-		timeout += (tvalp->tv_usec + 999) / 1000;
-	}
-
-	tevent_trace_point_callback(poll_ev->ev, TEVENT_TRACE_BEFORE_WAIT);
-	pollrtn = poll(poll_ev->fds, poll_ev->num_fds, timeout);
-	tevent_trace_point_callback(poll_ev->ev, TEVENT_TRACE_AFTER_WAIT);
-
-	if (pollrtn == -1 && errno == EINTR && ev->signal_events) {
-		tevent_common_check_signal(ev);
-		return 0;
-	}
-
-	if (pollrtn == -1 && errno == EBADF) {
-		/* the socket is dead! this should never
-		   happen as the socket should have first been
-		   made readable and that should have removed
-		   the event, so this must be a bug. This is a
-		   fatal error. */
-		tevent_debug(ev, TEVENT_DEBUG_FATAL,
-			     "ERROR: EBADF on poll_event_loop_once\n");
-		poll_ev->exit_code = EBADF;
-		return -1;
-	}
-
-	if (pollrtn == 0 && tvalp) {
-		/* we don't care about a possible delay here */
-		tevent_common_loop_timer_delay(ev);
-		return 0;
-	}
-
-	if (pollrtn <= 0) {
-		/*
-		 * No fd's ready
-		 */
-		return 0;
-	}
-
-	/* at least one file descriptor is ready - check
-	   which ones and call the handler, being careful to allow
-	   the handler to remove itself when called */
-
-	for (fde = ev->fd_events; fde; fde = fde->next) {
-		struct pollfd *pfd;
-		uint64_t pfd_idx = fde->additional_flags;
-		uint16_t flags = 0;
-
-		pfd = &poll_ev->fds[pfd_idx];
-
-		if (pfd->revents & (POLLHUP|POLLERR)) {
-			/* If we only wait for TEVENT_FD_WRITE, we
-			   should not tell the event handler about it,
-			   and remove the writable flag, as we only
-			   report errors when waiting for read events
-			   to match the select behavior. */
-			if (!(fde->flags & TEVENT_FD_READ)) {
-				TEVENT_FD_NOT_WRITEABLE(fde);
-				continue;
-			}
-			flags |= TEVENT_FD_READ;
-		}
-		if (pfd->revents & POLLIN) {
-			flags |= TEVENT_FD_READ;
-		}
-		if (pfd->revents & POLLOUT) {
-			flags |= TEVENT_FD_WRITE;
-		}
-		if (flags != 0) {
-			fde->handler(ev, fde, flags, fde->private_data);
-			break;
-		}
-	}
-
-	return 0;
-}
-
-/*
-  do a single event loop using the events defined in ev
-*/
-static int poll_event_loop_once(struct tevent_context *ev,
-				const char *location)
-{
-	struct timeval tval;
-
-	if (ev->signal_events &&
-	    tevent_common_check_signal(ev)) {
-		return 0;
-	}
-
-	if (ev->immediate_events &&
-	    tevent_common_loop_immediate(ev)) {
-		return 0;
-	}
-
-	tval = tevent_common_loop_timer_delay(ev);
-	if (tevent_timeval_is_zero(&tval)) {
-		return 0;
-	}
-
-	return poll_event_loop_poll(ev, &tval);
-}
-
-static const struct tevent_ops poll_event_ops = {
-	.context_init		= poll_event_context_init,
-	.add_fd			= poll_event_add_fd,
-	.set_fd_close_fn	= tevent_common_fd_set_close_fn,
-	.get_fd_flags		= tevent_common_fd_get_flags,
-	.set_fd_flags		= poll_event_set_fd_flags,
-	.add_timer		= tevent_common_add_timer,
-	.schedule_immediate	= tevent_common_schedule_immediate,
-	.add_signal		= tevent_common_add_signal,
-	.loop_once		= poll_event_loop_once,
-	.loop_wait		= tevent_common_loop_wait,
-};
-
-_PRIVATE_ bool tevent_poll_init(void)
-{
-	return tevent_register_backend("poll", &poll_event_ops);
-}
diff --git a/lib/tevent/tevent_queue.c b/lib/tevent/tevent_queue.c
deleted file mode 100644
index 4750675..0000000
--- a/lib/tevent/tevent_queue.c
+++ /dev/null
@@ -1,300 +0,0 @@
-/*
-   Unix SMB/CIFS implementation.
-   Infrastructure for async requests
-   Copyright (C) Volker Lendecke 2008
-   Copyright (C) Stefan Metzmacher 2009
-
-     ** NOTE! The following LGPL license applies to the tevent
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-
-#include "replace.h"
-#include "tevent.h"
-#include "tevent_internal.h"
-#include "tevent_util.h"
-
-struct tevent_queue_entry {
-	struct tevent_queue_entry *prev, *next;
-	struct tevent_queue *queue;
-
-	bool triggered;
-
-	struct tevent_req *req;
-	struct tevent_context *ev;
-
-	tevent_queue_trigger_fn_t trigger;
-	void *private_data;
-};
-
-struct tevent_queue {
-	const char *name;
-	const char *location;
-
-	bool running;
-	struct tevent_immediate *immediate;
-
-	size_t length;
-	struct tevent_queue_entry *list;
-};
-
-static void tevent_queue_immediate_trigger(struct tevent_context *ev,
-					   struct tevent_immediate *im,
-					   void *private_data);
-
-static int tevent_queue_entry_destructor(struct tevent_queue_entry *e)
-{
-	struct tevent_queue *q = e->queue;
-
-	if (!q) {
-		return 0;
-	}
-
-	DLIST_REMOVE(q->list, e);
-	q->length--;
-
-	if (!q->running) {
-		return 0;
-	}
-
-	if (!q->list) {
-		return 0;
-	}
-
-	if (q->list->triggered) {
-		return 0;
-	}
-
-	tevent_schedule_immediate(q->immediate,
-				  q->list->ev,
-				  tevent_queue_immediate_trigger,
-				  q);
-
-	return 0;
-}
-
-static int tevent_queue_destructor(struct tevent_queue *q)
-{
-	q->running = false;
-
-	while (q->list) {
-		struct tevent_queue_entry *e = q->list;
-		talloc_free(e);
-	}
-
-	return 0;
-}
-
-struct tevent_queue *_tevent_queue_create(TALLOC_CTX *mem_ctx,
-					  const char *name,
-					  const char *location)
-{
-	struct tevent_queue *queue;
-
-	queue = talloc_zero(mem_ctx, struct tevent_queue);
-	if (!queue) {
-		return NULL;
-	}
-
-	queue->name = talloc_strdup(queue, name);
-	if (!queue->name) {
-		talloc_free(queue);
-		return NULL;
-	}
-	queue->immediate = tevent_create_immediate(queue);
-	if (!queue->immediate) {
-		talloc_free(queue);
-		return NULL;
-	}
-
-	queue->location = location;
-
-	/* queue is running by default */
-	queue->running = true;
-
-	talloc_set_destructor(queue, tevent_queue_destructor);
-	return queue;
-}
-
-static void tevent_queue_immediate_trigger(struct tevent_context *ev,
-					   struct tevent_immediate *im,
-					   void *private_data)
-{
-	struct tevent_queue *q = talloc_get_type(private_data,
-				  struct tevent_queue);
-
-	if (!q->running) {
-		return;
-	}
-
-	q->list->triggered = true;
-	q->list->trigger(q->list->req, q->list->private_data);
-}
-
-static struct tevent_queue_entry *tevent_queue_add_internal(
-					struct tevent_queue *queue,
-					struct tevent_context *ev,
-					struct tevent_req *req,
-					tevent_queue_trigger_fn_t trigger,
-					void *private_data,
-					bool allow_direct)
-{
-	struct tevent_queue_entry *e;
-
-	e = talloc_zero(req, struct tevent_queue_entry);
-	if (e == NULL) {
-		return NULL;
-	}
-
-	e->queue = queue;
-	e->req = req;
-	e->ev = ev;
-	e->trigger = trigger;
-	e->private_data = private_data;
-
-	/*
-	 * if there is no trigger, it is just a blocker
-	 */
-	if (trigger == NULL) {
-		e->triggered = true;
-	}
-
-	if (queue->length > 0) {
-		/*
-		 * if there are already entries in the
-		 * queue do not optimize.
-		 */
-		allow_direct = false;
-	}
-
-	if (req->async.fn != NULL) {
-		/*
-		 * If the callers wants to optimize for the
-		 * empty queue case, call the trigger only
-		 * if there is no callback defined for the
-		 * request yet.
-		 */
-		allow_direct = false;
-	}
-
-	DLIST_ADD_END(queue->list, e, struct tevent_queue_entry *);
-	queue->length++;
-	talloc_set_destructor(e, tevent_queue_entry_destructor);
-
-	if (!queue->running) {
-		return e;
-	}
-
-	if (queue->list->triggered) {
-		return e;
-	}
-
-	/*
-	 * If allowed we directly call the trigger
-	 * avoiding possible delays caused by
-	 * an immediate event.
-	 */
-	if (allow_direct) {
-		queue->list->triggered = true;
-		queue->list->trigger(queue->list->req,
-				     queue->list->private_data);
-		return e;
-	}
-
-	tevent_schedule_immediate(queue->immediate,
-				  queue->list->ev,
-				  tevent_queue_immediate_trigger,
-				  queue);
-
-	return e;
-}
-
-bool tevent_queue_add(struct tevent_queue *queue,
-		      struct tevent_context *ev,
-		      struct tevent_req *req,
-		      tevent_queue_trigger_fn_t trigger,
-		      void *private_data)
-{
-	struct tevent_queue_entry *e;
-
-	e = tevent_queue_add_internal(queue, ev, req,
-				      trigger, private_data, false);
-	if (e == NULL) {
-		return false;
-	}
-
-	return true;
-}
-
-struct tevent_queue_entry *tevent_queue_add_entry(
-					struct tevent_queue *queue,
-					struct tevent_context *ev,
-					struct tevent_req *req,
-					tevent_queue_trigger_fn_t trigger,
-					void *private_data)
-{
-	return tevent_queue_add_internal(queue, ev, req,
-					 trigger, private_data, false);
-}
-
-struct tevent_queue_entry *tevent_queue_add_optimize_empty(
-					struct tevent_queue *queue,
-					struct tevent_context *ev,
-					struct tevent_req *req,
-					tevent_queue_trigger_fn_t trigger,
-					void *private_data)
-{
-	return tevent_queue_add_internal(queue, ev, req,
-					 trigger, private_data, true);
-}
-
-void tevent_queue_start(struct tevent_queue *queue)
-{
-	if (queue->running) {
-		/* already started */
-		return;
-	}
-
-	queue->running = true;
-
-	if (!queue->list) {
-		return;
-	}
-
-	if (queue->list->triggered) {
-		return;
-	}
-
-	tevent_schedule_immediate(queue->immediate,
-				  queue->list->ev,
-				  tevent_queue_immediate_trigger,
-				  queue);
-}
-
-void tevent_queue_stop(struct tevent_queue *queue)
-{
-	queue->running = false;
-}
-
-size_t tevent_queue_length(struct tevent_queue *queue)
-{
-	return queue->length;
-}
-
-bool tevent_queue_running(struct tevent_queue *queue)
-{
-	return queue->running;
-}
diff --git a/lib/tevent/tevent_req.c b/lib/tevent/tevent_req.c
deleted file mode 100644
index d8d0c5f..0000000
--- a/lib/tevent/tevent_req.c
+++ /dev/null
@@ -1,294 +0,0 @@
-/*
-   Unix SMB/CIFS implementation.
-   Infrastructure for async requests
-   Copyright (C) Volker Lendecke 2008
-   Copyright (C) Stefan Metzmacher 2009
-
-     ** NOTE! The following LGPL license applies to the tevent
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-
-#include "replace.h"
-#include "tevent.h"
-#include "tevent_internal.h"
-#include "tevent_util.h"
-
-char *tevent_req_default_print(struct tevent_req *req, TALLOC_CTX *mem_ctx)
-{
-	return talloc_asprintf(mem_ctx,
-			       "tevent_req[%p/%s]: state[%d] error[%lld (0x%llX)] "
-			       " state[%s (%p)] timer[%p]",
-			       req, req->internal.create_location,
-			       req->internal.state,
-			       (unsigned long long)req->internal.error,
-			       (unsigned long long)req->internal.error,
-			       talloc_get_name(req->data),
-			       req->data,
-			       req->internal.timer
-			       );
-}
-
-char *tevent_req_print(TALLOC_CTX *mem_ctx, struct tevent_req *req)
-{
-	if (!req->private_print) {
-		return tevent_req_default_print(req, mem_ctx);
-	}
-
-	return req->private_print(req, mem_ctx);
-}
-
-struct tevent_req *_tevent_req_create(TALLOC_CTX *mem_ctx,
-				    void *pdata,
-				    size_t data_size,
-				    const char *type,
-				    const char *location)
-{
-	struct tevent_req *req;
-	void **ppdata = (void **)pdata;
-	void *data;
-
-	req = talloc_zero(mem_ctx, struct tevent_req);
-	if (req == NULL) {
-		return NULL;
-	}
-	req->internal.private_type	= type;
-	req->internal.create_location	= location;
-	req->internal.finish_location	= NULL;
-	req->internal.state		= TEVENT_REQ_IN_PROGRESS;
-	req->internal.trigger		= tevent_create_immediate(req);
-	if (!req->internal.trigger) {
-		talloc_free(req);
-		return NULL;
-	}
-	req->internal.defer_callback_ev	= NULL;
-
-	data = talloc_zero_size(req, data_size);
-	if (data == NULL) {
-		talloc_free(req);
-		return NULL;
-	}
-	talloc_set_name_const(data, type);
-
-	req->data = data;
-
-	*ppdata = data;
-	return req;
-}
-
-void _tevent_req_notify_callback(struct tevent_req *req, const char *location)
-{
-	req->internal.finish_location = location;
-	if (req->internal.defer_callback_ev) {
-		(void)tevent_req_post(req, req->internal.defer_callback_ev);
-		req->internal.defer_callback_ev = NULL;
-		return;
-	}
-	if (req->async.fn != NULL) {
-		req->async.fn(req);
-	}
-}
-
-static void tevent_req_finish(struct tevent_req *req,
-			      enum tevent_req_state state,
-			      const char *location)
-{
-	req->internal.state = state;
-	_tevent_req_notify_callback(req, location);
-}
-
-void _tevent_req_done(struct tevent_req *req,
-		      const char *location)
-{
-	tevent_req_finish(req, TEVENT_REQ_DONE, location);
-}
-
-bool _tevent_req_error(struct tevent_req *req,
-		       uint64_t error,
-		       const char *location)
-{
-	if (error == 0) {
-		return false;
-	}
-
-	req->internal.error = error;
-	tevent_req_finish(req, TEVENT_REQ_USER_ERROR, location);
-	return true;
-}
-
-void _tevent_req_oom(struct tevent_req *req, const char *location)
-{
-	tevent_req_finish(req, TEVENT_REQ_NO_MEMORY, location);
-}
-
-bool _tevent_req_nomem(const void *p,
-		       struct tevent_req *req,
-		       const char *location)
-{
-	if (p != NULL) {
-		return false;
-	}
-	_tevent_req_oom(req, location);
-	return true;
-}
-
-/**
- * @internal
- *
- * @brief Immediate event callback.
- *
- * @param[in]  ev       The event context to use.
- *
- * @param[in]  im       The immediate event.
- *
- * @param[in]  priv     The async request to be finished.
- */
-static void tevent_req_trigger(struct tevent_context *ev,
-			       struct tevent_immediate *im,
-			       void *private_data)
-{
-	struct tevent_req *req = talloc_get_type(private_data,
-				 struct tevent_req);
-
-	tevent_req_finish(req, req->internal.state,
-			  req->internal.finish_location);
-}
-
-struct tevent_req *tevent_req_post(struct tevent_req *req,
-				   struct tevent_context *ev)
-{
-	tevent_schedule_immediate(req->internal.trigger,
-				  ev, tevent_req_trigger, req);
-	return req;
-}
-
-void tevent_req_defer_callback(struct tevent_req *req,
-			       struct tevent_context *ev)
-{
-	req->internal.defer_callback_ev = ev;
-}
-
-bool tevent_req_is_in_progress(struct tevent_req *req)
-{
-	if (req->internal.state == TEVENT_REQ_IN_PROGRESS) {
-		return true;
-	}
-
-	return false;
-}
-
-void tevent_req_received(struct tevent_req *req)
-{
-	TALLOC_FREE(req->data);
-	req->private_print = NULL;
-
-	TALLOC_FREE(req->internal.trigger);
-	TALLOC_FREE(req->internal.timer);
-
-	req->internal.state = TEVENT_REQ_RECEIVED;
-}
-
-bool tevent_req_poll(struct tevent_req *req,
-		     struct tevent_context *ev)
-{
-	while (tevent_req_is_in_progress(req)) {
-		int ret;
-
-		ret = tevent_loop_once(ev);
-		if (ret != 0) {
-			return false;
-		}
-	}
-
-	return true;
-}
-
-bool tevent_req_is_error(struct tevent_req *req, enum tevent_req_state *state,
-			uint64_t *error)
-{
-	if (req->internal.state == TEVENT_REQ_DONE) {
-		return false;
-	}
-	if (req->internal.state == TEVENT_REQ_USER_ERROR) {
-		*error = req->internal.error;
-	}
-	*state = req->internal.state;
-	return true;
-}
-
-static void tevent_req_timedout(struct tevent_context *ev,
-			       struct tevent_timer *te,
-			       struct timeval now,
-			       void *private_data)
-{
-	struct tevent_req *req = talloc_get_type(private_data,
-				 struct tevent_req);
-
-	TALLOC_FREE(req->internal.timer);
-
-	tevent_req_finish(req, TEVENT_REQ_TIMED_OUT, __FUNCTION__);
-}
-
-bool tevent_req_set_endtime(struct tevent_req *req,
-			    struct tevent_context *ev,
-			    struct timeval endtime)
-{
-	TALLOC_FREE(req->internal.timer);
-
-	req->internal.timer = tevent_add_timer(ev, req, endtime,
-					       tevent_req_timedout,
-					       req);
-	if (tevent_req_nomem(req->internal.timer, req)) {
-		return false;
-	}
-
-	return true;
-}
-
-void tevent_req_set_callback(struct tevent_req *req, tevent_req_fn fn, void *pvt)
-{
-	req->async.fn = fn;
-	req->async.private_data = pvt;
-}
-
-void *_tevent_req_callback_data(struct tevent_req *req)
-{
-	return req->async.private_data;
-}
-
-void *_tevent_req_data(struct tevent_req *req)
-{
-	return req->data;
-}
-
-void tevent_req_set_print_fn(struct tevent_req *req, tevent_req_print_fn fn)
-{
-	req->private_print = fn;
-}
-
-void tevent_req_set_cancel_fn(struct tevent_req *req, tevent_req_cancel_fn fn)
-{
-	req->private_cancel = fn;
-}
-
-bool _tevent_req_cancel(struct tevent_req *req, const char *location)
-{
-	if (req->private_cancel == NULL) {
-		return false;
-	}
-
-	return req->private_cancel(req);
-}
diff --git a/lib/tevent/tevent_select.c b/lib/tevent/tevent_select.c
deleted file mode 100644
index 47ad13e..0000000
--- a/lib/tevent/tevent_select.c
+++ /dev/null
@@ -1,260 +0,0 @@
-/*
-   Unix SMB/CIFS implementation.
-   main select loop and event handling
-   Copyright (C) Andrew Tridgell	2003-2005
-   Copyright (C) Stefan Metzmacher	2005-2009
-
-     ** NOTE! The following LGPL license applies to the tevent
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-
-#include "replace.h"
-#include "system/filesys.h"
-#include "system/select.h"
-#include "tevent.h"
-#include "tevent_util.h"
-#include "tevent_internal.h"
-
-struct select_event_context {
-	/* a pointer back to the generic event_context */
-	struct tevent_context *ev;
-
-	/* the maximum file descriptor number in fd_events */
-	int maxfd;
-
-	/* information for exiting from the event loop */
-	int exit_code;
-};
-
-/*
-  create a select_event_context structure.
-*/
-static int select_event_context_init(struct tevent_context *ev)
-{
-	struct select_event_context *select_ev;
-
-	select_ev = talloc_zero(ev, struct select_event_context);
-	if (!select_ev) return -1;
-	select_ev->ev = ev;
-
-	ev->additional_data = select_ev;
-	return 0;
-}
-
-/*
-  recalculate the maxfd
-*/
-static void calc_maxfd(struct select_event_context *select_ev)
-{
-	struct tevent_fd *fde;
-
-	select_ev->maxfd = 0;
-	for (fde = select_ev->ev->fd_events; fde; fde = fde->next) {
-		if (fde->fd > select_ev->maxfd) {
-			select_ev->maxfd = fde->fd;
-		}
-	}
-}
-
-
-/* to mark the ev->maxfd invalid
- * this means we need to recalculate it
- */
-#define EVENT_INVALID_MAXFD (-1)
-
-/*
-  destroy an fd_event
-*/
-static int select_event_fd_destructor(struct tevent_fd *fde)
-{
-	struct tevent_context *ev = fde->event_ctx;
-	struct select_event_context *select_ev = NULL;
-
-	if (ev) {
-		select_ev = talloc_get_type(ev->additional_data,
-					    struct select_event_context);
-
-		if (select_ev->maxfd == fde->fd) {
-			select_ev->maxfd = EVENT_INVALID_MAXFD;
-		}
-	}
-
-	return tevent_common_fd_destructor(fde);
-}
-
-/*
-  add a fd based event
-  return NULL on failure (memory allocation error)
-*/
-static struct tevent_fd *select_event_add_fd(struct tevent_context *ev, TALLOC_CTX *mem_ctx,
-					     int fd, uint16_t flags,
-					     tevent_fd_handler_t handler,
-					     void *private_data,
-					     const char *handler_name,
-					     const char *location)
-{
-	struct select_event_context *select_ev = talloc_get_type(ev->additional_data,
-							   struct select_event_context);
-	struct tevent_fd *fde;
-
-	if (fd < 0 || fd >= FD_SETSIZE) {
-		errno = EBADF;
-		return NULL;
-	}
-
-	fde = tevent_common_add_fd(ev, mem_ctx, fd, flags,
-				   handler, private_data,
-				   handler_name, location);
-	if (!fde) return NULL;
-
-	if ((select_ev->maxfd != EVENT_INVALID_MAXFD)
-	    && (fde->fd > select_ev->maxfd)) {
-		select_ev->maxfd = fde->fd;
-	}
-	talloc_set_destructor(fde, select_event_fd_destructor);
-
-	return fde;
-}
-
-/*
-  event loop handling using select()
-*/
-static int select_event_loop_select(struct select_event_context *select_ev, struct timeval *tvalp)
-{
-	fd_set r_fds, w_fds;
-	struct tevent_fd *fde;
-	int selrtn;
-
-	/* we maybe need to recalculate the maxfd */
-	if (select_ev->maxfd == EVENT_INVALID_MAXFD) {
-		calc_maxfd(select_ev);
-	}
-
-	FD_ZERO(&r_fds);
-	FD_ZERO(&w_fds);
-
-	/* setup any fd events */
-	for (fde = select_ev->ev->fd_events; fde; fde = fde->next) {
-		if (fde->fd < 0 || fde->fd >= FD_SETSIZE) {
-			errno = EBADF;
-			return -1;
-		}
-
-		if (fde->flags & TEVENT_FD_READ) {
-			FD_SET(fde->fd, &r_fds);
-		}
-		if (fde->flags & TEVENT_FD_WRITE) {
-			FD_SET(fde->fd, &w_fds);
-		}
-	}
-
-	if (select_ev->ev->signal_events &&
-	    tevent_common_check_signal(select_ev->ev)) {
-		return 0;
-	}
-
-	tevent_trace_point_callback(select_ev->ev, TEVENT_TRACE_BEFORE_WAIT);
-	selrtn = select(select_ev->maxfd+1, &r_fds, &w_fds, NULL, tvalp);
-	tevent_trace_point_callback(select_ev->ev, TEVENT_TRACE_AFTER_WAIT);
-
-	if (selrtn == -1 && errno == EINTR &&
-	    select_ev->ev->signal_events) {
-		tevent_common_check_signal(select_ev->ev);
-		return 0;
-	}
-
-	if (selrtn == -1 && errno == EBADF) {
-		/* the socket is dead! this should never
-		   happen as the socket should have first been
-		   made readable and that should have removed
-		   the event, so this must be a bug. This is a
-		   fatal error. */
-		tevent_debug(select_ev->ev, TEVENT_DEBUG_FATAL,
-			     "ERROR: EBADF on select_event_loop_once\n");
-		select_ev->exit_code = EBADF;
-		return -1;
-	}
-
-	if (selrtn == 0 && tvalp) {
-		/* we don't care about a possible delay here */
-		tevent_common_loop_timer_delay(select_ev->ev);
-		return 0;
-	}
-
-	if (selrtn > 0) {
-		/* at least one file descriptor is ready - check
-		   which ones and call the handler, being careful to allow
-		   the handler to remove itself when called */
-		for (fde = select_ev->ev->fd_events; fde; fde = fde->next) {
-			uint16_t flags = 0;
-
-			if (FD_ISSET(fde->fd, &r_fds)) flags |= TEVENT_FD_READ;
-			if (FD_ISSET(fde->fd, &w_fds)) flags |= TEVENT_FD_WRITE;
-			if (flags) {
-				fde->handler(select_ev->ev, fde, flags, fde->private_data);
-				break;
-			}
-		}
-	}
-
-	return 0;
-}
-
-/*
-  do a single event loop using the events defined in ev
-*/
-static int select_event_loop_once(struct tevent_context *ev, const char *location)
-{
-	struct select_event_context *select_ev = talloc_get_type(ev->additional_data,
-							   struct select_event_context);
-	struct timeval tval;
-
-	if (ev->signal_events &&
-	    tevent_common_check_signal(ev)) {
-		return 0;
-	}
-
-	if (ev->immediate_events &&
-	    tevent_common_loop_immediate(ev)) {
-		return 0;
-	}
-
-	tval = tevent_common_loop_timer_delay(ev);
-	if (tevent_timeval_is_zero(&tval)) {
-		return 0;
-	}
-
-	return select_event_loop_select(select_ev, &tval);
-}
-
-static const struct tevent_ops select_event_ops = {
-	.context_init		= select_event_context_init,
-	.add_fd			= select_event_add_fd,
-	.set_fd_close_fn	= tevent_common_fd_set_close_fn,
-	.get_fd_flags		= tevent_common_fd_get_flags,
-	.set_fd_flags		= tevent_common_fd_set_flags,
-	.add_timer		= tevent_common_add_timer,
-	.schedule_immediate	= tevent_common_schedule_immediate,
-	.add_signal		= tevent_common_add_signal,
-	.loop_once		= select_event_loop_once,
-	.loop_wait		= tevent_common_loop_wait,
-};
-
-_PRIVATE_ bool tevent_select_init(void)
-{
-	return tevent_register_backend("select", &select_event_ops);
-}
diff --git a/lib/tevent/tevent_signal.c b/lib/tevent/tevent_signal.c
deleted file mode 100644
index 56bcef9..0000000
--- a/lib/tevent/tevent_signal.c
+++ /dev/null
@@ -1,457 +0,0 @@
-/*
-   Unix SMB/CIFS implementation.
-
-   common events code for signal events
-
-   Copyright (C) Andrew Tridgell	2007
-
-     ** NOTE! The following LGPL license applies to the tevent
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-
-#include "replace.h"
-#include "system/filesys.h"
-#include "system/wait.h"
-#include "tevent.h"
-#include "tevent_internal.h"
-#include "tevent_util.h"
-
-#define TEVENT_NUM_SIGNALS 64
-
-/* maximum number of SA_SIGINFO signals to hold in the queue.
-  NB. This *MUST* be a power of 2, in order for the ring buffer
-  wrap to work correctly. Thanks to Petr Vandrovec <petr at vandrovec.name>
-  for this. */
-
-#define TEVENT_SA_INFO_QUEUE_COUNT 64
-
-struct tevent_sigcounter {
-	uint32_t count;
-	uint32_t seen;
-};
-
-#define TEVENT_SIG_INCREMENT(s) (s).count++
-#define TEVENT_SIG_SEEN(s, n) (s).seen += (n)
-#define TEVENT_SIG_PENDING(s) ((s).seen != (s).count)
-
-struct tevent_common_signal_list {
-	struct tevent_common_signal_list *prev, *next;
-	struct tevent_signal *se;
-};
-
-/*
-  the poor design of signals means that this table must be static global
-*/
-static struct tevent_sig_state {
-	struct tevent_common_signal_list *sig_handlers[TEVENT_NUM_SIGNALS+1];
-	struct sigaction *oldact[TEVENT_NUM_SIGNALS+1];
-	struct tevent_sigcounter signal_count[TEVENT_NUM_SIGNALS+1];
-	struct tevent_sigcounter got_signal;
-#ifdef SA_SIGINFO
-	/* with SA_SIGINFO we get quite a lot of info per signal */
-	siginfo_t *sig_info[TEVENT_NUM_SIGNALS+1];
-	struct tevent_sigcounter sig_blocked[TEVENT_NUM_SIGNALS+1];
-#endif
-} *sig_state;
-
-/*
-  return number of sigcounter events not processed yet
-*/
-static uint32_t tevent_sig_count(struct tevent_sigcounter s)
-{
-	return s.count - s.seen;
-}
-
-/*
-  signal handler - redirects to registered signals
-*/
-static void tevent_common_signal_handler(int signum)
-{
-	char c = 0;
-	struct tevent_common_signal_list *sl;
-	struct tevent_context *ev = NULL;
-	int saved_errno = errno;
-
-	TEVENT_SIG_INCREMENT(sig_state->signal_count[signum]);
-	TEVENT_SIG_INCREMENT(sig_state->got_signal);
-
-	/* Write to each unique event context. */
-	for (sl = sig_state->sig_handlers[signum]; sl; sl = sl->next) {
-		if (sl->se->event_ctx && sl->se->event_ctx != ev) {
-			ev = sl->se->event_ctx;
-			/* doesn't matter if this pipe overflows */
-			(void) write(ev->pipe_fds[1], &c, 1);
-		}
-	}
-
-	errno = saved_errno;
-}
-
-#ifdef SA_SIGINFO
-/*
-  signal handler with SA_SIGINFO - redirects to registered signals
-*/
-static void tevent_common_signal_handler_info(int signum, siginfo_t *info,
-					      void *uctx)
-{
-	uint32_t count = tevent_sig_count(sig_state->signal_count[signum]);
-	/* sig_state->signal_count[signum].seen % TEVENT_SA_INFO_QUEUE_COUNT
-	 * is the base of the unprocessed signals in the ringbuffer. */
-	uint32_t ofs = (sig_state->signal_count[signum].seen + count) %
-				TEVENT_SA_INFO_QUEUE_COUNT;
-	sig_state->sig_info[signum][ofs] = *info;
-
-	tevent_common_signal_handler(signum);
-
-	/* handle SA_SIGINFO */
-	if (count+1 == TEVENT_SA_INFO_QUEUE_COUNT) {
-		/* we've filled the info array - block this signal until
-		   these ones are delivered */
-		sigset_t set;
-		sigemptyset(&set);
-		sigaddset(&set, signum);
-		sigprocmask(SIG_BLOCK, &set, NULL);
-		TEVENT_SIG_INCREMENT(sig_state->sig_blocked[signum]);
-	}
-}
-#endif
-
-static int tevent_common_signal_list_destructor(struct tevent_common_signal_list *sl)
-{
-	if (sig_state->sig_handlers[sl->se->signum]) {
-		DLIST_REMOVE(sig_state->sig_handlers[sl->se->signum], sl);
-	}
-	return 0;
-}
-
-/*
-  destroy a signal event
-*/
-static int tevent_signal_destructor(struct tevent_signal *se)
-{
-	struct tevent_common_signal_list *sl;
-	sl = talloc_get_type(se->additional_data,
-			     struct tevent_common_signal_list);
-
-	if (se->event_ctx) {
-		DLIST_REMOVE(se->event_ctx->signal_events, se);
-	}
-
-	talloc_free(sl);
-
-	if (sig_state->sig_handlers[se->signum] == NULL) {
-		/* restore old handler, if any */
-		if (sig_state->oldact[se->signum]) {
-			sigaction(se->signum, sig_state->oldact[se->signum], NULL);
-			sig_state->oldact[se->signum] = NULL;
-		}
-#ifdef SA_SIGINFO
-		if (se->sa_flags & SA_SIGINFO) {
-			if (sig_state->sig_info[se->signum]) {
-				talloc_free(sig_state->sig_info[se->signum]);
-				sig_state->sig_info[se->signum] = NULL;
-			}
-		}
-#endif
-	}
-
-	return 0;
-}
-
-/*
-  this is part of the pipe hack needed to avoid the signal race condition
-*/
-static void signal_pipe_handler(struct tevent_context *ev, struct tevent_fd *fde,
-				uint16_t flags, void *_private)
-{
-	char c[16];
-	/* its non-blocking, doesn't matter if we read too much */
-	(void) read(fde->fd, c, sizeof(c));
-}
-
-/*
-  add a signal event
-  return NULL on failure (memory allocation error)
-*/
-struct tevent_signal *tevent_common_add_signal(struct tevent_context *ev,
-					       TALLOC_CTX *mem_ctx,
-					       int signum,
-					       int sa_flags,
-					       tevent_signal_handler_t handler,
-					       void *private_data,
-					       const char *handler_name,
-					       const char *location)
-{
-	struct tevent_signal *se;
-	struct tevent_common_signal_list *sl;
-	sigset_t set, oldset;
-
-	if (signum >= TEVENT_NUM_SIGNALS) {
-		errno = EINVAL;
-		return NULL;
-	}
-
-	/* the sig_state needs to be on a global context as it can last across
-	   multiple event contexts */
-	if (sig_state == NULL) {
-		sig_state = talloc_zero(NULL, struct tevent_sig_state);
-		if (sig_state == NULL) {
-			return NULL;
-		}
-	}
-
-	se = talloc(mem_ctx?mem_ctx:ev, struct tevent_signal);
-	if (se == NULL) return NULL;
-
-	se->event_ctx		= ev;
-	se->signum              = signum;
-	se->sa_flags            = sa_flags;
-	se->handler		= handler;
-	se->private_data	= private_data;
-	se->handler_name	= handler_name;
-	se->location		= location;
-	se->additional_data	= NULL;
-
-	sl = talloc(se, struct tevent_common_signal_list);
-	if (!sl) {
-		talloc_free(se);
-		return NULL;
-	}
-	sl->se = se;
-	se->additional_data	= sl;
-
-	/* Ensure, no matter the destruction order, that we always have a handle on the global sig_state */
-	if (!talloc_reference(se, sig_state)) {
-		talloc_free(se);
-		return NULL;
-	}
-
-	/* we need to setup the pipe hack handler if not already
-	   setup */
-	if (ev->pipe_fde == NULL) {
-		if (pipe(ev->pipe_fds) == -1) {
-			talloc_free(se);
-			return NULL;
-		}
-		ev_set_blocking(ev->pipe_fds[0], false);
-		ev_set_blocking(ev->pipe_fds[1], false);
-		ev->pipe_fde = tevent_add_fd(ev, ev, ev->pipe_fds[0],
-					     TEVENT_FD_READ,
-					     signal_pipe_handler, NULL);
-		if (!ev->pipe_fde) {
-			close(ev->pipe_fds[0]);
-			close(ev->pipe_fds[1]);
-			talloc_free(se);
-			return NULL;
-		}
-	}
-
-	/* only install a signal handler if not already installed */
-	if (sig_state->sig_handlers[signum] == NULL) {
-		struct sigaction act;
-		ZERO_STRUCT(act);
-		act.sa_handler = tevent_common_signal_handler;
-		act.sa_flags = sa_flags;
-#ifdef SA_SIGINFO
-		if (sa_flags & SA_SIGINFO) {
-			act.sa_handler   = NULL;
-			act.sa_sigaction = tevent_common_signal_handler_info;
-			if (sig_state->sig_info[signum] == NULL) {
-				sig_state->sig_info[signum] =
-					talloc_zero_array(sig_state, siginfo_t,
-							  TEVENT_SA_INFO_QUEUE_COUNT);
-				if (sig_state->sig_info[signum] == NULL) {
-					talloc_free(se);
-					return NULL;
-				}
-			}
-		}
-#endif
-		sig_state->oldact[signum] = talloc(sig_state, struct sigaction);
-		if (sig_state->oldact[signum] == NULL) {
-			talloc_free(se);
-			return NULL;
-		}
-		if (sigaction(signum, &act, sig_state->oldact[signum]) == -1) {
-			talloc_free(se);
-			return NULL;
-		}
-	}
-
-	DLIST_ADD(se->event_ctx->signal_events, se);
-
-	/* Make sure the signal doesn't come in while we're mangling list. */
-	sigemptyset(&set);
-	sigaddset(&set, signum);
-	sigprocmask(SIG_BLOCK, &set, &oldset);
-	DLIST_ADD(sig_state->sig_handlers[signum], sl);
-	sigprocmask(SIG_SETMASK, &oldset, NULL);
-
-	talloc_set_destructor(se, tevent_signal_destructor);
-	talloc_set_destructor(sl, tevent_common_signal_list_destructor);
-
-	return se;
-}
-
-struct tevent_se_exists {
-	struct tevent_se_exists **myself;
-};
-
-static int tevent_se_exists_destructor(struct tevent_se_exists *s)
-{
-	*s->myself = NULL;
-	return 0;
-}
-
-/*
-  check if a signal is pending
-  return != 0 if a signal was pending
-*/
-int tevent_common_check_signal(struct tevent_context *ev)
-{
-	int i;
-
-	if (!sig_state || !TEVENT_SIG_PENDING(sig_state->got_signal)) {
-		return 0;
-	}
-
-	for (i=0;i<TEVENT_NUM_SIGNALS+1;i++) {
-		struct tevent_common_signal_list *sl, *next;
-		struct tevent_sigcounter counter = sig_state->signal_count[i];
-		uint32_t count = tevent_sig_count(counter);
-#ifdef SA_SIGINFO
-		/* Ensure we null out any stored siginfo_t entries
-		 * after processing for debugging purposes. */
-		bool clear_processed_siginfo = false;
-#endif
-
-		if (count == 0) {
-			continue;
-		}
-		for (sl=sig_state->sig_handlers[i];sl;sl=next) {
-			struct tevent_signal *se = sl->se;
-			struct tevent_se_exists *exists;
-
-			next = sl->next;
-
-			/*
-			 * We have to be careful to not touch "se"
-			 * after it was deleted in its handler. Thus
-			 * we allocate a child whose destructor will
-			 * tell by nulling out itself that its parent
-			 * is gone.
-			 */
-			exists = talloc(se, struct tevent_se_exists);
-			if (exists == NULL) {
-				continue;
-			}
-			exists->myself = &exists;
-			talloc_set_destructor(
-				exists, tevent_se_exists_destructor);
-
-#ifdef SA_SIGINFO
-			if (se->sa_flags & SA_SIGINFO) {
-				uint32_t j;
-
-				clear_processed_siginfo = true;
-
-				for (j=0;j<count;j++) {
-					/* sig_state->signal_count[i].seen
-					 * % TEVENT_SA_INFO_QUEUE_COUNT is
-					 * the base position of the unprocessed
-					 * signals in the ringbuffer. */
-					uint32_t ofs = (counter.seen + j)
-						% TEVENT_SA_INFO_QUEUE_COUNT;
-					se->handler(ev, se, i, 1,
-						    (void*)&sig_state->sig_info[i][ofs],
-						    se->private_data);
-					if (!exists) {
-						break;
-					}
-				}
-#ifdef SA_RESETHAND
-				if (exists && (se->sa_flags & SA_RESETHAND)) {
-					talloc_free(se);
-				}
-#endif
-				talloc_free(exists);
-				continue;
-			}
-#endif
-			se->handler(ev, se, i, count, NULL, se->private_data);
-#ifdef SA_RESETHAND
-			if (exists && (se->sa_flags & SA_RESETHAND)) {
-				talloc_free(se);
-			}
-#endif
-			talloc_free(exists);
-		}
-
-#ifdef SA_SIGINFO
-		if (clear_processed_siginfo) {
-			uint32_t j;
-			for (j=0;j<count;j++) {
-				uint32_t ofs = (counter.seen + j)
-					% TEVENT_SA_INFO_QUEUE_COUNT;
-				memset((void*)&sig_state->sig_info[i][ofs],
-					'\0',
-					sizeof(siginfo_t));
-			}
-		}
-#endif
-
-		TEVENT_SIG_SEEN(sig_state->signal_count[i], count);
-		TEVENT_SIG_SEEN(sig_state->got_signal, count);
-
-#ifdef SA_SIGINFO
-		if (TEVENT_SIG_PENDING(sig_state->sig_blocked[i])) {
-			/* We'd filled the queue, unblock the
-			   signal now the queue is empty again.
-			   Note we MUST do this after the
-			   TEVENT_SIG_SEEN(sig_state->signal_count[i], count)
-			   call to prevent a new signal running
-			   out of room in the sig_state->sig_info[i][]
-			   ring buffer. */
-			sigset_t set;
-			sigemptyset(&set);
-			sigaddset(&set, i);
-			TEVENT_SIG_SEEN(sig_state->sig_blocked[i],
-				 tevent_sig_count(sig_state->sig_blocked[i]));
-			sigprocmask(SIG_UNBLOCK, &set, NULL);
-		}
-#endif
-	}
-
-	return 1;
-}
-
-void tevent_cleanup_pending_signal_handlers(struct tevent_signal *se)
-{
-	struct tevent_common_signal_list *sl;
-	sl = talloc_get_type(se->additional_data,
-			     struct tevent_common_signal_list);
-
-	tevent_common_signal_list_destructor(sl);
-
-	if (sig_state->sig_handlers[se->signum] == NULL) {
-		if (sig_state->oldact[se->signum]) {
-			sigaction(se->signum, sig_state->oldact[se->signum], NULL);
-			sig_state->oldact[se->signum] = NULL;
-		}
-	}
-	return;
-}
diff --git a/lib/tevent/tevent_standard.c b/lib/tevent/tevent_standard.c
deleted file mode 100644
index 6c34854..0000000
--- a/lib/tevent/tevent_standard.c
+++ /dev/null
@@ -1,591 +0,0 @@
-/*
-   Unix SMB/CIFS implementation.
-   main select loop and event handling
-   Copyright (C) Andrew Tridgell	2003-2005
-   Copyright (C) Stefan Metzmacher	2005-2009
-
-     ** NOTE! The following LGPL license applies to the tevent
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-
-/*
-  This is SAMBA's default event loop code
-
-  - we try to use epoll if configure detected support for it
-    otherwise we use select()
-  - if epoll is broken on the system or the kernel doesn't support it
-    at runtime we fallback to select()
-*/
-
-#include "replace.h"
-#include "system/filesys.h"
-#include "system/select.h"
-#include "tevent.h"
-#include "tevent_util.h"
-#include "tevent_internal.h"
-
-struct std_event_context {
-	/* a pointer back to the generic event_context */
-	struct tevent_context *ev;
-
-	/* the maximum file descriptor number in fd_events */
-	int maxfd;
-
-	/* information for exiting from the event loop */
-	int exit_code;
-
-	/* when using epoll this is the handle from epoll_create */
-	int epoll_fd;
-
-	/* our pid at the time the epoll_fd was created */
-	pid_t pid;
-};
-
-/* use epoll if it is available */
-#if HAVE_EPOLL
-/*
-  called when a epoll call fails, and we should fallback
-  to using select
-*/
-static void epoll_fallback_to_select(struct std_event_context *std_ev, const char *reason)
-{
-	tevent_debug(std_ev->ev, TEVENT_DEBUG_FATAL,
-		     "%s (%s) - falling back to select()\n",
-		     reason, strerror(errno));
-	close(std_ev->epoll_fd);
-	std_ev->epoll_fd = -1;
-	talloc_set_destructor(std_ev, NULL);
-}
-
-/*
-  map from TEVENT_FD_* to EPOLLIN/EPOLLOUT
-*/
-static uint32_t epoll_map_flags(uint16_t flags)
-{
-	uint32_t ret = 0;
-	if (flags & TEVENT_FD_READ) ret |= (EPOLLIN | EPOLLERR | EPOLLHUP);
-	if (flags & TEVENT_FD_WRITE) ret |= (EPOLLOUT | EPOLLERR | EPOLLHUP);
-	return ret;
-}
-
-/*
- free the epoll fd
-*/
-static int epoll_ctx_destructor(struct std_event_context *std_ev)
-{
-	if (std_ev->epoll_fd != -1) {
-		close(std_ev->epoll_fd);
-	}
-	std_ev->epoll_fd = -1;
-	return 0;
-}
-
-/*
- init the epoll fd
-*/
-static void epoll_init_ctx(struct std_event_context *std_ev)
-{
-	std_ev->epoll_fd = epoll_create(64);
-	if (std_ev->epoll_fd == -1) {
-		tevent_debug(std_ev->ev, TEVENT_DEBUG_FATAL,
-			     "Failed to create epoll handle.\n");
-		return;
-	}
-
-	if (!ev_set_close_on_exec(std_ev->epoll_fd)) {
-		tevent_debug(std_ev->ev, TEVENT_DEBUG_WARNING,
-			     "Failed to set close-on-exec, file descriptor may be leaked to children.\n");
-	}
-
-	std_ev->pid = getpid();
-	talloc_set_destructor(std_ev, epoll_ctx_destructor);
-}
-
-static void epoll_add_event(struct std_event_context *std_ev, struct tevent_fd *fde);
-
-/*
-  reopen the epoll handle when our pid changes
-  see http://junkcode.samba.org/ftp/unpacked/junkcode/epoll_fork.c for an
-  demonstration of why this is needed
- */
-static void epoll_check_reopen(struct std_event_context *std_ev)
-{
-	struct tevent_fd *fde;
-
-	if (std_ev->pid == getpid()) {
-		return;
-	}
-
-	close(std_ev->epoll_fd);
-	std_ev->epoll_fd = epoll_create(64);
-	if (std_ev->epoll_fd == -1) {
-		tevent_debug(std_ev->ev, TEVENT_DEBUG_FATAL,
-			     "Failed to recreate epoll handle after fork\n");
-		return;
-	}
-
-	if (!ev_set_close_on_exec(std_ev->epoll_fd)) {
-		tevent_debug(std_ev->ev, TEVENT_DEBUG_WARNING,
-			     "Failed to set close-on-exec, file descriptor may be leaked to children.\n");
-	}
-
-	std_ev->pid = getpid();
-	for (fde=std_ev->ev->fd_events;fde;fde=fde->next) {
-		epoll_add_event(std_ev, fde);
-	}
-}
-
-#define EPOLL_ADDITIONAL_FD_FLAG_HAS_EVENT	(1<<0)
-#define EPOLL_ADDITIONAL_FD_FLAG_REPORT_ERROR	(1<<1)
-#define EPOLL_ADDITIONAL_FD_FLAG_GOT_ERROR	(1<<2)
-
-/*
- add the epoll event to the given fd_event
-*/
-static void epoll_add_event(struct std_event_context *std_ev, struct tevent_fd *fde)
-{
-	struct epoll_event event;
-	if (std_ev->epoll_fd == -1) return;
-
-	fde->additional_flags &= ~EPOLL_ADDITIONAL_FD_FLAG_REPORT_ERROR;
-
-	/* if we don't want events yet, don't add an epoll_event */
-	if (fde->flags == 0) return;
-
-	ZERO_STRUCT(event);
-	event.events = epoll_map_flags(fde->flags);
-	event.data.ptr = fde;
-	if (epoll_ctl(std_ev->epoll_fd, EPOLL_CTL_ADD, fde->fd, &event) != 0) {
-		epoll_fallback_to_select(std_ev, "EPOLL_CTL_ADD failed");
-	}
-	fde->additional_flags |= EPOLL_ADDITIONAL_FD_FLAG_HAS_EVENT;
-
-	/* only if we want to read we want to tell the event handler about errors */
-	if (fde->flags & TEVENT_FD_READ) {
-		fde->additional_flags |= EPOLL_ADDITIONAL_FD_FLAG_REPORT_ERROR;
-	}
-}
-
-/*
- delete the epoll event for given fd_event
-*/
-static void epoll_del_event(struct std_event_context *std_ev, struct tevent_fd *fde)
-{
-	struct epoll_event event;
-	if (std_ev->epoll_fd == -1) return;
-
-	fde->additional_flags &= ~EPOLL_ADDITIONAL_FD_FLAG_REPORT_ERROR;
-
-	/* if there's no epoll_event, we don't need to delete it */
-	if (!(fde->additional_flags & EPOLL_ADDITIONAL_FD_FLAG_HAS_EVENT)) return;
-
-	ZERO_STRUCT(event);
-	event.events = epoll_map_flags(fde->flags);
-	event.data.ptr = fde;
-	epoll_ctl(std_ev->epoll_fd, EPOLL_CTL_DEL, fde->fd, &event);
-	fde->additional_flags &= ~EPOLL_ADDITIONAL_FD_FLAG_HAS_EVENT;
-}
-
-/*
- change the epoll event to the given fd_event
-*/
-static void epoll_mod_event(struct std_event_context *std_ev, struct tevent_fd *fde)
-{
-	struct epoll_event event;
-	if (std_ev->epoll_fd == -1) return;
-
-	fde->additional_flags &= ~EPOLL_ADDITIONAL_FD_FLAG_REPORT_ERROR;
-
-	ZERO_STRUCT(event);
-	event.events = epoll_map_flags(fde->flags);
-	event.data.ptr = fde;
-	if (epoll_ctl(std_ev->epoll_fd, EPOLL_CTL_MOD, fde->fd, &event) != 0) {
-		epoll_fallback_to_select(std_ev, "EPOLL_CTL_MOD failed");
-	}
-
-	/* only if we want to read we want to tell the event handler about errors */
-	if (fde->flags & TEVENT_FD_READ) {
-		fde->additional_flags |= EPOLL_ADDITIONAL_FD_FLAG_REPORT_ERROR;
-	}
-}
-
-static void epoll_change_event(struct std_event_context *std_ev, struct tevent_fd *fde)
-{
-	bool got_error = (fde->additional_flags & EPOLL_ADDITIONAL_FD_FLAG_GOT_ERROR);
-	bool want_read = (fde->flags & TEVENT_FD_READ);
-	bool want_write= (fde->flags & TEVENT_FD_WRITE);
-
-	if (std_ev->epoll_fd == -1) return;
-
-	fde->additional_flags &= ~EPOLL_ADDITIONAL_FD_FLAG_REPORT_ERROR;
-
-	/* there's already an event */
-	if (fde->additional_flags & EPOLL_ADDITIONAL_FD_FLAG_HAS_EVENT) {
-		if (want_read || (want_write && !got_error)) {
-			epoll_mod_event(std_ev, fde);
-			return;
-		}
-		/*
-		 * if we want to match the select behavior, we need to remove the epoll_event
-		 * when the caller isn't interested in events.
-		 *
-		 * this is because epoll reports EPOLLERR and EPOLLHUP, even without asking for them
-		 */
-		epoll_del_event(std_ev, fde);
-		return;
-	}
-
-	/* there's no epoll_event attached to the fde */
-	if (want_read || (want_write && !got_error)) {
-		epoll_add_event(std_ev, fde);
-		return;
-	}
-}
-
-/*
-  event loop handling using epoll
-*/
-static int epoll_event_loop(struct std_event_context *std_ev, struct timeval *tvalp)
-{
-	int ret, i;
-#define MAXEVENTS 1
-	struct epoll_event events[MAXEVENTS];
-	int timeout = -1;
-
-	if (std_ev->epoll_fd == -1) return -1;
-
-	if (tvalp) {
-		/* it's better to trigger timed events a bit later than to early */
-		timeout = ((tvalp->tv_usec+999) / 1000) + (tvalp->tv_sec*1000);
-	}
-
-	if (std_ev->ev->signal_events &&
-	    tevent_common_check_signal(std_ev->ev)) {
-		return 0;
-	}
-
-	tevent_trace_point_callback(std_ev->ev, TEVENT_TRACE_BEFORE_WAIT);
-	ret = epoll_wait(std_ev->epoll_fd, events, MAXEVENTS, timeout);
-	tevent_trace_point_callback(std_ev->ev, TEVENT_TRACE_AFTER_WAIT);
-
-	if (ret == -1 && errno == EINTR && std_ev->ev->signal_events) {
-		if (tevent_common_check_signal(std_ev->ev)) {
-			return 0;
-		}
-	}
-
-	if (ret == -1 && errno != EINTR) {
-		epoll_fallback_to_select(std_ev, "epoll_wait() failed");
-		return -1;
-	}
-
-	if (ret == 0 && tvalp) {
-		/* we don't care about a possible delay here */
-		tevent_common_loop_timer_delay(std_ev->ev);
-		return 0;
-	}
-
-	for (i=0;i<ret;i++) {
-		struct tevent_fd *fde = talloc_get_type(events[i].data.ptr,
-						       struct tevent_fd);
-		uint16_t flags = 0;
-
-		if (fde == NULL) {
-			epoll_fallback_to_select(std_ev, "epoll_wait() gave bad data");
-			return -1;
-		}
-		if (events[i].events & (EPOLLHUP|EPOLLERR)) {
-			fde->additional_flags |= EPOLL_ADDITIONAL_FD_FLAG_GOT_ERROR;
-			/*
-			 * if we only wait for TEVENT_FD_WRITE, we should not tell the
-			 * event handler about it, and remove the epoll_event,
-			 * as we only report errors when waiting for read events,
-			 * to match the select() behavior
-			 */
-			if (!(fde->additional_flags & EPOLL_ADDITIONAL_FD_FLAG_REPORT_ERROR)) {
-				epoll_del_event(std_ev, fde);
-				continue;
-			}
-			flags |= TEVENT_FD_READ;
-		}
-		if (events[i].events & EPOLLIN) flags |= TEVENT_FD_READ;
-		if (events[i].events & EPOLLOUT) flags |= TEVENT_FD_WRITE;
-		if (flags) {
-			fde->handler(std_ev->ev, fde, flags, fde->private_data);
-			break;
-		}
-	}
-
-	return 0;
-}
-#else
-#define epoll_init_ctx(std_ev)
-#define epoll_add_event(std_ev,fde)
-#define epoll_del_event(std_ev,fde)
-#define epoll_change_event(std_ev,fde)
-#define epoll_event_loop(std_ev,tvalp) (-1)
-#define epoll_check_reopen(std_ev)
-#endif
-
-/*
-  create a std_event_context structure.
-*/
-static int std_event_context_init(struct tevent_context *ev)
-{
-	struct std_event_context *std_ev;
-
-	std_ev = talloc_zero(ev, struct std_event_context);
-	if (!std_ev) return -1;
-	std_ev->ev = ev;
-	std_ev->epoll_fd = -1;
-
-	epoll_init_ctx(std_ev);
-
-	ev->additional_data = std_ev;
-	return 0;
-}
-
-/*
-  recalculate the maxfd
-*/
-static void calc_maxfd(struct std_event_context *std_ev)
-{
-	struct tevent_fd *fde;
-
-	std_ev->maxfd = 0;
-	for (fde = std_ev->ev->fd_events; fde; fde = fde->next) {
-		if (fde->fd > std_ev->maxfd) {
-			std_ev->maxfd = fde->fd;
-		}
-	}
-}
-
-
-/* to mark the ev->maxfd invalid
- * this means we need to recalculate it
- */
-#define EVENT_INVALID_MAXFD (-1)
-
-/*
-  destroy an fd_event
-*/
-static int std_event_fd_destructor(struct tevent_fd *fde)
-{
-	struct tevent_context *ev = fde->event_ctx;
-	struct std_event_context *std_ev = NULL;
-
-	if (ev) {
-		std_ev = talloc_get_type(ev->additional_data,
-					 struct std_event_context);
-
-		epoll_check_reopen(std_ev);
-
-		if (std_ev->maxfd == fde->fd) {
-			std_ev->maxfd = EVENT_INVALID_MAXFD;
-		}
-
-		epoll_del_event(std_ev, fde);
-	}
-
-	return tevent_common_fd_destructor(fde);
-}
-
-/*
-  add a fd based event
-  return NULL on failure (memory allocation error)
-*/
-static struct tevent_fd *std_event_add_fd(struct tevent_context *ev, TALLOC_CTX *mem_ctx,
-					  int fd, uint16_t flags,
-					  tevent_fd_handler_t handler,
-					  void *private_data,
-					  const char *handler_name,
-					  const char *location)
-{
-	struct std_event_context *std_ev = talloc_get_type(ev->additional_data,
-							   struct std_event_context);
-	struct tevent_fd *fde;
-
-	epoll_check_reopen(std_ev);
-
-	fde = tevent_common_add_fd(ev, mem_ctx, fd, flags,
-				   handler, private_data,
-				   handler_name, location);
-	if (!fde) return NULL;
-
-	if ((std_ev->maxfd != EVENT_INVALID_MAXFD)
-	    && (fde->fd > std_ev->maxfd)) {
-		std_ev->maxfd = fde->fd;
-	}
-	talloc_set_destructor(fde, std_event_fd_destructor);
-
-	epoll_add_event(std_ev, fde);
-
-	return fde;
-}
-
-/*
-  set the fd event flags
-*/
-static void std_event_set_fd_flags(struct tevent_fd *fde, uint16_t flags)
-{
-	struct tevent_context *ev;
-	struct std_event_context *std_ev;
-
-	if (fde->flags == flags) return;
-
-	ev = fde->event_ctx;
-	std_ev = talloc_get_type(ev->additional_data, struct std_event_context);
-
-	fde->flags = flags;
-
-	epoll_check_reopen(std_ev);
-
-	epoll_change_event(std_ev, fde);
-}
-
-/*
-  event loop handling using select()
-*/
-static int std_event_loop_select(struct std_event_context *std_ev, struct timeval *tvalp)
-{
-	fd_set r_fds, w_fds;
-	struct tevent_fd *fde;
-	int selrtn;
-
-	/* we maybe need to recalculate the maxfd */
-	if (std_ev->maxfd == EVENT_INVALID_MAXFD) {
-		calc_maxfd(std_ev);
-	}
-
-	FD_ZERO(&r_fds);
-	FD_ZERO(&w_fds);
-
-	/* setup any fd events */
-	for (fde = std_ev->ev->fd_events; fde; fde = fde->next) {
-		if (fde->fd < 0 || fde->fd >= FD_SETSIZE) {
-			std_ev->exit_code = EBADF;
-			return -1;
-		}
-		if (fde->flags & TEVENT_FD_READ) {
-			FD_SET(fde->fd, &r_fds);
-		}
-		if (fde->flags & TEVENT_FD_WRITE) {
-			FD_SET(fde->fd, &w_fds);
-		}
-	}
-
-	if (std_ev->ev->signal_events &&
-	    tevent_common_check_signal(std_ev->ev)) {
-		return 0;
-	}
-
-	selrtn = select(std_ev->maxfd+1, &r_fds, &w_fds, NULL, tvalp);
-
-	if (selrtn == -1 && errno == EINTR &&
-	    std_ev->ev->signal_events) {
-		tevent_common_check_signal(std_ev->ev);
-		return 0;
-	}
-
-	if (selrtn == -1 && errno == EBADF) {
-		/* the socket is dead! this should never
-		   happen as the socket should have first been
-		   made readable and that should have removed
-		   the event, so this must be a bug. This is a
-		   fatal error. */
-		tevent_debug(std_ev->ev, TEVENT_DEBUG_FATAL,
-			     "ERROR: EBADF on std_event_loop_once\n");
-		std_ev->exit_code = EBADF;
-		return -1;
-	}
-
-	if (selrtn == 0 && tvalp) {
-		/* we don't care about a possible delay here */
-		tevent_common_loop_timer_delay(std_ev->ev);
-		return 0;
-	}
-
-	if (selrtn > 0) {
-		/* at least one file descriptor is ready - check
-		   which ones and call the handler, being careful to allow
-		   the handler to remove itself when called */
-		for (fde = std_ev->ev->fd_events; fde; fde = fde->next) {
-			uint16_t flags = 0;
-
-			if (FD_ISSET(fde->fd, &r_fds)) flags |= TEVENT_FD_READ;
-			if (FD_ISSET(fde->fd, &w_fds)) flags |= TEVENT_FD_WRITE;
-			if (flags & fde->flags) {
-				fde->handler(std_ev->ev, fde, flags, fde->private_data);
-				break;
-			}
-		}
-	}
-
-	return 0;
-}
-
-/*
-  do a single event loop using the events defined in ev
-*/
-static int std_event_loop_once(struct tevent_context *ev, const char *location)
-{
-	struct std_event_context *std_ev = talloc_get_type(ev->additional_data,
-							   struct std_event_context);
-	struct timeval tval;
-
-	if (ev->signal_events &&
-	    tevent_common_check_signal(ev)) {
-		return 0;
-	}
-
-	if (ev->immediate_events &&
-	    tevent_common_loop_immediate(ev)) {
-		return 0;
-	}
-
-	tval = tevent_common_loop_timer_delay(ev);
-	if (tevent_timeval_is_zero(&tval)) {
-		return 0;
-	}
-
-	epoll_check_reopen(std_ev);
-
-	if (epoll_event_loop(std_ev, &tval) == 0) {
-		return 0;
-	}
-
-	return std_event_loop_select(std_ev, &tval);
-}
-
-static const struct tevent_ops std_event_ops = {
-	.context_init		= std_event_context_init,
-	.add_fd			= std_event_add_fd,
-	.set_fd_close_fn	= tevent_common_fd_set_close_fn,
-	.get_fd_flags		= tevent_common_fd_get_flags,
-	.set_fd_flags		= std_event_set_fd_flags,
-	.add_timer		= tevent_common_add_timer,
-	.schedule_immediate	= tevent_common_schedule_immediate,
-	.add_signal		= tevent_common_add_signal,
-	.loop_once		= std_event_loop_once,
-	.loop_wait		= tevent_common_loop_wait,
-};
-
-
-_PRIVATE_ bool tevent_standard_init(void)
-{
-	return tevent_register_backend("standard", &std_event_ops);
-}
diff --git a/lib/tevent/tevent_timed.c b/lib/tevent/tevent_timed.c
deleted file mode 100644
index cc25428..0000000
--- a/lib/tevent/tevent_timed.c
+++ /dev/null
@@ -1,267 +0,0 @@
-/*
-   Unix SMB/CIFS implementation.
-
-   common events code for timed events
-
-   Copyright (C) Andrew Tridgell	2003-2006
-   Copyright (C) Stefan Metzmacher	2005-2009
-
-     ** NOTE! The following LGPL license applies to the tevent
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-
-#include "replace.h"
-#include "system/time.h"
-#include "tevent.h"
-#include "tevent_internal.h"
-#include "tevent_util.h"
-
-/**
-  compare two timeval structures.
-  Return -1 if tv1 < tv2
-  Return 0 if tv1 == tv2
-  Return 1 if tv1 > tv2
-*/
-int tevent_timeval_compare(const struct timeval *tv1, const struct timeval *tv2)
-{
-	if (tv1->tv_sec  > tv2->tv_sec)  return 1;
-	if (tv1->tv_sec  < tv2->tv_sec)  return -1;
-	if (tv1->tv_usec > tv2->tv_usec) return 1;
-	if (tv1->tv_usec < tv2->tv_usec) return -1;
-	return 0;
-}
-
-/**
-  return a zero timeval
-*/
-struct timeval tevent_timeval_zero(void)
-{
-	struct timeval tv;
-	tv.tv_sec = 0;
-	tv.tv_usec = 0;
-	return tv;
-}
-
-/**
-  return a timeval for the current time
-*/
-struct timeval tevent_timeval_current(void)
-{
-	struct timeval tv;
-	gettimeofday(&tv, NULL);
-	return tv;
-}
-
-/**
-  return a timeval struct with the given elements
-*/
-struct timeval tevent_timeval_set(uint32_t secs, uint32_t usecs)
-{
-	struct timeval tv;
-	tv.tv_sec = secs;
-	tv.tv_usec = usecs;
-	return tv;
-}
-
-/**
-  return the difference between two timevals as a timeval
-  if tv1 comes after tv2, then return a zero timeval
-  (this is *tv2 - *tv1)
-*/
-struct timeval tevent_timeval_until(const struct timeval *tv1,
-				    const struct timeval *tv2)
-{
-	struct timeval t;
-	if (tevent_timeval_compare(tv1, tv2) >= 0) {
-		return tevent_timeval_zero();
-	}
-	t.tv_sec = tv2->tv_sec - tv1->tv_sec;
-	if (tv1->tv_usec > tv2->tv_usec) {
-		t.tv_sec--;
-		t.tv_usec = 1000000 - (tv1->tv_usec - tv2->tv_usec);
-	} else {
-		t.tv_usec = tv2->tv_usec - tv1->tv_usec;
-	}
-	return t;
-}
-
-/**
-  return true if a timeval is zero
-*/
-bool tevent_timeval_is_zero(const struct timeval *tv)
-{
-	return tv->tv_sec == 0 && tv->tv_usec == 0;
-}
-
-struct timeval tevent_timeval_add(const struct timeval *tv, uint32_t secs,
-				  uint32_t usecs)
-{
-	struct timeval tv2 = *tv;
-	tv2.tv_sec += secs;
-	tv2.tv_usec += usecs;
-	tv2.tv_sec += tv2.tv_usec / 1000000;
-	tv2.tv_usec = tv2.tv_usec % 1000000;
-
-	return tv2;
-}
-
-/**
-  return a timeval in the future with a specified offset
-*/
-struct timeval tevent_timeval_current_ofs(uint32_t secs, uint32_t usecs)
-{
-	struct timeval tv = tevent_timeval_current();
-	return tevent_timeval_add(&tv, secs, usecs);
-}
-
-/*
-  destroy a timed event
-*/
-static int tevent_common_timed_destructor(struct tevent_timer *te)
-{
-	tevent_debug(te->event_ctx, TEVENT_DEBUG_TRACE,
-		     "Destroying timer event %p \"%s\"\n",
-		     te, te->handler_name);
-
-	if (te->event_ctx) {
-		DLIST_REMOVE(te->event_ctx->timer_events, te);
-	}
-
-	return 0;
-}
-
-static int tevent_common_timed_deny_destructor(struct tevent_timer *te)
-{
-	return -1;
-}
-
-/*
-  add a timed event
-  return NULL on failure (memory allocation error)
-*/
-struct tevent_timer *tevent_common_add_timer(struct tevent_context *ev, TALLOC_CTX *mem_ctx,
-					     struct timeval next_event,
-					     tevent_timer_handler_t handler,
-					     void *private_data,
-					     const char *handler_name,
-					     const char *location)
-{
-	struct tevent_timer *te, *last_te, *cur_te;
-
-	te = talloc(mem_ctx?mem_ctx:ev, struct tevent_timer);
-	if (te == NULL) return NULL;
-
-	te->event_ctx		= ev;
-	te->next_event		= next_event;
-	te->handler		= handler;
-	te->private_data	= private_data;
-	te->handler_name	= handler_name;
-	te->location		= location;
-	te->additional_data	= NULL;
-
-	/* keep the list ordered */
-	last_te = NULL;
-	for (cur_te = ev->timer_events; cur_te; cur_te = cur_te->next) {
-		/* if the new event comes before the current one break */
-		if (tevent_timeval_compare(&te->next_event, &cur_te->next_event) < 0) {
-			break;
-		}
-
-		last_te = cur_te;
-	}
-
-	DLIST_ADD_AFTER(ev->timer_events, te, last_te);
-
-	talloc_set_destructor(te, tevent_common_timed_destructor);
-
-	tevent_debug(ev, TEVENT_DEBUG_TRACE,
-		     "Added timed event \"%s\": %p\n",
-		     handler_name, te);
-	return te;
-}
-
-/*
-  do a single event loop using the events defined in ev
-
-  return the delay until the next timed event,
-  or zero if a timed event was triggered
-*/
-struct timeval tevent_common_loop_timer_delay(struct tevent_context *ev)
-{
-	struct timeval current_time = tevent_timeval_zero();
-	struct tevent_timer *te = ev->timer_events;
-
-	if (!te) {
-		/* have a default tick time of 30 seconds. This guarantees
-		   that code that uses its own timeout checking will be
-		   able to proceed eventually */
-		return tevent_timeval_set(30, 0);
-	}
-
-	/*
-	 * work out the right timeout for the next timed event
-	 *
-	 * avoid the syscall to gettimeofday() if the timed event should
-	 * be triggered directly
-	 *
-	 * if there's a delay till the next timed event, we're done
-	 * with just returning the delay
-	 */
-	if (!tevent_timeval_is_zero(&te->next_event)) {
-		struct timeval delay;
-
-		current_time = tevent_timeval_current();
-
-		delay = tevent_timeval_until(&current_time, &te->next_event);
-		if (!tevent_timeval_is_zero(&delay)) {
-			return delay;
-		}
-	}
-
-	/*
-	 * ok, we have a timed event that we'll process ...
-	 */
-
-	/* deny the handler to free the event */
-	talloc_set_destructor(te, tevent_common_timed_deny_destructor);
-
-	/* We need to remove the timer from the list before calling the
-	 * handler because in a semi-async inner event loop called from the
-	 * handler we don't want to come across this event again -- vl */
-	DLIST_REMOVE(ev->timer_events, te);
-
-	/*
-	 * If the timed event was registered for a zero current_time,
-	 * then we pass a zero timeval here too! To avoid the
-	 * overhead of gettimeofday() calls.
-	 *
-	 * otherwise we pass the current time
-	 */
-	te->handler(ev, te, current_time, te->private_data);
-
-	/* The destructor isn't necessary anymore, we've already removed the
-	 * event from the list. */
-	talloc_set_destructor(te, NULL);
-
-	tevent_debug(te->event_ctx, TEVENT_DEBUG_TRACE,
-		     "Ending timer event %p \"%s\"\n",
-		     te, te->handler_name);
-
-	talloc_free(te);
-
-	return tevent_timeval_zero();
-}
diff --git a/lib/tevent/tevent_util.c b/lib/tevent/tevent_util.c
deleted file mode 100644
index 16af8f3..0000000
--- a/lib/tevent/tevent_util.c
+++ /dev/null
@@ -1,107 +0,0 @@
-/*
-   Unix SMB/CIFS implementation.
-
-   Copyright (C) Andrew Tridgell 2005
-   Copyright (C) Jelmer Vernooij 2005
-
-     ** NOTE! The following LGPL license applies to the tevent
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-
-#include "replace.h"
-#include "talloc.h"
-#include "tevent.h"
-#include "tevent_internal.h"
-#include "tevent_util.h"
-#include <fcntl.h>
-
-/**
-  return the number of elements in a string list
-*/
-size_t ev_str_list_length(const char **list)
-{
-	size_t ret;
-	for (ret=0;list && list[ret];ret++) /* noop */ ;
-	return ret;
-}
-
-/**
-  add an entry to a string list
-*/
-const char **ev_str_list_add(const char **list, const char *s)
-{
-	size_t len = ev_str_list_length(list);
-	const char **ret;
-
-	ret = talloc_realloc(NULL, list, const char *, len+2);
-	if (ret == NULL) return NULL;
-
-	ret[len] = talloc_strdup(ret, s);
-	if (ret[len] == NULL) return NULL;
-
-	ret[len+1] = NULL;
-
-	return ret;
-}
-
-
-/**
- Set a fd into blocking/nonblocking mode. Uses POSIX O_NONBLOCK if available,
- else
-  if SYSV use O_NDELAY
-  if BSD use FNDELAY
-**/
-
-int ev_set_blocking(int fd, bool set)
-{
-	int val;
-#ifdef O_NONBLOCK
-#define FLAG_TO_SET O_NONBLOCK
-#else
-#ifdef SYSV
-#define FLAG_TO_SET O_NDELAY
-#else /* BSD */
-#define FLAG_TO_SET FNDELAY
-#endif
-#endif
-
-	if((val = fcntl(fd, F_GETFL, 0)) == -1)
-		return -1;
-	if(set) /* Turn blocking on - ie. clear nonblock flag */
-		val &= ~FLAG_TO_SET;
-	else
-		val |= FLAG_TO_SET;
-	return fcntl( fd, F_SETFL, val);
-#undef FLAG_TO_SET
-}
-
-bool ev_set_close_on_exec(int fd)
-{
-#ifdef FD_CLOEXEC
-	int val;
-
-	val = fcntl(fd, F_GETFD, 0);
-	if (val >= 0) {
-		val |= FD_CLOEXEC;
-		val = fcntl(fd, F_SETFD, val);
-		if (val != -1) {
-			return true;
-		}
-	}
-#endif
-	return false;
-}
diff --git a/lib/tevent/tevent_util.h b/lib/tevent/tevent_util.h
deleted file mode 100644
index 311be60..0000000
--- a/lib/tevent/tevent_util.h
+++ /dev/null
@@ -1,192 +0,0 @@
-/*
-   Unix SMB/CIFS implementation.
-
-   Copyright (C) Andrew Tridgell 1998-2010
-   Copyright (C) Jelmer Vernooij 2005
-
-   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 3 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, see <http://www.gnu.org/licenses/>.
-*/
-
-/* To use these macros you must have a structure containing a next and
-   prev pointer */
-
-#ifndef _DLINKLIST_H
-#define _DLINKLIST_H
-
-/*
-  February 2010 - changed list format to have a prev pointer from the
-  list head. This makes DLIST_ADD_END() O(1) even though we only have
-  one list pointer.
-
-  The scheme is as follows:
-
-     1) with no entries in the list:
-          list_head == NULL
-
-     2) with 1 entry in the list:
-          list_head->next == NULL
-          list_head->prev == list_head
-
-     3) with 2 entries in the list:
-          list_head->next == element2
-          list_head->prev == element2
-	  element2->prev == list_head
-	  element2->next == NULL
-
-     4) with N entries in the list:
-          list_head->next == element2
-          list_head->prev == elementN
-	  elementN->prev == element{N-1}
-	  elementN->next == NULL
-
-  This allows us to find the tail of the list by using
-  list_head->prev, which means we can add to the end of the list in
-  O(1) time
-
-
-  Note that the 'type' arguments below are no longer needed, but
-  are kept for now to prevent an incompatible argument change
- */
-
-
-/*
-   add an element at the front of a list
-*/
-#define DLIST_ADD(list, p) \
-do { \
-        if (!(list)) { \
-		(p)->prev = (list) = (p);  \
-		(p)->next = NULL; \
-	} else { \
-		(p)->prev = (list)->prev; \
-		(list)->prev = (p); \
-		(p)->next = (list); \
-		(list) = (p); \
-	} \
-} while (0)
-
-/*
-   remove an element from a list
-   Note that the element doesn't have to be in the list. If it
-   isn't then this is a no-op
-*/
-#define DLIST_REMOVE(list, p) \
-do { \
-	if ((p) == (list)) { \
-		if ((p)->next) (p)->next->prev = (p)->prev; \
-		(list) = (p)->next; \
-	} else if ((list) && (p) == (list)->prev) {	\
-		(p)->prev->next = NULL; \
-		(list)->prev = (p)->prev; \
-	} else { \
-		if ((p)->prev) (p)->prev->next = (p)->next; \
-		if ((p)->next) (p)->next->prev = (p)->prev; \
-	} \
-	if ((p) != (list)) (p)->next = (p)->prev = NULL;	\
-} while (0)
-
-/*
-   find the head of the list given any element in it.
-   Note that this costs O(N), so you should avoid this macro
-   if at all possible!
-*/
-#define DLIST_HEAD(p, result_head) \
-do { \
-       (result_head) = (p); \
-       while (DLIST_PREV(result_head)) (result_head) = (result_head)->prev; \
-} while(0)
-
-/* return the last element in the list */
-#define DLIST_TAIL(list) ((list)?(list)->prev:NULL)
-
-/* return the previous element in the list. */
-#define DLIST_PREV(p) (((p)->prev && (p)->prev->next != NULL)?(p)->prev:NULL)
-
-/* insert 'p' after the given element 'el' in a list. If el is NULL then
-   this is the same as a DLIST_ADD() */
-#define DLIST_ADD_AFTER(list, p, el) \
-do { \
-        if (!(list) || !(el)) { \
-		DLIST_ADD(list, p); \
-	} else { \
-		(p)->prev = (el);   \
-		(p)->next = (el)->next;		\
-		(el)->next = (p);		\
-		if ((p)->next) (p)->next->prev = (p);	\
-		if ((list)->prev == (el)) (list)->prev = (p); \
-	}\
-} while (0)
-
-
-/*
-   add to the end of a list.
-   Note that 'type' is ignored
-*/
-#define DLIST_ADD_END(list, p, type)			\
-do { \
-	if (!(list)) { \
-		DLIST_ADD(list, p); \
-	} else { \
-		DLIST_ADD_AFTER(list, p, (list)->prev); \
-	} \
-} while (0)
-
-/* promote an element to the from of a list */
-#define DLIST_PROMOTE(list, p) \
-do { \
-          DLIST_REMOVE(list, p); \
-          DLIST_ADD(list, p); \
-} while (0)
-
-/*
-   demote an element to the end of a list.
-   Note that 'type' is ignored
-*/
-#define DLIST_DEMOTE(list, p, type)			\
-do { \
-	DLIST_REMOVE(list, p); \
-	DLIST_ADD_END(list, p, NULL);		\
-} while (0)
-
-/*
-   concatenate two lists - putting all elements of the 2nd list at the
-   end of the first list.
-   Note that 'type' is ignored
-*/
-#define DLIST_CONCATENATE(list1, list2, type)	\
-do { \
-	if (!(list1)) { \
-		(list1) = (list2); \
-	} else { \
-		(list1)->prev->next = (list2); \
-		if (list2) { \
-			void *_tmplist = (void *)(list1)->prev; \
-			(list1)->prev = (list2)->prev; \
-			(list2)->prev = _tmplist; \
-		} \
-	} \
-} while (0)
-
-#endif /* _DLINKLIST_H */
-
-const char **ev_str_list_add(const char **list, const char *s);
-int ev_set_blocking(int fd, bool set);
-size_t ev_str_list_length(const char **list);
-bool ev_set_close_on_exec(int fd);
-
-/* Defined here so we can build against older talloc versions that don't
- * have this define yet. */
-#ifndef TALLOC_FREE
-#define TALLOC_FREE(ctx) do { talloc_free(ctx); ctx=NULL; } while(0)
-#endif
diff --git a/lib/tevent/tevent_wakeup.c b/lib/tevent/tevent_wakeup.c
deleted file mode 100644
index d7cac06..0000000
--- a/lib/tevent/tevent_wakeup.c
+++ /dev/null
@@ -1,69 +0,0 @@
-/*
-   Unix SMB/CIFS implementation.
-   Infrastructure for async requests
-   Copyright (C) Volker Lendecke 2008
-   Copyright (C) Stefan Metzmacher 2009
-
-     ** NOTE! The following LGPL license applies to the tevent
-     ** library. This does NOT imply that all of Samba is released
-     ** under the LGPL
-
-   This library is free software; you can redistribute it and/or
-   modify it under the terms of the GNU Lesser General Public
-   License as published by the Free Software Foundation; either
-   version 3 of the License, or (at your option) any later version.
-
-   This library 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
-   Lesser General Public License for more details.
-
-   You should have received a copy of the GNU Lesser General Public
-   License along with this library; if not, see <http://www.gnu.org/licenses/>.
-*/
-
-#include "replace.h"
-#include "tevent.h"
-#include "tevent_internal.h"
-#include "tevent_util.h"
-
-struct tevent_wakeup_state {
-	struct timeval wakeup_time;
-};
-
-struct tevent_req *tevent_wakeup_send(TALLOC_CTX *mem_ctx,
-				      struct tevent_context *ev,
-				      struct timeval wakeup_time)
-{
-	struct tevent_req *req;
-	struct tevent_wakeup_state *state;
-
-	req = tevent_req_create(mem_ctx, &state,
-				struct tevent_wakeup_state);
-	if (!req) {
-		return NULL;
-	}
-	state->wakeup_time = wakeup_time;
-
-	if (!tevent_req_set_endtime(req, ev, wakeup_time)) {
-		goto post;
-	}
-
-	return req;
-post:
-	return tevent_req_post(req, ev);
-}
-
-bool tevent_wakeup_recv(struct tevent_req *req)
-{
-	enum tevent_req_state state;
-	uint64_t error;
-
-	if (tevent_req_is_error(req, &state, &error)) {
-		if (state == TEVENT_REQ_TIMED_OUT) {
-			return true;
-		}
-	}
-
-	return false;
-}
diff --git a/lib/util/fault.c b/lib/util/fault.c
index 31ac165..3dddd0e 100644
--- a/lib/util/fault.c
+++ b/lib/util/fault.c
@@ -109,8 +109,7 @@ _PUBLIC_ void call_backtrace(void)
      }
 #undef NAMESIZE
 #else
-	DEBUG(0, ("call_backstrace: not implemented\n"));
-#error bla
+	DEBUG(0, ("call_backtrace: not implemented\n"));
 #endif
 }
 
diff --git a/lib/util/util_file.c b/lib/util/util_file.c
index 21d64b2..3a90201 100644
--- a/lib/util/util_file.c
+++ b/lib/util/util_file.c
@@ -114,3 +114,19 @@ char *hex_encode_talloc(TALLOC_CTX *mem_ctx, const unsigned char *buff_in, size_
 
 	return hex_buffer;
 }
+
+uint8_t *hex_decode_talloc(TALLOC_CTX *mem_ctx, const char *hex_in, size_t *len)
+{
+	int i, num;
+	uint8_t *buffer;
+
+	*len = strlen(hex_in) / 2;
+	buffer = talloc_array(mem_ctx, unsigned char, *len);
+
+	for (i=0; i<*len; i++) {
+		sscanf(&hex_in[i*2], "%02X", &num);
+		buffer[i] = (uint8_t)num;
+	}
+
+	return buffer;
+}
diff --git a/libctdb/control.c b/libctdb/control.c
index 8d14cc8..64cc80e 100644
--- a/libctdb/control.c
+++ b/libctdb/control.c
@@ -16,6 +16,7 @@
    You should have received a copy of the GNU General Public License
    along with this program; if not, see <http://www.gnu.org/licenses/>.
 */
+#include <sys/time.h>
 #include <sys/socket.h>
 #include <string.h>
 #include <ctdb.h>
diff --git a/libctdb/ctdb.c b/libctdb/ctdb.c
index 191b097..dd1b572 100644
--- a/libctdb/ctdb.c
+++ b/libctdb/ctdb.c
@@ -17,6 +17,7 @@
    You should have received a copy of the GNU General Public License
    along with this program; if not, see <http://www.gnu.org/licenses/>.
 */
+#include <sys/time.h>
 #include <sys/socket.h>
 #include <string.h>
 #include <ctdb.h>
@@ -28,6 +29,7 @@
 #include <sys/socket.h>
 #include <sys/un.h>
 #include <sys/ioctl.h>
+#include <time.h>
 #include "libctdb_private.h"
 #include "io_elem.h"
 #include "local_tdb.h"
@@ -179,12 +181,12 @@ struct ctdb_connection *ctdb_connect(const char *addr,
 	if (ctdb->fd < 0)
 		goto free_fail;
 
-	set_nonblocking(ctdb->fd);
-	set_close_on_exec(ctdb->fd);
-
 	if (connect(ctdb->fd, (struct sockaddr *)&sun, sizeof(sun)) == -1)
 		goto close_fail;
 
+	set_nonblocking(ctdb->fd);
+	set_close_on_exec(ctdb->fd);
+
 	/* Immediately queue a request to get our pnn. */
 	if (!ctdb_getpnn_send(ctdb, CTDB_CURRENT_NODE, set_pnn, NULL))
 		goto close_fail;
diff --git a/libctdb/local_tdb.c b/libctdb/local_tdb.c
index 506e974..4009136 100644
--- a/libctdb/local_tdb.c
+++ b/libctdb/local_tdb.c
@@ -18,6 +18,7 @@
    along with this program; if not, see <http://www.gnu.org/licenses/>.
 */
 
+#include <sys/time.h>
 #include <sys/socket.h>
 #include <ctdb.h>
 #include <tdb.h>
diff --git a/libctdb/logging.c b/libctdb/logging.c
index d897b6f..2f33a3b 100644
--- a/libctdb/logging.c
+++ b/libctdb/logging.c
@@ -16,6 +16,7 @@
    You should have received a copy of the GNU General Public License
    along with this program; if not, see <http://www.gnu.org/licenses/>.
 */
+#include <sys/time.h>
 #include <sys/socket.h>
 #include <stdio.h>
 #include <errno.h>
diff --git a/libctdb/sync.c b/libctdb/sync.c
index 9a82747..ee49e38 100644
--- a/libctdb/sync.c
+++ b/libctdb/sync.c
@@ -16,6 +16,7 @@
    You should have received a copy of the GNU General Public License
    along with this program; if not, see <http://www.gnu.org/licenses/>.
 */
+#include <sys/time.h>
 #include <sys/socket.h>
 #include <ctdb.h>
 #include <stdbool.h>
diff --git a/packaging/RPM/ctdb.spec b/packaging/RPM/ctdb.spec
index f86abd0..2a31fe9 100644
--- a/packaging/RPM/ctdb.spec
+++ b/packaging/RPM/ctdb.spec
@@ -3,7 +3,7 @@ Name: ctdb
 Summary: Clustered TDB
 Vendor: Samba Team
 Packager: Samba Team <samba at samba.org>
-Version: 2.1
+Version: 2.2
 Release: 1
 Epoch: 0
 License: GNU GPL version 3
@@ -13,7 +13,7 @@ URL: http://ctdb.samba.org/
 Source: ctdb-%{version}.tar.gz
 
 # Packages
-Requires: coreutils, sed, gawk, iptables, iproute, procps, ethtool
+Requires: coreutils, sed, gawk, iptables, iproute, procps, ethtool, sudo
 # Commands - package name might vary
 Requires: /usr/bin/killall, /bin/kill, /bin/netstat
 # Directories
@@ -45,6 +45,12 @@ BuildRequires: libtdb-devel >= %{libtdb_version}
 BuildRequires: libtevent-devel >= %{libtevent_version}
 %endif
 
+# To build the ctdb-pcp-pmda package, run rpmbuild with "--with pmda"
+%define with_pcp_pmda  %{?_with_pmda: 1} %{?!_with_pmda: 0}
+%if %with_pcp_pmda
+BuildRequires: pcp-libs-devel
+%endif
+
 %description
 ctdb is the clustered database used by samba
 
@@ -81,6 +87,9 @@ CFLAGS="$RPM_OPT_FLAGS $EXTRA -O0 -D_GNU_SOURCE" ./configure \
 %if %with_included_tevent
 	--with-included-tevent \
 %endif
+%if %with_pcp_pmda
+	--enable-pmda \
+%endif
 	--prefix=%{_prefix} \
 	--sysconfdir=%{_sysconfdir} \
 	--mandir=%{_mandir} \
@@ -96,6 +105,7 @@ rm -rf $RPM_BUILD_ROOT
 # Create the target build directory hierarchy
 mkdir -p $RPM_BUILD_ROOT%{_sysconfdir}/sysconfig
 mkdir -p $RPM_BUILD_ROOT%{_sysconfdir}/init.d
+mkdir -p $RPM_BUILD_ROOT%{_sysconfdir}/sudoers.d
 
 make DESTDIR=$RPM_BUILD_ROOT docdir=%{_docdir} install install_tests
 
@@ -126,6 +136,7 @@ rm -rf $RPM_BUILD_ROOT
 %config(noreplace) %{_sysconfdir}/ctdb/gcore_trace.sh
 %config(noreplace) %{_sysconfdir}/ctdb/functions
 %attr(755,root,root) %{initdir}/ctdb
+%attr(755,root,root) %{_sysconfdir}/ctdb/notify.d
 
 %{_docdir}/ctdb/README
 %{_docdir}/ctdb/COPYING
@@ -136,6 +147,7 @@ rm -rf $RPM_BUILD_ROOT
 %{_docdir}/ctdb/onnode.1.html
 %{_docdir}/ctdb/ltdbtool.1.html
 %{_docdir}/ctdb/ping_pong.1.html
+%{_sysconfdir}/sudoers.d/ctdb
 %{_sysconfdir}/ctdb/events.d/00.ctdb
 %{_sysconfdir}/ctdb/events.d/01.reclock
 %{_sysconfdir}/ctdb/events.d/10.interface
@@ -154,9 +166,16 @@ rm -rf $RPM_BUILD_ROOT
 %{_sysconfdir}/ctdb/events.d/62.cnfs
 %{_sysconfdir}/ctdb/events.d/70.iscsi
 %{_sysconfdir}/ctdb/events.d/91.lvs
+%config(noreplace) %{_sysconfdir}/ctdb/nfs-rpc-checks.d/10.statd.check
+%config(noreplace) %{_sysconfdir}/ctdb/nfs-rpc-checks.d/20.nfsd.check
+%config(noreplace) %{_sysconfdir}/ctdb/nfs-rpc-checks.d/30.lockd.check
+%config(noreplace) %{_sysconfdir}/ctdb/nfs-rpc-checks.d/40.mountd.check
+%config(noreplace) %{_sysconfdir}/ctdb/nfs-rpc-checks.d/50.rquotad.check
 %{_sysconfdir}/ctdb/statd-callout
+%{_sysconfdir}/ctdb/notify.d/README
 %{_sbindir}/ctdbd
 %{_bindir}/ctdb
+%{_bindir}/ctdb_lock_helper
 %{_bindir}/smnotify
 %{_bindir}/ping_pong
 %{_bindir}/ltdbtool
@@ -206,6 +225,24 @@ test suite for ctdb
 %{_bindir}/ctdb_run_cluster_tests
 %doc tests/README
 
+%if %with_pcp_pmda
+
+%package pcp-pmda
+Summary: CTDB PCP pmda support
+Group: Development/Tools
+Requires: ctdb = %{version}
+Requires: pcp-libs
+
+%description pcp-pmda
+Performance Co-Pilot (PCP) support for CTDB
+
+%files pcp-pmda
+%dir /var/lib/pcp/pmdas/ctdb
+/var/lib/pcp/pmdas/ctdb/*
+
+%endif
+
+
 
 %changelog
 * Thu Mar 1 2012 : Version 1.13
diff --git a/packaging/RPM/ctdb.spec.in b/packaging/RPM/ctdb.spec.in
index 50287ab..44bd46f 100644
--- a/packaging/RPM/ctdb.spec.in
+++ b/packaging/RPM/ctdb.spec.in
@@ -13,7 +13,7 @@ URL: http://ctdb.samba.org/
 Source: ctdb-%{version}.tar.gz
 
 # Packages
-Requires: coreutils, sed, gawk, iptables, iproute, procps, ethtool
+Requires: coreutils, sed, gawk, iptables, iproute, procps, ethtool, sudo
 # Commands - package name might vary
 Requires: /usr/bin/killall, /bin/kill, /bin/netstat
 # Directories
@@ -45,6 +45,12 @@ BuildRequires: libtdb-devel >= %{libtdb_version}
 BuildRequires: libtevent-devel >= %{libtevent_version}
 %endif
 
+# To build the ctdb-pcp-pmda package, run rpmbuild with "--with pmda"
+%define with_pcp_pmda  %{?_with_pmda: 1} %{?!_with_pmda: 0}
+%if %with_pcp_pmda
+BuildRequires: pcp-libs-devel
+%endif
+
 %description
 ctdb is the clustered database used by samba
 
@@ -81,6 +87,9 @@ CFLAGS="$RPM_OPT_FLAGS $EXTRA -O0 -D_GNU_SOURCE" ./configure \
 %if %with_included_tevent
 	--with-included-tevent \
 %endif
+%if %with_pcp_pmda
+	--enable-pmda \
+%endif
 	--prefix=%{_prefix} \
 	--sysconfdir=%{_sysconfdir} \
 	--mandir=%{_mandir} \
@@ -96,6 +105,7 @@ rm -rf $RPM_BUILD_ROOT
 # Create the target build directory hierarchy
 mkdir -p $RPM_BUILD_ROOT%{_sysconfdir}/sysconfig
 mkdir -p $RPM_BUILD_ROOT%{_sysconfdir}/init.d
+mkdir -p $RPM_BUILD_ROOT%{_sysconfdir}/sudoers.d
 
 make DESTDIR=$RPM_BUILD_ROOT docdir=%{_docdir} install install_tests
 
@@ -126,6 +136,7 @@ rm -rf $RPM_BUILD_ROOT
 %config(noreplace) %{_sysconfdir}/ctdb/gcore_trace.sh
 %config(noreplace) %{_sysconfdir}/ctdb/functions
 %attr(755,root,root) %{initdir}/ctdb
+%attr(755,root,root) %{_sysconfdir}/ctdb/notify.d
 
 %{_docdir}/ctdb/README
 %{_docdir}/ctdb/COPYING
@@ -136,6 +147,7 @@ rm -rf $RPM_BUILD_ROOT
 %{_docdir}/ctdb/onnode.1.html
 %{_docdir}/ctdb/ltdbtool.1.html
 %{_docdir}/ctdb/ping_pong.1.html
+%{_sysconfdir}/sudoers.d/ctdb
 %{_sysconfdir}/ctdb/events.d/00.ctdb
 %{_sysconfdir}/ctdb/events.d/01.reclock
 %{_sysconfdir}/ctdb/events.d/10.interface
@@ -154,9 +166,16 @@ rm -rf $RPM_BUILD_ROOT
 %{_sysconfdir}/ctdb/events.d/62.cnfs
 %{_sysconfdir}/ctdb/events.d/70.iscsi
 %{_sysconfdir}/ctdb/events.d/91.lvs
+%config(noreplace) %{_sysconfdir}/ctdb/nfs-rpc-checks.d/10.statd.check
+%config(noreplace) %{_sysconfdir}/ctdb/nfs-rpc-checks.d/20.nfsd.check
+%config(noreplace) %{_sysconfdir}/ctdb/nfs-rpc-checks.d/30.lockd.check
+%config(noreplace) %{_sysconfdir}/ctdb/nfs-rpc-checks.d/40.mountd.check
+%config(noreplace) %{_sysconfdir}/ctdb/nfs-rpc-checks.d/50.rquotad.check
 %{_sysconfdir}/ctdb/statd-callout
+%{_sysconfdir}/ctdb/notify.d/README
 %{_sbindir}/ctdbd
 %{_bindir}/ctdb
+%{_bindir}/ctdb_lock_helper
 %{_bindir}/smnotify
 %{_bindir}/ping_pong
 %{_bindir}/ltdbtool
@@ -206,6 +225,24 @@ test suite for ctdb
 %{_bindir}/ctdb_run_cluster_tests
 %doc tests/README
 
+%if %with_pcp_pmda
+
+%package pcp-pmda
+Summary: CTDB PCP pmda support
+Group: Development/Tools
+Requires: ctdb = %{version}
+Requires: pcp-libs
+
+%description pcp-pmda
+Performance Co-Pilot (PCP) support for CTDB
+
+%files pcp-pmda
+%dir /var/lib/pcp/pmdas/ctdb
+/var/lib/pcp/pmdas/ctdb/*
+
+%endif
+
+
 
 %changelog
 * Thu Mar 1 2012 : Version 1.13
diff --git a/packaging/RPM/makerpms.sh b/packaging/RPM/makerpms.sh
index c216185..8dbec55 100755
--- a/packaging/RPM/makerpms.sh
+++ b/packaging/RPM/makerpms.sh
@@ -32,7 +32,7 @@
 #   /usr/src/redhat directory
 #
 
-EXTRA_OPTIONS="$1"
+EXTRA_OPTIONS="$*"
 
 DIRNAME=$(dirname $0)
 TOPDIR=${DIRNAME}/../..
@@ -52,7 +52,7 @@ mkdir -p `rpm --eval %_rpmdir`/noarch
 mkdir -p `rpm --eval %_rpmdir`/i386
 mkdir -p `rpm --eval %_rpmdir`/x86_64
 
-VERSION=$(${TOPDIR}/packaging/mkversion.sh ${TOPDIR}/include/version.h)
+VERSION=$(${TOPDIR}/packaging/mkversion.sh ${TOPDIR}/include/ctdb_version.h)
 if [ -z "$VERSION" ]; then
     exit 1
 fi
diff --git a/packaging/maketarball.sh b/packaging/maketarball.sh
index 221fede..be19869 100755
--- a/packaging/maketarball.sh
+++ b/packaging/maketarball.sh
@@ -1,4 +1,4 @@
-#!/bin/sh
+#!/bin/bash
 #
 # maketarball.sh - create a tarball from the git branch HEAD
 #
@@ -35,7 +35,7 @@ fi
 TAR_PREFIX_TMP="ctdb-tmp"
 SPECFILE=/tmp/${TAR_PREFIX_TMP}/packaging/RPM/ctdb.spec
 SPECFILE_IN=${SPECFILE}.in
-VERSION_H=/tmp/${TAR_PREFIX_TMP}/include/version.h
+VERSION_H=/tmp/${TAR_PREFIX_TMP}/include/ctdb_version.h
 
 if echo | gzip -c --rsyncable - > /dev/null 2>&1 ; then
 	GZIP="gzip -9 --rsyncable"
diff --git a/packaging/mkversion.sh b/packaging/mkversion.sh
index 18b432a..4a80b25 100755
--- a/packaging/mkversion.sh
+++ b/packaging/mkversion.sh
@@ -25,7 +25,7 @@
 OUTPUT=$1
 
 if [ -z "$OUTPUT" ]; then
-    OUTPUT="include/version.h"
+    OUTPUT="include/ctdb_version.h"
 fi
 
 # We use tags and determine the version, as follows:
diff --git a/server/ctdb_call.c b/server/ctdb_call.c
index 67219c4..a98903d 100644
--- a/server/ctdb_call.c
+++ b/server/ctdb_call.c
@@ -113,20 +113,9 @@ static void ctdb_send_error(struct ctdb_context *ctdb,
  * to its local ctdb (ctdb_request_call). If the node is not itself
  * the record's DMASTER, it first redirects the packet to  the
  * record's LMASTER. The LMASTER then redirects the call packet to
- * the current DMASTER. But there is a race: The record may have
- * been migrated off the DMASTER while the redirected packet is
- * on the wire (or in the local queue). So in case the record has
- * migrated off the new destinaton of the call packet, instead of
- * going back to the LMASTER to get the new DMASTER, we try to
- * reduce round-trips by first chasing the record a couple of times
- * before giving up the direct chase and finally going back to the
- * LMASTER (again). Note that this works because of this: When
+ * the current DMASTER. Note that this works because of this: When
  * a record is migrated off a node, then the new DMASTER is stored
  * in the record's copy on the former DMASTER.
- *
- * The maximum number of attempts for direct chase to make before
- * going back to the LMASTER is configurable by the tunable
- * "MaxRedirectCount".
  */
 static void ctdb_call_send_redirect(struct ctdb_context *ctdb,
 				    struct ctdb_db_context *ctdb_db,
@@ -134,7 +123,6 @@ static void ctdb_call_send_redirect(struct ctdb_context *ctdb,
 				    struct ctdb_req_call *c, 
 				    struct ctdb_ltdb_header *header)
 {
-	
 	uint32_t lmaster = ctdb_lmaster(ctdb, &key);
 
 	c->hdr.destnode = lmaster;
@@ -343,7 +331,7 @@ static void ctdb_become_dmaster(struct ctdb_db_context *ctdb_db,
 	DEBUG(DEBUG_DEBUG,("pnn %u dmaster response %08x\n", ctdb->pnn, ctdb_hash(&key)));
 
 	ZERO_STRUCT(header);
-	header.rsn = rsn + 1;
+	header.rsn = rsn;
 	header.dmaster = ctdb->pnn;
 	header.flags = record_flags;
 
@@ -787,7 +775,7 @@ void ctdb_request_call(struct ctdb_context *ctdb, struct ctdb_req_header *hdr)
 	}
 
 	if (header.flags & CTDB_REC_RO_REVOKE_COMPLETE) {
-		header.flags &= ~(CTDB_REC_RO_HAVE_DELEGATIONS|CTDB_REC_RO_HAVE_READONLY|CTDB_REC_RO_REVOKING_READONLY|CTDB_REC_RO_REVOKE_COMPLETE);
+		header.flags &= ~CTDB_REC_RO_FLAGS;
 		CTDB_INCREMENT_STAT(ctdb, total_ro_revokes);
 		CTDB_INCREMENT_DB_STAT(ctdb_db, db_ro_revokes);
 		if (ctdb_ltdb_store(ctdb_db, call->key, &header, data) != 0) {
@@ -813,8 +801,11 @@ void ctdb_request_call(struct ctdb_context *ctdb, struct ctdb_req_header *hdr)
 		return;
 	}
 
-	/* if we are not the dmaster and are not hosting any delegations,
-	   then send a redirect to the requesting node */
+	/*
+	 * If we are not the dmaster and are not hosting any delegations,
+	 * then we redirect the request to the node than can answer it
+	 * (the lmaster or the dmaster).
+	 */
 	if ((header.dmaster != ctdb->pnn) 
 	    && (!(header.flags & CTDB_REC_RO_HAVE_DELEGATIONS)) ) {
 		talloc_free(data.dptr);
diff --git a/server/ctdb_control.c b/server/ctdb_control.c
index 9708acd..bf4a20d 100644
--- a/server/ctdb_control.c
+++ b/server/ctdb_control.c
@@ -100,6 +100,7 @@ static int32_t ctdb_control_dispatch(struct ctdb_context *ctdb,
 		int i;
 		CHECK_CONTROL_DATA_SIZE(0);
 		ctdb->statistics.memory_used = talloc_total_size(NULL);
+		ctdb->statistics.num_clients = ctdb->num_clients;
 		ctdb->statistics.frozen = 0;
 		for (i=1; i<= NUM_DB_PRIORITIES; i++) {
 			if (ctdb->freeze_mode[i] == CTDB_FREEZE_FROZEN) {
@@ -169,7 +170,9 @@ static int32_t ctdb_control_dispatch(struct ctdb_context *ctdb,
 
 	case CTDB_CONTROL_SET_DMASTER: 
 		CHECK_CONTROL_DATA_SIZE(sizeof(struct ctdb_control_set_dmaster));
-		return ctdb_control_set_dmaster(ctdb, indata);
+		DEBUG(DEBUG_ERR, ("The SET_DMASTER control is not implemented "
+				  "any more.\n"));
+		return  -1;
 
 	case CTDB_CONTROL_PUSH_DB:
 		return ctdb_control_push_db(ctdb, indata);
@@ -202,7 +205,14 @@ static int32_t ctdb_control_dispatch(struct ctdb_context *ctdb,
 
 	case CTDB_CONTROL_PING:
 		CHECK_CONTROL_DATA_SIZE(0);
-		return ctdb->statistics.num_clients;
+		return ctdb->num_clients;
+
+	case CTDB_CONTROL_GET_RUNSTATE:
+		CHECK_CONTROL_DATA_SIZE(0);
+		outdata->dptr = (uint8_t *)&ctdb->runstate;
+		outdata->dsize = sizeof(uint32_t);
+		return 0;
+
 
 	case CTDB_CONTROL_SET_DB_READONLY: {
 		uint32_t db_id;
@@ -264,6 +274,9 @@ static int32_t ctdb_control_dispatch(struct ctdb_context *ctdb,
 	case CTDB_CONTROL_TRAVERSE_ALL:
 		return ctdb_control_traverse_all(ctdb, indata, outdata);
 
+	case CTDB_CONTROL_TRAVERSE_ALL_EXT:
+		return ctdb_control_traverse_all_ext(ctdb, indata, outdata);
+
 	case CTDB_CONTROL_TRAVERSE_DATA:
 		return ctdb_control_traverse_data(ctdb, indata, outdata);
 
@@ -319,6 +332,7 @@ static int32_t ctdb_control_dispatch(struct ctdb_context *ctdb,
 
 	case CTDB_CONTROL_SHUTDOWN:
 		DEBUG(DEBUG_NOTICE,("Received SHUTDOWN command. Stopping CTDB daemon.\n"));
+		ctdb_set_runstate(ctdb, CTDB_RUNSTATE_SHUTDOWN);
 		ctdb_stop_recoverd(ctdb);
 		ctdb_stop_keepalive(ctdb);
 		ctdb_stop_monitoring(ctdb);
@@ -345,6 +359,10 @@ static int32_t ctdb_control_dispatch(struct ctdb_context *ctdb,
 		CHECK_CONTROL_DATA_SIZE(sizeof(struct ctdb_public_ip));
 		return ctdb_control_release_ip(ctdb, c, indata, async_reply);
 
+	case CTDB_CONTROL_IPREALLOCATED:
+		CHECK_CONTROL_DATA_SIZE(0);
+		return ctdb_control_ipreallocated(ctdb, c, async_reply);
+
 	case CTDB_CONTROL_GET_PUBLIC_IPSv4:
 		CHECK_CONTROL_DATA_SIZE(0);
 		return ctdb_control_get_public_ipsv4(ctdb, c, outdata);
@@ -511,7 +529,7 @@ static int32_t ctdb_control_dispatch(struct ctdb_context *ctdb,
 
 	case CTDB_CONTROL_STOP_NODE:
 		CHECK_CONTROL_DATA_SIZE(0);
-		return ctdb_control_stop_node(ctdb, c, async_reply);
+		return ctdb_control_stop_node(ctdb);
 
 	case CTDB_CONTROL_CONTINUE_NODE:
 		CHECK_CONTROL_DATA_SIZE(0);
@@ -648,6 +666,9 @@ static int32_t ctdb_control_dispatch(struct ctdb_context *ctdb,
 		CHECK_CONTROL_DATA_SIZE(0);
 		return ctdb_control_reload_public_ips(ctdb, c, async_reply);
 
+	case CTDB_CONTROL_RECEIVE_RECORDS:
+		return ctdb_control_receive_records(ctdb, indata, outdata);
+
 	default:
 		DEBUG(DEBUG_CRIT,(__location__ " Unknown CTDB control opcode %u\n", opcode));
 		return -1;
diff --git a/server/ctdb_daemon.c b/server/ctdb_daemon.c
index fdfd5de..cedee09 100644
--- a/server/ctdb_daemon.c
+++ b/server/ctdb_daemon.c
@@ -24,6 +24,7 @@
 #include "system/network.h"
 #include "system/filesys.h"
 #include "system/wait.h"
+#include "../include/ctdb_version.h"
 #include "../include/ctdb_client.h"
 #include "../include/ctdb_private.h"
 #include "../common/rb_tree.h"
@@ -36,11 +37,17 @@ struct ctdb_client_pid_list {
 	struct ctdb_client *client;
 };
 
+const char *ctdbd_pidfile = NULL;
+
 static void daemon_incoming_packet(void *, struct ctdb_req_header *);
 
 static void print_exit_message(void)
 {
-	DEBUG(DEBUG_NOTICE,("CTDB daemon shutting down\n"));
+	if (debug_extra != NULL && debug_extra[0] != '\0') {
+		DEBUG(DEBUG_NOTICE,("CTDB %s shutting down\n", debug_extra));
+	} else {
+		DEBUG(DEBUG_NOTICE,("CTDB daemon shutting down\n"));
+	}
 }
 
 
@@ -69,25 +76,8 @@ static void ctdb_start_time_tickd(struct ctdb_context *ctdb)
 			ctdb_time_tick, ctdb);
 }
 
-
-/* called when CTDB is ready to process requests */
-static void ctdb_start_transport(struct ctdb_context *ctdb)
+static void ctdb_start_periodic_events(struct ctdb_context *ctdb)
 {
-	/* start the transport running */
-	if (ctdb->methods->start(ctdb) != 0) {
-		DEBUG(DEBUG_ALERT,("transport failed to start!\n"));
-		ctdb_fatal(ctdb, "transport failed to start");
-	}
-
-	/* start the recovery daemon process */
-	if (ctdb_start_recoverd(ctdb) != 0) {
-		DEBUG(DEBUG_ALERT,("Failed to start recovery daemon\n"));
-		exit(11);
-	}
-
-	/* Make sure we log something when the daemon terminates */
-	atexit(print_exit_message);
-
 	/* start monitoring for connected/disconnected nodes */
 	ctdb_start_keepalive(ctdb);
 
@@ -221,13 +211,7 @@ int daemon_check_srvids(struct ctdb_context *ctdb, TDB_DATA indata,
 		return -1;
 	}
 	for (i=0; i<num_ids; i++) {
-		struct ctdb_message_list *ml;
-		for (ml=ctdb->message_list; ml; ml=ml->next) {
-			if (ml->srvid == ids[i]) {
-				break;
-			}
-		}
-		if (ml != NULL) {
+		if (ctdb_check_message_handler(ctdb, ids[i])) {
 			results[i/8] |= (1 << (i%8));
 		}
 	}
@@ -245,7 +229,7 @@ static int ctdb_client_destructor(struct ctdb_client *client)
 
 	ctdb_takeover_client_destructor_hook(client);
 	ctdb_reqid_remove(client->ctdb, client->client_id);
-	CTDB_DECREMENT_STAT(client->ctdb, num_clients);
+	client->ctdb->num_clients--;
 
 	if (client->num_persistent_updates != 0) {
 		DEBUG(DEBUG_ERR,(__location__ " Client disconnecting with %u persistent updates in flight. Starting recovery\n", client->num_persistent_updates));
@@ -688,7 +672,7 @@ static void daemon_request_call_from_client(struct ctdb_client *client,
 	}
 
 	if (header.flags & CTDB_REC_RO_REVOKE_COMPLETE) {
-		header.flags &= ~(CTDB_REC_RO_HAVE_DELEGATIONS|CTDB_REC_RO_HAVE_READONLY|CTDB_REC_RO_REVOKING_READONLY|CTDB_REC_RO_REVOKE_COMPLETE);
+		header.flags &= ~CTDB_REC_RO_FLAGS;
 		CTDB_INCREMENT_STAT(ctdb, total_ro_revokes);
 		CTDB_INCREMENT_DB_STAT(ctdb_db, db_ro_revokes);
 		if (ctdb_ltdb_store(ctdb_db, key, &header, data) != 0) {
@@ -974,7 +958,7 @@ static void ctdb_accept_client(struct event_context *ev, struct fd_event *fde,
 
 	talloc_set_destructor(client, ctdb_client_destructor);
 	talloc_set_destructor(client_pid, ctdb_clientpid_destructor);
-	CTDB_INCREMENT_STAT(ctdb, num_clients);
+	ctdb->num_clients++;
 }
 
 
@@ -1048,16 +1032,26 @@ static void ctdb_setup_event_callback(struct ctdb_context *ctdb, int status,
 				      void *private_data)
 {
 	if (status != 0) {
-		ctdb_fatal(ctdb, "Failed to run setup event\n");
-		return;
+		DEBUG(DEBUG_ALERT,("Failed to run setup event - exiting\n"));
+		exit(1);
 	}
 	ctdb_run_notification_script(ctdb, "setup");
 
+	ctdb_set_runstate(ctdb, CTDB_RUNSTATE_FIRST_RECOVERY);
+
 	/* tell all other nodes we've just started up */
 	ctdb_daemon_send_control(ctdb, CTDB_BROADCAST_ALL,
 				 0, CTDB_CONTROL_STARTUP, 0,
 				 CTDB_CTRL_FLAG_NOREPLY,
 				 tdb_null, NULL, NULL);
+
+	/* Start the recovery daemon */
+	if (ctdb_start_recoverd(ctdb) != 0) {
+		DEBUG(DEBUG_ALERT,("Failed to start recovery daemon\n"));
+		exit(11);
+	}
+
+	ctdb_start_periodic_events(ctdb);
 }
 
 static struct timeval tevent_before_wait_ts;
@@ -1105,6 +1099,38 @@ static void ctdb_tevent_trace(enum tevent_trace_point tp,
 	}
 }
 
+static void ctdb_remove_pidfile(void)
+{
+	if (ctdbd_pidfile != NULL && !ctdb_is_child_process()) {
+		if (unlink(ctdbd_pidfile) == 0) {
+			DEBUG(DEBUG_NOTICE, ("Removed PID file %s\n",
+					     ctdbd_pidfile));
+		} else {
+			DEBUG(DEBUG_WARNING, ("Failed to Remove PID file %s\n",
+					      ctdbd_pidfile));
+		}
+	}
+}
+
+static void ctdb_create_pidfile(pid_t pid)
+{
+	if (ctdbd_pidfile != NULL) {
+		FILE *fp;
+
+		fp = fopen(ctdbd_pidfile, "w");
+		if (fp == NULL) {
+			DEBUG(DEBUG_ALERT,
+			      ("Failed to open PID file %s\n", ctdbd_pidfile));
+			exit(11);
+		}
+
+		fprintf(fp, "%d\n", pid);
+		fclose(fp);
+		DEBUG(DEBUG_NOTICE, ("Created PID file %s\n", ctdbd_pidfile));
+		atexit(ctdb_remove_pidfile);
+	}
+}
+
 /*
   start the protocol going as a daemon
 */
@@ -1142,8 +1168,9 @@ int ctdb_start_daemon(struct ctdb_context *ctdb, bool do_fork, bool use_syslog,
 
 	ctdbd_pid = getpid();
 	ctdb->ctdbd_pid = ctdbd_pid;
-
-	DEBUG(DEBUG_ERR, ("Starting CTDBD as pid : %u\n", ctdbd_pid));
+	DEBUG(DEBUG_ERR, ("Starting CTDBD (Version %s) as PID: %u\n",
+			  CTDB_VERSION_STRING, ctdbd_pid));
+	ctdb_create_pidfile(ctdb->ctdbd_pid);
 
 	if (ctdb->do_setsched) {
 		/* try to set us up as realtime */
@@ -1173,6 +1200,12 @@ int ctdb_start_daemon(struct ctdb_context *ctdb, bool do_fork, bool use_syslog,
 	}
 
 	ctdb_set_child_logging(ctdb);
+	if (use_syslog) {
+		if (start_syslog_daemon(ctdb)) {
+			DEBUG(DEBUG_CRIT, ("Failed to start syslog daemon\n"));
+			exit(10);
+		}
+	}
 
 	/* initialize statistics collection */
 	ctdb_statistics_init(ctdb);
@@ -1225,6 +1258,7 @@ int ctdb_start_daemon(struct ctdb_context *ctdb, bool do_fork, bool use_syslog,
 		ctdb_fatal(ctdb, "Failed to attach to databases\n");
 	}
 
+	ctdb_set_runstate(ctdb, CTDB_RUNSTATE_INIT);
 	ret = ctdb_event_script(ctdb, CTDB_EVENT_INIT);
 	if (ret != 0) {
 		ctdb_fatal(ctdb, "Failed to run init event\n");
@@ -1247,9 +1281,21 @@ int ctdb_start_daemon(struct ctdb_context *ctdb, bool do_fork, bool use_syslog,
 		ctdb_release_all_ips(ctdb);
 	}
 
-	/* start the transport going */
-	ctdb_start_transport(ctdb);
 
+	/* Make sure we log something when the daemon terminates */
+	atexit(print_exit_message);
+
+	/* Start the transport */
+	if (ctdb->methods->start(ctdb) != 0) {
+		DEBUG(DEBUG_ALERT,("transport failed to start!\n"));
+		ctdb_fatal(ctdb, "transport failed to start");
+	}
+
+	/* Recovery daemon and timed events are started from the
+	 * callback, only after the setup event completes
+	 * successfully.
+	 */
+	ctdb_set_runstate(ctdb, CTDB_RUNSTATE_SETUP);
 	ret = ctdb_event_script_callback(ctdb,
 					 ctdb,
 					 ctdb_setup_event_callback,
@@ -1263,13 +1309,6 @@ int ctdb_start_daemon(struct ctdb_context *ctdb, bool do_fork, bool use_syslog,
 		exit(1);
 	}
 
-	if (use_syslog) {
-		if (start_syslog_daemon(ctdb)) {
-			DEBUG(DEBUG_CRIT, ("Failed to start syslog daemon\n"));
-			exit(10);
-		}
-	}
-
 	ctdb_lockdown_memory(ctdb);
 	  
 	/* go into a wait loop to allow other nodes to complete */
diff --git a/server/ctdb_lock.c b/server/ctdb_lock.c
index 8a2ba5c..77b4da8 100644
--- a/server/ctdb_lock.c
+++ b/server/ctdb_lock.c
@@ -113,12 +113,15 @@ static bool later_db(struct ctdb_context *ctdb, const char *name)
 	return false;
 }
 
-/*
- * lock all databases
- */
-int ctdb_lockall_prio(struct ctdb_context *ctdb, uint32_t priority)
+typedef int (*db_handler_t)(struct ctdb_db_context *ctdb_db,
+			    uint32_t priority,
+			    void *private_data);
+
+static int ctdb_db_iterator(struct ctdb_context *ctdb, uint32_t priority,
+			    db_handler_t handler, void *private_data)
 {
 	struct ctdb_db_context *ctdb_db;
+	int ret;
 
 	for (ctdb_db = ctdb->db_list; ctdb_db; ctdb_db = ctdb_db->next) {
 		if (ctdb_db->priority != priority) {
@@ -127,11 +130,8 @@ int ctdb_lockall_prio(struct ctdb_context *ctdb, uint32_t priority)
 		if (later_db(ctdb, ctdb_db->db_name)) {
 			continue;
 		}
-		DEBUG(DEBUG_INFO, ("locking database %s, priority:%u\n",
-				   ctdb_db->db_name, priority));
-		if (tdb_lockall(ctdb_db->ltdb->tdb) != 0) {
-			DEBUG(DEBUG_ERR, ("Failed to lock database %s\n",
-					  ctdb_db->db_name));
+		ret = handler(ctdb_db, priority, private_data);
+		if (ret != 0) {
 			return -1;
 		}
 	}
@@ -145,24 +145,8 @@ int ctdb_lockall_prio(struct ctdb_context *ctdb, uint32_t priority)
 		if (!later_db(ctdb, ctdb_db->db_name)) {
 			continue;
 		}
-		DEBUG(DEBUG_INFO, ("locking database %s, priority:%u\n",
-				   ctdb_db->db_name, priority));
-		if (tdb_lockall(ctdb_db->ltdb->tdb) != 0) {
-			DEBUG(DEBUG_ERR, ("Failed to lock database %s\n",
-					  ctdb_db->db_name));
-			return -1;
-		}
-	}
-
-	return 0;
-}
-
-static int ctdb_lockall(struct ctdb_context *ctdb)
-{
-	uint32_t priority;
-
-	for (priority=1; priority<=NUM_DB_PRIORITIES; priority++) {
-		if (ctdb_lockall_prio(ctdb, priority) != 0) {
+		ret = handler(ctdb_db, priority, private_data);
+		if (ret != 0) {
 			return -1;
 		}
 	}
@@ -172,50 +156,33 @@ static int ctdb_lockall(struct ctdb_context *ctdb)
 
 
 /*
- * unlock all databases
+ * lock all databases - mark only
  */
-int ctdb_unlockall_prio(struct ctdb_context *ctdb, uint32_t priority)
+static int db_lock_mark_handler(struct ctdb_db_context *ctdb_db, uint32_t priority,
+				void *private_data)
 {
-	struct ctdb_db_context *ctdb_db;
-
-	for (ctdb_db = ctdb->db_list; ctdb_db; ctdb_db = ctdb_db->next) {
-		if (ctdb_db->priority != priority) {
-			continue;
-		}
-		DEBUG(DEBUG_INFO, ("unlocking database %s, priority:%u\n",
-				   ctdb_db->db_name, priority));
-		if (tdb_unlockall(ctdb_db->ltdb->tdb) != 0) {
-			DEBUG(DEBUG_ERR, ("Failed to unlock database %s\n",
-					  ctdb_db->db_name));
-			return -1;
-		}
-	}
+	int tdb_transaction_write_lock_mark(struct tdb_context *);
 
-	return 0;
-}
+	DEBUG(DEBUG_INFO, ("marking locked database %s, priority:%u\n",
+			   ctdb_db->db_name, priority));
 
-static int ctdb_unlockall(struct ctdb_context *ctdb)
-{
-	uint32_t priority;
+	if (tdb_transaction_write_lock_mark(ctdb_db->ltdb->tdb) != 0) {
+		DEBUG(DEBUG_ERR, ("Failed to mark (transaction lock) database %s\n",
+				  ctdb_db->db_name));
+		return -1;
+	}
 
-	for (priority=NUM_DB_PRIORITIES; priority>=0; priority--) {
-		if (ctdb_unlockall_prio(ctdb, priority) != 0) {
-			return -1;
-		}
+	if (tdb_lockall_mark(ctdb_db->ltdb->tdb) != 0) {
+		DEBUG(DEBUG_ERR, ("Failed to mark (all lock) database %s\n",
+				  ctdb_db->db_name));
+		return -1;
 	}
 
 	return 0;
 }
 
-
-/*
- * lock all databases - mark only
- */
 int ctdb_lockall_mark_prio(struct ctdb_context *ctdb, uint32_t priority)
 {
-	struct ctdb_db_context *ctdb_db;
-	int tdb_transaction_write_lock_mark(struct tdb_context *);
-
 	/*
 	 * This function is only used by the main dameon during recovery.
 	 * At this stage, the databases have already been locked, by a
@@ -228,41 +195,7 @@ int ctdb_lockall_mark_prio(struct ctdb_context *ctdb, uint32_t priority)
 		return -1;
 	}
 
-	for (ctdb_db = ctdb->db_list; ctdb_db; ctdb_db = ctdb_db->next) {
-		if (ctdb_db->priority != priority) {
-			continue;
-		}
-		if (later_db(ctdb, ctdb_db->db_name)) {
-			continue;
-		}
-		if (tdb_transaction_write_lock_mark(ctdb_db->ltdb->tdb) != 0) {
-			return -1;
-		}
-		if (tdb_lockall_mark(ctdb_db->ltdb->tdb) != 0) {
-			/* FIXME: Shouldn't we unmark here? */
-			return -1;
-		}
-	}
-
-	/* If priority != 1, later_db check is not required and can return */
-	if (priority != 1) {
-		return 0;
-	}
-
-	for (ctdb_db = ctdb->db_list; ctdb_db; ctdb_db = ctdb_db->next) {
-		if (!later_db(ctdb, ctdb_db->db_name)) {
-			continue;
-		}
-		if (tdb_transaction_write_lock_mark(ctdb_db->ltdb->tdb) != 0) {
-			return -1;
-		}
-		if (tdb_lockall_mark(ctdb_db->ltdb->tdb) != 0) {
-			/* FIXME: Shouldn't we unmark here? */
-			return -1;
-		}
-	}
-
-	return 0;
+	return ctdb_db_iterator(ctdb, priority, db_lock_mark_handler, NULL);
 }
 
 static int ctdb_lockall_mark(struct ctdb_context *ctdb)
@@ -270,7 +203,7 @@ static int ctdb_lockall_mark(struct ctdb_context *ctdb)
 	uint32_t priority;
 
 	for (priority=1; priority<=NUM_DB_PRIORITIES; priority++) {
-		if (ctdb_lockall_mark_prio(ctdb, priority) != 0) {
+		if (ctdb_db_iterator(ctdb, priority, db_lock_mark_handler, NULL) != 0) {
 			return -1;
 		}
 	}
@@ -282,11 +215,31 @@ static int ctdb_lockall_mark(struct ctdb_context *ctdb)
 /*
  * lock all databases - unmark only
  */
-int ctdb_lockall_unmark_prio(struct ctdb_context *ctdb, uint32_t priority)
+static int db_lock_unmark_handler(struct ctdb_db_context *ctdb_db, uint32_t priority,
+				  void *private_data)
 {
-	struct ctdb_db_context *ctdb_db;
 	int tdb_transaction_write_lock_unmark(struct tdb_context *);
 
+	DEBUG(DEBUG_INFO, ("unmarking locked database %s, priority:%u\n",
+			   ctdb_db->db_name, priority));
+
+	if (tdb_transaction_write_lock_unmark(ctdb_db->ltdb->tdb) != 0) {
+		DEBUG(DEBUG_ERR, ("Failed to unmark (transaction lock) database %s\n",
+				  ctdb_db->db_name));
+		return -1;
+	}
+
+	if (tdb_lockall_unmark(ctdb_db->ltdb->tdb) != 0) {
+		DEBUG(DEBUG_ERR, ("Failed to unmark (all lock) database %s\n",
+				  ctdb_db->db_name));
+		return -1;
+	}
+
+	return 0;
+}
+
+int ctdb_lockall_unmark_prio(struct ctdb_context *ctdb, uint32_t priority)
+{
 	/*
 	 * This function is only used by the main dameon during recovery.
 	 * At this stage, the databases have already been locked, by a
@@ -299,19 +252,7 @@ int ctdb_lockall_unmark_prio(struct ctdb_context *ctdb, uint32_t priority)
 		return -1;
 	}
 
-	for (ctdb_db = ctdb->db_list; ctdb_db; ctdb_db = ctdb_db->next) {
-		if (ctdb_db->priority != priority) {
-			continue;
-		}
-		if (tdb_transaction_write_lock_unmark(ctdb_db->ltdb->tdb) != 0) {
-			return -1;
-		}
-		if (tdb_lockall_unmark(ctdb_db->ltdb->tdb) != 0) {
-			return -1;
-		}
-	}
-
-	return 0;
+	return ctdb_db_iterator(ctdb, priority, db_lock_unmark_handler, NULL);
 }
 
 static int ctdb_lockall_unmark(struct ctdb_context *ctdb)
@@ -319,7 +260,7 @@ static int ctdb_lockall_unmark(struct ctdb_context *ctdb)
 	uint32_t priority;
 
 	for (priority=NUM_DB_PRIORITIES; priority>=0; priority--) {
-		if (ctdb_lockall_unmark_prio(ctdb, priority) != 0) {
+		if (ctdb_db_iterator(ctdb, priority, db_lock_unmark_handler, NULL) != 0) {
 			return -1;
 		}
 	}
@@ -328,68 +269,6 @@ static int ctdb_lockall_unmark(struct ctdb_context *ctdb)
 }
 
 
-/*
- * Lock record / db depending on lock_ctx->type
- * Called from child context.
- */
-static bool ctdb_lock_item(struct lock_context *lock_ctx)
-{
-	bool status = false;
-
-	switch (lock_ctx->type) {
-	case LOCK_RECORD:
-		if (tdb_chainlock(lock_ctx->ctdb_db->ltdb->tdb, lock_ctx->key) == 0) {
-			status = true;
-		}
-		break;
-
-	case LOCK_DB:
-		if (tdb_lockall(lock_ctx->ctdb_db->ltdb->tdb) == 0) {
-			status = true;
-		}
-		break;
-
-	case LOCK_ALLDB_PRIO:
-		if (ctdb_lockall_prio(lock_ctx->ctdb, lock_ctx->priority) == 0) {
-			status = true;
-		}
-		break;
-
-	case LOCK_ALLDB:
-		if (ctdb_lockall(lock_ctx->ctdb) == 0) {
-			status = true;
-		}
-		break;
-	}
-
-	return status;
-}
-
-
-/*
- * Unlock record / db depending on lock_ctx->type
- */
-void ctdb_unlock_item(struct lock_context *lock_ctx)
-{
-	switch (lock_ctx->type) {
-	case LOCK_RECORD:
-		tdb_chainunlock(lock_ctx->ctdb_db->ltdb->tdb, lock_ctx->key);
-		break;
-
-	case LOCK_DB:
-		tdb_unlockall(lock_ctx->ctdb_db->ltdb->tdb);
-		break;
-
-	case LOCK_ALLDB_PRIO:
-		ctdb_unlockall_prio(lock_ctx->ctdb, lock_ctx->priority);
-		break;
-
-	case LOCK_ALLDB:
-		ctdb_unlockall(lock_ctx->ctdb);
-		break;
-	}
-}
-
 static void ctdb_lock_schedule(struct ctdb_context *ctdb);
 
 /*
@@ -631,32 +510,118 @@ static void ctdb_lock_timeout_handler(struct tevent_context *ev,
 }
 
 
-static char *lock_child_log_prefix(struct lock_context *lock_ctx)
+static int db_count_handler(struct ctdb_db_context *ctdb_db, uint32_t priority,
+			    void *private_data)
 {
-	char *prefix;
-	pid_t pid;
+	int *count = (int *)private_data;
+
+	(*count)++;
+
+	return 0;
+}
+
+struct db_namelist {
+	char **names;
+	int n;
+};
+
+static int db_name_handler(struct ctdb_db_context *ctdb_db, uint32_t priority,
+			   void *private_data)
+{
+	struct db_namelist *list = (struct db_namelist *)private_data;
+
+	list->names[list->n] = talloc_strdup(list->names, ctdb_db->db_path);
+	list->n++;
+
+	return 0;
+}
+
+static char **lock_helper_args(TALLOC_CTX *mem_ctx, struct lock_context *lock_ctx, int fd)
+{
+	struct ctdb_context *ctdb = lock_ctx->ctdb;
+	char **args = NULL;
+	int nargs, i;
+	int priority;
+	struct db_namelist list;
+
+	switch (lock_ctx->type) {
+	case LOCK_RECORD:
+		nargs = 6;
+		break;
+
+	case LOCK_DB:
+		nargs = 5;
+		break;
+
+	case LOCK_ALLDB_PRIO:
+		nargs = 4;
+		ctdb_db_iterator(ctdb, lock_ctx->priority, db_count_handler, &nargs);
+		break;
+
+	case LOCK_ALLDB:
+		nargs = 4;
+		for (priority=1; priority<NUM_DB_PRIORITIES; priority++) {
+			ctdb_db_iterator(ctdb, priority, db_count_handler, &nargs);
+		}
+		break;
+	}
+
+	/* Add extra argument for null termination */
+	nargs++;
+
+	args = talloc_array(mem_ctx, char *, nargs);
+	if (args == NULL) {
+		return NULL;
+	}
 
-	pid = getpid();
+	args[0] = talloc_strdup(args, "ctdb_lock_helper");
+	args[1] = talloc_asprintf(args, "%d", getpid());
+	args[2] = talloc_asprintf(args, "%d", fd);
 
 	switch (lock_ctx->type) {
 	case LOCK_RECORD:
-		prefix = talloc_asprintf(NULL, "lockR(%d): ", pid);
+		args[3] = talloc_strdup(args, "RECORD");
+		args[4] = talloc_strdup(args, lock_ctx->ctdb_db->db_path);
+		if (lock_ctx->key.dsize == 0) {
+			args[5] = talloc_strdup(args, "NULL");
+		} else {
+			args[5] = hex_encode_talloc(args, lock_ctx->key.dptr, lock_ctx->key.dsize);
+		}
 		break;
 
 	case LOCK_DB:
-		prefix = talloc_asprintf(NULL, "lockD(%d): ", pid);
+		args[3] = talloc_strdup(args, "DB");
+		args[4] = talloc_strdup(args, lock_ctx->ctdb_db->db_path);
 		break;
 
 	case LOCK_ALLDB_PRIO:
-		prefix = talloc_asprintf(NULL, "lockP(%d): ", pid);
+		args[3] = talloc_strdup(args, "DB");
+		list.names = args;
+		list.n = 4;
+		ctdb_db_iterator(ctdb, lock_ctx->priority, db_name_handler, &list);
 		break;
 
 	case LOCK_ALLDB:
-		prefix = talloc_asprintf(NULL, "lockA(%d): ", pid);
+		args[3] = talloc_strdup(args, "DB");
+		list.names = args;
+		list.n = 4;
+		for (priority=1; priority<NUM_DB_PRIORITIES; priority++) {
+			ctdb_db_iterator(ctdb, priority, db_name_handler, &list);
+		}
 		break;
 	}
 
-	return prefix;
+	/* Make sure last argument is NULL */
+	args[nargs-1] = NULL;
+
+	for (i=0; i<nargs-1; i++) {
+		if (args[i] == NULL) {
+			talloc_free(args);
+			return NULL;
+		}
+	}
+
+	return args;
 }
 
 
@@ -668,7 +633,22 @@ static void ctdb_lock_schedule(struct ctdb_context *ctdb)
 {
 	struct lock_context *lock_ctx, *next_ctx;
 	int ret;
-	pid_t parent;
+	TALLOC_CTX *tmp_ctx;
+	const char *helper = BINDIR "/ctdb_lock_helper";
+	static const char *prog = NULL;
+	char **args;
+
+	if (prog == NULL) {
+		const char *t;
+
+		t = getenv("CTDB_LOCK_HELPER");
+		if (t != NULL) {
+			prog = talloc_strdup(ctdb, t);
+		} else {
+			prog = talloc_strdup(ctdb, helper);
+		}
+		CTDB_NO_MEMORY_VOID(ctdb, prog);
+	}
 
 	if (ctdb->lock_num_current >= MAX_LOCK_PROCESSES_PER_DB) {
 		return;
@@ -710,41 +690,55 @@ static void ctdb_lock_schedule(struct ctdb_context *ctdb)
 		return;
 	}
 
-	parent = getpid();
+	set_close_on_exec(lock_ctx->fd[0]);
+
+	/* Create data for child process */
+	tmp_ctx = talloc_new(lock_ctx);
+	if (tmp_ctx == NULL) {
+		DEBUG(DEBUG_ERR, ("Failed to allocate memory for helper args\n"));
+		close(lock_ctx->fd[0]);
+		close(lock_ctx->fd[1]);
+		return;
+	}
+
+	/* Create arguments for lock helper */
+	args = lock_helper_args(tmp_ctx, lock_ctx, lock_ctx->fd[1]);
+	if (args == NULL) {
+		DEBUG(DEBUG_ERR, ("Failed to create lock helper args\n"));
+		close(lock_ctx->fd[0]);
+		close(lock_ctx->fd[1]);
+		talloc_free(tmp_ctx);
+		return;
+	}
+
 	lock_ctx->child = ctdb_fork(ctdb);
 
 	if (lock_ctx->child == (pid_t)-1) {
 		DEBUG(DEBUG_ERR, ("Failed to create a child in ctdb_lock_schedule\n"));
 		close(lock_ctx->fd[0]);
 		close(lock_ctx->fd[1]);
+		talloc_free(tmp_ctx);
 		return;
 	}
 
+
 	/* Child process */
 	if (lock_ctx->child == 0) {
-		char c;
-		close(lock_ctx->fd[0]);
-		debug_extra = lock_child_log_prefix(lock_ctx);
-		if (ctdb_lock_item(lock_ctx)) {
-			c = 0;
-		} else {
-			c = 1;
+		ret = execv(prog, args);
+		if (ret < 0) {
+			DEBUG(DEBUG_ERR, ("Failed to execute helper %s (%d, %s)\n",
+					  prog, errno, strerror(errno)));
 		}
-		write(lock_ctx->fd[1], &c, 1);
-
-		/* Hang around, but if parent dies, terminate */
-		while (kill(parent, 0) == 0 || errno != ESRCH) {
-			sleep(5);
-		}
-		_exit(0);
+		_exit(1);
 	}
 
 	/* Parent process */
 	close(lock_ctx->fd[1]);
-	set_close_on_exec(lock_ctx->fd[0]);
 
 	talloc_set_destructor(lock_ctx, ctdb_lock_context_destructor);
 
+	talloc_free(tmp_ctx);
+
 	/* Set up timeout handler */
 	lock_ctx->ttimer = tevent_add_timer(ctdb->ev,
 					    lock_ctx,
@@ -853,7 +847,7 @@ static struct lock_request *ctdb_lock_internal(struct ctdb_context *ctdb,
 	struct lock_request *request;
 
 	if (callback == NULL) {
-		DEBUG(DEBUG_WARNING, ("No callback function specified, not locking"));
+		DEBUG(DEBUG_WARNING, ("No callback function specified, not locking\n"));
 		return NULL;
 	}
 
@@ -865,7 +859,7 @@ static struct lock_request *ctdb_lock_internal(struct ctdb_context *ctdb,
 	if (lock_ctx == NULL) {
 		lock_ctx = talloc_zero(ctdb, struct lock_context);
 		if (lock_ctx == NULL) {
-			DEBUG(DEBUG_ERR, ("Failed to create a new lock context"));
+			DEBUG(DEBUG_ERR, ("Failed to create a new lock context\n"));
 			return NULL;
 		}
 
diff --git a/server/ctdb_lock_helper.c b/server/ctdb_lock_helper.c
new file mode 100644
index 0000000..d8a1d24
--- /dev/null
+++ b/server/ctdb_lock_helper.c
@@ -0,0 +1,148 @@
+/*
+   ctdb lock helper
+
+   Copyright (C) Amitay Isaacs  2013
+
+   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 3 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, see <http://www.gnu.org/licenses/>.
+*/
+
+#include "includes.h"
+#include "tdb.h"
+#include "system/filesys.h"
+#include "../include/ctdb_private.h"
+
+static char *progname = NULL;
+
+static void send_result(int fd, char result)
+{
+	write(fd, &result, 1);
+	if (result == 1) {
+		exit(1);
+	}
+}
+
+
+static void usage(void)
+{
+	fprintf(stderr, "\n");
+	fprintf(stderr, "Usage: %s <ctdbd-pid> <output-fd> RECORD <db-path> <db-key>\n",
+		progname);
+	fprintf(stderr, "       %s <ctdbd-pid> <output-fd> DB <db1-path> [<db2-path> ...]\n",
+		progname);
+}
+
+
+static int lock_record(const char *dbpath, const char *dbkey)
+{
+	TDB_DATA key;
+	struct tdb_context *tdb;
+
+	/* Convert hex key to key */
+	if (strcmp(dbkey, "NULL") == 0) {
+		key.dptr = NULL;
+		key.dsize = 0;
+	} else {
+		key.dptr = hex_decode_talloc(NULL, dbkey, &key.dsize);
+	}
+
+	tdb = tdb_open(dbpath, 0, TDB_DEFAULT, O_RDWR, 0600);
+	if (tdb == NULL) {
+		fprintf(stderr, "%s: Error opening database %s\n", progname, dbpath);
+		return 1;
+	}
+
+	if (tdb_chainlock(tdb, key) < 0) {
+		fprintf(stderr, "%s: Error getting record lock (%s)\n",
+			progname, tdb_errorstr(tdb));
+		return 1;
+	}
+
+	return 0;
+
+}
+
+
+static int lock_db(const char *dbpath)
+{
+	struct tdb_context *tdb;
+
+	tdb = tdb_open(dbpath, 0, TDB_DEFAULT, O_RDWR, 0600);
+	if (tdb == NULL) {
+		fprintf(stderr, "%s: Error opening database %s\n", progname, dbpath);
+		return 1;
+	}
+
+	if (tdb_lockall(tdb) < 0) {
+		fprintf(stderr, "%s: Error getting db lock (%s)\n",
+			progname, tdb_errorstr(tdb));
+		return 1;
+	}
+
+	return 0;
+}
+
+
+int main(int argc, char *argv[])
+{
+	int write_fd;
+	char result = 0;
+	int ppid;
+	const char *lock_type;
+
+	progname = argv[0];
+
+	if (argc < 4) {
+		usage();
+		exit(1);
+	}
+
+	ppid = atoi(argv[1]);
+	write_fd = atoi(argv[2]);
+	lock_type = argv[3];
+
+	if (strcmp(lock_type, "RECORD") == 0) {
+		if (argc != 6) {
+			fprintf(stderr, "%s: Invalid number of arguments (%d)\n",
+				progname, argc);
+			usage();
+			exit(1);
+		}
+		result = lock_record(argv[4], argv[5]);
+
+	} else if (strcmp(lock_type, "DB") == 0) {
+		int n;
+
+		/* If there are no databases specified, no need for lock */
+		if (argc > 4) {
+			for (n=4; n<argc; n++) {
+				result = lock_db(argv[n]);
+				if (result != 0) {
+					break;
+				}
+			}
+		}
+
+	} else {
+		fprintf(stderr, "%s: Invalid lock-type '%s'\n", progname, lock_type);
+		usage();
+		exit(1);
+	}
+
+	send_result(write_fd, result);
+
+	while (kill(ppid, 0) == 0 || errno != ESRCH) {
+		sleep(5);
+	}
+	return 0;
+}
diff --git a/server/ctdb_logging.c b/server/ctdb_logging.c
index 7cf8b9f..0b6ac12 100644
--- a/server/ctdb_logging.c
+++ b/server/ctdb_logging.c
@@ -65,7 +65,7 @@ static void ctdb_syslog_handler(struct event_context *ev, struct fd_event *fde,
 }
 
 
-/* called when the pipd from the main daemon has closed
+/* called when the pipe from the main daemon has closed
  * this is for the syslog daemon, we can not use DEBUG here
  */
 static void ctdb_syslog_terminate_handler(struct event_context *ev, struct fd_event *fde, 
@@ -538,11 +538,6 @@ int ctdb_set_child_logging(struct ctdb_context *ctdb)
 	close(old_stdout);
 	close(old_stderr);
 
-	/* Is this correct for STDOUT and STDERR ? */
-	set_close_on_exec(STDOUT_FILENO);
-	set_close_on_exec(STDERR_FILENO);
-	set_close_on_exec(p[0]);
-
 	fde = event_add_fd(ctdb->ev, ctdb->log, p[0],
 			   EVENT_FD_READ, ctdb_log_handler, ctdb->log);
 	tevent_fd_set_auto_close(fde);
diff --git a/server/ctdb_ltdb_server.c b/server/ctdb_ltdb_server.c
index 0432e49..0426d96 100644
--- a/server/ctdb_ltdb_server.c
+++ b/server/ctdb_ltdb_server.c
@@ -82,7 +82,7 @@ static int ctdb_ltdb_store_server(struct ctdb_db_context *ctdb_db,
 	 */
 	if (data.dsize != 0) {
 		keep = true;
-	} else if (header->flags & (CTDB_REC_RO_HAVE_DELEGATIONS|CTDB_REC_RO_HAVE_READONLY|CTDB_REC_RO_REVOKING_READONLY|CTDB_REC_RO_REVOKE_COMPLETE)) {
+	} else if (header->flags & CTDB_REC_RO_FLAGS) {
 		keep = true;
 	} else if (ctdb_db->persistent) {
 		keep = true;
@@ -125,12 +125,15 @@ static int ctdb_ltdb_store_server(struct ctdb_db_context *ctdb_db,
 	}
 
 	if (keep) {
-		if ((data.dsize == 0) &&
-		    !ctdb_db->persistent &&
+		if (!ctdb_db->persistent &&
 		    (ctdb_db->ctdb->pnn == header->dmaster) &&
-		    !(header->flags & (CTDB_REC_RO_HAVE_DELEGATIONS|CTDB_REC_RO_HAVE_READONLY|CTDB_REC_RO_REVOKING_READONLY|CTDB_REC_RO_REVOKE_COMPLETE)))
+		    !(header->flags & CTDB_REC_RO_FLAGS))
 		{
-			schedule_for_deletion = true;
+			header->rsn++;
+
+			if (data.dsize == 0) {
+				schedule_for_deletion = true;
+			}
 		}
 		remove_from_delete_queue = !schedule_for_deletion;
 	}
@@ -653,7 +656,7 @@ int32_t ctdb_control_db_set_healthy(struct ctdb_context *ctdb, TDB_DATA indata)
 		return -1;
 	}
 
-	if (may_recover && !ctdb->done_startup) {
+	if (may_recover && ctdb->runstate == CTDB_RUNSTATE_STARTUP) {
 		DEBUG(DEBUG_ERR, (__location__ " db %s become healthy  - force recovery for startup\n",
 				  ctdb_db->db_name));
 		ctdb->recovery_mode = CTDB_RECOVERY_ACTIVE;
@@ -791,7 +794,7 @@ static int ctdb_local_attach(struct ctdb_context *ctdb, const char *db_name,
 		if (ctdb->max_persistent_check_errors > 0) {
 			remaining_tries = 1;
 		}
-		if (ctdb->done_startup) {
+		if (ctdb->runstate == CTDB_RUNSTATE_RUNNING) {
 			remaining_tries = 0;
 		}
 
@@ -1079,13 +1082,13 @@ int32_t ctdb_control_db_attach(struct ctdb_context *ctdb, TDB_DATA indata,
 		   databases
 		*/
 		if (node->flags & NODE_FLAGS_INACTIVE) {
-			DEBUG(DEBUG_ERR,("DB Attach to database %s refused since node is inactive (disconnected or banned)\n", db_name));
+			DEBUG(DEBUG_ERR,("DB Attach to database %s refused since node is inactive (flags=0x%x)\n", db_name, node->flags));
 			return -1;
 		}
 
-		if (ctdb->recovery_mode == CTDB_RECOVERY_ACTIVE
-		 && client->pid != ctdb->recoverd_pid
-		 && !ctdb->done_startup) {
+		if (ctdb->recovery_mode == CTDB_RECOVERY_ACTIVE &&
+		    client->pid != ctdb->recoverd_pid &&
+		    ctdb->runstate < CTDB_RUNSTATE_RUNNING) {
 			struct ctdb_deferred_attach_context *da_ctx = talloc(client, struct ctdb_deferred_attach_context);
 
 			if (da_ctx == NULL) {
diff --git a/server/ctdb_monitor.c b/server/ctdb_monitor.c
index 984f947..1608804 100644
--- a/server/ctdb_monitor.c
+++ b/server/ctdb_monitor.c
@@ -204,7 +204,7 @@ static void ctdb_startup_callback(struct ctdb_context *ctdb, int status, void *p
 		DEBUG(DEBUG_ERR,("startup event failed\n"));
 	} else if (status == 0) {
 		DEBUG(DEBUG_NOTICE,("startup event OK - enabling monitoring\n"));
-		ctdb->done_startup = true;
+		ctdb_set_runstate(ctdb, CTDB_RUNSTATE_RUNNING);
 		ctdb->monitor->next_interval = 2;
 		ctdb_run_notification_script(ctdb, "startup");
 	}
@@ -307,7 +307,6 @@ static void ctdb_wait_until_recovered(struct event_context *ev, struct timed_eve
 	}
 	ctdb->db_persistent_check_errors = 0;
 
-	DEBUG(DEBUG_NOTICE,(__location__ " Recoveries finished. Running the \"startup\" event.\n"));
 	event_add_timed(ctdb->ev, ctdb->monitor->monitor_context,
 			     timeval_current(),
 			     ctdb_check_health, ctdb);
@@ -323,15 +322,25 @@ static void ctdb_check_health(struct event_context *ev, struct timed_event *te,
 	struct ctdb_context *ctdb = talloc_get_type(private_data, struct ctdb_context);
 	int ret = 0;
 
+	if (ctdb->runstate < CTDB_RUNSTATE_STARTUP) {
+		DEBUG(DEBUG_NOTICE,("Not yet in startup runstate. Wait one more second\n"));
+		event_add_timed(ctdb->ev, ctdb->monitor->monitor_context,
+				timeval_current_ofs(1, 0), 
+				ctdb_check_health, ctdb);
+		return;
+	}
+	
 	if (ctdb->recovery_mode != CTDB_RECOVERY_NORMAL ||
-	    (ctdb->monitor->monitoring_mode == CTDB_MONITORING_DISABLED && ctdb->done_startup)) {
+	    (ctdb->monitor->monitoring_mode == CTDB_MONITORING_DISABLED &&
+	     ctdb->runstate == CTDB_RUNSTATE_RUNNING)) {
 		event_add_timed(ctdb->ev, ctdb->monitor->monitor_context,
 				timeval_current_ofs(ctdb->monitor->next_interval, 0), 
 				ctdb_check_health, ctdb);
 		return;
 	}
 	
-	if (!ctdb->done_startup) {
+	if (ctdb->runstate == CTDB_RUNSTATE_STARTUP) {
+		DEBUG(DEBUG_NOTICE,("Recoveries finished. Running the \"startup\" event.\n"));
 		ret = ctdb_event_script_callback(ctdb, 
 						 ctdb->monitor->monitor_context, ctdb_startup_callback, 
 						 ctdb, false,
@@ -477,7 +486,7 @@ int32_t ctdb_control_modflags(struct ctdb_context *ctdb, TDB_DATA indata)
 
 	DEBUG(DEBUG_INFO, ("Control modflags on node %u - flags now 0x%x\n", c->pnn, node->flags));
 
-	if (node->flags == 0 && !ctdb->done_startup) {
+	if (node->flags == 0 && ctdb->runstate == CTDB_RUNSTATE_STARTUP) {
 		DEBUG(DEBUG_ERR, (__location__ " Node %u became healthy - force recovery for startup\n",
 				  c->pnn));
 		ctdb->recovery_mode = CTDB_RECOVERY_ACTIVE;
diff --git a/server/ctdb_persistent.c b/server/ctdb_persistent.c
index 91c336c..2b3da32 100644
--- a/server/ctdb_persistent.c
+++ b/server/ctdb_persistent.c
@@ -121,15 +121,16 @@ static void ctdb_persistent_store_timeout(struct event_context *ev, struct timed
  * Finish pending trans3 commit controls, i.e. send
  * reply to the client. This is called by the end-recovery
  * control to fix the situation when a recovery interrupts
- * the usual porgress of a transaction.
+ * the usual progress of a transaction.
  */
 void ctdb_persistent_finish_trans3_commits(struct ctdb_context *ctdb)
 {
 	struct ctdb_db_context *ctdb_db;
 
 	if (ctdb->recovery_mode != CTDB_RECOVERY_NORMAL) {
-		DEBUG(DEBUG_INFO, ("ctdb_persistent_store_timeout: ignoring "
-				   "timeout during recovery\n"));
+		DEBUG(DEBUG_INFO, ("ctdb_persistent_finish_trans3_commits: "
+				   "skipping execution when recovery is "
+				   "active\n"));
 		return;
 	}
 
diff --git a/server/ctdb_recover.c b/server/ctdb_recover.c
index 32c87bb..d7741ab 100644
--- a/server/ctdb_recover.c
+++ b/server/ctdb_recover.c
@@ -418,7 +418,7 @@ int32_t ctdb_control_push_db(struct ctdb_context *ctdb, TDB_DATA indata)
 		/* strip off any read only record flags. All readonly records
 		   are revoked implicitely by a recovery
 		*/
-		hdr->flags &= ~(CTDB_REC_RO_HAVE_DELEGATIONS|CTDB_REC_RO_HAVE_READONLY|CTDB_REC_RO_REVOKING_READONLY|CTDB_REC_RO_REVOKE_COMPLETE);
+		hdr->flags &= ~CTDB_REC_RO_FLAGS;
 
 		data.dptr += sizeof(*hdr);
 		data.dsize -= sizeof(*hdr);
@@ -458,59 +458,6 @@ failed:
 	return -1;
 }
 
-
-static int traverse_setdmaster(struct tdb_context *tdb, TDB_DATA key, TDB_DATA data, void *p)
-{
-	uint32_t *dmaster = (uint32_t *)p;
-	struct ctdb_ltdb_header *header = (struct ctdb_ltdb_header *)data.dptr;
-	int ret;
-
-	/* skip if already correct */
-	if (header->dmaster == *dmaster) {
-		return 0;
-	}
-
-	header->dmaster = *dmaster;
-
-	ret = tdb_store(tdb, key, data, TDB_REPLACE);
-	if (ret) {
-		DEBUG(DEBUG_CRIT,(__location__ " failed to write tdb data back  ret:%d\n",ret));
-		return ret;
-	}
-
-	/* TODO: add error checking here */
-
-	return 0;
-}
-
-int32_t ctdb_control_set_dmaster(struct ctdb_context *ctdb, TDB_DATA indata)
-{
-	struct ctdb_control_set_dmaster *p = (struct ctdb_control_set_dmaster *)indata.dptr;
-	struct ctdb_db_context *ctdb_db;
-
-	ctdb_db = find_ctdb_db(ctdb, p->db_id);
-	if (!ctdb_db) {
-		DEBUG(DEBUG_ERR,(__location__ " Unknown db 0x%08x\n", p->db_id));
-		return -1;
-	}
-
-	if (ctdb->freeze_mode[ctdb_db->priority] != CTDB_FREEZE_FROZEN) {
-		DEBUG(DEBUG_DEBUG,("rejecting ctdb_control_set_dmaster when not frozen\n"));
-		return -1;
-	}
-
-	if (ctdb_lockall_mark_prio(ctdb, ctdb_db->priority) != 0) {
-		DEBUG(DEBUG_ERR,(__location__ " Failed to get lock on entired db - failing\n"));
-		return -1;
-	}
-
-	tdb_traverse(ctdb_db->ltdb->tdb, traverse_setdmaster, &p->dmaster);
-
-	ctdb_lockall_unmark_prio(ctdb, ctdb_db->priority);
-	
-	return 0;
-}
-
 struct ctdb_set_recmode_state {
 	struct ctdb_context *ctdb;
 	struct ctdb_req_control *c;
@@ -896,13 +843,13 @@ static int delete_tdb_record(struct ctdb_context *ctdb, struct ctdb_db_context *
 	}
 
 	/* do not allow deleting record that have readonly flags set. */
-	if (hdr->flags & (CTDB_REC_RO_HAVE_DELEGATIONS|CTDB_REC_RO_HAVE_READONLY|CTDB_REC_RO_REVOKING_READONLY|CTDB_REC_RO_REVOKE_COMPLETE)) {
+	if (hdr->flags & CTDB_REC_RO_FLAGS) {
 		tdb_chainunlock(ctdb_db->ltdb->tdb, key);
 		DEBUG(DEBUG_INFO,(__location__ " Skipping record with readonly flags set\n"));
 		free(data.dptr);
 		return -1;		
 	}
-	if (hdr2->flags & (CTDB_REC_RO_HAVE_DELEGATIONS|CTDB_REC_RO_HAVE_READONLY|CTDB_REC_RO_REVOKING_READONLY|CTDB_REC_RO_REVOKE_COMPLETE)) {
+	if (hdr2->flags & CTDB_REC_RO_FLAGS) {
 		tdb_chainunlock(ctdb_db->ltdb->tdb, key);
 		DEBUG(DEBUG_INFO,(__location__ " Skipping record with readonly flags set\n"));
 		free(data.dptr);
@@ -964,6 +911,10 @@ static void ctdb_end_recovery_callback(struct ctdb_context *ctdb, int status, vo
 	talloc_free(state);
 
 	gettimeofday(&ctdb->last_recovery_finished, NULL);
+
+	if (ctdb->runstate == CTDB_RUNSTATE_FIRST_RECOVERY) {
+		ctdb_set_runstate(ctdb, CTDB_RUNSTATE_STARTUP);
+	}
 }
 
 /*
@@ -1145,6 +1096,202 @@ int32_t ctdb_control_try_delete_records(struct ctdb_context *ctdb, TDB_DATA inda
 	return 0;
 }
 
+/**
+ * Store a record as part of the vacuum process:
+ * This is called from the RECEIVE_RECORD control which
+ * the lmaster uses to send the current empty copy
+ * to all nodes for storing, before it lets the other
+ * nodes delete the records in the second phase with
+ * the TRY_DELETE_RECORDS control.
+ *
+ * Only store if we are not lmaster or dmaster, and our
+ * rsn is <= the provided rsn. Use non-blocking locks.
+ *
+ * return 0 if the record was successfully stored.
+ * return !0 if the record still exists in the tdb after returning.
+ */
+static int store_tdb_record(struct ctdb_context *ctdb,
+			    struct ctdb_db_context *ctdb_db,
+			    struct ctdb_rec_data *rec)
+{
+	TDB_DATA key, data, data2;
+	struct ctdb_ltdb_header *hdr, *hdr2;
+	int ret;
+
+	key.dsize = rec->keylen;
+	key.dptr = &rec->data[0];
+	data.dsize = rec->datalen;
+	data.dptr = &rec->data[rec->keylen];
+
+	if (ctdb_lmaster(ctdb, &key) == ctdb->pnn) {
+		DEBUG(DEBUG_INFO, (__location__ " Called store_tdb_record "
+				   "where we are lmaster\n"));
+		return -1;
+	}
+
+	if (data.dsize != sizeof(struct ctdb_ltdb_header)) {
+		DEBUG(DEBUG_ERR, (__location__ " Bad record size\n"));
+		return -1;
+	}
+
+	hdr = (struct ctdb_ltdb_header *)data.dptr;
+
+	/* use a non-blocking lock */
+	if (tdb_chainlock_nonblock(ctdb_db->ltdb->tdb, key) != 0) {
+		DEBUG(DEBUG_INFO, (__location__ " Failed to lock chain in non-blocking mode\n"));
+		return -1;
+	}
+
+	data2 = tdb_fetch(ctdb_db->ltdb->tdb, key);
+	if (data2.dptr == NULL || data2.dsize < sizeof(struct ctdb_ltdb_header)) {
+		tdb_store(ctdb_db->ltdb->tdb, key, data, 0);
+		DEBUG(DEBUG_INFO, (__location__ " Stored record\n"));
+		ret = 0;
+		goto done;
+	}
+
+	hdr2 = (struct ctdb_ltdb_header *)data.dptr;
+
+	if (hdr2->rsn > hdr->rsn) {
+		DEBUG(DEBUG_INFO, (__location__ " Skipping record with "
+				   "rsn=%llu - called with rsn=%llu\n",
+				   (unsigned long long)hdr2->rsn,
+				   (unsigned long long)hdr->rsn));
+		ret = -1;
+		goto done;
+	}
+
+	/* do not allow vacuuming of records that have readonly flags set. */
+	if (hdr->flags & CTDB_REC_RO_FLAGS) {
+		DEBUG(DEBUG_INFO,(__location__ " Skipping record with readonly "
+				  "flags set\n"));
+		ret = -1;
+		goto done;
+	}
+	if (hdr2->flags & CTDB_REC_RO_FLAGS) {
+		DEBUG(DEBUG_INFO,(__location__ " Skipping record with readonly "
+				  "flags set\n"));
+		ret = -1;
+		goto done;
+	}
+
+	if (hdr2->dmaster == ctdb->pnn) {
+		DEBUG(DEBUG_INFO, (__location__ " Attempted to store record "
+				   "where we are the dmaster\n"));
+		ret = -1;
+		goto done;
+	}
+
+	if (tdb_store(ctdb_db->ltdb->tdb, key, data, 0) != 0) {
+		DEBUG(DEBUG_INFO,(__location__ " Failed to store record\n"));
+		ret = -1;
+		goto done;
+	}
+
+	ret = 0;
+
+done:
+	tdb_chainunlock(ctdb_db->ltdb->tdb, key);
+	free(data2.dptr);
+	return  ret;
+}
+
+
+
+/**
+ * Try to store all these records as part of the vacuuming process
+ * and return the records we failed to store.
+ */
+int32_t ctdb_control_receive_records(struct ctdb_context *ctdb,
+				     TDB_DATA indata, TDB_DATA *outdata)
+{
+	struct ctdb_marshall_buffer *reply = (struct ctdb_marshall_buffer *)indata.dptr;
+	struct ctdb_db_context *ctdb_db;
+	int i;
+	struct ctdb_rec_data *rec;
+	struct ctdb_marshall_buffer *records;
+
+	if (indata.dsize < offsetof(struct ctdb_marshall_buffer, data)) {
+		DEBUG(DEBUG_ERR,
+		      (__location__ " invalid data in receive_records\n"));
+		return -1;
+	}
+
+	ctdb_db = find_ctdb_db(ctdb, reply->db_id);
+	if (!ctdb_db) {
+		DEBUG(DEBUG_ERR, (__location__ " Unknown db 0x%08x\n",
+				  reply->db_id));
+		return -1;
+	}
+
+	DEBUG(DEBUG_DEBUG, ("starting receive_records of %u records for "
+			    "dbid 0x%x\n", reply->count, reply->db_id));
+
+	/* create a blob to send back the records we could not store */
+	records = (struct ctdb_marshall_buffer *)
+			talloc_zero_size(outdata,
+				offsetof(struct ctdb_marshall_buffer, data));
+	if (records == NULL) {
+		DEBUG(DEBUG_ERR, (__location__ " Out of memory\n"));
+		return -1;
+	}
+	records->db_id = ctdb_db->db_id;
+
+	rec = (struct ctdb_rec_data *)&reply->data[0];
+	for (i=0; i<reply->count; i++) {
+		TDB_DATA key, data;
+
+		key.dptr = &rec->data[0];
+		key.dsize = rec->keylen;
+		data.dptr = &rec->data[key.dsize];
+		data.dsize = rec->datalen;
+
+		if (data.dsize < sizeof(struct ctdb_ltdb_header)) {
+			DEBUG(DEBUG_CRIT, (__location__ " bad ltdb record "
+					   "in indata\n"));
+			return -1;
+		}
+
+		/*
+		 * If we can not store the record we must add it to the reply
+		 * so the lmaster knows it may not purge this record.
+		 */
+		if (store_tdb_record(ctdb, ctdb_db, rec) != 0) {
+			size_t old_size;
+			struct ctdb_ltdb_header *hdr;
+
+			hdr = (struct ctdb_ltdb_header *)data.dptr;
+			data.dptr += sizeof(*hdr);
+			data.dsize -= sizeof(*hdr);
+
+			DEBUG(DEBUG_INFO, (__location__ " Failed to store "
+					   "record with hash 0x%08x in vacuum "
+					   "via RECEIVE_RECORDS\n",
+					   ctdb_hash(&key)));
+
+			old_size = talloc_get_size(records);
+			records = talloc_realloc_size(outdata, records,
+						      old_size + rec->length);
+			if (records == NULL) {
+				DEBUG(DEBUG_ERR, (__location__ " Failed to "
+						  "expand\n"));
+				return -1;
+			}
+			records->count++;
+			memcpy(old_size+(uint8_t *)records, rec, rec->length);
+		}
+
+		rec = (struct ctdb_rec_data *)(rec->length + (uint8_t *)rec);
+	}
+
+
+	outdata->dptr = (uint8_t *)records;
+	outdata->dsize = talloc_get_size(records);
+
+	return 0;
+}
+
+
 /*
   report capabilities
  */
@@ -1207,73 +1354,38 @@ int32_t ctdb_control_recd_ping(struct ctdb_context *ctdb)
 
 int32_t ctdb_control_set_recmaster(struct ctdb_context *ctdb, uint32_t opcode, TDB_DATA indata)
 {
-	CHECK_CONTROL_DATA_SIZE(sizeof(uint32_t));
-
-	ctdb->recovery_master = ((uint32_t *)(&indata.dptr[0]))[0];
-	return 0;
-}
-
+	uint32_t new_recmaster;
 
-struct stop_node_callback_state {
-	struct ctdb_req_control *c;
-};
+	CHECK_CONTROL_DATA_SIZE(sizeof(uint32_t));
+	new_recmaster = ((uint32_t *)(&indata.dptr[0]))[0];
 
-/*
-  called when the 'stopped' event script has finished
- */
-static void ctdb_stop_node_callback(struct ctdb_context *ctdb, int status, void *p)
-{
-	struct stop_node_callback_state *state = talloc_get_type(p, struct stop_node_callback_state);
+	if (ctdb->pnn != new_recmaster && ctdb->recovery_master == ctdb->pnn) {
+		DEBUG(DEBUG_NOTICE,
+		      ("This node (%u) is no longer the recovery master\n", ctdb->pnn));
+	}
 
-	if (status != 0) {
-		DEBUG(DEBUG_ERR,(__location__ " stopped event script failed (status %d)\n", status));
-		ctdb->nodes[ctdb->pnn]->flags &= ~NODE_FLAGS_STOPPED;
-		if (status == -ETIME) {
-			ctdb_ban_self(ctdb);
-		}
+	if (ctdb->pnn == new_recmaster && ctdb->recovery_master != new_recmaster) {
+		DEBUG(DEBUG_NOTICE,
+		      ("This node (%u) is now the recovery master\n", ctdb->pnn));
 	}
 
-	ctdb_request_control_reply(ctdb, state->c, NULL, status, NULL);
-	talloc_free(state);
+	ctdb->recovery_master = new_recmaster;
+	return 0;
 }
 
-int32_t ctdb_control_stop_node(struct ctdb_context *ctdb, struct ctdb_req_control *c, bool *async_reply)
-{
-	int ret;
-	struct stop_node_callback_state *state;
-
-	DEBUG(DEBUG_INFO,(__location__ " Stopping node\n"));
-
-	state = talloc(ctdb, struct stop_node_callback_state);
-	CTDB_NO_MEMORY(ctdb, state);
-
-	state->c    = talloc_steal(state, c);
 
+int32_t ctdb_control_stop_node(struct ctdb_context *ctdb)
+{
+	DEBUG(DEBUG_NOTICE, ("Stopping node\n"));
 	ctdb_disable_monitoring(ctdb);
-
-	ret = ctdb_event_script_callback(ctdb, state,
-					 ctdb_stop_node_callback, 
-					 state, false,
-					 CTDB_EVENT_STOPPED, "%s", "");
-
-	if (ret != 0) {
-		ctdb_enable_monitoring(ctdb);
-
-		DEBUG(DEBUG_ERR,(__location__ " Failed to stop node\n"));
-		talloc_free(state);
-		return -1;
-	}
-
 	ctdb->nodes[ctdb->pnn]->flags |= NODE_FLAGS_STOPPED;
 
-	*async_reply = true;
-
 	return 0;
 }
 
 int32_t ctdb_control_continue_node(struct ctdb_context *ctdb)
 {
-	DEBUG(DEBUG_INFO,(__location__ " Continue node\n"));
+	DEBUG(DEBUG_NOTICE, ("Continue node\n"));
 	ctdb->nodes[ctdb->pnn]->flags &= ~NODE_FLAGS_STOPPED;
 
 	return 0;
diff --git a/server/ctdb_recoverd.c b/server/ctdb_recoverd.c
index 5f83044..c3a1852 100644
--- a/server/ctdb_recoverd.c
+++ b/server/ctdb_recoverd.c
@@ -254,7 +254,7 @@ static int update_capabilities(struct ctdb_context *ctdb, struct ctdb_node_map *
 	tmp_ctx = talloc_new(ctdb);
 	CTDB_NO_MEMORY(ctdb, tmp_ctx);
 
-	nodes = list_of_active_nodes(ctdb, nodemap, tmp_ctx, true);
+	nodes = list_of_connected_nodes(ctdb, nodemap, tmp_ctx, true);
 	if (ctdb_client_async_control(ctdb, CTDB_CONTROL_GET_CAPABILITIES,
 					nodes, 0,
 					CONTROL_TIMEOUT(),
@@ -2126,7 +2126,7 @@ static void getlog_handler(struct ctdb_context *ctdb, uint64_t srvid,
 	}
 	log_addr = (struct ctdb_get_log_addr *)data.dptr;
 
-	child = ctdb_fork(ctdb);
+	child = ctdb_fork_no_free_ringbuffer(ctdb);
 	if (child == (pid_t)-1) {
 		DEBUG(DEBUG_ERR,("Failed to fork a log collector child\n"));
 		return;
@@ -2855,17 +2855,61 @@ static enum monitor_result verify_recmaster(struct ctdb_recoverd *rec, struct ct
 	return status;
 }
 
+static bool interfaces_have_changed(struct ctdb_context *ctdb,
+				    struct ctdb_recoverd *rec)
+{
+	struct ctdb_control_get_ifaces *ifaces = NULL;
+	TALLOC_CTX *mem_ctx;
+	bool ret = false;
+
+	mem_ctx = talloc_new(NULL);
+
+	/* Read the interfaces from the local node */
+	if (ctdb_ctrl_get_ifaces(ctdb, CONTROL_TIMEOUT(),
+				 CTDB_CURRENT_NODE, mem_ctx, &ifaces) != 0) {
+		DEBUG(DEBUG_ERR, ("Unable to get interfaces from local node %u\n", ctdb->pnn));
+		/* We could return an error.  However, this will be
+		 * rare so we'll decide that the interfaces have
+		 * actually changed, just in case.
+		 */
+		talloc_free(mem_ctx);
+		return true;
+	}
+
+	if (!rec->ifaces) {
+		/* We haven't been here before so things have changed */
+		ret = true;
+	} else if (rec->ifaces->num != ifaces->num) {
+		/* Number of interfaces has changed */
+		ret = true;
+	} else {
+		/* See if interface names or link states have changed */
+		int i;
+		for (i = 0; i < rec->ifaces->num; i++) {
+			struct ctdb_control_iface_info * iface = &rec->ifaces->ifaces[i];
+			if (strcmp(iface->name, ifaces->ifaces[i].name) != 0 ||
+			    iface->link_state != ifaces->ifaces[i].link_state) {
+				ret = true;
+				break;
+			}
+		}
+	}
+
+	talloc_free(rec->ifaces);
+	rec->ifaces = talloc_steal(rec, ifaces);
+
+	talloc_free(mem_ctx);
+	return ret;
+}
 
 /* called to check that the local allocation of public ip addresses is ok.
 */
 static int verify_local_ip_allocation(struct ctdb_context *ctdb, struct ctdb_recoverd *rec, uint32_t pnn, struct ctdb_node_map *nodemap)
 {
 	TALLOC_CTX *mem_ctx = talloc_new(NULL);
-	struct ctdb_control_get_ifaces *ifaces = NULL;
 	struct ctdb_uptime *uptime1 = NULL;
 	struct ctdb_uptime *uptime2 = NULL;
 	int ret, j;
-	bool need_iface_check = false;
 	bool need_takeover_run = false;
 
 	ret = ctdb_ctrl_uptime(ctdb, mem_ctx, CONTROL_TIMEOUT(),
@@ -2876,27 +2920,7 @@ static int verify_local_ip_allocation(struct ctdb_context *ctdb, struct ctdb_rec
 		return -1;
 	}
 
-
-	/* read the interfaces from the local node */
-	ret = ctdb_ctrl_get_ifaces(ctdb, CONTROL_TIMEOUT(), CTDB_CURRENT_NODE, mem_ctx, &ifaces);
-	if (ret != 0) {
-		DEBUG(DEBUG_ERR, ("Unable to get interfaces from local node %u\n", pnn));
-		talloc_free(mem_ctx);
-		return -1;
-	}
-
-	if (!rec->ifaces) {
-		need_iface_check = true;
-	} else if (rec->ifaces->num != ifaces->num) {
-		need_iface_check = true;
-	} else if (memcmp(rec->ifaces, ifaces, talloc_get_size(ifaces)) != 0) {
-		need_iface_check = true;
-	}
-
-	talloc_free(rec->ifaces);
-	rec->ifaces = talloc_steal(rec, ifaces);
-
-	if (need_iface_check) {
+	if (interfaces_have_changed(ctdb, rec)) {
 		DEBUG(DEBUG_NOTICE, ("The interfaces status has changed on "
 				     "local node %u - force takeover run\n",
 				     pnn));
@@ -3469,7 +3493,6 @@ static void main_loop(struct ctdb_context *ctdb, struct ctdb_recoverd *rec,
 	/* check that we (recovery daemon) and the local ctdb daemon
 	   agrees on whether we are banned or not
 	*/
-//qqq
 
 	/* remember our own node flags */
 	rec->node_flags = nodemap->nodes[pnn].flags;
@@ -3699,7 +3722,7 @@ static void main_loop(struct ctdb_context *ctdb, struct ctdb_recoverd *rec,
 				  nodemap->nodes[j].pnn, 
 				  nodemap->nodes[i].pnn, 
 				  remote_nodemaps[j]->nodes[i].flags,
-				  nodemap->nodes[j].flags));
+				  nodemap->nodes[i].flags));
 				if (i == j) {
 					DEBUG(DEBUG_ERR,("Use flags 0x%02x from remote node %d for cluster update of its own flags\n", remote_nodemaps[j]->nodes[i].flags, j));
 					update_flags_on_all_nodes(ctdb, nodemap, nodemap->nodes[i].pnn, remote_nodemaps[j]->nodes[i].flags);
@@ -3971,7 +3994,7 @@ static void ctdb_check_recd(struct event_context *ev, struct timed_event *te,
 		return;
 	}
 
-	event_add_timed(ctdb->ev, ctdb, 
+	event_add_timed(ctdb->ev, ctdb->recd_ctx,
 			timeval_current_ofs(30, 0),
 			ctdb_check_recd, ctdb);
 }
@@ -4014,7 +4037,7 @@ int ctdb_start_recoverd(struct ctdb_context *ctdb)
 
 	ctdb->ctdbd_pid = getpid();
 
-	ctdb->recoverd_pid = ctdb_fork(ctdb);
+	ctdb->recoverd_pid = ctdb_fork_no_free_ringbuffer(ctdb);
 	if (ctdb->recoverd_pid == -1) {
 		return -1;
 	}
@@ -4035,6 +4058,9 @@ int ctdb_start_recoverd(struct ctdb_context *ctdb)
 
 	srandom(getpid() ^ time(NULL));
 
+	/* Clear the log ringbuffer */
+	ctdb_clear_log(ctdb);
+
 	if (switch_from_server_to_client(ctdb, "recoverd") != 0) {
 		DEBUG(DEBUG_CRIT, (__location__ "ERROR: failed to switch recovery daemon into client mode. shutting down.\n"));
 		exit(1);
diff --git a/server/ctdb_takeover.c b/server/ctdb_takeover.c
index d601b17..fda7c56 100644
--- a/server/ctdb_takeover.c
+++ b/server/ctdb_takeover.c
@@ -33,6 +33,12 @@
 #define CTDB_ARP_INTERVAL 1
 #define CTDB_ARP_REPEAT   3
 
+/* Flags used in IP allocation algorithms. */
+struct ctdb_ipflags {
+	bool noiptakeover;
+	bool noiphost;
+};
+
 struct ctdb_iface {
 	struct ctdb_iface *prev, *next;
 	const char *name;
@@ -78,7 +84,7 @@ static int ctdb_add_local_iface(struct ctdb_context *ctdb, const char *iface)
 	 * IPs can't be assigned, and after startup IPs can be
 	 * assigned immediately.
 	 */
-	i->link_up = ctdb->done_startup;
+	i->link_up = (ctdb->runstate == CTDB_RUNSTATE_RUNNING);
 
 	DLIST_ADD(ctdb->ifaces, i);
 
@@ -158,7 +164,6 @@ static struct ctdb_iface *ctdb_find_iface(struct ctdb_context *ctdb,
 {
 	struct ctdb_iface *i;
 
-	/* Verify that we dont have an entry for this ip yet */
 	for (i=ctdb->ifaces;i;i=i->next) {
 		if (strcmp(i->name, iface) == 0) {
 			return i;
@@ -1299,61 +1304,64 @@ static int node_ip_coverage(struct ctdb_context *ctdb,
 }
 
 
-/* Check if this is a public ip known to the node, i.e. can that
-   node takeover this ip ?
+/* Can the given node host the given IP: is the public IP known to the
+ * node and is NOIPHOST unset?
 */
-static int can_node_serve_ip(struct ctdb_context *ctdb, int32_t pnn, 
-		struct ctdb_public_ip_list *ip)
+static bool can_node_host_ip(struct ctdb_context *ctdb, int32_t pnn, 
+			     struct ctdb_ipflags ipflags,
+			     struct ctdb_public_ip_list *ip)
 {
 	struct ctdb_all_public_ips *public_ips;
 	int i;
 
+	if (ipflags.noiphost) {
+		return false;
+	}
+
 	public_ips = ctdb->nodes[pnn]->available_public_ips;
 
 	if (public_ips == NULL) {
-		return -1;
+		return false;
 	}
 
-	for (i=0;i<public_ips->num;i++) {
+	for (i=0; i<public_ips->num; i++) {
 		if (ctdb_same_ip(&ip->addr, &public_ips->ips[i].addr)) {
 			/* yes, this node can serve this public ip */
-			return 0;
+			return true;
 		}
 	}
 
-	return -1;
+	return false;
 }
 
+static bool can_node_takeover_ip(struct ctdb_context *ctdb, int32_t pnn, 
+				 struct ctdb_ipflags ipflags,
+				 struct ctdb_public_ip_list *ip)
+{
+	if (ipflags.noiptakeover) {
+		return false;
+	}
+
+	return can_node_host_ip(ctdb, pnn, ipflags, ip);
+}
 
 /* search the node lists list for a node to takeover this ip.
    pick the node that currently are serving the least number of ips
    so that the ips get spread out evenly.
 */
 static int find_takeover_node(struct ctdb_context *ctdb, 
-		struct ctdb_node_map *nodemap, uint32_t mask, 
+		struct ctdb_ipflags *ipflags,
 		struct ctdb_public_ip_list *ip,
 		struct ctdb_public_ip_list *all_ips)
 {
 	int pnn, min=0, num;
-	int i;
+	int i, numnodes;
 
+	numnodes = talloc_array_length(ipflags);
 	pnn    = -1;
-	for (i=0;i<nodemap->num;i++) {
-		if (nodemap->nodes[i].flags & NODE_FLAGS_NOIPTAKEOVER) {
-			/* This node is not allowed to takeover any addresses
-			*/
-			continue;
-		}
-
-		if (nodemap->nodes[i].flags & mask) {
-			/* This node is not healty and can not be used to serve
-			   a public address 
-			*/
-			continue;
-		}
-
+	for (i=0; i<numnodes; i++) {
 		/* verify that this node can serve this ip */
-		if (can_node_serve_ip(ctdb, i, ip)) {
+		if (!can_node_takeover_ip(ctdb, i, ipflags[i], ip)) {
 			/* no it couldnt   so skip to the next node */
 			continue;
 		}
@@ -1463,7 +1471,13 @@ create_merged_ip_list(struct ctdb_context *ctdb)
 
 			tmp_ip = talloc_zero(ctdb->ip_tree, struct ctdb_public_ip_list);
 			CTDB_NO_MEMORY_NULL(ctdb, tmp_ip);
-			tmp_ip->pnn  = public_ips->ips[j].pnn;
+			/* Do not use information about IP addresses hosted
+			 * on other nodes, it may not be accurate */
+			if (public_ips->ips[j].pnn == ctdb->nodes[i]->pnn) {
+				tmp_ip->pnn = public_ips->ips[j].pnn;
+			} else {
+				tmp_ip->pnn = -1;
+			}
 			tmp_ip->addr = public_ips->ips[j].addr;
 			tmp_ip->next = NULL;
 
@@ -1583,8 +1597,7 @@ static uint32_t lcp2_imbalance(struct ctdb_public_ip_list * all_ips, int pnn)
  * finding the best node for each.
  */
 static void basic_allocate_unassigned(struct ctdb_context *ctdb,
-				      struct ctdb_node_map *nodemap,
-				      uint32_t mask,
+				      struct ctdb_ipflags *ipflags,
 				      struct ctdb_public_ip_list *all_ips)
 {
 	struct ctdb_public_ip_list *tmp_ip;
@@ -1594,7 +1607,7 @@ static void basic_allocate_unassigned(struct ctdb_context *ctdb,
 	*/
 	for (tmp_ip=all_ips;tmp_ip;tmp_ip=tmp_ip->next) {
 		if (tmp_ip->pnn == -1) {
-			if (find_takeover_node(ctdb, nodemap, mask, tmp_ip, all_ips)) {
+			if (find_takeover_node(ctdb, ipflags, tmp_ip, all_ips)) {
 				DEBUG(DEBUG_WARNING,("Failed to find node to cover ip %s\n",
 					ctdb_addr_to_str(&tmp_ip->addr)));
 			}
@@ -1605,15 +1618,15 @@ static void basic_allocate_unassigned(struct ctdb_context *ctdb,
 /* Basic non-deterministic rebalancing algorithm.
  */
 static void basic_failback(struct ctdb_context *ctdb,
-			   struct ctdb_node_map *nodemap,
-			   uint32_t mask,
+			   struct ctdb_ipflags *ipflags,
 			   struct ctdb_public_ip_list *all_ips,
 			   int num_ips)
 {
-	int i;
+	int i, numnodes;
 	int maxnode, maxnum, minnode, minnum, num, retries;
 	struct ctdb_public_ip_list *tmp_ip;
 
+	numnodes = talloc_array_length(ipflags);
 	retries = 0;
 
 try_again:
@@ -1635,18 +1648,9 @@ try_again:
 		*/
 		maxnode = -1;
 		minnode = -1;
-		for (i=0;i<nodemap->num;i++) {
-			if (nodemap->nodes[i].flags & mask) {
-				continue;
-			}
-
-			/* Only check nodes that are allowed to takeover an ip */
-			if (nodemap->nodes[i].flags & NODE_FLAGS_NOIPTAKEOVER) {
-				continue;
-			}
-
+		for (i=0; i<numnodes; i++) {
 			/* only check nodes that can actually serve this ip */
-			if (can_node_serve_ip(ctdb, i, tmp_ip)) {
+			if (!can_node_takeover_ip(ctdb, i, ipflags[i], tmp_ip)) {
 				/* no it couldnt   so skip to the next node */
 				continue;
 			}
@@ -1691,7 +1695,7 @@ try_again:
 			/* Reassign one of maxnode's VNNs */
 			for (tmp=all_ips;tmp;tmp=tmp->next) {
 				if (tmp->pnn == maxnode) {
-					(void)find_takeover_node(ctdb, nodemap, mask, tmp, all_ips);
+					(void)find_takeover_node(ctdb, ipflags, tmp, all_ips);
 					retries++;
 					goto try_again;;
 				}
@@ -1729,32 +1733,38 @@ void lcp2_forcerebalance(struct ctdb_context *ctdb, uint32_t pnn)
 /* Do necessary LCP2 initialisation.  Bury it in a function here so
  * that we can unit test it.
  */
-static void lcp2_init(struct ctdb_context * tmp_ctx,
-	       struct ctdb_node_map * nodemap,
-	       uint32_t mask,
-	       struct ctdb_public_ip_list *all_ips,
-	       uint32_t **lcp2_imbalances,
-	       bool **newly_healthy)
+static void lcp2_init(struct ctdb_context *tmp_ctx,
+		      struct ctdb_ipflags *ipflags,
+		      struct ctdb_public_ip_list *all_ips,
+		      uint32_t **lcp2_imbalances,
+		      bool **rebalance_candidates)
 {
-	int i;
+	int i, numnodes;
 	struct ctdb_public_ip_list *tmp_ip;
 
-	*newly_healthy = talloc_array(tmp_ctx, bool, nodemap->num);
-	CTDB_NO_MEMORY_FATAL(tmp_ctx, *newly_healthy);
-	*lcp2_imbalances = talloc_array(tmp_ctx, uint32_t, nodemap->num);
+	numnodes = talloc_array_length(ipflags);
+
+	*rebalance_candidates = talloc_array(tmp_ctx, bool, numnodes);
+	CTDB_NO_MEMORY_FATAL(tmp_ctx, *rebalance_candidates);
+	*lcp2_imbalances = talloc_array(tmp_ctx, uint32_t, numnodes);
 	CTDB_NO_MEMORY_FATAL(tmp_ctx, *lcp2_imbalances);
 
-	for (i=0;i<nodemap->num;i++) {
+	for (i=0; i<numnodes; i++) {
 		(*lcp2_imbalances)[i] = lcp2_imbalance(all_ips, i);
-		/* First step: is the node "healthy"? */
-		(*newly_healthy)[i] = ! (bool)(nodemap->nodes[i].flags & mask);
+		/* First step: assume all nodes are candidates */
+		(*rebalance_candidates)[i] = true;
 	}
 
-	/* 2nd step: if a ndoe has IPs assigned then it must have been
-	 * healthy before, so we remove it from consideration... */
+	/* 2nd step: if a node has IPs assigned then it must have been
+	 * healthy before, so we remove it from consideration.  This
+	 * is overkill but is all we have because we don't maintain
+	 * state between takeover runs.  An alternative would be to
+	 * keep state and invalidate it every time the recovery master
+	 * changes.
+	 */
 	for (tmp_ip=all_ips;tmp_ip;tmp_ip=tmp_ip->next) {
 		if (tmp_ip->pnn != -1) {
-			(*newly_healthy)[tmp_ip->pnn] = false;
+			(*rebalance_candidates)[tmp_ip->pnn] = false;
 		}
 	}
 
@@ -1763,8 +1773,8 @@ static void lcp2_init(struct ctdb_context * tmp_ctx,
 	while (force_rebalance_list != NULL) {
 		struct ctdb_rebalancenodes *next = force_rebalance_list->next;
 
-		if (force_rebalance_list->pnn <= nodemap->num) {
-			(*newly_healthy)[force_rebalance_list->pnn] = true;
+		if (force_rebalance_list->pnn <= numnodes) {
+			(*rebalance_candidates)[force_rebalance_list->pnn] = true;
 		}
 
 		DEBUG(DEBUG_ERR,("During ipreallocation, forced rebalance of node %d\n", force_rebalance_list->pnn));
@@ -1777,13 +1787,12 @@ static void lcp2_init(struct ctdb_context * tmp_ctx,
  * the IP/node combination that will cost the least.
  */
 static void lcp2_allocate_unassigned(struct ctdb_context *ctdb,
-			      struct ctdb_node_map *nodemap,
-			      uint32_t mask,
-			      struct ctdb_public_ip_list *all_ips,
-			      uint32_t *lcp2_imbalances)
+				     struct ctdb_ipflags *ipflags,
+				     struct ctdb_public_ip_list *all_ips,
+				     uint32_t *lcp2_imbalances)
 {
 	struct ctdb_public_ip_list *tmp_ip;
-	int dstnode;
+	int dstnode, numnodes;
 
 	int minnode;
 	uint32_t mindsum, dstdsum, dstimbl, minimbl;
@@ -1792,6 +1801,8 @@ static void lcp2_allocate_unassigned(struct ctdb_context *ctdb,
 	bool should_loop = true;
 	bool have_unassigned = true;
 
+	numnodes = talloc_array_length(ipflags);
+
 	while (have_unassigned && should_loop) {
 		should_loop = false;
 
@@ -1808,20 +1819,14 @@ static void lcp2_allocate_unassigned(struct ctdb_context *ctdb,
 				continue;
 			}
 
-			for (dstnode=0; dstnode < nodemap->num; dstnode++) {
-				/* Only check nodes that are allowed to takeover an ip */
-				if (nodemap->nodes[dstnode].flags & NODE_FLAGS_NOIPTAKEOVER) {
-					continue;
-				}
-
-				/* only check nodes that can actually serve this ip */
-				if (can_node_serve_ip(ctdb, dstnode, tmp_ip)) {
+			for (dstnode=0; dstnode<numnodes; dstnode++) {
+				/* only check nodes that can actually takeover this ip */
+				if (!can_node_takeover_ip(ctdb, dstnode,
+							  ipflags[dstnode],
+							  tmp_ip)) {
 					/* no it couldnt   so skip to the next node */
 					continue;
 				}
-				if (nodemap->nodes[dstnode].flags & mask) {
-					continue;
-				}
 
 				dstdsum = ip_distance_2_sum(&(tmp_ip->addr), all_ips, dstnode);
 				dstimbl = lcp2_imbalances[dstnode] + dstdsum;
@@ -1880,14 +1885,14 @@ static void lcp2_allocate_unassigned(struct ctdb_context *ctdb,
  * combination to move from the source node.
  */
 static bool lcp2_failback_candidate(struct ctdb_context *ctdb,
-				    struct ctdb_node_map *nodemap,
+				    struct ctdb_ipflags *ipflags,
 				    struct ctdb_public_ip_list *all_ips,
 				    int srcnode,
 				    uint32_t candimbl,
 				    uint32_t *lcp2_imbalances,
-				    bool *newly_healthy)
+				    bool *rebalance_candidates)
 {
-	int dstnode, mindstnode;
+	int dstnode, mindstnode, numnodes;
 	uint32_t srcimbl, srcdsum, dstimbl, dstdsum;
 	uint32_t minsrcimbl, mindstimbl;
 	struct ctdb_public_ip_list *minip;
@@ -1899,6 +1904,8 @@ static bool lcp2_failback_candidate(struct ctdb_context *ctdb,
 	mindstnode = -1;
 	mindstimbl = 0;
 
+	numnodes = talloc_array_length(ipflags);
+
 	DEBUG(DEBUG_DEBUG,(" ----------------------------------------\n"));
 	DEBUG(DEBUG_DEBUG,(" CONSIDERING MOVES FROM %d [%d]\n", srcnode, candimbl));
 
@@ -1918,18 +1925,14 @@ static bool lcp2_failback_candidate(struct ctdb_context *ctdb,
 		 * to do gratuitous failover of IPs just to make minor
 		 * balance improvements.
 		 */
-		for (dstnode=0; dstnode < nodemap->num; dstnode++) {
-			if (! newly_healthy[dstnode]) {
-				continue;
-			}
-
-			/* Only check nodes that are allowed to takeover an ip */
-			if (nodemap->nodes[dstnode].flags & NODE_FLAGS_NOIPTAKEOVER) {
+		for (dstnode=0; dstnode<numnodes; dstnode++) {
+			if (!rebalance_candidates[dstnode]) {
 				continue;
 			}
 
-			/* only check nodes that can actually serve this ip */
-			if (can_node_serve_ip(ctdb, dstnode, tmp_ip)) {
+			/* only check nodes that can actually takeover this ip */
+			if (!can_node_takeover_ip(ctdb, dstnode,
+						  ipflags[dstnode], tmp_ip)) {
 				/* no it couldnt   so skip to the next node */
 				continue;
 			}
@@ -1997,29 +2000,30 @@ static int lcp2_cmp_imbalance_pnn(const void * a, const void * b)
  * IP/destination node combination to move from the source node.
  */
 static void lcp2_failback(struct ctdb_context *ctdb,
-			  struct ctdb_node_map *nodemap,
-			  uint32_t mask,
+			  struct ctdb_ipflags *ipflags,
 			  struct ctdb_public_ip_list *all_ips,
 			  uint32_t *lcp2_imbalances,
-			  bool *newly_healthy)
+			  bool *rebalance_candidates)
 {
-	int i, num_newly_healthy;
+	int i, num_rebalance_candidates, numnodes;
 	struct lcp2_imbalance_pnn * lips;
 	bool again;
 
+	numnodes = talloc_array_length(ipflags);
+
 try_again:
 
 	/* It is only worth continuing if we have suitable target
 	 * nodes to transfer IPs to.  This check is much cheaper than
 	 * continuing on...
 	 */
-	num_newly_healthy = 0;
-	for (i = 0; i < nodemap->num; i++) {
-		if (newly_healthy[i]) {
-			num_newly_healthy++;
+	num_rebalance_candidates = 0;
+	for (i=0; i<numnodes; i++) {
+		if (rebalance_candidates[i]) {
+			num_rebalance_candidates++;
 		}
 	}
-	if (num_newly_healthy == 0) {
+	if (num_rebalance_candidates == 0) {
 		return;
 	}
 
@@ -2027,16 +2031,16 @@ try_again:
 	 * iterate through candidates.  Usually the 1st one will be
 	 * used, so this doesn't cost much...
 	 */
-	lips = talloc_array(ctdb, struct lcp2_imbalance_pnn, nodemap->num);
-	for (i = 0; i < nodemap->num; i++) {
+	lips = talloc_array(ctdb, struct lcp2_imbalance_pnn, numnodes);
+	for (i=0; i<numnodes; i++) {
 		lips[i].imbalance = lcp2_imbalances[i];
 		lips[i].pnn = i;
 	}
-	qsort(lips, nodemap->num, sizeof(struct lcp2_imbalance_pnn),
+	qsort(lips, numnodes, sizeof(struct lcp2_imbalance_pnn),
 	      lcp2_cmp_imbalance_pnn);
 
 	again = false;
-	for (i = 0; i < nodemap->num; i++) {
+	for (i=0; i<numnodes; i++) {
 		/* This means that all nodes had 0 or 1 addresses, so
 		 * can't be imbalanced.
 		 */
@@ -2045,12 +2049,12 @@ try_again:
 		}
 
 		if (lcp2_failback_candidate(ctdb,
-					    nodemap,
+					    ipflags,
 					    all_ips,
 					    lips[i].pnn,
 					    lips[i].imbalance,
 					    lcp2_imbalances,
-					    newly_healthy)) {
+					    rebalance_candidates)) {
 			again = true;
 			break;
 		}
@@ -2063,24 +2067,11 @@ try_again:
 }
 
 static void unassign_unsuitable_ips(struct ctdb_context *ctdb,
-				    struct ctdb_node_map *nodemap,
-				    struct ctdb_public_ip_list *all_ips,
-				    uint32_t mask)
+				    struct ctdb_ipflags *ipflags,
+				    struct ctdb_public_ip_list *all_ips)
 {
 	struct ctdb_public_ip_list *tmp_ip;
 
-	/* mark all public addresses with a masked node as being served by
-	   node -1
-	*/
-	for (tmp_ip=all_ips;tmp_ip;tmp_ip=tmp_ip->next) {
-		if (tmp_ip->pnn == -1) {
-			continue;
-		}
-		if (nodemap->nodes[tmp_ip->pnn].flags & mask) {
-			tmp_ip->pnn = -1;
-		}
-	}
-
 	/* verify that the assigned nodes can serve that public ip
 	   and set it to -1 if not
 	*/
@@ -2088,20 +2079,25 @@ static void unassign_unsuitable_ips(struct ctdb_context *ctdb,
 		if (tmp_ip->pnn == -1) {
 			continue;
 		}
-		if (can_node_serve_ip(ctdb, tmp_ip->pnn, tmp_ip) != 0) {
+		if (!can_node_host_ip(ctdb, tmp_ip->pnn,
+				      ipflags[tmp_ip->pnn], tmp_ip) != 0) {
 			/* this node can not serve this ip. */
+			DEBUG(DEBUG_DEBUG,("Unassign IP: %s from %d\n",
+					   ctdb_addr_to_str(&(tmp_ip->addr)),
+					   tmp_ip->pnn));
 			tmp_ip->pnn = -1;
 		}
 	}
 }
 
 static void ip_alloc_deterministic_ips(struct ctdb_context *ctdb,
-				       struct ctdb_node_map *nodemap,
-				       struct ctdb_public_ip_list *all_ips,
-				       uint32_t mask)
+				       struct ctdb_ipflags *ipflags,
+				       struct ctdb_public_ip_list *all_ips)
 {
 	struct ctdb_public_ip_list *tmp_ip;
-	int i;
+	int i, numnodes;
+
+	numnodes = talloc_array_length(ipflags);
 
 	DEBUG(DEBUG_NOTICE,("Deterministic IPs enabled. Resetting all ip allocations\n"));
        /* Allocate IPs to nodes in a modulo fashion so that IPs will
@@ -2110,7 +2106,7 @@ static void ip_alloc_deterministic_ips(struct ctdb_context *ctdb,
 	*/
 
 	for (i=0,tmp_ip=all_ips;tmp_ip;tmp_ip=tmp_ip->next,i++) {
-		tmp_ip->pnn = i%nodemap->num;
+		tmp_ip->pnn = i % numnodes;
 	}
 
 	/* IP failback doesn't make sense with deterministic
@@ -2121,17 +2117,16 @@ static void ip_alloc_deterministic_ips(struct ctdb_context *ctdb,
 		DEBUG(DEBUG_WARNING, ("WARNING: 'NoIPFailback' set but ignored - incompatible with 'DeterministicIPs\n"));
 	}
 
-	unassign_unsuitable_ips(ctdb, nodemap, all_ips, mask);
+	unassign_unsuitable_ips(ctdb, ipflags, all_ips);
 
-	basic_allocate_unassigned(ctdb, nodemap, mask, all_ips);
+	basic_allocate_unassigned(ctdb, ipflags, all_ips);
 
 	/* No failback here! */
 }
 
 static void ip_alloc_nondeterministic_ips(struct ctdb_context *ctdb,
-					  struct ctdb_node_map *nodemap,
-					  struct ctdb_public_ip_list *all_ips,
-					  uint32_t mask)
+					  struct ctdb_ipflags *ipflags,
+					  struct ctdb_public_ip_list *all_ips)
 {
 	/* This should be pushed down into basic_failback. */
 	struct ctdb_public_ip_list *tmp_ip;
@@ -2140,9 +2135,9 @@ static void ip_alloc_nondeterministic_ips(struct ctdb_context *ctdb,
 		num_ips++;
 	}
 
-	unassign_unsuitable_ips(ctdb, nodemap, all_ips, mask);
+	unassign_unsuitable_ips(ctdb, ipflags, all_ips);
 
-	basic_allocate_unassigned(ctdb, nodemap, mask, all_ips);
+	basic_allocate_unassigned(ctdb, ipflags, all_ips);
 
 	/* If we don't want IPs to fail back then don't rebalance IPs. */
 	if (1 == ctdb->tunable.no_ip_failback) {
@@ -2152,24 +2147,24 @@ static void ip_alloc_nondeterministic_ips(struct ctdb_context *ctdb,
 	/* Now, try to make sure the ip adresses are evenly distributed
 	   across the nodes.
 	*/
-	basic_failback(ctdb, nodemap, mask, all_ips, num_ips);
+	basic_failback(ctdb, ipflags, all_ips, num_ips);
 }
 
 static void ip_alloc_lcp2(struct ctdb_context *ctdb,
-			  struct ctdb_node_map *nodemap,
-			  struct ctdb_public_ip_list *all_ips,
-			  uint32_t mask)
+			  struct ctdb_ipflags *ipflags,
+			  struct ctdb_public_ip_list *all_ips)
 {
 	uint32_t *lcp2_imbalances;
-	bool *newly_healthy;
+	bool *rebalance_candidates;
 
 	TALLOC_CTX *tmp_ctx = talloc_new(ctdb);
 
-	unassign_unsuitable_ips(ctdb, nodemap, all_ips, mask);
+	unassign_unsuitable_ips(ctdb, ipflags, all_ips);
 
-	lcp2_init(tmp_ctx, nodemap, mask, all_ips, &lcp2_imbalances, &newly_healthy);
+	lcp2_init(tmp_ctx, ipflags, all_ips,
+		  &lcp2_imbalances, &rebalance_candidates);
 
-	lcp2_allocate_unassigned(ctdb, nodemap, mask, all_ips, lcp2_imbalances);
+	lcp2_allocate_unassigned(ctdb, ipflags, all_ips, lcp2_imbalances);
 
 	/* If we don't want IPs to fail back then don't rebalance IPs. */
 	if (1 == ctdb->tunable.no_ip_failback) {
@@ -2179,19 +2174,16 @@ static void ip_alloc_lcp2(struct ctdb_context *ctdb,
 	/* Now, try to make sure the ip adresses are evenly distributed
 	   across the nodes.
 	*/
-	lcp2_failback(ctdb, nodemap, mask, all_ips, lcp2_imbalances, newly_healthy);
+	lcp2_failback(ctdb, ipflags, all_ips,
+		      lcp2_imbalances, rebalance_candidates);
 
 finished:
 	talloc_free(tmp_ctx);
 }
 
-/* The calculation part of the IP allocation algorithm. */
-static void ctdb_takeover_run_core(struct ctdb_context *ctdb,
-				   struct ctdb_node_map *nodemap,
-				   struct ctdb_public_ip_list **all_ips_p)
+static bool all_nodes_are_disabled(struct ctdb_node_map *nodemap)
 {
 	int i, num_healthy;
-	uint32_t mask;
 
 	/* Count how many completely healthy nodes we have */
 	num_healthy = 0;
@@ -2201,18 +2193,14 @@ static void ctdb_takeover_run_core(struct ctdb_context *ctdb,
 		}
 	}
 
-	/* If we have healthy nodes then we will only consider them
-	   for serving public addresses
-	*/
-	mask = NODE_FLAGS_INACTIVE|NODE_FLAGS_DISABLED;
-	if ((num_healthy == 0) &&
-	    (ctdb->tunable.no_ip_takeover_on_disabled == 0)) {
-		/* We didnt have any completely healthy nodes so
-		   use "disabled" nodes as a fallback
-		*/
-		mask = NODE_FLAGS_INACTIVE;
-	}
+	return num_healthy == 0;
+}
 
+/* The calculation part of the IP allocation algorithm. */
+static void ctdb_takeover_run_core(struct ctdb_context *ctdb,
+				   struct ctdb_ipflags *ipflags,
+				   struct ctdb_public_ip_list **all_ips_p)
+{
 	/* since nodes only know about those public addresses that
 	   can be served by that particular node, no single node has
 	   a full list of all public addresses that exist in the cluster.
@@ -2224,11 +2212,11 @@ static void ctdb_takeover_run_core(struct ctdb_context *ctdb,
 	*all_ips_p = create_merged_ip_list(ctdb);
 
         if (1 == ctdb->tunable.lcp2_public_ip_assignment) {
-		ip_alloc_lcp2(ctdb, nodemap, *all_ips_p, mask);
+		ip_alloc_lcp2(ctdb, ipflags, *all_ips_p);
 	} else if (1 == ctdb->tunable.deterministic_public_ips) {
-		ip_alloc_deterministic_ips(ctdb, nodemap, *all_ips_p, mask);
+		ip_alloc_deterministic_ips(ctdb, ipflags, *all_ips_p);
 	} else {
-		ip_alloc_nondeterministic_ips(ctdb, nodemap, *all_ips_p, mask);
+		ip_alloc_nondeterministic_ips(ctdb, ipflags, *all_ips_p);
 	}
 
 	/* at this point ->pnn is the node which will own each IP
@@ -2238,27 +2226,375 @@ static void ctdb_takeover_run_core(struct ctdb_context *ctdb,
 	return;
 }
 
-static void noiptakeover_cb(struct ctdb_context *ctdb, uint32_t pnn, int32_t res, TDB_DATA outdata, void *callback)
+struct get_tunable_callback_data {
+	const char *tunable;
+	uint32_t *out;
+	bool fatal;
+};
+
+static void get_tunable_callback(struct ctdb_context *ctdb, uint32_t pnn,
+				 int32_t res, TDB_DATA outdata,
+				 void *callback)
+{
+	struct get_tunable_callback_data *cd =
+		(struct get_tunable_callback_data *)callback;
+	int size;
+
+	if (res != 0) {
+		/* Already handled in fail callback */
+		return;
+	}
+
+	if (outdata.dsize != sizeof(uint32_t)) {
+		DEBUG(DEBUG_ERR,("Wrong size of returned data when reading \"%s\" tunable from node %d. Expected %d bytes but received %d bytes\n",
+				 cd->tunable, pnn, (int)sizeof(uint32_t),
+				 (int)outdata.dsize));
+		cd->fatal = true;
+		return;
+	}
+
+	size = talloc_array_length(cd->out);
+	if (pnn >= size) {
+		DEBUG(DEBUG_ERR,("Got %s reply from node %d but nodemap only has %d entries\n",
+				 cd->tunable, pnn, size));
+		return;
+	}
+
+		
+	cd->out[pnn] = *(uint32_t *)outdata.dptr;
+}
+
+static void get_tunable_fail_callback(struct ctdb_context *ctdb, uint32_t pnn,
+				       int32_t res, TDB_DATA outdata,
+				       void *callback)
+{
+	struct get_tunable_callback_data *cd =
+		(struct get_tunable_callback_data *)callback;
+
+	switch (res) {
+	case -ETIME:
+		DEBUG(DEBUG_ERR,
+		      ("Timed out getting tunable \"%s\" from node %d\n",
+		       cd->tunable, pnn));
+		cd->fatal = true;
+		break;
+	case -EINVAL:
+	case -1:
+		DEBUG(DEBUG_WARNING,
+		      ("Tunable \"%s\" not implemented on node %d\n",
+		       cd->tunable, pnn));
+		break;
+	default:
+		DEBUG(DEBUG_ERR,
+		      ("Unexpected error getting tunable \"%s\" from node %d\n",
+		       cd->tunable, pnn));
+		cd->fatal = true;
+	}
+}
+
+static uint32_t *get_tunable_from_nodes(struct ctdb_context *ctdb,
+					TALLOC_CTX *tmp_ctx,
+					struct ctdb_node_map *nodemap,
+					const char *tunable,
+					uint32_t default_value)
+{
+	TDB_DATA data;
+	struct ctdb_control_get_tunable *t;
+	uint32_t *nodes;
+	uint32_t *tvals;
+	struct get_tunable_callback_data callback_data;
+	int i;
+
+	tvals = talloc_array(tmp_ctx, uint32_t, nodemap->num);
+	CTDB_NO_MEMORY_NULL(ctdb, tvals);
+	for (i=0; i<nodemap->num; i++) {
+		tvals[i] = default_value;
+	}
+		
+	callback_data.out = tvals;
+	callback_data.tunable = tunable;
+	callback_data.fatal = false;
+
+	data.dsize = offsetof(struct ctdb_control_get_tunable, name) + strlen(tunable) + 1;
+	data.dptr  = talloc_size(tmp_ctx, data.dsize);
+	t = (struct ctdb_control_get_tunable *)data.dptr;
+	t->length = strlen(tunable)+1;
+	memcpy(t->name, tunable, t->length);
+	nodes = list_of_connected_nodes(ctdb, nodemap, tmp_ctx, true);
+	if (ctdb_client_async_control(ctdb, CTDB_CONTROL_GET_TUNABLE,
+				      nodes, 0, TAKEOVER_TIMEOUT(),
+				      false, data,
+				      get_tunable_callback,
+				      get_tunable_fail_callback,
+				      &callback_data) != 0) {
+		if (callback_data.fatal) {
+			talloc_free(tvals);
+			tvals = NULL;
+		}
+	}
+	talloc_free(nodes);
+	talloc_free(data.dptr);
+
+	return tvals;
+}
+
+struct get_runstate_callback_data {
+	enum ctdb_runstate *out;
+	bool fatal;
+};
+
+static void get_runstate_callback(struct ctdb_context *ctdb, uint32_t pnn,
+				  int32_t res, TDB_DATA outdata,
+				  void *callback_data)
 {
-	struct ctdb_node_map *nodemap = (struct ctdb_node_map *)callback;
+	struct get_runstate_callback_data *cd =
+		(struct get_runstate_callback_data *)callback_data;
+	int size;
 
 	if (res != 0) {
-		DEBUG(DEBUG_ERR,("Failure to read NoIPTakeover tunable from remote node %d\n", pnn));
+		/* Already handled in fail callback */
 		return;
 	}
 
 	if (outdata.dsize != sizeof(uint32_t)) {
-		DEBUG(DEBUG_ERR,("Wrong size of returned data when reading NoIPTakeover tunable from node %d. Expected %d bytes but received %d bytes\n", pnn, (int)sizeof(uint32_t), (int)outdata.dsize));
+		DEBUG(DEBUG_ERR,("Wrong size of returned data when getting runstate from node %d. Expected %d bytes but received %d bytes\n",
+				 pnn, (int)sizeof(uint32_t),
+				 (int)outdata.dsize));
+		cd->fatal = true;
 		return;
 	}
 
-	if (pnn >= nodemap->num) {
-		DEBUG(DEBUG_ERR,("Got NoIPTakeover reply from node %d but nodemap only has %d entries\n", pnn, nodemap->num));
+	size = talloc_array_length(cd->out);
+	if (pnn >= size) {
+		DEBUG(DEBUG_ERR,("Got reply from node %d but nodemap only has %d entries\n",
+				 pnn, size));
 		return;
 	}
 
-	if (*(uint32_t *)outdata.dptr != 0) {
-		nodemap->nodes[pnn].flags |= NODE_FLAGS_NOIPTAKEOVER;
+	cd->out[pnn] = (enum ctdb_runstate)*(uint32_t *)outdata.dptr;
+}
+
+static void get_runstate_fail_callback(struct ctdb_context *ctdb, uint32_t pnn,
+				       int32_t res, TDB_DATA outdata,
+				       void *callback)
+{
+	struct get_runstate_callback_data *cd =
+		(struct get_runstate_callback_data *)callback;
+
+	switch (res) {
+	case -ETIME:
+		DEBUG(DEBUG_ERR,
+		      ("Timed out getting runstate from node %d\n", pnn));
+		cd->fatal = true;
+		break;
+	default:
+		DEBUG(DEBUG_WARNING,
+		      ("Error getting runstate from node %d - assuming runstates not supported\n",
+		       pnn));
+	}
+}
+
+static enum ctdb_runstate * get_runstate_from_nodes(struct ctdb_context *ctdb,
+						    TALLOC_CTX *tmp_ctx,
+						    struct ctdb_node_map *nodemap,
+						    enum ctdb_runstate default_value)
+{
+	uint32_t *nodes;
+	enum ctdb_runstate *rs;
+	struct get_runstate_callback_data callback_data;
+	int i;
+
+	rs = talloc_array(tmp_ctx, enum ctdb_runstate, nodemap->num);
+	CTDB_NO_MEMORY_NULL(ctdb, rs);
+	for (i=0; i<nodemap->num; i++) {
+		rs[i] = default_value;
+	}
+
+	callback_data.out = rs;
+	callback_data.fatal = false;
+
+	nodes = list_of_connected_nodes(ctdb, nodemap, tmp_ctx, true);
+	if (ctdb_client_async_control(ctdb, CTDB_CONTROL_GET_RUNSTATE,
+				      nodes, 0, TAKEOVER_TIMEOUT(),
+				      true, tdb_null,
+				      get_runstate_callback,
+				      get_runstate_fail_callback,
+				      &callback_data) != 0) {
+		if (callback_data.fatal) {
+			free(rs);
+			rs = NULL;
+		}
+	}
+	talloc_free(nodes);
+
+	return rs;
+}
+
+/* Set internal flags for IP allocation:
+ *   Clear ip flags
+ *   Set NOIPTAKOVER ip flags from per-node NoIPTakeover tunable
+ *   Set NOIPHOST ip flag for each INACTIVE node
+ *   if all nodes are disabled:
+ *     Set NOIPHOST ip flags from per-node NoIPHostOnAllDisabled tunable
+ *   else
+ *     Set NOIPHOST ip flags for disabled nodes
+ */
+static struct ctdb_ipflags *
+set_ipflags_internal(struct ctdb_context *ctdb,
+		     TALLOC_CTX *tmp_ctx,
+		     struct ctdb_node_map *nodemap,
+		     uint32_t *tval_noiptakeover,
+		     uint32_t *tval_noiphostonalldisabled,
+		     enum ctdb_runstate *runstate)
+{
+	int i;
+	struct ctdb_ipflags *ipflags;
+
+	/* Clear IP flags - implicit due to talloc_zero */
+	ipflags = talloc_zero_array(tmp_ctx, struct ctdb_ipflags, nodemap->num);
+	CTDB_NO_MEMORY_NULL(ctdb, ipflags);
+
+	for (i=0;i<nodemap->num;i++) {
+		/* Can not take IPs on node with NoIPTakeover set */
+		if (tval_noiptakeover[i] != 0) {
+			ipflags[i].noiptakeover = true;
+		}
+
+		/* Can not host IPs on node not in RUNNING state */
+		if (runstate[i] != CTDB_RUNSTATE_RUNNING) {
+			ipflags[i].noiphost = true;
+			continue;
+		}
+		/* Can not host IPs on INACTIVE node */
+		if (nodemap->nodes[i].flags & NODE_FLAGS_INACTIVE) {
+			ipflags[i].noiphost = true;
+		}
+	}
+
+	if (all_nodes_are_disabled(nodemap)) {
+		/* If all nodes are disabled, can not host IPs on node
+		 * with NoIPHostOnAllDisabled set
+		 */
+		for (i=0;i<nodemap->num;i++) {
+			if (tval_noiphostonalldisabled[i] != 0) {
+				ipflags[i].noiphost = true;
+			}
+		}
+	} else {
+		/* If some nodes are not disabled, then can not host
+		 * IPs on DISABLED node
+		 */
+		for (i=0;i<nodemap->num;i++) {
+			if (nodemap->nodes[i].flags & NODE_FLAGS_DISABLED) {
+				ipflags[i].noiphost = true;
+			}
+		}
+	}
+
+	return ipflags;
+}
+
+static struct ctdb_ipflags *set_ipflags(struct ctdb_context *ctdb,
+					TALLOC_CTX *tmp_ctx,
+					struct ctdb_node_map *nodemap)
+{
+	uint32_t *tval_noiptakeover;
+	uint32_t *tval_noiphostonalldisabled;
+	struct ctdb_ipflags *ipflags;
+	enum ctdb_runstate *runstate;
+
+
+	tval_noiptakeover = get_tunable_from_nodes(ctdb, tmp_ctx, nodemap,
+						   "NoIPTakeover", 0);
+	if (tval_noiptakeover == NULL) {
+		return NULL;
+	}
+
+	tval_noiphostonalldisabled =
+		get_tunable_from_nodes(ctdb, tmp_ctx, nodemap,
+				       "NoIPHostOnAllDisabled", 0);
+	if (tval_noiphostonalldisabled == NULL) {
+		/* Caller frees tmp_ctx */
+		return NULL;
+	}
+
+	/* Any nodes where CTDB_CONTROL_GET_RUNSTATE is not supported
+	 * will default to CTDB_RUNSTATE_RUNNING.  This ensures
+	 * reasonable behaviour on a mixed cluster during upgrade.
+	 */
+	runstate = get_runstate_from_nodes(ctdb, tmp_ctx, nodemap,
+					   CTDB_RUNSTATE_RUNNING);
+	if (runstate == NULL) {
+		/* Caller frees tmp_ctx */
+		return NULL;
+	}
+
+	ipflags = set_ipflags_internal(ctdb, tmp_ctx, nodemap,
+				       tval_noiptakeover,
+				       tval_noiphostonalldisabled,
+				       runstate);
+
+	talloc_free(tval_noiptakeover);
+	talloc_free(tval_noiphostonalldisabled);
+	talloc_free(runstate);
+
+	return ipflags;
+}
+
+struct iprealloc_callback_data {
+	bool *retry_nodes;
+	int retry_count;
+	client_async_callback fail_callback;
+	void *fail_callback_data;
+	struct ctdb_node_map *nodemap;
+};
+
+static void iprealloc_fail_callback(struct ctdb_context *ctdb, uint32_t pnn,
+					int32_t res, TDB_DATA outdata,
+					void *callback)
+{
+	int numnodes;
+	struct iprealloc_callback_data *cd =
+		(struct iprealloc_callback_data *)callback;
+
+	switch (res) {
+	case -ETIME:
+		/* If the control timed out then that's a real error,
+		 * so call the real fail callback
+		 */
+		cd->fail_callback(ctdb, pnn, res, outdata,
+				  cd->fail_callback_data);
+		break;
+	default:
+		/* If not a timeout then either the ipreallocated
+		 * eventscript (or some setup) failed.  This might
+		 * have failed because the IPREALLOCATED control isn't
+		 * implemented - right now there is no way of knowing
+		 * because the error codes are all folded down to -1.
+		 * Consider retrying using EVENTSCRIPT control...
+		 */
+
+		numnodes = talloc_array_length(cd->retry_nodes);
+		if (pnn > numnodes) {
+			DEBUG(DEBUG_ERR,
+			      ("ipreallocated failure from node %d, but only %d nodes in nodemap\n",
+			       pnn, numnodes));
+			return;
+		}
+
+		/* Can't run the "ipreallocated" event on a STOPPED node */
+		if (cd->nodemap->nodes[pnn].flags & NODE_FLAGS_STOPPED) {
+			DEBUG(DEBUG_ERR,
+			      ("ipreallocated failure from node %d, but node is stopped - not flagging a retry\n",
+			       pnn));
+			return;
+		}
+
+		DEBUG(DEBUG_WARNING,
+		      ("ipreallocated failure from node %d, flagging retry\n",
+		       pnn));
+		cd->retry_nodes[pnn] = true;
+		cd->retry_count++;
 	}
 }
 
@@ -2268,10 +2604,9 @@ static void noiptakeover_cb(struct ctdb_context *ctdb, uint32_t pnn, int32_t res
 int ctdb_takeover_run(struct ctdb_context *ctdb, struct ctdb_node_map *nodemap,
 		      client_async_callback fail_callback, void *callback_data)
 {
-	int i;
+	int i, j;
 	struct ctdb_public_ip ip;
 	struct ctdb_public_ipv4 ipv4;
-	struct ctdb_control_get_tunable *t;
 	uint32_t *nodes;
 	struct ctdb_public_ip_list *all_ips, *tmp_ip;
 	TDB_DATA data;
@@ -2280,6 +2615,9 @@ int ctdb_takeover_run(struct ctdb_context *ctdb, struct ctdb_node_map *nodemap,
 	struct ctdb_client_control_state *state;
 	TALLOC_CTX *tmp_ctx = talloc_new(ctdb);
 	uint32_t disable_timeout;
+	struct ctdb_ipflags *ipflags;
+	struct iprealloc_callback_data iprealloc_data;
+	bool *retry_data;
 
 	/*
 	 * ip failover is completely disabled, just send out the 
@@ -2289,32 +2627,21 @@ int ctdb_takeover_run(struct ctdb_context *ctdb, struct ctdb_node_map *nodemap,
 		goto ipreallocated;
 	}
 
-
-	/* assume all nodes do support failback */
-	for (i=0;i<nodemap->num;i++) {
-		nodemap->nodes[i].flags &= ~NODE_FLAGS_NOIPTAKEOVER;
-	}
-	data.dsize = offsetof(struct ctdb_control_get_tunable, name) + strlen("NoIPTakeover") + 1;
-	data.dptr  = talloc_size(tmp_ctx, data.dsize);
-	t = (struct ctdb_control_get_tunable *)data.dptr;
-	t->length = strlen("NoIPTakeover")+1;
-	memcpy(t->name, "NoIPTakeover", t->length);
-	nodes = list_of_connected_nodes(ctdb, nodemap, tmp_ctx, true);
-	if (ctdb_client_async_control(ctdb, CTDB_CONTROL_GET_TUNABLE,
-				      nodes, 0, TAKEOVER_TIMEOUT(),
-				      false, data,
-				      noiptakeover_cb, NULL,
-				      nodemap) != 0) {
-		DEBUG(DEBUG_ERR, (__location__ " ctdb_control to get noiptakeover tunable failed\n"));
+	ipflags = set_ipflags(ctdb, tmp_ctx, nodemap);
+	if (ipflags == NULL) {
+		DEBUG(DEBUG_ERR,("Failed to set IP flags - aborting takeover run\n"));
+		talloc_free(tmp_ctx);
+		return -1;
 	}
-	talloc_free(nodes);
-	talloc_free(data.dptr);
-
 
 	ZERO_STRUCT(ip);
 
 	/* Do the IP reassignment calculations */
-	ctdb_takeover_run_core(ctdb, nodemap, &all_ips);
+	ctdb_takeover_run_core(ctdb, ipflags, &all_ips);
+
+	/* The IP flags need to be cleared because they should never
+	 * be seen outside the IP allocation code.
+	 */
 
 	/* The recovery daemon does regular sanity checks of the IPs.
 	 * However, sometimes it is overzealous and thinks changes are
@@ -2450,15 +2777,53 @@ ipreallocated:
 	 * IPs have moved.  Once upon a time this event only used to
 	 * update natwg.
 	 */
-	data.dptr  = discard_const("ipreallocated");
-	data.dsize = strlen((char *)data.dptr) + 1; 
+	retry_data = talloc_zero_array(tmp_ctx, bool, nodemap->num);
+	CTDB_NO_MEMORY_FATAL(ctdb, retry_data);
+	iprealloc_data.retry_nodes = retry_data;
+	iprealloc_data.retry_count = 0;
+	iprealloc_data.fail_callback = fail_callback;
+	iprealloc_data.fail_callback_data = callback_data;
+	iprealloc_data.nodemap = nodemap;
+
 	nodes = list_of_connected_nodes(ctdb, nodemap, tmp_ctx, true);
-	if (ctdb_client_async_control(ctdb, CTDB_CONTROL_RUN_EVENTSCRIPTS,
+	if (ctdb_client_async_control(ctdb, CTDB_CONTROL_IPREALLOCATED,
 				      nodes, 0, TAKEOVER_TIMEOUT(),
-				      false, data,
-				      NULL, fail_callback,
-				      callback_data) != 0) {
-		DEBUG(DEBUG_ERR, (__location__ " failed to send control to run eventscripts with \"ipreallocated\"\n"));
+				      false, tdb_null,
+				      NULL, iprealloc_fail_callback,
+				      &iprealloc_data) != 0) {
+
+		/* If the control failed then we should retry to any
+		 * nodes flagged by iprealloc_fail_callback using the
+		 * EVENTSCRIPT control.  This is a best-effort at
+		 * backward compatiblity when running a mixed cluster
+		 * where some nodes have not yet been upgraded to
+		 * support the IPREALLOCATED control.
+		 */
+		DEBUG(DEBUG_WARNING,
+		      ("Retry ipreallocated to some nodes using eventscript control\n"));
+
+		nodes = talloc_array(tmp_ctx, uint32_t,
+				     iprealloc_data.retry_count);
+		CTDB_NO_MEMORY_FATAL(ctdb, nodes);
+
+		j = 0;
+		for (i=0; i<nodemap->num; i++) {
+			if (iprealloc_data.retry_nodes[i]) {
+				nodes[j] = i;
+				j++;
+			}
+		}
+
+		data.dptr  = discard_const("ipreallocated");
+		data.dsize = strlen((char *)data.dptr) + 1; 
+		if (ctdb_client_async_control(ctdb,
+					      CTDB_CONTROL_RUN_EVENTSCRIPTS,
+					      nodes, 0, TAKEOVER_TIMEOUT(),
+					      false, data,
+					      NULL, fail_callback,
+					      callback_data) != 0) {
+			DEBUG(DEBUG_ERR, (__location__ " failed to send control to run eventscripts with \"ipreallocated\"\n"));
+		}
 	}
 
 	talloc_free(tmp_ctx);
@@ -3725,6 +4090,8 @@ int32_t ctdb_control_add_public_address(struct ctdb_context *ctdb, TDB_DATA inda
 		return -1;
 	}
 
+	DEBUG(DEBUG_NOTICE,("Add IP %s\n", ctdb_addr_to_str(&pub->addr)));
+
 	ret = ctdb_add_public_address(ctdb, &pub->addr, pub->mask, &pub->iface[0], true);
 
 	if (ret != 0) {
@@ -3766,6 +4133,8 @@ int32_t ctdb_control_del_public_address(struct ctdb_context *ctdb, TDB_DATA inda
 		return -1;
 	}
 
+	DEBUG(DEBUG_NOTICE,("Delete IP %s\n", ctdb_addr_to_str(&pub->addr)));
+
 	/* walk over all public addresses until we find a match */
 	for (vnn=ctdb->vnn;vnn;vnn=vnn->next) {
 		if (ctdb_same_ip(&vnn->public_address, &pub->addr)) {
@@ -3804,6 +4173,62 @@ int32_t ctdb_control_del_public_address(struct ctdb_context *ctdb, TDB_DATA inda
 	return -1;
 }
 
+
+struct ipreallocated_callback_state {
+	struct ctdb_req_control *c;
+};
+
+static void ctdb_ipreallocated_callback(struct ctdb_context *ctdb,
+					int status, void *p)
+{
+	struct ipreallocated_callback_state *state =
+		talloc_get_type(p, struct ipreallocated_callback_state);
+
+	if (status != 0) {
+		DEBUG(DEBUG_ERR,
+		      (" \"ipreallocated\" event script failed (status %d)\n",
+		       status));
+		if (status == -ETIME) {
+			ctdb_ban_self(ctdb);
+		}
+	}
+
+	ctdb_request_control_reply(ctdb, state->c, NULL, status, NULL);
+	talloc_free(state);
+}
+
+/* A control to run the ipreallocated event */
+int32_t ctdb_control_ipreallocated(struct ctdb_context *ctdb,
+				   struct ctdb_req_control *c,
+				   bool *async_reply)
+{
+	int ret;
+	struct ipreallocated_callback_state *state;
+
+	state = talloc(ctdb, struct ipreallocated_callback_state);
+	CTDB_NO_MEMORY(ctdb, state);
+
+	DEBUG(DEBUG_INFO,(__location__ " Running \"ipreallocated\" event\n"));
+
+	ret = ctdb_event_script_callback(ctdb, state,
+					 ctdb_ipreallocated_callback, state,
+					 false, CTDB_EVENT_IPREALLOCATED,
+					 "%s", "");
+
+	if (ret != 0) {
+		DEBUG(DEBUG_ERR,("Failed to run \"ipreallocated\" event \n"));
+		talloc_free(state);
+		return -1;
+	}
+
+	/* tell the control that we will be reply asynchronously */
+	state->c    = talloc_steal(state, c);
+	*async_reply = true;
+
+	return 0;
+}
+
+
 /* This function is called from the recovery daemon to verify that a remote
    node has the expected ip allocation.
    This is verified against ctdb->ip_tree
diff --git a/server/ctdb_traverse.c b/server/ctdb_traverse.c
index 54ee70f..d9aed2b 100644
--- a/server/ctdb_traverse.c
+++ b/server/ctdb_traverse.c
@@ -214,6 +214,7 @@ struct ctdb_traverse_all_handle {
 	ctdb_traverse_fn_t callback;
 	void *private_data;
 	uint32_t null_count;
+	bool timedout;
 };
 
 /*
@@ -231,6 +232,14 @@ struct ctdb_traverse_all {
 	uint32_t pnn;
 	uint32_t client_reqid;
 	uint64_t srvid;
+};
+
+struct ctdb_traverse_all_ext {
+	uint32_t db_id;
+	uint32_t reqid;
+	uint32_t pnn;
+	uint32_t client_reqid;
+	uint64_t srvid;
 	bool withemptyrecords;
 };
 
@@ -243,6 +252,7 @@ static void ctdb_traverse_all_timeout(struct event_context *ev, struct timed_eve
 	DEBUG(DEBUG_ERR,(__location__ " Traverse all timeout on database:%s\n", state->ctdb_db->db_name));
 	CTDB_INCREMENT_STAT(state->ctdb, timeouts.traverse);
 
+	state->timedout = true;
 	state->callback(state->private_data, tdb_null, tdb_null);
 }
 
@@ -261,7 +271,7 @@ struct traverse_start_state {
 /*
   setup a cluster-wide non-blocking traverse of a ctdb. The
   callback function will be called on every record in the local
-  ltdb. To stop the travserse, talloc_free() the traverse_handle.
+  ltdb. To stop the traverse, talloc_free() the traverse_handle.
 
   The traverse is finished when the callback is called with tdb_null
   for key and data
@@ -275,6 +285,7 @@ static struct ctdb_traverse_all_handle *ctdb_daemon_traverse_all(struct ctdb_db_
 	int ret;
 	TDB_DATA data;
 	struct ctdb_traverse_all r;
+	struct ctdb_traverse_all_ext r_ext;
 	uint32_t destination;
 
 	state = talloc(start_state, struct ctdb_traverse_all_handle);
@@ -288,18 +299,30 @@ static struct ctdb_traverse_all_handle *ctdb_daemon_traverse_all(struct ctdb_db_
 	state->callback     = callback;
 	state->private_data = start_state;
 	state->null_count   = 0;
+	state->timedout     = false;
 	
 	talloc_set_destructor(state, ctdb_traverse_all_destructor);
 
-	r.db_id = ctdb_db->db_id;
-	r.reqid = state->reqid;
-	r.pnn   = ctdb->pnn;
-	r.client_reqid = start_state->reqid;
-	r.srvid = start_state->srvid;
-	r.withemptyrecords = start_state->withemptyrecords;
+	if (start_state->withemptyrecords) {
+		r_ext.db_id = ctdb_db->db_id;
+		r_ext.reqid = state->reqid;
+		r_ext.pnn   = ctdb->pnn;
+		r_ext.client_reqid = start_state->reqid;
+		r_ext.srvid = start_state->srvid;
+		r_ext.withemptyrecords = start_state->withemptyrecords;
 
-	data.dptr = (uint8_t *)&r;
-	data.dsize = sizeof(r);
+		data.dptr = (uint8_t *)&r_ext;
+		data.dsize = sizeof(r_ext);
+	} else {
+		r.db_id = ctdb_db->db_id;
+		r.reqid = state->reqid;
+		r.pnn   = ctdb->pnn;
+		r.client_reqid = start_state->reqid;
+		r.srvid = start_state->srvid;
+
+		data.dptr = (uint8_t *)&r;
+		data.dsize = sizeof(r);
+	}
 
 	if (ctdb_db->persistent == 0) {
 		/* normal database, traverse all nodes */	  
@@ -328,9 +351,16 @@ static struct ctdb_traverse_all_handle *ctdb_daemon_traverse_all(struct ctdb_db_
 	 * node, or if it is a persistent database, just tell the local
 	 * node
 	 */
-	ret = ctdb_daemon_send_control(ctdb, destination, 0, 
-			       CTDB_CONTROL_TRAVERSE_ALL,
-			       0, CTDB_CTRL_FLAG_NOREPLY, data, NULL, NULL);
+
+	if (start_state->withemptyrecords) {
+		ret = ctdb_daemon_send_control(ctdb, destination, 0,
+				       CTDB_CONTROL_TRAVERSE_ALL_EXT,
+				       0, CTDB_CTRL_FLAG_NOREPLY, data, NULL, NULL);
+	} else {
+		ret = ctdb_daemon_send_control(ctdb, destination, 0,
+				       CTDB_CONTROL_TRAVERSE_ALL,
+				       0, CTDB_CTRL_FLAG_NOREPLY, data, NULL, NULL);
+	}
 
 	if (ret != 0) {
 		talloc_free(state);
@@ -378,6 +408,56 @@ static void traverse_all_callback(void *p, TDB_DATA key, TDB_DATA data)
 }
 
 /*
+ * extended version to take the "withemptyrecords" parameter"
+ */
+int32_t ctdb_control_traverse_all_ext(struct ctdb_context *ctdb, TDB_DATA data, TDB_DATA *outdata)
+{
+	struct ctdb_traverse_all_ext *c = (struct ctdb_traverse_all_ext *)data.dptr;
+	struct traverse_all_state *state;
+	struct ctdb_db_context *ctdb_db;
+
+	if (data.dsize != sizeof(struct ctdb_traverse_all_ext)) {
+		DEBUG(DEBUG_ERR,(__location__ " Invalid size in ctdb_control_traverse_all_ext\n"));
+		return -1;
+	}
+
+	ctdb_db = find_ctdb_db(ctdb, c->db_id);
+	if (ctdb_db == NULL) {
+		return -1;
+	}
+
+	if (ctdb_db->unhealthy_reason) {
+		if (ctdb->tunable.allow_unhealthy_db_read == 0) {
+			DEBUG(DEBUG_ERR,("db(%s) unhealty in ctdb_control_traverse_all: %s\n",
+					ctdb_db->db_name, ctdb_db->unhealthy_reason));
+			return -1;
+		}
+		DEBUG(DEBUG_WARNING,("warn: db(%s) unhealty in ctdb_control_traverse_all: %s\n",
+				     ctdb_db->db_name, ctdb_db->unhealthy_reason));
+	}
+
+	state = talloc(ctdb_db, struct traverse_all_state);
+	if (state == NULL) {
+		return -1;
+	}
+
+	state->reqid = c->reqid;
+	state->srcnode = c->pnn;
+	state->ctdb = ctdb;
+	state->client_reqid = c->client_reqid;
+	state->srvid = c->srvid;
+	state->withemptyrecords = c->withemptyrecords;
+
+	state->h = ctdb_traverse_local(ctdb_db, traverse_all_callback, state);
+	if (state->h == NULL) {
+		talloc_free(state);
+		return -1;
+	}
+
+	return 0;
+}
+
+/*
   called when a CTDB_CONTROL_TRAVERSE_ALL control comes in. We then
   setup a traverse of our local ltdb, sending the records as
   CTDB_CONTROL_TRAVERSE_DATA records back to the originator
@@ -418,7 +498,7 @@ int32_t ctdb_control_traverse_all(struct ctdb_context *ctdb, TDB_DATA data, TDB_
 	state->ctdb = ctdb;
 	state->client_reqid = c->client_reqid;
 	state->srvid = c->srvid;
-	state->withemptyrecords = c->withemptyrecords;
+	state->withemptyrecords = false;
 
 	state->h = ctdb_traverse_local(ctdb_db, traverse_all_callback, state);
 	if (state->h == NULL) {
@@ -549,9 +629,14 @@ static void traverse_start_callback(void *p, TDB_DATA key, TDB_DATA data)
 
 	ctdb_dispatch_message(state->ctdb, state->srvid, cdata);
 	if (key.dsize == 0 && data.dsize == 0) {
-		/* end of traverse */
-		talloc_set_destructor(state, NULL);
-		talloc_free(state);
+	    	if (state->h->timedout) {
+		    	/* timed out, send TRAVERSE_KILL control */
+			talloc_free(state);
+		} else {
+			/* end of traverse */
+			talloc_set_destructor(state, NULL);
+			talloc_free(state);
+		}
 	}
 }
 
diff --git a/server/ctdb_tunables.c b/server/ctdb_tunables.c
index b86d6d2..365c6ba 100644
--- a/server/ctdb_tunables.c
+++ b/server/ctdb_tunables.c
@@ -83,8 +83,8 @@ static const struct {
 	{ "DBRecordCountWarn",    100000,  offsetof(struct ctdb_tunable, db_record_count_warn), false },
 	{ "DBRecordSizeWarn",   10000000,  offsetof(struct ctdb_tunable, db_record_size_warn), false },
 	{ "DBSizeWarn",        100000000,  offsetof(struct ctdb_tunable, db_size_warn), false },
-	{ "PullDBPreallocation", 10*1024*10240,  offsetof(struct ctdb_tunable, pulldb_preallocation_size), false },
-	{ "NoIPTakeoverOnDisabled",    0,  offsetof(struct ctdb_tunable, no_ip_takeover_on_disabled), false },
+	{ "PullDBPreallocation", 10*1024*1024,  offsetof(struct ctdb_tunable, pulldb_preallocation_size), false },
+	{ "NoIPHostOnAllDisabled",    0,  offsetof(struct ctdb_tunable, no_ip_host_on_all_disabled), false },
 	{ "DeadlockTimeout",	300, offsetof(struct ctdb_tunable, deadlock_timeout), false },
 	{ "Samba3AvoidDeadlocks", 0, offsetof(struct ctdb_tunable, samba3_hack), false },
 };
@@ -128,7 +128,7 @@ int32_t ctdb_control_get_tunable(struct ctdb_context *ctdb, TDB_DATA indata,
 	talloc_free(name);
 	
 	if (i == ARRAY_SIZE(tunable_map)) {
-		return -1;
+		return -EINVAL;
 	}
 
 	val = *(uint32_t *)(tunable_map[i].offset + (uint8_t*)&ctdb->tunable);
diff --git a/server/ctdb_vacuum.c b/server/ctdb_vacuum.c
index 4a000b0..d7527d4 100644
--- a/server/ctdb_vacuum.c
+++ b/server/ctdb_vacuum.c
@@ -2,7 +2,7 @@
    ctdb vacuuming events
 
    Copyright (C) Ronnie Sahlberg  2009
-   Copyright (C) Michael Adam 2010-2011
+   Copyright (C) Michael Adam 2010-2013
    Copyright (C) Stefan Metzmacher 2010-2011
 
    This program is free software; you can redistribute it and/or modify
@@ -96,6 +96,7 @@ struct delete_record_data {
 
 struct delete_records_list {
 	struct ctdb_marshall_buffer *records;
+	struct vacuum_data *vdata;
 };
 
 /**
@@ -303,6 +304,141 @@ static int delete_marshall_traverse(void *param, void *data)
 }
 
 /**
+ * Variant of delete_marshall_traverse() that bumps the
+ * RSN of each traversed record in the database.
+ *
+ * This is needed to ensure that when rolling out our
+ * empty record copy before remote deletion, we as the
+ * record's dmaster keep a higher RSN than the non-dmaster
+ * nodes. This is needed to prevent old copies from
+ * resurrection in recoveries.
+ */
+static int delete_marshall_traverse_first(void *param, void *data)
+{
+	struct delete_record_data *dd = talloc_get_type(data, struct delete_record_data);
+	struct delete_records_list *recs = talloc_get_type(param, struct delete_records_list);
+	struct ctdb_db_context *ctdb_db = dd->ctdb_db;
+	struct ctdb_context *ctdb = ctdb_db->ctdb;
+	struct ctdb_ltdb_header *header;
+	TDB_DATA tdb_data, ctdb_data;
+	uint32_t lmaster;
+	uint32_t hash = ctdb_hash(&(dd->key));
+	int res;
+
+	res = tdb_chainlock(ctdb_db->ltdb->tdb, dd->key);
+	if (res != 0) {
+		DEBUG(DEBUG_ERR,
+		      (__location__ " Error getting chainlock on record with "
+		       "key hash [0x%08x] on database db[%s].\n",
+		       hash, ctdb_db->db_name));
+		recs->vdata->delete_skipped++;
+		talloc_free(dd);
+		return 0;
+	}
+
+	/*
+	 * Verify that the record is still empty, its RSN has not
+	 * changed and that we are still its lmaster and dmaster.
+	 */
+
+	tdb_data = tdb_fetch(ctdb_db->ltdb->tdb, dd->key);
+	if (tdb_data.dsize < sizeof(struct ctdb_ltdb_header)) {
+		DEBUG(DEBUG_INFO, (__location__ ": record with hash [0x%08x] "
+				   "on database db[%s] does not exist or is not"
+				   " a ctdb-record.  skipping.\n",
+				   hash, ctdb_db->db_name));
+		goto skip;
+	}
+
+	if (tdb_data.dsize > sizeof(struct ctdb_ltdb_header)) {
+		DEBUG(DEBUG_INFO, (__location__ ": record with hash [0x%08x] "
+				   "on database db[%s] has been recycled. "
+				   "skipping.\n",
+				   hash, ctdb_db->db_name));
+		goto skip;
+	}
+
+	header = (struct ctdb_ltdb_header *)tdb_data.dptr;
+
+	if (header->flags & CTDB_REC_RO_FLAGS) {
+		DEBUG(DEBUG_INFO, (__location__ ": record with hash [0x%08x] "
+				   "on database db[%s] has read-only flags. "
+				   "skipping.\n",
+				   hash, ctdb_db->db_name));
+		goto skip;
+	}
+
+	if (header->dmaster != ctdb->pnn) {
+		DEBUG(DEBUG_INFO, (__location__ ": record with hash [0x%08x] "
+				   "on database db[%s] has been migrated away. "
+				   "skipping.\n",
+				   hash, ctdb_db->db_name));
+		goto skip;
+	}
+
+	if (header->rsn != dd->hdr.rsn) {
+		DEBUG(DEBUG_INFO, (__location__ ": record with hash [0x%08x] "
+				   "on database db[%s] seems to have been "
+				   "migrated away and back again (with empty "
+				   "data). skipping.\n",
+				   hash, ctdb_db->db_name));
+		goto skip;
+	}
+
+	lmaster = ctdb_lmaster(ctdb_db->ctdb, &dd->key);
+
+	if (lmaster != ctdb->pnn) {
+		DEBUG(DEBUG_INFO, (__location__ ": not lmaster for record in "
+				   "delete list (key hash [0x%08x], db[%s]). "
+				   "Strange! skipping.\n",
+				   hash, ctdb_db->db_name));
+		goto skip;
+	}
+
+	/*
+	 * Increment the record's RSN to ensure the dmaster (i.e. the current
+	 * node) has the highest RSN of the record in the cluster.
+	 * This is to prevent old record copies from resurrecting in recoveries
+	 * if something should fail during the deletion process.
+	 * Note that ctdb_ltdb_store_server() increments the RSN if called
+	 * on the record's dmaster.
+	 */
+
+	ctdb_data.dptr = tdb_data.dptr + sizeof(struct ctdb_ltdb_header);
+	ctdb_data.dsize = tdb_data.dsize - sizeof(struct ctdb_ltdb_header);
+
+	res = ctdb_ltdb_store(ctdb_db, dd->key, header, ctdb_data);
+	if (res != 0) {
+		DEBUG(DEBUG_ERR, (__location__ ": Failed to store record with "
+				  "key hash [0x%08x] on database db[%s].\n",
+				  hash, ctdb_db->db_name));
+		goto skip;
+	}
+
+	tdb_chainunlock(ctdb_db->ltdb->tdb, dd->key);
+
+	goto done;
+
+skip:
+	tdb_chainunlock(ctdb_db->ltdb->tdb, dd->key);
+
+	recs->vdata->delete_skipped++;
+	talloc_free(dd);
+	dd = NULL;
+
+done:
+	if (tdb_data.dptr != NULL) {
+		free(tdb_data.dptr);
+	}
+
+	if (dd == NULL) {
+		return 0;
+	}
+
+	return delete_marshall_traverse(param, data);
+}
+
+/**
  * traverse function for the traversal of the delete_queue,
  * the fast-path vacuuming list.
  *
@@ -478,37 +614,55 @@ static int delete_record_traverse(void *param, void *data)
 
 	tdb_data = tdb_fetch(ctdb_db->ltdb->tdb, dd->key);
 	if (tdb_data.dsize < sizeof(struct ctdb_ltdb_header)) {
-		/* Does not exist or not a ctdb record. Skip. */
+		DEBUG(DEBUG_INFO, (__location__ ": record with hash [0x%08x] "
+				   "on database db[%s] does not exist or is not"
+				   " a ctdb-record.  skipping.\n",
+				   hash, ctdb_db->db_name));
 		vdata->delete_skipped++;
 		goto done;
 	}
 
 	if (tdb_data.dsize > sizeof(struct ctdb_ltdb_header)) {
-		/* The record has been recycled (filled with data). Skip. */
+		DEBUG(DEBUG_INFO, (__location__ ": record with hash [0x%08x] "
+				   "on database db[%s] has been recycled. "
+				   "skipping.\n",
+				   hash, ctdb_db->db_name));
 		vdata->delete_skipped++;
 		goto done;
 	}
 
 	header = (struct ctdb_ltdb_header *)tdb_data.dptr;
 
-	if (header->flags & (CTDB_REC_RO_HAVE_DELEGATIONS|CTDB_REC_RO_HAVE_READONLY|CTDB_REC_RO_REVOKING_READONLY|CTDB_REC_RO_REVOKE_COMPLETE)) {
-	  /* The record has readonly flags set. skip deleting */
+	if (header->flags & CTDB_REC_RO_FLAGS) {
+		DEBUG(DEBUG_INFO, (__location__ ": record with hash [0x%08x] "
+				   "on database db[%s] has read-only flags. "
+				   "skipping.\n",
+				   hash, ctdb_db->db_name));
 		vdata->delete_skipped++;
 		goto done;
 	}
 
 	if (header->dmaster != ctdb->pnn) {
-		/* The record has been migrated off the node. Skip. */
+		DEBUG(DEBUG_INFO, (__location__ ": record with hash [0x%08x] "
+				   "on database db[%s] has been migrated away. "
+				   "skipping.\n",
+				   hash, ctdb_db->db_name));
 		vdata->delete_skipped++;
 		goto done;
 	}
 
-
-	if (header->rsn != dd->hdr.rsn) {
+	if (header->rsn != dd->hdr.rsn + 1) {
 		/*
 		 * The record has been migrated off the node and back again.
 		 * But not requeued for deletion. Skip it.
+		 * (Note that the first marshall traverse has bumped the RSN
+		 *  on disk.)
 		 */
+		DEBUG(DEBUG_INFO, (__location__ ": record with hash [0x%08x] "
+				   "on database db[%s] seems to have been "
+				   "migrated away and back again (with empty "
+				   "data). skipping.\n",
+				   hash, ctdb_db->db_name));
 		vdata->delete_skipped++;
 		goto done;
 	}
@@ -516,7 +670,10 @@ static int delete_record_traverse(void *param, void *data)
 	lmaster = ctdb_lmaster(ctdb_db->ctdb, &dd->key);
 
 	if (lmaster != ctdb->pnn) {
-		/* we are not lmaster - strange */
+		DEBUG(DEBUG_INFO, (__location__ ": not lmaster for record in "
+				   "delete list (key hash [0x%08x], db[%s]). "
+				   "Strange! skipping.\n",
+				   hash, ctdb_db->db_name));
 		vdata->delete_skipped++;
 		goto done;
 	}
@@ -682,154 +839,295 @@ static int ctdb_process_vacuum_fetch_lists(struct ctdb_db_context *ctdb_db,
 
 /**
  * Process the delete list:
- * Send the records to delete to all other nodes with the
- * try_delete_records control.
+ *
+ * This is the last step of vacuuming that consistently deletes
+ * those records that have been migrated with data and can hence
+ * not be deleted when leaving a node.
+ *
+ * In this step, the lmaster does the final deletion of those empty
+ * records that it is also dmaster for. It has ususally received
+ * at least some of these records previously from the former dmasters
+ * with the vacuum fetch message.
+ *
+ * This last step is implemented as a 3-phase process to protect from
+ * races leading to data corruption:
+ *
+ *  1) Send the lmaster's copy to all other active nodes with the
+ *     RECEIVE_RECORDS control: The remote nodes store the lmaster's copy.
+ *  2) Send the records that could successfully be stored remotely
+ *     in step #1 to all active nodes with the TRY_DELETE_RECORDS
+ *     control. The remote notes delete their local copy.
+ *  3) The lmaster locally deletes its copies of all records that
+ *     could successfully be deleted remotely in step #2.
  */
 static int ctdb_process_delete_list(struct ctdb_db_context *ctdb_db,
 				    struct vacuum_data *vdata)
 {
 	int ret, i;
 	struct ctdb_context *ctdb = ctdb_db->ctdb;
+	struct delete_records_list *recs;
+	TDB_DATA indata;
+	struct ctdb_node_map *nodemap;
+	uint32_t *active_nodes;
+	int num_active_nodes;
+	TALLOC_CTX *tmp_ctx;
+
+	if (vdata->delete_count == 0) {
+		return 0;
+	}
+
+	tmp_ctx = talloc_new(vdata);
+	if (tmp_ctx == NULL) {
+		DEBUG(DEBUG_ERR,(__location__ " Out of memory\n"));
+		return 0;
+	}
 
 	vdata->delete_left = vdata->delete_count;
 
-	if (vdata->delete_count > 0) {
-		struct delete_records_list *recs;
-		TDB_DATA indata, outdata;
-		int32_t res;
-		struct ctdb_node_map *nodemap;
-		uint32_t *active_nodes;
-		int num_active_nodes;
+	/*
+	 * get the list of currently active nodes
+	 */
 
-		recs = talloc_zero(vdata, struct delete_records_list);
-		if (recs == NULL) {
-			DEBUG(DEBUG_ERR,(__location__ " Out of memory\n"));
-			return -1;
-		}
-		recs->records = (struct ctdb_marshall_buffer *)
-			talloc_zero_size(vdata, 
-				    offsetof(struct ctdb_marshall_buffer, data));
-		if (recs->records == NULL) {
-			DEBUG(DEBUG_ERR,(__location__ " Out of memory\n"));
-			return -1;
-		}
-		recs->records->db_id = ctdb_db->db_id;
+	ret = ctdb_ctrl_getnodemap(ctdb, TIMELIMIT(),
+				   CTDB_CURRENT_NODE,
+				   tmp_ctx,
+				   &nodemap);
+	if (ret != 0) {
+		DEBUG(DEBUG_ERR,(__location__ " unable to get node map\n"));
+		ret = -1;
+		goto done;
+	}
 
-		/* 
-		 * traverse the tree of all records we want to delete and
-		 * create a blob we can send to the other nodes.
-		 */
-		trbt_traversearray32(vdata->delete_list, 1,
-				     delete_marshall_traverse, recs);
+	active_nodes = list_of_active_nodes(ctdb, nodemap,
+					    nodemap, /* talloc context */
+					    false /* include self */);
+	/* yuck! ;-) */
+	num_active_nodes = talloc_get_size(active_nodes)/sizeof(*active_nodes);
 
-		indata.dsize = talloc_get_size(recs->records);
-		indata.dptr  = (void *)recs->records;
+	/*
+	 * Now delete the records all active nodes in a three-phase process:
+	 * 1) send all active remote nodes the current empty copy with this
+	 *    node as DMASTER
+	 * 2) if all nodes could store the new copy,
+	 *    tell all the active remote nodes to delete all their copy
+	 * 3) if all remote nodes deleted their record copy, delete it locally
+	 */
 
-		/* 
-		 * now tell all the active nodes to delete all these records
-		 * (if possible)
-		 */
+	/*
+	 * Step 1:
+	 * Send currently empty record copy to all active nodes for storing.
+	 */
 
-		ret = ctdb_ctrl_getnodemap(ctdb, TIMELIMIT(),
-					   CTDB_CURRENT_NODE,
-					   recs, /* talloc context */
-					   &nodemap);
-		if (ret != 0) {
-			DEBUG(DEBUG_ERR,(__location__ " unable to get node map\n"));
-			return -1;
+	recs = talloc_zero(tmp_ctx, struct delete_records_list);
+	if (recs == NULL) {
+		DEBUG(DEBUG_ERR,(__location__ " Out of memory\n"));
+		ret = -1;
+		goto done;
+	}
+	recs->records = (struct ctdb_marshall_buffer *)
+		talloc_zero_size(recs,
+				 offsetof(struct ctdb_marshall_buffer, data));
+	if (recs->records == NULL) {
+		DEBUG(DEBUG_ERR,(__location__ " Out of memory\n"));
+		ret = -1;
+		goto done;
+	}
+	recs->records->db_id = ctdb_db->db_id;
+	recs->vdata = vdata;
+
+	/*
+	 * traverse the tree of all records we want to delete and
+	 * create a blob we can send to the other nodes.
+	 *
+	 * We call delete_marshall_traverse_first() to bump the
+	 * records' RSNs in the database, to ensure we (as dmaster)
+	 * keep the highest RSN of the records in the cluster.
+	 */
+	trbt_traversearray32(vdata->delete_list, 1,
+			     delete_marshall_traverse_first, recs);
+
+	indata.dsize = talloc_get_size(recs->records);
+	indata.dptr  = (void *)recs->records;
+
+	for (i = 0; i < num_active_nodes; i++) {
+		struct ctdb_marshall_buffer *records;
+		struct ctdb_rec_data *rec;
+		int32_t res;
+		TDB_DATA outdata;
+
+		ret = ctdb_control(ctdb, active_nodes[i], 0,
+				CTDB_CONTROL_RECEIVE_RECORDS, 0,
+				indata, recs, &outdata, &res,
+				NULL, NULL);
+		if (ret != 0 || res != 0) {
+			DEBUG(DEBUG_ERR, ("Error storing record copies on "
+					  "node %u: ret[%d] res[%d]\n",
+					  active_nodes[i], ret, res));
+			ret = -1;
+			goto done;
 		}
 
-		active_nodes = list_of_active_nodes(ctdb, nodemap,
-						    nodemap, /* talloc context */
-						    false /* include self */);
-		/* yuck! ;-) */
-		num_active_nodes = talloc_get_size(active_nodes)/sizeof(*active_nodes);
-
-		for (i = 0; i < num_active_nodes; i++) {
-			struct ctdb_marshall_buffer *records;
-			struct ctdb_rec_data *rec;
-
-			ret = ctdb_control(ctdb, active_nodes[i], 0,
-					CTDB_CONTROL_TRY_DELETE_RECORDS, 0,
-					indata, recs, &outdata, &res,
-					NULL, NULL);
-			if (ret != 0 || res != 0) {
-				DEBUG(DEBUG_ERR, ("Failed to delete records on "
-						  "node %u: ret[%d] res[%d]\n",
-						  active_nodes[i], ret, res));
-				return -1;
+		/*
+		 * outdata contains the list of records coming back
+		 * from the node: These are the records that the
+		 * remote node could not store. We remove these from
+		 * the list to process further.
+		 */
+		records = (struct ctdb_marshall_buffer *)outdata.dptr;
+		rec = (struct ctdb_rec_data *)&records->data[0];
+		while (records->count-- > 1) {
+			TDB_DATA reckey, recdata;
+			struct ctdb_ltdb_header *rechdr;
+			struct delete_record_data *dd;
+
+			reckey.dptr = &rec->data[0];
+			reckey.dsize = rec->keylen;
+			recdata.dptr = &rec->data[reckey.dsize];
+			recdata.dsize = rec->datalen;
+
+			if (recdata.dsize < sizeof(struct ctdb_ltdb_header)) {
+				DEBUG(DEBUG_CRIT,(__location__ " bad ltdb record\n"));
+				ret = -1;
+				goto done;
 			}
-
-			/*
-			 * outdata contains the list of records coming back
-			 * from the node: These are the records that the
-			 * remote node could not delete.
-			 *
-			 * NOTE: There is a problem here:
-			 *
-			 * When a node failed to delete the record, but
-			 * others succeeded, we may have created gaps in the
-			 * history of the record. Hence when a node dies, an
-			 * closed file handle might be resurrected or an open
-			 * file handle might be lost, leading to blocked access
-			 * or data corruption.
-			 *
-			 * TODO: This needs to be fixed!
-			 */
-			records = (struct ctdb_marshall_buffer *)outdata.dptr;
-			rec = (struct ctdb_rec_data *)&records->data[0];
-			while (records->count-- > 1) {
-				TDB_DATA reckey, recdata;
-				struct ctdb_ltdb_header *rechdr;
-				struct delete_record_data *dd;
-
-				reckey.dptr = &rec->data[0];
-				reckey.dsize = rec->keylen;
-				recdata.dptr = &rec->data[reckey.dsize];
-				recdata.dsize = rec->datalen;
-
-				if (recdata.dsize < sizeof(struct ctdb_ltdb_header)) {
-					DEBUG(DEBUG_CRIT,(__location__ " bad ltdb record\n"));
-					return -1;
-				}
-				rechdr = (struct ctdb_ltdb_header *)recdata.dptr;
-				recdata.dptr += sizeof(*rechdr);
-				recdata.dsize -= sizeof(*rechdr);
-
-				dd = (struct delete_record_data *)trbt_lookup32(
-						vdata->delete_list,
-						ctdb_hash(&reckey));
-				if (dd != NULL) {
-					/*
-					 * The other node could not delete the
-					 * record and it is the first node that
-					 * failed. So we should remove it from
-					 * the tree and update statistics.
-					 */
-					talloc_free(dd);
-					vdata->delete_remote_error++;
-					vdata->delete_left--;
-				}
-
-				rec = (struct ctdb_rec_data *)(rec->length + (uint8_t *)rec);
+			rechdr = (struct ctdb_ltdb_header *)recdata.dptr;
+			recdata.dptr += sizeof(*rechdr);
+			recdata.dsize -= sizeof(*rechdr);
+
+			dd = (struct delete_record_data *)trbt_lookup32(
+					vdata->delete_list,
+					ctdb_hash(&reckey));
+			if (dd != NULL) {
+				/*
+				 * The other node could not store the record
+				 * copy and it is the first node that failed.
+				 * So we should remove it from the tree and
+				 * update statistics.
+				 */
+				talloc_free(dd);
+				vdata->delete_remote_error++;
+				vdata->delete_left--;
 			}
+
+			rec = (struct ctdb_rec_data *)(rec->length + (uint8_t *)rec);
 		}
+	}
+
+	if (vdata->delete_left == 0) {
+		goto success;
+	}
+
+	/*
+	 * Step 2:
+	 * Send the remaining records to all active nodes for deletion.
+	 *
+	 * The lmaster's (i.e. our) copies of these records have been stored
+	 * successfully on the other nodes.
+	 */
+
+	/*
+	 * Create a marshall blob from the remaining list of records to delete.
+	 */
+
+	talloc_free(recs->records);
 
-		/* free nodemap and active_nodes */
-		talloc_free(nodemap);
+	recs->records = (struct ctdb_marshall_buffer *)
+		talloc_zero_size(recs,
+				 offsetof(struct ctdb_marshall_buffer, data));
+	if (recs->records == NULL) {
+		DEBUG(DEBUG_ERR,(__location__ " Out of memory\n"));
+		ret = -1;
+		goto done;
 	}
+	recs->records->db_id = ctdb_db->db_id;
+
+	trbt_traversearray32(vdata->delete_list, 1,
+			     delete_marshall_traverse, recs);
+
+	indata.dsize = talloc_get_size(recs->records);
+	indata.dptr  = (void *)recs->records;
+
+	for (i = 0; i < num_active_nodes; i++) {
+		struct ctdb_marshall_buffer *records;
+		struct ctdb_rec_data *rec;
+		int32_t res;
+		TDB_DATA outdata;
+
+		ret = ctdb_control(ctdb, active_nodes[i], 0,
+				CTDB_CONTROL_TRY_DELETE_RECORDS, 0,
+				indata, recs, &outdata, &res,
+				NULL, NULL);
+		if (ret != 0 || res != 0) {
+			DEBUG(DEBUG_ERR, ("Failed to delete records on "
+					  "node %u: ret[%d] res[%d]\n",
+					  active_nodes[i], ret, res));
+			ret = -1;
+			goto done;
+		}
 
-	if (vdata->delete_left > 0) {
 		/*
-		 * The only records remaining in the tree are those
-		 * records which all other nodes could successfully
-		 * delete, so we can safely delete them on the
-		 * lmaster as well.
+		 * outdata contains the list of records coming back
+		 * from the node: These are the records that the
+		 * remote node could not delete. We remove these from
+		 * the list to delete locally.
 		 */
-		trbt_traversearray32(vdata->delete_list, 1,
-				     delete_record_traverse, vdata);
+		records = (struct ctdb_marshall_buffer *)outdata.dptr;
+		rec = (struct ctdb_rec_data *)&records->data[0];
+		while (records->count-- > 1) {
+			TDB_DATA reckey, recdata;
+			struct ctdb_ltdb_header *rechdr;
+			struct delete_record_data *dd;
+
+			reckey.dptr = &rec->data[0];
+			reckey.dsize = rec->keylen;
+			recdata.dptr = &rec->data[reckey.dsize];
+			recdata.dsize = rec->datalen;
+
+			if (recdata.dsize < sizeof(struct ctdb_ltdb_header)) {
+				DEBUG(DEBUG_CRIT,(__location__ " bad ltdb record\n"));
+				ret = -1;
+				goto done;
+			}
+			rechdr = (struct ctdb_ltdb_header *)recdata.dptr;
+			recdata.dptr += sizeof(*rechdr);
+			recdata.dsize -= sizeof(*rechdr);
+
+			dd = (struct delete_record_data *)trbt_lookup32(
+					vdata->delete_list,
+					ctdb_hash(&reckey));
+			if (dd != NULL) {
+				/*
+				 * The other node could not delete the
+				 * record and it is the first node that
+				 * failed. So we should remove it from
+				 * the tree and update statistics.
+				 */
+				talloc_free(dd);
+				vdata->delete_remote_error++;
+				vdata->delete_left--;
+			}
+
+			rec = (struct ctdb_rec_data *)(rec->length + (uint8_t *)rec);
+		}
 	}
 
+	if (vdata->delete_left == 0) {
+		goto success;
+	}
+
+	/*
+	 * Step 3:
+	 * Delete the remaining records locally.
+	 *
+	 * These records have successfully been deleted on all
+	 * active remote nodes.
+	 */
+
+	trbt_traversearray32(vdata->delete_list, 1,
+			     delete_record_traverse, vdata);
+
+success:
+
 	if (vdata->delete_count > 0) {
 		DEBUG(DEBUG_INFO,
 		      (__location__
@@ -850,7 +1148,12 @@ static int ctdb_process_delete_list(struct ctdb_db_context *ctdb_db,
 		       (unsigned)vdata->delete_left));
 	}
 
-	return 0;
+	ret = 0;
+
+done:
+	talloc_free(tmp_ctx);
+
+	return ret;
 }
 
 /**
diff --git a/server/ctdbd.c b/server/ctdbd.c
index ad1baac..b8768f1 100644
--- a/server/ctdbd.c
+++ b/server/ctdbd.c
@@ -33,7 +33,6 @@ static struct {
 	const char *public_address_list;
 	const char *event_script_dir;
 	const char *notification_script;
-	const char *debug_hung_script;
 	const char *logfile;
 	const char *recovery_lock_file;
 	const char *db_dir;
@@ -61,7 +60,6 @@ static struct {
 	.db_dir_persistent = VARDIR "/ctdb/persistent",
 	.db_dir_state = VARDIR "/ctdb/state",
 	.script_log_level = DEBUG_ERR,
-	.debug_hung_script = ETCDIR "/ctdb/debug-hung-script.sh",
 };
 
 int script_log_level;
@@ -126,13 +124,13 @@ int main(int argc, const char *argv[])
 		{ "logfile", 0, POPT_ARG_STRING, &options.logfile, 0, "log file location", "filename" },
 		{ "nlist", 0, POPT_ARG_STRING, &options.nlist, 0, "node list file", "filename" },
 		{ "notification-script", 0, POPT_ARG_STRING, &options.notification_script, 0, "notification script", "filename" },
-		{ "debug-hung-script", 0, POPT_ARG_STRING, &options.debug_hung_script, 0, "debug script for hung eventscripts", "filename" },
 		{ "listen", 0, POPT_ARG_STRING, &options.myaddress, 0, "address to listen on", "address" },
 		{ "transport", 0, POPT_ARG_STRING, &options.transport, 0, "protocol transport", NULL },
 		{ "dbdir", 0, POPT_ARG_STRING, &options.db_dir, 0, "directory for the tdb files", NULL },
 		{ "dbdir-persistent", 0, POPT_ARG_STRING, &options.db_dir_persistent, 0, "directory for persistent tdb files", NULL },
 		{ "dbdir-state", 0, POPT_ARG_STRING, &options.db_dir_state, 0, "directory for internal state tdb files", NULL },
 		{ "reclock", 0, POPT_ARG_STRING, &options.recovery_lock_file, 0, "location of recovery lock file", "filename" },
+		{ "pidfile", 0, POPT_ARG_STRING, &ctdbd_pidfile, 0, "location of PID file", "filename" },
 		{ "valgrinding", 0, POPT_ARG_NONE, &options.valgrinding, 0, "disable setscheduler SCHED_FIFO call, use mmap for tdbs", NULL },
 		{ "nosetsched", 0, POPT_ARG_NONE, &options.nosetsched, 0, "disable setscheduler SCHED_FIFO call, use mmap for tdbs", NULL },
 		{ "syslog", 0, POPT_ARG_NONE, &options.use_syslog, 0, "log messages to syslog", NULL },
@@ -310,14 +308,6 @@ int main(int argc, const char *argv[])
 		}
 	}
 
-	if (options.debug_hung_script != NULL) {
-		ret = ctdb_set_debug_hung_script(ctdb, options.debug_hung_script);
-	}
-	if (ret == -1) {
-		DEBUG(DEBUG_ALERT,("Unable to setup script to debug hung eventscripts\n"));
-		exit(1);
-	}
-
 	ctdb->valgrinding = options.valgrinding;
 	if (options.valgrinding || options.nosetsched) {
 		ctdb->do_setsched = 0;
diff --git a/server/eventscript.c b/server/eventscript.c
index 762f950..5c448c7 100644
--- a/server/eventscript.c
+++ b/server/eventscript.c
@@ -503,21 +503,12 @@ static void ctdb_event_script_handler(struct event_context *ev, struct fd_event
 	}
 }
 
-/*
-  setup the script to debug hung eventscripts
-*/
-int ctdb_set_debug_hung_script(struct ctdb_context *ctdb, const char *script)
-{
-	ctdb->debug_hung_script = talloc_strdup(ctdb, script);
-	CTDB_NO_MEMORY(ctdb, ctdb->debug_hung_script);
-	return 0;
-}
-
 static void ctdb_run_debug_hung_script(struct ctdb_context *ctdb, struct ctdb_event_script_state *state)
 {
 	struct ctdb_script_wire *current = get_current_script(state);
 	char *cmd;
 	pid_t pid;
+	const char * debug_hung_script = ETCDIR "/ctdb/debug-hung-script.sh";
 
 	cmd = child_command_string(ctdb, state,
 				   state->from_user, current->name,
@@ -528,9 +519,7 @@ static void ctdb_run_debug_hung_script(struct ctdb_context *ctdb, struct ctdb_ev
 			 cmd, timeval_elapsed(&current->start), state->child));
 	talloc_free(cmd);
 
-	talloc_free(ctdb->debug_hung_script_ctx);
-	ctdb->debug_hung_script_ctx = talloc_new(ctdb);
- 	if (!ctdb_fork_with_logging(ctdb->debug_hung_script_ctx, ctdb, "Hung script", NULL, NULL, &pid)) {
+	if (!ctdb_fork_with_logging(ctdb, ctdb, "Hung script", NULL, NULL, &pid)) {
 		DEBUG(DEBUG_ERR,("Failed to fork a child process with logging to track hung event script\n"));
 		ctdb_kill(state->ctdb, state->child, SIGTERM);
 		return;
@@ -542,22 +531,16 @@ static void ctdb_run_debug_hung_script(struct ctdb_context *ctdb, struct ctdb_ev
 		return;
 	}
 	if (pid == 0) {
-		struct stat st;
-		char buf[200];
-
-		if (stat(ctdb->debug_hung_script, &st) != 0) {
-			DEBUG(DEBUG_ERR,("Failed to stat the script to debug hung eventscript. Is it not installed correctly? (script:%s)\n", ctdb->debug_hung_script));
-			ctdb_kill(state->ctdb, state->child, SIGTERM);
-			_exit(0);
-		}		
-		if (!(st.st_mode & S_IXUSR)) {
-			DEBUG(DEBUG_DEBUG,("Debug script %s is not executable.\n", ctdb->debug_hung_script));
-			ctdb_kill(state->ctdb, state->child, SIGTERM);
-			_exit(0);
+		char *buf;
+
+		if (getenv("CTDB_DEBUG_HUNG_SCRIPT") != NULL) {
+			debug_hung_script = getenv("CTDB_DEBUG_HUNG_SCRIPT");
 		}
 
-		sprintf(buf, "%s %d", ctdb->debug_hung_script, state->child);
+		buf = talloc_asprintf(NULL, "%s %d",
+				      debug_hung_script, state->child);
 		system(buf);
+		talloc_free(buf);
 
 		/* Now we can kill the child */
 		ctdb_kill(state->ctdb, state->child, SIGTERM);
@@ -585,7 +568,6 @@ static void ctdb_event_script_timeout(struct event_context *ev, struct timed_eve
 	case CTDB_EVENT_RECOVERED:
 	case CTDB_EVENT_TAKE_IP:
 	case CTDB_EVENT_RELEASE_IP:
-	case CTDB_EVENT_STOPPED:
 	case CTDB_EVENT_STATUS:
 		state->scripts->scripts[state->current].status = 0;
 		DEBUG(DEBUG_ERR,("Ignoring hung script for %s call %d\n", state->options, state->call));
@@ -683,7 +665,6 @@ static bool check_options(enum ctdb_eventscript_call call, const char *options)
 	case CTDB_EVENT_STARTUP:
 	case CTDB_EVENT_START_RECOVERY:
 	case CTDB_EVENT_RECOVERED:
-	case CTDB_EVENT_STOPPED:
 	case CTDB_EVENT_MONITOR:
 	case CTDB_EVENT_STATUS:
 	case CTDB_EVENT_SHUTDOWN:
@@ -724,36 +705,6 @@ static int ctdb_event_script_callback_v(struct ctdb_context *ctdb,
 {
 	struct ctdb_event_script_state *state;
 
-	state = talloc(ctdb->event_script_ctx, struct ctdb_event_script_state);
-	CTDB_NO_MEMORY(ctdb, state);
-
-	/* The callback isn't done if the context is freed. */
-	state->callback = talloc(mem_ctx, struct event_script_callback);
-	CTDB_NO_MEMORY(ctdb, state->callback);
-	DLIST_ADD(ctdb->script_callbacks, state->callback);
-	talloc_set_destructor(state->callback, remove_callback);
-	state->callback->ctdb         = ctdb;
-	state->callback->fn           = callback;
-	state->callback->private_data = private_data;
-
-	state->ctdb = ctdb;
-	state->from_user = from_user;
-	state->call = call;
-	state->options = talloc_vasprintf(state, fmt, ap);
-	state->timeout = timeval_set(ctdb->tunable.script_timeout, 0);
-	state->scripts = NULL;
-	if (state->options == NULL) {
-		DEBUG(DEBUG_ERR, (__location__ " could not allocate state->options\n"));
-		talloc_free(state);
-		return -1;
-	}
-	if (!check_options(state->call, state->options)) {
-		DEBUG(DEBUG_ERR, ("Bad eventscript options '%s' for %s\n",
-				  ctdb_eventscript_call_names[state->call], state->options));
-		talloc_free(state);
-		return -1;
-	}
-
 	if (ctdb->recovery_mode != CTDB_RECOVERY_NORMAL) {
 		/* we guarantee that only some specifically allowed event scripts are run
 		   while in recovery */
@@ -763,7 +714,7 @@ static int ctdb_event_script_callback_v(struct ctdb_context *ctdb,
 			CTDB_EVENT_START_RECOVERY,
 			CTDB_EVENT_SHUTDOWN,
 			CTDB_EVENT_RELEASE_IP,
-			CTDB_EVENT_STOPPED
+			CTDB_EVENT_IPREALLOCATED,
 		};
 		int i;
 		for (i=0;i<ARRAY_SIZE(allowed_calls);i++) {
@@ -772,7 +723,6 @@ static int ctdb_event_script_callback_v(struct ctdb_context *ctdb,
 		if (i == ARRAY_SIZE(allowed_calls)) {
 			DEBUG(DEBUG_ERR,("Refusing to run event scripts call '%s' while in recovery\n",
 				 ctdb_eventscript_call_names[call]));
-			talloc_free(state);
 			return -1;
 		}
 	}
@@ -795,6 +745,36 @@ static int ctdb_event_script_callback_v(struct ctdb_context *ctdb,
 		ctdb->current_monitor = NULL;
 	}
 
+	state = talloc(ctdb->event_script_ctx, struct ctdb_event_script_state);
+	CTDB_NO_MEMORY(ctdb, state);
+
+	/* The callback isn't done if the context is freed. */
+	state->callback = talloc(mem_ctx, struct event_script_callback);
+	CTDB_NO_MEMORY(ctdb, state->callback);
+	DLIST_ADD(ctdb->script_callbacks, state->callback);
+	talloc_set_destructor(state->callback, remove_callback);
+	state->callback->ctdb         = ctdb;
+	state->callback->fn           = callback;
+	state->callback->private_data = private_data;
+
+	state->ctdb = ctdb;
+	state->from_user = from_user;
+	state->call = call;
+	state->options = talloc_vasprintf(state, fmt, ap);
+	state->timeout = timeval_set(ctdb->tunable.script_timeout, 0);
+	state->scripts = NULL;
+	if (state->options == NULL) {
+		DEBUG(DEBUG_ERR, (__location__ " could not allocate state->options\n"));
+		talloc_free(state);
+		return -1;
+	}
+	if (!check_options(state->call, state->options)) {
+		DEBUG(DEBUG_ERR, ("Bad eventscript options '%s' for %s\n",
+				  ctdb_eventscript_call_names[state->call], state->options));
+		talloc_free(state);
+		return -1;
+	}
+
 	DEBUG(DEBUG_INFO,(__location__ " Starting eventscript %s %s\n",
 			  ctdb_eventscript_call_names[state->call],
 			  state->options));
diff --git a/tests/INSTALL b/tests/INSTALL
index 8c3f777..5581989 100755
--- a/tests/INSTALL
+++ b/tests/INSTALL
@@ -71,7 +71,7 @@ for d in $data_subdirs ; do
 done
 # Some of the unit tests have relative symlinks back to in-tree bits
 # and pieces.  These links will be broken!
-for i in "events.d" "functions" ; do
+for i in "events.d" "functions" "nfs-rpc-checks.d" ; do
     ln -sf "${etcdir}/ctdb/${i}" "${ctdb_datadir}/eventscripts/etc-ctdb/${i}"
 done
 # test_wrap needs to set TEST_BIN_DIR
diff --git a/tests/eventscripts/13.per_ip_routing.016.sh b/tests/eventscripts/13.per_ip_routing.016.sh
index 485353e..85320b6 100755
--- a/tests/eventscripts/13.per_ip_routing.016.sh
+++ b/tests/eventscripts/13.per_ip_routing.016.sh
@@ -9,7 +9,7 @@ setup_ctdb_policy_routing
 
 create_policy_routing_config 0
 
-ok 'Reconfiguring service "13.per_ip_routing"...'
+ok "Reconfiguring service \"${service_name}\"..."
 simple_test_event "reconfigure"
 
 check_routes 0
diff --git a/tests/eventscripts/13.per_ip_routing.017.sh b/tests/eventscripts/13.per_ip_routing.017.sh
index dcb436a..8870015 100755
--- a/tests/eventscripts/13.per_ip_routing.017.sh
+++ b/tests/eventscripts/13.per_ip_routing.017.sh
@@ -10,7 +10,7 @@ setup_ctdb_policy_routing
 create_policy_routing_config 1 default
 
 # no takeip, but reconfigure should add any missing routes
-ok 'Reconfiguring service "13.per_ip_routing"...'
+ok "Reconfiguring service \"${service_name}\"..."
 simple_test_event "reconfigure"
 
 check_routes 1 default
diff --git a/tests/eventscripts/13.per_ip_routing.018.sh b/tests/eventscripts/13.per_ip_routing.018.sh
index 7a02b0c..ce91989 100755
--- a/tests/eventscripts/13.per_ip_routing.018.sh
+++ b/tests/eventscripts/13.per_ip_routing.018.sh
@@ -16,7 +16,7 @@ simple_test_event "ipreallocated"
 create_policy_routing_config 1 default
 
 # reconfigure should update routes even though rules are unchanged
-ok 'Reconfiguring service "13.per_ip_routing"...'
+ok "Reconfiguring service \"${service_name}\"..."
 simple_test_event "reconfigure"
 
 check_routes 1 default
diff --git a/tests/eventscripts/13.per_ip_routing.019.sh b/tests/eventscripts/13.per_ip_routing.019.sh
index 2afee08..072c929 100755
--- a/tests/eventscripts/13.per_ip_routing.019.sh
+++ b/tests/eventscripts/13.per_ip_routing.019.sh
@@ -18,7 +18,7 @@ simple_test_event "ipreallocated"
 create_policy_routing_config 1
 
 # reconfigure should update routes even though rules are unchanged
-ok 'Reconfiguring service "13.per_ip_routing"...'
+ok "Reconfiguring service \""${service_name}\""..."
 simple_test_event "reconfigure"
 
 check_routes 1
diff --git a/tests/eventscripts/49.winbind.monitor.102.sh b/tests/eventscripts/49.winbind.monitor.102.sh
index 77e2a32..e4a4cac 100755
--- a/tests/eventscripts/49.winbind.monitor.102.sh
+++ b/tests/eventscripts/49.winbind.monitor.102.sh
@@ -7,6 +7,6 @@ define_test "winbind down"
 setup_winbind
 wbinfo_down
 
-required_result 1 "ERROR: winbind - wbinfo -p returned error"
+required_result 1 "ERROR: wbinfo -p returned error"
 
 simple_test
diff --git a/tests/eventscripts/50.samba.monitor.107.sh b/tests/eventscripts/50.samba.monitor.107.sh
index 4c776ac..573ff80 100755
--- a/tests/eventscripts/50.samba.monitor.107.sh
+++ b/tests/eventscripts/50.samba.monitor.107.sh
@@ -4,8 +4,7 @@
 
 define_test "port 139 down, default tcp checker, debug"
 
-# This has to go before the setup, otherwise it will write a dud file.
-export CTDB_DEBUGLEVEL=4
+export CTDB_SCRIPT_DEBUGLEVEL=4
 
 setup_samba
 tcp_port_down 139
diff --git a/tests/eventscripts/50.samba.monitor.109.sh b/tests/eventscripts/50.samba.monitor.109.sh
index f90ba62..0104fd9 100755
--- a/tests/eventscripts/50.samba.monitor.109.sh
+++ b/tests/eventscripts/50.samba.monitor.109.sh
@@ -6,8 +6,7 @@ define_test "port 139 down, ctdb checktcpport not implemented, debug"
 
 ctdb_not_implemented "checktcpport"
 
-# This has to go before the setup, otherwise it will write a dud file.
-export CTDB_DEBUGLEVEL=4
+export CTDB_SCRIPT_DEBUGLEVEL=4
 
 setup_nmap_output_filter
 
diff --git a/tests/eventscripts/50.samba.monitor.110.sh b/tests/eventscripts/50.samba.monitor.110.sh
index 639cc51..4697e54 100755
--- a/tests/eventscripts/50.samba.monitor.110.sh
+++ b/tests/eventscripts/50.samba.monitor.110.sh
@@ -7,8 +7,7 @@ define_test "port 139 down, ctdb checktcpport/nmap not implemented, debug"
 ctdb_not_implemented "checktcpport"
 export FAKE_NMAP_NOT_FOUND="yes"
 
-# This has to go before the setup, otherwise it will write a dud file.
-export CTDB_DEBUGLEVEL=4
+export CTDB_SCRIPT_DEBUGLEVEL=4
 
 setup_nmap_output_filter
 
diff --git a/tests/eventscripts/60.nfs.monitor.100.sh b/tests/eventscripts/60.nfs.monitor.100.sh
deleted file mode 100755
index e846d82..0000000
--- a/tests/eventscripts/60.nfs.monitor.100.sh
+++ /dev/null
@@ -1,19 +0,0 @@
-#!/bin/sh
-
-. "${TEST_SCRIPTS_DIR}/unit.sh"
-
-define_test "get RPC service fail limits/actions"
-
-setup_nfs
-
-set -e
-
-rm -f "$rpc_fail_limits_file"
-CTDB_RC_LOCAL="$CTDB_BASE/rc.local.nfs.monitor.get-limits" \
-    "${CTDB_BASE}/events.d/60.nfs" "monitor" >"$rpc_fail_limits_file"
-
-services="knfsd|mountd|rquotad|lockd|statd"
-
-echo "Doing rough check of file format..."
-
-! grep -v -E "^(${services}) " "$rpc_fail_limits_file"
diff --git a/tests/eventscripts/60.nfs.monitor.112.sh b/tests/eventscripts/60.nfs.monitor.112.sh
index 666a38a..c5c39b2 100755
--- a/tests/eventscripts/60.nfs.monitor.112.sh
+++ b/tests/eventscripts/60.nfs.monitor.112.sh
@@ -10,6 +10,6 @@ setup_nfs
 rpc_services_down "nfs"
 
 iterate_test 6 'ok_null' \
-    2 'rpc_set_service_failure_response "knfsd"' \
-    4 'rpc_set_service_failure_response "knfsd"' \
-    6 'rpc_set_service_failure_response "knfsd"'
+    2 'rpc_set_service_failure_response "nfsd"' \
+    4 'rpc_set_service_failure_response "nfsd"' \
+    6 'rpc_set_service_failure_response "nfsd"'
diff --git a/tests/eventscripts/etc-ctdb/nfs-rpc-checks.d b/tests/eventscripts/etc-ctdb/nfs-rpc-checks.d
new file mode 120000
index 0000000..991b966
--- /dev/null
+++ b/tests/eventscripts/etc-ctdb/nfs-rpc-checks.d
@@ -0,0 +1 @@
+../../../config/nfs-rpc-checks.d
\ No newline at end of file
diff --git a/tests/eventscripts/etc-ctdb/rc.local.nfs.monitor.get-limits b/tests/eventscripts/etc-ctdb/rc.local.nfs.monitor.get-limits
deleted file mode 100755
index 96e4cff..0000000
--- a/tests/eventscripts/etc-ctdb/rc.local.nfs.monitor.get-limits
+++ /dev/null
@@ -1,25 +0,0 @@
-# Hey Emacs, this is a -*- shell-script -*- !!!  :-)
-
-# This scripts nobble the 60.nfs monitor event so that it prints out
-# the service fail limits for each RPC service.
-
-CTDB_INIT_STYLE="redhat"
-PATH="${EVENTSCRIPTS_PATH}:$PATH"
-
-service () { : ; }
-
-update_tickles () { : ; }
-
-ctdb_setup_service_state_dir "nfs"
-
-CTDB_NFS_SKIP_KNFSD_ALIVE_CHECK="no"
-CTDB_NFS_SKIP_SHARE_CHECK="yes"
-
-# Ugly but necessary - if this file was touched less then 60 seconds
-# ago then this skips some code.
-touch "$service_state_dir/update-trigger"
-
-nfs_check_rpc_service ()
-{
-    echo "$*"
-}
diff --git a/tests/eventscripts/scripts/local.sh b/tests/eventscripts/scripts/local.sh
index 9e746b5..3f55830 100644
--- a/tests/eventscripts/scripts/local.sh
+++ b/tests/eventscripts/scripts/local.sh
@@ -368,6 +368,8 @@ ctdb_fake_scriptstatus ()
 
 setup_ctdb_policy_routing ()
 {
+    service_name="per_ip_routing"
+
     export CTDB_PER_IP_ROUTING_CONF="$CTDB_BASE/policy_routing"
     export CTDB_PER_IP_ROUTING_RULE_PREF=100
     export CTDB_PER_IP_ROUTING_TABLE_ID_LOW=1000
@@ -455,11 +457,13 @@ setup_samba ()
 {
     setup_ctdb
 
+    service_name="samba"
+
     if [ "$1" != "down" ] ; then
 
 	debug "Marking Samba services as up, listening and managed by CTDB"
         # Get into known state.
-	eventscript_call ctdb_service_managed "samba"
+	eventscript_call ctdb_service_managed
 
         # All possible service names for all known distros.
 	for i in "smb" "nmb" "samba" ; do
@@ -479,7 +483,7 @@ setup_samba ()
     else
 	debug "Marking Samba services as down, not listening and not managed by CTDB"
         # Get into known state.
-	eventscript_call ctdb_service_unmanaged "samba"
+	eventscript_call ctdb_service_unmanaged
 
         # All possible service names for all known distros.
 	for i in "smb" "nmb" "samba" ; do
@@ -503,11 +507,13 @@ setup_winbind ()
 {
     setup_ctdb
 
+    service_name="winbind"
+
     if [ "$1" != "down" ] ; then
 
 	debug "Marking Winbind service as up and managed by CTDB"
         # Get into known state.
-	eventscript_call ctdb_service_managed "winbind"
+	eventscript_call ctdb_service_managed
 
 	service "winbind" force-started
 
@@ -518,7 +524,7 @@ setup_winbind ()
     else
 	debug "Marking Winbind service as down and not managed by CTDB"
         # Get into known state.
-	eventscript_call ctdb_service_unmanaged "winbind"
+	eventscript_call ctdb_service_unmanaged
 
 	service "winbind" force-stopped
 
@@ -543,30 +549,19 @@ setup_nfs ()
 {
     setup_ctdb
 
+    service_name="nfs"
+
     export FAKE_RPCINFO_SERVICES=""
 
     export CTDB_NFS_SKIP_SHARE_CHECK="no"
-    export CTDB_NFS_SKIP_KNFSD_ALIVE_CHECK="no"
 
     # Reset the failcounts for nfs services.
     eventscript_call eval rm -f '$ctdb_fail_dir/nfs_*'
 
-    rpc_fail_limits_file="${EVENTSCRIPTS_TESTS_VAR_DIR}/rpc_fail_limits"
-
-    # Force this file to exist so tests can be individually run.
-    if [ ! -f "$rpc_fail_limits_file" ] ; then
-	# This is gross... but is needed to fake through the nfs monitor event.
-	eventscript_call ctdb_service_managed "nfs"
-	service "nfs" force-started  # might not be enough
-	CTDB_RC_LOCAL="$CTDB_BASE/rc.local.nfs.monitor.get-limits" \
-	    CTDB_MANAGES_NFS="yes" \
-	    "${CTDB_BASE}/events.d/60.nfs" "monitor" >"$rpc_fail_limits_file"
-    fi
-    
     if [ "$1" != "down" ] ; then
 	debug "Setting up NFS environment: all RPC services up, NFS managed by CTDB"
 
-	eventscript_call ctdb_service_managed "nfs"
+	eventscript_call ctdb_service_managed
 	service "nfs" force-started  # might not be enough
 
 	export CTDB_MANAGED_SERVICES="foo nfs bar"
@@ -575,7 +570,7 @@ setup_nfs ()
     else
 	debug "Setting up NFS environment: all RPC services down, NFS not managed by CTDB"
 
-	eventscript_call ctdb_service_unmanaged "nfs"
+	eventscript_call ctdb_service_unmanaged
 	service "nfs" force-stopped  # might not be enough
 	eventscript_call startstop_nfs stop
 
@@ -640,31 +635,14 @@ rpc_set_service_failure_response ()
     # Default
     ok_null
 
-    _ts=$(sed -n -e "s@^${_progname} @@p" "$rpc_fail_limits_file")
-
-    while [ -n "$_ts" ] ; do
-	# Get the triple: operator, fail limit and actions.
-	_op="${_ts%% *}" ; _ts="${_ts#* }"
-	_li="${_ts%% *}" ; _ts="${_ts#* }"
-	# We've lost some of the quoting but we can simulate
-	# because we know an operator is always the first in a
-	# triple.
-  	_actions=""
-	while [ -n "$_ts" ] ; do
-	    # If this is an operator then we've got all of the
-	    # actions.
-	    case "$_ts" in
-		-*) break ;;
-	    esac
-
-	    _actions="${_actions}${_actions:+ }${_ts%% *}"
-	    # Special case for end of list.
-	    if [ "$_ts" != "${_ts#* }" ] ; then
-		_ts="${_ts#* }"
-	    else
-		_ts=""
-	    fi
-	done
+    _file=$(ls "${CTDB_BASE}/nfs-rpc-checks.d/"[0-9][0-9]."${_progname}.check")
+    [ -r "$_file" ] || die "RPC check file \"$_file\" does not exist or is not unique"
+
+    while read _op _li _actions ; do
+	# Skip comments
+	case "$_op" in
+	    \#*) continue ;;
+	esac
 
 	if [ "$_numfails" "$_op" "$_li" ] ; then
 	    _out=""
@@ -675,7 +653,7 @@ rpc_set_service_failure_response ()
 			_ver=1
 			_pn="$_progname"
 			case "$_progname" in
-			    knfsd) _ver=3 ; _pn="nfs" ;;
+			    nfsd) _ver=3 ; _pn="nfs" ;;
 			    lockd) _ver=4 ; _pn="nlockmgr" ;;
 			    statd) _pn="status" ;;
 			esac
@@ -693,13 +671,13 @@ program $_pn version $_ver is not available"
 				;;
 			esac
 			case "${_progname}${_action#restart}" in
-			    knfsd)
+			    nfsd)
 				_t="\
 Trying to restart NFS service
 Starting nfslock: OK
 Starting nfs: OK"
 				;;
-			    knfsd:bs)
+			    nfsd:bs)
 				_t="Trying to restart NFS service"
 				;;
 			    lockd|lockd:b)
@@ -723,7 +701,7 @@ Starting nfslock: OK"
 	    required_result $_rc "$_out"
 	    return
 	fi
-    done
+    done <"$_file"
 }
 
 ######################################################################
@@ -732,12 +710,14 @@ Starting nfslock: OK"
 
 setup_vsftpd ()
 {
+    service_name="vsftpd"
+
     if [ "$1" != "down" ] ; then
 	die "setup_vsftpd up not implemented!!!"
     else
 	debug "Setting up VSFTPD environment: service down, not managed by CTDB"
 
-	eventscript_call ctdb_service_unmanaged vsftpd
+	eventscript_call ctdb_service_unmanaged
 	service vsftpd force-stopped
 
 	export CTDB_MANAGED_SERVICES="foo"
@@ -756,9 +736,9 @@ setup_httpd ()
     else
 	debug "Setting up HTTPD environment: service down, not managed by CTDB"
 
-	for i in "apache2" "httpd" ; do
-	    eventscript_call ctdb_service_unmanaged "$i"
-	    service "$i" force-stopped
+	for service_name in "apache2" "httpd" ; do
+	    eventscript_call ctdb_service_unmanaged
+	    service "$service_name" force-stopped
 	done
 
 	export CTDB_MANAGED_SERVICES="foo"
diff --git a/tests/eventscripts/stubs/ctdb b/tests/eventscripts/stubs/ctdb
index 3abdd16..34ac47e 100755
--- a/tests/eventscripts/stubs/ctdb
+++ b/tests/eventscripts/stubs/ctdb
@@ -274,24 +274,6 @@ case "$1" in
 		exit 1
 	esac
 	;;
-    getdebug)
-	case "${CTDB_DEBUGLEVEL:-0}" in
-	    -3) _t="EMERG"  ;;
-	    -2) _t="ALERT"  ;;
-	    -1) _t="CRIT"   ;;
-	    0) _t="ERR"     ;;
-	    1) _t="WARNING" ;;
-	    2) _t="NOTICE"  ;;
-	    3) _t="INFO"    ;;
-	    4) _t="DEBUG"   ;;
-	    *) _t="ERR"     ;;
-	esac
-
-	cat<<EOF
-:Name:Level:
-:${_t}:${CTDB_DEBUGLEVEL}:
-EOF
-	;;
     checktcpport)
 	for _i in $FAKE_TCP_LISTEN ; do
 	    if [ "$2" = "${_i##*:}" ] ; then
diff --git a/tests/scripts/integration.bash b/tests/scripts/integration.bash
index 2e5fb37..45e0b99 100644
--- a/tests/scripts/integration.bash
+++ b/tests/scripts/integration.bash
@@ -14,6 +14,7 @@ if [ -n "$TEST_LOCAL_DAEMONS" ] ; then
     # Otherwise CTDB need to be installed on all nodes.
     if [ -n "$ctdb_dir" -a -d "${ctdb_dir}/bin" ] ; then
 	PATH="${ctdb_dir}/bin:${PATH}"
+        export CTDB_LOCK_HELPER="${ctdb_dir}/bin/ctdb_lock_helper"
     fi
 
     export CTDB_NODES="${TEST_VAR_DIR}/nodes.txt"
@@ -370,7 +371,7 @@ node_has_status ()
     local pnn="$1"
     local status="$2"
 
-    local bits fpat mpat
+    local bits fpat mpat rpat
     case "$status" in
 	(unhealthy)    bits="?:?:?:1:*" ;;
 	(healthy)      bits="?:?:?:0:*" ;;
@@ -386,6 +387,7 @@ node_has_status ()
 	(unfrozen)     fpat='^[[:space:]]+frozen[[:space:]]+0$' ;;
 	(monon)        mpat='^Monitoring mode:ACTIVE \(0\)$' ;;
 	(monoff)       mpat='^Monitoring mode:DISABLED \(1\)$' ;;
+	(recovered)    rpat='^Recovery mode:NORMAL \(0\)$' ;;
 	*)
 	    echo "node_has_status: unknown status \"$status\""
 	    return 1
@@ -410,6 +412,8 @@ node_has_status ()
 	$CTDB statistics -n "$pnn" | egrep -q "$fpat"
     elif [ -n "$mpat" ] ; then
 	$CTDB getmonmode -n "$pnn" | egrep -q "$mpat"
+    elif [ -n "$rpat" ] ; then
+        $CTDB status -n "$pnn" | egrep -q "$rpat"
     else
 	echo 'node_has_status: unknown mode, neither $bits nor $fpat is set'
 	return 1
@@ -570,8 +574,8 @@ daemons_setup ()
 	    echo 127.0.0.$i >>"$CTDB_NODES"
 	    # 2 public addresses on most nodes, just to make things interesting.
 	    if [ $(($i - 1)) -ne $no_public_ips ] ; then
-		echo "192.0.2.$i/24 lo" >>"$public_addresses_all"
-		echo "192.0.2.$(($i + $TEST_LOCAL_DAEMONS))/24 lo" >>"$public_addresses_all"
+		echo "192.168.234.$i/24 lo" >>"$public_addresses_all"
+		echo "192.168.234.$(($i + $TEST_LOCAL_DAEMONS))/24 lo" >>"$public_addresses_all"
 	    fi
 	fi
     done
@@ -736,8 +740,6 @@ restart_ctdb ()
 	    continue
 	}
 
-	local debug_out=$(onnode -p all ctdb status -Y 2>&1; onnode -p all ctdb scriptstatus 2>&1)
-
 	echo "Setting RerecoveryTimeout to 1"
 	onnode -pq all "$CTDB setvar RerecoveryTimeout 1"
 
@@ -752,7 +754,10 @@ restart_ctdb ()
 
 	# Cluster is still healthy.  Good, we're done!
 	if ! onnode 0 $CTDB_TEST_WRAPPER _cluster_is_healthy ; then
-	    echo "Cluster become UNHEALTHY again.  Restarting..."
+	    echo "Cluster became UNHEALTHY again [$(date)]"
+	    onnode -p all ctdb status -Y 2>&1
+	    onnode -p all ctdb scriptstatus 2>&1
+	    echo "Restarting..."
 	    continue
 	fi
 
@@ -764,7 +769,9 @@ restart_ctdb ()
     done
 
     echo "Cluster UNHEALTHY...  too many attempts..."
-    echo "$debug_out"
+    onnode -p all ctdb status -Y 2>&1
+    onnode -p all ctdb scriptstatus 2>&1
+
     # Try to make the calling test fail
     status=1
     return 1
diff --git a/tests/scripts/run_tests b/tests/scripts/run_tests
index 50a578b..a3af5cb 100755
--- a/tests/scripts/run_tests
+++ b/tests/scripts/run_tests
@@ -8,8 +8,8 @@ Options:
   -s		Print a summary of tests results after running all tests
   -l		Use local daemons for integration tests
   -e		Exit on the first test failure
-  -V <dir>	Use <dir> as $TEST_VAR_DIR
-  -C		Clean up - kill daemons and remove $TEST_VAR_DIR when done
+  -V <dir>	Use <dir> as TEST_VAR_DIR
+  -C		Clean up - kill daemons and remove TEST_VAR_DIR when done
   -v		Verbose - print test output for non-failures (only some tests)
   -A		Use "cat -A" to print test output (only some tests)
   -D		Show diff between failed/expected test output (some tests only)
@@ -140,8 +140,26 @@ tests_passed=0
 tests_failed=0
 summary=""
 
-rows=$(if tty -s ; then stty size ; else echo x 80 ; fi | sed -e 's at .* @@' -e 's@^0$@80@')
-ww=$((rows - 7))
+if ! which mktemp >/dev/null 2>&1 ; then
+    # Not perfect, but it will do...
+    mktemp ()
+    {
+	_dir=false
+	if [ "$1" = "-d" ] ; then
+	    _dir=true
+	fi
+	_t="${TMPDIR:-/tmp}/tmp.$$.$RANDOM"
+	(
+	    umask 077
+	    if $_dir ; then
+		mkdir "$_t"
+	    else
+		>"$_t"
+	    fi
+	)
+	echo "$_t"
+    }
+fi
 
 tf=$(mktemp)
 sf=$(mktemp)
diff --git a/tests/scripts/unit.sh b/tests/scripts/unit.sh
index b27df45..c7c2b7a 100644
--- a/tests/scripts/unit.sh
+++ b/tests/scripts/unit.sh
@@ -75,7 +75,7 @@ EOF
 	    echo "$required_output" >"$_outr"
 
 	    _outf=$(mktemp)
-	    echo "$_out" >"$_outf"
+	    echo "$_fout" >"$_outf"
 
 	    cat <<EOF
 --------------------------------------------------
diff --git a/tests/simple/76_ctdb_pdb_recovery.sh b/tests/simple/76_ctdb_pdb_recovery.sh
index 2f21fdd..50f241e 100755
--- a/tests/simple/76_ctdb_pdb_recovery.sh
+++ b/tests/simple/76_ctdb_pdb_recovery.sh
@@ -86,7 +86,7 @@ wait_until_node_has_status 1 notstopped
 #
 TESTDB="persistent_test.tdb"
 
-stauts=0
+status=0
 
 # Create a temporary persistent database to test with
 echo "create persistent test database $TESTDB"
diff --git a/tests/simple/77_ctdb_db_recovery.sh b/tests/simple/77_ctdb_db_recovery.sh
new file mode 100755
index 0000000..00fa096
--- /dev/null
+++ b/tests/simple/77_ctdb_db_recovery.sh
@@ -0,0 +1,133 @@
+#!/bin/bash
+
+test_info()
+{
+    cat <<EOF
+Recovery can under certain circumstances lead to old record copies
+resurrecting: Recovery selects the newest record copy purely by RSN. At
+the end of the recovery, the recovery master is the dmaster for all
+records in all (non-persistent) databases. And the other nodes locally
+hold the complete copy of the databases. The bug is that the recovery
+process does not increment the RSN on the recovery master at the end of
+the recovery. Now clients acting directly on the Recovery master will
+directly change a record's content on the recmaster without migration
+and hence without RSN bump.  So a subsequent recovery can not tell that
+the recmaster's copy is newer than the copies on the other nodes, since
+their RSN is the same. Hence, if the recmaster is not node 0 (or more
+precisely not the active node with the lowest node number), the recovery
+will choose copies from nodes with lower number and stick to these.
+
+Steps:
+
+1. Create a test database
+2. Add a record with value value1 on recovery master
+3. Force a recovery
+4. Update the record with value value2 on recovery master
+5. Force a recovery
+6. Fetch the record
+
+Expected results:
+
+* The record should have value value2 and not value1
+
+EOF
+}
+
+. "${TEST_SCRIPTS_DIR}/integration.bash"
+
+ctdb_test_init "$@"
+
+set -e
+
+cluster_is_healthy
+
+# Reset configuration
+ctdb_restart_when_done
+
+#
+# Main test
+#
+TESTDB="rec_test.tdb"
+
+status=0
+
+# Make sure node 0 is not the recovery master
+echo "find out which node is recmaster"
+try_command_on_node -q any $CTDB_TEST_WRAPPER ctdb recmaster
+recmaster="$out"
+if [ "$recmaster" = "0" ]; then
+    echo "node 0 is recmaster, disable recmasterrole on node 0"
+    #
+    # Note:
+    # It should be sufficient to run "ctdb setrecmasterrole off"
+    # on node 0 and wait for election and recovery to finish.
+    # But there were problems related to this in this automatic
+    # test, so for now use "ctdb stop" and "ctdb continue".
+    #
+    echo "stop node 0"
+    try_command_on_node -q 0 $CTDB_TEST_WRAPPER ctdb stop
+    wait_until_node_has_status 0 stopped
+    echo "continue node 0"
+    try_command_on_node -q 0 $CTDB_TEST_WRAPPER ctdb continue
+    wait_until_node_has_status 0 notstopped
+
+    try_command_on_node -q any $CTDB_TEST_WRAPPER ctdb recmaster
+    recmaster="$out"
+    if [ "$recmaster" = "0" ]; then
+	echo "failed to move recmaster to different node"
+	exit 1
+    fi
+fi
+
+echo "Recmaster:$recmaster"
+
+# Create a temporary non-persistent database to test with
+echo "create test database $TESTDB"
+try_command_on_node -q $recmaster $CTDB_TEST_WRAPPER ctdb attach $TESTDB
+
+# Wipe Test database
+echo "wipe test database"
+try_command_on_node -q $recmaster $CTDB_TEST_WRAPPER ctdb wipedb $TESTDB
+
+# Add a record   key=test1 data=value1
+echo "store key(test1) data(value1)"
+try_command_on_node -q $recmaster $CTDB_TEST_WRAPPER ctdb writekey $TESTDB test1 value1
+
+# Fetch a record   key=test1
+echo "read key(test1)"
+try_command_on_node -q $recmaster $CTDB_TEST_WRAPPER ctdb readkey $TESTDB test1
+echo "$out"
+
+# Do a recovery
+echo "force recovery"
+try_command_on_node -q $recmaster $CTDB_TEST_WRAPPER ctdb recover
+
+wait_until_node_has_status $recmaster recovered
+
+# Add a record   key=test1 data=value2
+echo "store key(test1) data(value2)"
+try_command_on_node -q $recmaster $CTDB_TEST_WRAPPER ctdb writekey $TESTDB test1 value2
+
+# Fetch a record   key=test1
+echo "read key(test1)"
+try_command_on_node -q $recmaster $CTDB_TEST_WRAPPER ctdb readkey $TESTDB test1
+echo "$out"
+
+# Do a recovery
+echo "force recovery"
+try_command_on_node -q $recmaster $CTDB_TEST_WRAPPER ctdb recover
+
+wait_until_node_has_status $recmaster recovered
+
+# Verify record   key=test1
+echo "read key(test1)"
+try_command_on_node $recmaster $CTDB_TEST_WRAPPER ctdb readkey $TESTDB test1
+echo "$out"
+if [ "$out" = "Data: size:6 ptr:[value2]" ]; then
+	echo "GOOD: Recovery did not corrupt database"
+else
+	echo "BAD: Recovery corrupted database"
+	status=1
+fi
+
+exit $status
diff --git a/tests/src/ctdb_fetch_lock_once.c b/tests/src/ctdb_fetch_lock_once.c
index b273b44..f92b0b4 100644
--- a/tests/src/ctdb_fetch_lock_once.c
+++ b/tests/src/ctdb_fetch_lock_once.c
@@ -22,7 +22,6 @@
 #include "system/filesys.h"
 #include "popt.h"
 #include <poll.h>
-#include <err.h>
 #include "ctdb.h"
 
 #define TESTKEY "testkey"
@@ -78,7 +77,8 @@ static void fetch_lock_once(struct ctdb_connection *ctdb, struct ctdb_db *ctdb_d
 			exit(10);
 		}
 		if (ctdb_service(ctdb, pfd.revents) < 0) {
-			err(1, "Failed to service");
+			printf("Failed to service\n");
+			exit(10);
 		}
 	}
 }
@@ -120,8 +120,10 @@ int main(int argc, const char *argv[])
 
 	ctdb = ctdb_connect("/tmp/ctdb.socket",
 				       ctdb_log_file, stderr);
-	if (!ctdb)
-		err(1, "Connecting to /tmp/ctdb.socket");
+	if (!ctdb) {
+		printf("Connecting to /tmp/ctdb.socket\n");
+		exit(1);
+	}
 
 	/* attach to a specific database */
 	ctdb_db = ctdb_attachdb(ctdb, "test.tdb", false, 0);
diff --git a/tests/src/ctdb_fetch_readonly_loop.c b/tests/src/ctdb_fetch_readonly_loop.c
index 557954f..d3cc72c 100644
--- a/tests/src/ctdb_fetch_readonly_loop.c
+++ b/tests/src/ctdb_fetch_readonly_loop.c
@@ -18,9 +18,9 @@
    along with this program; if not, see <http://www.gnu.org/licenses/>.
 */
 
-#include <time.h>
 #include "includes.h"
 #include "system/filesys.h"
+#include "system/time.h"
 #include "popt.h"
 #include "cmdline.h"
 #include "ctdb_private.h"
diff --git a/tests/src/ctdb_porting_tests.c b/tests/src/ctdb_porting_tests.c
new file mode 100644
index 0000000..0c43451
--- /dev/null
+++ b/tests/src/ctdb_porting_tests.c
@@ -0,0 +1,305 @@
+/*
+   Test porting lib (common/system_*.c)
+
+   Copyright (C) Mathieu Parent 2013
+
+   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 3 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, see <http://www.gnu.org/licenses/>.
+*/
+
+#include "includes.h"
+#include "include/ctdb_private.h"
+#include "system/filesys.h"
+#include "popt.h"
+#include "cmdline.h"
+
+static struct {
+	const char *socketname;
+	const char *debuglevel;
+	pid_t helper_pid;
+	int socket;
+	int successcount;
+	int testcount;
+} globals = {
+	.socketname = "/tmp/test.sock"
+};
+
+
+
+/*
+  Socket functions
+*/
+/*
+  create a unix domain socket and bind it
+  return a file descriptor open on the socket
+*/
+static int socket_server_create(void)
+{
+	struct sockaddr_un addr;
+
+	globals.socket = socket(AF_UNIX, SOCK_STREAM, 0);
+	if (globals.socket == -1) {
+		DEBUG(DEBUG_CRIT,("Unable to create server socket: %s\n", strerror(errno)));
+		return -1;
+	}
+
+	set_close_on_exec(globals.socket);
+	//set_nonblocking(globals.socket);
+
+	memset(&addr, 0, sizeof(addr));
+	addr.sun_family = AF_UNIX;
+	strncpy(addr.sun_path, globals.socketname, sizeof(addr.sun_path));
+
+	if (bind(globals.socket, (struct sockaddr *)&addr, sizeof(addr)) == -1) {
+		DEBUG(DEBUG_CRIT,("Unable to bind on socket '%s': %s\n", globals.socketname, strerror(errno)));
+		goto failed;
+	}
+
+	if (chown(globals.socketname, geteuid(), getegid()) != 0 ||
+		chmod(globals.socketname, 0700) != 0) {
+		DEBUG(DEBUG_CRIT,("Unable to secure socket '%s': %s\n", globals.socketname, strerror(errno)));
+		goto failed;
+	}
+
+
+	if (listen(globals.socket, 100) != 0) {
+		DEBUG(DEBUG_CRIT,("Unable to listen on socket '%s': %s\n", globals.socketname, strerror(errno)));
+		goto failed;
+	}
+	return 0;
+
+failed:
+	close(globals.socket);
+	globals.socket = -1;
+	return -1;
+}
+
+static int socket_server_wait_peer(void)
+{
+	struct sockaddr_un addr;
+	socklen_t len;
+	int fd;
+
+	memset(&addr, 0, sizeof(addr));
+	len = sizeof(addr);
+	fd = accept(globals.socket, (struct sockaddr *)&addr, &len);
+	if (fd == -1) {
+		DEBUG(DEBUG_CRIT,("Unable to accept on ctdb socket '%s': %s\n", globals.socketname, strerror(errno)));
+		return -1;
+	}
+
+	//set_nonblocking(fd);
+	set_close_on_exec(fd);
+	return fd;
+}
+
+static int socket_server_close(void)
+{
+	if (close(globals.socket) == -1) {
+		DEBUG(DEBUG_CRIT,("Unable to close server socket: %s\n", strerror(errno)));
+		return -1;
+	}
+	if (unlink(globals.socketname) == -1) {
+		DEBUG(DEBUG_CRIT,("Unable to remove server socket: %s\n", strerror(errno)));
+		return -1;
+	}
+	return 0;
+}
+
+static int socket_client_connect(void)
+{
+	struct sockaddr_un addr;
+	int client = 0;
+
+	client = socket(AF_UNIX, SOCK_STREAM, 0);
+	if (client == -1) {
+		DEBUG(DEBUG_CRIT,("Unable to create client socket: %s\n", strerror(errno)));
+		return -1;
+	}
+
+	memset(&addr, 0, sizeof(addr));
+	addr.sun_family = AF_UNIX;
+	strncpy(addr.sun_path, globals.socketname, sizeof(addr.sun_path));
+	if (connect(client, (struct sockaddr *)&addr, sizeof(addr))==-1) {
+		DEBUG(DEBUG_CRIT,("Unable to connect to '%s': %s\n", globals.socketname, strerror(errno)));
+		close(client);
+		return -1;
+	}
+
+	return client;
+}
+
+static int socket_client_write(int client)
+{
+	if (write(client, "\0", 1) == -1) {
+		DEBUG(DEBUG_CRIT,("Unable to write to client socket: %s\n", strerror(errno)));
+		return -1;
+	}
+	return 0;
+}
+
+static int socket_client_close(int client)
+{
+	if (close(client) == -1) {
+		DEBUG(DEBUG_CRIT,("Unable to close client socket: %s\n", strerror(errno)));
+		return -1;
+	}
+	return 0;
+}
+
+/*
+  forked program
+*/
+static int fork_helper(void)
+{
+	pid_t pid;
+	int i, client, max_rounds = 10;
+
+	pid = fork();
+	if (pid == -1) {
+		DEBUG(DEBUG_CRIT,("Unable to fork: %s\n", strerror(errno)));
+		return -1;
+	}
+	if (pid == 0) { // Child
+		client = socket_client_connect();
+		socket_client_write(client);
+		for (i = 1 ; i <= max_rounds ; i++ ) {
+			DEBUG(DEBUG_DEBUG,("Child process waiting ( %d/%d)\n", i, max_rounds));
+			sleep(1);
+		}
+		socket_client_close(client);
+		exit(0);
+	} else {
+		globals.helper_pid = pid;
+	}
+	return 0;
+}
+
+/*
+  tests
+*/
+int test_ctdb_sys_check_iface_exists(void)
+{
+	const char *fakename;
+	bool test;
+	globals.testcount++;
+	fakename = strdup("fake");
+	if (fakename == NULL) {
+		DEBUG(DEBUG_CRIT,("Unable to allocate memory\n"));
+		return -1;
+	}
+	test = ctdb_sys_check_iface_exists(fakename);
+	if(test == true) {
+		DEBUG(DEBUG_CRIT,("Test failed: Fake interface detected: %s\n", fakename));
+		return -1;
+	}
+	DEBUG(DEBUG_INFO,("Test OK: Fake interface not detected: %s\n", fakename));
+	globals.successcount++;
+	return 0;
+}
+
+int test_ctdb_get_peer_pid(void)
+{
+	int ret;
+	int fd;
+	pid_t peer_pid = 0;
+	globals.testcount++;
+	fd = socket_server_wait_peer();
+	ret = ctdb_get_peer_pid(fd, &peer_pid);
+	if (ret == -1) {
+		DEBUG(DEBUG_CRIT,("Test failed: Unable to get peer process id\n"));
+		return -1;
+	}
+	if (peer_pid <= 0) {
+		DEBUG(DEBUG_CRIT,("Test failed: Invalid peer process id: %d\n", peer_pid));
+		return -1;
+	}
+	DEBUG(DEBUG_INFO,("Test OK: Peer process id: %d\n", peer_pid));
+	globals.successcount++;
+	return 0;
+}
+
+int test_ctdb_get_process_name(void)
+{
+	char *process_name = NULL;
+	globals.testcount++;
+	process_name = ctdb_get_process_name(globals.helper_pid);
+	if ((process_name == NULL) || !strcmp(process_name, "unknown")) {
+		DEBUG(DEBUG_CRIT,("Test failed: Invalid process name of %d: %s\n", globals.helper_pid, process_name));
+		return -1;
+	}
+	DEBUG(DEBUG_INFO,("Test OK: Name of PID=%d: %s\n", globals.helper_pid, process_name));
+	globals.successcount++;
+	return 0;
+}
+
+/*
+  main program
+*/
+int main(int argc, const char *argv[])
+{
+	struct poptOption popt_options[] = {
+		POPT_AUTOHELP
+		{ "socket", 0, POPT_ARG_STRING, &globals.socketname, 0, "local socket name", "filename" },
+		POPT_TABLEEND
+	};
+	int opt;
+	const char **extra_argv;
+	int extra_argc = 0;
+	poptContext pc;
+
+	LogLevel = DEBUG_INFO;
+
+	pc = poptGetContext(argv[0], argc, argv, popt_options, POPT_CONTEXT_KEEP_FIRST);
+
+	while ((opt = poptGetNextOpt(pc)) != -1) {
+		switch (opt) {
+		default:
+			fprintf(stderr, "Invalid option %s: %s\n",
+				poptBadOption(pc, 0), poptStrerror(opt));
+			exit(1);
+		}
+	}
+
+	/* setup the remaining options for the main program to use */
+	extra_argv = poptGetArgs(pc);
+	if (extra_argv) {
+		extra_argv++;
+		while (extra_argv[extra_argc]) extra_argc++;
+	}
+
+	if (globals.socketname == NULL) {
+		DEBUG(DEBUG_CRIT,("Socket name is undefined\n"));
+		exit(1);
+	}
+	if (socket_server_create()) {
+		DEBUG(DEBUG_CRIT,("Socket error: exiting\n"));
+		exit(1);
+	}
+	if (fork_helper()) {
+		DEBUG(DEBUG_CRIT,("Forking error: exiting\n"));
+		exit(1);
+	}
+	/* FIXME: Test tcp_checksum6, tcp_checksum */
+	/* FIXME: Test ctdb_sys_send_arp, ctdb_sys_send_tcp */
+	/* FIXME: Test ctdb_sys_{open,close}_capture_socket, ctdb_sys_read_tcp_packet */
+	test_ctdb_sys_check_iface_exists();
+	test_ctdb_get_peer_pid();
+	test_ctdb_get_process_name();
+	/* FIXME: Test ctdb_get_lock_info, ctdb_get_blocker_pid*/
+
+	socket_server_close();
+
+	DEBUG(DEBUG_INFO,("%d/%d tests successfull\n", globals.successcount, globals.testcount));
+	return 0;
+}
diff --git a/tests/src/ctdb_takeover_tests.c b/tests/src/ctdb_takeover_tests.c
index 837741e..1aa0620 100644
--- a/tests/src/ctdb_takeover_tests.c
+++ b/tests/src/ctdb_takeover_tests.c
@@ -21,7 +21,7 @@
 
 /* This is lazy... but it is test code! */
 #define CTDB_TEST_MAX_NODES 256
-#define CTDB_TEST_MAX_IPS 256
+#define CTDB_TEST_MAX_IPS 1024
 
 /* Format of each line is "IP pnn" - the separator has to be at least
  * 1 space (not a tab or whatever - a space!).
@@ -127,6 +127,11 @@ read_ctdb_public_ip_info(TALLOC_CTX *ctx,
 			*t = '\0';
 		}
 
+		/* Exit on an empty line */
+		if (line[0] == '\0') {
+			break;
+		}
+
 		/* Get the IP address */
 		tok = strtok(line, " \t");
 		if (tok == NULL) {
@@ -140,6 +145,10 @@ read_ctdb_public_ip_info(TALLOC_CTX *ctx,
 		}
 
 		numips++;
+		if (numips > CTDB_TEST_MAX_IPS) {
+			DEBUG(DEBUG_ERR, ("ERROR: Exceeding CTDB_TEST_MAX_IPS: %d\n", CTDB_TEST_MAX_IPS));
+			exit(1);
+		}
 
 		/* Get the PNN */
 		pnn = -1;
@@ -236,6 +245,10 @@ void ctdb_test_read_ctdb_public_ip_info(const char nodestates[])
 	tok = strtok(ns, ",");
 	while (tok != NULL) {
 		numnodes++;
+		if (numnodes > CTDB_TEST_MAX_NODES) {
+			DEBUG(DEBUG_ERR, ("ERROR: Exceeding CTDB_TEST_MAX_NODES: %d\n", CTDB_TEST_MAX_NODES));
+			exit(1);
+		}
 		tok = strtok(NULL, ",");
 	}
 	
@@ -320,15 +333,92 @@ void ctdb_test_lcp2_imbalance(int pnn)
 	talloc_free(tmp_ctx);
 }
 
+static uint32_t *get_tunable_values(TALLOC_CTX *tmp_ctx,
+				    int numnodes,
+				    const char *tunable)
+{
+	int i;
+	char *tok;
+	uint32_t *tvals = talloc_zero_array(tmp_ctx, uint32_t, numnodes);
+	char *t = getenv(tunable);
+
+	if (t) {
+		if (strcmp(t, "1") == 0) {
+			for (i=0; i<numnodes; i++) {
+				tvals[i] = 1;
+			}
+		} else {
+			tok = strtok(t, ",");
+			i = 0;
+			while (tok != NULL) {
+				tvals[i] =
+					(uint32_t) strtol(tok, NULL, 0);
+				i++;
+				tok = strtok(NULL, ",");
+			}
+			if (i != numnodes) {
+				fprintf(stderr, "ERROR: Wrong number of values in %s\n", tunable);
+				exit(1);
+			}
+		}
+	}
+
+	return tvals;
+}
+
+static enum ctdb_runstate *get_runstate(TALLOC_CTX *tmp_ctx,
+					int numnodes)
+{
+	int i;
+	uint32_t *tvals;
+	enum ctdb_runstate *runstate =
+		talloc_zero_array(tmp_ctx, enum ctdb_runstate, numnodes);
+	char *t = getenv("CTDB_TEST_RUNSTATE");
+
+	if (t == NULL) {
+		for (i=0; i<numnodes; i++) {
+			runstate[i] = CTDB_RUNSTATE_RUNNING;
+		}
+	} else {
+		tvals = get_tunable_values(tmp_ctx, numnodes, "CTDB_TEST_RUNSTATE");
+		for (i=0; i<numnodes; i++) {
+			runstate[i] = (enum ctdb_runstate) tvals[i];
+		}
+		talloc_free(tvals);
+	}
+
+	return runstate;
+}
+
+/* Fake up enough CTDB state to be able to run the IP allocation
+ * algorithm.  Usually this sets up some standard state, sets the node
+ * states from the command-line and reads the current IP layout from
+ * stdin.
+ *
+ * However, if read_ips_for_multiple_nodes is true then each node's
+ * idea of the IP layout is read separately from stdin.  In this mode
+ * is doesn't make much sense to use read_ctdb_public_ip_info's
+ * optional ALLOWED_PNN,... list in the input, since each node is
+ * being handled separately anyway.  IPs for each node are separated
+ * by a blank line.  This mode is for testing weird behaviours where
+ * the IP layouts differs across nodes and we want to improve
+ * create_merged_ip_list(), so should only be used in tests of
+ * ctdb_takeover_run_core().  Yes, it is a hack...  :-)
+ */
 void ctdb_test_init(const char nodestates[],
 		    struct ctdb_context **ctdb,
 		    struct ctdb_public_ip_list **all_ips,
-		    struct ctdb_node_map **nodemap)
+		    struct ctdb_ipflags **ipflags,
+		    bool read_ips_for_multiple_nodes)
 {
 	struct ctdb_all_public_ips **avail;
 	int i, numnodes;
 	uint32_t nodeflags[CTDB_TEST_MAX_NODES];
-	char *tok, *ns;
+	char *tok, *ns, *t;
+	struct ctdb_node_map *nodemap;
+	uint32_t *tval_noiptakeover;
+	uint32_t *tval_noiptakeoverondisabled;
+	enum ctdb_runstate *runstate;
 
 	*ctdb = talloc_zero(NULL, struct ctdb_context);
 
@@ -338,8 +428,12 @@ void ctdb_test_init(const char nodestates[],
 	numnodes = 0;
 	tok = strtok(ns, ",");
 	while (tok != NULL) {
-		nodeflags[numnodes] = (uint32_t) strtol(tok, NULL, 16);
+		nodeflags[numnodes] = (uint32_t) strtol(tok, NULL, 0);
 		numnodes++;
+		if (numnodes > CTDB_TEST_MAX_NODES) {
+			DEBUG(DEBUG_ERR, ("ERROR: Exceeding CTDB_TEST_MAX_NODES: %d\n", CTDB_TEST_MAX_NODES));
+			exit(1);
+		}
 		tok = strtok(NULL, ",");
 	}
 	
@@ -352,44 +446,58 @@ void ctdb_test_init(const char nodestates[],
 	(*ctdb)->tunable.disable_ip_failover = 0;
 	(*ctdb)->tunable.no_ip_failback = 0;
 
-	if (getenv("CTDB_IP_ALGORITHM")) {
-		if (strcmp(getenv("CTDB_IP_ALGORITHM"), "lcp2") == 0) {
+	if ((t = getenv("CTDB_IP_ALGORITHM"))) {
+		if (strcmp(t, "lcp2") == 0) {
 			(*ctdb)->tunable.lcp2_public_ip_assignment = 1;
-		} else if (strcmp(getenv("CTDB_IP_ALGORITHM"), "nondet") == 0) {
+		} else if (strcmp(t, "nondet") == 0) {
 			(*ctdb)->tunable.lcp2_public_ip_assignment = 0;
-		} else if (strcmp(getenv("CTDB_IP_ALGORITHM"), "det") == 0) {
+		} else if (strcmp(t, "det") == 0) {
 			(*ctdb)->tunable.lcp2_public_ip_assignment = 0;
 			(*ctdb)->tunable.deterministic_public_ips = 1;
 		} else {
-			fprintf(stderr, "ERROR: unknown IP algorithm %s\n",
-				getenv("CTDB_IP_ALGORITHM"));
+			fprintf(stderr, "ERROR: unknown IP algorithm %s\n", t);
 			exit(1);
 		}
 	}
 
-	(*ctdb)->tunable.no_ip_takeover_on_disabled = 0;
-	if (getenv("CTDB_SET_NoIPTakeoverOnDisabled")) {
-		(*ctdb)->tunable.no_ip_takeover_on_disabled = (uint32_t) strtoul(getenv("CTDB_SET_NoIPTakeoverOnDisabled"), NULL, 0);
-	}
-		
-	*nodemap =  talloc_array(*ctdb, struct ctdb_node_map, numnodes);
-	(*nodemap)->num = numnodes;
+	tval_noiptakeover = get_tunable_values(*ctdb, numnodes,
+					       "CTDB_SET_NoIPTakeover");
+	tval_noiptakeoverondisabled =
+		get_tunable_values(*ctdb, numnodes,
+				   "CTDB_SET_NoIPHostOnAllDisabled");
 
-	read_ctdb_public_ip_info(*ctdb, numnodes, all_ips, &avail);
+	runstate = get_runstate(*ctdb, numnodes);
+
+	nodemap =  talloc_array(*ctdb, struct ctdb_node_map, numnodes);
+	nodemap->num = numnodes;
+
+	if (!read_ips_for_multiple_nodes) {
+		read_ctdb_public_ip_info(*ctdb, numnodes, all_ips, &avail);
+	}
 
 	(*ctdb)->nodes = talloc_array(*ctdb, struct ctdb_node *, numnodes); // FIXME: bogus size, overkill
 
 	for (i=0; i < numnodes; i++) {
-		(*nodemap)->nodes[i].pnn = i;
-		(*nodemap)->nodes[i].flags = nodeflags[i];
+		nodemap->nodes[i].pnn = i;
+		nodemap->nodes[i].flags = nodeflags[i];
 		/* nodemap->nodes[i].sockaddr is uninitialised */
 
+		if (read_ips_for_multiple_nodes) {
+			read_ctdb_public_ip_info(*ctdb, numnodes,
+						 all_ips, &avail);
+		}
+
 		(*ctdb)->nodes[i] = talloc(*ctdb, struct ctdb_node);
 		(*ctdb)->nodes[i]->pnn = i;
 		(*ctdb)->nodes[i]->flags = nodeflags[i];
 		(*ctdb)->nodes[i]->available_public_ips = avail[i];
 		(*ctdb)->nodes[i]->known_public_ips = avail[i];
 	}
+
+	*ipflags = set_ipflags_internal(*ctdb, *ctdb, nodemap,
+					tval_noiptakeover,
+					tval_noiptakeoverondisabled,
+					runstate);
 }
 
 /* IP layout is read from stdin. */
@@ -397,19 +505,16 @@ void ctdb_test_lcp2_allocate_unassigned(const char nodestates[])
 {
 	struct ctdb_context *ctdb;
 	struct ctdb_public_ip_list *all_ips;
-	struct ctdb_node_map *nodemap;
+	struct ctdb_ipflags *ipflags;
 
 	uint32_t *lcp2_imbalances;
 	bool *newly_healthy;
 
-	ctdb_test_init(nodestates, &ctdb, &all_ips, &nodemap);
+	ctdb_test_init(nodestates, &ctdb, &all_ips, &ipflags, false);
 
-	lcp2_init(ctdb, nodemap,
-		  NODE_FLAGS_INACTIVE|NODE_FLAGS_DISABLED,
-		  all_ips, &lcp2_imbalances, &newly_healthy);
+	lcp2_init(ctdb, ipflags, all_ips, &lcp2_imbalances, &newly_healthy);
 
-	lcp2_allocate_unassigned(ctdb, nodemap,
-				 NODE_FLAGS_INACTIVE|NODE_FLAGS_DISABLED,
+	lcp2_allocate_unassigned(ctdb, ipflags,
 				 all_ips, lcp2_imbalances);
 
 	print_ctdb_public_ip_list(all_ips);
@@ -422,19 +527,16 @@ void ctdb_test_lcp2_failback(const char nodestates[])
 {
 	struct ctdb_context *ctdb;
 	struct ctdb_public_ip_list *all_ips;
-	struct ctdb_node_map *nodemap;
+	struct ctdb_ipflags *ipflags;
 
 	uint32_t *lcp2_imbalances;
 	bool *newly_healthy;
 
-	ctdb_test_init(nodestates, &ctdb, &all_ips, &nodemap);
+	ctdb_test_init(nodestates, &ctdb, &all_ips, &ipflags, false);
 
-	lcp2_init(ctdb, nodemap,
-		  NODE_FLAGS_INACTIVE|NODE_FLAGS_DISABLED,
-		  all_ips, &lcp2_imbalances, &newly_healthy);
+	lcp2_init(ctdb, ipflags, all_ips, &lcp2_imbalances, &newly_healthy);
 
-	lcp2_failback(ctdb, nodemap,
-				 NODE_FLAGS_INACTIVE|NODE_FLAGS_DISABLED,
+	lcp2_failback(ctdb, ipflags,
 		      all_ips, lcp2_imbalances, newly_healthy);
 
 	print_ctdb_public_ip_list(all_ips);
@@ -447,19 +549,16 @@ void ctdb_test_lcp2_failback_loop(const char nodestates[])
 {
 	struct ctdb_context *ctdb;
 	struct ctdb_public_ip_list *all_ips;
-	struct ctdb_node_map *nodemap;
+	struct ctdb_ipflags *ipflags;
 
 	uint32_t *lcp2_imbalances;
 	bool *newly_healthy;
 
-	ctdb_test_init(nodestates, &ctdb, &all_ips, &nodemap);
+	ctdb_test_init(nodestates, &ctdb, &all_ips, &ipflags, false);
 
-	lcp2_init(ctdb, nodemap,
-		  NODE_FLAGS_INACTIVE|NODE_FLAGS_DISABLED,
-		  all_ips, &lcp2_imbalances, &newly_healthy);
+	lcp2_init(ctdb, ipflags, all_ips, &lcp2_imbalances, &newly_healthy);
 
-	lcp2_failback(ctdb, nodemap,
-		      NODE_FLAGS_INACTIVE|NODE_FLAGS_DISABLED,
+	lcp2_failback(ctdb, ipflags,
 		      all_ips, lcp2_imbalances, newly_healthy);
 
 	print_ctdb_public_ip_list(all_ips);
@@ -467,16 +566,20 @@ void ctdb_test_lcp2_failback_loop(const char nodestates[])
 	talloc_free(ctdb);
 }
 
-/* IP layout is read from stdin. */
-void ctdb_test_ctdb_takeover_run_core(const char nodestates[])
+/* IP layout is read from stdin.  See comment for ctdb_test_init() for
+ * explanation of read_ips_for_multiple_nodes.
+ */
+void ctdb_test_ctdb_takeover_run_core(const char nodestates[],
+				      bool read_ips_for_multiple_nodes)
 {
 	struct ctdb_context *ctdb;
 	struct ctdb_public_ip_list *all_ips;
-	struct ctdb_node_map *nodemap;
+	struct ctdb_ipflags *ipflags;
 
-	ctdb_test_init(nodestates, &ctdb, &all_ips, &nodemap);
+	ctdb_test_init(nodestates, &ctdb, &all_ips, &ipflags,
+		       read_ips_for_multiple_nodes);
 
-	ctdb_takeover_run_core(ctdb, nodemap, &all_ips);
+	ctdb_takeover_run_core(ctdb, ipflags, &all_ips);
 
 	print_ctdb_public_ip_list(all_ips);
 
@@ -516,8 +619,13 @@ int main(int argc, const char *argv[])
 		ctdb_test_lcp2_failback(argv[2]);
 	} else if (argc == 3 && strcmp(argv[1], "lcp2_failback_loop") == 0) {
 		ctdb_test_lcp2_failback_loop(argv[2]);
-	} else if (argc == 3 && strcmp(argv[1], "ctdb_takeover_run_core") == 0) {
-		ctdb_test_ctdb_takeover_run_core(argv[2]);
+	} else if (argc == 3 &&
+		   strcmp(argv[1], "ctdb_takeover_run_core") == 0) {
+		ctdb_test_ctdb_takeover_run_core(argv[2], false);
+	} else if (argc == 4 &&
+		   strcmp(argv[1], "ctdb_takeover_run_core") == 0 &&
+		   strcmp(argv[3], "multi") == 0) {
+		ctdb_test_ctdb_takeover_run_core(argv[2], true);
 	} else {
 		usage();
 	}
diff --git a/tests/src/ctdb_test.c b/tests/src/ctdb_test.c
index ea1e7aa..5319305 100644
--- a/tests/src/ctdb_test.c
+++ b/tests/src/ctdb_test.c
@@ -23,10 +23,6 @@
 #ifdef CTDB_TEST_USE_MAIN
 
 /* Use main, stubify some stuff */
-#define _GNU_SOURCE
-#include <stdio.h>
-#include <sys/socket.h>
-
 #define ctdb_cmdline_client(x, y) ctdb_cmdline_client_foobar(x, y)
 #define ctdb_get_socketname(x) ctdb_get_socketname_foobar(x)
 
diff --git a/tests/src/ctdb_trackingdb_test.c b/tests/src/ctdb_trackingdb_test.c
index 0dcdcb4..d8525d5 100644
--- a/tests/src/ctdb_trackingdb_test.c
+++ b/tests/src/ctdb_trackingdb_test.c
@@ -22,10 +22,9 @@
    along with this program; if not, see <http://www.gnu.org/licenses/>.
 */
 
-#include <stdlib.h>
-#include <time.h>
 #include "includes.h"
 #include "system/filesys.h"
+#include "system/time.h"
 #include "popt.h"
 #include "cmdline.h"
 #include "ctdb_private.h"
diff --git a/tests/takeover/det.001.sh b/tests/takeover/det.001.sh
index dec7010..2387f12 100755
--- a/tests/takeover/det.001.sh
+++ b/tests/takeover/det.001.sh
@@ -6,6 +6,12 @@ define_test "3 nodes, 1 healthy"
 
 required_result <<EOF
 DATE TIME [PID]: Deterministic IPs enabled. Resetting all ip allocations
+DATE TIME [PID]: Unassign IP: 192.168.21.254 from 0
+DATE TIME [PID]: Unassign IP: 192.168.21.253 from 1
+DATE TIME [PID]: Unassign IP: 192.168.20.254 from 0
+DATE TIME [PID]: Unassign IP: 192.168.20.253 from 1
+DATE TIME [PID]: Unassign IP: 192.168.20.251 from 0
+DATE TIME [PID]: Unassign IP: 192.168.20.250 from 1
 192.168.21.254 2
 192.168.21.253 2
 192.168.21.252 2
diff --git a/tests/takeover/det.002.sh b/tests/takeover/det.002.sh
index 21c55bd..21fbaec 100755
--- a/tests/takeover/det.002.sh
+++ b/tests/takeover/det.002.sh
@@ -6,6 +6,9 @@ define_test "3 nodes, 2 healthy"
 
 required_result <<EOF
 DATE TIME [PID]: Deterministic IPs enabled. Resetting all ip allocations
+DATE TIME [PID]: Unassign IP: 192.168.21.253 from 1
+DATE TIME [PID]: Unassign IP: 192.168.20.253 from 1
+DATE TIME [PID]: Unassign IP: 192.168.20.250 from 1
 192.168.21.254 0
 192.168.21.253 0
 192.168.21.252 2
diff --git a/tests/takeover/lcp2.012.sh b/tests/takeover/lcp2.012.sh
index 70dad93..8f5c537 100755
--- a/tests/takeover/lcp2.012.sh
+++ b/tests/takeover/lcp2.012.sh
@@ -18,7 +18,9 @@ required_result <<EOF
 192.168.20.249 1
 EOF
 
-simple_test 0x01000000,0,0 <<EOF
+export CTDB_SET_NoIPTakeover="1,0,0"
+
+simple_test 0,0,0 <<EOF
 192.168.20.249 1
 192.168.20.250 1
 192.168.20.251 1
diff --git a/tests/takeover/lcp2.013.sh b/tests/takeover/lcp2.013.sh
index 4d01f12..fb9d724 100755
--- a/tests/takeover/lcp2.013.sh
+++ b/tests/takeover/lcp2.013.sh
@@ -18,7 +18,9 @@ required_result <<EOF
 192.168.20.249 0
 EOF
 
-simple_test 0x01000000,0,0 <<EOF
+export CTDB_SET_NoIPTakeover="1,0,0"
+
+simple_test 0,0,0 <<EOF
 192.168.20.249 0
 192.168.20.250 1
 192.168.20.251 2
diff --git a/tests/takeover/lcp2.017.sh b/tests/takeover/lcp2.017.sh
index b09cb00..07b22fb 100755
--- a/tests/takeover/lcp2.017.sh
+++ b/tests/takeover/lcp2.017.sh
@@ -2,10 +2,10 @@
 
 . "${TEST_SCRIPTS_DIR}/unit.sh"
 
-define_test "3 nodes, no IPs assigned, all unhealthy, NoIPTakeoverOnDisabled"
+define_test "3 nodes, no IPs assigned, all unhealthy, NoIPHostOnAllDisabled"
 
 export CTDB_TEST_LOGLEVEL=0
-export CTDB_SET_NoIPTakeoverOnDisabled=1
+export CTDB_SET_NoIPHostOnAllDisabled=1
 
 required_result <<EOF
 192.168.21.254 -1
diff --git a/tests/takeover/lcp2.018.sh b/tests/takeover/lcp2.018.sh
index 6bc448b..4a797f7 100755
--- a/tests/takeover/lcp2.018.sh
+++ b/tests/takeover/lcp2.018.sh
@@ -2,10 +2,10 @@
 
 . "${TEST_SCRIPTS_DIR}/unit.sh"
 
-define_test "3 nodes, all IPs assigned, all unhealthy, NoIPTakeoverOnDisabled"
+define_test "3 nodes, all IPs assigned, all unhealthy, NoIPHostOnAllDisabled"
 
 export CTDB_TEST_LOGLEVEL=0
-export CTDB_SET_NoIPTakeoverOnDisabled=1
+export CTDB_SET_NoIPHostOnAllDisabled=1
 
 required_result <<EOF
 192.168.21.254 -1
diff --git a/tests/takeover/lcp2.019.sh b/tests/takeover/lcp2.019.sh
index 5080e07..0d8937c 100755
--- a/tests/takeover/lcp2.019.sh
+++ b/tests/takeover/lcp2.019.sh
@@ -2,10 +2,10 @@
 
 . "${TEST_SCRIPTS_DIR}/unit.sh"
 
-define_test "3 nodes, all IPs assigned, 2->3 unhealthy, NoIPTakeoverOnDisabled"
+define_test "3 nodes, all IPs assigned, 2->3 unhealthy, NoIPHostOnAllDisabled"
 
 export CTDB_TEST_LOGLEVEL=0
-export CTDB_SET_NoIPTakeoverOnDisabled=1
+export CTDB_SET_NoIPHostOnAllDisabled=1
 
 required_result <<EOF
 192.168.21.254 -1
diff --git a/tests/takeover/lcp2.016.sh b/tests/takeover/lcp2.020.sh
similarity index 59%
copy from tests/takeover/lcp2.016.sh
copy to tests/takeover/lcp2.020.sh
index 2e2df1b..e3fe3c4 100755
--- a/tests/takeover/lcp2.016.sh
+++ b/tests/takeover/lcp2.020.sh
@@ -2,22 +2,24 @@
 
 . "${TEST_SCRIPTS_DIR}/unit.sh"
 
-define_test "3 nodes, all IPs assigned, 2->3 unhealthy"
+define_test "3 nodes, all IPs assigned, 2->3 unhealthy, NoIPHostOnAllDisabled on 2"
 
 export CTDB_TEST_LOGLEVEL=0
 
 required_result <<EOF
-192.168.21.254 1
-192.168.21.253 0
+192.168.21.254 2
+192.168.21.253 2
 192.168.21.252 2
-192.168.20.254 1
-192.168.20.253 0
+192.168.20.254 2
+192.168.20.253 2
 192.168.20.252 2
-192.168.20.251 1
-192.168.20.250 0
+192.168.20.251 2
+192.168.20.250 2
 192.168.20.249 2
 EOF
 
+export CTDB_SET_NoIPHostOnAllDisabled=1,1,0
+
 simple_test 2,2,2 <<EOF
 192.168.21.254 2
 192.168.21.253 2
diff --git a/tests/takeover/lcp2.016.sh b/tests/takeover/lcp2.021.sh
similarity index 58%
copy from tests/takeover/lcp2.016.sh
copy to tests/takeover/lcp2.021.sh
index 2e2df1b..7dcddb1 100755
--- a/tests/takeover/lcp2.016.sh
+++ b/tests/takeover/lcp2.021.sh
@@ -2,22 +2,24 @@
 
 . "${TEST_SCRIPTS_DIR}/unit.sh"
 
-define_test "3 nodes, all IPs assigned, 2->3 unhealthy"
+define_test "3 nodes, no IPs assigned, 3->2 unhealthy, NoIPHostOnAllDisabled on 2 others"
 
 export CTDB_TEST_LOGLEVEL=0
 
 required_result <<EOF
-192.168.21.254 1
+192.168.21.254 0
 192.168.21.253 0
-192.168.21.252 2
-192.168.20.254 1
+192.168.21.252 0
+192.168.20.254 0
 192.168.20.253 0
-192.168.20.252 2
-192.168.20.251 1
+192.168.20.252 0
+192.168.20.251 0
 192.168.20.250 0
-192.168.20.249 2
+192.168.20.249 0
 EOF
 
+export CTDB_SET_NoIPHostOnAllDisabled=0,1,1
+
 simple_test 2,2,2 <<EOF
 192.168.21.254 2
 192.168.21.253 2
diff --git a/tests/takeover/lcp2.016.sh b/tests/takeover/lcp2.022.sh
similarity index 56%
copy from tests/takeover/lcp2.016.sh
copy to tests/takeover/lcp2.022.sh
index 2e2df1b..7eb4d8a 100755
--- a/tests/takeover/lcp2.016.sh
+++ b/tests/takeover/lcp2.022.sh
@@ -2,22 +2,26 @@
 
 . "${TEST_SCRIPTS_DIR}/unit.sh"
 
-define_test "3 nodes, all IPs assigned, 2->3 unhealthy"
+define_test "3 nodes, no IPs assigned, 3->2 unhealthy, NoIPTakeover on 2 others"
 
 export CTDB_TEST_LOGLEVEL=0
 
+# We expect 1/2 the IPs to move, but the rest to stay (as opposed to
+# NoIPHostOnAllDisabled)
 required_result <<EOF
-192.168.21.254 1
+192.168.21.254 2
 192.168.21.253 0
 192.168.21.252 2
-192.168.20.254 1
+192.168.20.254 0
 192.168.20.253 0
 192.168.20.252 2
-192.168.20.251 1
-192.168.20.250 0
+192.168.20.251 0
+192.168.20.250 2
 192.168.20.249 2
 EOF
 
+export CTDB_SET_NoIPTakeover=0,1,1
+
 simple_test 2,2,2 <<EOF
 192.168.21.254 2
 192.168.21.253 2
diff --git a/tests/takeover/lcp2.023.sh b/tests/takeover/lcp2.023.sh
new file mode 100755
index 0000000..9bffc58
--- /dev/null
+++ b/tests/takeover/lcp2.023.sh
@@ -0,0 +1,77 @@
+#!/bin/sh
+
+. "${TEST_SCRIPTS_DIR}/unit.sh"
+
+define_test "3 nodes, all IPs assigned, 1->3 unhealthy"
+
+export CTDB_TEST_LOGLEVEL=4
+
+required_result <<EOF
+DATE TIME [PID]:  ----------------------------------------
+DATE TIME [PID]:  CONSIDERING MOVES (UNASSIGNED)
+DATE TIME [PID]:  ----------------------------------------
+DATE TIME [PID]:  ----------------------------------------
+DATE TIME [PID]:  CONSIDERING MOVES FROM 2 [147968]
+DATE TIME [PID]:  2 [-58359] -> 192.168.21.254 -> 1 [+0]
+DATE TIME [PID]:  2 [-58359] -> 192.168.21.252 -> 1 [+0]
+DATE TIME [PID]:  2 [-59572] -> 192.168.20.253 -> 1 [+0]
+DATE TIME [PID]:  2 [-59823] -> 192.168.20.251 -> 1 [+0]
+DATE TIME [PID]:  2 [-59823] -> 192.168.20.249 -> 1 [+0]
+DATE TIME [PID]:  ----------------------------------------
+DATE TIME [PID]: 2 [-59823] -> 192.168.20.251 -> 1 [+0]
+DATE TIME [PID]:  ----------------------------------------
+DATE TIME [PID]:  CONSIDERING MOVES FROM 0 [89609]
+DATE TIME [PID]:  0 [-42483] -> 192.168.21.253 -> 1 [+14161]
+DATE TIME [PID]:  0 [-45662] -> 192.168.20.254 -> 1 [+15625]
+DATE TIME [PID]:  0 [-45662] -> 192.168.20.252 -> 1 [+15625]
+DATE TIME [PID]:  0 [-45411] -> 192.168.20.250 -> 1 [+16129]
+DATE TIME [PID]:  ----------------------------------------
+DATE TIME [PID]: 0 [-45662] -> 192.168.20.254 -> 1 [+15625]
+DATE TIME [PID]:  ----------------------------------------
+DATE TIME [PID]:  CONSIDERING MOVES FROM 2 [88145]
+DATE TIME [PID]:  2 [-44198] -> 192.168.21.254 -> 1 [+28322]
+DATE TIME [PID]:  2 [-44198] -> 192.168.21.252 -> 1 [+28322]
+DATE TIME [PID]:  2 [-43947] -> 192.168.20.253 -> 1 [+31501]
+DATE TIME [PID]:  2 [-43947] -> 192.168.20.249 -> 1 [+31501]
+DATE TIME [PID]:  ----------------------------------------
+DATE TIME [PID]: 2 [-44198] -> 192.168.21.254 -> 1 [+28322]
+DATE TIME [PID]:  ----------------------------------------
+DATE TIME [PID]:  CONSIDERING MOVES FROM 0 [44198]
+DATE TIME [PID]:  0 [-28322] -> 192.168.21.253 -> 1 [+44198]
+DATE TIME [PID]:  0 [-29786] -> 192.168.20.252 -> 1 [+45662]
+DATE TIME [PID]:  0 [-29786] -> 192.168.20.250 -> 1 [+45915]
+DATE TIME [PID]:  ----------------------------------------
+DATE TIME [PID]:  ----------------------------------------
+DATE TIME [PID]:  CONSIDERING MOVES FROM 2 [44198]
+DATE TIME [PID]:  2 [-28322] -> 192.168.21.252 -> 1 [+44198]
+DATE TIME [PID]:  2 [-29786] -> 192.168.20.253 -> 1 [+45662]
+DATE TIME [PID]:  2 [-29786] -> 192.168.20.249 -> 1 [+45662]
+DATE TIME [PID]:  ----------------------------------------
+DATE TIME [PID]:  ----------------------------------------
+DATE TIME [PID]:  CONSIDERING MOVES FROM 1 [43947]
+DATE TIME [PID]:  1 [-28322] -> 192.168.21.254 -> 1 [+28322]
+DATE TIME [PID]:  1 [-29786] -> 192.168.20.254 -> 1 [+29786]
+DATE TIME [PID]:  1 [-29786] -> 192.168.20.251 -> 1 [+29786]
+DATE TIME [PID]:  ----------------------------------------
+192.168.21.254 1
+192.168.21.253 0
+192.168.21.252 2
+192.168.20.254 1
+192.168.20.253 2
+192.168.20.252 0
+192.168.20.251 1
+192.168.20.250 0
+192.168.20.249 2
+EOF
+
+simple_test 2,2,2 <<EOF
+192.168.21.254 2
+192.168.21.253 0
+192.168.21.252 2
+192.168.20.254 0
+192.168.20.253 2
+192.168.20.252 0
+192.168.20.251 2
+192.168.20.250 0
+192.168.20.249 2
+EOF
diff --git a/tests/takeover/lcp2.024.sh b/tests/takeover/lcp2.024.sh
new file mode 100755
index 0000000..0509552
--- /dev/null
+++ b/tests/takeover/lcp2.024.sh
@@ -0,0 +1,42 @@
+#!/bin/sh
+
+. "${TEST_SCRIPTS_DIR}/unit.sh"
+
+define_test "3 nodes, no IPs assigned, all healthy, all in STARTUP runstate"
+
+export CTDB_TEST_LOGLEVEL=2
+
+required_result <<EOF
+DATE TIME [PID]: Failed to find node to cover ip 192.168.21.254
+DATE TIME [PID]: Failed to find node to cover ip 192.168.21.253
+DATE TIME [PID]: Failed to find node to cover ip 192.168.21.252
+DATE TIME [PID]: Failed to find node to cover ip 192.168.20.254
+DATE TIME [PID]: Failed to find node to cover ip 192.168.20.253
+DATE TIME [PID]: Failed to find node to cover ip 192.168.20.252
+DATE TIME [PID]: Failed to find node to cover ip 192.168.20.251
+DATE TIME [PID]: Failed to find node to cover ip 192.168.20.250
+DATE TIME [PID]: Failed to find node to cover ip 192.168.20.249
+192.168.21.254 -1
+192.168.21.253 -1
+192.168.21.252 -1
+192.168.20.254 -1
+192.168.20.253 -1
+192.168.20.252 -1
+192.168.20.251 -1
+192.168.20.250 -1
+192.168.20.249 -1
+EOF
+
+export CTDB_TEST_RUNSTATE=4,4,4
+
+simple_test 0,0,0 <<EOF
+192.168.21.254 -1
+192.168.21.253 -1
+192.168.21.252 -1
+192.168.20.254 -1
+192.168.20.253 -1
+192.168.20.252 -1
+192.168.20.251 -1
+192.168.20.250 -1
+192.168.20.249 -1
+EOF
diff --git a/tests/takeover/lcp2.007.sh b/tests/takeover/lcp2.025.sh
similarity index 71%
copy from tests/takeover/lcp2.007.sh
copy to tests/takeover/lcp2.025.sh
index 76fa06e..44b8583 100755
--- a/tests/takeover/lcp2.007.sh
+++ b/tests/takeover/lcp2.025.sh
@@ -2,9 +2,9 @@
 
 . "${TEST_SCRIPTS_DIR}/unit.sh"
 
-define_test "3 nodes, 0 -> 2 healthy"
+define_test "3 nodes, no IPs assigned, all healthy, 1 in STARTUP runstate"
 
-export CTDB_TEST_LOGLEVEL=0
+export CTDB_TEST_LOGLEVEL=2
 
 required_result <<EOF
 192.168.21.254 1
@@ -18,14 +18,16 @@ required_result <<EOF
 192.168.20.249 2
 EOF
 
-simple_test 2,0,0 <<EOF
-192.168.20.249 -1
-192.168.20.250 -1
-192.168.20.251 -1
-192.168.20.252 -1
-192.168.20.253 -1
-192.168.20.254 -1
-192.168.21.252 -1
-192.168.21.253 -1
+export CTDB_TEST_RUNSTATE=4,5,5
+
+simple_test 0,0,0 <<EOF
 192.168.21.254 -1
+192.168.21.253 -1
+192.168.21.252 -1
+192.168.20.254 -1
+192.168.20.253 -1
+192.168.20.252 -1
+192.168.20.251 -1
+192.168.20.250 -1
+192.168.20.249 -1
 EOF
diff --git a/tests/takeover/lcp2.007.sh b/tests/takeover/lcp2.026.sh
similarity index 70%
copy from tests/takeover/lcp2.007.sh
copy to tests/takeover/lcp2.026.sh
index 76fa06e..4c22ba5 100755
--- a/tests/takeover/lcp2.007.sh
+++ b/tests/takeover/lcp2.026.sh
@@ -2,9 +2,9 @@
 
 . "${TEST_SCRIPTS_DIR}/unit.sh"
 
-define_test "3 nodes, 0 -> 2 healthy"
+define_test "3 nodes, no IPs assigned, all unhealthy, 1 in STARTUP runstate"
 
-export CTDB_TEST_LOGLEVEL=0
+export CTDB_TEST_LOGLEVEL=2
 
 required_result <<EOF
 192.168.21.254 1
@@ -18,14 +18,16 @@ required_result <<EOF
 192.168.20.249 2
 EOF
 
-simple_test 2,0,0 <<EOF
-192.168.20.249 -1
-192.168.20.250 -1
-192.168.20.251 -1
-192.168.20.252 -1
-192.168.20.253 -1
-192.168.20.254 -1
-192.168.21.252 -1
-192.168.21.253 -1
+export CTDB_TEST_RUNSTATE=4,5,5
+
+simple_test 2,2,2 <<EOF
 192.168.21.254 -1
+192.168.21.253 -1
+192.168.21.252 -1
+192.168.20.254 -1
+192.168.20.253 -1
+192.168.20.252 -1
+192.168.20.251 -1
+192.168.20.250 -1
+192.168.20.249 -1
 EOF
diff --git a/tests/takeover/lcp2.027.sh b/tests/takeover/lcp2.027.sh
new file mode 100755
index 0000000..20e0f28
--- /dev/null
+++ b/tests/takeover/lcp2.027.sh
@@ -0,0 +1,45 @@
+#!/bin/sh
+
+. "${TEST_SCRIPTS_DIR}/unit.sh"
+
+define_test "4 nodes, all IPs assigned, 3->4 unhealthy"
+
+export CTDB_TEST_LOGLEVEL=0
+
+required_result <<EOF
+130.216.30.181 0
+130.216.30.180 1
+130.216.30.179 3
+130.216.30.178 3
+130.216.30.177 0
+130.216.30.176 1
+130.216.30.175 0
+130.216.30.174 1
+130.216.30.173 0
+130.216.30.172 3
+130.216.30.171 1
+130.216.30.170 3
+10.19.99.253 0
+10.19.99.252 1
+10.19.99.251 0
+10.19.99.250 3
+EOF
+
+simple_test 0,0,2,0 <<EOF
+130.216.30.170 3
+130.216.30.171 2
+130.216.30.172 3
+130.216.30.173 2
+130.216.30.174 1
+130.216.30.175 0
+130.216.30.176 1
+130.216.30.177 0
+130.216.30.178 3
+130.216.30.179 2
+130.216.30.180 1
+130.216.30.181 0
+10.19.99.250 3
+10.19.99.251 2
+10.19.99.252 1
+10.19.99.253 0
+EOF
diff --git a/tests/takeover/lcp2.028.sh b/tests/takeover/lcp2.028.sh
new file mode 100755
index 0000000..60d22d9
--- /dev/null
+++ b/tests/takeover/lcp2.028.sh
@@ -0,0 +1,45 @@
+#!/bin/sh
+
+. "${TEST_SCRIPTS_DIR}/unit.sh"
+
+define_test "4 nodes, all healthy/assigned, stays unbalanced"
+
+export CTDB_TEST_LOGLEVEL=3
+
+required_result <<EOF
+130.216.30.181 0
+130.216.30.180 1
+130.216.30.179 2
+130.216.30.178 3
+130.216.30.177 0
+130.216.30.176 1
+130.216.30.175 0
+130.216.30.174 1
+130.216.30.173 0
+130.216.30.172 3
+130.216.30.171 1
+130.216.30.170 3
+10.19.99.253 0
+10.19.99.252 1
+10.19.99.251 0
+10.19.99.250 3
+EOF
+
+simple_test 0,0,0,0 <<EOF
+130.216.30.181 0
+130.216.30.180 1
+130.216.30.179 2
+130.216.30.178 3
+130.216.30.177 0
+130.216.30.176 1
+130.216.30.175 0
+130.216.30.174 1
+130.216.30.173 0
+130.216.30.172 3
+130.216.30.171 1
+130.216.30.170 3
+10.19.99.253 0
+10.19.99.252 1
+10.19.99.251 0
+10.19.99.250 3
+EOF
diff --git a/tests/takeover/lcp2.029.sh b/tests/takeover/lcp2.029.sh
new file mode 100755
index 0000000..d3c817f
--- /dev/null
+++ b/tests/takeover/lcp2.029.sh
@@ -0,0 +1,111 @@
+#!/bin/sh
+
+. "${TEST_SCRIPTS_DIR}/unit.sh"
+
+define_test "4 nodes, some IPs unassigned on target nodes"
+
+export CTDB_TEST_LOGLEVEL=3
+
+required_result <<EOF
+DATE TIME [PID]:  10.19.99.251 -> 2 [+9216]
+DATE TIME [PID]:  130.216.30.173 -> 2 [+24345]
+DATE TIME [PID]:  130.216.30.171 -> 2 [+39970]
+130.216.30.181 0
+130.216.30.180 1
+130.216.30.179 2
+130.216.30.178 3
+130.216.30.177 0
+130.216.30.176 1
+130.216.30.175 0
+130.216.30.174 1
+130.216.30.173 2
+130.216.30.172 3
+130.216.30.171 2
+130.216.30.170 3
+10.19.99.253 0
+10.19.99.252 1
+10.19.99.251 2
+10.19.99.250 3
+EOF
+
+# In this example were 4 releases from node 2 in a previous iteration
+#
+#   Release of IP 130.216.30.179/27 on interface ethX1  node:3
+#   Release of IP 130.216.30.173/27 on interface ethX1  node:0
+#   Release of IP 130.216.30.171/27 on interface ethX1  node:1
+#   Release of IP 10.19.99.251/22 on interface ethX2  node:0
+#
+# However, one release failed so no takeovers were done.  This means
+# that the target node for each IP still thinks that the IPs are held
+# by node 2.  The release of 130.216.30.179 was so late that node 2
+# still thought that it held that address.
+
+simple_test 0,0,0,0 multi <<EOF
+130.216.30.181 0
+130.216.30.180 1
+130.216.30.179 3
+130.216.30.178 3
+130.216.30.177 0
+130.216.30.176 1
+130.216.30.175 0
+130.216.30.174 1
+130.216.30.173 2
+130.216.30.172 3
+130.216.30.171 1
+130.216.30.170 3
+10.19.99.253 0
+10.19.99.252 1
+10.19.99.251 2
+10.19.99.250 3
+
+130.216.30.181 0
+130.216.30.180 1
+130.216.30.179 3
+130.216.30.178 3
+130.216.30.177 0
+130.216.30.176 1
+130.216.30.175 0
+130.216.30.174 1
+130.216.30.173 0
+130.216.30.172 3
+130.216.30.171 2
+130.216.30.170 3
+10.19.99.253 0
+10.19.99.252 1
+10.19.99.251 0
+10.19.99.250 3
+
+130.216.30.181 0
+130.216.30.180 1
+130.216.30.179 2
+130.216.30.178 3
+130.216.30.177 0
+130.216.30.176 1
+130.216.30.175 0
+130.216.30.174 1
+130.216.30.173 0
+130.216.30.172 3
+130.216.30.171 1
+130.216.30.170 3
+10.19.99.253 0
+10.19.99.252 1
+10.19.99.251 0
+10.19.99.250 3
+
+130.216.30.181 0
+130.216.30.180 1
+130.216.30.179 2
+130.216.30.178 3
+130.216.30.177 0
+130.216.30.176 1
+130.216.30.175 0
+130.216.30.174 1
+130.216.30.173 0
+130.216.30.172 3
+130.216.30.171 1
+130.216.30.170 3
+10.19.99.253 0
+10.19.99.252 1
+10.19.99.251 0
+10.19.99.250 3
+EOF
diff --git a/tests/takeover/lcp2.030.sh b/tests/takeover/lcp2.030.sh
new file mode 100755
index 0000000..739757b
--- /dev/null
+++ b/tests/takeover/lcp2.030.sh
@@ -0,0 +1,1813 @@
+#!/bin/sh
+
+. "${TEST_SCRIPTS_DIR}/unit.sh"
+
+define_test "900 IPs, 5 nodes, 0 -> 5 healthy"
+
+export CTDB_TEST_LOGLEVEL=0
+
+required_result <<EOF
+192.168.10.90 0
+192.168.10.89 1
+192.168.10.88 2
+192.168.10.87 3
+192.168.10.86 4
+192.168.10.85 0
+192.168.10.84 1
+192.168.10.83 2
+192.168.10.82 3
+192.168.10.81 4
+192.168.10.80 0
+192.168.10.79 0
+192.168.10.78 1
+192.168.10.77 2
+192.168.10.76 3
+192.168.10.75 4
+192.168.10.74 1
+192.168.10.73 2
+192.168.10.72 3
+192.168.10.71 3
+192.168.10.70 4
+192.168.10.69 0
+192.168.10.68 1
+192.168.10.67 2
+192.168.10.66 4
+192.168.10.65 0
+192.168.10.64 1
+192.168.10.63 0
+192.168.10.62 1
+192.168.10.61 2
+192.168.10.60 3
+192.168.10.59 4
+192.168.10.58 2
+192.168.10.57 3
+192.168.10.56 0
+192.168.10.55 0
+192.168.10.54 1
+192.168.10.53 2
+192.168.10.52 3
+192.168.10.51 4
+192.168.10.50 1
+192.168.10.49 4
+192.168.10.48 2
+192.168.10.47 0
+192.168.10.46 1
+192.168.10.45 2
+192.168.10.44 3
+192.168.10.43 4
+192.168.10.42 2
+192.168.10.41 3
+192.168.10.40 1
+192.168.10.39 3
+192.168.10.38 4
+192.168.10.37 0
+192.168.10.36 1
+192.168.10.35 2
+192.168.10.34 4
+192.168.10.33 0
+192.168.10.32 3
+192.168.10.31 0
+192.168.10.30 1
+192.168.10.29 2
+192.168.10.28 3
+192.168.10.27 4
+192.168.10.26 3
+192.168.10.25 2
+192.168.10.24 0
+192.168.10.23 3
+192.168.10.22 4
+192.168.10.21 0
+192.168.10.20 1
+192.168.10.19 2
+192.168.10.18 4
+192.168.10.17 1
+192.168.10.16 4
+192.168.10.15 0
+192.168.10.14 1
+192.168.10.13 2
+192.168.10.12 3
+192.168.10.11 4
+192.168.10.10 2
+192.168.10.9 3
+192.168.10.8 4
+192.168.10.7 0
+192.168.10.6 1
+192.168.10.5 2
+192.168.10.4 3
+192.168.10.3 4
+192.168.10.2 0
+192.168.10.1 1
+192.168.9.90 0
+192.168.9.89 1
+192.168.9.88 2
+192.168.9.87 3
+192.168.9.86 4
+192.168.9.85 0
+192.168.9.84 1
+192.168.9.83 2
+192.168.9.82 3
+192.168.9.81 4
+192.168.9.80 0
+192.168.9.79 0
+192.168.9.78 1
+192.168.9.77 2
+192.168.9.76 3
+192.168.9.75 4
+192.168.9.74 1
+192.168.9.73 2
+192.168.9.72 3
+192.168.9.71 3
+192.168.9.70 4
+192.168.9.69 0
+192.168.9.68 1
+192.168.9.67 2
+192.168.9.66 4
+192.168.9.65 0
+192.168.9.64 1
+192.168.9.63 0
+192.168.9.62 1
+192.168.9.61 2
+192.168.9.60 3
+192.168.9.59 4
+192.168.9.58 2
+192.168.9.57 3
+192.168.9.56 4
+192.168.9.55 0
+192.168.9.54 1
+192.168.9.53 2
+192.168.9.52 3
+192.168.9.51 4
+192.168.9.50 0
+192.168.9.49 1
+192.168.9.48 2
+192.168.9.47 0
+192.168.9.46 1
+192.168.9.45 2
+192.168.9.44 3
+192.168.9.43 4
+192.168.9.42 2
+192.168.9.41 4
+192.168.9.40 3
+192.168.9.39 0
+192.168.9.38 1
+192.168.9.37 2
+192.168.9.36 3
+192.168.9.35 4
+192.168.9.34 0
+192.168.9.33 1
+192.168.9.32 4
+192.168.9.31 0
+192.168.9.30 1
+192.168.9.29 2
+192.168.9.28 3
+192.168.9.27 4
+192.168.9.26 2
+192.168.9.25 3
+192.168.9.24 0
+192.168.9.23 3
+192.168.9.22 4
+192.168.9.21 0
+192.168.9.20 1
+192.168.9.19 2
+192.168.9.18 4
+192.168.9.17 1
+192.168.9.16 3
+192.168.9.15 0
+192.168.9.14 1
+192.168.9.13 2
+192.168.9.12 3
+192.168.9.11 4
+192.168.9.10 2
+192.168.9.9 4
+192.168.9.8 3
+192.168.9.7 0
+192.168.9.6 1
+192.168.9.5 2
+192.168.9.4 3
+192.168.9.3 4
+192.168.9.2 0
+192.168.9.1 1
+192.168.8.90 0
+192.168.8.89 1
+192.168.8.88 2
+192.168.8.87 3
+192.168.8.86 4
+192.168.8.85 0
+192.168.8.84 1
+192.168.8.83 2
+192.168.8.82 3
+192.168.8.81 4
+192.168.8.80 0
+192.168.8.79 0
+192.168.8.78 1
+192.168.8.77 2
+192.168.8.76 3
+192.168.8.75 4
+192.168.8.74 1
+192.168.8.73 2
+192.168.8.72 3
+192.168.8.71 3
+192.168.8.70 4
+192.168.8.69 0
+192.168.8.68 1
+192.168.8.67 2
+192.168.8.66 4
+192.168.8.65 3
+192.168.8.64 0
+192.168.8.63 0
+192.168.8.62 1
+192.168.8.61 2
+192.168.8.60 3
+192.168.8.59 4
+192.168.8.58 1
+192.168.8.57 2
+192.168.8.56 3
+192.168.8.55 0
+192.168.8.54 1
+192.168.8.53 2
+192.168.8.52 3
+192.168.8.51 4
+192.168.8.50 0
+192.168.8.49 4
+192.168.8.48 1
+192.168.8.47 0
+192.168.8.46 1
+192.168.8.45 2
+192.168.8.44 3
+192.168.8.43 4
+192.168.8.42 2
+192.168.8.41 1
+192.168.8.40 4
+192.168.8.39 0
+192.168.8.38 1
+192.168.8.37 2
+192.168.8.36 3
+192.168.8.35 4
+192.168.8.34 3
+192.168.8.33 0
+192.168.8.32 2
+192.168.8.31 0
+192.168.8.30 1
+192.168.8.29 2
+192.168.8.28 3
+192.168.8.27 4
+192.168.8.26 2
+192.168.8.25 1
+192.168.8.24 3
+192.168.8.23 3
+192.168.8.22 4
+192.168.8.21 0
+192.168.8.20 1
+192.168.8.19 2
+192.168.8.18 4
+192.168.8.17 0
+192.168.8.16 4
+192.168.8.15 0
+192.168.8.14 1
+192.168.8.13 2
+192.168.8.12 3
+192.168.8.11 4
+192.168.8.10 1
+192.168.8.9 2
+192.168.8.8 4
+192.168.8.7 0
+192.168.8.6 1
+192.168.8.5 2
+192.168.8.4 3
+192.168.8.3 4
+192.168.8.2 3
+192.168.8.1 0
+192.168.7.90 0
+192.168.7.89 1
+192.168.7.88 2
+192.168.7.87 3
+192.168.7.86 4
+192.168.7.85 0
+192.168.7.84 1
+192.168.7.83 2
+192.168.7.82 3
+192.168.7.81 4
+192.168.7.80 1
+192.168.7.79 0
+192.168.7.78 1
+192.168.7.77 2
+192.168.7.76 3
+192.168.7.75 4
+192.168.7.74 2
+192.168.7.73 3
+192.168.7.72 0
+192.168.7.71 3
+192.168.7.70 4
+192.168.7.69 0
+192.168.7.68 1
+192.168.7.67 2
+192.168.7.66 4
+192.168.7.65 1
+192.168.7.64 3
+192.168.7.63 0
+192.168.7.62 1
+192.168.7.61 2
+192.168.7.60 3
+192.168.7.59 4
+192.168.7.58 2
+192.168.7.57 0
+192.168.7.56 1
+192.168.7.55 0
+192.168.7.54 1
+192.168.7.53 2
+192.168.7.52 3
+192.168.7.51 4
+192.168.7.50 3
+192.168.7.49 4
+192.168.7.48 2
+192.168.7.47 0
+192.168.7.46 1
+192.168.7.45 2
+192.168.7.44 3
+192.168.7.43 4
+192.168.7.42 2
+192.168.7.41 0
+192.168.7.40 1
+192.168.7.39 4
+192.168.7.38 0
+192.168.7.37 1
+192.168.7.36 2
+192.168.7.35 3
+192.168.7.34 4
+192.168.7.33 3
+192.168.7.32 0
+192.168.7.31 0
+192.168.7.30 1
+192.168.7.29 2
+192.168.7.28 3
+192.168.7.27 4
+192.168.7.26 2
+192.168.7.25 0
+192.168.7.24 1
+192.168.7.23 3
+192.168.7.22 4
+192.168.7.21 0
+192.168.7.20 1
+192.168.7.19 2
+192.168.7.18 4
+192.168.7.17 3
+192.168.7.16 4
+192.168.7.15 0
+192.168.7.14 1
+192.168.7.13 2
+192.168.7.12 3
+192.168.7.11 4
+192.168.7.10 3
+192.168.7.9 2
+192.168.7.8 0
+192.168.7.7 2
+192.168.7.6 4
+192.168.7.5 0
+192.168.7.4 1
+192.168.7.3 3
+192.168.7.2 4
+192.168.7.1 1
+192.168.6.90 0
+192.168.6.89 1
+192.168.6.88 2
+192.168.6.87 3
+192.168.6.86 4
+192.168.6.85 0
+192.168.6.84 1
+192.168.6.83 2
+192.168.6.82 4
+192.168.6.81 3
+192.168.6.80 0
+192.168.6.79 0
+192.168.6.78 1
+192.168.6.77 2
+192.168.6.76 3
+192.168.6.75 4
+192.168.6.74 2
+192.168.6.73 3
+192.168.6.72 1
+192.168.6.71 3
+192.168.6.70 4
+192.168.6.69 0
+192.168.6.68 1
+192.168.6.67 2
+192.168.6.66 4
+192.168.6.65 0
+192.168.6.64 1
+192.168.6.63 0
+192.168.6.62 1
+192.168.6.61 2
+192.168.6.60 3
+192.168.6.59 4
+192.168.6.58 2
+192.168.6.57 3
+192.168.6.56 0
+192.168.6.55 3
+192.168.6.54 4
+192.168.6.53 1
+192.168.6.52 2
+192.168.6.51 0
+192.168.6.50 4
+192.168.6.49 1
+192.168.6.48 2
+192.168.6.47 0
+192.168.6.46 1
+192.168.6.45 2
+192.168.6.44 3
+192.168.6.43 4
+192.168.6.42 2
+192.168.6.41 4
+192.168.6.40 3
+192.168.6.39 0
+192.168.6.38 1
+192.168.6.37 2
+192.168.6.36 3
+192.168.6.35 4
+192.168.6.34 0
+192.168.6.33 1
+192.168.6.32 4
+192.168.6.31 0
+192.168.6.30 1
+192.168.6.29 2
+192.168.6.28 3
+192.168.6.27 4
+192.168.6.26 2
+192.168.6.25 3
+192.168.6.24 0
+192.168.6.23 3
+192.168.6.22 4
+192.168.6.21 0
+192.168.6.20 1
+192.168.6.19 2
+192.168.6.18 4
+192.168.6.17 1
+192.168.6.16 3
+192.168.6.15 0
+192.168.6.14 1
+192.168.6.13 2
+192.168.6.12 3
+192.168.6.11 4
+192.168.6.10 2
+192.168.6.9 3
+192.168.6.8 4
+192.168.6.7 0
+192.168.6.6 1
+192.168.6.5 2
+192.168.6.4 3
+192.168.6.3 4
+192.168.6.2 0
+192.168.6.1 1
+192.168.5.90 0
+192.168.5.89 1
+192.168.5.88 2
+192.168.5.87 3
+192.168.5.86 4
+192.168.5.85 0
+192.168.5.84 1
+192.168.5.83 2
+192.168.5.82 4
+192.168.5.81 3
+192.168.5.80 0
+192.168.5.79 0
+192.168.5.78 1
+192.168.5.77 2
+192.168.5.76 3
+192.168.5.75 4
+192.168.5.74 2
+192.168.5.73 3
+192.168.5.72 1
+192.168.5.71 3
+192.168.5.70 4
+192.168.5.69 2
+192.168.5.68 0
+192.168.5.67 1
+192.168.5.66 4
+192.168.5.65 2
+192.168.5.64 0
+192.168.5.63 0
+192.168.5.62 1
+192.168.5.61 2
+192.168.5.60 3
+192.168.5.59 4
+192.168.5.58 1
+192.168.5.57 3
+192.168.5.56 2
+192.168.5.55 0
+192.168.5.54 1
+192.168.5.53 2
+192.168.5.52 3
+192.168.5.51 4
+192.168.5.50 0
+192.168.5.49 4
+192.168.5.48 1
+192.168.5.47 0
+192.168.5.46 1
+192.168.5.45 2
+192.168.5.44 3
+192.168.5.43 4
+192.168.5.42 1
+192.168.5.41 3
+192.168.5.40 2
+192.168.5.39 2
+192.168.5.38 3
+192.168.5.37 4
+192.168.5.36 0
+192.168.5.35 1
+192.168.5.34 4
+192.168.5.33 0
+192.168.5.32 4
+192.168.5.31 0
+192.168.5.30 1
+192.168.5.29 2
+192.168.5.28 3
+192.168.5.27 4
+192.168.5.26 1
+192.168.5.25 3
+192.168.5.24 2
+192.168.5.23 3
+192.168.5.22 4
+192.168.5.21 2
+192.168.5.20 0
+192.168.5.19 1
+192.168.5.18 4
+192.168.5.17 0
+192.168.5.16 3
+192.168.5.15 0
+192.168.5.14 1
+192.168.5.13 2
+192.168.5.12 3
+192.168.5.11 4
+192.168.5.10 1
+192.168.5.9 4
+192.168.5.8 3
+192.168.5.7 0
+192.168.5.6 1
+192.168.5.5 2
+192.168.5.4 3
+192.168.5.3 4
+192.168.5.2 2
+192.168.5.1 0
+192.168.4.90 0
+192.168.4.89 1
+192.168.4.88 2
+192.168.4.87 3
+192.168.4.86 4
+192.168.4.85 0
+192.168.4.84 1
+192.168.4.83 2
+192.168.4.82 3
+192.168.4.81 4
+192.168.4.80 0
+192.168.4.79 0
+192.168.4.78 1
+192.168.4.77 2
+192.168.4.76 3
+192.168.4.75 4
+192.168.4.74 1
+192.168.4.73 2
+192.168.4.72 3
+192.168.4.71 3
+192.168.4.70 4
+192.168.4.69 0
+192.168.4.68 1
+192.168.4.67 2
+192.168.4.66 4
+192.168.4.65 1
+192.168.4.64 3
+192.168.4.63 0
+192.168.4.62 1
+192.168.4.61 2
+192.168.4.60 3
+192.168.4.59 4
+192.168.4.58 0
+192.168.4.57 2
+192.168.4.56 1
+192.168.4.55 0
+192.168.4.54 1
+192.168.4.53 2
+192.168.4.52 3
+192.168.4.51 4
+192.168.4.50 3
+192.168.4.49 4
+192.168.4.48 0
+192.168.4.47 0
+192.168.4.46 1
+192.168.4.45 2
+192.168.4.44 3
+192.168.4.43 4
+192.168.4.42 2
+192.168.4.41 0
+192.168.4.40 1
+192.168.4.39 4
+192.168.4.38 0
+192.168.4.37 1
+192.168.4.36 2
+192.168.4.35 3
+192.168.4.34 4
+192.168.4.33 3
+192.168.4.32 2
+192.168.4.31 0
+192.168.4.30 1
+192.168.4.29 2
+192.168.4.28 3
+192.168.4.27 4
+192.168.4.26 0
+192.168.4.25 2
+192.168.4.24 1
+192.168.4.23 3
+192.168.4.22 4
+192.168.4.21 0
+192.168.4.20 1
+192.168.4.19 2
+192.168.4.18 4
+192.168.4.17 3
+192.168.4.16 1
+192.168.4.15 0
+192.168.4.14 1
+192.168.4.13 2
+192.168.4.12 3
+192.168.4.11 4
+192.168.4.10 3
+192.168.4.9 0
+192.168.4.8 2
+192.168.4.7 2
+192.168.4.6 3
+192.168.4.5 4
+192.168.4.4 0
+192.168.4.3 1
+192.168.4.2 4
+192.168.4.1 4
+192.168.3.90 0
+192.168.3.89 1
+192.168.3.88 2
+192.168.3.87 3
+192.168.3.86 4
+192.168.3.85 0
+192.168.3.84 1
+192.168.3.83 2
+192.168.3.82 3
+192.168.3.81 4
+192.168.3.80 0
+192.168.3.79 0
+192.168.3.78 1
+192.168.3.77 2
+192.168.3.76 3
+192.168.3.75 4
+192.168.3.74 1
+192.168.3.73 2
+192.168.3.72 3
+192.168.3.71 3
+192.168.3.70 4
+192.168.3.69 0
+192.168.3.68 1
+192.168.3.67 2
+192.168.3.66 4
+192.168.3.65 0
+192.168.3.64 3
+192.168.3.63 0
+192.168.3.62 1
+192.168.3.61 2
+192.168.3.60 3
+192.168.3.59 4
+192.168.3.58 2
+192.168.3.57 1
+192.168.3.56 3
+192.168.3.55 0
+192.168.3.54 1
+192.168.3.53 2
+192.168.3.52 3
+192.168.3.51 4
+192.168.3.50 0
+192.168.3.49 4
+192.168.3.48 2
+192.168.3.47 0
+192.168.3.46 1
+192.168.3.45 2
+192.168.3.44 3
+192.168.3.43 4
+192.168.3.42 2
+192.168.3.41 1
+192.168.3.40 0
+192.168.3.39 1
+192.168.3.38 2
+192.168.3.37 3
+192.168.3.36 4
+192.168.3.35 0
+192.168.3.34 4
+192.168.3.33 3
+192.168.3.32 4
+192.168.3.31 0
+192.168.3.30 1
+192.168.3.29 2
+192.168.3.28 3
+192.168.3.27 4
+192.168.3.26 2
+192.168.3.25 1
+192.168.3.24 0
+192.168.3.23 3
+192.168.3.22 4
+192.168.3.21 0
+192.168.3.20 1
+192.168.3.19 2
+192.168.3.18 4
+192.168.3.17 3
+192.168.3.16 1
+192.168.3.15 0
+192.168.3.14 1
+192.168.3.13 2
+192.168.3.12 3
+192.168.3.11 4
+192.168.3.10 2
+192.168.3.9 1
+192.168.3.8 0
+192.168.3.7 4
+192.168.3.6 0
+192.168.3.5 1
+192.168.3.4 2
+192.168.3.3 3
+192.168.3.2 4
+192.168.3.1 3
+192.168.2.90 0
+192.168.2.89 1
+192.168.2.88 2
+192.168.2.87 3
+192.168.2.86 4
+192.168.2.85 0
+192.168.2.84 1
+192.168.2.83 2
+192.168.2.82 3
+192.168.2.81 4
+192.168.2.80 1
+192.168.2.79 0
+192.168.2.78 1
+192.168.2.77 2
+192.168.2.76 3
+192.168.2.75 4
+192.168.2.74 2
+192.168.2.73 3
+192.168.2.72 0
+192.168.2.71 3
+192.168.2.70 4
+192.168.2.69 0
+192.168.2.68 1
+192.168.2.67 2
+192.168.2.66 4
+192.168.2.65 1
+192.168.2.64 3
+192.168.2.63 0
+192.168.2.62 1
+192.168.2.61 2
+192.168.2.60 3
+192.168.2.59 4
+192.168.2.58 0
+192.168.2.57 2
+192.168.2.56 1
+192.168.2.55 0
+192.168.2.54 1
+192.168.2.53 2
+192.168.2.52 3
+192.168.2.51 4
+192.168.2.50 3
+192.168.2.49 4
+192.168.2.48 0
+192.168.2.47 0
+192.168.2.46 1
+192.168.2.45 2
+192.168.2.44 3
+192.168.2.43 4
+192.168.2.42 2
+192.168.2.41 0
+192.168.2.40 1
+192.168.2.39 0
+192.168.2.38 1
+192.168.2.37 2
+192.168.2.36 3
+192.168.2.35 4
+192.168.2.34 3
+192.168.2.33 4
+192.168.2.32 2
+192.168.2.31 0
+192.168.2.30 1
+192.168.2.29 2
+192.168.2.28 3
+192.168.2.27 4
+192.168.2.26 2
+192.168.2.25 0
+192.168.2.24 1
+192.168.2.23 3
+192.168.2.22 4
+192.168.2.21 0
+192.168.2.20 1
+192.168.2.19 2
+192.168.2.18 4
+192.168.2.17 3
+192.168.2.16 4
+192.168.2.15 0
+192.168.2.14 1
+192.168.2.13 2
+192.168.2.12 3
+192.168.2.11 4
+192.168.2.10 0
+192.168.2.9 2
+192.168.2.8 3
+192.168.2.7 2
+192.168.2.6 4
+192.168.2.5 0
+192.168.2.4 1
+192.168.2.3 3
+192.168.2.2 4
+192.168.2.1 1
+192.168.1.90 0
+192.168.1.89 1
+192.168.1.88 2
+192.168.1.87 3
+192.168.1.86 4
+192.168.1.85 0
+192.168.1.84 1
+192.168.1.83 2
+192.168.1.82 3
+192.168.1.81 4
+192.168.1.80 0
+192.168.1.79 0
+192.168.1.78 1
+192.168.1.77 2
+192.168.1.76 3
+192.168.1.75 4
+192.168.1.74 1
+192.168.1.73 2
+192.168.1.72 3
+192.168.1.71 3
+192.168.1.70 4
+192.168.1.69 0
+192.168.1.68 1
+192.168.1.67 2
+192.168.1.66 4
+192.168.1.65 0
+192.168.1.64 1
+192.168.1.63 0
+192.168.1.62 1
+192.168.1.61 2
+192.168.1.60 3
+192.168.1.59 4
+192.168.1.58 2
+192.168.1.57 3
+192.168.1.56 1
+192.168.1.55 0
+192.168.1.54 1
+192.168.1.53 2
+192.168.1.52 3
+192.168.1.51 4
+192.168.1.50 0
+192.168.1.49 4
+192.168.1.48 2
+192.168.1.47 0
+192.168.1.46 1
+192.168.1.45 2
+192.168.1.44 3
+192.168.1.43 4
+192.168.1.42 2
+192.168.1.41 3
+192.168.1.40 0
+192.168.1.39 3
+192.168.1.38 4
+192.168.1.37 0
+192.168.1.36 1
+192.168.1.35 2
+192.168.1.34 4
+192.168.1.33 1
+192.168.1.32 3
+192.168.1.31 0
+192.168.1.30 1
+192.168.1.29 2
+192.168.1.28 3
+192.168.1.27 4
+192.168.1.26 2
+192.168.1.25 3
+192.168.1.24 0
+192.168.1.23 3
+192.168.1.22 4
+192.168.1.21 0
+192.168.1.20 1
+192.168.1.19 2
+192.168.1.18 4
+192.168.1.17 1
+192.168.1.16 4
+192.168.1.15 0
+192.168.1.14 1
+192.168.1.13 2
+192.168.1.12 3
+192.168.1.11 4
+192.168.1.10 2
+192.168.1.9 3
+192.168.1.8 0
+192.168.1.7 3
+192.168.1.6 4
+192.168.1.5 0
+192.168.1.4 1
+192.168.1.3 2
+192.168.1.2 4
+192.168.1.1 1
+EOF
+
+simple_test 0,0,0,0,0 <<EOF
+192.168.1.1 -1
+192.168.1.2 -1
+192.168.1.3 -1
+192.168.1.4 -1
+192.168.1.5 -1
+192.168.1.6 -1
+192.168.1.7 -1
+192.168.1.8 -1
+192.168.1.9 -1
+192.168.1.10 -1
+192.168.1.11 -1
+192.168.1.12 -1
+192.168.1.13 -1
+192.168.1.14 -1
+192.168.1.15 -1
+192.168.1.16 -1
+192.168.1.17 -1
+192.168.1.18 -1
+192.168.1.19 -1
+192.168.1.20 -1
+192.168.1.21 -1
+192.168.1.22 -1
+192.168.1.23 -1
+192.168.1.24 -1
+192.168.1.25 -1
+192.168.1.26 -1
+192.168.1.27 -1
+192.168.1.28 -1
+192.168.1.29 -1
+192.168.1.30 -1
+192.168.1.31 -1
+192.168.1.32 -1
+192.168.1.33 -1
+192.168.1.34 -1
+192.168.1.35 -1
+192.168.1.36 -1
+192.168.1.37 -1
+192.168.1.38 -1
+192.168.1.39 -1
+192.168.1.40 -1
+192.168.1.41 -1
+192.168.1.42 -1
+192.168.1.43 -1
+192.168.1.44 -1
+192.168.1.45 -1
+192.168.1.46 -1
+192.168.1.47 -1
+192.168.1.48 -1
+192.168.1.49 -1
+192.168.1.50 -1
+192.168.1.51 -1
+192.168.1.52 -1
+192.168.1.53 -1
+192.168.1.54 -1
+192.168.1.55 -1
+192.168.1.56 -1
+192.168.1.57 -1
+192.168.1.58 -1
+192.168.1.59 -1
+192.168.1.60 -1
+192.168.1.61 -1
+192.168.1.62 -1
+192.168.1.63 -1
+192.168.1.64 -1
+192.168.1.65 -1
+192.168.1.66 -1
+192.168.1.67 -1
+192.168.1.68 -1
+192.168.1.69 -1
+192.168.1.70 -1
+192.168.1.71 -1
+192.168.1.72 -1
+192.168.1.73 -1
+192.168.1.74 -1
+192.168.1.75 -1
+192.168.1.76 -1
+192.168.1.77 -1
+192.168.1.78 -1
+192.168.1.79 -1
+192.168.1.80 -1
+192.168.1.81 -1
+192.168.1.82 -1
+192.168.1.83 -1
+192.168.1.84 -1
+192.168.1.85 -1
+192.168.1.86 -1
+192.168.1.87 -1
+192.168.1.88 -1
+192.168.1.89 -1
+192.168.1.90 -1
+192.168.2.1 -1
+192.168.2.2 -1
+192.168.2.3 -1
+192.168.2.4 -1
+192.168.2.5 -1
+192.168.2.6 -1
+192.168.2.7 -1
+192.168.2.8 -1
+192.168.2.9 -1
+192.168.2.10 -1
+192.168.2.11 -1
+192.168.2.12 -1
+192.168.2.13 -1
+192.168.2.14 -1
+192.168.2.15 -1
+192.168.2.16 -1
+192.168.2.17 -1
+192.168.2.18 -1
+192.168.2.19 -1
+192.168.2.20 -1
+192.168.2.21 -1
+192.168.2.22 -1
+192.168.2.23 -1
+192.168.2.24 -1
+192.168.2.25 -1
+192.168.2.26 -1
+192.168.2.27 -1
+192.168.2.28 -1
+192.168.2.29 -1
+192.168.2.30 -1
+192.168.2.31 -1
+192.168.2.32 -1
+192.168.2.33 -1
+192.168.2.34 -1
+192.168.2.35 -1
+192.168.2.36 -1
+192.168.2.37 -1
+192.168.2.38 -1
+192.168.2.39 -1
+192.168.2.40 -1
+192.168.2.41 -1
+192.168.2.42 -1
+192.168.2.43 -1
+192.168.2.44 -1
+192.168.2.45 -1
+192.168.2.46 -1
+192.168.2.47 -1
+192.168.2.48 -1
+192.168.2.49 -1
+192.168.2.50 -1
+192.168.2.51 -1
+192.168.2.52 -1
+192.168.2.53 -1
+192.168.2.54 -1
+192.168.2.55 -1
+192.168.2.56 -1
+192.168.2.57 -1
+192.168.2.58 -1
+192.168.2.59 -1
+192.168.2.60 -1
+192.168.2.61 -1
+192.168.2.62 -1
+192.168.2.63 -1
+192.168.2.64 -1
+192.168.2.65 -1
+192.168.2.66 -1
+192.168.2.67 -1
+192.168.2.68 -1
+192.168.2.69 -1
+192.168.2.70 -1
+192.168.2.71 -1
+192.168.2.72 -1
+192.168.2.73 -1
+192.168.2.74 -1
+192.168.2.75 -1
+192.168.2.76 -1
+192.168.2.77 -1
+192.168.2.78 -1
+192.168.2.79 -1
+192.168.2.80 -1
+192.168.2.81 -1
+192.168.2.82 -1
+192.168.2.83 -1
+192.168.2.84 -1
+192.168.2.85 -1
+192.168.2.86 -1
+192.168.2.87 -1
+192.168.2.88 -1
+192.168.2.89 -1
+192.168.2.90 -1
+192.168.3.1 -1
+192.168.3.2 -1
+192.168.3.3 -1
+192.168.3.4 -1
+192.168.3.5 -1
+192.168.3.6 -1
+192.168.3.7 -1
+192.168.3.8 -1
+192.168.3.9 -1
+192.168.3.10 -1
+192.168.3.11 -1
+192.168.3.12 -1
+192.168.3.13 -1
+192.168.3.14 -1
+192.168.3.15 -1
+192.168.3.16 -1
+192.168.3.17 -1
+192.168.3.18 -1
+192.168.3.19 -1
+192.168.3.20 -1
+192.168.3.21 -1
+192.168.3.22 -1
+192.168.3.23 -1
+192.168.3.24 -1
+192.168.3.25 -1
+192.168.3.26 -1
+192.168.3.27 -1
+192.168.3.28 -1
+192.168.3.29 -1
+192.168.3.30 -1
+192.168.3.31 -1
+192.168.3.32 -1
+192.168.3.33 -1
+192.168.3.34 -1
+192.168.3.35 -1
+192.168.3.36 -1
+192.168.3.37 -1
+192.168.3.38 -1
+192.168.3.39 -1
+192.168.3.40 -1
+192.168.3.41 -1
+192.168.3.42 -1
+192.168.3.43 -1
+192.168.3.44 -1
+192.168.3.45 -1
+192.168.3.46 -1
+192.168.3.47 -1
+192.168.3.48 -1
+192.168.3.49 -1
+192.168.3.50 -1
+192.168.3.51 -1
+192.168.3.52 -1
+192.168.3.53 -1
+192.168.3.54 -1
+192.168.3.55 -1
+192.168.3.56 -1
+192.168.3.57 -1
+192.168.3.58 -1
+192.168.3.59 -1
+192.168.3.60 -1
+192.168.3.61 -1
+192.168.3.62 -1
+192.168.3.63 -1
+192.168.3.64 -1
+192.168.3.65 -1
+192.168.3.66 -1
+192.168.3.67 -1
+192.168.3.68 -1
+192.168.3.69 -1
+192.168.3.70 -1
+192.168.3.71 -1
+192.168.3.72 -1
+192.168.3.73 -1
+192.168.3.74 -1
+192.168.3.75 -1
+192.168.3.76 -1
+192.168.3.77 -1
+192.168.3.78 -1
+192.168.3.79 -1
+192.168.3.80 -1
+192.168.3.81 -1
+192.168.3.82 -1
+192.168.3.83 -1
+192.168.3.84 -1
+192.168.3.85 -1
+192.168.3.86 -1
+192.168.3.87 -1
+192.168.3.88 -1
+192.168.3.89 -1
+192.168.3.90 -1
+192.168.4.1 -1
+192.168.4.2 -1
+192.168.4.3 -1
+192.168.4.4 -1
+192.168.4.5 -1
+192.168.4.6 -1
+192.168.4.7 -1
+192.168.4.8 -1
+192.168.4.9 -1
+192.168.4.10 -1
+192.168.4.11 -1
+192.168.4.12 -1
+192.168.4.13 -1
+192.168.4.14 -1
+192.168.4.15 -1
+192.168.4.16 -1
+192.168.4.17 -1
+192.168.4.18 -1
+192.168.4.19 -1
+192.168.4.20 -1
+192.168.4.21 -1
+192.168.4.22 -1
+192.168.4.23 -1
+192.168.4.24 -1
+192.168.4.25 -1
+192.168.4.26 -1
+192.168.4.27 -1
+192.168.4.28 -1
+192.168.4.29 -1
+192.168.4.30 -1
+192.168.4.31 -1
+192.168.4.32 -1
+192.168.4.33 -1
+192.168.4.34 -1
+192.168.4.35 -1
+192.168.4.36 -1
+192.168.4.37 -1
+192.168.4.38 -1
+192.168.4.39 -1
+192.168.4.40 -1
+192.168.4.41 -1
+192.168.4.42 -1
+192.168.4.43 -1
+192.168.4.44 -1
+192.168.4.45 -1
+192.168.4.46 -1
+192.168.4.47 -1
+192.168.4.48 -1
+192.168.4.49 -1
+192.168.4.50 -1
+192.168.4.51 -1
+192.168.4.52 -1
+192.168.4.53 -1
+192.168.4.54 -1
+192.168.4.55 -1
+192.168.4.56 -1
+192.168.4.57 -1
+192.168.4.58 -1
+192.168.4.59 -1
+192.168.4.60 -1
+192.168.4.61 -1
+192.168.4.62 -1
+192.168.4.63 -1
+192.168.4.64 -1
+192.168.4.65 -1
+192.168.4.66 -1
+192.168.4.67 -1
+192.168.4.68 -1
+192.168.4.69 -1
+192.168.4.70 -1
+192.168.4.71 -1
+192.168.4.72 -1
+192.168.4.73 -1
+192.168.4.74 -1
+192.168.4.75 -1
+192.168.4.76 -1
+192.168.4.77 -1
+192.168.4.78 -1
+192.168.4.79 -1
+192.168.4.80 -1
+192.168.4.81 -1
+192.168.4.82 -1
+192.168.4.83 -1
+192.168.4.84 -1
+192.168.4.85 -1
+192.168.4.86 -1
+192.168.4.87 -1
+192.168.4.88 -1
+192.168.4.89 -1
+192.168.4.90 -1
+192.168.5.1 -1
+192.168.5.2 -1
+192.168.5.3 -1
+192.168.5.4 -1
+192.168.5.5 -1
+192.168.5.6 -1
+192.168.5.7 -1
+192.168.5.8 -1
+192.168.5.9 -1
+192.168.5.10 -1
+192.168.5.11 -1
+192.168.5.12 -1
+192.168.5.13 -1
+192.168.5.14 -1
+192.168.5.15 -1
+192.168.5.16 -1
+192.168.5.17 -1
+192.168.5.18 -1
+192.168.5.19 -1
+192.168.5.20 -1
+192.168.5.21 -1
+192.168.5.22 -1
+192.168.5.23 -1
+192.168.5.24 -1
+192.168.5.25 -1
+192.168.5.26 -1
+192.168.5.27 -1
+192.168.5.28 -1
+192.168.5.29 -1
+192.168.5.30 -1
+192.168.5.31 -1
+192.168.5.32 -1
+192.168.5.33 -1
+192.168.5.34 -1
+192.168.5.35 -1
+192.168.5.36 -1
+192.168.5.37 -1
+192.168.5.38 -1
+192.168.5.39 -1
+192.168.5.40 -1
+192.168.5.41 -1
+192.168.5.42 -1
+192.168.5.43 -1
+192.168.5.44 -1
+192.168.5.45 -1
+192.168.5.46 -1
+192.168.5.47 -1
+192.168.5.48 -1
+192.168.5.49 -1
+192.168.5.50 -1
+192.168.5.51 -1
+192.168.5.52 -1
+192.168.5.53 -1
+192.168.5.54 -1
+192.168.5.55 -1
+192.168.5.56 -1
+192.168.5.57 -1
+192.168.5.58 -1
+192.168.5.59 -1
+192.168.5.60 -1
+192.168.5.61 -1
+192.168.5.62 -1
+192.168.5.63 -1
+192.168.5.64 -1
+192.168.5.65 -1
+192.168.5.66 -1
+192.168.5.67 -1
+192.168.5.68 -1
+192.168.5.69 -1
+192.168.5.70 -1
+192.168.5.71 -1
+192.168.5.72 -1
+192.168.5.73 -1
+192.168.5.74 -1
+192.168.5.75 -1
+192.168.5.76 -1
+192.168.5.77 -1
+192.168.5.78 -1
+192.168.5.79 -1
+192.168.5.80 -1
+192.168.5.81 -1
+192.168.5.82 -1
+192.168.5.83 -1
+192.168.5.84 -1
+192.168.5.85 -1
+192.168.5.86 -1
+192.168.5.87 -1
+192.168.5.88 -1
+192.168.5.89 -1
+192.168.5.90 -1
+192.168.6.1 -1
+192.168.6.2 -1
+192.168.6.3 -1
+192.168.6.4 -1
+192.168.6.5 -1
+192.168.6.6 -1
+192.168.6.7 -1
+192.168.6.8 -1
+192.168.6.9 -1
+192.168.6.10 -1
+192.168.6.11 -1
+192.168.6.12 -1
+192.168.6.13 -1
+192.168.6.14 -1
+192.168.6.15 -1
+192.168.6.16 -1
+192.168.6.17 -1
+192.168.6.18 -1
+192.168.6.19 -1
+192.168.6.20 -1
+192.168.6.21 -1
+192.168.6.22 -1
+192.168.6.23 -1
+192.168.6.24 -1
+192.168.6.25 -1
+192.168.6.26 -1
+192.168.6.27 -1
+192.168.6.28 -1
+192.168.6.29 -1
+192.168.6.30 -1
+192.168.6.31 -1
+192.168.6.32 -1
+192.168.6.33 -1
+192.168.6.34 -1
+192.168.6.35 -1
+192.168.6.36 -1
+192.168.6.37 -1
+192.168.6.38 -1
+192.168.6.39 -1
+192.168.6.40 -1
+192.168.6.41 -1
+192.168.6.42 -1
+192.168.6.43 -1
+192.168.6.44 -1
+192.168.6.45 -1
+192.168.6.46 -1
+192.168.6.47 -1
+192.168.6.48 -1
+192.168.6.49 -1
+192.168.6.50 -1
+192.168.6.51 -1
+192.168.6.52 -1
+192.168.6.53 -1
+192.168.6.54 -1
+192.168.6.55 -1
+192.168.6.56 -1
+192.168.6.57 -1
+192.168.6.58 -1
+192.168.6.59 -1
+192.168.6.60 -1
+192.168.6.61 -1
+192.168.6.62 -1
+192.168.6.63 -1
+192.168.6.64 -1
+192.168.6.65 -1
+192.168.6.66 -1
+192.168.6.67 -1
+192.168.6.68 -1
+192.168.6.69 -1
+192.168.6.70 -1
+192.168.6.71 -1
+192.168.6.72 -1
+192.168.6.73 -1
+192.168.6.74 -1
+192.168.6.75 -1
+192.168.6.76 -1
+192.168.6.77 -1
+192.168.6.78 -1
+192.168.6.79 -1
+192.168.6.80 -1
+192.168.6.81 -1
+192.168.6.82 -1
+192.168.6.83 -1
+192.168.6.84 -1
+192.168.6.85 -1
+192.168.6.86 -1
+192.168.6.87 -1
+192.168.6.88 -1
+192.168.6.89 -1
+192.168.6.90 -1
+192.168.7.1 -1
+192.168.7.2 -1
+192.168.7.3 -1
+192.168.7.4 -1
+192.168.7.5 -1
+192.168.7.6 -1
+192.168.7.7 -1
+192.168.7.8 -1
+192.168.7.9 -1
+192.168.7.10 -1
+192.168.7.11 -1
+192.168.7.12 -1
+192.168.7.13 -1
+192.168.7.14 -1
+192.168.7.15 -1
+192.168.7.16 -1
+192.168.7.17 -1
+192.168.7.18 -1
+192.168.7.19 -1
+192.168.7.20 -1
+192.168.7.21 -1
+192.168.7.22 -1
+192.168.7.23 -1
+192.168.7.24 -1
+192.168.7.25 -1
+192.168.7.26 -1
+192.168.7.27 -1
+192.168.7.28 -1
+192.168.7.29 -1
+192.168.7.30 -1
+192.168.7.31 -1
+192.168.7.32 -1
+192.168.7.33 -1
+192.168.7.34 -1
+192.168.7.35 -1
+192.168.7.36 -1
+192.168.7.37 -1
+192.168.7.38 -1
+192.168.7.39 -1
+192.168.7.40 -1
+192.168.7.41 -1
+192.168.7.42 -1
+192.168.7.43 -1
+192.168.7.44 -1
+192.168.7.45 -1
+192.168.7.46 -1
+192.168.7.47 -1
+192.168.7.48 -1
+192.168.7.49 -1
+192.168.7.50 -1
+192.168.7.51 -1
+192.168.7.52 -1
+192.168.7.53 -1
+192.168.7.54 -1
+192.168.7.55 -1
+192.168.7.56 -1
+192.168.7.57 -1
+192.168.7.58 -1
+192.168.7.59 -1
+192.168.7.60 -1
+192.168.7.61 -1
+192.168.7.62 -1
+192.168.7.63 -1
+192.168.7.64 -1
+192.168.7.65 -1
+192.168.7.66 -1
+192.168.7.67 -1
+192.168.7.68 -1
+192.168.7.69 -1
+192.168.7.70 -1
+192.168.7.71 -1
+192.168.7.72 -1
+192.168.7.73 -1
+192.168.7.74 -1
+192.168.7.75 -1
+192.168.7.76 -1
+192.168.7.77 -1
+192.168.7.78 -1
+192.168.7.79 -1
+192.168.7.80 -1
+192.168.7.81 -1
+192.168.7.82 -1
+192.168.7.83 -1
+192.168.7.84 -1
+192.168.7.85 -1
+192.168.7.86 -1
+192.168.7.87 -1
+192.168.7.88 -1
+192.168.7.89 -1
+192.168.7.90 -1
+192.168.8.1 -1
+192.168.8.2 -1
+192.168.8.3 -1
+192.168.8.4 -1
+192.168.8.5 -1
+192.168.8.6 -1
+192.168.8.7 -1
+192.168.8.8 -1
+192.168.8.9 -1
+192.168.8.10 -1
+192.168.8.11 -1
+192.168.8.12 -1
+192.168.8.13 -1
+192.168.8.14 -1
+192.168.8.15 -1
+192.168.8.16 -1
+192.168.8.17 -1
+192.168.8.18 -1
+192.168.8.19 -1
+192.168.8.20 -1
+192.168.8.21 -1
+192.168.8.22 -1
+192.168.8.23 -1
+192.168.8.24 -1
+192.168.8.25 -1
+192.168.8.26 -1
+192.168.8.27 -1
+192.168.8.28 -1
+192.168.8.29 -1
+192.168.8.30 -1
+192.168.8.31 -1
+192.168.8.32 -1
+192.168.8.33 -1
+192.168.8.34 -1
+192.168.8.35 -1
+192.168.8.36 -1
+192.168.8.37 -1
+192.168.8.38 -1
+192.168.8.39 -1
+192.168.8.40 -1
+192.168.8.41 -1
+192.168.8.42 -1
+192.168.8.43 -1
+192.168.8.44 -1
+192.168.8.45 -1
+192.168.8.46 -1
+192.168.8.47 -1
+192.168.8.48 -1
+192.168.8.49 -1
+192.168.8.50 -1
+192.168.8.51 -1
+192.168.8.52 -1
+192.168.8.53 -1
+192.168.8.54 -1
+192.168.8.55 -1
+192.168.8.56 -1
+192.168.8.57 -1
+192.168.8.58 -1
+192.168.8.59 -1
+192.168.8.60 -1
+192.168.8.61 -1
+192.168.8.62 -1
+192.168.8.63 -1
+192.168.8.64 -1
+192.168.8.65 -1
+192.168.8.66 -1
+192.168.8.67 -1
+192.168.8.68 -1
+192.168.8.69 -1
+192.168.8.70 -1
+192.168.8.71 -1
+192.168.8.72 -1
+192.168.8.73 -1
+192.168.8.74 -1
+192.168.8.75 -1
+192.168.8.76 -1
+192.168.8.77 -1
+192.168.8.78 -1
+192.168.8.79 -1
+192.168.8.80 -1
+192.168.8.81 -1
+192.168.8.82 -1
+192.168.8.83 -1
+192.168.8.84 -1
+192.168.8.85 -1
+192.168.8.86 -1
+192.168.8.87 -1
+192.168.8.88 -1
+192.168.8.89 -1
+192.168.8.90 -1
+192.168.9.1 -1
+192.168.9.2 -1
+192.168.9.3 -1
+192.168.9.4 -1
+192.168.9.5 -1
+192.168.9.6 -1
+192.168.9.7 -1
+192.168.9.8 -1
+192.168.9.9 -1
+192.168.9.10 -1
+192.168.9.11 -1
+192.168.9.12 -1
+192.168.9.13 -1
+192.168.9.14 -1
+192.168.9.15 -1
+192.168.9.16 -1
+192.168.9.17 -1
+192.168.9.18 -1
+192.168.9.19 -1
+192.168.9.20 -1
+192.168.9.21 -1
+192.168.9.22 -1
+192.168.9.23 -1
+192.168.9.24 -1
+192.168.9.25 -1
+192.168.9.26 -1
+192.168.9.27 -1
+192.168.9.28 -1
+192.168.9.29 -1
+192.168.9.30 -1
+192.168.9.31 -1
+192.168.9.32 -1
+192.168.9.33 -1
+192.168.9.34 -1
+192.168.9.35 -1
+192.168.9.36 -1
+192.168.9.37 -1
+192.168.9.38 -1
+192.168.9.39 -1
+192.168.9.40 -1
+192.168.9.41 -1
+192.168.9.42 -1
+192.168.9.43 -1
+192.168.9.44 -1
+192.168.9.45 -1
+192.168.9.46 -1
+192.168.9.47 -1
+192.168.9.48 -1
+192.168.9.49 -1
+192.168.9.50 -1
+192.168.9.51 -1
+192.168.9.52 -1
+192.168.9.53 -1
+192.168.9.54 -1
+192.168.9.55 -1
+192.168.9.56 -1
+192.168.9.57 -1
+192.168.9.58 -1
+192.168.9.59 -1
+192.168.9.60 -1
+192.168.9.61 -1
+192.168.9.62 -1
+192.168.9.63 -1
+192.168.9.64 -1
+192.168.9.65 -1
+192.168.9.66 -1
+192.168.9.67 -1
+192.168.9.68 -1
+192.168.9.69 -1
+192.168.9.70 -1
+192.168.9.71 -1
+192.168.9.72 -1
+192.168.9.73 -1
+192.168.9.74 -1
+192.168.9.75 -1
+192.168.9.76 -1
+192.168.9.77 -1
+192.168.9.78 -1
+192.168.9.79 -1
+192.168.9.80 -1
+192.168.9.81 -1
+192.168.9.82 -1
+192.168.9.83 -1
+192.168.9.84 -1
+192.168.9.85 -1
+192.168.9.86 -1
+192.168.9.87 -1
+192.168.9.88 -1
+192.168.9.89 -1
+192.168.9.90 -1
+192.168.10.1 -1
+192.168.10.2 -1
+192.168.10.3 -1
+192.168.10.4 -1
+192.168.10.5 -1
+192.168.10.6 -1
+192.168.10.7 -1
+192.168.10.8 -1
+192.168.10.9 -1
+192.168.10.10 -1
+192.168.10.11 -1
+192.168.10.12 -1
+192.168.10.13 -1
+192.168.10.14 -1
+192.168.10.15 -1
+192.168.10.16 -1
+192.168.10.17 -1
+192.168.10.18 -1
+192.168.10.19 -1
+192.168.10.20 -1
+192.168.10.21 -1
+192.168.10.22 -1
+192.168.10.23 -1
+192.168.10.24 -1
+192.168.10.25 -1
+192.168.10.26 -1
+192.168.10.27 -1
+192.168.10.28 -1
+192.168.10.29 -1
+192.168.10.30 -1
+192.168.10.31 -1
+192.168.10.32 -1
+192.168.10.33 -1
+192.168.10.34 -1
+192.168.10.35 -1
+192.168.10.36 -1
+192.168.10.37 -1
+192.168.10.38 -1
+192.168.10.39 -1
+192.168.10.40 -1
+192.168.10.41 -1
+192.168.10.42 -1
+192.168.10.43 -1
+192.168.10.44 -1
+192.168.10.45 -1
+192.168.10.46 -1
+192.168.10.47 -1
+192.168.10.48 -1
+192.168.10.49 -1
+192.168.10.50 -1
+192.168.10.51 -1
+192.168.10.52 -1
+192.168.10.53 -1
+192.168.10.54 -1
+192.168.10.55 -1
+192.168.10.56 -1
+192.168.10.57 -1
+192.168.10.58 -1
+192.168.10.59 -1
+192.168.10.60 -1
+192.168.10.61 -1
+192.168.10.62 -1
+192.168.10.63 -1
+192.168.10.64 -1
+192.168.10.65 -1
+192.168.10.66 -1
+192.168.10.67 -1
+192.168.10.68 -1
+192.168.10.69 -1
+192.168.10.70 -1
+192.168.10.71 -1
+192.168.10.72 -1
+192.168.10.73 -1
+192.168.10.74 -1
+192.168.10.75 -1
+192.168.10.76 -1
+192.168.10.77 -1
+192.168.10.78 -1
+192.168.10.79 -1
+192.168.10.80 -1
+192.168.10.81 -1
+192.168.10.82 -1
+192.168.10.83 -1
+192.168.10.84 -1
+192.168.10.85 -1
+192.168.10.86 -1
+192.168.10.87 -1
+192.168.10.88 -1
+192.168.10.89 -1
+192.168.10.90 -1
+EOF
diff --git a/tests/takeover/nondet.001.sh b/tests/takeover/nondet.001.sh
index 7150607..6f79c34 100755
--- a/tests/takeover/nondet.001.sh
+++ b/tests/takeover/nondet.001.sh
@@ -5,6 +5,12 @@
 define_test "3 nodes, 1 healthy"
 
 required_result <<EOF
+DATE TIME [PID]: Unassign IP: 192.168.21.253 from 1
+DATE TIME [PID]: Unassign IP: 192.168.21.252 from 0
+DATE TIME [PID]: Unassign IP: 192.168.20.253 from 1
+DATE TIME [PID]: Unassign IP: 192.168.20.252 from 0
+DATE TIME [PID]: Unassign IP: 192.168.20.250 from 1
+DATE TIME [PID]: Unassign IP: 192.168.20.249 from 0
 192.168.21.254 2
 192.168.21.253 2
 192.168.21.252 2
diff --git a/tests/takeover/nondet.002.sh b/tests/takeover/nondet.002.sh
index 4ff801b..c46f6a2 100755
--- a/tests/takeover/nondet.002.sh
+++ b/tests/takeover/nondet.002.sh
@@ -5,6 +5,9 @@
 define_test "3 nodes, 2 healthy"
 
 required_result <<EOF
+DATE TIME [PID]: Unassign IP: 192.168.21.253 from 1
+DATE TIME [PID]: Unassign IP: 192.168.20.253 from 1
+DATE TIME [PID]: Unassign IP: 192.168.20.250 from 1
 192.168.21.254 2
 192.168.21.253 0
 192.168.21.252 0
diff --git a/tests/takeover/scripts/local.sh b/tests/takeover/scripts/local.sh
index dc8c5e6..3b69d14 100644
--- a/tests/takeover/scripts/local.sh
+++ b/tests/takeover/scripts/local.sh
@@ -18,13 +18,9 @@ define_test ()
 simple_test ()
 {
     # Do some filtering of the output to replace date/time.
-    if [ \( "$CTDB_IP_ALGORITHM" = "lcp2" -a -n "$CTDB_TEST_LOGLEVEL" \) -o \
-	"$CTDB_IP_ALGORITHM" = "det" ] ; then
-	OUT_FILTER='s@^.*:@DATE\ TIME\ \[PID\]:@'
-    fi
+    OUT_FILTER='s@^[^\]]*\]:@DATE\ TIME\ \[PID\]:@'
 
-    _states="$1"
-    _out=$($VALGRIND $test_prog $_states 2>&1)
+    _out=$($VALGRIND $test_prog "$@" 2>&1)
 
     result_check "Algorithm: $CTDB_IP_ALGORITHM"
 }
diff --git a/tools/ctdb.c b/tools/ctdb.c
index 678b555..b3cbade 100644
--- a/tools/ctdb.c
+++ b/tools/ctdb.c
@@ -25,7 +25,7 @@
 #include "system/locale.h"
 #include "popt.h"
 #include "cmdline.h"
-#include "../include/version.h"
+#include "../include/ctdb_version.h"
 #include "../include/ctdb.h"
 #include "../include/ctdb_client.h"
 #include "../include/ctdb_private.h"
@@ -1594,13 +1594,88 @@ static int move_ip(struct ctdb_context *ctdb, ctdb_sock_addr *addr, uint32_t pnn
 	return 0;
 }
 
+
+/* 
+ * scans all other nodes and returns a pnn for another node that can host this 
+ * ip address or -1
+ */
+static int
+find_other_host_for_public_ip(struct ctdb_context *ctdb, ctdb_sock_addr *addr)
+{
+	TALLOC_CTX *tmp_ctx = talloc_new(ctdb);
+	struct ctdb_all_public_ips *ips;
+	struct ctdb_node_map *nodemap=NULL;
+	int i, j, ret;
+
+	ret = ctdb_ctrl_getnodemap(ctdb, TIMELIMIT(), CTDB_CURRENT_NODE, tmp_ctx, &nodemap);
+	if (ret != 0) {
+		DEBUG(DEBUG_ERR, ("Unable to get nodemap from node %u\n", options.pnn));
+		talloc_free(tmp_ctx);
+		return ret;
+	}
+
+	for(i=0;i<nodemap->num;i++){
+		if (nodemap->nodes[i].flags & NODE_FLAGS_INACTIVE) {
+			continue;
+		}
+		if (nodemap->nodes[i].pnn == options.pnn) {
+			continue;
+		}
+
+		/* read the public ip list from this node */
+		ret = ctdb_ctrl_get_public_ips(ctdb, TIMELIMIT(), nodemap->nodes[i].pnn, tmp_ctx, &ips);
+		if (ret != 0) {
+			DEBUG(DEBUG_ERR, ("Unable to get public ip list from node %u\n", nodemap->nodes[i].pnn));
+			return -1;
+		}
+
+		for (j=0;j<ips->num;j++) {
+			if (ctdb_same_ip(addr, &ips->ips[j].addr)) {
+				talloc_free(tmp_ctx);
+				return nodemap->nodes[i].pnn;
+			}
+		}
+		talloc_free(ips);
+	}
+
+	talloc_free(tmp_ctx);
+	return -1;
+}
+
+/* If pnn is -1 then try to find a node to move IP to... */
+static bool try_moveip(struct ctdb_context *ctdb, ctdb_sock_addr *addr, uint32_t pnn)
+{
+	bool pnn_specified = (pnn == -1 ? false : true);
+	int retries = 0;
+
+	while (retries < 5) {
+		if (!pnn_specified) {
+			pnn = find_other_host_for_public_ip(ctdb, addr);
+			if (pnn == -1) {
+				return false;
+			}
+			DEBUG(DEBUG_NOTICE,
+			      ("Trying to move public IP to node %u\n", pnn));
+		}
+
+		if (move_ip(ctdb, addr, pnn) == 0) {
+			return true;
+		}
+
+		sleep(3);
+		retries++;
+	}
+
+	return false;
+}
+
+
 /*
   move/failover an ip address to a specific node
  */
 static int control_moveip(struct ctdb_context *ctdb, int argc, const char **argv)
 {
 	uint32_t pnn;
-	int ret, retries = 0;
 	ctdb_sock_addr addr;
 
 	if (argc < 2) {
@@ -1619,16 +1694,8 @@ static int control_moveip(struct ctdb_context *ctdb, int argc, const char **argv
 		return -1;
 	}
 
-	do {
-		ret = move_ip(ctdb, &addr, pnn);
-		if (ret != 0) {
-			DEBUG(DEBUG_ERR,("Failed to move ip to node %d. Wait 3 second and try again.\n", pnn));
-			sleep(3);
-			retries++;
-		}
-	} while (retries < 5 && ret != 0);
-	if (ret != 0) {
-		DEBUG(DEBUG_ERR,("Failed to move ip to node %d. Giving up.\n", pnn));
+	if (!try_moveip(ctdb, &addr, pnn)) {
+		DEBUG(DEBUG_ERR,("Failed to move IP to node %d.\n", pnn));
 		return -1;
 	}
 
@@ -1861,54 +1928,7 @@ control_get_all_public_ips(struct ctdb_context *ctdb, TALLOC_CTX *tmp_ctx, struc
 }
 
 
-/* 
- * scans all other nodes and returns a pnn for another node that can host this 
- * ip address or -1
- */
-static int
-find_other_host_for_public_ip(struct ctdb_context *ctdb, ctdb_sock_addr *addr)
-{
-	TALLOC_CTX *tmp_ctx = talloc_new(ctdb);
-	struct ctdb_all_public_ips *ips;
-	struct ctdb_node_map *nodemap=NULL;
-	int i, j, ret;
-
-	ret = ctdb_ctrl_getnodemap(ctdb, TIMELIMIT(), CTDB_CURRENT_NODE, tmp_ctx, &nodemap);
-	if (ret != 0) {
-		DEBUG(DEBUG_ERR, ("Unable to get nodemap from node %u\n", options.pnn));
-		talloc_free(tmp_ctx);
-		return ret;
-	}
-
-	for(i=0;i<nodemap->num;i++){
-		if (nodemap->nodes[i].flags & NODE_FLAGS_INACTIVE) {
-			continue;
-		}
-		if (nodemap->nodes[i].pnn == options.pnn) {
-			continue;
-		}
-
-		/* read the public ip list from this node */
-		ret = ctdb_ctrl_get_public_ips(ctdb, TIMELIMIT(), nodemap->nodes[i].pnn, tmp_ctx, &ips);
-		if (ret != 0) {
-			DEBUG(DEBUG_ERR, ("Unable to get public ip list from node %u\n", nodemap->nodes[i].pnn));
-			return -1;
-		}
-
-		for (j=0;j<ips->num;j++) {
-			if (ctdb_same_ip(addr, &ips->ips[j].addr)) {
-				talloc_free(tmp_ctx);
-				return nodemap->nodes[i].pnn;
-			}
-		}
-		talloc_free(ips);
-	}
-
-	talloc_free(tmp_ctx);
-	return -1;
-}
-
-static uint32_t ipreallocate_finished;
+static bool ipreallocate_finished;
 
 /*
   handler for receiving the response to ipreallocate
@@ -1916,7 +1936,7 @@ static uint32_t ipreallocate_finished;
 static void ip_reallocate_handler(struct ctdb_context *ctdb, uint64_t srvid, 
 			     TDB_DATA data, void *private_data)
 {
-	ipreallocate_finished = 1;
+	ipreallocate_finished = true;
 }
 
 static void ctdb_every_second(struct event_context *ev, struct timed_event *te, struct timeval t, void *p)
@@ -1936,9 +1956,8 @@ static int control_ipreallocate(struct ctdb_context *ctdb, int argc, const char
 	int i, ret;
 	TDB_DATA data;
 	struct takeover_run_reply rd;
-	uint32_t recmaster;
 	struct ctdb_node_map *nodemap=NULL;
-	int retries=0;
+	int count;
 	struct timeval tv = timeval_current();
 
 	/* we need some events to trigger so we can timeout and restart
@@ -1964,81 +1983,41 @@ static int control_ipreallocate(struct ctdb_context *ctdb, int argc, const char
 	data.dsize = sizeof(rd);
 
 again:
-	/* check that there are valid nodes available */
+	/* get the number of nodes and node flags */
 	if (ctdb_ctrl_getnodemap(ctdb, TIMELIMIT(), options.pnn, ctdb, &nodemap) != 0) {
 		DEBUG(DEBUG_ERR, ("Unable to get nodemap from local node\n"));
 		return -1;
 	}
-	for (i=0; i<nodemap->num;i++) {
-		if ((nodemap->nodes[i].flags & (NODE_FLAGS_DELETED|NODE_FLAGS_BANNED|NODE_FLAGS_STOPPED)) == 0) {
-			break;
-		}
-	}
-	if (i==nodemap->num) {
-		DEBUG(DEBUG_ERR,("No recmaster available, no need to wait for cluster convergence\n"));
-		return 0;
-	}
-
-
-	if (!ctdb_getrecmaster(ctdb_connection, options.pnn, &recmaster)) {
-		DEBUG(DEBUG_ERR, ("Unable to get recmaster from node %u\n", options.pnn));
-		return -1;
-	}
-
-	/* verify the node exists */
-	if (ctdb_ctrl_getnodemap(ctdb, TIMELIMIT(), recmaster, ctdb, &nodemap) != 0) {
-		DEBUG(DEBUG_ERR, ("Unable to get nodemap from local node\n"));
-		return -1;
-	}
 
-
-	/* check tha there are nodes available that can act as a recmaster */
-	for (i=0; i<nodemap->num; i++) {
-		if (nodemap->nodes[i].flags & (NODE_FLAGS_DELETED|NODE_FLAGS_BANNED|NODE_FLAGS_STOPPED)) {
+	ipreallocate_finished = false;
+	count = 0;
+	for (i=0; i<nodemap->num;i++) {
+		if (nodemap->nodes[i].flags & NODE_FLAGS_INACTIVE) {
 			continue;
+		} else {
+			/* Send to all active nodes. Only recmaster will reply. */
+			ret = ctdb_client_send_message(ctdb, i, CTDB_SRVID_TAKEOVER_RUN, data);
+			if (ret != 0) {
+				DEBUG(DEBUG_ERR,("Failed to send ip takeover run request message to %u\n", options.pnn));
+				return -1;
+			}
+			count++;
 		}
-		break;
 	}
-	if (i == nodemap->num) {
-		DEBUG(DEBUG_ERR,("No possible nodes to host addresses.\n"));
+	if (count == 0) {
+		DEBUG(DEBUG_ERR,("No recmaster available, no need to wait for cluster convergence\n"));
 		return 0;
 	}
 
-	/* verify the recovery master is not STOPPED, nor BANNED */
-	if (nodemap->nodes[recmaster].flags & (NODE_FLAGS_DELETED|NODE_FLAGS_BANNED|NODE_FLAGS_STOPPED)) {
-		DEBUG(DEBUG_ERR,("No suitable recmaster found. Try again\n"));
-		retries++;
-		sleep(1);
-		goto again;
-	} 
-	
-	/* verify the recovery master is not STOPPED, nor BANNED */
-	if (nodemap->nodes[recmaster].flags & (NODE_FLAGS_DELETED|NODE_FLAGS_BANNED|NODE_FLAGS_STOPPED)) {
-		DEBUG(DEBUG_ERR,("No suitable recmaster found. Try again\n"));
-		retries++;
-		sleep(1);
-		goto again;
-	} 
-
-	ipreallocate_finished = 0;
-	ret = ctdb_client_send_message(ctdb, recmaster, CTDB_SRVID_TAKEOVER_RUN, data);
-	if (ret != 0) {
-		DEBUG(DEBUG_ERR,("Failed to send ip takeover run request message to %u\n", options.pnn));
-		return -1;
-	}
-
 	tv = timeval_current();
 	/* this loop will terminate when we have received the reply */
-	while (timeval_elapsed(&tv) < 5.0 && ipreallocate_finished == 0) {
+	while (timeval_elapsed(&tv) < 5.0 && !ipreallocate_finished) {
 		event_loop_once(ctdb->ev);
 	}
-	if (ipreallocate_finished == 1) {
-		return 0;
-	}
 
-	retries++;
-	sleep(1);
-	goto again;
+	if (!ipreallocate_finished) {
+		goto again;
+	}
 
 	return 0;
 }
@@ -2220,7 +2199,6 @@ static int control_delip_all(struct ctdb_context *ctdb, int argc, const char **a
 static int control_delip(struct ctdb_context *ctdb, int argc, const char **argv)
 {
 	int i, ret;
-	int retries = 0;
 	ctdb_sock_addr addr;
 	struct ctdb_control_ip_iface pub;
 	TALLOC_CTX *tmp_ctx = talloc_new(ctdb);
@@ -2264,24 +2242,12 @@ static int control_delip(struct ctdb_context *ctdb, int argc, const char **argv)
 		return -1;
 	}
 
+	/* This is an optimisation.  If this node is hosting the IP
+	 * then try to move it somewhere else without invoking a full
+	 * takeover run.  We don't care if this doesn't work!
+	 */
 	if (ips->ips[i].pnn == options.pnn) {
-		int pnn;
-
-		pnn = find_other_host_for_public_ip(ctdb, &addr);
-		if (pnn != -1) {
-			do {
-				ret = move_ip(ctdb, &addr, pnn);
-				if (ret != 0) {
-					DEBUG(DEBUG_ERR,("Failed to move ip to node %d. Wait 3 seconds and try again.\n", options.pnn));
-					sleep(3);
-					retries++;
-				}
-			} while (retries < 5 && ret != 0);
-			if (ret != 0) {
-				DEBUG(DEBUG_ERR,("Failed to move ip to node %d. Giving up.\n", options.pnn));
-				return -1;
-			}
-		}
+		(void) try_moveip(ctdb, &addr, -1);
 	}
 
 	ret = ctdb_ctrl_del_public_ip(ctdb, TIMELIMIT(), options.pnn, &pub);
@@ -4407,6 +4373,49 @@ static int control_ping(struct ctdb_context *ctdb, int argc, const char **argv)
 
 
 /*
+  get a node's runstate
+ */
+static int control_runstate(struct ctdb_context *ctdb, int argc, const char **argv)
+{
+	int ret;
+	enum ctdb_runstate runstate;
+
+	ret = ctdb_ctrl_get_runstate(ctdb, TIMELIMIT(), options.pnn, &runstate);
+	if (ret == -1) {
+		printf("Unable to get runstate response from node %u\n",
+		       options.pnn);
+		return -1;
+	} else {
+		bool found = true;
+		enum ctdb_runstate t;
+		int i;
+		for (i=0; i<argc; i++) {
+			found = false;
+			t = runstate_from_string(argv[i]);
+			if (t == CTDB_RUNSTATE_UNKNOWN) {
+				printf("Invalid run state (%s)\n", argv[i]);
+				return -1;
+			}
+
+			if (t == runstate) {
+				found = true;
+				break;
+			}
+		}
+
+		if (!found) {
+			printf("CTDB not in required run state (got %s)\n", 
+			       runstate_to_string((enum ctdb_runstate)runstate));
+			return -1;
+		}
+	}
+
+	printf("%s\n", runstate_to_string(runstate));
+	return 0;
+}
+
+
+/*
   get a tunable
  */
 static int control_getvar(struct ctdb_context *ctdb, int argc, const char **argv)
@@ -4421,7 +4430,7 @@ static int control_getvar(struct ctdb_context *ctdb, int argc, const char **argv
 
 	name = argv[0];
 	ret = ctdb_ctrl_get_tunable(ctdb, TIMELIMIT(), options.pnn, name, &value);
-	if (ret == -1) {
+	if (ret != 0) {
 		DEBUG(DEBUG_ERR, ("Unable to get tunable variable '%s'\n", name));
 		return -1;
 	}
@@ -4935,7 +4944,7 @@ static int control_setdbseqnum(struct ctdb_context *ctdb, int argc, const char *
 	}
 
 	key.dptr  = (uint8_t *)discard_const(CTDB_DB_SEQNUM_KEY);
-	key.dsize = strlen(key.dptr) + 1;
+	key.dsize = strlen(CTDB_DB_SEQNUM_KEY) + 1;
 
 	data.dsize = sizeof(new_seqnum);
 	data.dptr = talloc_size(tmp_ctx, data.dsize);
@@ -5838,6 +5847,7 @@ static const struct {
 	{ "status",          control_status,            true,	false,  "show node status" },
 	{ "uptime",          control_uptime,            true,	false,  "show node uptime" },
 	{ "ping",            control_ping,              true,	false,  "ping all nodes" },
+	{ "runstate",        control_runstate,          true,	false,  "get/check runstate of a node", "[setup|first_recovery|startup|running]" },
 	{ "getvar",          control_getvar,            true,	false,  "get a tunable variable",               "<name>"},
 	{ "setvar",          control_setvar,            true,	false,  "set a tunable variable",               "<name> <value>"},
 	{ "listvars",        control_listvars,          true,	false,  "list tunable variables"},
@@ -5877,7 +5887,7 @@ static const struct {
 	{ "showban",         control_showban,           true,	false,  "show ban information"},
 	{ "shutdown",        control_shutdown,          true,	false,  "shutdown ctdbd" },
 	{ "recover",         control_recover,           true,	false,  "force recovery" },
-	{ "sync", 	     control_ipreallocate,      true,	false,  "wait until ctdbd has synced all state changes" },
+	{ "sync", 	     control_ipreallocate,      false,	false,  "wait until ctdbd has synced all state changes" },
 	{ "ipreallocate",    control_ipreallocate,      true,	false,  "force the recovery daemon to perform a ip reallocation procedure" },
 	{ "thaw",            control_thaw,              true,	false,  "thaw databases", "[priority:1-3]" },
 	{ "isnotrecmaster",  control_isnotrecmaster,    false,	false,  "check if the local node is recmaster or not" },
@@ -5924,7 +5934,6 @@ static const struct {
 	{ "setdbsticky",      control_setdbsticky,	false,	false, "Set DB sticky-records capable", "<dbname|dbid>"},
 	{ "msglisten",        control_msglisten,	false,	false, "Listen on a srvid port for messages", "<msg srvid>"},
 	{ "msgsend",          control_msgsend,	false,	false, "Send a message to srvid", "<srvid> <message>"},
-	{ "sync", 	     control_ipreallocate,      false,	false,  "wait until ctdbd has synced all state changes" },
 	{ "pfetch", 	     control_pfetch,      	false,	false,  "fetch a record from a persistent database", "<dbname|dbid> <key> [<file>]" },
 	{ "pstore", 	     control_pstore,      	false,	false,  "write a record to a persistent database", "<dbname|dbid> <key> <file containing record>" },
 	{ "pdelete", 	     control_pdelete,      	false,	false,  "delete a record from a persistent database", "<dbname|dbid> <key>" },
diff --git a/tools/ltdbtool.c b/tools/ltdbtool.c
index b7ad5a5..add9c32 100644
--- a/tools/ltdbtool.c
+++ b/tools/ltdbtool.c
@@ -77,7 +77,9 @@ static int help(const char* cmd)
 "   -O <num>        the number of bytes to interpret as ctdb record header\n"
 "                   for the output database (beware!)\n"
 "\n"
-"   -p              print header (for the dump command), defaults ot off\n"
+"   -e              Include empty records, defaults to off\n"
+"\n"
+"   -p              print header (for the dump command), defaults to off\n"
 "\n"
 "   -h              print this help\n"
 "\n"
@@ -91,8 +93,8 @@ static int help(const char* cmd)
 static int usage(const char* cmd)
 {
 	fprintf(stderr,
-		"Usage: %s dump [-p] [-s{0|32|64}] <idb>\n"
-		"       %s convert [-s{0|32|64}] [-o{0|32|64}] <idb> <odb>\n"
+		"Usage: %s dump [-e] [-p] [-s{0|32|64}] <idb>\n"
+		"       %s convert [-e] [-s{0|32|64}] [-o{0|32|64}] <idb> <odb>\n"
 		"       %s {help|-h}\n"
 		, cmd, cmd, cmd);
 	return -1;
@@ -229,6 +231,7 @@ int main(int argc, char* argv[])
 			break;
 		case 'e':
 			keep_empty = true;
+			break;
 		case 'h':
 			return help(argv[0]);
 		default:
diff --git a/utils/pmda/config.m4 b/utils/pmda/config.m4
new file mode 100644
index 0000000..6b3fbb0
--- /dev/null
+++ b/utils/pmda/config.m4
@@ -0,0 +1,32 @@
+AC_ARG_ENABLE(pmda, 
+AS_HELP_STRING([--enable-pmda], [Turn on PCP pmda support (default=no)]))
+
+HAVE_PMDA=no
+
+if eval "test x$enable_pmda = xyes"; then
+	HAVE_PMDA=yes
+
+	AC_CHECK_HEADERS(pcp/pmapi.h pcp/impl.h pcp/pmda.h, [],
+	[AC_MSG_ERROR([Missing PCP pmda headers])],
+	[[#ifdef HAVE_PCP_PMAPI_H
+	# include <pcp/pmapi.h>
+	#endif
+	#ifdef HAVE_PCP_IMPL_H
+	# include <pcp/impl.h>
+	#endif
+	#ifdef HAVE_PCP_PMDA_H
+	# include <pcp/pmda.h>
+	#endif
+	]])
+fi
+
+if test x"$HAVE_PMDA" = x"yes"; then
+    CTDB_PMDA=bin/pmdactdb
+    CTDB_PMDA_INSTALL=install_pmda
+else
+    CTDB_PMDA=
+    CTDB_PMDA_INSTALL=
+fi
+
+AC_SUBST(CTDB_PMDA)
+AC_SUBST(CTDB_PMDA_INSTALL)
diff --git a/utils/pmda/pmda_ctdb.c b/utils/pmda/pmda_ctdb.c
index c8983ef..e8033be 100644
--- a/utils/pmda/pmda_ctdb.c
+++ b/utils/pmda/pmda_ctdb.c
@@ -121,10 +121,10 @@ static pmdaMetric metrictab[] = {
 	/* pending_calls */
 	{ NULL, { PMDA_PMID(14,25), PM_TYPE_U32, PM_INDOM_NULL, PM_SEM_INSTANT,
 		PMDA_PMUNITS(0,0,0,0,0,0) }, },
-	/* lockwait_calls */
+	/* locks.num_calls */
 	{ NULL, { PMDA_PMID(15,27), PM_TYPE_U32, PM_INDOM_NULL, PM_SEM_COUNTER,
 		PMDA_PMUNITS(0,0,1,0,0,PM_COUNT_ONE) }, },
-	/* pending_lockwait_calls */
+	/* locks.pending_calls */
 	{ NULL, { PMDA_PMID(16,27), PM_TYPE_U32, PM_INDOM_NULL, PM_SEM_INSTANT,
 		PMDA_PMUNITS(0,0,0,0,0,0) }, },
 	/* childwrite_calls */
@@ -148,10 +148,10 @@ static pmdaMetric metrictab[] = {
 	/* max_call_latency */
 	{ NULL, { PMDA_PMID(23,34), PM_TYPE_DOUBLE, PM_INDOM_NULL, PM_SEM_INSTANT,
 		PMDA_PMUNITS(0,1,0,0,PM_TIME_SEC,0) }, },
-	/* max_lockwait_latency */
+	/* locks.latency.max */
 	{ NULL, { PMDA_PMID(24,35), PM_TYPE_DOUBLE, PM_INDOM_NULL, PM_SEM_INSTANT,
 		PMDA_PMUNITS(0,1,0,0,PM_TIME_SEC,0) }, },
-	/* max_childwrite_latency */
+	/* childwrite_latency.max */
 	{ NULL, { PMDA_PMID(25,36), PM_TYPE_DOUBLE, PM_INDOM_NULL, PM_SEM_INSTANT,
 		PMDA_PMUNITS(0,1,0,0,PM_TIME_SEC,0) }, },
 	/* num_recoveries */
@@ -423,10 +423,10 @@ pmda_ctdb_fetch_cb(pmdaMetric *mdesc, unsigned int inst, pmAtomValue *atom)
 		atom->ul = stats->pending_calls;
 		break;
 	case 15:
-		atom->ul = stats->lockwait_calls;
+		atom->ul = stats->locks.num_calls;
 		break;
 	case 16:
-		atom->ul = stats->pending_lockwait_calls;
+		atom->ul = stats->locks.num_pending;
 		break;
 	case 17:
 		atom->ul = stats->childwrite_calls;
@@ -450,7 +450,7 @@ pmda_ctdb_fetch_cb(pmdaMetric *mdesc, unsigned int inst, pmAtomValue *atom)
 		atom->d = stats->call_latency.max;
 		break;
 	case 24:
-		atom->d = stats->lockwait_latency.max;
+		atom->d = stats->locks.latency.max;
 		break;
 	case 25:
 		atom->d = stats->childwrite_latency.max;

-- 
CTDB



More information about the Pkg-samba-maint mailing list