Add logmsg() and refactor connection handling - quark - quark web server | |
git clone git://git.suckless.org/quark | |
Log | |
Files | |
Refs | |
LICENSE | |
--- | |
commit 0823ba4c3e480fb5e2c246b8ac6c4783d866ab87 | |
parent a36b901d404f4d4268384a379fd040898f78b1b3 | |
Author: Laslo Hunhold <[email protected]> | |
Date: Sat, 29 Aug 2020 13:02:51 +0200 | |
Add logmsg() and refactor connection handling | |
Also use compound literals for immediate pointers we don't use later | |
(same as with setsockopt() in 32223c96bdee8f94980d3a1877a643a4d59f897f). | |
Signed-off-by: Laslo Hunhold <[email protected]> | |
Diffstat: | |
M http.h | 2 ++ | |
M main.c | 79 +++++++++++++++++------------… | |
2 files changed, 45 insertions(+), 36 deletions(-) | |
--- | |
diff --git a/http.h b/http.h | |
@@ -3,6 +3,7 @@ | |
#define HTTP_H | |
#include <limits.h> | |
+#include <sys/socket.h> | |
#include "util.h" | |
@@ -95,6 +96,7 @@ enum conn_state { | |
struct connection { | |
enum conn_state state; | |
int fd; | |
+ struct sockaddr_storage ia; | |
char header[HEADER_MAX]; /* general req/res-header buffer */ | |
size_t off; /* general offset (header/file/dir) */ | |
struct request req; | |
diff --git a/main.c b/main.c | |
@@ -24,49 +24,57 @@ | |
static char *udsname; | |
static void | |
-serve(int infd, const struct sockaddr_storage *in_sa, const struct server *srv) | |
+logmsg(const struct connection *c) | |
{ | |
- struct connection c = { .fd = infd }; | |
- time_t t; | |
- enum status s; | |
- char inaddr[INET6_ADDRSTRLEN /* > INET_ADDRSTRLEN */]; | |
+ char inaddr_str[INET6_ADDRSTRLEN /* > INET_ADDRSTRLEN */]; | |
char tstmp[21]; | |
+ /* create timestamp */ | |
+ if (!strftime(tstmp, sizeof(tstmp), "%Y-%m-%dT%H:%M:%SZ", | |
+ gmtime(&(time_t){time(NULL)}))) { | |
+ warn("strftime: Exceeded buffer capacity"); | |
+ /* continue anyway (we accept the truncation) */ | |
+ } | |
+ | |
+ /* generate address-string */ | |
+ if (sock_get_inaddr_str(&c->ia, inaddr_str, LEN(inaddr_str))) { | |
+ warn("sock_get_inaddr_str: Couldn't generate adress-string"); | |
+ inaddr_str[0] = '\0'; | |
+ } | |
+ | |
+ printf("%s\t%s\t%d\t%s\t%s\n", tstmp, inaddr_str, c->res.status, | |
+ c->req.field[REQ_HOST], c->req.uri); | |
+} | |
+ | |
+static void | |
+serve(struct connection *c, const struct server *srv) | |
+{ | |
+ enum status s; | |
+ | |
/* set connection timeout */ | |
- if (sock_set_timeout(c.fd, 30)) { | |
+ if (sock_set_timeout(c->fd, 30)) { | |
goto cleanup; | |
} | |
/* handle request */ | |
- if ((s = http_recv_header(c.fd, c.header, LEN(c.header), &c.off)) || | |
- (s = http_parse_header(c.header, &c.req))) { | |
- http_prepare_error_response(&c.req, &c.res, s); | |
+ if ((s = http_recv_header(c->fd, c->header, LEN(c->header), &c->off)) … | |
+ (s = http_parse_header(c->header, &c->req))) { | |
+ http_prepare_error_response(&c->req, &c->res, s); | |
} else { | |
- http_prepare_response(&c.req, &c.res, srv); | |
+ http_prepare_response(&c->req, &c->res, srv); | |
} | |
- if ((s = http_send_header(c.fd, &c.res)) || | |
- (s = http_send_body(c.fd, &c.res, &c.req))) { | |
- c.res.status = s; | |
+ if ((s = http_send_header(c->fd, &c->res)) || | |
+ (s = http_send_body(c->fd, &c->res, &c->req))) { | |
+ c->res.status = s; | |
} | |
- /* write output to log */ | |
- t = time(NULL); | |
- if (!strftime(tstmp, sizeof(tstmp), "%Y-%m-%dT%H:%M:%SZ", | |
- gmtime(&t))) { | |
- warn("strftime: Exceeded buffer capacity"); | |
- goto cleanup; | |
- } | |
- if (sock_get_inaddr_str(in_sa, inaddr, LEN(inaddr))) { | |
- goto cleanup; | |
- } | |
- printf("%s\t%s\t%d\t%s\t%s\n", tstmp, inaddr, c.res.status, | |
- c.req.field[REQ_HOST], c.req.uri); | |
+ logmsg(c); | |
cleanup: | |
/* clean up and finish */ | |
- shutdown(c.fd, SHUT_RD); | |
- shutdown(c.fd, SHUT_WR); | |
- close(c.fd); | |
+ shutdown(c->fd, SHUT_RD); | |
+ shutdown(c->fd, SHUT_WR); | |
+ close(c->fd); | |
} | |
static void | |
@@ -189,10 +197,8 @@ main(int argc, char *argv[]) | |
struct server srv = { | |
.docindex = "index.html", | |
}; | |
- struct sockaddr_storage in_sa; | |
size_t i; | |
- socklen_t in_sa_len; | |
- int insock, status = 0, infd; | |
+ int insock, status = 0; | |
const char *err; | |
char *tok[4]; | |
@@ -367,9 +373,10 @@ main(int argc, char *argv[]) | |
/* accept incoming connections */ | |
while (1) { | |
- in_sa_len = sizeof(in_sa); | |
- if ((infd = accept(insock, (struct sockaddr *)&in_sa, | |
- &in_sa_len)) < 0) { | |
+ struct connection c = { 0 }; | |
+ | |
+ if ((c.fd = accept(insock, (struct sockaddr *)&c.ia, | |
+ &(socklen_t){sizeof(c.ia)})) < 0) { | |
warn("accept:"); | |
continue; | |
} | |
@@ -377,7 +384,7 @@ main(int argc, char *argv[]) | |
/* fork and handle */ | |
switch (fork()) { | |
case 0: | |
- serve(infd, &in_sa, &srv); | |
+ serve(&c, &srv); | |
exit(0); | |
break; | |
case -1: | |
@@ -385,7 +392,7 @@ main(int argc, char *argv[]) | |
/* fallthrough */ | |
default: | |
/* close the connection in the parent */ | |
- close(infd); | |
+ close(c.fd); | |
} | |
} | |
exit(0); |