commit - 8b2180d40ae950c447339c459dc82e4708136cbf
commit + b419fc475bafd6efb01d324f86b462e1a24eda93
blob - 8c6c1506e6a1ce41d6b432ec25ddd744d509e7a9
blob + 8706e35fba0b89f57c66633608d8653ef595eba2
--- include/got_error.h
+++ include/got_error.h
#define GOT_ERR_PRIVSEP_PIPE 37
#define GOT_ERR_PRIVSEP_NO_FD 38
#define GOT_ERR_PRIVSEP_MSG 39
+#define GOT_ERR_PRIVSEP_DIED 40
+#define GOT_ERR_PRIVSEP_EXIT 41
static const struct got_error {
int code;
{ GOT_ERR_PRIVSEP_PIPE, "unprivileged process closed pipe" },
{ GOT_ERR_PRIVSEP_NO_FD,"out of file descriptors for privsep" },
{ GOT_ERR_PRIVSEP_MSG,"unexpected message from unprivileged process" },
+ { GOT_ERR_PRIVSEP_DIED,"unprivileged process died unexpectedly" },
+ { GOT_ERR_PRIVSEP_EXIT,"bad exit code from unprivileged process" },
};
/*
blob - 070c41a421af9076bc2ee24a8adba8ba911a2a60
blob + c3822193b294b2380efac47729fd22101b9c0157
--- lib/object.c
+++ lib/object.c
imsg_clear(&ibuf);
close(imsg_fds[1]);
_exit(status);
+}
+
+static const struct got_error *
+wait_for_child(pid_t pid)
+{
+ int child_status;
+
+ waitpid(pid, &child_status, 0);
+
+ if (!WIFEXITED(child_status))
+ return got_error(GOT_ERR_PRIVSEP_DIED);
+
+ if (WEXITSTATUS(child_status) != 0)
+ return got_error(GOT_ERR_PRIVSEP_EXIT);
+
+ return NULL;
}
static const struct got_error *
{
struct imsgbuf parent_ibuf;
int imsg_fds[2];
- const struct got_error *err = NULL;
+ const struct got_error *err = NULL, *err_child = NULL;
pid_t pid;
- int child_status;
if (socketpair(AF_UNIX, SOCK_STREAM, PF_UNSPEC, imsg_fds) == -1)
return got_error_from_errno();
imsg_init(&parent_ibuf, imsg_fds[0]);
err = got_privsep_recv_obj(obj, &parent_ibuf);
imsg_clear(&parent_ibuf);
- waitpid(pid, &child_status, 0);
+ err_child = wait_for_child(pid);
close(imsg_fds[0]);
- return err;
+ return err ? err : err_child;
}
static const struct got_error *
read_commit_object_privsep(struct got_commit_object **commit,
struct got_repository *repo, struct got_object *obj, int fd)
{
- const struct got_error *err = NULL;
+ const struct got_error *err = NULL, *err_child = NULL;
struct imsgbuf parent_ibuf;
int imsg_fds[2];
pid_t pid;
- int child_status;
if (socketpair(AF_UNIX, SOCK_STREAM, PF_UNSPEC, imsg_fds) == -1)
return got_error_from_errno();
imsg_init(&parent_ibuf, imsg_fds[0]);
err = got_privsep_recv_commit(commit, &parent_ibuf);
imsg_clear(&parent_ibuf);
- waitpid(pid, &child_status, 0);
+ err_child = wait_for_child(pid);
close(imsg_fds[0]);
- return err;
+ return err ? err : err_child;
}
const struct got_error *
read_tree_object_privsep(struct got_tree_object **tree, struct got_object *obj,
int fd)
{
- const struct got_error *err = NULL;
+ const struct got_error *err = NULL, *err_child = NULL;
struct imsgbuf parent_ibuf;
int imsg_fds[2];
pid_t pid;
- int child_status;
if (socketpair(AF_UNIX, SOCK_STREAM, PF_UNSPEC, imsg_fds) == -1)
return got_error_from_errno();
imsg_init(&parent_ibuf, imsg_fds[0]);
err = got_privsep_recv_tree(tree, &parent_ibuf);
imsg_clear(&parent_ibuf);
- waitpid(pid, &child_status, 0);
+ err_child = wait_for_child(pid);
close(imsg_fds[0]);
- return err;
+ return err ? err : err_child;
}
const struct got_error *
{
struct imsgbuf parent_ibuf;
int imsg_fds[2];
- const struct got_error *err = NULL;
+ const struct got_error *err = NULL, *err_child = NULL;
pid_t pid;
- int child_status;
if (socketpair(AF_UNIX, SOCK_STREAM, PF_UNSPEC, imsg_fds) == -1)
return got_error_from_errno();
imsg_init(&parent_ibuf, imsg_fds[0]);
err = got_privsep_recv_blob(size, &parent_ibuf);
imsg_clear(&parent_ibuf);
- waitpid(pid, &child_status, 0);
+ err_child = wait_for_child(pid);
close(imsg_fds[0]);
if (lseek(outfd, SEEK_SET, 0) == -1)
err = got_error_from_errno();
- return err;
+ return err ? err : err_child;
}
const struct got_error *