Exemplo n.º 1
0
static
int send_fd_to_worker(struct run_as_worker *worker, enum run_as_cmd cmd, int fd)
{
	int ret = 0;

	switch (cmd) {
	case RUN_AS_EXTRACT_ELF_SYMBOL_OFFSET:
	case RUN_AS_EXTRACT_SDT_PROBE_OFFSETS:
	case RUN_AS_MKDIRAT:
	case RUN_AS_MKDIRAT_RECURSIVE:
		break;
	default:
		return 0;
	}

	if (fd < 0) {
		ERR("Refusing to send invalid fd to worker (fd = %i)", fd);
		return -1;
	}

	ret = do_send_fd(worker->sockpair[0], fd);
	if (ret < 0) {
		PERROR("do_send_fd");
		ret = -1;
	}

	return ret;
}
Exemplo n.º 2
0
static
int send_fd_to_master(struct run_as_worker *worker, enum run_as_cmd cmd, int fd)
{
	int ret = 0, ret_close = 0;

	switch (cmd) {
	case RUN_AS_OPEN:
		break;
	default:
		return 0;
	}

	if (fd < 0) {
		DBG("Not sending file descriptor to master as it is invalid (fd = %i)", fd);
		return 0;
	}
	ret = do_send_fd(worker->sockpair[1], fd);
	if (ret < 0) {
		PERROR("do_send_fd error");
		ret = -1;
	}

	ret_close = close(fd);
	if (ret_close < 0) {
		PERROR("close");
	}

	return ret;
}
Exemplo n.º 3
0
/*
 * Return < 0 on error, 0 if OK, 1 on hangup.
 */
static
int handle_one_cmd(struct run_as_worker *worker)
{
	int ret = 0;
	struct run_as_data data;
	ssize_t readlen, writelen;
	struct run_as_ret sendret;
	run_as_fct cmd;
	uid_t prev_euid;

	/* Read data */
	readlen = lttcomm_recv_unix_sock(worker->sockpair[1], &data,
			sizeof(data));
	if (readlen == 0) {
		/* hang up */
		ret = 1;
		goto end;
	}
	if (readlen < sizeof(data)) {
		PERROR("lttcomm_recv_unix_sock error");
		ret = -1;
		goto end;
	}

	cmd = run_as_enum_to_fct(data.cmd);
	if (!cmd) {
		ret = -1;
		goto end;
	}

	prev_euid = getuid();
	if (data.gid != getegid()) {
		ret = setegid(data.gid);
		if (ret < 0) {
			PERROR("setegid");
			goto write_return;
		}
	}
	if (data.uid != prev_euid) {
		ret = seteuid(data.uid);
		if (ret < 0) {
			PERROR("seteuid");
			goto write_return;
		}
	}
	/*
	 * Also set umask to 0 for mkdir executable bit.
	 */
	umask(0);
	ret = (*cmd)(&data);

write_return:
	sendret.ret = ret;
	sendret._errno = errno;
	/* send back return value */
	writelen = lttcomm_send_unix_sock(worker->sockpair[1], &sendret,
			sizeof(sendret));
	if (writelen < sizeof(sendret)) {
		PERROR("lttcomm_send_unix_sock error");
		ret = -1;
		goto end;
	}
	ret = do_send_fd(worker, data.cmd, ret);
	if (ret) {
		PERROR("do_send_fd error");
		ret = -1;
		goto end;
	}
	if (seteuid(prev_euid) < 0) {
		PERROR("seteuid");
		ret = -1;
		goto end;
	}
	ret = 0;
end:
	return ret;
}