summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorNathan Straz <nstraz@redhat.com>2013-09-19 17:22:03 -0400
committerNathan Straz <nstraz@redhat.com>2013-09-19 17:22:03 -0400
commit2da3d279e360bfb4ac470874d4b43b765b6596fa (patch)
treeb712cb32baf01eddfa4bba8c3a090817aa6c38eb
parentfe8b924760c9ad8b81100a195f29b9c0eff54736 (diff)
Handle stdin pipe closing on us
If xiogen is flooding requests across qarsh and xdoio decides to stop, we need to handle that gracefully. Also, making the pipe non-blocking was not a good idea, xdoio gets the read error EAGAIN and stops there.
-rw-r--r--qarsh.c6
-rw-r--r--qarshd.c11
-rw-r--r--qarshd@.service1
3 files changed, 15 insertions, 3 deletions
diff --git a/qarsh.c b/qarsh.c
index 51a876b..2683591 100644
--- a/qarsh.c
+++ b/qarsh.c
@@ -395,6 +395,12 @@ run_remote_cmd(char *cmdline)
fprintf(stderr, "ERROR: Received data allow for fd %d\n",
qp->qp_dallow.qp_remfd);
}
+ } else if (qp->qp_type == QP_RETURNCODE) { /* qarshd hit an error while writing to stdin */
+ fprintf(stderr, "Remote command hit I/O error: %s\n", qp->qp_returncode.qp_strerror);
+ close(fileno(stdin));
+ allowed_in = -1;
+ } else {
+ fprintf(stderr, "Unexpected packet type %s\n", qp_packet_type(qp->qp_type));
}
qpfree(qp);
nset--;
diff --git a/qarshd.c b/qarshd.c
index b911ef7..d686078 100644
--- a/qarshd.c
+++ b/qarshd.c
@@ -117,7 +117,7 @@ run_cmd(const char *cmd)
pid_t pid;
int pipefds[2], parentfds[3];
- pipe2(pipefds, O_NONBLOCK);
+ pipe(pipefds);
childfds[0] = pipefds[1]; parentfds[0] = pipefds[0]; /* stdin */
pipe(pipefds);
childfds[1] = pipefds[0]; parentfds[1] = pipefds[1]; /* stdout */
@@ -310,6 +310,7 @@ handle_qarsh()
sa.sa_mask = sigmask;
sa.sa_flags = SA_RESTART;
sigaction(SIGCHLD, &sa, NULL);
+ signal(SIGPIPE, SIG_IGN);
qp = make_qp_data_allow(0, QARSHD_BUFSIZE);
send_packet(qoutfd, qp);
@@ -416,7 +417,13 @@ handle_qarsh()
if (nfd && FD_ISSET(childfds[0], &wfds)) {
/* Child is ready for data on stdin */
nbytes = write(childfds[0], buf_in, z_in);
- if (nbytes == z_in) {
+ if (nbytes == -1) { /* Don't try writing to the child again */
+ close(childfds[0]);
+ childfds[0] = -1;
+ qp = make_qp_returncode(-1, errno, strerror(errno));
+ send_packet(qoutfd, qp);
+ qpfree(qp);
+ } else if (nbytes == z_in) {
z_in = 0;
if (eof_in) {
close(childfds[0]);
diff --git a/qarshd@.service b/qarshd@.service
index 875f924..408a6f5 100644
--- a/qarshd@.service
+++ b/qarshd@.service
@@ -5,4 +5,3 @@ Description=qarsh Per-Connection Server
ExecStart=/usr/sbin/qarshd
StandardInput=socket
StandardError=journal
-IgnoreSIGPIPE=no