From a0676a969b4634af6e6c8d99bb84aabd0c48eab3 Mon Sep 17 00:00:00 2001 From: Joe Wingbermuehle Date: Thu, 12 May 2022 20:12:06 -0500 Subject: [PATCH] Better pipe handling (issue #563). --- src/command.c | 44 +++++++++++++++++++++----------------------- 1 file changed, 21 insertions(+), 23 deletions(-) diff --git a/src/command.c b/src/command.c index ee28e4ba..9f219222 100644 --- a/src/command.c +++ b/src/command.c @@ -164,9 +164,12 @@ char *ReadFromProcess(const char *command, unsigned timeout_ms) pid = fork(); if(pid == 0) { /* The child process. */ - close(ConnectionNumber(display)); - close(fds[0]); + if(display) { + close(ConnectionNumber(display)); + } dup2(fds[1], 1); /* stdout */ + close(fds[0]); + close(fds[1]); setsid(); execl(SHELL_NAME, SHELL_NAME, "-c", command, NULL); Warning(_("exec failed: (%s) %s"), SHELL_NAME, command); @@ -176,6 +179,7 @@ char *ReadFromProcess(const char *command, unsigned timeout_ms) unsigned buffer_size, max_size; TimeType start_time, current_time; + close(fds[1]); max_size = BLOCK_SIZE; buffer_size = 0; buffer = Allocate(max_size); @@ -185,13 +189,7 @@ char *ReadFromProcess(const char *command, unsigned timeout_ms) struct timeval tv; unsigned long diff_ms; fd_set fs; - int rc; - - /* Make sure we have room to read. */ - if(buffer_size + BLOCK_SIZE > max_size) { - max_size *= 2; - buffer = Reallocate(buffer, max_size); - } + int rc, got_read; FD_ZERO(&fs); FD_SET(fds[0], &fs); @@ -204,7 +202,7 @@ char *ReadFromProcess(const char *command, unsigned timeout_ms) tv.tv_usec = (diff_ms % 1000) * 1000; /* Wait for data (or a timeout). */ - rc = select(fds[0] + 1, &fs, &fs, &fs, &tv); + rc = select(fds[0] + 1, &fs, NULL, &fs, &tv); if(rc == 0) { close(fds[0]); /* Timeout */ @@ -215,19 +213,19 @@ char *ReadFromProcess(const char *command, unsigned timeout_ms) break; } - rc = read(fds[0], &buffer[buffer_size], BLOCK_SIZE); - if(rc > 0) { - buffer_size += rc; - } else { - /* Process exited, check for any leftovers and return. */ - do { - if(buffer_size + BLOCK_SIZE > max_size) { - max_size *= 2; - buffer = Reallocate(buffer, max_size); - } - rc = read(fds[0], &buffer[buffer_size], BLOCK_SIZE); - buffer_size += (rc > 0) ? rc : 0; - } while(rc > 0); + got_read = 0; + do { + /* Make sure we have room to read. */ + if(buffer_size + BLOCK_SIZE > max_size) { + max_size *= 2; + buffer = Reallocate(buffer, max_size); + } + rc = read(fds[0], &buffer[buffer_size], BLOCK_SIZE); + buffer_size += (rc > 0) ? rc : 0; + got_read = got_read || rc > 0; + } while(rc > 0); + if(!got_read) { + /* Process exited */ close(fds[0]); break; }