From: Michael D. Lowis Date: Fri, 11 Dec 2020 03:52:37 +0000 (-0500) Subject: implemented dial command X-Git-Url: https://git.mdlowis.com/?a=commitdiff_plain;h=e524b3337347d6979a08a593d6f7da8b3b7d6587;p=proto%2Faos.git implemented dial command --- diff --git a/bin/dial.c b/bin/dial.c index ef5373f..d66a2d0 100644 --- a/bin/dial.c +++ b/bin/dial.c @@ -2,6 +2,34 @@ #include #include +int copy_data(int fromfd, int tofd, int events) +{ + char buf[16384]; + int open = 1; + + if (events & POLLIN) + { + long nread; + if ((nread = read(fromfd, buf, sizeof(buf))) > 0) + { + write(tofd, buf, nread); + } + else + { + open = 0; + } + } + + if (!open || (events & (POLLHUP|POLLERR))) + { + perror("close():"); + close(fromfd); + open = 0; + } + + return open; +} + int main(int argc, char** argv) { if (argc < 2) @@ -10,32 +38,32 @@ int main(int argc, char** argv) return 1; } - int sockfd = netdial(argv[1]); - - char buf[8192]; - struct pollfd fds[] = { - { .fd = sockfd, .events = POLLIN }, - { .fd = STDIN_FILENO, .events = POLLIN }, - }; - - while(1) + int running = 1; + int sockfd = netdial(argv[1]); + int cmdinfd = STDIN_FILENO; + int cmdoutfd = STDOUT_FILENO; + if (argc > 2) { - if (poll(fds, nelem(fds), -1) < 0) - { - fatal("poll():"); - } - - if (fds[0].revents & POLLIN) + cmdinfd = fork_exec(&argv[2]); + cmdoutfd = cmdinfd; + if (cmdinfd < 0) { - write(fds[1].fd, buf, read(fds[0].fd, buf, sizeof(buf))); - fds[0].revents = 0; + fatal("fork_exec():"); } + } - if (fds[1].revents & POLLIN) + while (running) + { + struct pollfd fds[] = { + { .fd = sockfd, .events = POLLIN }, + { .fd = cmdinfd, .events = POLLIN }, + }; + if (poll(fds, nelem(fds), -1) < 0) { - write(fds[0].fd, buf, read(fds[1].fd, buf, sizeof(buf))); - fds[0].revents = 0; + fatal("poll():"); } + running = running && copy_data(sockfd, cmdoutfd, fds[0].revents); + running = running && copy_data(cmdinfd, sockfd, fds[1].revents); } close(sockfd); diff --git a/inc/liba.h b/inc/liba.h index 1d72e44..d181469 100644 --- a/inc/liba.h +++ b/inc/liba.h @@ -140,8 +140,6 @@ static inline char* _getopt_(int* p_argc, char*** p_argv) { typedef char unique_id[( expr )?1:-1] #endif - - void fatal(const char* fmt, ...); void warn(const char* fmt, ...); void esignal(int sig, void (*func)(int)); @@ -153,3 +151,4 @@ char* smprintf(const char* fmt, ...); FILE* efopen(const char* filename, const char* mode); char* efreadline(FILE* input); char* estrdup(const char *s); +int fork_exec(char** cmd); diff --git a/lib/a/fork_exec.c b/lib/a/fork_exec.c new file mode 100644 index 0000000..927f305 --- /dev/null +++ b/lib/a/fork_exec.c @@ -0,0 +1,35 @@ +#include +#include +#include +#include + +int fork_exec(char** cmd) +{ + int pid, fds[2] = {-1,-1}; + /* create the sockets */ + if (!socketpair(AF_UNIX, SOCK_STREAM, 0, fds)) + { + /* create the process */ + if ((pid = fork()) < 0) + { + close(fds[0]), close(fds[1]), fds[0] = -1; + } + else if (0 == pid) + { + /* redirect child process's io to the pipes */ + if ((dup2(fds[1], 0) < 0) || (dup2(fds[1], 1) < 0) || (dup2(fds[1], 2) < 0)) + { + fatal("failed to pipe"); + } + /* execute the process */ + close(fds[0]); + exit(execvp(cmd[0], cmd)); + } + else + { + close(fds[1]); + fcntl(fds[0], F_SETFL, fcntl(fds[0], F_GETFL, 0) | O_NONBLOCK); + } + } + return fds[0]; +} diff --git a/lib/net/netresolve.c b/lib/net/netresolve.c index 44a29c1..b3ed729 100644 --- a/lib/net/netresolve.c +++ b/lib/net/netresolve.c @@ -1,9 +1,7 @@ #include #include -#include #include -#include -#include +#include #include struct in_addr netresolve(char *hostname)