コード例 #1
0
ファイル: subr_nvlist.c プロジェクト: fengsi/freebsd
nvlist_t *
nvlist_recv(int sock, int flags)
{
	struct nvlist_header nvlhdr;
	nvlist_t *nvl, *ret;
	unsigned char *buf;
	size_t nfds, size, i;
	int *fds;

	if (buf_recv(sock, &nvlhdr, sizeof(nvlhdr)) == -1)
		return (NULL);

	if (!nvlist_check_header(&nvlhdr))
		return (NULL);

	nfds = (size_t)nvlhdr.nvlh_descriptors;
	size = sizeof(nvlhdr) + (size_t)nvlhdr.nvlh_size;

	buf = nv_malloc(size);
	if (buf == NULL)
		return (NULL);

	memcpy(buf, &nvlhdr, sizeof(nvlhdr));

	ret = NULL;
	fds = NULL;

	if (buf_recv(sock, buf + sizeof(nvlhdr), size - sizeof(nvlhdr)) == -1)
		goto out;

	if (nfds > 0) {
		fds = nv_malloc(nfds * sizeof(fds[0]));
		if (fds == NULL)
			goto out;
		if (fd_recv(sock, fds, nfds) == -1)
			goto out;
	}

	nvl = nvlist_xunpack(buf, size, fds, nfds, flags);
	if (nvl == NULL) {
		ERRNO_SAVE();
		for (i = 0; i < nfds; i++)
			close(fds[i]);
		ERRNO_RESTORE();
		goto out;
	}

	ret = nvl;
out:
	ERRNO_SAVE();
	nv_free(buf);
	nv_free(fds);
	ERRNO_RESTORE();

	return (ret);
}
コード例 #2
0
ファイル: nvlist.c プロジェクト: BillTheBest/libuinet
nvlist_t *
nvlist_recv(int sock)
{
	struct nvlist_header nvlhdr;
	nvlist_t *nvl, *ret;
	unsigned char *buf;
	size_t nfds, size;
	int serrno, *fds;

	if (buf_recv(sock, &nvlhdr, sizeof(nvlhdr)) == -1)
		return (NULL);

	if (!nvlist_check_header(&nvlhdr))
		return (NULL);

	nfds = (size_t)nvlhdr.nvlh_descriptors;
	size = sizeof(nvlhdr) + (size_t)nvlhdr.nvlh_size;

	buf = malloc(size);
	if (buf == NULL)
		return (NULL);

	memcpy(buf, &nvlhdr, sizeof(nvlhdr));

	ret = NULL;
	fds = NULL;

	if (buf_recv(sock, buf + sizeof(nvlhdr), size - sizeof(nvlhdr)) == -1)
		goto out;

	if (nfds > 0) {
		fds = malloc(nfds * sizeof(fds[0]));
		if (fds == NULL)
			goto out;
		if (fd_recv(sock, fds, nfds) == -1)
			goto out;
	}

	nvl = nvlist_xunpack(buf, size, fds, nfds);
	if (nvl == NULL)
		goto out;

	ret = nvl;
out:
	serrno = errno;
	free(buf);
	free(fds);
	errno = serrno;

	return (ret);
}
コード例 #3
0
const unsigned char *
nvlist_unpack_header(nvlist_t *nvl, const unsigned char *ptr, size_t nfds,
    bool *isbep, size_t *leftp)
{
	struct nvlist_header nvlhdr;
	int inarrayf;

	if (*leftp < sizeof(nvlhdr))
		goto fail;

	memcpy(&nvlhdr, ptr, sizeof(nvlhdr));

	if (!nvlist_check_header(&nvlhdr))
		goto fail;

	if (nvlhdr.nvlh_size != *leftp - sizeof(nvlhdr))
		goto fail;

	/*
	 * nvlh_descriptors might be smaller than nfds in embedded nvlists.
	 */
	if (nvlhdr.nvlh_descriptors > nfds)
		goto fail;

	if ((nvlhdr.nvlh_flags & ~NV_FLAG_ALL_MASK) != 0)
		goto fail;

	inarrayf = (nvl->nvl_flags & NV_FLAG_IN_ARRAY);
	nvl->nvl_flags = (nvlhdr.nvlh_flags & NV_FLAG_PUBLIC_MASK) | inarrayf;

	ptr += sizeof(nvlhdr);
	if (isbep != NULL)
		*isbep = (((int)nvlhdr.nvlh_flags & NV_FLAG_BIG_ENDIAN) != 0);
	*leftp -= sizeof(nvlhdr);

	return (ptr);
fail:
	ERRNO_SET(EINVAL);
	return (NULL);
}
コード例 #4
0
ファイル: nvlist.c プロジェクト: BillTheBest/libuinet
static const unsigned char *
nvlist_unpack_header(nvlist_t *nvl, const unsigned char *ptr, size_t nfds,
    int *flagsp, size_t *leftp)
{
	struct nvlist_header nvlhdr;

	if (*leftp < sizeof(nvlhdr))
		goto failed;

	memcpy(&nvlhdr, ptr, sizeof(nvlhdr));

	if (!nvlist_check_header(&nvlhdr))
		goto failed;

	if (nvlhdr.nvlh_size != *leftp - sizeof(nvlhdr))
		goto failed;

	/*
	 * nvlh_descriptors might be smaller than nfds in embedded nvlists.
	 */
	if (nvlhdr.nvlh_descriptors > nfds)
		goto failed;

	if ((nvlhdr.nvlh_flags & ~NV_FLAG_ALL_MASK) != 0)
		goto failed;

	nvl->nvl_flags = (nvlhdr.nvlh_flags & NV_FLAG_PUBLIC_MASK);

	ptr += sizeof(nvlhdr);
	*flagsp = (int)nvlhdr.nvlh_flags;
	*leftp -= sizeof(nvlhdr);

	return (ptr);
failed:
	errno = EINVAL;
	return (NULL);
}