this includes revs from -current: Makefile 1.30-1.31 Makefile.boot 1.7-1.9 auth-bozo.c 1.25-1.26 bozohttpd.8 1.80-1.87 bozohttpd.c 1.114-1.123,1.125-1.128 bozohttpd.h 1.61-1.68 cgi-bozo.c 1.49-1.53 content-bozo.c 1.17-1.20 daemon-bozo.c 1-.22 dir-index-bozo.c 1.33-1.34 main.c 1.23-1.27 printenv.lua 1.4-1.5 ssl-bozo.c 1.27-1.29 libbozohttpd/libbozohttpd.3 1.5-1.6 small/Makefile 1.4 testsuite/Makefile 1.14 testsuite/t16.in 1.1 testsuite/t16.out 1.1 testsuite/t17.in 1.1 testsuite/t17.out 1.1 testsuite/t18.in 1.1 testsuite/t18.out 1.1 the summary comes from the CHANGES: changes in bozohttpd 20210227: o new support for content types: .tar.bz2, .tar.xz, .tar.lz, .tar.zst, .tbz2, .txz, .tlz, .zipx, .xz, .zst, .sz, .lz, .lzma, .lzo, .7z, .lzo, .cab, .dmg, .jar, and .rar. should fix netbsd PR#56026: MIME type of .tar.xz file on ny{cdn,ftp}.NetBSD.org is invalid changes in bozohttpd 20210211: o fix various NULL derefs from malformed headers. mostly from . o fix memory leaks in library interface: add bozo_cleanup(). changes in bozohttpd 20201014: o also set -D_GNU_SOURCE in Makefile.boot. from hadrien.lacour@posteo.net. o fix array size botch (assertion, not exploitable.) from martin@netbsd.org. o also match %2F as well as %2f. from leah@vuxu.org. o many manual and help fixes. clean ups for higher lint levels, consistency/style clean ups. various option fixes including made -f imply -b. from for freebsd. changes in bozohttpd 20200912: o add .m4a and .m4v file extensions. changes in bozohttpd 20200820: o make this work on sun2 by reducing mmap window there. o fix SSL shutdown sequence. from spz@netbsd.org. o add readme support to directory indexing. from jmcneill@netbsd.org o add blocklist(8) support. from jruoho@netbsd.org. Index: libexec/httpd/Makefile =================================================================== RCS file: /cvsroot/src/libexec/httpd/Makefile,v retrieving revision 1.28 diff -p -u -r1.28 Makefile --- libexec/httpd/Makefile 17 Jan 2019 07:39:00 -0000 1.28 +++ libexec/httpd/Makefile 3 Mar 2021 09:45:38 -0000 @@ -23,7 +23,7 @@ # for setting CFLAGS relevant to your make, eg # % make COPTS="-DDO_HTPASSWD" Index: libexec/httpd/CHANGES =================================================================== RCS file: /cvsroot/src/libexec/httpd/CHANGES,v retrieving revision 1.40 diff -p -u -r1.40 CHANGES --- libexec/httpd/CHANGES 28 Feb 2019 09:16:42 -0000 1.40 +++ libexec/httpd/CHANGES 3 Mar 2021 09:45:38 -0000 @@ -1,5 +1,36 @@ $NetBSD: CHANGES,v 1.40 2019/02/28 09:16:42 mrg Exp $ +changes in bozohttpd 20210227: + o new support for content types: .tar.bz2, .tar.xz, .tar.lz, + .tar.zst, .tbz2, .txz, .tlz, .zipx, .xz, .zst, .sz, .lz, .lzma, + .lzo, .7z, .lzo, .cab, .dmg, .jar, and .rar. should fix + netbsd PR#56026: + MIME type of .tar.xz file on ny{cdn,ftp}.NetBSD.org is invalid + +changes in bozohttpd 20210211: + o fix various NULL derefs from malformed headers. mostly from + . + o fix memory leaks in library interface: add bozo_cleanup(). + +changes in bozohttpd 20201014: + o also set -D_GNU_SOURCE in Makefile.boot. from + hadrien.lacour@posteo.net. + o fix array size botch (assertion, not exploitable.) from + martin@netbsd.org. + o also match %2F as well as %2f. from leah@vuxu.org. + o many manual and help fixes. clean ups for higher lint levels, + consistency/style clean ups. various option fixes including made + -f imply -b. from for freebsd. + +changes in bozohttpd 20200912: + o add .m4a and .m4v file extensions. + +changes in bozohttpd 20200820: + o make this work on sun2 by reducing mmap window there. + o fix SSL shutdown sequence. from spz@netbsd.org. + o add readme support to directory indexing. from jmcneill@netbsd.org + o add blocklist(8) support. from jruoho@netbsd.org. + changes in bozohttpd 20190228: o extend timeout facility to ssl and stop servers hanging forever if the client never sends anything. reported by Steffen in netbsd Index: libexec/httpd/Makefile =================================================================== RCS file: /cvsroot/src/libexec/httpd/Makefile,v retrieving revision 1.28 diff -p -u -r1.28 Makefile --- libexec/httpd/Makefile 17 Jan 2019 07:39:00 -0000 1.28 +++ libexec/httpd/Makefile 3 Mar 2021 09:45:38 -0000 @@ -23,7 +23,7 @@ # for setting CFLAGS relevant to your make, eg # % make COPTS="-DDO_HTPASSWD" -COPTS+= -DDO_HTPASSWD +COPTS+= -DDO_HTPASSWD -DNO_BLOCKLIST_SUPPORT PROG= bozohttpd LINKS= ${BINDIR}/bozohttpd ${BINDIR}/httpd MAN= bozohttpd.8 @@ -80,6 +80,12 @@ CLEANFILES+= bozohttpd.8.html bozohttpd. check: cd ${.CURDIR}/testsuite && ${MAKE} check +.if empty(BOZOVER) +BOZOVER!= sed -n \ + -e s/\"$$// -e \ + 's/\#define[ ]*SERVER_SOFTWARE[ ]*\"bozohttpd\///p' ${.PARSEDIR}/bozohttpd.c +.endif + # Create a distfile: uses /tmp BASE=bozohttpd-${BOZOVER} TAR=${BASE}.tar Index: libexec/httpd/Makefile.boot =================================================================== RCS file: /cvsroot/src/libexec/httpd/Makefile.boot,v retrieving revision 1.6 diff -p -u -r1.6 Makefile.boot --- libexec/httpd/Makefile.boot 2 Jan 2014 08:30:22 -0000 1.6 +++ libexec/httpd/Makefile.boot 3 Mar 2021 09:45:38 -0000 @@ -6,18 +6,20 @@ CC= cc OPT= -O LARGE_CFLAGS= -D_LARGEFILE_SOURCE -D_FILE_OFFSET_BITS=64 -LOCAL_CFLAGS= -DNO_LUA_SUPPORT +LOCAL_CFLAGS= -DNO_LUA_SUPPORT -DNO_BLOCKLIST_SUPPORT -D_GNU_SOURCE -D_DEFAULT_SOURCE CFLAGS= $(OPT) $(LARGE_CFLAGS) $(LOCAL_CFLAGS) GROFF= groff -Tascii CRYPTOLIBDIR= # -L/usr/local/lib CRYPTOLIBS= $(CRYPTOLIBDIR) -lcrypto -lssl +LIBS= $(CRYPTOLIBS) $(EXTRALIBS) + FILES= bozohttpd.c auth-bozo.c cgi-bozo.c content-bozo.c daemon-bozo.c \ dir-index-bozo.c lua-bozo.c ssl-bozo.c tilde-luzah-bozo.c main.c all: - $(CC) $(CPPFLAGS) $(CFLAGS) $(LDFLAGS) -o bozohttpd $(FILES) $(CRYPTOLIBS) + $(CC) $(CPPFLAGS) $(CFLAGS) $(LDFLAGS) -o bozohttpd $(FILES) $(LIBS) man: $(GROFF) -mandoc bozohttpd.8 > bozohttpd.cat8 Index: libexec/httpd/auth-bozo.c =================================================================== RCS file: /cvsroot/src/libexec/httpd/auth-bozo.c,v retrieving revision 1.24 diff -p -u -r1.24 auth-bozo.c --- libexec/httpd/auth-bozo.c 28 Feb 2019 08:28:21 -0000 1.24 +++ libexec/httpd/auth-bozo.c 3 Mar 2021 09:45:38 -0000 @@ -3,7 +3,7 @@ /* $eterna: auth-bozo.c,v 1.17 2011/11/18 09:21:15 mrg Exp $ */ /* - * Copyright (c) 1997-2019 Matthew R. Green + * Copyright (c) 1997-2020 Matthew R. Green * All rights reserved. * * Redistribution and use in source and binary forms, with or without @@ -105,6 +105,11 @@ bozo_auth_check(bozo_httpreq_t *request, pass) != 0) break; fclose(fp); + +#ifndef NO_BLOCKLIST_SUPPORT + pfilter_notify(BLOCKLIST_AUTH_OK, 200); +#endif /* !NO_BLOCKLIST_SUPPORT */ + return 0; } } Index: libexec/httpd/bozohttpd.8 =================================================================== RCS file: /cvsroot/src/libexec/httpd/bozohttpd.8,v retrieving revision 1.79 diff -p -u -r1.79 bozohttpd.8 --- libexec/httpd/bozohttpd.8 28 Feb 2019 08:28:21 -0000 1.79 +++ libexec/httpd/bozohttpd.8 3 Mar 2021 09:45:38 -0000 @@ -2,7 +2,7 @@ .\" .\" $eterna: bozohttpd.8,v 1.101 2011/11/18 01:25:11 mrg Exp $ .\" -.\" Copyright (c) 1997-2019 Matthew R. Green +.\" Copyright (c) 1997-2021 Matthew R. Green .\" All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without @@ -26,7 +26,7 @@ .\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF .\" SUCH DAMAGE. .\" -.Dd February 27, 2019 +.Dd February 27, 2021 .Dt BOZOHTTPD 8 .Os .Sh NAME @@ -34,13 +34,14 @@ .Nd hyper text transfer protocol version 1.1 daemon .Sh SYNOPSIS .Nm -.Op Fl EGHVXefhnsu +.Op Fl EGHVXdefhnsu .Op Fl C Ar suffix cgihandler .Op Fl I Ar port .Op Fl L Ar prefix script .Op Fl M Ar suffix type encoding encoding11 .Op Fl P Ar pidfile -.Op Fl S Ar server_software +.Op Fl R Ar readme +.Op Fl S Ar version .Op Fl T Ar type timeout .Op Fl U Ar username .Op Fl Z Ar cert privkey @@ -119,6 +120,15 @@ Note that the CGI/1.1 interface is avail translation using .Fl E switch. +.It Fl d +Enables debug support. +.It Fl E +Enables CGI/1.1 interface for +.Em ~user +translation. +Note that enabling this support implies that users can run commands +as the web server user. +This may have security implications. .It Fl e Causes .Nm @@ -130,9 +140,12 @@ options. .It Fl f Stops the .Fl b -flag from +flag from detaching .Nm -detaching from the tty and going into the background. +from the tty and going into the background. +This implies the +.Fl b +flag. .It Fl G Get the .Nm @@ -211,12 +224,10 @@ options may be passed. .It Fl n Stops .Nm -from doing IP address to name resolution of hosts for setting the +from doing IP address to name resolution of remote hosts. +This affects the .Ev REMOTE_HOST -variable before running a CGI program. -This option has no effect without the -.Fl c -option. +environment variable for CGI programs and Lua scripts. .It Fl P Ar pidfile Causes .Nm @@ -232,9 +243,13 @@ translations from .Dq public_html to .Ar pubdir . -.It Fl S Ar server_software +.It Fl R Ar readme +When directory indexing is enabled, include the contents of the file +.Ar readme +in the footer of the directory index. +.It Fl S Ar version Sets the internal server version to -.Ar server_software . +.Ar version . .It Fl s Forces logging to be set to stderr always. .It Fl T Ar type timeout @@ -285,12 +300,6 @@ into the directory (but see the .Fl p option above). -.It Fl E -Enables CGI/1.1 interface for -.Em ~user -translation. -Note that enabling this support implies that users can run -commands as web server user, this may have security implications. .It Fl V Sets the backup virtual host directory to the .Ar slashdir @@ -325,15 +334,15 @@ Changes the default file read for direct .Dq index.html to .Ar index . -.It Fl z Ar ciphers -Sets the list of SSL ciphers (see -.Xr SSL_CTX_set_cipher_list 3 ) . .It Fl Z Ar certificate_path privatekey_path Sets the path to the server certificate file and the private key file in PEM format. It also causes .Nm to start SSL mode. +.It Fl z Ar ciphers +Sets the list of SSL ciphers (see +.Xr SSL_CTX_set_cipher_list 3 ) . .El .Pp Note that in @@ -449,6 +458,44 @@ with on the compiler command line to enable this support. It may require linking with the crypt library, using .Dq -lcrypt . +.Ss BLOCKLIST SUPPORT +On +.Nx , +.Nm +supports +.Xr blocklistd 8 +by default. +The support can be disabled with the +.Dq -DNO_BLOCKLIST_SUPPORT +compilation option. +.Pp +Upon occurrence, +.Nm +reports two HTTP status codes to +.Xr blocklistd 8 +as failures: +.Em 401 +(``Unauthorized'') +and +.Em 403 +(``Forbidden'') . +Of these, +.Em 401 +is the one received upon authorization failure with the +HTTP Basic Authorization mechanism. +A successful authorization decreases the counter kept by +.Xr blocklistd 8 . +.Pp +Note that the implementation of the HTTP Basic Authorization mechanism +uses a redirection; a status code +.Em 401 +is always initially received. +Therefore, a single authorization failure of +.Pa .htpasswd +is reported as two failures to +.Xr blocklistd 8 , +but no failures are recorded upon successful authorization +due to the decrease of the failure counter. .Ss SSL SUPPORT .Nm has support for TLSv1.1 and TLSv1.2 protocols that are included by @@ -599,7 +646,7 @@ The focus has always been simplicity and and regular code audits. This manual documents .Nm -version 20190116. +version 20210227. .Sh AUTHORS .An -nosplit .Nm @@ -652,14 +699,17 @@ added support for serving gzipped files .Aq Mt pek@pdc.kth.se provided a fix for a minor (non-security) buffer overflow condition .It +.Aq Mt emily@ingalls.rocks +provided fixes for some bad request parsing +.It .An Jun-ichiro itojun Hagino, KAME .Aq Mt itojun@iijlab.net provided initial IPv6 support .It .An Martin Husemann .Aq Mt martin@NetBSD.org -provided .bzabsredirect and .bzredir support, and fixed various -redirection issues +provided .bzabsredirect and .bzredir support, fixed various +redirection issues and more .It .An Arto Huusko .Aq Mt arto.huusko@pp2.inet.fi @@ -704,6 +754,10 @@ provided man page fixes .Aq Mt denafcm@gmail.com provided a cgi-bin fix .It +.An Jared McNeill +.Aq Mt jmcneill@NetBSD.org +added support for readme in directory indexing +.It .An Julio Merino .Aq Mt jmmv@NetBSD.org Added the @@ -742,6 +796,11 @@ provided the .Fl V option .It +.An Jukka Ruohonen +.Aq Mt jruoho@NetBSD.org +provided support for +.Xr blocklistd 8 +.It .An Thor Lancelot Simon .Aq Mt tls@NetBSD.org enhanced cgi-bin support @@ -760,6 +819,11 @@ provided http authorization fixes .It .Aq Mt xs@kittenz.org provided chroot and change-to-user support, and other various fixes + +.It +.An S.P.Zeidler +.Aq Mt spz@NetBSD.org +fixed several SSL shutdown issues .It Coyote Point provided various CGI fixes .El Index: libexec/httpd/bozohttpd.c =================================================================== RCS file: /cvsroot/src/libexec/httpd/bozohttpd.c,v retrieving revision 1.113.2.1 diff -p -u -r1.113.2.1 bozohttpd.c --- libexec/httpd/bozohttpd.c 19 Nov 2020 11:25:18 -0000 1.113.2.1 +++ libexec/httpd/bozohttpd.c 3 Mar 2021 09:45:38 -0000 @@ -3,7 +3,7 @@ /* $eterna: bozohttpd.c,v 1.178 2011/11/18 09:21:15 mrg Exp $ */ /* - * Copyright (c) 1997-2019 Matthew R. Green + * Copyright (c) 1997-2021 Matthew R. Green * All rights reserved. * * Redistribution and use in source and binary forms, with or without @@ -40,7 +40,6 @@ * - CGI/1.1 this will only be provided for "system" scripts * - automatic "missing trailing slash" redirections * - configurable translation of /~user/ to ~user/public_html, - * however, this does not include cgi-bin support * - access lists via libwrap via inetd/tcpd * - virtual hosting * - not that we do not even pretend to understand MIME, but @@ -109,7 +108,7 @@ #define INDEX_HTML "index.html" #endif #ifndef SERVER_SOFTWARE -#define SERVER_SOFTWARE "bozohttpd/20190228" +#define SERVER_SOFTWARE "bozohttpd/20210227" #endif #ifndef PUBLIC_HTML #define PUBLIC_HTML "public_html" @@ -240,6 +239,20 @@ bozo_set_pref(bozohttpd_t *httpd, bozopr return 1; } +static void +bozo_clear_prefs(bozohttpd_t *httpd, bozoprefs_t *prefs) +{ + size_t i; + + for (i = 0; i < prefs->count; i++) { + free(prefs->name[i]); + free(prefs->value[i]); + } + + free(prefs->name); + free(prefs->value); +} + /* * get a variable's value, or NULL */ @@ -317,7 +330,7 @@ parse_request(bozohttpd_t *httpd, char * debug((httpd, DEBUG_FAT, "url: method: \"%s\" file: \"%s\" query: \"%s\" proto: \"%s\"", - *method, *file, *query, *proto)); + *method, *file, *query ? *query : "", *proto ? *proto : "")); } /* @@ -339,8 +352,12 @@ bozo_clean_request(bozo_httpreq_t *reque free(request->hr_remoteaddr); free(request->hr_serverport); free(request->hr_virthostname); - free(request->hr_file); - free(request->hr_oldfile); + free(request->hr_file_free); + /* XXX this is gross */ + if (request->hr_file_free != request->hr_oldfile) + free(request->hr_oldfile); + else + free(request->hr_file); free(request->hr_query); free(request->hr_host); bozo_user_free(request->hr_user); @@ -373,6 +390,7 @@ bozo_clean_request(bozo_httpreq_t *reque static void alarmer(int sig) { + USE_ARG(sig); bozo_timeout_hit = 1; } @@ -496,7 +514,7 @@ got_proto_09: if (strncasecmp(proto, "HTTP/", 5) != 0) goto bad; - strncpy(majorstr, proto + 5, sizeof majorstr); + strncpy(majorstr, proto + 5, sizeof(majorstr)-1); majorstr[sizeof(majorstr)-1] = 0; minorstr = strchr(majorstr, '.'); if (minorstr == NULL) @@ -619,6 +637,7 @@ bozo_read_request(bozohttpd_t *httpd) request->hr_last_byte_pos = -1; request->hr_if_modified_since = NULL; request->hr_virthostname = NULL; + request->hr_file_free = NULL; request->hr_file = NULL; request->hr_oldfile = NULL; SIMPLEQ_INIT(&request->hr_replheaders); @@ -651,7 +670,7 @@ bozo_read_request(bozohttpd_t *httpd) * if passed through a proxy that doesn't rewrite the port. */ if (httpd->bindport) { - if (strcmp(httpd->bindport, "80") != 0) + if (strcmp(httpd->bindport, BOZO_HTTP_PORT) != 0) port = httpd->bindport; else port = NULL; @@ -735,7 +754,7 @@ bozo_read_request(bozohttpd_t *httpd) /* we allocate return space in file and query only */ parse_request(httpd, str, &method, &file, &query, &proto); - request->hr_file = file; + request->hr_file_free = request->hr_file = file; request->hr_query = query; if (method == NULL) { bozo_http_error(httpd, 404, NULL, "null method"); @@ -771,11 +790,17 @@ bozo_read_request(bozohttpd_t *httpd) val = bozostrnsep(&str, ":", &len); debug((httpd, DEBUG_EXPLODING, "read_req2: after " - "bozostrnsep: str `%s' val `%s'", str, val)); + "bozostrnsep: str `%s' val `%s'", + str ? str : "", val ? val : "")); if (val == NULL || len == -1) { bozo_http_error(httpd, 404, request, "no header"); goto cleanup; } + if (str == NULL) { + bozo_http_error(httpd, 404, request, + "malformed header"); + goto cleanup; + } while (*str == ' ' || *str == '\t') len--, str++; while (*val == ' ' || *val == '\t') @@ -914,7 +939,7 @@ mmap_and_write_part(bozohttpd_t *httpd, wroffset = (size_t)(first_byte_pos - mappedoffset); addr = mmap(0, mappedsz, PROT_READ, MAP_SHARED, fd, mappedoffset); - if (addr == (char *)-1) { + if (addr == MAP_FAILED) { bozowarn(httpd, "mmap failed: %s", strerror(errno)); return -1; } @@ -1099,7 +1124,7 @@ handle_redirect(bozo_httpreq_t *request, hostname = ""; portbuf[0] = '\0'; } else { - const char *defport = httpd->sslinfo ? "443" : "80"; + const char *defport = httpd->sslinfo ? BOZO_HTTPS_PORT : BOZO_HTTP_PORT; if (request->hr_serverport && strcmp(request->hr_serverport, defport) != 0) @@ -1201,7 +1226,7 @@ check_remap(bozo_httpreq_t *request) } fmap = mmap(NULL, st.st_size, PROT_READ, MAP_SHARED, mapfile, 0); - if (fmap == NULL) { + if (fmap == MAP_FAILED) { bozowarn(httpd, "could not mmap " REMAP_FILE ", error %d", errno); goto out; @@ -1284,8 +1309,8 @@ check_remap(bozo_httpreq_t *request) strcpy(newfile+rlen, file + len); debug((httpd, DEBUG_NORMAL, "remapping found '%s'", newfile)); - free(request->hr_file); - request->hr_file = newfile; + free(request->hr_file_free); + request->hr_file_free = request->hr_file = newfile; } munmap(fmap, st.st_size); @@ -1313,9 +1338,6 @@ check_virtual(bozo_httpreq_t *request) debug((httpd, DEBUG_OBESE, "checking for http:// virtual host in '%s'", file)); if (strncasecmp(file, "http://", 7) == 0) { - /* bozostrdup() might access it. */ - char *old_file = request->hr_file; - /* we would do virtual hosting here? */ file += 7; /* RFC 2616 (HTTP/1.1), 5.2: URI takes precedence over Host: */ @@ -1324,8 +1346,9 @@ check_virtual(bozo_httpreq_t *request) if ((s = strchr(request->hr_host, '/')) != NULL) *s = '\0'; s = strchr(file, '/'); - request->hr_file = bozostrdup(httpd, request, s ? s : "/"); - free(old_file); + free(request->hr_file_free); + request->hr_file_free = request->hr_file = + bozostrdup(httpd, request, s ? s : "/"); debug((httpd, DEBUG_OBESE, "got host '%s' file is now '%s'", request->hr_host, request->hr_file)); } else if (!request->hr_host) @@ -1335,7 +1358,8 @@ check_virtual(bozo_httpreq_t *request) * canonicalise hr_host - that is, remove any :80. */ len = strlen(request->hr_host); - if (len > 3 && strcmp(request->hr_host + len - 3, ":80") == 0) { + if (len > 3 && + strcmp(request->hr_host + len - 3, ":" BOZO_HTTP_PORT) == 0) { request->hr_host[len - 3] = '\0'; len = strlen(request->hr_host); } @@ -1554,7 +1578,7 @@ bozo_decode_url_percent(bozo_httpreq_t * if (s[1] == '0' && s[2] == '0') return bozo_http_error(httpd, 404, request, "percent hack was %00"); - if (s[1] == '2' && s[2] == 'f') + if (s[1] == '2' && (s[2] == 'f' || s[2] == 'F')) return bozo_http_error(httpd, 404, request, "percent hack was %2f (/)"); @@ -1709,7 +1733,7 @@ transform_request(bozo_httpreq_t *reques goto bad_done; if (strlen(newfile)) { - request->hr_oldfile = request->hr_file; + request->hr_oldfile = request->hr_file_free; request->hr_file = newfile; } @@ -1912,6 +1936,8 @@ bozo_process_request(bozo_httpreq_t *req cleanup: close(fd); cleanup_nofd: + /* If SSL enabled send close_notify. */ + bozo_ssl_shutdown(request->hr_httpd); close(STDIN_FILENO); close(STDOUT_FILENO); /*close(STDERR_FILENO);*/ @@ -2133,6 +2159,7 @@ static struct errors_map { const char *shortmsg; /* short version of message */ const char *longmsg; /* long version of message */ } errors_map[] = { + { 200, "200 OK", "The request was valid", }, { 400, "400 Bad Request", "The request was not valid", }, { 401, "401 Unauthorized", "No authorization", }, { 403, "403 Forbidden", "Access to this item has been denied",}, @@ -2170,8 +2197,24 @@ http_errors_long(int code) return (help); } +#ifndef NO_BLOCKLIST_SUPPORT +static struct blocklist *blstate; + +void +pfilter_notify(const int what, const int code) +{ + + if (blstate == NULL) + blstate = blocklist_open(); + + if (blstate == NULL) + return; + + (void)blocklist_r(blstate, what, 0, http_errors_short(code)); +} +#endif /* !NO_BLOCKLIST_SUPPORT */ + /* the follow functions and variables are used in handling HTTP errors */ -/* ARGSUSED */ int bozo_http_error(bozohttpd_t *httpd, int code, bozo_httpreq_t *request, const char *msg) @@ -2184,6 +2227,8 @@ bozo_http_error(bozohttpd_t *httpd, int int size; bozoheaders_t *hdr; + USE_ARG(msg); + debug((httpd, DEBUG_FAT, "bozo_http_error %d: %s", code, msg)); if (header == NULL || reason == NULL) { bozoerr(httpd, 1, @@ -2193,7 +2238,7 @@ bozo_http_error(bozohttpd_t *httpd, int } if (request && request->hr_serverport && - strcmp(request->hr_serverport, "80") != 0) + strcmp(request->hr_serverport, BOZO_HTTP_PORT) != 0) snprintf(portbuf, sizeof(portbuf), ":%s", request->hr_serverport); else @@ -2272,6 +2317,19 @@ bozo_http_error(bozohttpd_t *httpd, int bozo_printf(httpd, "%s", httpd->errorbuf); bozo_flush(httpd, stdout); +#ifndef NO_BLOCKLIST_SUPPORT + switch(code) { + + case 401: + pfilter_notify(BLOCKLIST_AUTH_FAIL, code); + break; + + case 403: + pfilter_notify(BLOCKLIST_ABUSIVE_BEHAVIOR, code); + break; + } +#endif /* !NO_BLOCKLIST_SUPPORT */ + return code; } @@ -2385,6 +2443,11 @@ bozodgetln(bozohttpd_t *httpd, int fd, s return httpd->getln_buffer; } +/* + * allocation frontends with error handling. + * + * note that these may access members of the httpd and/or request. + */ void * bozorealloc(bozohttpd_t *httpd, void *ptr, size_t size) { @@ -2570,6 +2633,9 @@ bozo_setup(bozohttpd_t *httpd, bozoprefs strcmp(cp, "true") == 0) { httpd->dir_indexing = 1; } + if ((cp = bozo_get_pref(prefs, "directory index readme")) != NULL) { + httpd->dir_readme = bozostrdup(httpd, NULL, cp); + } if ((cp = bozo_get_pref(prefs, "public_html")) != NULL) { httpd->public_html = bozostrdup(httpd, NULL, cp); } @@ -2645,6 +2711,23 @@ bozo_setup(bozohttpd_t *httpd, bozoprefs return 1; } +void +bozo_cleanup(bozohttpd_t *httpd, bozoprefs_t *prefs) +{ + bozo_clear_prefs(httpd, prefs); + + free(httpd->virthostname); + free(httpd->errorbuf); + free(httpd->getln_buffer); + free(httpd->slashdir); +#define bozo_unconst(x) ((void *)(uintptr_t)x) + free(bozo_unconst(httpd->server_software)); + free(bozo_unconst(httpd->index_html)); + free(bozo_unconst(httpd->dir_readme)); + free(bozo_unconst(httpd->public_html)); +#undef bozo_unconst +} + int bozo_get_version(char *buf, size_t size) { Index: libexec/httpd/bozohttpd.h =================================================================== RCS file: /cvsroot/src/libexec/httpd/bozohttpd.h,v retrieving revision 1.60 diff -p -u -r1.60 bozohttpd.h --- libexec/httpd/bozohttpd.h 8 Mar 2019 03:12:28 -0000 1.60 +++ libexec/httpd/bozohttpd.h 3 Mar 2021 09:45:38 -0000 @@ -3,7 +3,7 @@ /* $eterna: bozohttpd.h,v 1.39 2011/11/18 09:21:15 mrg Exp $ */ /* - * Copyright (c) 1997-2019 Matthew R. Green + * Copyright (c) 1997-2021 Matthew R. Green * All rights reserved. * * Redistribution and use in source and binary forms, with or without @@ -29,12 +29,13 @@ * SUCH DAMAGE. * */ -#ifndef BOZOHTTOPD_H_ -#define BOZOHTTOPD_H_ 1 +#ifndef BOZOHTTPD_H_ +#define BOZOHTTPD_H_ 1 #include "netbsd_queue.h" #include +#include #include #include @@ -42,7 +43,11 @@ #ifndef NO_LUA_SUPPORT #include #endif -#include + +#ifndef NO_BLOCKLIST_SUPPORT +#include +void pfilter_notify(const int, const int); +#endif /* QNX provides a lot of NetBSD things in nbutil.h */ #ifdef HAVE_NBUTIL_H @@ -117,6 +122,7 @@ typedef struct bozohttpd_t { struct pollfd *fds; /* current poll fd set */ int request_times; /* # times a request was processed */ int dir_indexing; /* handle directories */ + const char *dir_readme; /* include README footer in indexes */ int hide_dots; /* hide .* */ int process_cgi; /* use the cgi handler */ char *cgibin; /* cgi-bin directory */ @@ -153,7 +159,8 @@ typedef struct bozo_httpreq_t { const char *hr_methodstr; char *hr_virthostname; /* server name (if not identical to hr_httpd->virthostname) */ - char *hr_file; + char *hr_file_free; /* pointer to file buffer to free() */ + char *hr_file; /* pointer into file buffer */ char *hr_oldfile; /* if we added an index_html */ char *hr_query; char *hr_host; /* HTTP/1.1 Host: or virtual hostname, @@ -247,6 +254,9 @@ void debug__(bozohttpd_t *, int, const c #define have_debug (1) #endif /* NO_DEBUG */ +#define BOZO_HTTP_PORT "80" +#define BOZO_HTTPS_PORT "443" + /* * bozohttpd special files. avoid serving these out. * @@ -298,7 +308,7 @@ char *bozostrdup(bozohttpd_t *, bozo_htt #define bozo_noop do { /* nothing */ } while (/*CONSTCOND*/0) -#define have_all (1) +#define have_core (1) /* ssl-bozo.c */ #ifdef NO_SSL_SUPPORT @@ -306,6 +316,7 @@ char *bozostrdup(bozohttpd_t *, bozo_htt #define bozo_ssl_set_ciphers(w, x) bozo_noop #define bozo_ssl_init(x) bozo_noop #define bozo_ssl_accept(x) (0) +#define bozo_ssl_shutdown(x) bozo_noop #define bozo_ssl_destroy(x) bozo_noop #define have_ssl (0) #else @@ -313,6 +324,7 @@ void bozo_ssl_set_opts(bozohttpd_t *, co void bozo_ssl_set_ciphers(bozohttpd_t *, const char *); void bozo_ssl_init(bozohttpd_t *); int bozo_ssl_accept(bozohttpd_t *); +void bozo_ssl_shutdown(bozohttpd_t *); void bozo_ssl_destroy(bozohttpd_t *); #define have_ssl (1) #endif @@ -431,6 +443,7 @@ int bozo_init_httpd(bozohttpd_t *); int bozo_init_prefs(bozohttpd_t *, bozoprefs_t *); int bozo_set_defaults(bozohttpd_t *, bozoprefs_t *); int bozo_setup(bozohttpd_t *, bozoprefs_t *, const char *, const char *); +void bozo_cleanup(bozohttpd_t *, bozoprefs_t *); bozo_httpreq_t *bozo_read_request(bozohttpd_t *); void bozo_process_request(bozo_httpreq_t *); void bozo_clean_request(bozo_httpreq_t *); @@ -448,4 +461,4 @@ int bozo_get_version(char */*buf*/, size extern volatile sig_atomic_t bozo_timeout_hit; -#endif /* BOZOHTTOPD_H_ */ +#endif /* BOZOHTTPD_H_ */ Index: libexec/httpd/cgi-bozo.c =================================================================== RCS file: /cvsroot/src/libexec/httpd/cgi-bozo.c,v retrieving revision 1.48 diff -p -u -r1.48 cgi-bozo.c --- libexec/httpd/cgi-bozo.c 29 Mar 2019 14:46:44 -0000 1.48 +++ libexec/httpd/cgi-bozo.c 3 Mar 2021 09:45:38 -0000 @@ -3,7 +3,7 @@ /* $eterna: cgi-bozo.c,v 1.40 2011/11/18 09:21:15 mrg Exp $ */ /* - * Copyright (c) 1997-2019 Matthew R. Green + * Copyright (c) 1997-2021 Matthew R. Green * All rights reserved. * * Redistribution and use in source and binary forms, with or without @@ -137,7 +137,7 @@ finish_cgi_output(bozohttpd_t *httpd, bo * return it in the response. If the cgi program does * not return any `Status:' header then the server should * respond with 200 OK. - * XXX The CGI 1.1 and 1.2 specification differ slightly on + * The CGI 1.1 and 1.2 specification differ slightly on * this in that v1.2 says that the script MUST NOT return a * `Status:' header if it is returning a `Location:' header. * For compatibility we are going with the CGI 1.1 behavior. @@ -182,8 +182,7 @@ finish_cgi_output(bozohttpd_t *httpd, bo bozo_flush(httpd, stdout); } - /* XXX we should have some goo that times us out - */ + /* CGI programs should perform their own timeouts */ while ((rbytes = read(in, buf, sizeof buf)) > 0) { ssize_t wbytes; char *bp = buf; @@ -611,10 +610,16 @@ bozo_process_cgi(bozo_httpreq_t *request bozo_daemon_closefds(httpd); if (-1 == execve(path, argv, envp)) { + int saveerrno = errno; bozo_http_error(httpd, 404, request, "Cannot execute CGI"); - bozoerr(httpd, 1, "child exec failed: %s: %s", - path, strerror(errno)); + /* don't log easy to trigger events */ + if (saveerrno != ENOENT && + saveerrno != EISDIR && + saveerrno != EACCES) + bozoerr(httpd, 1, "child exec failed: %s: %s", + path, strerror(saveerrno)); + _exit(1); } /* NOT REACHED */ bozoerr(httpd, 1, "child execve returned?!"); @@ -638,6 +643,8 @@ bozo_process_cgi(bozo_httpreq_t *request /* child reader/writer */ close(STDIN_FILENO); finish_cgi_output(httpd, request, sv[0], nph); + /* if we do SSL, send a SSL_shutdown now */ + bozo_ssl_shutdown(request->hr_httpd); /* if we're done output, our parent is useless... */ kill(getppid(), SIGKILL); debug((httpd, DEBUG_FAT, "done processing cgi output")); @@ -645,8 +652,7 @@ bozo_process_cgi(bozo_httpreq_t *request } close(STDOUT_FILENO); - /* XXX we should have some goo that times us out - */ + /* CGI programs should perform their own timeouts */ while ((rbytes = bozo_read(httpd, STDIN_FILENO, buf, sizeof buf)) > 0) { ssize_t wbytes; char *bp = buf; Index: libexec/httpd/content-bozo.c =================================================================== RCS file: /cvsroot/src/libexec/httpd/content-bozo.c,v retrieving revision 1.16 diff -p -u -r1.16 content-bozo.c --- libexec/httpd/content-bozo.c 23 Nov 2018 08:11:20 -0000 1.16 +++ libexec/httpd/content-bozo.c 3 Mar 2021 09:45:38 -0000 @@ -3,7 +3,7 @@ /* $eterna: content-bozo.c,v 1.17 2011/11/18 09:21:15 mrg Exp $ */ /* - * Copyright (c) 1997-2018 Matthew R. Green + * Copyright (c) 1997-2021 Matthew R. Green * All rights reserved. * * Redistribution and use in source and binary forms, with or without @@ -63,11 +63,18 @@ static bozo_content_map_t static_content { ".pa", "application/x-ns-proxy-autoconfig", "", "", NULL }, { ".tar", "multipart/x-tar", "", "", NULL }, { ".gtar", "application/x-gtar-compressed", "", "", NULL }, - { ".tar.Z", "application/x-gtar-compressed", "", "", NULL }, { ".tar.gz", "application/x-gtar-compressed", "", "", NULL }, - { ".taz", "application/x-gtar-compressed", "", "", NULL }, + { ".tar.bz2", "application/x-gtar-compressed", "", "", NULL }, + { ".tar.xz", "application/x-gtar-compressed", "", "", NULL }, + { ".tar.lz", "application/x-gtar-compressed", "", "", NULL }, + { ".tar.zst", "application/x-gtar-compressed", "", "", NULL }, { ".tgz", "application/x-gtar-compressed", "", "", NULL }, + { ".tbz2", "application/x-gtar-compressed", "", "", NULL }, + { ".txz", "application/x-gtar-compressed", "", "", NULL }, + { ".tlz", "application/x-gtar-compressed", "", "", NULL }, { ".tar.z", "application/x-gtar-compressed", "", "", NULL }, + { ".tar.Z", "application/x-gtar-compressed", "", "", NULL }, + { ".taz", "application/x-gtar-compressed", "", "", NULL }, { ".Z", "application/x-compress", "", "", NULL }, { ".gz", "application/x-gzip", "", "", NULL }, { ".z", "unknown", "", "", NULL }, @@ -131,10 +138,24 @@ static bozo_content_map_t static_content { ".ustar", "application/x-ustar", "", "", NULL }, { ".src", "application/x-wais-source", "", "", NULL }, { ".zip", "application/zip", "", "", NULL }, + { ".zipx", "application/zip", "", "", NULL }, + { ".xz", "application/x-xz", "", "", NULL }, + { ".zst", "application/x-zstd", "", "", NULL }, + { ".sz", "application/x-snappy-framed", "", "", NULL }, + { ".lz", "application/x-lzip", "", "", NULL }, + { ".lzma", "application/x-lzma", "", "", NULL }, + { ".lzo", "application/x-lzop", "", "", NULL }, + { ".7z", "application/x-7z-compressed", "", "", NULL }, + { ".lzo", "application/x-lzop", "", "", NULL }, + { ".cab", "application/vnd.ms-cab-compressed", "", "", NULL }, + { ".dmg", "application/x-apple-diskimage","", "", NULL }, + { ".jar", "application/java-archive", "", "", NULL }, + { ".rar", "application/x-rar-compressed", "", "", NULL }, { ".au", "audio/basic", "", "", NULL }, { ".snd", "audio/basic", "", "", NULL }, { ".mpga", "audio/mpeg", "", "", NULL }, { ".mp2", "audio/mpeg", "", "", NULL }, + { ".m4a", "audio/mp4", "", "", NULL }, { ".aif", "audio/x-aiff", "", "", NULL }, { ".aiff", "audio/x-aiff", "", "", NULL }, { ".aifc", "audio/x-aiff", "", "", NULL }, @@ -167,6 +188,7 @@ static bozo_content_map_t static_content { ".ts", "video/mpeg", "", "", NULL }, { ".vob", "video/mpeg", "", "", NULL }, { ".mp4", "video/mp4", "", "", NULL }, + { ".m4v", "video/mp4", "", "", NULL }, { ".qt", "video/quicktime", "", "", NULL }, { ".mov", "video/quicktime", "", "", NULL }, { ".avi", "video/x-msvideo", "", "", NULL }, @@ -211,7 +233,6 @@ bozo_match_content_map(bozohttpd_t *http /* * given the file name, return a valid Content-Type: value. */ -/* ARGSUSED */ const char * bozo_content_type(bozo_httpreq_t *request, const char *file) { Index: libexec/httpd/daemon-bozo.c =================================================================== RCS file: /cvsroot/src/libexec/httpd/daemon-bozo.c,v retrieving revision 1.21 diff -p -u -r1.21 daemon-bozo.c --- libexec/httpd/daemon-bozo.c 17 Jan 2019 07:46:16 -0000 1.21 +++ libexec/httpd/daemon-bozo.c 3 Mar 2021 09:45:38 -0000 @@ -62,26 +62,27 @@ static void sigchild(int); /* SIGCHLD ha #ifndef INFTIM #define INFTIM -1 #endif +#ifndef USE_ARG +#define USE_ARG(x) /*LINTED*/(void)&(x) +#endif static const char* pidfile_path = NULL; static pid_t pidfile_pid = 0; -/* ARGSUSED */ static void sigchild(int signo) { - + USE_ARG(signo); while (waitpid(-1, NULL, WNOHANG) > 0) /* nothing */; } /* Signal handler to exit in a controlled manner. This ensures that * any atexit(3) handlers are properly executed. */ -/* ARGSUSED */ BOZO_DEAD static void controlled_exit(int signo) { - + USE_ARG(signo); exit(EXIT_SUCCESS); } @@ -128,9 +129,12 @@ bozo_daemon_init(bozohttpd_t *httpd) const char *portnum; int e, i, on = 1; - if (!httpd->background) + if (!httpd->background && !httpd->foreground) return; + if (!httpd->background) + httpd->background = 1; + portnum = (httpd->bindport) ? httpd->bindport : "http"; memset(&h, 0, sizeof(h)); Index: libexec/httpd/dir-index-bozo.c =================================================================== RCS file: /cvsroot/src/libexec/httpd/dir-index-bozo.c,v retrieving revision 1.32 diff -p -u -r1.32 dir-index-bozo.c --- libexec/httpd/dir-index-bozo.c 28 Feb 2019 08:28:21 -0000 1.32 +++ libexec/httpd/dir-index-bozo.c 3 Mar 2021 09:45:38 -0000 @@ -3,7 +3,7 @@ /* $eterna: dir-index-bozo.c,v 1.20 2011/11/18 09:21:15 mrg Exp $ */ /* - * Copyright (c) 1997-2019 Matthew R. Green + * Copyright (c) 1997-2020 Matthew R. Green * All rights reserved. * * Redistribution and use in source and binary forms, with or without @@ -38,9 +38,11 @@ #include #include +#include #include #include #include +#include #include #include "bozohttpd.h" @@ -57,7 +59,8 @@ bozo_dir_index(bozo_httpreq_t *request, DIR *dp; char buf[MAXPATHLEN]; char *file = NULL, *printname = NULL, *p; - int k, j; + int k, j, fd; + ssize_t rlen; if (!isindex || !httpd->dir_indexing) return 0; @@ -197,6 +200,23 @@ bozo_dir_index(bozo_httpreq_t *request, free(deo[k]); free(deo); bozo_printf(httpd, "\r\n"); + if (httpd->dir_readme != NULL) { + if (httpd->dir_readme[0] == '/') + snprintf(buf, sizeof buf, "%s", httpd->dir_readme); + else + snprintf(buf, sizeof buf, "%s/%s", dirpath, httpd->dir_readme); + fd = open(buf, O_RDONLY); + if (fd != -1) { + bozo_flush(httpd, stdout); + do { + rlen = read(fd, buf, sizeof buf); + if (rlen <= 0) + break; + bozo_write(httpd, STDOUT_FILENO, buf, rlen); + } while (1); + close(fd); + } + } bozo_printf(httpd, "\r\n\r\n"); bozo_flush(httpd, stdout); Index: libexec/httpd/main.c =================================================================== RCS file: /cvsroot/src/libexec/httpd/main.c,v retrieving revision 1.22 diff -p -u -r1.22 main.c --- libexec/httpd/main.c 25 Nov 2018 07:37:20 -0000 1.22 +++ libexec/httpd/main.c 3 Mar 2021 09:45:38 -0000 @@ -4,7 +4,7 @@ /* from: eterna: bozohttpd.c,v 1.159 2009/05/23 02:14:30 mrg Exp */ /* - * Copyright (c) 1997-2018 Matthew R. Green + * Copyright (c) 1997-2021 Matthew R. Green * All rights reserved. * * Redistribution and use in source and binary forms, with or without @@ -63,53 +63,58 @@ usage(bozohttpd_t *httpd, char *progname bozowarn(httpd, "options:"); if (have_daemon_mode) - bozowarn(httpd, " -b\t\t\tbackground and go into daemon mode"); + bozowarn(httpd, " -b\t\t\tbackground in daemon mode"); if (have_cgibin && have_dynamic_content) - bozowarn(httpd, " -C arg prog\t\tadd this CGI handler"); + bozowarn(httpd, " -C suffix handler\tadd this CGI handler " + "for paths ending with `suffix'"); if (have_cgibin) bozowarn(httpd, " -c cgibin\t\tenable cgi-bin support in " "this directory"); if (have_debug) bozowarn(httpd, " -d\t\t\tenable debug support"); - if (have_cgibin) - bozowarn(httpd, " -E\t\t\tenable CGI support for user dirs"); if (have_user && have_cgibin) + bozowarn(httpd, " -E\t\t\tenable CGI support for user dirs"); + if (have_core) bozowarn(httpd, " -e\t\t\tdon't clean the environment " "(-t and -U only)"); if (have_daemon_mode) bozowarn(httpd, " -f\t\t\tforeground in daemon mode"); - if (have_all) - bozowarn(httpd, " -G print version number and exit"); + if (have_core) + bozowarn(httpd, " -G\t\t\tprint version number and exit"); if (have_dirindex) bozowarn(httpd, " -H\t\t\thide files starting with a period " "(.) in index mode"); - if (have_all) + if (have_core) bozowarn(httpd, " -I port\t\tbind or use on this port"); if (have_daemon_mode) bozowarn(httpd, " -i address\t\tbind on this address " "(daemon mode only)"); if (have_lua) - bozowarn(httpd, " -L arg script\tadd this Lua script"); + bozowarn(httpd, " -L prefix script\tadd this Lua script for " + "paths starting with `prefix'"); if (have_dynamic_content) - bozowarn(httpd, " -M arg t c c11\tadd this mime extenstion"); + bozowarn(httpd, " -M suffix t c c11\tadd this mime entry"); + if (have_core) + bozowarn(httpd, " -n\t\t\tdon't resolve host names"); if (have_daemon_mode) bozowarn(httpd, " -P pidfile\t\tpid file path"); if (have_user) bozowarn(httpd, " -p dir\t\t\"public_html\" directory name"); - if (have_all) { + if (have_core) { bozowarn(httpd, " -S version\t\tset server version string"); bozowarn(httpd, " -s\t\t\talways log to stderr"); - bozowarn(httpd, " -T type timeout\tset `type' timeout"); + bozowarn(httpd, " -T type timeout\t" + "set timeout"); bozowarn(httpd, " -t dir\t\tchroot to `dir'"); - bozowarn(httpd, " -U username\t\tchange user to `user'"); + bozowarn(httpd, " -U user\t\tchange user to `user'"); } if (have_user) bozowarn(httpd, " -u\t\t\tenable ~user/public_html support"); - if (have_all) { + if (have_core) { bozowarn(httpd, " -V\t\t\tUnknown virtual hosts go to " "`slashdir'"); bozowarn(httpd, " -v virtualroot\tenable virtual host " @@ -118,7 +123,7 @@ usage(bozohttpd_t *httpd, char *progname if (have_dirindex) bozowarn(httpd, " -X\t\t\tdirectory index support"); - if (have_all) + if (have_core) bozowarn(httpd, " -x index\t\tdefault \"index.html\" " "file name"); @@ -160,7 +165,7 @@ main(int argc, char **argv) */ while ((c = getopt(argc, argv, - "C:EGHI:L:M:P:S:T:U:VXZ:bc:defhi:np:st:uv:x:z:")) != -1) { + "C:EGHI:L:M:P:R:S:T:U:VXZ:bc:defhi:np:st:uv:x:z:")) != -1) { switch (c) { case 'b': @@ -178,15 +183,9 @@ main(int argc, char **argv) bozo_set_pref(&httpd, &prefs, "background", val); break; - case 'c': - if (!have_cgibin) - bozoerr(&httpd, 1, "CGI not enabled"); - - bozo_cgi_setbin(&httpd, optarg); - break; - case 'C': - if (!have_dynamic_content && !have_cgibin) + if (!have_dynamic_content || + !have_cgibin) bozoerr(&httpd, 1, "dynamic CGI handler support not enabled"); @@ -197,6 +196,13 @@ main(int argc, char **argv) argv[optind++]); break; + case 'c': + if (!have_cgibin) + bozoerr(&httpd, 1, "CGI not enabled"); + + bozo_cgi_setbin(&httpd, optarg); + break; + case 'd': if (!have_debug) bozowarn(&httpd, "Debugging not enabled"); @@ -204,8 +210,8 @@ main(int argc, char **argv) break; case 'E': - if (have_user && - have_cgibin) + if (!have_user || + !have_cgibin) bozoerr(&httpd, 1, "CGI not enabled"); bozo_set_pref(&httpd, &prefs, "enable user cgibin", @@ -213,9 +219,6 @@ main(int argc, char **argv) break; case 'e': - if (!have_daemon_mode) - goto no_daemon_mode; - bozo_set_pref(&httpd, &prefs, "dirty environment", "true"); break; @@ -299,6 +302,11 @@ main(int argc, char **argv) bozo_set_pref(&httpd, &prefs, "public_html", optarg); break; + case 'R': + bozo_set_pref(&httpd, &prefs, "directory index readme", + optarg); + break; + case 'S': bozo_set_pref(&httpd, &prefs, "server software", optarg); @@ -400,5 +408,7 @@ main(int argc, char **argv) } } while (httpd.background); + bozo_cleanup(&httpd, &prefs); + return (0); } Index: libexec/httpd/printenv.lua =================================================================== RCS file: /cvsroot/src/libexec/httpd/printenv.lua,v retrieving revision 1.3 diff -p -u -r1.3 printenv.lua --- libexec/httpd/printenv.lua 7 Dec 2015 03:11:48 -0000 1.3 +++ libexec/httpd/printenv.lua 3 Mar 2021 09:45:38 -0000 @@ -1,10 +1,10 @@ --- $NetBSD$ +-- $NetBSD: printenv.lua,v 1.3 2015/12/07 03:11:48 kamil Exp $ -- this small Lua script demonstrates the use of Lua in (bozo)httpd -- it will simply output the "environment" -- Keep in mind that bozohttpd forks for each request when started in --- daemon mode, you can set global veriables here, but they will have +-- daemon mode, you can set global variables here, but they will have -- the same value on each invocation. You can not keep state between -- two calls. @@ -14,6 +14,10 @@ local httpd = require 'httpd' +function escape_html(s) + return s:gsub('&', '&'):gsub('<', '<'):gsub('>', '>'):gsub('"', '"') +end + function printenv(env, headers, query) -- we get the "environment" in the env table, the values are more @@ -40,18 +44,18 @@ function printenv(env, headers, query) httpd.print('

