Example #1
0
int async_fs_mkdir_sync(const char* path, int mode) {
	async_pool_enter(NULL);
	int rc = async_fs_mkdir_nosync(path, mode);
	if(rc >= 0) {
		rc = async_fs_sync_dirname(path);
	}
	async_pool_leave(NULL);
	return rc;
}
Example #2
0
int SLNSubmissionEnd(SLNSubmissionRef const sub) {
	if(!sub) return 0;
	if(sub->size <= 0) return UV_EINVAL;
	assert(sub->tmppath);
	assert(sub->tmpfile >= 0);
	assert(sub->type);

	sub->URIs = SLNHasherEnd(sub->hasher);
	sub->internalHash = strdup(SLNHasherGetInternalHash(sub->hasher));
	SLNHasherFree(&sub->hasher);
	if(!sub->URIs || !sub->internalHash) return UV_ENOMEM;

	SLNRepoRef const repo = SLNSubmissionGetRepo(sub);
	str_t *internalPath = NULL;
	bool worker = false;
	int rc = 0;

	rc = verify(sub);
	if(rc < 0) goto cleanup;

	internalPath = SLNRepoCopyInternalPath(repo, sub->internalHash);
	if(!internalPath) rc = UV_ENOMEM;
	if(rc < 0) goto cleanup;

	async_pool_enter(NULL); worker = true;

	rc = async_fs_fdatasync(sub->tmpfile);
	if(rc < 0) goto cleanup;

	// We use link(2) rather than rename(2) because link gives an error
	// if there's a name collision, rather than overwriting. We want to
	// keep the oldest file for any given hash, rather than the newest.
	rc = async_fs_link_mkdirp(sub->tmppath, internalPath);
	if(UV_EEXIST == rc) {
		rc = 0;
		goto cleanup;
	}
	if(rc < 0) {
		alogf("SLNSubmission couldn't move '%s' to '%s' (%s)\n", sub->tmppath, internalPath, sln_strerror(rc));
		goto cleanup;
	}

	rc = async_fs_sync_dirname(internalPath);

cleanup:
	if(worker) { async_pool_leave(NULL); worker = false; }
	FREE(&internalPath);

	async_fs_unlink(sub->tmppath);
	FREE(&sub->tmppath);
	return rc;
}