Net-LibNFS

 view release on metacpan or  search on metacpan

libnfs/lib/nfs_v3.c  view on Meta::CPAN

}

int
nfs3_utimes_async_internal(struct nfs_context *nfs, const char *path,
                           int no_follow, struct timeval *times,
                           nfs_cb cb, void *private_data)
{
	struct timeval *new_times = NULL;

	if (times != NULL) {
		new_times = malloc(sizeof(struct timeval)*2);
		if (new_times == NULL) {
			nfs_set_error(nfs, "Failed to allocate memory "
                                      "for timeval structure");
			return -1;
		}

		memcpy(new_times, times, sizeof(struct timeval)*2);
	}

	if (nfs3_lookuppath_async(nfs, path, no_follow, cb, private_data,
                                  nfs3_utimes_continue_internal,
                                  new_times, free, 0) != 0) {
		return -1;
	}

	return 0;
}

int
nfs3_utime_async(struct nfs_context *nfs, const char *path,
                 struct utimbuf *times, nfs_cb cb, void *private_data)
{
	struct timeval *new_times = NULL;

	if (times != NULL) {
		new_times = malloc(sizeof(struct timeval)*2);
		if (new_times == NULL) {
			nfs_set_error(nfs, "Failed to allocate memory "
                                      "for timeval structure");
			return -1;
		}

		new_times[0].tv_sec  = times->actime;
		new_times[0].tv_usec = 0;
		new_times[1].tv_sec  = times->modtime;
		new_times[1].tv_usec = 0;
	}

	if (nfs3_lookuppath_async(nfs, path, 0, cb, private_data,
                                  nfs3_utimes_continue_internal,
                                  new_times, free, 0) != 0) {
		return -1;
	}

	return 0;
}

        
static void
nfs3_chown_cb(struct rpc_context *rpc, int status, void *command_data,
              void *private_data)
{
	struct nfs_cb_data *data = private_data;
	struct nfs_context *nfs = data->nfs;
	SETATTR3res *res;

	assert(rpc->magic == RPC_CONTEXT_MAGIC);

	if (check_nfs3_error(nfs, status, data, command_data)) {
		free_nfs_cb_data(data);
		return;
	}

	res = command_data;
	if (res->status != NFS3_OK) {
		nfs_set_error(nfs, "NFS: SETATTR failed with %s(%d)",
                              nfsstat3_to_str(res->status),
                              nfsstat3_to_errno(res->status));
		data->cb(nfsstat3_to_errno(res->status), nfs,
                         nfs_get_error(nfs), data->private_data);
		free_nfs_cb_data(data);
		return;
	}

	data->cb(0, nfs, NULL, data->private_data);
	free_nfs_cb_data(data);
}

struct nfs_chown_data {
       uid_t uid;
       gid_t gid;
};

static int
nfs3_chown_continue_internal(struct nfs_context *nfs,
                             struct nfs_attr *attr _U_,
                             struct nfs_cb_data *data)
{
	SETATTR3args args;
	struct nfs_chown_data *chown_data = data->continue_data;

	memset(&args, 0, sizeof(SETATTR3args));
	args.object.data.data_len = data->fh.len;
	args.object.data.data_val = data->fh.val;
	if (chown_data->uid != (uid_t)-1) {
		args.new_attributes.uid.set_it = 1;
		args.new_attributes.uid.set_uid3_u.uid = chown_data->uid;
	}
	if (chown_data->gid != (gid_t)-1) {
		args.new_attributes.gid.set_it = 1;
		args.new_attributes.gid.set_gid3_u.gid = chown_data->gid;
	}

	if (rpc_nfs3_setattr_async(nfs->rpc, nfs3_chown_cb, &args, data) != 0) {
		nfs_set_error(nfs, "RPC error: Failed to send SETATTR "
                              "call for %s", data->path);
		data->cb(-ENOMEM, nfs, nfs_get_error(nfs),
                         data->private_data);
		free_nfs_cb_data(data);
		return -1;
	}
	return 0;
}