Server Environment

') -- print the list of "environment" variables for k, v in pairs(env) do - httpd.print(k .. '=' .. v .. '
') + httpd.print(escape_html(k) .. '=' .. escape_html(v) .. '
') end httpd.print('

Request Headers

') for k, v in pairs(headers) do - httpd.print(k .. '=' .. v .. '
') + httpd.print(escape_html(k) .. '=' .. escape_html(v) .. '
') end if query ~= nil then httpd.print('

Query Variables

') for k, v in pairs(query) do - httpd.print(k .. '=' .. v .. '
') + httpd.print(escape_html(k) .. '=' .. escape_html(v) .. '
') end end @@ -83,7 +87,7 @@ function form(env, header, query) end for k, v in pairs(query) do - httpd.print(k .. '=' .. v .. '
') + httpd.print(escape_html(k) .. '=' .. escape_html(v) .. '
') end else httpd.print('No values') Index: libexec/httpd/ssl-bozo.c =================================================================== RCS file: /cvsroot/src/libexec/httpd/ssl-bozo.c,v retrieving revision 1.26 diff -p -u -r1.26 ssl-bozo.c --- libexec/httpd/ssl-bozo.c 28 Feb 2019 08:28:21 -0000 1.26 +++ libexec/httpd/ssl-bozo.c 3 Mar 2021 09:45:38 -0000 @@ -3,7 +3,7 @@ /* $eterna: ssl-bozo.c,v 1.15 2011/11/18 09:21:15 mrg Exp $ */ /* - * Copyright (c) 1997-2019 Matthew R. Green + * Copyright (c) 1997-2020 Matthew R. Green * All rights reserved. * * Redistribution and use in source and binary forms, with or without @@ -40,15 +40,15 @@ #include "bozohttpd.h" +#ifndef USE_ARG +#define USE_ARG(x) /*LINTED*/(void)&(x) +#endif + #ifndef NO_SSL_SUPPORT #include #include -#ifndef USE_ARG -#define USE_ARG(x) /*LINTED*/(void)&(x) -#endif - #ifndef BOZO_SSL_CIPHERS #define BOZO_SSL_CIPHERS \ "AES256-GCM-SHA384:AES256-SHA256:AES256-SHA:" \ @@ -287,6 +287,15 @@ bozo_ssl_accept(bozohttpd_t *httpd) } void +bozo_ssl_shutdown(bozohttpd_t *httpd) +{ + const sslinfo_t *sslinfo = httpd->sslinfo; + + if (sslinfo && sslinfo->bozossl) + SSL_shutdown(sslinfo->bozossl); +} + +void bozo_ssl_destroy(bozohttpd_t *httpd) { const sslinfo_t *sslinfo = httpd->sslinfo; @@ -319,7 +328,7 @@ bozo_ssl_set_opts(bozohttpd_t *httpd, co sslinfo->certificate_file, sslinfo->privatekey_file)); if (!httpd->bindport) - httpd->bindport = bozostrdup(httpd, NULL, "https"); + httpd->bindport = bozostrdup(httpd, NULL, BOZO_HTTPS_PORT); } void @@ -343,6 +352,8 @@ bozo_printf(bozohttpd_t *httpd, const ch va_list args; int cc; + USE_ARG(httpd); + va_start(args, fmt); #ifndef NO_SSL_SUPPORT if (httpd->sslinfo) @@ -361,6 +372,7 @@ bozo_read(bozohttpd_t *httpd, int fd, vo if (httpd->sslinfo) return bozo_ssl_read(httpd, fd, buf, len); #endif + USE_ARG(httpd); return read(fd, buf, len); } @@ -371,6 +383,7 @@ bozo_write(bozohttpd_t *httpd, int fd, c if (httpd->sslinfo) return bozo_ssl_write(httpd, fd, buf, len); #endif + USE_ARG(httpd); return write(fd, buf, len); } @@ -381,5 +394,6 @@ bozo_flush(bozohttpd_t *httpd, FILE *fp) if (httpd->sslinfo) return 0; #endif + USE_ARG(httpd); return fflush(fp); } Index: libexec/httpd/libbozohttpd/Makefile =================================================================== RCS file: /cvsroot/src/libexec/httpd/libbozohttpd/Makefile,v retrieving revision 1.3 diff -p -u -r1.3 Makefile --- libexec/httpd/libbozohttpd/Makefile 21 May 2017 15:28:41 -0000 1.3 +++ libexec/httpd/libbozohttpd/Makefile 3 Mar 2021 09:45:38 -0000 @@ -6,8 +6,8 @@ LIB= bozohttpd COPTS+= -I$(.CURDIR)/.. -COPTS+= -DDO_HTPASSWD -CPPFLAGS+= -DDO_HTPASSWD +COPTS+= -DDO_HTPASSWD +CPPFLAGS+= -DDO_HTPASSWD -DNO_BLOCKLIST_SUPPORT SRCS= bozohttpd.c ssl-bozo.c auth-bozo.c cgi-bozo.c daemon-bozo.c SRCS+= tilde-luzah-bozo.c dir-index-bozo.c content-bozo.c SRCS+= lua-bozo.c Index: libexec/httpd/libbozohttpd/libbozohttpd.3 =================================================================== RCS file: /cvsroot/src/libexec/httpd/libbozohttpd/libbozohttpd.3,v retrieving revision 1.4 diff -p -u -r1.4 libbozohttpd.3 --- libexec/httpd/libbozohttpd/libbozohttpd.3 4 Feb 2017 01:32:54 -0000 1.4 +++ libexec/httpd/libbozohttpd/libbozohttpd.3 3 Mar 2021 09:45:38 -0000 @@ -2,7 +2,7 @@ .\" .\" $eterna: libbozohttpd.3,v 1.2 2010/05/10 02:48:23 mrg Exp $ .\" -.\" Copyright (c) 2009 The NetBSD Foundation, Inc. +.\" Copyright (c) 2009, 2021 The NetBSD Foundation, Inc. .\" All rights reserved. .\" .\" This manual page is derived from software contributed to The @@ -29,7 +29,7 @@ .\" ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE .\" POSSIBILITY OF SUCH DAMAGE. .\" -.Dd February 2, 2017 +.Dd February 11, 2021 .Dt LIBBOZOHTTPD 3 .Os .Sh NAME @@ -67,6 +67,10 @@ .Fo bozo_clean_request .Fa "bozo_httpreq_t *" .Fc +.Ft void +.Fo bozo_cleanup +.Fa "bozohttpd_t *httpd" "bozoprefs_t *prefs" +.Fc .Sh DESCRIPTION .Nm is a library interface to the @@ -124,6 +128,9 @@ and queried using the two function. This is the main interface for selecting options, and for setting preferences. +The memory allocated by +.Fn bozo_setup +for both the httpd structure and the preferences will be freed. .Sh SEE ALSO .Xr gethostname 3 , .Xr ssl 3 , Index: libexec/httpd/small/Makefile =================================================================== RCS file: /cvsroot/src/libexec/httpd/small/Makefile,v retrieving revision 1.3 diff -p -u -r1.3 Makefile --- libexec/httpd/small/Makefile 17 Jul 2014 06:24:57 -0000 1.3 +++ libexec/httpd/small/Makefile 3 Mar 2021 09:45:38 -0000 @@ -9,7 +9,7 @@ LEAN_IFDEF_FLAGS= -UDEBUG -DNO_USER_SUPP -DNO_CGIBIN_SUPPORT -DNO_DIRINDEX_SUPPORT \ -DNO_DAEMON_MODE -DNO_DYNAMIC_CONTENT \ -DNO_SSL_SUPPORT -UDO_HTPASSWD \ - -DNO_LUA_SUPPORT + -DNO_LUA_SUPPORT -DNO_BLOCKLIST_SUPPORT CFLAGS= -I$(.CURDIR)/.. ${LEAN_IFDEF_FLAGS} Index: libexec/httpd/testsuite/Makefile =================================================================== RCS file: /cvsroot/src/libexec/httpd/testsuite/Makefile,v retrieving revision 1.13 diff -p -u -r1.13 Makefile --- libexec/httpd/testsuite/Makefile 27 Mar 2019 04:50:30 -0000 1.13 +++ libexec/httpd/testsuite/Makefile 3 Mar 2021 09:45:38 -0000 @@ -1,7 +1,7 @@ # $NetBSD: Makefile,v 1.13 2019/03/27 04:50:30 mrg Exp $ # $eterna: Makefile,v 1.14 2009/05/22 21:51:39 mrg Exp $ -SIMPLETESTS= t1 t2 t3 t4 t5 t6 t7 t8 t9 t10 t12 t13 t14 t15 +SIMPLETESTS= t1 t2 t3 t4 t5 t6 t7 t8 t9 t10 t12 t13 t14 t15 t16 t17 t18 CGITESTS= t11 BIGFILETESTS= partial4000 partial8000 Index: libexec/httpd/testsuite/t16.in =================================================================== RCS file: libexec/httpd/testsuite/t16.in diff -N libexec/httpd/testsuite/t16.in Binary files /dev/null and t16.in differ Index: libexec/httpd/testsuite/t16.out =================================================================== RCS file: libexec/httpd/testsuite/t16.out diff -N libexec/httpd/testsuite/t16.out --- /dev/null 1 Jan 1970 00:00:00 -0000 +++ libexec/httpd/testsuite/t16.out 3 Mar 2021 09:45:38 -0000 @@ -0,0 +1,11 @@ +HTTP/1.1 404 Not Found +Content-Type: text/html +Content-Length: 251 +Server: bozohttpd/20201014 +Allow: GET, HEAD, POST + +404 Not Found +

