[Box Backup-commit] COMMIT r3376 - in box/trunk: lib/backupclient lib/backupstore test/backupstore test/bbackupd

subversion at boxbackup.org subversion at boxbackup.org
Thu Sep 4 02:36:00 BST 2014


Author: chris
Date: 2014-09-04 02:35:59 +0100 (Thu, 04 Sep 2014)
New Revision: 3376

Modified:
   box/trunk/lib/backupclient/BackupClientRestore.cpp
   box/trunk/lib/backupclient/BackupClientRestore.h
   box/trunk/lib/backupstore/StoreTestUtils.cpp
   box/trunk/lib/backupstore/StoreTestUtils.h
   box/trunk/test/backupstore/testbackupstore.cpp
   box/trunk/test/bbackupd/testbbackupd.cpp
Log:
Define some functions to reduce duplication in testbbackupd.

Merged back changes from the test refactor branch to reduce diffs.

Fix wrong setting of log level in compare() function.

We want to only show errors if we expect mismatches, and show warnings if we
didn't expect mismatches. I had it the other way around before.

Modified: box/trunk/lib/backupclient/BackupClientRestore.cpp
===================================================================
--- box/trunk/lib/backupclient/BackupClientRestore.cpp	2014-08-24 20:31:46 UTC (rev 3375)
+++ box/trunk/lib/backupclient/BackupClientRestore.cpp	2014-09-04 01:35:59 UTC (rev 3376)
@@ -204,13 +204,13 @@
 // --------------------------------------------------------------------------
 //
 // Function
-//		Name:    BackupClientRestoreDir(BackupProtocolClient &,
+//		Name:    BackupClientRestoreDir(BackupProtocolCallable &,
 //			 int64_t, const char *, bool)
 //		Purpose: Restore a directory
 //		Created: 23/11/03
 //
 // --------------------------------------------------------------------------
-static int BackupClientRestoreDir(BackupProtocolClient &rConnection,
+static int BackupClientRestoreDir(BackupProtocolCallable &rConnection,
 	int64_t DirectoryID, const std::string &rRemoteDirectoryName,
 	const std::string &rLocalDirectoryName,
 	RestoreParams &Params, RestoreResumeInfo &rLevel)
@@ -813,7 +813,7 @@
 // --------------------------------------------------------------------------
 //
 // Function
-//		Name:    BackupClientRestore(BackupProtocolClient &, int64_t,
+//		Name:    BackupClientRestore(BackupProtocolCallable &, int64_t,
 //			 const char *, bool, bool, bool, bool, bool)
 //		Purpose: Restore a directory on the server to a local
 //			 directory on the disc. The local directory must not
@@ -840,7 +840,7 @@
 //		Created: 23/11/03
 //
 // --------------------------------------------------------------------------
-int BackupClientRestore(BackupProtocolClient &rConnection,
+int BackupClientRestore(BackupProtocolCallable &rConnection,
 	int64_t DirectoryID, const std::string& RemoteDirectoryName,
 	const std::string& LocalDirectoryName, bool PrintDots, bool RestoreDeleted,
 	bool UndeleteAfterRestoreDeleted, bool Resume,

Modified: box/trunk/lib/backupclient/BackupClientRestore.h
===================================================================
--- box/trunk/lib/backupclient/BackupClientRestore.h	2014-08-24 20:31:46 UTC (rev 3375)
+++ box/trunk/lib/backupclient/BackupClientRestore.h	2014-09-04 01:35:59 UTC (rev 3376)
@@ -10,7 +10,7 @@
 #ifndef BACKUPSCLIENTRESTORE_H
 #define BACKUPSCLIENTRESTORE__H
 
-class BackupProtocolClient;
+class BackupProtocolCallable;
 
 enum
 {
@@ -22,7 +22,7 @@
 	Restore_CompleteWithErrors,
 };
 
-int BackupClientRestore(BackupProtocolClient &rConnection,
+int BackupClientRestore(BackupProtocolCallable &rConnection,
 	int64_t DirectoryID,
 	const std::string& RemoteDirectoryName,
 	const std::string& LocalDirectoryName,

Modified: box/trunk/lib/backupstore/StoreTestUtils.cpp
===================================================================
--- box/trunk/lib/backupstore/StoreTestUtils.cpp	2014-08-24 20:31:46 UTC (rev 3375)
+++ box/trunk/lib/backupstore/StoreTestUtils.cpp	2014-09-04 01:35:59 UTC (rev 3376)
@@ -87,9 +87,14 @@
 		StopServer();
 	}
 
-	TEST_THAT_THROWONFAIL(system("rm -rf testfiles/0_0 testfiles/0_1 "
-		"testfiles/0_2 testfiles/accounts.txt testfiles/test* "
-		"testfiles/file*") == 0);
+	TEST_THAT_THROWONFAIL(system(
+		"rm -rf testfiles/TestDir* testfiles/0_0 testfiles/0_1 "
+		"testfiles/0_2 testfiles/accounts.txt " // testfiles/test* .tgz!
+		"testfiles/file* testfiles/notifyran testfiles/notifyran.* "
+		"testfiles/notifyscript.tag* "
+		"testfiles/restore* "
+		"testfiles/syncallowscript.control "
+		"testfiles/syncallowscript.notifyran.*") == 0);
 	TEST_THAT_THROWONFAIL(mkdir("testfiles/0_0", 0755) == 0);
 	TEST_THAT_THROWONFAIL(mkdir("testfiles/0_1", 0755) == 0);
 	TEST_THAT_THROWONFAIL(mkdir("testfiles/0_2", 0755) == 0);
@@ -102,11 +107,13 @@
 	return true;
 }
 
-void tearDown()
+bool tearDown()
 {
+	bool status = true;
+
 	if (ServerIsAlive(bbstored_pid))
 	{
-		StopServer();
+		TEST_THAT_OR(StopServer(), status = false);
 	}
 
 	if (FileExists("testfiles/0_0/backup/01234567/info.rf"))
@@ -114,8 +121,16 @@
 		TEST_THAT(check_reference_counts());
 		TEST_THAT(check_account());
 	}
+
+	return status;
 }
 
+bool fail()
+{
+	TEST_THAT(tearDown());
+	return false;
+}
+
 void set_refcount(int64_t ObjectID, uint32_t RefCount)
 {
 	if ((int64_t)ExpectedRefCounts.size() <= ObjectID)
@@ -143,12 +158,11 @@
 	return static_cast<std::auto_ptr<SocketStream> >(conn);
 }
 
-std::auto_ptr<BackupProtocolCallable> test_server_login(const char *hostname,
-	TLSContext& rContext, int flags)
+std::auto_ptr<BackupProtocolCallable> connect_to_bbstored(TLSContext& rContext)
 {
 	// Make a protocol
 	std::auto_ptr<BackupProtocolCallable> protocol(new
-		BackupProtocolClient(open_conn(hostname, rContext)));
+		BackupProtocolClient(open_conn("localhost", rContext)));
 	
 	// Check the version
 	std::auto_ptr<BackupProtocolVersion> serverVersion(
@@ -155,9 +169,18 @@
 		protocol->QueryVersion(BACKUP_STORE_SERVER_VERSION));
 	TEST_THAT(serverVersion->GetVersion() == BACKUP_STORE_SERVER_VERSION);
 
+	return protocol;
+}
+
+std::auto_ptr<BackupProtocolCallable> connect_and_login(TLSContext& rContext,
+	int flags)
+{
+	// Make a protocol
+	std::auto_ptr<BackupProtocolCallable> protocol =
+		connect_to_bbstored(rContext);
+
 	// Login
-	std::auto_ptr<BackupProtocolLoginConfirmed> loginConf(
-		protocol->QueryLogin(0x01234567, flags));
+	protocol->QueryLogin(0x01234567, flags);
 
 	return protocol;
 }
@@ -203,6 +226,18 @@
 		Dirs == usage->GetBlocksInDirectories());
 }
 
