diff options
author | Peter Wu <lekensteyn@gmail.com> | 2012-09-26 15:04:18 +0200 |
---|---|---|
committer | Peter Wu <lekensteyn@gmail.com> | 2012-09-26 15:04:18 +0200 |
commit | 2497c1392b81e093f4de2541a98746aebd449a7f (patch) | |
tree | db87e59d4c70c677ddb1899d9161b004f6e454ac /pipe.cpp | |
download | c-files-2497c1392b81e093f4de2541a98746aebd449a7f.tar.gz |
Initial commit
Diffstat (limited to 'pipe.cpp')
-rw-r--r-- | pipe.cpp | 56 |
1 files changed, 56 insertions, 0 deletions
diff --git a/pipe.cpp b/pipe.cpp new file mode 100644 index 0000000..76cd19d --- /dev/null +++ b/pipe.cpp @@ -0,0 +1,56 @@ +#include <iostream> +#include <unistd.h> +#include <cstdio> +#include <sys/types.h> +#include <sys/wait.h> +#include <signal.h> +#include <fcntl.h> +#include <errno.h> + +#define BS 10 + +int main(int argc, char **argv) { + int fds[2], fu[2]; + if (argc <= 1){ + std::cerr << "Usage: " << argv[0] << " program args..." << std::endl; + return 1; + } + if (pipe(fds) == -1 || pipe(fu) == -1) { + perror("pipe"); + return 1; + } + pid_t p = fork(); + if (p == 0) { + /*child*/ + close(fu[1]); + close(fds[0]); + if (dup2(fu[0], STDIN_FILENO) == -1) perror("dup stdin"); + if (dup2(fds[1], STDOUT_FILENO) == -1) perror("dup stdout"); + execvp(argv[1], argv+1); + perror("Execvp"); + _exit(42); + } else { + char buf[BS]; + std::string in("meh\n\04"); + int flags = fcntl(fds[0], F_GETFL); + fcntl(fds[0], F_SETFL, flags | O_NONBLOCK); + close(fds[1]);close(fu[0]); + do { + int r = read(fds[0], buf, BS); + if (r == -1 && errno == EWOULDBLOCK) ; + else if (r == -1) perror("read"); + else if (r > 0) { + std::cout.write(buf, r); + } + if (write(fu[1], in.c_str(), in.size()) == -1) perror("write"); + int status = 0; + if (waitpid(p, &status, WNOHANG) != 0) { + if (WIFEXITED(status) || WTERMSIG(status)) { + break; + } + } + } while (1); + kill(p, 15); + } + return 0; +} |