404 Not Found

+/:
This item has not been found
+
yesterday-when-i-was-mad.eterna23.net
+ Index: libexec/httpd/testsuite/t17.in =================================================================== RCS file: libexec/httpd/testsuite/t17.in diff -N libexec/httpd/testsuite/t17.in Binary files /dev/null and t17.in differ Index: libexec/httpd/testsuite/t17.out =================================================================== RCS file: libexec/httpd/testsuite/t17.out diff -N libexec/httpd/testsuite/t17.out --- /dev/null 1 Jan 1970 00:00:00 -0000 +++ libexec/httpd/testsuite/t17.out 3 Mar 2021 09:45:38 -0000 @@ -0,0 +1,2 @@ +HTTP/0.9 200 OK +this is the bozohttpd testsuite ./data/index.html file Index: libexec/httpd/testsuite/t18.in =================================================================== RCS file: libexec/httpd/testsuite/t18.in diff -N libexec/httpd/testsuite/t18.in Binary files /dev/null and t18.in differ Index: libexec/httpd/testsuite/t18.out =================================================================== RCS file: libexec/httpd/testsuite/t18.out diff -N libexec/httpd/testsuite/t18.out --- /dev/null 1 Jan 1970 00:00:00 -0000 +++ libexec/httpd/testsuite/t18.out 3 Mar 2021 09:45:38 -0000 @@ -0,0 +1,10 @@ +HTTP/0.9 403 Forbidden +Content-Type: text/html +Content-Length: 260 +Server: bozohttpd/20201014 + +403 Forbidden +

403 Forbidden

+/..:
Access to this item has been denied
+
yesterday-when-i-was-mad.eterna23.net
+ Index: lib/lua/bozohttpd/Makefile =================================================================== RCS file: /cvsroot/src/lib/lua/bozohttpd/Makefile,v retrieving revision 1.1 diff -p -u -r1.1 Makefile --- lib/lua/bozohttpd/Makefile 3 May 2018 22:51:18 -0000 1.1 +++ lib/lua/bozohttpd/Makefile 3 Mar 2021 09:45:38 -0000 @@ -7,7 +7,7 @@ LUA_DPLIBS+= bozohttpd \ EXTDIST= ${.CURDIR}/../../../libexec/httpd -CPPFLAGS+= -I${EXTDIST} +CPPFLAGS+= -I${EXTDIST} -DNO_BLOCKLIST_SUPPORT .PATH: ${EXTDIST}/lua