X-Git-Url: http://git.madism.org/?a=blobdiff_plain;f=main-srsd.c;h=ce4113b3a6fd8703794c4e596e6169415b5204c8;hb=002766b52f65c43202f6649c5cd1e4a7e4dea885;hp=891f7ee83b4fed1a2c21402659d805d069ebdf55;hpb=083a49e2edd85f2aa4cc949f4cbf4e7b00cdb88c;p=apps%2Fpfixtools.git diff --git a/main-srsd.c b/main-srsd.c index 891f7ee..ce4113b 100644 --- a/main-srsd.c +++ b/main-srsd.c @@ -33,20 +33,17 @@ * Copyright © 2005-2007 Pierre Habouzit */ -#include -#include -#include -#include +#include "common.h" #include -#include "common.h" +#include "epoll.h" #include "mem.h" #include "buffer.h" #define DAEMON_NAME "pfix-srsd" -#define DEFAULT_ENCODER_PORT 10000 -#define DEFAULT_DECODER_PORT 10001 +#define DEFAULT_ENCODER_PORT 10001 +#define DEFAULT_DECODER_PORT 10002 #define RUNAS_USER "nobody" #define RUNAS_GROUP "nogroup" @@ -58,7 +55,6 @@ typedef struct srsd_t { unsigned listener : 1; unsigned decoder : 1; - unsigned watchwr : 1; int fd; buffer_t ibuf; buffer_t obuf; @@ -104,6 +100,11 @@ void urldecode(char *s, char *end) int process_srs(srs_t *srs, const char *domain, srsd_t *srsd) { + int res = buffer_read(&srsd->ibuf, srsd->fd, -1); + + if ((res < 0 && errno != EINTR && errno != EAGAIN) || res == 0) + return -1; + while (srsd->ibuf.len > 4) { char buf[BUFSIZ], *p, *q, *nl; int err; @@ -163,13 +164,12 @@ int process_srs(srs_t *srs, const char *domain, srsd_t *srsd) return 0; } -int start_listener(int epollfd, int port, bool decoder) +int start_listener(int port, bool decoder) { struct sockaddr_in addr = { .sin_family = AF_INET, .sin_addr = { htonl(INADDR_LOOPBACK) }, }; - struct epoll_event evt = { .events = EPOLLIN }; srsd_t *tmp; int sock; @@ -179,17 +179,31 @@ int start_listener(int epollfd, int port, bool decoder) return -1; } - evt.data.ptr = tmp = srsd_new(); + tmp = srsd_new(); tmp->fd = sock; tmp->decoder = decoder; tmp->listener = true; - if (epoll_ctl(epollfd, EPOLL_CTL_ADD, sock, &evt) < 0) { - UNIXERR("epoll_ctl"); - return -1; - } + epoll_register(sock, EPOLLIN, tmp); return 0; } +void start_client(srsd_t *srsd) +{ + srsd_t *tmp; + int sock; + + sock = accept_nonblock(srsd->fd); + if (sock < 0) { + UNIXERR("accept"); + return; + } + + tmp = srsd_new(); + tmp->decoder = srsd->decoder; + tmp->fd = sock; + epoll_register(sock, EPOLLIN, tmp); +} + /* }}} */ /* administrivia {{{ */ @@ -224,6 +238,7 @@ void usage(void) " (default: "STR(DEFAULT_DECODER_PORT)")\n" " -p file to write our pid to\n" " -u unsafe mode: don't drop privilegies\n" + " -f stay in foreground\n" , stderr); } @@ -231,30 +246,20 @@ void usage(void) int main_loop(srs_t *srs, const char *domain, int port_enc, int port_dec) { - int exitcode = EXIT_SUCCESS; - int epollfd = epoll_create(128); - - if (epollfd < 0) { - UNIXERR("epoll_create"); - exitcode = EXIT_FAILURE; - goto error; - } - - if (start_listener(epollfd, port_enc, false) < 0) + if (start_listener(port_enc, false) < 0) return EXIT_FAILURE; - if (start_listener(epollfd, port_dec, true) < 0) + if (start_listener(port_dec, true) < 0) return EXIT_FAILURE; while (!sigint) { struct epoll_event evts[1024]; int n; - n = epoll_wait(epollfd, evts, countof(evts), -1); + n = epoll_select(evts, countof(evts), -1); if (n < 0) { if (errno != EAGAIN && errno != EINTR) { UNIXERR("epoll_wait"); - exitcode = EXIT_FAILURE; - break; + return EXIT_FAILURE; } continue; } @@ -263,75 +268,33 @@ int main_loop(srs_t *srs, const char *domain, int port_enc, int port_dec) srsd_t *srsd = evts[n].data.ptr; if (srsd->listener) { - struct epoll_event evt = { .events = EPOLLIN }; - srsd_t *tmp; - int sock; - - sock = accept_nonblock(srsd->fd); - if (sock < 0) { - UNIXERR("accept"); - continue; - } - - evt.data.ptr = tmp = srsd_new(); - tmp->decoder = srsd->decoder; - tmp->fd = sock; - if (epoll_ctl(epollfd, EPOLL_CTL_ADD, sock, &evt) < 0) { - UNIXERR("epoll_ctl"); - srsd_delete(&tmp); - close(sock); - } + start_client(srsd); continue; } if (evts[n].events & EPOLLIN) { - int res = buffer_read(&srsd->ibuf, srsd->fd, -1); - - if ((res < 0 && errno != EINTR && errno != EAGAIN) - || res == 0) - { - srsd_delete(&srsd); - continue; - } - if (process_srs(srs, domain, srsd) < 0) { srsd_delete(&srsd); continue; } + if (srsd->obuf.len) { + epoll_register(srsd->fd, EPOLLIN | EPOLLOUT, srsd); + } } if ((evts[n].events & EPOLLOUT) && srsd->obuf.len) { - int res = write(srsd->fd, srsd->obuf.data, srsd->obuf.len); - - if (res < 0 && errno != EINTR && errno != EAGAIN) { + if (buffer_write(&srsd->obuf, srsd->fd) < 0) { srsd_delete(&srsd); continue; } - - if (res > 0) { - buffer_consume(&srsd->obuf, res); - } - } - - if (srsd->watchwr == !srsd->obuf.len) { - struct epoll_event evt = { - .events = EPOLLIN | (srsd->obuf.len ? EPOLLOUT : 0), - .data.ptr = srsd, - }; - if (epoll_ctl(epollfd, EPOLL_CTL_MOD, srsd->fd, &evt) < 0) { - UNIXERR("epoll_ctl"); - srsd_delete(&srsd); - continue; + if (!srsd->obuf.len) { + epoll_modify(srsd->fd, EPOLLIN, srsd); } - srsd->watchwr = srsd->obuf.len != 0; } } } - close(epollfd); - - error: - return exitcode; + return EXIT_SUCCESS; } static srs_t *srs_read_secrets(const char *sfile) @@ -378,25 +341,22 @@ static srs_t *srs_read_secrets(const char *sfile) int main(int argc, char *argv[]) { bool unsafe = false; + bool daemonize = true; int port_enc = DEFAULT_ENCODER_PORT; int port_dec = DEFAULT_DECODER_PORT; const char *pidfile = NULL; - FILE *f = NULL; int res; srs_t *srs; - if (atexit(common_shutdown)) { - fputs("Cannot hook my atexit function, quitting !\n", stderr); - return EXIT_FAILURE; - } - common_initialize(); - - for (int c = 0; (c = getopt(argc, argv, "he:d:p:u")) >= 0; ) { + for (int c = 0; (c = getopt(argc, argv, "hfu" "e:d:p:")) >= 0; ) { switch (c) { case 'e': port_enc = atoi(optarg); break; + case 'f': + daemonize = false; + break; case 'd': port_dec = atoi(optarg); break; @@ -422,13 +382,9 @@ int main(int argc, char *argv[]) return EXIT_FAILURE; } - if (pidfile) { - f = fopen(pidfile, "w"); - if (!f) { - syslog(LOG_CRIT, "unable to write pidfile %s", pidfile); - } - fprintf(f, "%d\n", getpid()); - fflush(f); + if (pidfile_open(pidfile) < 0) { + syslog(LOG_CRIT, "unable to write pidfile %s", pidfile); + return EXIT_FAILURE; } if (!unsafe && drop_privileges(RUNAS_USER, RUNAS_GROUP) < 0) { @@ -436,24 +392,13 @@ int main(int argc, char *argv[]) return EXIT_FAILURE; } - if (daemon_detach() < 0) { + if (daemonize && daemon_detach() < 0) { syslog(LOG_CRIT, "unable to fork"); return EXIT_FAILURE; } - if (f) { - rewind(f); - ftruncate(fileno(f), 0); - fprintf(f, "%d\n", getpid()); - fflush(f); - } + pidfile_refresh(); res = main_loop(srs, argv[optind], port_enc, port_dec); - if (f) { - rewind(f); - ftruncate(fileno(f), 0); - fclose(f); - f = NULL; - } syslog(LOG_INFO, "Stopping..."); return res; }