Пример #1
0
static int merge_into_global_sparse(const char *sparse, const char *global)
{
	int ret=-1;
	char *tmpfile=NULL;
	struct stat statp;
	struct lock *lock=NULL;
	const char *globalsrc=NULL;
	
	if(!(tmpfile=get_global_sparse_tmp(global)))
		goto end;

	if(!(lock=try_to_get_sparse_lock(global)))
		goto end;

	if(!lstat(global, &statp)) globalsrc=global;

	if(merge_sparse_indexes(tmpfile, globalsrc, sparse))
		goto end;

	// FIX THIS: nasty race condition needs to be recoverable.
	if(do_rename(tmpfile, global)) goto end;

	ret=0;
end:
	lock_release(lock);
	lock_free(&lock);
	free_w(&tmpfile);
	return ret;
}
Пример #2
0
static int merge_into_global_sparse(const char *sparse, const char *global,
	struct conf **confs)
{
	int ret=-1;
	char *tmpfile=NULL;
	struct stat statp;
	char *lockfile=NULL;
	struct lock *lock=NULL;
	const char *globalsrc=NULL;
	
	if(!(tmpfile=prepend_n(global, "tmp", strlen("tmp"), ".")))
		goto end;

	// Get a lock before messing with the global sparse index.
	if(!(lockfile=prepend_n(global, "lock", strlen("lock"), "."))
	  || !(lock=lock_alloc_and_init(lockfile)))
		goto end;

	if(try_to_get_lock(lock)) goto end;

	if(!lstat(global, &statp)) globalsrc=global;

	if(merge_sparse_indexes(sparse, globalsrc, tmpfile, confs))
		goto end;

	// FIX THIS: nasty race condition needs to be recoverable.
	if(do_rename(tmpfile, global)) goto end;

	ret=0;
end:
	lock_release(lock);
	lock_free(&lock);
	if(lockfile) free(lockfile);
	if(tmpfile) free(tmpfile);
	return ret;
}
Пример #3
0
int backup_phase4_server_protocol2(struct sdirs *sdirs, struct conf **confs)
{
	int ret=-1;
	uint64_t i=0;
	uint64_t pass=0;
	char *sparse=NULL;
	char *global_sparse=NULL;
	char *h1dir=NULL;
	char *h2dir=NULL;
	char *hooksdir=NULL;
	char *srca=NULL;
	char *srcb=NULL;
	char *dst=NULL;
	char compa[32]="";
	char compb[32]="";
	char compd[32]="";
	struct manio *newmanio=NULL;
	char *logpath=NULL;
	char *fmanifest=NULL; // FIX THIS: should be part of sdirs.

	if(!(logpath=prepend_s(sdirs->finishing, "log")))
		goto end;
	if(set_logfp(logpath, confs))
		goto end;

	logp("Begin phase4 (sparse generation)\n");

	if(!(newmanio=manio_alloc())
	  || !(fmanifest=prepend_s(sdirs->finishing, "manifest"))
	  || manio_init_read(newmanio, fmanifest)
	  || manio_read_fcount(newmanio)
	  || !(hooksdir=prepend_s(fmanifest, "hooks"))
	  || !(h1dir=prepend_s(fmanifest, "h1"))
	  || !(h2dir=prepend_s(fmanifest, "h2")))
		goto end;

	while(1)
	{
		char *srcdir=NULL;
		char *dstdir=NULL;
		if(!pass)
		{
			srcdir=hooksdir;
			dstdir=h1dir;
		}
		else if(pass%2)
		{
			srcdir=h1dir;
			dstdir=h2dir;
		}
		else
		{
			srcdir=h2dir;
			dstdir=h1dir;
		}
		pass++;
		for(i=0; i<newmanio->offset.fcount; i+=2)
		{
			free_w(&srca);
			free_w(&srcb);
			free_w(&dst);
			snprintf(compa, sizeof(compa), "%08"PRIX64, i);
			snprintf(compb, sizeof(compb), "%08"PRIX64, i+1);
			snprintf(compd, sizeof(compd), "%08"PRIX64, i/2);
			if(!(srca=prepend_s(srcdir, compa))
			  || !(dst=prepend_s(dstdir, compd)))
				goto end;
			if(i+1<newmanio->offset.fcount
			  && !(srcb=prepend_s(srcdir, compb)))
				goto end;
			if(merge_sparse_indexes(srca, srcb, dst, confs))
				goto end;
		}
		if((newmanio->offset.fcount=i/2)<2) break;
	}

	if(!(sparse=prepend_s(fmanifest, "sparse"))
	  || !(global_sparse=prepend_s(sdirs->data, "sparse")))
		goto end;

	// FIX THIS: nasty race condition here needs to be automatically
	// recoverable.
	if(do_rename(dst, sparse)) goto end;

	if(merge_into_global_sparse(sparse, global_sparse, confs)) goto end;

	logp("End phase4 (sparse generation)\n");

	ret=0;
end:
	manio_free(&newmanio);
	free_w(&sparse);
	free_w(&global_sparse);
	free_w(&srca);
	free_w(&srcb);
	recursive_delete(h1dir, NULL, 1);
	recursive_delete(h2dir, NULL, 1);
	free_w(&h1dir);
	free_w(&h2dir);
	free_w(&logpath);
	free_w(&fmanifest);
	return ret;
}