mirror of https://github.com/omar-polo/gmid.git
accumulate the whole response line for CGI scripts
This commit is contained in:
parent
45b4aa6e57
commit
3309ef975c
|
@ -33,7 +33,7 @@ testdata: fill-file
|
||||||
./sha testdata/bigfile testdata/bigfile.sha
|
./sha testdata/bigfile testdata/bigfile.sha
|
||||||
printf "# hello world\n" > testdata/index.gmi
|
printf "# hello world\n" > testdata/index.gmi
|
||||||
./sha testdata/index.gmi testdata/index.gmi.sha
|
./sha testdata/index.gmi testdata/index.gmi.sha
|
||||||
cp hello slow err testdata/
|
cp hello slow err invalid testdata/
|
||||||
mkdir testdata/dir
|
mkdir testdata/dir
|
||||||
cp testdata/index.gmi testdata/dir/foo.gmi
|
cp testdata/index.gmi testdata/dir/foo.gmi
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,3 @@
|
||||||
|
#!/bin/sh
|
||||||
|
|
||||||
|
echo 'iiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiii'
|
|
@ -159,5 +159,9 @@ eq "$(head /err)" "" "Unexpected head for /err"
|
||||||
eq "$(get /err)" "" "Unexpected body for /err"
|
eq "$(get /err)" "" "Unexpected body for /err"
|
||||||
echo OK GET /err with cgi
|
echo OK GET /err with cgi
|
||||||
|
|
||||||
|
eq "$(head /invalid | wc -c | xargs)" 2049 "Unexpected body for /invalid"
|
||||||
|
eq "$(get /invalid)" "" "Unexpected body for /invalid"
|
||||||
|
echo OK GET /invalid with cgi
|
||||||
|
|
||||||
check "should be running"
|
check "should be running"
|
||||||
quit
|
quit
|
||||||
|
|
59
server.c
59
server.c
|
@ -448,6 +448,43 @@ cgi_poll_on_client(struct pollfd *fds, struct client *c)
|
||||||
c->fd = fd;
|
c->fd = fd;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* handle the read from the child process. Return like read(2) */
|
||||||
|
static ssize_t
|
||||||
|
read_from_cgi(struct client *c)
|
||||||
|
{
|
||||||
|
void *buf;
|
||||||
|
size_t len;
|
||||||
|
ssize_t r;
|
||||||
|
|
||||||
|
/* if we haven't read a whole response line, we want to
|
||||||
|
* continue reading. */
|
||||||
|
|
||||||
|
if (c->code == -1) {
|
||||||
|
buf = c->sbuf + c->len;
|
||||||
|
len = sizeof(c->sbuf) - c->len;
|
||||||
|
} else {
|
||||||
|
buf = c->sbuf;
|
||||||
|
len = sizeof(c->sbuf);
|
||||||
|
}
|
||||||
|
|
||||||
|
r = read(c->fd, buf, len);
|
||||||
|
if (r == 0 || r == -1)
|
||||||
|
return r;
|
||||||
|
|
||||||
|
c->len += r;
|
||||||
|
c->off = 0;
|
||||||
|
|
||||||
|
if (c->code != -1)
|
||||||
|
return r;
|
||||||
|
|
||||||
|
if (strchr(c->sbuf, '\n') || c->len == sizeof(c->sbuf)) {
|
||||||
|
c->code = 0;
|
||||||
|
log_request(c, c->sbuf, c->len);
|
||||||
|
}
|
||||||
|
|
||||||
|
return r;
|
||||||
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
handle_cgi(struct pollfd *fds, struct client *c)
|
handle_cgi(struct pollfd *fds, struct client *c)
|
||||||
{
|
{
|
||||||
|
@ -457,25 +494,23 @@ handle_cgi(struct pollfd *fds, struct client *c)
|
||||||
cgi_poll_on_client(fds, c);
|
cgi_poll_on_client(fds, c);
|
||||||
|
|
||||||
while (1) {
|
while (1) {
|
||||||
if (c->len == 0) {
|
if (c->code == -1 || c->len == 0) {
|
||||||
if ((r = read(c->fd, c->sbuf, sizeof(c->sbuf))) == 0)
|
switch (r = read_from_cgi(c)) {
|
||||||
|
case 0:
|
||||||
goto end;
|
goto end;
|
||||||
if (r == -1) {
|
|
||||||
|
case -1:
|
||||||
if (errno == EAGAIN || errno == EWOULDBLOCK) {
|
if (errno == EAGAIN || errno == EWOULDBLOCK) {
|
||||||
cgi_poll_on_child(fds, c);
|
cgi_poll_on_child(fds, c);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
goto end;
|
goto end;
|
||||||
}
|
}
|
||||||
c->len = r;
|
}
|
||||||
c->off = 0;
|
|
||||||
|
|
||||||
/* XXX: if we haven't still read a whole
|
if (c->code == -1) {
|
||||||
* reply line, we should go back to poll! */
|
cgi_poll_on_child(fds, c);
|
||||||
if (c->code == -1) {
|
return;
|
||||||
c->code = 0;
|
|
||||||
log_request(c, c->sbuf, sizeof(c->sbuf));
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
while (c->len > 0) {
|
while (c->len > 0) {
|
||||||
|
|
Loading…
Reference in New Issue