+bool change_account_limits(const char* soft, const char* hard)
+{
+	std::string errs;
+	std::auto_ptr<Configuration> config(
+		Configuration::LoadAndVerify
+			("testfiles/bbstored.conf", &BackupConfigFileVerify, errs));
+	BackupStoreAccountsControl control(*config);
+	int result = control.SetLimit(0x01234567, soft, hard);
+	TEST_EQUAL(0, result);
+	return (result == 0);
+}
+
 int check_account_for_errors(Log::Level log_level)
 {
 	Logger::LevelGuard guard(Logging::GetConsole(), log_level);
@@ -296,31 +331,27 @@
 
 bool StartServer()
 {
-	TEST_THAT_THROWONFAIL(bbstored_pid == 0);
+	TEST_THAT_OR(bbstored_pid == 0, return false);
 
-	std::string cmd = BBSTORED " " + bbstored_args + 
+	std::string cmd = BBSTORED " " + bbstored_args +
 		" testfiles/bbstored.conf";
 	bbstored_pid = LaunchServer(cmd.c_str(), "testfiles/bbstored.pid");
 
-	TEST_THAT(bbstored_pid != -1 && bbstored_pid != 0);
-	if(bbstored_pid <= 0)
-	{
-		return false;
-	}
+	TEST_THAT_OR(bbstored_pid != -1 && bbstored_pid != 0, return false);
 
 	::sleep(1);
-	TEST_THAT_THROWONFAIL(ServerIsAlive(bbstored_pid));
+	TEST_THAT_OR(ServerIsAlive(bbstored_pid), return false);
 	return true;
 }
 
 bool StopServer(bool wait_for_process)
 {
-	TEST_THAT_THROWONFAIL(bbstored_pid != 0);
-	TEST_THAT_THROWONFAIL(ServerIsAlive(bbstored_pid));
-	TEST_THAT_THROWONFAIL(KillServer(bbstored_pid, wait_for_process));
+	TEST_THAT_OR(bbstored_pid != 0, return false);
+	TEST_THAT_OR(ServerIsAlive(bbstored_pid), return false);
+	TEST_THAT_OR(KillServer(bbstored_pid, wait_for_process), return false);
 	::sleep(1);
 
-	TEST_THAT_THROWONFAIL(!ServerIsAlive(bbstored_pid));
+	TEST_THAT_OR(!ServerIsAlive(bbstored_pid), return false);
 	bbstored_pid = 0;
 
 	#ifdef WIN32

Modified: box/trunk/lib/backupstore/StoreTestUtils.h
===================================================================
--- box/trunk/lib/backupstore/StoreTestUtils.h	2014-08-24 20:31:46 UTC (rev 3375)
+++ box/trunk/lib/backupstore/StoreTestUtils.h	2014-09-04 01:35:59 UTC (rev 3376)
@@ -30,8 +30,11 @@
 bool setUp(const char* function_name);
 
 //! Checks account for errors and shuts down daemons at end of every test.
-void tearDown();
+bool tearDown();
 
+//! Like tearDown() but returns false, because a test failure was detected.
+bool fail();
+
 //! Sets the expected refcount of an object, resizing vector if necessary.
 void set_refcount(int64_t ObjectID, uint32_t RefCount = 1);
 
@@ -42,9 +45,12 @@
 std::auto_ptr<SocketStream> open_conn(const char *hostname,
 	TLSContext& rContext);
 
+//! Opens a connection to the server (bbstored) without logging in.
+std::auto_ptr<BackupProtocolCallable> connect_to_bbstored(TLSContext& rContext);
+
 //! Opens a connection to the server (bbstored) and logs in.
-std::auto_ptr<BackupProtocolCallable> test_server_login(const char *hostname,
-	TLSContext& rContext, int flags = 0);
+std::auto_ptr<BackupProtocolCallable> connect_and_login(TLSContext& rContext,
+	int flags = 0);
 
 //! Checks the number of files of each type in the store against expectations.
 bool check_num_files(int files, int old, int deleted, int dirs);
@@ -53,6 +59,9 @@
 bool check_num_blocks(BackupProtocolCallable& Client, int Current, int Old,
 	int Deleted, int Dirs, int Total);
 
+//! Change the soft and hard limits on the test account.
+bool change_account_limits(const char* soft, const char* hard);
+
 //! Checks an account for errors, returning the number of errors found and fixed.
 int check_account_for_errors(Log::Level log_level = Log::WARNING);
 

Modified: box/trunk/test/backupstore/testbackupstore.cpp
===================================================================
--- box/trunk/test/backupstore/testbackupstore.cpp	2014-08-24 20:31:46 UTC (rev 3375)
+++ box/trunk/test/backupstore/testbackupstore.cpp	2014-09-04 01:35:59 UTC (rev 3376)
@@ -761,22 +761,6 @@
 	return RaidFileRead::Open(0, filename);
 }
 
-bool check_num_files(int files, int old, int deleted, int dirs);
-bool check_num_blocks(BackupProtocolCallable& Client, int Current, int Old,
-	int Deleted, int Dirs, int Total);
-
-bool change_account_limits(const char* soft, const char* hard)
-{
-	std::string errs;
-	std::auto_ptr<Configuration> config(
-		Configuration::LoadAndVerify
-			("testfiles/bbstored.conf", &BackupConfigFileVerify, errs));
-	BackupStoreAccountsControl control(*config);
-	int result = control.SetLimit(0x01234567, soft, hard);
-	TEST_EQUAL(0, result);
-	return (result == 0);
-}
-
 int64_t create_directory(BackupProtocolCallable& protocol,
 	int64_t parent_dir_id = BACKUPSTORE_ROOT_DIRECTORY_ID);
 int64_t create_file(BackupProtocolCallable& protocol, int64_t subdirid,
@@ -805,14 +789,8 @@
 
 	BackupProtocolLocal2 protocol(0x01234567, "test", "backup/01234567/",
 		0, false);
-
-	std::string root_dir_fn;
-	StoreStructure::MakeObjectFilename(
-		BackupProtocolListDirectory::RootDirectory, 
-		"backup/01234567/" /* mStoreRoot */, 0 /* mStoreDiscSet */, 
-		root_dir_fn, false /* EnsureDirectoryExists */);
-	std::auto_ptr<RaidFileRead> storedFile(RaidFileRead::Open(0, root_dir_fn));
-	int root_dir_blocks = storedFile->GetDiscUsageInBlocks();
+	
+	int root_dir_blocks = get_raid_file(BACKUPSTORE_ROOT_DIRECTORY_ID)->GetDiscUsageInBlocks();
 	TEST_THAT(check_num_files(0, 0, 0, 1));
 	TEST_THAT(check_num_blocks(protocol, 0, 0, 0, root_dir_blocks,
 		root_dir_blocks));
@@ -1197,14 +1175,14 @@
 	SETUP();
 	TEST_THAT_THROWONFAIL(StartServer());
 
-	std::auto_ptr<BackupProtocolCallable> apProtocol(
-		test_server_login("localhost", context).release());
+	std::auto_ptr<BackupProtocolCallable> apProtocol =
+		connect_and_login(context);
 
 #ifndef WIN32
 	// Open a new connection which is read only
 	// TODO FIXME replace protocolReadOnly with apProtocolReadOnly.
 	std::auto_ptr<BackupProtocolCallable> apProtocolReadOnly =
-		test_server_login("localhost", context,
+		connect_and_login(context,
 			BackupProtocolLogin::Flags_ReadOnly);
 	BackupProtocolCallable& protocolReadOnly(*apProtocolReadOnly);
 #else // WIN32
@@ -1287,7 +1265,7 @@
 
 			apProtocol->QueryFinished();
 			TEST_THAT(run_housekeeping_and_check_account());
-			apProtocol = test_server_login("localhost", context);
+			apProtocol = connect_and_login(context);
 
 			TEST_THAT(check_num_files(expected_num_current_files,
 				expected_num_old_files, 0, 1));
@@ -1392,7 +1370,7 @@
 			" -c testfiles/bbstored.conf check 01234567 fix") == 0);
 		TestRemoteProcessMemLeaks("bbstoreaccounts.memleaks");
 
-		apProtocol = test_server_login("localhost", context);
+		apProtocol = connect_and_login(context);
 
 		TEST_THAT(check_num_files(UPLOAD_NUM - 4, 3, 2, 1));
 
@@ -1697,7 +1675,7 @@
 
 		apProtocol->QueryFinished();
 		TEST_THAT(run_housekeeping_and_check_account());
-		apProtocol = test_server_login("localhost", context);
+		apProtocol = connect_and_login(context);
 
 		// Query names -- test that invalid stuff returns not found OK
 		{
@@ -2421,11 +2399,10 @@
 	// we're locked out of the account until housekeeping has recreated
 	// the refcount db.
 	TEST_EQUAL(0, ::unlink("testfiles/0_0/backup/01234567/refcount.rdb.rfw"));
+	TEST_CHECK_THROWS(BackupProtocolLocal2 protocolLocal(0x01234567,
+		"test", "backup/01234567/", 0, false), // Not read-only
+		BackupStoreException, CorruptReferenceCountDatabase);
 
-	TEST_CHECK_THROWS(test_server_login("localhost", context),
-		ConnectionException, TLSReadFailed);
-	TEST_THAT(ServerIsAlive(bbstored_pid));
-
 	std::auto_ptr<BackupStoreAccountDatabase> apAccounts(
 		BackupStoreAccountDatabase::Read("testfiles/accounts.txt"));
 	BackupStoreAccountDatabase::Entry account =

Modified: box/trunk/test/bbackupd/testbbackupd.cpp
===================================================================
--- box/trunk/test/bbackupd/testbbackupd.cpp	2014-08-24 20:31:46 UTC (rev 3375)
+++ box/trunk/test/bbackupd/testbbackupd.cpp	2014-09-04 01:35:59 UTC (rev 3376)
@@ -88,6 +88,16 @@
 // two cycles and a bit
 #define TIME_TO_WAIT_FOR_BACKUP_OPERATION	12
 
+std::string current_test_name;
+std::map<std::string, std::string> s_test_status;
+
+#define FAIL { \
+	std::ostringstream os; \
+	os << "failed at " << __FUNCTION__ << ":" << __LINE__; \
+	s_test_status[current_test_name] = os.str(); \
+	return fail(); \
+}
+
 void wait_for_backup_operation(const char* message)
 {
 	wait_for_operation(TIME_TO_WAIT_FOR_BACKUP_OPERATION, message);
@@ -95,6 +105,44 @@
 
 int bbackupd_pid = 0;
 
+bool StartClient(const std::string& bbackupd_conf_file = "testfiles/bbackupd.conf")
+{
+	TEST_THAT_OR(bbackupd_pid == 0, FAIL);
+
+	std::string cmd = BBACKUPD " " + bbackupd_args + " " + bbackupd_conf_file;
+	bbackupd_pid = LaunchServer(cmd.c_str(), "testfiles/bbackupd.pid");
+
+	TEST_THAT_OR(bbackupd_pid != -1 && bbackupd_pid != 0, FAIL);
+	::sleep(1);
+	TEST_THAT_OR(ServerIsAlive(bbackupd_pid), FAIL);
+
+	return true;
+}
+
+bool StopClient(bool wait_for_process = false)
+{
+	TEST_THAT_OR(bbackupd_pid != 0, FAIL);
+	TEST_THAT_OR(ServerIsAlive(bbackupd_pid), FAIL);
+	TEST_THAT_OR(KillServer(bbackupd_pid, wait_for_process), FAIL);
+	::sleep(1);
+
+	TEST_THAT_OR(!ServerIsAlive(bbackupd_pid), FAIL);
+	bbackupd_pid = 0;
+
+	#ifdef WIN32
+		int unlink_result = unlink("testfiles/bbackupd.pid");
+		TEST_EQUAL_LINE(0, unlink_result, "unlink testfiles/bbackupd.pid");
+		if(unlink_result != 0)
+		{
+			FAIL;
+		}
+	#else
+		TestRemoteProcessMemLeaks("bbackupd.memleaks");
+	#endif
+
+	return true;
+}
+
 #ifdef HAVE_SYS_XATTR_H
 bool readxattr_into_map(const char *filename, std::map<std::string,std::string> &rOutput)
 {
@@ -306,8 +354,115 @@
 	return (s1.st_mode == s2.st_mode && s1.st_uid == s2.st_uid && s1.st_gid == s2.st_gid);
 }
 
-int test_basics()
+bool unpack_files(const std::string& archive_file,
+	const std::string& destination_dir = "testfiles",
+	const std::string& tar_options = "")
 {
+#ifdef WIN32
+	std::string cmd("tar xzv ");
+	cmd += tar_options + " -f testfiles/" + archive_file + ".tgz " +
+		"-C " + destination_dir;
+#else
+	std::string cmd("gzip -d < testfiles/");
+	cmd += archive_file + ".tgz | ( cd " + destination_dir + " && tar xv " +
+		tar_options + ")";
+#endif
+
+	TEST_THAT_OR(::system(cmd.c_str()) == 0, return false);
+	return true;
+}
+
+Daemon* spDaemon = NULL;
+
+bool configure_bbackupd(BackupDaemon& bbackupd, const std::string& config_file)
+{
+	// Stop bbackupd initialisation from changing the console logging level
+	Logger& console(Logging::GetConsole());
+	Logger::LevelGuard guard(console, console.GetLevel());
+
+	std::vector<std::string> args;
+	size_t last_arg_start = 0;
+	for (size_t pos = 0; pos <= bbackupd_args.size(); pos++)
+	{
+		char c;
+
+		if (pos == bbackupd_args.size())
+		{
+			c = ' '; // finish last argument
+		}
+		else
+		{
+			c = bbackupd_args[pos];
+		}
+
+		if (c == ' ')
+		{
+			if (last_arg_start < pos)
+			{
+				std::string last_arg =
+					bbackupd_args.substr(last_arg_start,
+						pos - last_arg_start);
+				args.push_back(last_arg);
+			}
+
+			last_arg_start = pos + 1;
+		}
+	}
+
+	MemoryBlockGuard<const char **> argv_buffer(sizeof(const char*) * (args.size() + 1));
+	const char **argv = argv_buffer;
+	argv_buffer[0] = "bbackupd";
+	for (int i = 0; i < args.size(); i++)
+	{
+		argv_buffer[i + 1] = args[i].c_str();
+	}
+
+	TEST_EQUAL_LINE(0, bbackupd.ProcessOptions(args.size() + 1, argv),
+		"processing command-line options");
+
+	bbackupd.Configure(config_file);
+	bbackupd.InitCrypto();
+
+	return true;
+}
+
+bool kill_running_daemons()
+{
+	TEST_THAT_OR(::system("test ! -r testfiles/bbstored.pid || "
+		"kill `cat testfiles/bbstored.pid`") == 0, FAIL);
+	TEST_THAT_OR(::system("test ! -r testfiles/bbackupd.pid || "
+		"kill `cat testfiles/bbackupd.pid`") == 0, FAIL);
+	TEST_THAT_OR(::system("rm -f testfiles/bbackupd.pid "
+		"testfiles/bbstored.pid") == 0, FAIL);
+	return true;
+}
+
+int num_tests_selected = 0;
+
+//! Checks account for errors and shuts down daemons at end of every test.
+bool teardown_test_bbackupd(std::string test_name, int old_failure_count)
+{
+	if (failures == old_failure_count)
+	{
+		BOX_NOTICE(test_name << " passed");
+		s_test_status[test_name] = "passed";
+	}
+	else
+	{
+		BOX_NOTICE(test_name << " failed"); \
+		s_test_status[test_name] = "failed";
+	}
+
+	if(bbackupd_pid != 0)
+	{
+		TEST_THAT(StopClient());
+	}
+
+	return tearDown();
+}
+
+bool test_basics()
+{
 	// Read attributes from files
 	BackupClientFileAttributes t1;
 	t1.ReadAttributes("testfiles/test1");
@@ -423,10 +578,10 @@
 	finish_with_write_xattr_test();
 #endif // HAVE_SYS_XATTR_H
 
-	return 0;
+	return false;
 }
 
-int64_t GetDirID(BackupProtocolClient &protocol, const char *name, int64_t InDirectory)
+int64_t GetDirID(BackupProtocolCallable &protocol, const char *name, int64_t InDirectory)
 {
 	protocol.QueryListDirectory(
 			InDirectory,
@@ -599,20 +754,17 @@
 	
 std::auto_ptr<BackupStoreDirectory> ReadDirectory
 (
-	BackupProtocolClient& rClient,
+	BackupProtocolCallable& rClient,
 	int64_t id = BackupProtocolListDirectory::RootDirectory
 )
 {
 	std::auto_ptr<BackupProtocolSuccess> dirreply(
 		rClient.QueryListDirectory(id, false, 0, false));
-	std::auto_ptr<IOStream> dirstream(rClient.ReceiveStream());
-	std::auto_ptr<BackupStoreDirectory> apDir(new BackupStoreDirectory());
-	apDir->ReadFromStream(*dirstream, rClient.GetTimeout());
+	std::auto_ptr<BackupStoreDirectory> apDir(
+		new BackupStoreDirectory(rClient.ReceiveStream()));
 	return apDir;
 }
 	
-Daemon* spDaemon = NULL;
-
 int start_internal_daemon()
 {
 	// ensure that no child processes end up running tests!
@@ -798,7 +950,7 @@
 	return old_ret;
 }
 
-bool test_entry_deleted(BackupStoreDirectory& rDir, 
+bool test_entry_deleted(BackupStoreDirectory& rDir,
 	const std::string& rName)
 {
 	BackupStoreDirectory::Iterator i(rDir);
@@ -805,32 +957,32 @@
 
 	BackupStoreDirectory::Entry *en = i.FindMatchingClearName(
 		BackupStoreFilenameClear(rName));
-	TEST_THAT(en != 0);
-	if (en == 0) return false;
+	TEST_THAT_OR(en != 0, return false);
 
 	int16_t flags = en->GetFlags();
-	TEST_THAT(flags && BackupStoreDirectory::Entry::Flags_Deleted);
+	TEST_LINE(flags && BackupStoreDirectory::Entry::Flags_Deleted,
+		rName + " should have been deleted");
 	return flags && BackupStoreDirectory::Entry::Flags_Deleted;
 }
 
-bool compare_all(BackupQueries::ReturnCode::Type expected_status,
-	std::string config_file = "testfiles/bbackupd.conf")
+bool compare(BackupQueries::ReturnCode::Type expected_status,
+	const std::string& bbackupquery_options = "",
+	const std::string& compare_options = "-acQ")
 {
 	std::string cmd = BBACKUPQUERY;
 	cmd += " ";
 	cmd += (expected_status == BackupQueries::ReturnCode::Compare_Same)
-		? "-Werror" : "-Wwarning";
-	cmd += " -c ";
-	cmd += config_file;
-	cmd += " \"compare -acQ\" quit";
+		? "-Wwarning" : "-Werror";
+	cmd += " -c testfiles/bbackupd.conf ";
+	cmd += " " + bbackupquery_options;
+	cmd += " \"compare " + compare_options + "\" quit";
 
 	int returnValue = ::system(cmd.c_str());
-
 	int expected_system_result = (int) expected_status;
 
-	#ifndef WIN32
-		expected_system_result <<= 8;
-	#endif
+#ifndef WIN32
+	expected_system_result <<= 8;
+#endif
 
 	TEST_EQUAL_LINE(expected_system_result, returnValue, "compare return value");
 	TestRemoteProcessMemLeaks("bbackupquery.memleaks");
@@ -837,6 +989,30 @@
 	return (returnValue == expected_system_result);
 }
 
+bool bbackupquery(const std::string& arguments,
+	const std::string& memleaks_file = "bbackupquery.memleaks")
+{
+	std::string cmd = BBACKUPQUERY;
+	cmd += " -c testfiles/bbackupd.conf " + arguments + " quit";
+
+	int returnValue = ::system(cmd.c_str());
+
+#ifndef WIN32
+	returnValue >>= 8;
+#endif
+
+	TestRemoteProcessMemLeaks(memleaks_file.c_str());
+	TEST_EQUAL(returnValue, BackupQueries::ReturnCode::Command_OK);
+	return (returnValue == BackupQueries::ReturnCode::Command_OK);
+}
+
+bool restore(const std::string& location, const std::string& dest_dir)
+{
+	std::string cmd = "\"restore " + location + " " + dest_dir + "\"";
+	TEST_THAT_OR(bbackupquery(cmd), FAIL);
+	return true;
+}
+
 bool touch_and_wait(const std::string& filename)
 {
 	int fd = open(filename.c_str(), O_CREAT | O_WRONLY, 0755);
@@ -857,7 +1033,7 @@
 }
 
 #define TEST_COMPARE(...) \
-	TEST_THAT(compare_all(BackupQueries::ReturnCode::__VA_ARGS__));
+	TEST_THAT(compare(BackupQueries::ReturnCode::__VA_ARGS__));
 
 int test_bbackupd()
 {
@@ -1326,7 +1502,8 @@
 		// wait for files to be uploaded
 		BOX_TRACE("Waiting for all outstanding files to be uploaded")
 		wait_for_sync_end();
-		BOX_TRACE("done.")
+		BOX_TRACE("Done. Comparing to check that it worked...")
+		TEST_COMPARE(Compare_Same);
 
 		// Set limit to something very small
 		// 26 blocks will be used at this point.
@@ -1334,19 +1511,10 @@
 		// 20 is what we'll need in a minute
 		// set soft limit to 0 to ensure that all deleted files
 		// are deleted immediately by housekeeping
-		TEST_THAT_ABORTONFAIL(::system(BBSTOREACCOUNTS " -c "
-			"testfiles/bbstored.conf setlimit 01234567 0B 20B") 
-			== 0);
-		TestRemoteProcessMemLeaks("bbstoreaccounts.memleaks");
+		TEST_THAT(change_account_limits("0B", "20B"));
 
 		// Unpack some more files
-		#ifdef WIN32
-			TEST_THAT(::system("tar xzvf testfiles/spacetest2.tgz "
-				"-C testfiles/TestDir1") == 0);
-		#else
-			TEST_THAT(::system("gzip -d < testfiles/spacetest2.tgz "
-				"| ( cd testfiles/TestDir1 && tar xf - )") == 0);
-		#endif
+		unpack_files("spacetest2", "testfiles/TestDir1");
 
 		// Delete a file and a directory
 		TEST_THAT(::unlink("testfiles/TestDir1/spacetest/f1") == 0);
@@ -1404,8 +1572,8 @@
 
 		// BLOCK
 		{
-			std::auto_ptr<BackupProtocolClient> client =
-				ConnectAndLogin(context, 0 /* read-write */);
+			std::auto_ptr<BackupProtocolCallable> client =
+				connect_and_login(context, 0 /* read-write */);
 			TEST_THAT(check_num_files(4, 0, 0, 8));
 			TEST_THAT(check_num_blocks(*client, 8, 0, 0, 16, 24));
 			client->QueryFinished();
@@ -1435,18 +1603,9 @@
 
 		BackupDaemon bbackupd;
 
-		{
-			const char* argv[] = { "bbackupd",
-				bbackupd_args.c_str() };
-			TEST_EQUAL_LINE(0, bbackupd.ProcessOptions(2, argv),
-				"processing command-line options");
-		}
-
-		bbackupd.Configure("testfiles/bbackupd-exclude.conf");
-		bbackupd.InitCrypto();
-		BOX_TRACE("done.");
-
-		// Should be marked as deleted by this run
+		TEST_THAT(configure_bbackupd(bbackupd, "testfiles/bbackupd-exclude.conf"));
+		// Should be marked as deleted by this run. Hold onto the
+		// BackupClientContext to stop housekeeping from running.
 		// wait_for_sync_end();
 		{
 			// Logging::Guard guard(Log::ERROR);
@@ -1481,8 +1640,9 @@
 
 		BOX_TRACE("Find out whether bbackupd marked files as deleted");
 		{
-			std::auto_ptr<BackupProtocolClient> client =
-				ConnectAndLogin(context, 0 /* read-write */);
+			std::auto_ptr<BackupProtocolCallable> client =
+				connect_and_login(context,
+					BackupProtocolLogin::Flags_ReadOnly);
 		
 			std::auto_ptr<BackupStoreDirectory> rootDir =
 				ReadDirectory(*client);
@@ -1553,8 +1713,8 @@
 
 		BOX_TRACE("Check that the files were removed");
 		{
-			std::auto_ptr<BackupProtocolClient> client =
-				ConnectAndLogin(context, 0 /* read-write */);
+			std::auto_ptr<BackupProtocolCallable> client =
+				connect_and_login(context, 0 /* read-write */);
 
 			std::auto_ptr<BackupStoreDirectory> rootDir =
 				ReadDirectory(*client);
@@ -1577,18 +1737,13 @@
 			TEST_THAT(SearchDir(*spacetest_dir, "d3") == 0);
 			TEST_THAT(SearchDir(*spacetest_dir, "d7") == 0);
 
-			std::auto_ptr<BackupProtocolAccountUsage> usage(
-				client->QueryGetAccountUsage());
-			TEST_EQUAL_LINE(16, usage->GetBlocksUsed(),
-				"blocks used");
-			TEST_EQUAL_LINE(0, usage->GetBlocksInDeletedFiles(),
-				"deleted blocks");
-			TEST_EQUAL_LINE(12, usage->GetBlocksInDirectories(),
-				"directory blocks");
-			// d1/f3 and d1/f4 are the only two files on the
-			// server, they use 2 blocks each, the rest is
-			// directories.
 
+			// f2, d3, d3/d4 and d3/d4/f5 have been removed.
+			// The files were counted as deleted files before, the
+			// deleted directories just as directories.
+			TEST_THAT(check_num_files(2, 0, 0, 6));
+			TEST_THAT(check_num_blocks(*client, 4, 0, 0, 12, 16));
+
 			// Log out.
 			client->QueryFinished();
 		}
@@ -1608,22 +1763,17 @@
 
 		// Check that the contents of the store are the same 
 		// as the contents of the disc 
-		TEST_COMPARE(Compare_Same, "testfiles/bbackupd-exclude.conf");
+		TEST_COMPARE(Compare_Same, "-c testfiles/bbackupd-exclude.conf");
 		BOX_TRACE("done.");
 
 		// BLOCK
 		{
-			std::auto_ptr<BackupProtocolClient> client =
-				ConnectAndLogin(context, 0 /* read-write */);
+			std::auto_ptr<BackupProtocolCallable> client =
+				connect_and_login(context, 0 /* read-write */);
 
-			std::auto_ptr<BackupProtocolAccountUsage> usage(
-				client->QueryGetAccountUsage());
-			TEST_EQUAL_LINE(22, usage->GetBlocksUsed(),
-				"blocks used");
-			TEST_EQUAL_LINE(0, usage->GetBlocksInDeletedFiles(),
-				"deleted blocks");
-			TEST_EQUAL_LINE(14, usage->GetBlocksInDirectories(),
-				"directory blocks");
+			TEST_THAT(check_num_files(4, 0, 0, 7));
+			TEST_THAT(check_num_blocks(*client, 8, 0, 0, 14, 22));
+
 			// d2/f6, d6/d8 and d6/d8/f7 are new
 			// i.e. 2 new files, 1 new directory
 
@@ -1707,8 +1857,7 @@
 			(int)strlen(control_string));
 		close(fd);
 
-		// sleep to make it old enough to upload
-		safe_sleep(4);
+		wait_for_operation(5, "new file to be old enough");
 
 		// Start a bbstored with a test hook that makes it terminate
 		// on the first StoreFile command, breaking the connection to
@@ -1715,6 +1864,10 @@
 		// bbackupd.
 		class MyHook : public BackupStoreContext::TestHook
 		{
+		public:
+			int trigger_count;
+			MyHook() : trigger_count(0) { }
+
 			virtual std::auto_ptr<BackupProtocolMessage> StartCommand(
 				const BackupProtocolMessage& rCommand)
 			{
@@ -2001,15 +2154,8 @@
 
 	// create the location directory and unpack some files into it
 	TEST_THAT(::mkdir("testfiles/TestDir2", 0777) == 0);
+	TEST_THAT(unpack_files("spacetest1", "testfiles/TestDir2"));
 
-	#ifdef WIN32
-		TEST_THAT(::system("tar xzvf testfiles/spacetest1.tgz "
-			"-C testfiles/TestDir2") == 0);
-	#else
-		TEST_THAT(::system("gzip -d < testfiles/spacetest1.tgz "
-			"| ( cd testfiles/TestDir2 && tar xf - )") == 0);
-	#endif
-
 	// check that the files are backed up now
 	sync_and_wait();
 	TEST_COMPARE(Compare_Same);
@@ -2095,6 +2241,12 @@
 
 			client->QueryFinished();
 		}
+
+		std::auto_ptr<BackupProtocolCallable> client = connect_and_login(
+			context, 0 /* read-write */);
+		std::auto_ptr<BackupStoreDirectory> root_dir =
+			ReadDirectory(*client, BACKUPSTORE_ROOT_DIRECTORY_ID);
+		TEST_THAT(test_entry_deleted(*root_dir, "Test2"));
 	}
 
 	TEST_THAT(ServerIsAlive(bbackupd_pid));
@@ -2124,62 +2276,22 @@
 
 			wait_for_sync_end(); // too new
 			wait_for_sync_end(); // should be backed up now
+			TEST_COMPARE(Compare_Same, "", "-cEQ Test1 testfiles/TestDir1");
 
-			compareReturnValue = ::system(BBACKUPQUERY " "
-				"-Wwarning "
-				"-c testfiles/bbackupd.conf "
-				"\"compare -cEQ Test1 testfiles/TestDir1\" " 
-				"quit");
-			TEST_RETURN(compareReturnValue,
-				BackupQueries::ReturnCode::Compare_Same);
-			TestRemoteProcessMemLeaks("bbackupquery.memleaks");
-
 			// check that we can restore it
-			compareReturnValue = ::system(BBACKUPQUERY " "
-				"-Wwarning "
-				"-c testfiles/bbackupd.conf "
-				"\"restore Test1 testfiles/restore1\" "
-				"quit");
-			TEST_RETURN(compareReturnValue,
-				BackupQueries::ReturnCode::Command_OK);
-			TestRemoteProcessMemLeaks("bbackupquery.memleaks");
+			TEST_THAT(restore("Test1", "testfiles/restore1"));
+			TEST_COMPARE(Compare_Same, "", "-cEQ Test1 testfiles/restore1");
 
-			// check that it restored properly
-			compareReturnValue = ::system(BBACKUPQUERY " "
-				"-Wwarning "
-				"-c testfiles/bbackupd.conf "
-				"\"compare -cEQ Test1 testfiles/restore1\" " 
-				"quit");
-			TEST_RETURN(compareReturnValue,
-				BackupQueries::ReturnCode::Compare_Same);
-			TestRemoteProcessMemLeaks("bbackupquery.memleaks");
-
 			// Try a restore with just the remote directory name,
 			// check that it uses the same name in the local
 			// directory.
 			TEST_THAT(::mkdir("testfiles/restore-test", 0700) == 0);
+			TEST_THAT(bbackupquery("\"lcd testfiles/restore-test\" "
+				"\"restore Test1\"",
+				"testfiles/restore-test/bbackupquery.memleaks"));
+			TEST_COMPARE(Compare_Same, "", "-cEQ Test1 "
+				"testfiles/restore-test/Test1");
 
-			compareReturnValue = ::system(BBACKUPQUERY " "
-				"-Wwarning "
-				"-c testfiles/bbackupd.conf "
-				"\"lcd testfiles/restore-test\" "
-				"\"restore Test1\" "
-				"quit");
-			TEST_RETURN(compareReturnValue,
-				BackupQueries::ReturnCode::Command_OK);
-			TestRemoteProcessMemLeaks("testfiles/restore-test/"
-				"bbackupquery.memleaks");
-
-			// check that it restored properly
-			compareReturnValue = ::system(BBACKUPQUERY " "
-				"-Wwarning "
-				"-c testfiles/bbackupd.conf "
-				"\"compare -cEQ Test1 testfiles/restore-test/Test1\" " 
-				"quit");
-			TEST_RETURN(compareReturnValue,
-				BackupQueries::ReturnCode::Compare_Same);
-			TestRemoteProcessMemLeaks("bbackupquery.memleaks");
-
 			// put the permissions back to sensible values
 			#ifdef WIN32
 				TEST_THAT(::system("chmod 0755 testfiles/"
@@ -2265,47 +2377,14 @@
 			consoleFileName));
 
 		// test that bbackupd will let us lcd into the local 
-		// directory using a relative path
-		std::string command = BBACKUPQUERY " "
-			"-Wwarning "
-			"-c testfiles/bbackupd.conf "
-			"\"lcd testfiles/TestDir1/" + systemDirName + "\" "
-			"quit";
-		compareReturnValue = ::system(command.c_str());
-		TEST_RETURN(compareReturnValue,
-			BackupQueries::ReturnCode::Command_OK);
+		// directory using a relative path, and back out
+		TEST_THAT(bbackupquery("\"lcd testfiles/TestDir1/" +
+			systemDirName + "\" \"lcd ..\""));
 
-		// and back out again
-		command = BBACKUPQUERY " "
-			"-Wwarning "
-			"-c testfiles/bbackupd.conf "
-			"\"lcd testfiles/TestDir1/" + systemDirName + "\" "
-			"\"lcd ..\" quit";
-		compareReturnValue = ::system(command.c_str());
-		TEST_RETURN(compareReturnValue,
-			BackupQueries::ReturnCode::Command_OK);
-
 		// and using an absolute path
-		command = BBACKUPQUERY " "
-			"-Wwarning "
-			"-c testfiles/bbackupd.conf "
-			"\"lcd " + cwd + "/testfiles/TestDir1/" + 
-			systemDirName + "\" quit";
-		compareReturnValue = ::system(command.c_str());
-		TEST_RETURN(compareReturnValue,
-			BackupQueries::ReturnCode::Command_OK);
+		TEST_THAT(bbackupquery("\"lcd " + cwd + "/testfiles/" +
+			"TestDir1/" + systemDirName + "\"  \"lcd ..\""));
 
-		// and back out again
-		command = BBACKUPQUERY " "
-			"-Wwarning "
-			"-c testfiles/bbackupd.conf "
-			"\"lcd " + cwd + "/testfiles/TestDir1/" + 
-			systemDirName + "\" "
-			"\"lcd ..\" quit";
-		compareReturnValue = ::system(command.c_str());
-		TEST_RETURN(compareReturnValue,
-			BackupQueries::ReturnCode::Command_OK);
-
 		{
 			FileStream fs(filepath.c_str(), O_CREAT | O_RDWR);
 
@@ -2323,8 +2402,8 @@
 
 		// Check that we can find it in directory listing
 		{
-			std::auto_ptr<BackupProtocolClient> client =
-				ConnectAndLogin(context, 0);
+			std::auto_ptr<BackupProtocolCallable> client =
+				connect_and_login(context, 0);
 
 			std::auto_ptr<BackupStoreDirectory> dir = ReadDirectory(
 				*client);
@@ -2396,36 +2475,18 @@
 
 		// Check that bbackupquery can compare the dir when given
 		// on the command line in system encoding.
-		command = BBACKUPQUERY " -c testfiles/bbackupd.conf "
-			"-Wwarning \"compare -cEQ Test1/" + systemDirName +
-			" testfiles/TestDir1/" + systemDirName + "\" quit";
+		TEST_COMPARE(Compare_Same, "", "-cEQ Test1/" + systemDirName +
+			" testfiles/TestDir1/" + systemDirName);
 
-		compareReturnValue = ::system(command.c_str());
-		TestRemoteProcessMemLeaks("bbackupquery.memleaks");
-		TEST_RETURN(compareReturnValue,
-			BackupQueries::ReturnCode::Compare_Same);
-
 		// Check that bbackupquery can restore the dir when given
 		// on the command line in system encoding.
-		command = BBACKUPQUERY " -c testfiles/bbackupd.conf "
-			"-Wwarning \"restore Test1/" + systemDirName +
-			" testfiles/restore-" + systemDirName + "\" quit";
+		TEST_THAT(restore("Test1/" + systemDirName,
+			"testfiles/restore-" + systemDirName));
 
-		compareReturnValue = ::system(command.c_str());
-		TestRemoteProcessMemLeaks("bbackupquery.memleaks");
-		TEST_RETURN(compareReturnValue,
-			BackupQueries::ReturnCode::Command_OK);
-
 		// Compare to make sure it was restored properly.
-		command = BBACKUPQUERY " -c testfiles/bbackupd.conf "
-			"-Wwarning \"compare -cEQ Test1/" + systemDirName +
-			" testfiles/restore-" + systemDirName + "\" quit";
+		TEST_COMPARE(Compare_Same, "", "-cEQ Test1/" + systemDirName +
+			" testfiles/restore-" + systemDirName);
 
-		compareReturnValue = ::system(command.c_str());
-		TestRemoteProcessMemLeaks("bbackupquery.memleaks");
-		TEST_RETURN(compareReturnValue,
-			BackupQueries::ReturnCode::Compare_Same);
-
 		std::string fileToUnlink = "testfiles/restore-" + 
 			dirname + "/" + filename;
 		TEST_THAT(::unlink(fileToUnlink.c_str()) == 0);
@@ -2432,65 +2493,35 @@
 
 		// Check that bbackupquery can get the file when given
 		// on the command line in system encoding.
-		command = BBACKUPQUERY " -c testfiles/bbackupd.conf "
-			"-Wwarning \"get Test1/" + systemDirName + "/" + 
+		TEST_THAT(bbackupquery("\"get Test1/" + systemDirName + "/" +
 			systemFileName + " " + "testfiles/restore-" + 
-			systemDirName + "/" + systemFileName + "\" quit";
+			systemDirName + "/" + systemFileName + "\""));
 
-		compareReturnValue = ::system(command.c_str());
-		TEST_RETURN(compareReturnValue,
-			BackupQueries::ReturnCode::Command_OK);
-		TestRemoteProcessMemLeaks("bbackupquery.memleaks");
-
 		// And after changing directory to a relative path
-		command = BBACKUPQUERY " -c testfiles/bbackupd.conf "
-			"-Wwarning "
+		TEST_THAT(bbackupquery(
 			"\"lcd testfiles\" "
 			"\"cd Test1/" + systemDirName + "\" " + 
-			"\"get " + systemFileName + "\" quit";
+			"\"get " + systemFileName + "\""));
 
-		compareReturnValue = ::system(command.c_str());
-		TEST_RETURN(compareReturnValue,
-			BackupQueries::ReturnCode::Command_OK);
-		TestRemoteProcessMemLeaks("testfiles/bbackupquery.memleaks");
-
 		// cannot overwrite a file that exists, so delete it
 		std::string tmp = "testfiles/" + filename;
 		TEST_THAT(::unlink(tmp.c_str()) == 0);
 
 		// And after changing directory to an absolute path
-		command = BBACKUPQUERY " -c testfiles/bbackupd.conf -Wwarning "
+		TEST_THAT(bbackupquery(
 			"\"lcd " + cwd + "/testfiles\" "
 			"\"cd Test1/" + systemDirName + "\" " + 
-			"\"get " + systemFileName + "\" quit";
+			"\"get " + systemFileName + "\""));
 
-		compareReturnValue = ::system(command.c_str());
-		TEST_RETURN(compareReturnValue,
-			BackupQueries::ReturnCode::Command_OK);
-		TestRemoteProcessMemLeaks("testfiles/bbackupquery.memleaks");
-
 		// Compare to make sure it was restored properly.
 		// The Get command does not restore attributes, so
 		// we must compare without them (-A) to succeed.
-		command = BBACKUPQUERY " "
-			"-c testfiles/bbackupd.conf "
-			"-Wwarning \"compare -cAEQ Test1/" + systemDirName +
-			" testfiles/restore-" + systemDirName + "\" quit";
+		TEST_COMPARE(Compare_Same, "", "-cAEQ Test1/" + systemDirName +
+			" testfiles/restore-" + systemDirName);
 
-		compareReturnValue = ::system(command.c_str());
-		TestRemoteProcessMemLeaks("bbackupquery.memleaks");
-		TEST_RETURN(compareReturnValue,
-			BackupQueries::ReturnCode::Compare_Same);
-
 		// Compare without attributes. This should fail.
-		command = BBACKUPQUERY " "
-			"-c testfiles/bbackupd.conf "
-			"-Werror \"compare -cEQ Test1/" + systemDirName +
-			" testfiles/restore-" + systemDirName + "\" quit";
-		compareReturnValue = ::system(command.c_str());
-		TestRemoteProcessMemLeaks("bbackupquery.memleaks");
-		TEST_RETURN(compareReturnValue,
-			BackupQueries::ReturnCode::Compare_Different);
+		TEST_COMPARE(Compare_Different, "", "-cEQ Test1/" + systemDirName +
+			" testfiles/restore-" + systemDirName);
 #endif // WIN32
 
 		// Check that no read error has been reported yet
@@ -2644,13 +2675,7 @@
 		TEST_COMPARE(Compare_Same);
 
 		// Try a quick compare, just for fun
-		compareReturnValue = ::system(BBACKUPQUERY " "
-			"-c testfiles/bbackupd.conf "
-			"-l testfiles/query2q.log "
-			"-Wwarning \"compare -acqQ\" quit");
-		TEST_RETURN(compareReturnValue,
-			BackupQueries::ReturnCode::Compare_Same);
-		TestRemoteProcessMemLeaks("bbackupquery.memleaks");
+		TEST_COMPARE(Compare_Same, "", "-acqQ");
 		
 		TEST_THAT(ServerIsAlive(bbackupd_pid));
 		TEST_THAT(ServerIsAlive(bbstored_pid));
@@ -2710,12 +2735,8 @@
 		// Now kill bbackupd and start one that's running in
 		// snapshot mode, check that it automatically syncs after
 		// an error, without waiting for another sync command.
-		terminate_bbackupd(bbackupd_pid);
-		std::string cmd = BBACKUPD " " + bbackupd_args + 
-			" testfiles/bbackupd-snapshot.conf";
-		bbackupd_pid = LaunchServer(cmd, "testfiles/bbackupd.pid");
-		TEST_THAT(bbackupd_pid != -1 && bbackupd_pid != 0);
-		::safe_sleep(1);
+		TEST_THAT(StopClient());
+		TEST_THAT(StartClient("testfiles/bbackupd-snapshot.conf"));
 		TEST_THAT(ServerIsAlive(bbackupd_pid));
 		TEST_THAT(ServerIsAlive(bbstored_pid));
 		if (!ServerIsAlive(bbackupd_pid)) return 1;
@@ -2780,7 +2801,7 @@
 		TEST_THAT(::unlink("testfiles/notifyscript.tag") == 0);
 
 		// Stop the snapshot bbackupd
-		terminate_bbackupd(bbackupd_pid);
+		TEST_THAT(StopClient());
 
 		// Break the store again
 		TEST_THAT(::rename("testfiles/0_0/backup/01234567/info.rf",
@@ -2799,12 +2820,8 @@
 			TEST_THAT(close(fd1) == 0);
 		}
 
-		// Restart the old bbackupd, in automatic mode
-		cmd = BBACKUPD " " + bbackupd_args + 
-			" testfiles/bbackupd.conf";
-		bbackupd_pid = LaunchServer(cmd, "testfiles/bbackupd.pid");
-		TEST_THAT(bbackupd_pid != -1 && bbackupd_pid != 0);
-		::safe_sleep(1);
+		// Restart bbackupd in automatic mode
+		TEST_THAT_OR(StartClient(), FAIL);
 		TEST_THAT(ServerIsAlive(bbackupd_pid));
 		TEST_THAT(ServerIsAlive(bbstored_pid));
 		if (!ServerIsAlive(bbackupd_pid)) return 1;
@@ -3109,12 +3126,9 @@
 		// Because the 'm' option is not used, these files will 
 		// look very old to the daemon.
 		// Lucky it'll upload them then!
-		#ifdef WIN32
-			TEST_THAT(::system("tar xzvf testfiles/test2.tgz "
-				"-C testfiles") == 0);
-		#else
-			TEST_THAT(::system("gzip -d < testfiles/test2.tgz "
-				"| ( cd  testfiles && tar xf - )") == 0);
+		TEST_THAT(unpack_files("test2"));
+
+		#ifndef WIN32
 			::chmod("testfiles/TestDir1/sub23/dhsfdss/blf.h", 0415);
 		#endif
 		
@@ -3191,14 +3205,7 @@
 
 		// Add some files and directories which are marked as excluded
 		printf("\n==== Add files and dirs for exclusion test\n");
-		#ifdef WIN32
-			TEST_THAT(::system("tar xzvf testfiles/testexclude.tgz "
-				"-C testfiles") == 0);
-		#else
-			TEST_THAT(::system("gzip -d < "
-				"testfiles/testexclude.tgz "
-				"| ( cd testfiles && tar xf - )") == 0);
-		#endif
+		TEST_THAT(unpack_files("testexclude"));
 
 		// Wait and test
 		wait_for_sync_end();
@@ -3208,20 +3215,8 @@
 		TEST_COMPARE(Compare_Same);
 
 		// compare without exclusions, should find differences
-		compareReturnValue = ::system(BBACKUPQUERY " "
-			"-c testfiles/bbackupd.conf "
-			"-l testfiles/query3n.log "
-			"-Werror \"compare -acEQ\" quit");
-		TEST_RETURN(compareReturnValue,
-			BackupQueries::ReturnCode::Compare_Different);
-		TestRemoteProcessMemLeaks("bbackupquery.memleaks");
+		TEST_COMPARE(Compare_Different, "", "-acEQ");
 
-		TEST_THAT(ServerIsAlive(bbackupd_pid));
-		TEST_THAT(ServerIsAlive(bbstored_pid));
-		if (!ServerIsAlive(bbackupd_pid)) return 1;
-		if (!ServerIsAlive(bbstored_pid)) return 1;
-		if (failures) return 1;
-
 		// check that the excluded files did not make it
 		// into the store, and the included files did
 		printf("\n==== Check that exclude/alwaysinclude commands "
@@ -3228,8 +3223,8 @@
 			"actually work\n");
 
 		{
-			std::auto_ptr<BackupProtocolClient> client = 
-				ConnectAndLogin(context,
+			std::auto_ptr<BackupProtocolCallable> client =
+				connect_and_login(context,
 				BackupProtocolLogin::Flags_ReadOnly);
 			
 			std::auto_ptr<BackupStoreDirectory> dir = 
@@ -3398,8 +3393,8 @@
 		int64_t restoredirid = 0;
 		{
 			// connect and log in
-			std::auto_ptr<BackupProtocolClient> client = 
-				ConnectAndLogin(context,
+			std::auto_ptr<BackupProtocolCallable> client = 
+				connect_and_login(context,
 					BackupProtocolLogin::Flags_ReadOnly);
 
 			// Find the ID of the Test1 directory
@@ -3540,13 +3535,7 @@
 	
 		// Add some more files and modify others
 		// Use the m flag this time so they have a recent modification time
-		#ifdef WIN32
-			TEST_THAT(::system("tar xzvmf testfiles/test3.tgz "
-				"-C testfiles") == 0);
-		#else
-			TEST_THAT(::system("gzip -d < testfiles/test3.tgz "
-				"| ( cd testfiles && tar xmf - )") == 0);
-		#endif
+		TEST_THAT(unpack_files("test3", "testfiles", "-m"));
 		
 		// Wait and test
 		wait_for_backup_operation("bbackupd to sync new files");
@@ -3569,13 +3558,7 @@
 		TEST_COMPARE(Compare_Same);
 
 		// and again, but with quick flag
-		compareReturnValue = ::system(BBACKUPQUERY " "
-			"-c testfiles/bbackupd.conf "
-			"-l testfiles/query6q.log "
-			"-Wwarning \"compare -acqQ\" quit");
-		TEST_RETURN(compareReturnValue,
-			BackupQueries::ReturnCode::Compare_Same);
-		TestRemoteProcessMemLeaks("bbackupquery.memleaks");
+		TEST_COMPARE(Compare_Same, "", "-acqQ");
 
 		// Rename some files -- one under the threshold, others above
 		printf("\n==== Rename files\n");
@@ -3645,8 +3628,8 @@
 			{
 				try
 				{
-					std::auto_ptr<BackupProtocolClient>
-						protocol = Connect(context);
+					std::auto_ptr<BackupProtocolCallable>
+						protocol = connect_to_bbstored(context);
 					// Make sure the marker isn't zero,
 					// because that's the default, and
 					// it should have changed
@@ -3694,14 +3677,9 @@
 		// Test that there *are* differences
 		TEST_COMPARE(Compare_Different);
 	
-		TEST_THAT(ServerIsAlive(bbackupd_pid));
-		TEST_THAT(ServerIsAlive(bbstored_pid));
-		if (!ServerIsAlive(bbackupd_pid)) return 1;
-		if (!ServerIsAlive(bbstored_pid)) return 1;
-		if (failures) return 1;
+		wait_for_operation(BACKUP_ERROR_RETRY_SECONDS,
+			"bbackupd to recover");
 
-		wait_for_operation(100, "bbackupd to recover");
-
 		// Then check it has backed up successfully.
 		TEST_COMPARE(Compare_Same);
 
@@ -3766,8 +3744,8 @@
 		printf("\n==== Check restore deleted files\n");
 
 		{
-			std::auto_ptr<BackupProtocolClient> client = 
-				ConnectAndLogin(context, 0 /* read-write */);
+			std::auto_ptr<BackupProtocolCallable> client =
+				connect_and_login(context, 0 /* read-write */);
 
 			// Do restore and undelete
 			TEST_THAT(BackupClientRestore(*client, deldirid, 
@@ -3783,15 +3761,8 @@
 			client.reset();
 
 			// Do a compare with the now undeleted files
-			compareReturnValue = ::system(BBACKUPQUERY " "
-				"-c testfiles/bbackupd.conf "
-				"-l testfiles/query11.log "
-				"-Wwarning "
-				"\"compare -cEQ Test1/x1 "
-				"testfiles/restore-Test1-x1-2\" quit");
-			TEST_RETURN(compareReturnValue,
-				BackupQueries::ReturnCode::Compare_Same);
-			TestRemoteProcessMemLeaks("bbackupquery.memleaks");
+			TEST_COMPARE(Compare_Same, "", "-cEQ Test1/x1 "
+				"testfiles/restore-Test1-x1-2");
 		}
 		
 		// Final check on notifications
@@ -3858,6 +3829,7 @@
 			// still no read errors?
 			TEST_THAT(!TestFileExists("testfiles/"
 				"notifyran.read-error.2"));
+			TEST_COMPARE(Compare_Same);
 		}
 
 		TEST_THAT(ServerIsAlive(bbackupd_pid));
@@ -3868,19 +3840,6 @@
 
 		if (handle != 0)
 		{
-			// compare, and check that it works
-			// reports the correct error message (and finishes)
-			TEST_THAT(compare_all(false));
-		}
-
-		TEST_THAT(ServerIsAlive(bbackupd_pid));
-		TEST_THAT(ServerIsAlive(bbstored_pid));
-		if (!ServerIsAlive(bbackupd_pid)) return 1;
-		if (!ServerIsAlive(bbstored_pid)) return 1;
-		if (failures) return 1;
-
-		if (handle != 0)
-		{
 			// open the file again, compare and check that compare
 			// reports the correct error message (and finishes)
 			handle = openfile("testfiles/TestDir1/lockedfile",




More information about the Boxbackup-commit mailing list