int
nfs3_chown_async_internal(struct nfs_context *nfs, const char *path,
                          int no_follow, int uid, int gid,
                          nfs_cb cb, void *private_data)
{
	struct nfs_chown_data *chown_data;

	chown_data = malloc(sizeof(struct nfs_chown_data));
	if (chown_data == NULL) {
		nfs_set_error(nfs, "Failed to allocate memory for "
                              "chown data structure");
		return -1;
	}

	chown_data->uid = uid;
	chown_data->gid = gid;

	if (nfs3_lookuppath_async(nfs, path, no_follow, cb, private_data,
                                  nfs3_chown_continue_internal,
                                  chown_data, free, 0) != 0) {
		return -1;
	}

	return 0;
}

int
nfs3_fchown_async(struct nfs_context *nfs, struct nfsfh *nfsfh, int uid,
                  int gid, nfs_cb cb, void *private_data)
{
	struct nfs_cb_data *data;
	struct nfs_chown_data *chown_data;

	chown_data = malloc(sizeof(struct nfs_chown_data));
	if (chown_data == NULL) {
		nfs_set_error(nfs, "Failed to allocate memory for "
                              "fchown data structure");
		return -1;
	}

	chown_data->uid = uid;
	chown_data->gid = gid;

	data = malloc(sizeof(struct nfs_cb_data));
	if (data == NULL) {
		nfs_set_error(nfs, "out of memory. failed to allocate "
                              "memory for fchown data");
		free(chown_data);
		return -1;
	}
	memset(data, 0, sizeof(struct nfs_cb_data));
	data->nfs           = nfs;
	data->cb            = cb;
	data->private_data  = private_data;
	data->continue_data = chown_data;
	data->free_continue_data = free;
	data->fh.len = nfsfh->fh.len;
	data->fh.val = malloc(data->fh.len);
	if (data->fh.val == NULL) {
		nfs_set_error(nfs, "Out of memory: Failed to allocate fh");
		free_nfs_cb_data(data);
		return -1;
	}
	memcpy(data->fh.val, nfsfh->fh.val, data->fh.len);

	if (nfs3_chown_continue_internal(nfs, NULL, data) != 0) {
		return -1;
	}

	return 0;
}

static void
nfs3_chmod_cb(struct rpc_context *rpc, int status, void *command_data,
              void *private_data)
{
	struct nfs_cb_data *data = private_data;
	struct nfs_context *nfs = data->nfs;
	SETATTR3res *res;

	assert(rpc->magic == RPC_CONTEXT_MAGIC);

	if (check_nfs3_error(nfs, status, data, command_data)) {
		free_nfs_cb_data(data);
		return;
	}

	res = command_data;
	if (res->status != NFS3_OK) {
		nfs_set_error(nfs, "NFS: SETATTR failed with %s(%d)",
                              nfsstat3_to_str(res->status),
                              nfsstat3_to_errno(res->status));
		data->cb(nfsstat3_to_errno(res->status), nfs,
                         nfs_get_error(nfs), data->private_data);
		free_nfs_cb_data(data);
		return;
	}

	nfs_dircache_drop(nfs, &data->fh);
	data->cb(0, nfs, NULL, data->private_data);
	free_nfs_cb_data(data);
}

static int
nfs3_chmod_continue_internal(struct nfs_context *nfs,
                             struct nfs_attr *attr _U_,
                             struct nfs_cb_data *data)
{
	SETATTR3args args;

	memset(&args, 0, sizeof(SETATTR3args));
	args.object.data.data_len = data->fh.len;
	args.object.data.data_val = data->fh.val;
	args.new_attributes.mode.set_it = 1;
	args.new_attributes.mode.set_mode3_u.mode = (mode3)data->continue_int;

	if (rpc_nfs3_setattr_async(nfs->rpc, nfs3_chmod_cb, &args, data) != 0) {
		nfs_set_error(nfs, "RPC error: Failed to send SETATTR "
                              "call for %s", data->path);
		data->cb(-ENOMEM, nfs, nfs_get_error(nfs),
                         data->private_data);
		free_nfs_cb_data(data);
		return -1;
	}
	return 0;
}



( run in 1.018 second using v1.01-cache-2.11-cpan-71847e10f99 )