Respect "Connection: close" if sent by the browser.

git-svn-id: https://shellinabox.googlecode.com/svn/trunk@123 0da03de8-d603-11dd-86c2-0f8696b7b6f9
This commit is contained in:
zodiac@gmail.com 2009-06-21 18:51:14 +00:00
parent db631d5e35
commit 2c090c8beb
8 changed files with 74 additions and 40 deletions

View file

@ -70,6 +70,9 @@
/* Define to 1 if you have the <stdlib.h> header file. */
#define HAVE_STDLIB_H 1
/* Define to 1 if you have the `strcasestr' function. */
#define HAVE_STRCASESTR 1
/* Define to 1 if you have the <strings.h> header file. */
#define HAVE_STRINGS_H 1
@ -129,7 +132,7 @@
#define STDC_HEADERS 1
/* Most recent revision number in the version control system */
#define VCS_REVISION "122"
#define VCS_REVISION "123"
/* Version number of package */
#define VERSION "2.8"

View file

@ -69,6 +69,9 @@
/* Define to 1 if you have the <stdlib.h> header file. */
#undef HAVE_STDLIB_H
/* Define to 1 if you have the `strcasestr' function. */
#undef HAVE_STRCASESTR
/* Define to 1 if you have the <strings.h> header file. */
#undef HAVE_STRINGS_H

6
configure vendored
View file

@ -2037,7 +2037,7 @@ ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $
ac_compiler_gnu=$ac_cv_c_compiler_gnu
VCS_REVISION=122
VCS_REVISION=123
cat >>confdefs.h <<_ACEOF
@ -11743,7 +11743,9 @@ done
for ac_func in getgrgid_r getgrnam_r getpwnam_r getpwuid_r openpty
for ac_func in getgrgid_r getgrnam_r getpwnam_r getpwuid_r openpty \
strcasestr
do
as_ac_var=`$as_echo "ac_cv_func_$ac_func" | $as_tr_sh`
{ $as_echo "$as_me:$LINENO: checking for $ac_func" >&5

View file

@ -2,7 +2,7 @@ AC_PREREQ(2.57)
dnl This is the one location where the authoritative version number is stored
AC_INIT(shellinabox, 2.8, markus@shellinabox.com)
VCS_REVISION=122
VCS_REVISION=123
AC_SUBST(VCS_REVISION)
AC_DEFINE_UNQUOTED(VCS_REVISION, "${VCS_REVISION}",
[Most recent revision number in the version control system])
@ -33,7 +33,8 @@ dnl Use strlcat() instead of strncat() to avoid spurious warnings
AC_CHECK_FUNCS([strlcat])
dnl Prefer thread-safe functions, if available
AC_CHECK_FUNCS([getgrgid_r getgrnam_r getpwnam_r getpwuid_r openpty])
AC_CHECK_FUNCS([getgrgid_r getgrnam_r getpwnam_r getpwuid_r openpty \
strcasestr ])
dnl We prefer ptsname_r(), but will settle for ptsname() if necessary
AC_TRY_LINK([#ifndef _XOPEN_SOURCE

View file

@ -1500,7 +1500,7 @@ VT100.prototype.toggleBell = function() {
};
VT100.prototype.about = function() {
alert("VT100 Terminal Emulator " + "2.8 (revision 122)" +
alert("VT100 Terminal Emulator " + "2.8 (revision 123)" +
"\nCopyright 2008-2009 by Markus Gutschke\n" +
"For more information check http://shellinabox.com");
};

View file

@ -43,6 +43,7 @@
// The most up-to-date version of this program is always available from
// http://shellinabox.com
#define _GNU_SOURCE
#include "config.h"
#include <errno.h>
@ -198,6 +199,21 @@ static void httpCloseRead(struct HttpConnection *http) {
}
}
#ifndef HAVE_STRCASESTR
static char *strcasestr(const char *haystack, const char *needle) {
// This algorithm is O(len(haystack)*len(needle)). Much better algorithms
// are available, but this code is much simpler and performance is not
// critical for our workloads.
int len = strlen(needle);
do {
if (!strncasecmp(haystack, needle, len)) {
return haystack;
}
} while (*haystack++);
return NULL;
}
#endif
static int httpFinishCommand(struct HttpConnection *http) {
int rc = HTTP_DONE;
if (http->callback && !http->done) {
@ -210,6 +226,13 @@ static int httpFinishCommand(struct HttpConnection *http) {
httpCloseRead(http);
}
}
if (!http->closed) {
const char *con = getFromHashMap(&http->header, "connection");
if ((con && strcasestr(con, "close")) ||
!http->version || strcmp(http->version, "HTTP/1.1") < 0) {
httpCloseRead(http);
}
}
if (logIsInfo()) {
check(http->method);
check(http->path);
@ -260,7 +283,9 @@ static char *getPeerName(int fd, int *port, int numericHosts) {
if (port) {
*port = ntohs(((struct sockaddr_in *)&peerAddr)->sin_port);
}
return strdup(host);
char *ret;
check(ret = strdup(host));
return ret;
}
static void httpSetState(struct HttpConnection *http, int state) {
@ -619,7 +644,7 @@ static int httpHandleCommand(struct HttpConnection *http,
}
if (query) {
http->query = strdup(query + 1);
check(http->query = strdup(query + 1));
}
return h->handler(http, h->arg);
}
@ -645,13 +670,13 @@ static int httpParseCommand(struct HttpConnection *http, int offset,
if (firstSpace < 1 || lastSpace < 0) {
bad_request:
if (!http->method) {
http->method = strdup("");
check(http->method = strdup(""));
}
if (!http->path) {
http->path = strdup("");
check(http->path = strdup(""));
}
if (!http->version) {
http->version = strdup("");
check(http->version = strdup(""));
}
httpSendReply(http, 400, "Bad Request", NO_MSG);
httpSetState(http, COMMAND);
@ -748,7 +773,7 @@ static int httpParseHeaders(struct HttpConnection *http,
struct ServerConnection *connection = httpGetServerConnection(http);
switch (rc) {
case HTTP_DONE:
case HTTP_ERROR:
case HTTP_ERROR: {
if (http->expecting < 0 || rc == HTTP_ERROR) {
httpCloseRead(http);
}
@ -759,7 +784,7 @@ static int httpParseHeaders(struct HttpConnection *http,
serverSetTimeout(connection, CONNECTION_TIMEOUT);
}
httpSetState(http, http->expecting ? DISCARD_PAYLOAD : COMMAND);
break;
break; }
case HTTP_READ_MORE:
http->isSuspended = 0;
http->isPartialReply = 0;

View file

@ -355,7 +355,7 @@ ShellInABox.prototype.extendContextMenu = function(entries, actions) {
};
ShellInABox.prototype.about = function() {
alert("Shell In A Box version " + "2.8 (revision 122)" +
alert("Shell In A Box version " + "2.8 (revision 123)" +
"\nCopyright 2008-2009 by Markus Gutschke\n" +
"For more information check http://shellinabox.com" +
(typeof serverSupportsSSL != 'undefined' && serverSupportsSSL ?

View file

@ -1500,7 +1500,7 @@ VT100.prototype.toggleBell = function() {
};
VT100.prototype.about = function() {
alert("VT100 Terminal Emulator " + "2.8 (revision 122)" +
alert("VT100 Terminal Emulator " + "2.8 (revision 123)" +
"\nCopyright 2008-2009 by Markus Gutschke\n" +
"For more information check http://shellinabox.com");
};