2
0

Compare commits

..

No commits in common. "727ec9041797ad9d50182da369925d76f4f674a3" and "10f54c2d83605d07e7518b9b33af04af4f100cac" have entirely different histories.

29 changed files with 2845 additions and 219 deletions

16
.gitignore vendored
View File

@ -1,3 +1,19 @@
*build/ *build/
autom4te.cache/
m4/
Makefile.in
aclocal.m4
ar-lib
compile
config.guess
config.sub
configure
depcomp
include/lighttpd/config.h.in
include/lighttpd/config.h.in~
install-sh
ltmain.sh
missing
CMakeLists.txt.user
.vscode .vscode
.mypy_cache .mypy_cache

14
CMakeLists.txt Normal file
View File

@ -0,0 +1,14 @@
CMAKE_MINIMUM_REQUIRED(VERSION 3.0 FATAL_ERROR)
PROJECT(lighttpd C)
SET(PACKAGE_NAME ${CMAKE_PROJECT_NAME})
SET(PACKAGE_VERSION 2.0.0)
SET(CMAKE_MODULE_PATH ${CMAKE_SOURCE_DIR}/cmake)
#INCLUDE(CTest)
ENABLE_TESTING()
ADD_SUBDIRECTORY(src build)
add_subdirectory(tests)

6
Makefile.am Normal file
View File

@ -0,0 +1,6 @@
SUBDIRS=contrib doc src include tests
ACLOCAL_AMFLAGS=-I m4
EXTRA_DIST=autogen.sh CMakeLists.txt cmake build-helpers
DISTCHECK_CONFIGURE_FLAGS=--with-lua --with-openssl --with-kerberos5 --with-gnutls --with-zlib --with-bzip2

14
autogen.sh Executable file
View File

@ -0,0 +1,14 @@
#!/bin/sh
# Run this to generate all the initial makefiles, etc.
set -e
if [ ! -f configure.ac -o ! -f COPYING ]; then
echo "Doesn't look like you're in the source directory" >&2
exit 1
fi
# old autoreconf/aclocal versions fail hard if m4 doesn't exist
mkdir -p m4
autoreconf --force --install
echo "Now type './configure ...' and 'make' to compile."

136
build-helpers/glib-tap.mk Normal file
View File

@ -0,0 +1,136 @@
# GLIB - Library of useful C routines
AM_TESTS_ENVIRONMENT= \
G_TEST_SRCDIR="$(abs_srcdir)" \
G_TEST_BUILDDIR="$(abs_builddir)" \
G_DEBUG=gc-friendly \
MALLOC_CHECK_=2 \
MALLOC_PERTURB_=$$(($${RANDOM:-256} % 256))
LOG_DRIVER = env AM_TAP_AWK='$(AWK)' $(SHELL) $(top_srcdir)/build-helpers/tap-driver.sh
LOG_COMPILER = $(top_srcdir)/build-helpers/tap-test
NULL =
# initialize variables for unconditional += appending
BUILT_SOURCES =
BUILT_EXTRA_DIST =
CLEANFILES = *.log *.trs
DISTCLEANFILES =
MAINTAINERCLEANFILES =
EXTRA_DIST =
TESTS =
installed_test_LTLIBRARIES =
installed_test_PROGRAMS =
installed_test_SCRIPTS =
nobase_installed_test_DATA =
noinst_LTLIBRARIES =
noinst_PROGRAMS =
noinst_SCRIPTS =
noinst_DATA =
check_LTLIBRARIES =
check_PROGRAMS =
check_SCRIPTS =
check_DATA =
# We support a fairly large range of possible variables. It is expected that all types of files in a test suite
# will belong in exactly one of the following variables.
#
# First, we support the usual automake suffixes, but in lowercase, with the customary meaning:
#
# test_programs, test_scripts, test_data, test_ltlibraries
#
# The above are used to list files that are involved in both uninstalled and installed testing. The
# test_programs and test_scripts are taken to be actual testcases and will be run as part of the test suite.
# Note that _data is always used with the nobase_ automake variable name to ensure that installed test data is
# installed in the same way as it appears in the package layout.
#
# In order to mark a particular file as being only for one type of testing, use 'installed' or 'uninstalled',
# like so:
#
# installed_test_programs, uninstalled_test_programs
# installed_test_scripts, uninstalled_test_scripts
# installed_test_data, uninstalled_test_data
# installed_test_ltlibraries, uninstalled_test_ltlibraries
#
# Additionally, we support 'extra' infixes for programs and scripts. This is used for support programs/scripts
# that should not themselves be run as testcases (but exist to be used from other testcases):
#
# test_extra_programs, installed_test_extra_programs, uninstalled_test_extra_programs
# test_extra_scripts, installed_test_extra_scripts, uninstalled_test_extra_scripts
#
# Additionally, for _scripts and _data, we support the customary dist_ prefix so that the named script or data
# file automatically end up in the tarball.
#
# dist_test_scripts, dist_test_data, dist_test_extra_scripts
# dist_installed_test_scripts, dist_installed_test_data, dist_installed_test_extra_scripts
# dist_uninstalled_test_scripts, dist_uninstalled_test_data, dist_uninstalled_test_extra_scripts
#
# Note that no file is automatically disted unless it appears in one of the dist_ variables. This follows the
# standard automake convention of not disting programs scripts or data by default.
#
# test_programs, test_scripts, uninstalled_test_programs and uninstalled_test_scripts (as well as their disted
# variants) will be run as part of the in-tree 'make check'. These are all assumed to be runnable under
# gtester. That's a bit strange for scripts, but it's possible.
TESTS += $(test_programs) $(test_scripts) $(uninstalled_test_programs) $(uninstalled_test_scripts) \
$(dist_test_scripts) $(dist_uninstalled_test_scripts)
# Note: build even the installed-only targets during 'make check' to ensure that they still work.
# We need to do a bit of trickery here and manage disting via EXTRA_DIST instead of using dist_ prefixes to
# prevent automake from mistreating gmake functions like $(wildcard ...) and $(addprefix ...) as if they were
# filenames, including removing duplicate instances of the opening part before the space, eg. '$(addprefix'.
all_test_programs = $(test_programs) $(uninstalled_test_programs) $(installed_test_programs) \
$(test_extra_programs) $(uninstalled_test_extra_programs) $(installed_test_extra_programs)
all_test_scripts = $(test_scripts) $(uninstalled_test_scripts) $(installed_test_scripts) \
$(test_extra_scripts) $(uninstalled_test_extra_scripts) $(installed_test_extra_scripts)
all_dist_test_scripts = $(dist_test_scripts) $(dist_uninstalled_test_scripts) $(dist_installed_test_scripts) \
$(dist_test_extra_scripts) $(dist_uninstalled_test_extra_scripts) $(dist_installed_test_extra_scripts)
all_test_scripts += $(all_dist_test_scripts)
EXTRA_DIST += $(all_dist_test_scripts)
all_test_data = $(test_data) $(uninstalled_test_data) $(installed_test_data)
all_dist_test_data = $(dist_test_data) $(dist_uninstalled_test_data) $(dist_installed_test_data)
all_test_data += $(all_dist_test_data)
EXTRA_DIST += $(all_dist_test_data)
all_test_ltlibs = $(test_ltlibraries) $(uninstalled_test_ltlibraries) $(installed_test_ltlibraries)
if ENABLE_ALWAYS_BUILD_TESTS
noinst_LTLIBRARIES += $(all_test_ltlibs)
noinst_PROGRAMS += $(all_test_programs)
noinst_SCRIPTS += $(all_test_scripts)
noinst_DATA += $(all_test_data)
else
check_LTLIBRARIES += $(all_test_ltlibs)
check_PROGRAMS += $(all_test_programs)
check_SCRIPTS += $(all_test_scripts)
check_DATA += $(all_test_data)
endif
if ENABLE_INSTALLED_TESTS
installed_test_PROGRAMS += $(test_programs) $(installed_test_programs) \
$(test_extra_programs) $(installed_test_extra_programs)
installed_test_SCRIPTS += $(test_scripts) $(installed_test_scripts) \
$(test_extra_scripts) $(installed_test_extra_scripts)
installed_test_SCRIPTS += $(dist_test_scripts) $(dist_test_extra_scripts) \
$(dist_installed_test_scripts) $(dist_installed_test_extra_scripts)
nobase_installed_test_DATA += $(test_data) $(installed_test_data)
nobase_installed_test_DATA += $(dist_test_data) $(dist_installed_test_data)
installed_test_LTLIBRARIES += $(test_ltlibraries) $(installed_test_ltlibraries)
installed_testcases = $(test_programs) $(installed_test_programs) \
$(test_scripts) $(installed_test_scripts) \
$(dist_test_scripts) $(dist_installed_test_scripts)
installed_test_meta_DATA = $(installed_testcases:=.test)
%.test: %$(EXEEXT) Makefile
$(AM_V_GEN) ($(MKDIR_P) $(@D); \
echo '[Test]' > $@.tmp; \
echo 'Type=session' >> $@.tmp; \
echo 'Exec=$(installed_testdir)/$(notdir $<) --tap' >> $@.tmp; \
echo 'Output=TAP' >> $@.tmp; \
mv $@.tmp $@)
CLEANFILES += $(installed_test_meta_DATA)
endif

View File

@ -0,0 +1,31 @@
# Increment this whenever this file is changed.
#serial 1
dnl GLIB_TESTS
dnl
AC_DEFUN([GLIB_TESTS],
[
AC_ARG_ENABLE(installed-tests,
AS_HELP_STRING([--enable-installed-tests],
[Enable installation of some test cases]),
[case ${enableval} in
yes) ENABLE_INSTALLED_TESTS="1" ;;
no) ENABLE_INSTALLED_TESTS="" ;;
*) AC_MSG_ERROR([bad value ${enableval} for --enable-installed-tests]) ;;
esac])
AM_CONDITIONAL([ENABLE_INSTALLED_TESTS], test "$ENABLE_INSTALLED_TESTS" = "1")
AC_ARG_ENABLE(always-build-tests,
AS_HELP_STRING([--enable-always-build-tests],
[Enable always building tests during 'make all']),
[case ${enableval} in
yes) ENABLE_ALWAYS_BUILD_TESTS="1" ;;
no) ENABLE_ALWAYS_BUILD_TESTS="" ;;
*) AC_MSG_ERROR([bad value ${enableval} for --enable-always-build-tests]) ;;
esac])
AM_CONDITIONAL([ENABLE_ALWAYS_BUILD_TESTS], test "$ENABLE_ALWAYS_BUILD_TESTS" = "1")
if test "$ENABLE_INSTALLED_TESTS" = "1"; then
AC_SUBST(installed_test_metadir, [${datadir}/installed-tests/]AC_PACKAGE_NAME)
AC_SUBST(installed_testdir, [${libexecdir}/installed-tests/]AC_PACKAGE_NAME)
fi
])

652
build-helpers/tap-driver.sh Normal file
View File

@ -0,0 +1,652 @@
#! /bin/sh
# Copyright (C) 2011-2013 Free Software Foundation, Inc.
#
# This program is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation; either version 2, or (at your option)
# any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program. If not, see <http://www.gnu.org/licenses/>.
# As a special exception to the GNU General Public License, if you
# distribute this file as part of a program that contains a
# configuration script generated by Autoconf, you may include it under
# the same distribution terms that you use for the rest of that program.
# This file is maintained in Automake, please report
# bugs to <bug-automake@gnu.org> or send patches to
# <automake-patches@gnu.org>.
scriptversion=2011-12-27.17; # UTC
# Make unconditional expansion of undefined variables an error. This
# helps a lot in preventing typo-related bugs.
set -u
me=tap-driver.sh
fatal ()
{
echo "$me: fatal: $*" >&2
exit 1
}
usage_error ()
{
echo "$me: $*" >&2
print_usage >&2
exit 2
}
print_usage ()
{
cat <<END
Usage:
tap-driver.sh --test-name=NAME --log-file=PATH --trs-file=PATH
[--expect-failure={yes|no}] [--color-tests={yes|no}]
[--enable-hard-errors={yes|no}] [--ignore-exit]
[--diagnostic-string=STRING] [--merge|--no-merge]
[--comments|--no-comments] [--] TEST-COMMAND
The \`--test-name', \`--log-file' and \`--trs-file' options are mandatory.
END
}
# TODO: better error handling in option parsing (in particular, ensure
# TODO: $log_file, $trs_file and $test_name are defined).
test_name= # Used for reporting.
log_file= # Where to save the result and output of the test script.
trs_file= # Where to save the metadata of the test run.
expect_failure=0
color_tests=0
merge=0
ignore_exit=0
comments=0
diag_string='#'
while test $# -gt 0; do
case $1 in
--help) print_usage; exit $?;;
--version) echo "$me $scriptversion"; exit $?;;
--test-name) test_name=$2; shift;;
--log-file) log_file=$2; shift;;
--trs-file) trs_file=$2; shift;;
--color-tests) color_tests=$2; shift;;
--expect-failure) expect_failure=$2; shift;;
--enable-hard-errors) shift;; # No-op.
--merge) merge=1;;
--no-merge) merge=0;;
--ignore-exit) ignore_exit=1;;
--comments) comments=1;;
--no-comments) comments=0;;
--diagnostic-string) diag_string=$2; shift;;
--) shift; break;;
-*) usage_error "invalid option: '$1'";;
esac
shift
done
test $# -gt 0 || usage_error "missing test command"
case $expect_failure in
yes) expect_failure=1;;
*) expect_failure=0;;
esac
if test $color_tests = yes; then
init_colors='
color_map["red"]="" # Red.
color_map["grn"]="" # Green.
color_map["lgn"]="" # Light green.
color_map["blu"]="" # Blue.
color_map["mgn"]="" # Magenta.
color_map["std"]="" # No color.
color_for_result["ERROR"] = "mgn"
color_for_result["PASS"] = "grn"
color_for_result["XPASS"] = "red"
color_for_result["FAIL"] = "red"
color_for_result["XFAIL"] = "lgn"
color_for_result["SKIP"] = "blu"'
else
init_colors=''
fi
# :; is there to work around a bug in bash 3.2 (and earlier) which
# does not always set '$?' properly on redirection failure.
# See the Autoconf manual for more details.
:;{
(
# Ignore common signals (in this subshell only!), to avoid potential
# problems with Korn shells. Some Korn shells are known to propagate
# to themselves signals that have killed a child process they were
# waiting for; this is done at least for SIGINT (and usually only for
# it, in truth). Without the `trap' below, such a behaviour could
# cause a premature exit in the current subshell, e.g., in case the
# test command it runs gets terminated by a SIGINT. Thus, the awk
# script we are piping into would never seen the exit status it
# expects on its last input line (which is displayed below by the
# last `echo $?' statement), and would thus die reporting an internal
# error.
# For more information, see the Autoconf manual and the threads:
# <http://lists.gnu.org/archive/html/bug-autoconf/2011-09/msg00004.html>
# <http://mail.opensolaris.org/pipermail/ksh93-integration-discuss/2009-February/004121.html>
trap : 1 3 2 13 15
if test $merge -gt 0; then
exec 2>&1
else
exec 2>&3
fi
"$@"
echo $?
) | LC_ALL=C ${AM_TAP_AWK-awk} \
-v me="$me" \
-v test_script_name="$test_name" \
-v log_file="$log_file" \
-v trs_file="$trs_file" \
-v expect_failure="$expect_failure" \
-v merge="$merge" \
-v ignore_exit="$ignore_exit" \
-v comments="$comments" \
-v diag_string="$diag_string" \
'
# FIXME: the usages of "cat >&3" below could be optimized when using
# FIXME: GNU awk, and/or on systems that supports /dev/fd/.
# Implementation note: in what follows, `result_obj` will be an
# associative array that (partly) simulates a TAP result object
# from the `TAP::Parser` perl module.
## ----------- ##
## FUNCTIONS ##
## ----------- ##
function fatal(msg)
{
print me ": " msg | "cat >&2"
exit 1
}
function abort(where)
{
fatal("internal error " where)
}
# Convert a boolean to a "yes"/"no" string.
function yn(bool)
{
return bool ? "yes" : "no";
}
function add_test_result(result)
{
if (!test_results_index)
test_results_index = 0
test_results_list[test_results_index] = result
test_results_index += 1
test_results_seen[result] = 1;
}
# Whether the test script should be re-run by "make recheck".
function must_recheck()
{
for (k in test_results_seen)
if (k != "XFAIL" && k != "PASS" && k != "SKIP")
return 1
return 0
}
# Whether the content of the log file associated to this test should
# be copied into the "global" test-suite.log.
function copy_in_global_log()
{
for (k in test_results_seen)
if (k != "PASS")
return 1
return 0
}
# FIXME: this can certainly be improved ...
function get_global_test_result()
{
if ("ERROR" in test_results_seen)
return "ERROR"
if ("FAIL" in test_results_seen || "XPASS" in test_results_seen)
return "FAIL"
all_skipped = 1
for (k in test_results_seen)
if (k != "SKIP")
all_skipped = 0
if (all_skipped)
return "SKIP"
return "PASS";
}
function stringify_result_obj(result_obj)
{
if (result_obj["is_unplanned"] || result_obj["number"] != testno)
return "ERROR"
if (plan_seen == LATE_PLAN)
return "ERROR"
if (result_obj["directive"] == "TODO")
return result_obj["is_ok"] ? "XPASS" : "XFAIL"
if (result_obj["directive"] == "SKIP")
return result_obj["is_ok"] ? "SKIP" : COOKED_FAIL;
if (length(result_obj["directive"]))
abort("in function stringify_result_obj()")
return result_obj["is_ok"] ? COOKED_PASS : COOKED_FAIL
}
function decorate_result(result)
{
color_name = color_for_result[result]
if (color_name)
return color_map[color_name] "" result "" color_map["std"]
# If we are not using colorized output, or if we do not know how
# to colorize the given result, we should return it unchanged.
return result
}
function report(result, details)
{
if (result ~ /^(X?(PASS|FAIL)|SKIP|ERROR)/)
{
msg = ": " test_script_name
add_test_result(result)
}
else if (result == "#")
{
msg = " " test_script_name ":"
}
else
{
abort("in function report()")
}
if (length(details))
msg = msg " " details
# Output on console might be colorized.
print decorate_result(result) msg
# Log the result in the log file too, to help debugging (this is
# especially true when said result is a TAP error or "Bail out!").
print result msg | "cat >&3";
}
function testsuite_error(error_message)
{
report("ERROR", "- " error_message)
}
function handle_tap_result()
{
details = result_obj["number"];
if (length(result_obj["description"]))
details = details " " result_obj["description"]
if (plan_seen == LATE_PLAN)
{
details = details " # AFTER LATE PLAN";
}
else if (result_obj["is_unplanned"])
{
details = details " # UNPLANNED";
}
else if (result_obj["number"] != testno)
{
details = sprintf("%s # OUT-OF-ORDER (expecting %d)",
details, testno);
}
else if (result_obj["directive"])
{
details = details " # " result_obj["directive"];
if (length(result_obj["explanation"]))
details = details " " result_obj["explanation"]
}
report(stringify_result_obj(result_obj), details)
}
# `skip_reason` should be empty whenever planned > 0.
function handle_tap_plan(planned, skip_reason)
{
planned += 0 # Avoid getting confused if, say, `planned` is "00"
if (length(skip_reason) && planned > 0)
abort("in function handle_tap_plan()")
if (plan_seen)
{
# Error, only one plan per stream is acceptable.
testsuite_error("multiple test plans")
return;
}
planned_tests = planned
# The TAP plan can come before or after *all* the TAP results; we speak
# respectively of an "early" or a "late" plan. If we see the plan line
# after at least one TAP result has been seen, assume we have a late
# plan; in this case, any further test result seen after the plan will
# be flagged as an error.
plan_seen = (testno >= 1 ? LATE_PLAN : EARLY_PLAN)
# If testno > 0, we have an error ("too many tests run") that will be
# automatically dealt with later, so do not worry about it here. If
# $plan_seen is true, we have an error due to a repeated plan, and that
# has already been dealt with above. Otherwise, we have a valid "plan
# with SKIP" specification, and should report it as a particular kind
# of SKIP result.
if (planned == 0 && testno == 0)
{
if (length(skip_reason))
skip_reason = "- " skip_reason;
report("SKIP", skip_reason);
}
}
function extract_tap_comment(line)
{
if (index(line, diag_string) == 1)
{
# Strip leading `diag_string` from `line`.
line = substr(line, length(diag_string) + 1)
# And strip any leading and trailing whitespace left.
sub("^[ \t]*", "", line)
sub("[ \t]*$", "", line)
# Return what is left (if any).
return line;
}
return "";
}
# When this function is called, we know that line is a TAP result line,
# so that it matches the (perl) RE "^(not )?ok\b".
function setup_result_obj(line)
{
# Get the result, and remove it from the line.
result_obj["is_ok"] = (substr(line, 1, 2) == "ok" ? 1 : 0)
sub("^(not )?ok[ \t]*", "", line)
# If the result has an explicit number, get it and strip it; otherwise,
# automatically assing the next progresive number to it.
if (line ~ /^[0-9]+$/ || line ~ /^[0-9]+[^a-zA-Z0-9_]/)
{
match(line, "^[0-9]+")
# The final `+ 0` is to normalize numbers with leading zeros.
result_obj["number"] = substr(line, 1, RLENGTH) + 0
line = substr(line, RLENGTH + 1)
}
else
{
result_obj["number"] = testno
}
if (plan_seen == LATE_PLAN)
# No further test results are acceptable after a "late" TAP plan
# has been seen.
result_obj["is_unplanned"] = 1
else if (plan_seen && testno > planned_tests)
result_obj["is_unplanned"] = 1
else
result_obj["is_unplanned"] = 0
# Strip trailing and leading whitespace.
sub("^[ \t]*", "", line)
sub("[ \t]*$", "", line)
# This will have to be corrected if we have a "TODO"/"SKIP" directive.
result_obj["description"] = line
result_obj["directive"] = ""
result_obj["explanation"] = ""
if (index(line, "#") == 0)
return # No possible directive, nothing more to do.
# Directives are case-insensitive.
rx = "[ \t]*#[ \t]*([tT][oO][dD][oO]|[sS][kK][iI][pP])[ \t]*"
# See whether we have the directive, and if yes, where.
pos = match(line, rx "$")
if (!pos)
pos = match(line, rx "[^a-zA-Z0-9_]")
# If there was no TAP directive, we have nothing more to do.
if (!pos)
return
# Let`s now see if the TAP directive has been escaped. For example:
# escaped: ok \# SKIP
# not escaped: ok \\# SKIP
# escaped: ok \\\\\# SKIP
# not escaped: ok \ # SKIP
if (substr(line, pos, 1) == "#")
{
bslash_count = 0
for (i = pos; i > 1 && substr(line, i - 1, 1) == "\\"; i--)
bslash_count += 1
if (bslash_count % 2)
return # Directive was escaped.
}
# Strip the directive and its explanation (if any) from the test
# description.
result_obj["description"] = substr(line, 1, pos - 1)
# Now remove the test description from the line, that has been dealt
# with already.
line = substr(line, pos)
# Strip the directive, and save its value (normalized to upper case).
sub("^[ \t]*#[ \t]*", "", line)
result_obj["directive"] = toupper(substr(line, 1, 4))
line = substr(line, 5)
# Now get the explanation for the directive (if any), with leading
# and trailing whitespace removed.
sub("^[ \t]*", "", line)
sub("[ \t]*$", "", line)
result_obj["explanation"] = line
}
function get_test_exit_message(status)
{
if (status == 0)
return ""
if (status !~ /^[1-9][0-9]*$/)
abort("getting exit status")
if (status < 127)
exit_details = ""
else if (status == 127)
exit_details = " (command not found?)"
else if (status >= 128 && status <= 255)
exit_details = sprintf(" (terminated by signal %d?)", status - 128)
else if (status > 256 && status <= 384)
# We used to report an "abnormal termination" here, but some Korn
# shells, when a child process die due to signal number n, can leave
# in $? an exit status of 256+n instead of the more standard 128+n.
# Apparently, both behaviours are allowed by POSIX (2008), so be
# prepared to handle them both. See also Austing Group report ID
# 0000051 <http://www.austingroupbugs.net/view.php?id=51>
exit_details = sprintf(" (terminated by signal %d?)", status - 256)
else
# Never seen in practice.
exit_details = " (abnormal termination)"
return sprintf("exited with status %d%s", status, exit_details)
}
function write_test_results()
{
print ":global-test-result: " get_global_test_result() > trs_file
print ":recheck: " yn(must_recheck()) > trs_file
print ":copy-in-global-log: " yn(copy_in_global_log()) > trs_file
for (i = 0; i < test_results_index; i += 1)
print ":test-result: " test_results_list[i] > trs_file
close(trs_file);
}
BEGIN {
## ------- ##
## SETUP ##
## ------- ##
'"$init_colors"'
# Properly initialized once the TAP plan is seen.
planned_tests = 0
COOKED_PASS = expect_failure ? "XPASS": "PASS";
COOKED_FAIL = expect_failure ? "XFAIL": "FAIL";
# Enumeration-like constants to remember which kind of plan (if any)
# has been seen. It is important that NO_PLAN evaluates "false" as
# a boolean.
NO_PLAN = 0
EARLY_PLAN = 1
LATE_PLAN = 2
testno = 0 # Number of test results seen so far.
bailed_out = 0 # Whether a "Bail out!" directive has been seen.
# Whether the TAP plan has been seen or not, and if yes, which kind
# it is ("early" is seen before any test result, "late" otherwise).
plan_seen = NO_PLAN
## --------- ##
## PARSING ##
## --------- ##
is_first_read = 1
while (1)
{
# Involutions required so that we are able to read the exit status
# from the last input line.
st = getline
if (st < 0) # I/O error.
fatal("I/O error while reading from input stream")
else if (st == 0) # End-of-input
{
if (is_first_read)
abort("in input loop: only one input line")
break
}
if (is_first_read)
{
is_first_read = 0
nextline = $0
continue
}
else
{
curline = nextline
nextline = $0
$0 = curline
}
# Copy any input line verbatim into the log file.
print | "cat >&3"
# Parsing of TAP input should stop after a "Bail out!" directive.
if (bailed_out)
continue
# TAP test result.
if ($0 ~ /^(not )?ok$/ || $0 ~ /^(not )?ok[^a-zA-Z0-9_]/)
{
testno += 1
setup_result_obj($0)
handle_tap_result()
}
# TAP plan (normal or "SKIP" without explanation).
else if ($0 ~ /^1\.\.[0-9]+[ \t]*$/)
{
# The next two lines will put the number of planned tests in $0.
sub("^1\\.\\.", "")
sub("[^0-9]*$", "")
handle_tap_plan($0, "")
continue
}
# TAP "SKIP" plan, with an explanation.
else if ($0 ~ /^1\.\.0+[ \t]*#/)
{
# The next lines will put the skip explanation in $0, stripping
# any leading and trailing whitespace. This is a little more
# tricky in truth, since we want to also strip a potential leading
# "SKIP" string from the message.
sub("^[^#]*#[ \t]*(SKIP[: \t][ \t]*)?", "")
sub("[ \t]*$", "");
handle_tap_plan(0, $0)
}
# "Bail out!" magic.
# Older versions of prove and TAP::Harness (e.g., 3.17) did not
# recognize a "Bail out!" directive when preceded by leading
# whitespace, but more modern versions (e.g., 3.23) do. So we
# emulate the latter, "more modern" behaviour.
else if ($0 ~ /^[ \t]*Bail out!/)
{
bailed_out = 1
# Get the bailout message (if any), with leading and trailing
# whitespace stripped. The message remains stored in `$0`.
sub("^[ \t]*Bail out![ \t]*", "");
sub("[ \t]*$", "");
# Format the error message for the
bailout_message = "Bail out!"
if (length($0))
bailout_message = bailout_message " " $0
testsuite_error(bailout_message)
}
# Maybe we have too look for dianogtic comments too.
else if (comments != 0)
{
comment = extract_tap_comment($0);
if (length(comment))
report("#", comment);
}
}
## -------- ##
## FINISH ##
## -------- ##
# A "Bail out!" directive should cause us to ignore any following TAP
# error, as well as a non-zero exit status from the TAP producer.
if (!bailed_out)
{
if (!plan_seen)
{
testsuite_error("missing test plan")
}
else if (planned_tests != testno)
{
bad_amount = testno > planned_tests ? "many" : "few"
testsuite_error(sprintf("too %s tests run (expected %d, got %d)",
bad_amount, planned_tests, testno))
}
if (!ignore_exit)
{
# Fetch exit status from the last line.
exit_message = get_test_exit_message(nextline)
if (exit_message)
testsuite_error(exit_message)
}
}
write_test_results()
exit 0
} # End of "BEGIN" block.
'
# TODO: document that we consume the file descriptor 3 :-(
} 3>"$log_file"
test $? -eq 0 || fatal "I/O or internal error"
# Local Variables:
# mode: shell-script
# sh-indentation: 2
# eval: (add-hook 'write-file-hooks 'time-stamp)
# time-stamp-start: "scriptversion="
# time-stamp-format: "%:y-%02m-%02d.%02H"
# time-stamp-time-zone: "UTC"
# time-stamp-end: "; # UTC"
# End:

5
build-helpers/tap-test Normal file
View File

@ -0,0 +1,5 @@
#! /bin/sh
# run a GTest in tap mode. The test binary is passed as $1
$1 -k --tap

75
cmake/FindLibEV.cmake Normal file
View File

@ -0,0 +1,75 @@
SET(LIBEV_PATH "" CACHE PATH "Base path for include/ev.h and lib/libev*")
SET(LIBEV_INCLUDE_PATH "" CACHE PATH "Include path for ev.h")
SET(LIBEV_LIBDIR "" CACHE PATH "Path containing libev")
IF(LIBEV_PATH)
SET(LIBEV_INCLUDE_PATH "${LIBEV_PATH}/include" CACHE PATH "Include path for ev.h" FORCE)
SET(LIBEV_LIBDIR "${LIBEV_PATH}/lib" CACHE PATH "Path containing libev" FORCE)
ENDIF(LIBEV_PATH)
IF(LIBEV_INCLUDE_PATH)
INCLUDE_DIRECTORIES(${LIBEV_INCLUDE_PATH})
ENDIF(LIBEV_INCLUDE_PATH)
# Use cached result
IF(NOT LIBEV_FOUND)
UNSET(HAVE_EV_H)
UNSET(HAVE_LIBEV)
UNSET(HAVE_EV_H CACHE)
UNSET(HAVE_LIBEV CACHE)
UNSET(LIBEV_CFLAGS)
UNSET(LIBEV_LDFLAGS)
IF(LIBEV_INCLUDE_PATH OR LIBEV_LIBDIR)
SET(CMAKE_REQUIRED_INCLUDES ${LIBEV_INCLUDE_PATH})
# MESSAGE(STATUS "Looking for ev.h in ${CMAKE_REQUIRED_INCLUDES}")
CHECK_INCLUDE_FILES(ev.h HAVE_EV_H)
IF(HAVE_EV_H)
# MESSAGE(STATUS "Looking for lib ev in ${LIBEV_LIBDIR}")
CHECK_LIBRARY_EXISTS(ev ev_time "${LIBEV_LIBDIR}" HAVE_LIBEV)
IF(HAVE_LIBEV)
SET(LIBEV_LIBRARIES ev CACHE INTERNAL "")
SET(LIBEV_CFLAGS "" CACHE INTERNAL "")
SET(LIBEV_CFLAGS_OTHER "" CACHE INTERNAL "")
SET(LIBEV_INCLUDE_DIRS "" CACHE INTERNAL "")
SET(LIBEV_LDFLAGS "-L${LIBEV_LIBDIR} -lev" CACHE INTERNAL "")
SET(LIBEV_FOUND TRUE CACHE INTERNAL "Found libev" FORCE)
ELSE(HAVE_LIBEV)
MESSAGE(STATUS "Couldn't find lib ev in ${LIBEV_LIBDIR}")
ENDIF(HAVE_LIBEV)
ELSE(HAVE_EV_H)
MESSAGE(STATUS "Couldn't find <ev.h> in ${LIBEV_INCLUDE_PATH}")
ENDIF(HAVE_EV_H)
ELSE(LIBEV_INCLUDE_PATH OR LIBEV_LIBDIR)
pkg_check_modules(LIBEV libev)
IF(NOT LIBEV_FOUND)
# MESSAGE(STATUS "Looking for ev.h in ${CMAKE_REQUIRED_INCLUDES}")
CHECK_INCLUDE_FILES(ev.h HAVE_EV_H)
IF(HAVE_EV_H)
# MESSAGE(STATUS "Looking for lib ev")
CHECK_LIBRARY_EXISTS(ev ev_time "" HAVE_LIBEV)
IF(HAVE_LIBEV)
SET(LIBEV_CFLAGS "" CACHE INTERNAL "")
SET(LIBEV_CFLAGS_OTHER "" CACHE INTERNAL "")
SET(LIBEV_INCLUDE_DIRS "" CACHE INTERNAL "")
SET(LIBEV_LDFLAGS "-lev" CACHE INTERNAL "")
SET(LIBEV_FOUND TRUE CACHE INTERNAL "Found libev" FORCE)
ELSE(HAVE_LIBEV)
MESSAGE(STATUS "Couldn't find lib ev")
ENDIF(HAVE_LIBEV)
ELSE(HAVE_EV_H)
MESSAGE(STATUS "Couldn't find <ev.h>")
ENDIF(HAVE_EV_H)
ENDIF(NOT LIBEV_FOUND)
ENDIF(LIBEV_INCLUDE_PATH OR LIBEV_LIBDIR)
ENDIF(NOT LIBEV_FOUND)
IF(NOT LIBEV_FOUND)
IF(LibEV_FIND_REQUIRED)
MESSAGE(FATAL_ERROR "Could not find libev")
ENDIF(LibEV_FIND_REQUIRED)
ENDIF(NOT LIBEV_FOUND)
MARK_AS_ADVANCED(LIBEV_PATH LIBEV_INCLUDE_PATH LIBEV_LIBDIR)

48
cmake/FindRagel.cmake Normal file
View File

@ -0,0 +1,48 @@
IF(NOT RAGEL_EXECUTABLE)
MESSAGE(STATUS "Looking for ragel")
FIND_PROGRAM(RAGEL_EXECUTABLE ragel)
IF(RAGEL_EXECUTABLE)
EXECUTE_PROCESS(COMMAND "${RAGEL_EXECUTABLE}" -v OUTPUT_VARIABLE _version)
STRING(REGEX MATCH "[0-9.]+" RAGEL_VERSION ${_version})
SET(RAGEL_FOUND TRUE)
ENDIF(RAGEL_EXECUTABLE)
ELSE(NOT RAGEL_EXECUTABLE)
EXECUTE_PROCESS(COMMAND "${RAGEL_EXECUTABLE}" -v OUTPUT_VARIABLE _version)
STRING(REGEX MATCH "[0-9.]+" RAGEL_VERSION ${_version})
SET(RAGEL_FOUND TRUE)
ENDIF(NOT RAGEL_EXECUTABLE)
IF(RAGEL_FOUND)
IF (NOT Ragel_FIND_QUIETLY)
MESSAGE(STATUS "Found ragel: ${RAGEL_EXECUTABLE} (${RAGEL_VERSION})")
ENDIF (NOT Ragel_FIND_QUIETLY)
IF(NOT RAGEL_FLAGS)
SET(RAGEL_FLAGS "-T1")
ENDIF(NOT RAGEL_FLAGS)
MACRO(RAGEL_PARSER SRCFILE)
GET_FILENAME_COMPONENT(SRCPATH "${SRCFILE}" PATH)
GET_FILENAME_COMPONENT(SRCBASE "${SRCFILE}" NAME_WE)
SET(OUTFILE "${CMAKE_CURRENT_BINARY_DIR}/${SRCPATH}/${SRCBASE}.c")
FILE(MAKE_DIRECTORY "${CMAKE_CURRENT_BINARY_DIR}/${SRCPATH}")
SET(INFILE "${CMAKE_CURRENT_SOURCE_DIR}/${SRCFILE}")
SET(_flags ${ARGV1})
IF(NOT _flags)
SET(_flags ${RAGEL_FLAGS})
ENDIF(NOT _flags)
ADD_CUSTOM_COMMAND(OUTPUT ${OUTFILE}
COMMAND "${RAGEL_EXECUTABLE}"
ARGS -C ${_flags} -o "${OUTFILE}" "${INFILE}"
DEPENDS "${INFILE}"
COMMENT "Generating ${SRCBASE}.c from ${SRCFILE}"
)
ENDMACRO(RAGEL_PARSER)
ELSE(RAGEL_FOUND)
IF(Ragel_FIND_REQUIRED)
MESSAGE(FATAL_ERROR "Could not find ragel")
ENDIF(Ragel_FIND_REQUIRED)
ENDIF(RAGEL_FOUND)

View File

@ -0,0 +1,45 @@
## our modules are without the "lib" prefix
MACRO(ADD_AND_INSTALL_LIBRARY LIBNAME SRCFILES)
IF(BUILD_STATIC)
ADD_LIBRARY(${LIBNAME} STATIC ${SRCFILES})
TARGET_LINK_LIBRARIES(lighttpd2 ${LIBNAME})
ELSE(BUILD_STATIC)
ADD_LIBRARY(${LIBNAME} MODULE ${SRCFILES})
SET(L_INSTALL_TARGETS ${L_INSTALL_TARGETS} ${LIBNAME})
ADD_TARGET_PROPERTIES(${LIBNAME} LINK_FLAGS ${COMMON_LDFLAGS})
ADD_TARGET_PROPERTIES(${LIBNAME} COMPILE_FLAGS ${COMMON_CFLAGS})
SET_TARGET_PROPERTIES(${LIBNAME} PROPERTIES CMAKE_INSTALL_PREFIX "${CMAKE_INSTALL_PREFIX}")
TARGET_INCLUDE_DIRECTORIES(${LIBNAME} PRIVATE ${COMMON_INCLUDE_DIRECTORIES})
TARGET_LINK_LIBRARIES(${LIBNAME} lighttpd-${PACKAGE_VERSION}-common lighttpd-${PACKAGE_VERSION}-shared)
IF(APPLE)
SET_TARGET_PROPERTIES(${LIBNAME} PROPERTIES LINK_FLAGS "-flat_namespace -undefined suppress")
ENDIF(APPLE)
ENDIF(BUILD_STATIC)
ENDMACRO(ADD_AND_INSTALL_LIBRARY)
MACRO(ADD_TARGET_PROPERTIES _target _name)
SET(_properties)
FOREACH(_prop ${ARGN})
SET(_properties "${_properties} ${_prop}")
ENDFOREACH(_prop)
GET_TARGET_PROPERTY(_old_properties ${_target} ${_name})
#MESSAGE(STATUS "adding property to ${_target} ${_name}:" ${_properties})
IF(NOT _old_properties)
# in case it's NOTFOUND
SET(_old_properties)
ENDIF(NOT _old_properties)
SET_TARGET_PROPERTIES(${_target} PROPERTIES ${_name} "${_old_properties} ${_properties}")
ENDMACRO(ADD_TARGET_PROPERTIES)
MACRO(ADD_PREFIX _target _prefix)
SET(_oldtarget ${${_target}})
SET(_newtarget)
FOREACH(_t ${_oldtarget})
SET(_newtarget ${_newtarget} "${_prefix}${_t}")
ENDFOREACH(_t)
SET(${_target} ${_newtarget})
ENDMACRO(ADD_PREFIX)

475
configure.ac Normal file
View File

@ -0,0 +1,475 @@
# -*- Autoconf -*-
# Process this file with autoconf to produce a configure script.
AC_PREREQ([2.69])
AC_INIT([lighttpd],[2.0.0],[],[],[https://redmine.lighttpd.net/projects/lighttpd2/wiki])
AC_CONFIG_SRCDIR([src/main/lighttpd_worker.c])
AC_CONFIG_HEADERS([include/lighttpd/config.h])
AC_CONFIG_MACRO_DIR([m4])
AM_INIT_AUTOMAKE([-Wall -Wno-portability -Wno-override -Werror foreign dist-bzip2 tar-ustar] serial-tests)
m4_include([build-helpers/glibtests.m4])
GLIB_TESTS
dnl check environment
AC_USE_SYSTEM_EXTENSIONS
# Checks for programs.
AC_PROG_CC
AC_PROG_MAKE_SET
AC_PROG_INSTALL
# AC_PROG_RANLIB
AM_PROG_AR
AC_PATH_PROG([RAGEL], [ragel])
if test "x$RAGEL" = "x"; then
AC_MSG_ERROR([ragel not found])
fi
AC_SUBST([RAGEL])
m4_ifndef([PKG_PROG_PKG_CONFIG], [m4_fatal([pkg-config not installed])])
m4_ifndef([LT_INIT], [m4_fatal([libtool not installed])])
LT_INIT([shared disable-static])
# Checks for header files.
AC_HEADER_SYS_WAIT
AC_CHECK_HEADERS([ \
unistd.h \
stddef.h \
sys/mman.h \
sys/resource.h \
sys/sendfile.h \
sys/types.h \
sys/uio.h \
sys/un.h \
execinfo.h \
])
# pkglibdir
AC_ARG_WITH(
[pkglibdir],
AS_HELP_STRING([--with-pkglibdir=dir],
[specify directory for driver files (default LIBDIR/lighttpd-VERSION]),
[pkglibdir=$withval],
[pkglibdir=$libdir/lighttpd-$PACKAGE_VERSION])
AC_SUBST(pkglibdir)
# libexecdir
libexecdir=$libexecdir/lighttpd2
AC_SUBST([libexecdir])
# Checks for libraries.
# glib/gthread (gthread includes glib)
PKG_CHECK_MODULES([GTHREAD], [gthread-2.0 >= 2.16.0], [],[AC_MSG_ERROR("gthread-2.0 >= 2.16.0 not found")])
# gmodule
PKG_CHECK_MODULES([GMODULE], [gmodule-2.0 >= 2.16.0], [],[AC_MSG_ERROR("gmodule-2.0 >= 2.16.0 not found")])
AC_MSG_CHECKING([for libev support])
AC_ARG_WITH([libev],
[AS_HELP_STRING([--with-libev@<:@=PATH@:>@],[Search for libev in PATH/include and PATH/lib])],
[WITH_LIBEV=$withval],[WITH_LIBEV=yes])
LIBEV_CFLAGS=""
LIBEV_LIBS=""
PKG_CHECK_MODULES([LIBEV], [libev], [], [
# no pkg-config for libev, searching manually:
if test "$WITH_LIBEV" != "yes"; then
LIBEV_CFLAGS="-I$WITH_LIBEV/include"
LIBEV_LIBS="-L$WITH_LIBEV/lib -lev"
else
AC_CHECK_HEADERS([ev.h],[
AC_CHECK_LIB([ev], [ev_time], [
LIBEV_LIBS="-lev"
],[
AC_MSG_ERROR([libev not found])
]
)],[
AC_MSG_ERROR([libev not found])
]
)
fi
])
AC_SUBST([LIBEV_CFLAGS])
AC_SUBST([LIBEV_LIBS])
dnl Large File Support
AC_ARG_ENABLE([lfs],
[AS_HELP_STRING([--disable-lfs],[disable large file support])],
[case "${enableval}" in
yes) lfs=true ;;
no) lfs=false ;;
*) AC_MSG_ERROR([bad value ${enableval} for --enable-lfs]) ;;
esac],[lfs=true])
if test x$lfs = xtrue; then
CFLAGS="${CFLAGS} -D_FILE_OFFSET_BITS=64 -D_LARGEFILE_SOURCE -D_LARGE_FILES"
fi
dnl Check for gnutls
AC_ARG_WITH([gnutls], [AS_HELP_STRING([--with-gnutls],[gnutls library for ssl/tls (default)])],
[WITH_GNUTLS=$withval],[WITH_GNUTLS=yes])
if test "$WITH_GNUTLS" != "no"; then
PKG_CHECK_MODULES([GNUTLS], [gnutls],[],[
AC_MSG_ERROR([gnutls not found])
])
AC_SUBST([GNUTLS_CFLAGS])
AC_SUBST([GNUTLS_LIBS])
USE_GNUTLS=true
fi
AM_CONDITIONAL([USE_GNUTLS], [test "$USE_GNUTLS" = "true"])
dnl Check for libidn, needed to decode SNI names
AC_ARG_WITH([sni], [AS_HELP_STRING([--with-sni],[SNI support for gnutls/openssl, needs libidn (default)])],
[WITH_SNI=$withval],[WITH_SNI=yes])
if test "$WITH_SNI" != "no"; then
PKG_CHECK_MODULES([IDN], [libidn],[],[
AC_MSG_ERROR([libidn not found])
])
AC_SUBST([IDN_CFLAGS])
AC_SUBST([IDN_LIBS])
AC_DEFINE([USE_SNI], [1], [use sni])
USE_SNI=true
fi
AM_CONDITIONAL([USE_SNI], [test "$USE_SNI" = "true"])
dnl Check for lua
AC_MSG_CHECKING([for lua])
AC_ARG_WITH([lua], [AS_HELP_STRING([--with-lua],[lua engine (default)])],
[WITH_LUA=$withval],[WITH_LUA=yes])
AC_MSG_RESULT([$WITH_LUA])
if test "$WITH_LUA" != "no"; then
# try pkgconfig
if test "$WITH_LUA" = "yes"; then
LUAPC=lua
else
LUAPC=$WITH_LUA
fi
PKG_CHECK_MODULES([LUA], [$LUAPC >= 5.1], [
AC_DEFINE([HAVE_LUA], [1], [liblua])
AC_DEFINE([HAVE_LUA_H], [1], [lua.h])
],[
# for debian based systems
PKG_CHECK_MODULES([LUA], [lua5.1 >= 5.1], [
AC_DEFINE([HAVE_LUA], [1], [liblua])
AC_DEFINE([HAVE_LUA_H], [1], [lua.h])
],[
# for freebsd
PKG_CHECK_MODULES([LUA], [lua-5.1 >= 5.1], [
AC_DEFINE([HAVE_LUA], [1], [liblua])
AC_DEFINE([HAVE_LUA_H], [1], [lua.h])
],[
AC_MSG_ERROR([lua not found])
])
])
])
AC_SUBST([LUA_CFLAGS])
AC_SUBST([LUA_LIBS])
USE_LUA=true
fi
AM_CONDITIONAL([USE_LUA], [test "$USE_LUA" = "true"])
# Checks for typedefs, structures, and compiler characteristics.
AC_C_CONST
AC_TYPE_UID_T
AC_TYPE_PID_T
AC_TYPE_SIZE_T
## solaris needs -lsocket -lnsl
AC_SEARCH_LIBS([socket],[socket])
AC_SEARCH_LIBS([inet_addr],[nsl socket])
## freebsd: kvm
AC_SEARCH_LIBS([kvm_open],[kvm])
## math functions
AC_SEARCH_LIBS([fmod],[m])
# Checks for library functions.
AC_CHECK_FUNCS([ \
chroot \
getrlimit \
gmtime_r \
inet_aton \
inet_ntop \
localtime_r \
madvise \
mmap \
posix_fadvise \
sendfile \
sendfile64 \
sendfilev \
writev \
accept4 \
])
dnl Check for IPv6 support
AC_ARG_ENABLE([ipv6],
[AS_HELP_STRING([--disable-ipv6],[disable IPv6 support])],
[case "${enableval}" in
yes) ipv6=true ;;
no) ipv6=false ;;
*) AC_MSG_ERROR([bad value ${enableval} for --enable-ipv6]) ;;
esac],[ipv6=true])
if test x$ipv6 = xtrue; then
AC_CACHE_CHECK([for IPv6 support], [ac_cv_ipv6_support],
[AC_LINK_IFELSE([AC_LANG_PROGRAM([[ #include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>]], [[struct sockaddr_in6 s; struct in6_addr t=in6addr_any; int i=AF_INET6; s; t.s6_addr[0] = 0; ]])],[ac_cv_ipv6_support=yes],[ac_cv_ipv6_support=no])])
if test "$ac_cv_ipv6_support" = yes; then
AC_DEFINE([HAVE_IPV6],[1],[Whether to enable IPv6 support])
else
AC_MSG_ERROR([IPv6 not supported. Use --disable-ipv6 if this is acceptable.])
fi
fi
dnl Check for struct sockaddr_storage
AC_CACHE_CHECK([for struct sockaddr_storage support], [ac_cv_sockaddr_storage_support],
[AC_LINK_IFELSE([AC_LANG_PROGRAM([[ #include <sys/socket.h> ]], [[struct sockaddr_storage s; ]])],[ac_cv_sockaddr_storage_support=yes],[ac_cv_sockaddr_storage_support=no])])
if test "ac_cv_sockaddr_storage_support" = yes; then
AC_DEFINE([HAVE_SOCKADDR_STORAGE],[1],[Whether we have struct sockaddr_storage])
fi
dnl Checking for libunwind
AC_MSG_CHECKING(for libunwind)
AC_ARG_WITH(libunwind,
AS_HELP_STRING([--with-libunwind],[Include libunwind support for backtraces on assert failures (default)]),
[WITH_LIBUNWIND=$withval],[WITH_LIBUNWIND=yes])
if test "$WITH_LIBUNWIND" != "no"; then
have_libunwind=no
PKG_CHECK_MODULES(LIBUNWIND, libunwind, [have_libunwind=yes], [
# pkg-config failed, search manually
OLDLIBS="$LIBS"
LIBS="$LIBS -lunwind"
AC_CACHE_CHECK([for libunwind support], [ac_cv_libunwind],
[AC_LINK_IFELSE([AC_LANG_PROGRAM([[
# define UNW_LOCAL_ONLY
# include <libunwind.h>
]], [[
unw_context_t context;
unw_getcontext(&context);
]])],[ac_cv_libunwind=yes],[ac_cv_libunwind=no])])
LIBS="$OLDLIBS"
if test "$ac_cv_libunwind" = yes; then
LIBUNWIND_CFLAGS=
LIBUNWIND_LIBS=-lunwind
fi
have_libunwind="$ac_cv_libunwind"
])
if test "$have_libunwind" = yes; then
AC_DEFINE(HAVE_LIBUNWIND, 1, [Have libunwind support])
else
AC_MSG_ERROR("couldn't find libunwind")
fi
AC_SUBST([LIBUNWIND_CFLAGS])
AC_SUBST([LIBUNWIND_LIBS])
fi
dnl Check for openssl
AC_MSG_CHECKING([for OpenSSL])
AC_ARG_WITH([openssl],
AS_HELP_STRING([--with-openssl@<:@=DIR@:>@],[Include openssl support (default)]),
[WITH_OPENSSL=$withval],[WITH_OPENSSL=yes])
OPENSSL_CFLAGS=""
OPENSSL_LIBS=""
if test "$WITH_OPENSSL" != "no"; then
use_openssl=yes
if test "$WITH_OPENSSL" != "yes"; then
OPENSSL_CFLAGS="-I$WITH_OPENSSL/include"
OPENSSL_LIBS="-L$WITH_OPENSSL/lib"
fi
else
use_openssl=no
fi
AC_MSG_RESULT([$use_openssl])
AC_ARG_WITH([openssl-includes],
[AS_HELP_STRING([--with-openssl-includes=DIR],[Custom OpenSSL include path])],
[ use_openssl=yes OPENSSL_CFLAGS="-I$withval" ]
)
AC_ARG_WITH([openssl-libs],
[AS_HELP_STRING([--with-openssl-libs=DIR],[Custom OpenSSL library path])],
[ use_openssl=yes OPENSSL_LIBS="-L$withval" ]
)
AC_ARG_WITH([kerberos5],
[AS_HELP_STRING([--with-kerberos5],[use Kerberos5 support with OpenSSL])],
[ use_kerberos=$withval ], [use_kerberos=no]
)
if test "$use_openssl" = "yes"; then
if test "$use_kerberos" = "no"; then
OPENSSL_CFLAGS="$OPENSSL_CFLAGS -DOPENSSL_NO_KRB5"
fi
OLD_LIBS="$LIBS"
OLD_LDFLAGS="$LDFLAGS"
OLD_CPPFLAGS="$CPPFLAGS"
LDFLAGS="$LDFLAGS $OPENSSL_LIBS"
CPPFLAGS="$CPPFLAGS $OPENSSL_CFLAGS"
AC_CHECK_HEADERS([openssl/ssl.h])
AC_CHECK_LIB([crypto], [BIO_f_base64], [
AC_CHECK_LIB([ssl], [SSL_new], [
OPENSSL_LIBS="$OPENSSL_LIBS -lssl -lcrypto"
have_openssl=yes
AC_DEFINE([HAVE_OPENSSL], [], [Have openssl])
], [], [ -lcrypto "$DL_LIB" ])
], [], [])
LIBS="$OLD_LIBS"
LDFLAGS="$OLD_LDFLAGS"
CPPFLAGS="$OLD_CPPFLAGS"
if test "x$have_openssl" != "xyes"; then
AC_MSG_ERROR([Couldn't find openssl])
fi
AC_SUBST([OPENSSL_CFLAGS])
AC_SUBST([OPENSSL_LIBS])
fi
AM_CONDITIONAL([USE_OPENSSL], [test "x$have_openssl" = "xyes"])
# mod-deflate:
use_mod_deflate=no
# check for zlib
AC_MSG_CHECKING([for zlib support])
AC_ARG_WITH([zlib], [AS_HELP_STRING([--with-zlib],[Enable zlib support for mod_deflate (default)])],
[WITH_ZLIB=$withval],[WITH_ZLIB=yes])
AC_MSG_RESULT([$WITH_ZLIB])
if test "$WITH_BZIP2" != "no"; then
AC_CHECK_LIB([z], [deflate], [
AC_CHECK_HEADERS([zlib.h],[
Z_LIB=-lz
use_mod_deflate=yes
AC_DEFINE([HAVE_ZLIB], [1], [with zlib])
])
])
fi
AC_SUBST([Z_LIB])
# check for bzip2
AC_MSG_CHECKING([for bzip2 support])
AC_ARG_WITH([bzip2], [AS_HELP_STRING([--with-bzip2],[Enable bzip2 support for mod_deflate (default)])],
[WITH_BZIP2=$withval],[WITH_BZIP2=yes])
AC_MSG_RESULT([$WITH_BZIP2])
if test "$WITH_BZIP2" != "no"; then
AC_CHECK_LIB([bz2], [BZ2_bzCompress], [
AC_CHECK_HEADERS([bzlib.h],[
BZ_LIB=-lbz2
use_mod_deflate=yes
AC_DEFINE([HAVE_BZIP], [1], [with bzip2])
])
])
fi
AC_SUBST([BZ_LIB])
AM_CONDITIONAL([USE_MOD_DEFLATE], [test "x$use_mod_deflate" = "xyes"])
AC_ARG_ENABLE([profiler],
[AS_HELP_STRING([--enable-profiler],[enable memory profiler support])],[
profiler=yes
AC_DEFINE([WITH_PROFILER], [1], [profiler])
AC_CHECK_HEADERS([execinfo.h])
],[])
AM_CONDITIONAL([WITH_PROFILER], [test "x$profiler" = "xyes"])
dnl search for crypt_r and (fallback) for crypt
save_LIBS=$LIBS
LIBS=
AC_SEARCH_LIBS([crypt_r],[crypt],[
AC_DEFINE([HAVE_CRYPT_R], [1], [crypt_r])
AC_CHECK_HEADERS([crypt.h],[
AC_DEFINE([HAVE_CRYPT_H], [1], [crypt.h])
])
CRYPT_LIB=$LIBS
],[
AC_SEARCH_LIBS([crypt],[crypt],[
AC_CHECK_HEADERS([crypt.h],[
AC_DEFINE([HAVE_CRYPT_H], [1], [crypt.h])
])
CRYPT_LIB=$LIBS
])
])
LIBS=$save_LIBS
AC_SUBST([CRYPT_LIB])
# check for extra compiler options (warning options)
if test "${GCC}" = "yes"; then
CFLAGS="${CFLAGS} -Wall -W -Wshadow -pedantic -std=gnu99"
fi
AC_ARG_ENABLE([extra-warnings],
[AS_HELP_STRING([--enable-extra-warnings],[enable extra warnings (gcc specific)])],
[case "${enableval}" in
yes) extrawarnings=true ;;
no) extrawarnings=false ;;
*) AC_MSG_ERROR([bad value ${enableval} for --enable-extra-warnings]) ;;
esac],[extrawarnings=false])
if test x$extrawarnings = xtrue; then
CFLAGS="${CFLAGS} -g -O2 -g2 -Wall -Wmissing-declarations -Wdeclaration-after-statement -Wcast-align -Wsign-compare -Wnested-externs -Wpointer-arith -Wmissing-prototypes -Wshadow -Wno-pointer-sign -Wformat-security -Wl,--as-needed -Wl,--no-undefined"
fi
AC_CONFIG_FILES([Makefile \
contrib/Makefile \
doc/Makefile \
include/Makefile \
include/lighttpd/Makefile \
src/Makefile \
src/common/Makefile \
src/main/Makefile \
src/angel/Makefile \
src/modules/Makefile \
src/unittests/Makefile \
src/lighttpd2.pc \
tests/Makefile \
])
AC_OUTPUT

10
contrib/Makefile.am Normal file
View File

@ -0,0 +1,10 @@
EXTRA_DIST=angel.conf lighttpd.conf mimetypes.conf service systemd \
default.html create-mimetypes.conf.pl
# see src/modules/Makefile.am
luadir = $(datarootdir)/lighttpd2/lua
dist_lua_DATA = core__cached_html.lua \
core.lua \
core__xsendfile.lua \
secdownload.lua \
secdownload__secdownload.lua

45
doc/Makefile.am Normal file
View File

@ -0,0 +1,45 @@
dist_man8_MANS=lighttpd2.8 lighttpd2-worker.8
EXTRA_DIST=\
jquery-1.10.1.min.js \
bootstrap.min.js \
bootstrap.min.css \
bootstrap-theme.min.css \
style.css \
doc_schema.xsd \
core_config.xml \
core_config_angel.xml \
core_fetch.xml \
core_introduction.xml \
core_lua.xml \
core_pattern.xml \
core_regex.xml \
mod_accesslog.xml \
mod_access.xml \
mod_auth.xml \
mod_balance.xml \
mod_cache_disk_etag.xml \
mod_core.lua.xml \
mod_debug.xml \
mod_deflate.xml \
mod_dirlist.xml \
mod_expire.xml \
mod_fastcgi.xml \
mod_flv.xml \
mod_fortune.xml \
mod_gnutls.xml \
mod_limit.xml \
mod_lua.xml \
mod_memcached.xml \
mod_openssl.xml \
mod_progress.xml \
mod_proxy.xml \
mod_redirect.xml \
mod_rewrite.xml \
mod_scgi.xml \
mod_secdownload.lua.xml \
mod_status.xml \
mod_throttle.xml \
mod_userdir.xml \
mod_vhost.xml \
plugin_core.xml \
compile.rb

1
include/Makefile.am Normal file
View File

@ -0,0 +1 @@
SUBDIRS=lighttpd

View File

@ -0,0 +1,7 @@
headerfiles=$(filter-out $(srcdir)/config.h,$(wildcard $(srcdir)/*.h))
EXTRA_DIST=$(headerfiles)
headersdir=$(includedir)/lighttpd
headers_DATA=$(headerfiles) config.h

View File

@ -88,7 +88,7 @@ if get_option('unwind')
endif endif
if get_option('openssl') if get_option('openssl')
dep_openssl = dependency('openssl', version: '>=1.1') # should find both ssl and crypto dep_openssl = dependency('openssl') # should find both ssl and crypto
else else
dep_openssl = disabler() dep_openssl = disabler()
endif endif

483
src/CMakeLists.txt Normal file
View File

@ -0,0 +1,483 @@
INCLUDE(CheckCSourceCompiles)
INCLUDE(CheckIncludeFiles)
INCLUDE(CheckFunctionExists)
INCLUDE(CheckVariableExists)
INCLUDE(CheckTypeSize)
INCLUDE(CheckLibraryExists)
INCLUDE(CMakeDetermineCCompiler)
INCLUDE(FindThreads)
INCLUDE(FindPkgConfig)
INCLUDE(LighttpdMacros)
FIND_PACKAGE(Ragel REQUIRED)
FIND_PACKAGE(LibEV REQUIRED)
cmake_policy(VERSION 2.6.4)
ADD_DEFINITIONS(-D_FILE_OFFSET_BITS=64 -D_LARGEFILE_SOURCE -D_LARGE_FILES)
OPTION(WITH_LUA "with lua 5.1 for lua-configfile [default: on]" ON)
OPTION(WITHOUT_CONFIG_PARSER "without standard config parser [default: off]" OFF)
OPTION(WITH_UNWIND "with (lib)unwind support in asserts to print backtraces [default: on]" ON)
OPTION(WITH_OPENSSL "with openssl support [default: on]" ON)
OPTION(WITH_GNUTLS "with gnutls support [default: on]" ON)
OPTION(WITH_SNI "with SNI support for gnutls/openssl, needs libidn [default: on]" ON)
OPTION(BUILD_STATIC "build a static lighttpd with all modules added")
OPTION(BUILD_EXTRA_WARNINGS "extra warnings [default: on]" ON)
OPTION(WITH_BZIP "with bzip2 support for mod_deflate [default: on]" ON)
OPTION(WITH_ZLIB "with deflate support for mod_deflate [default: on]" ON)
OPTION(WITH_PROFILER "with memory profiler")
OPTION(BUILD_UNIT_TESTS "build unit tests for testing")
IF(BUILD_STATIC)
SET(LIGHTTPD_STATIC 1)
ENDIF(BUILD_STATIC)
SET(CMAKE_REQUIRED_INCLUDES ${CMAKE_SYSTEM_INCLUDE_PATH})
CHECK_INCLUDE_FILES(inttypes.h HAVE_INTTYPES_H)
CHECK_INCLUDE_FILES(stddef.h HAVE_STDDEF_H)
CHECK_INCLUDE_FILES(stdint.h HAVE_STDINT_H)
CHECK_INCLUDE_FILES(sys/mman.h HAVE_SYS_MMAN_H)
CHECK_INCLUDE_FILES(sys/resource.h HAVE_SYS_RESOURCE_H)
CHECK_INCLUDE_FILES(sys/sendfile.h HAVE_SYS_SENDFILE_H)
CHECK_INCLUDE_FILES(sys/types.h HAVE_SYS_TYPES_H)
CHECK_INCLUDE_FILES(sys/uio.h HAVE_SYS_UIO_H)
CHECK_INCLUDE_FILES(sys/un.h HAVE_SYS_UN_H)
CHECK_INCLUDE_FILES(unistd.h HAVE_UNISTD_H)
CHECK_INCLUDE_FILES(execinfo.h HAVE_EXECINFO_H)
# will be needed for auth
CHECK_INCLUDE_FILES(crypt.h HAVE_CRYPT_H)
# check if we need libcrypt for crypt_r()
CHECK_LIBRARY_EXISTS(crypt crypt_r "" HAVE_LIBCRYPT_CRYPT_R)
IF(HAVE_LIBCRYPT_CRYPT_R)
SET(HAVE_CRYPT_R 1 FORCE)
SET(HAVE_LIBCRYPT 1 FORCE)
ELSE(HAVE_LIBCRYPT_CRYPT_R)
CHECK_LIBRARY_EXISTS(crypt crypt "" HAVE_LIBCRYPT)
ENDIF(HAVE_LIBCRYPT_CRYPT_R)
CHECK_FUNCTION_EXISTS(crypt_r HAVE_CRYPT_R)
CHECK_LIBRARY_EXISTS(kvm kvm_open "" HAVE_LIBKVM)
CHECK_TYPE_SIZE(long SIZEOF_LONG)
CHECK_TYPE_SIZE(off_t SIZEOF_OFF_T)
CHECK_FUNCTION_EXISTS(chroot HAVE_CHROOT)
CHECK_FUNCTION_EXISTS(getrlimit HAVE_GETRLIMIT)
CHECK_FUNCTION_EXISTS(gmtime_r HAVE_GMTIME_R)
CHECK_FUNCTION_EXISTS(inet_aton HAVE_INET_ATON)
CHECK_FUNCTION_EXISTS(inet_ntop HAVE_INET_NTOP)
CHECK_FUNCTION_EXISTS(localtime_r HAVE_LOCALTIME_R)
CHECK_FUNCTION_EXISTS(madvise HAVE_MADVISE)
CHECK_FUNCTION_EXISTS(mmap HAVE_MMAP)
CHECK_FUNCTION_EXISTS(posix_fadvise HAVE_POSIX_FADVISE)
CHECK_FUNCTION_EXISTS(sendfile HAVE_SENDFILE)
CHECK_FUNCTION_EXISTS(sendfile64 HAVE_SENDFILE64)
CHECK_FUNCTION_EXISTS(sendfilev HAVE_SENDFILEV)
CHECK_FUNCTION_EXISTS(writev HAVE_WRITEV)
CHECK_FUNCTION_EXISTS(accept4 HAVE_ACCEPT4)
CHECK_C_SOURCE_COMPILES("
#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
int main() {
struct sockaddr_in6 s; struct in6_addr t=in6addr_any; int i=AF_INET6; s; t.s6_addr[0] = 0;
return 0;
}" HAVE_IPV6)
CHECK_C_SOURCE_COMPILES("
#include <sys/socket.h>
int main() {
struct sockaddr_storage s;
return 0;
}" HAVE_SOCKADDR_STORAGE)
# glib/gthread
pkg_check_modules(GTHREAD REQUIRED gthread-2.0>=2.16)
pkg_check_modules(GMODULE REQUIRED gmodule-2.0>=2.16)
IF(WITH_LUA)
pkg_search_module(LUA REQUIRED lua lua5.1 lua-5.1)
SET(HAVE_LIBLUA 1 "Have liblua")
SET(HAVE_LUA_H 1 "Have liblua header")
ENDIF(WITH_LUA)
IF(WITH_GNUTLS)
pkg_search_module(GNUTLS REQUIRED gnutls)
ENDIF(WITH_GNUTLS)
IF(WITH_UNWIND)
pkg_search_module(UNWIND REQUIRED libunwind)
SET(HAVE_LIBUNWIND 1 "Have libunwind")
ENDIF(WITH_UNWIND)
IF(WITH_OPENSSL)
CHECK_INCLUDE_FILES(openssl/ssl.h HAVE_OPENSSL_SSL_H)
IF(HAVE_OPENSSL_SSL_H)
CHECK_LIBRARY_EXISTS(crypto BIO_f_base64 "" HAVE_LIBCRYPTO)
IF(HAVE_LIBCRYPTO)
SET(OPENSSL_NO_KRB5 1)
CHECK_LIBRARY_EXISTS(ssl SSL_new "" HAVE_LIBSSL)
ENDIF(HAVE_LIBCRYPTO)
ENDIF(HAVE_OPENSSL_SSL_H)
ENDIF(WITH_OPENSSL)
IF(WITH_SNI)
pkg_search_module(IDN REQUIRED libidn)
ADD_DEFINITIONS(-DUSE_SNI)
ENDIF(WITH_SNI)
IF(WITH_BZIP)
CHECK_INCLUDE_FILES(bzlib.h HAVE_BZLIB_H)
CHECK_LIBRARY_EXISTS(bz2 BZ2_bzCompressInit "" HAVE_LIBBZ2)
IF(HAVE_BZLIB_H AND HAVE_LIBBZ2)
SET(BZIP_LDFLAGS "-lbz2")
SET(BZIP_CFLAGS "")
SET(HAVE_BZIP 1)
ENDIF(HAVE_BZLIB_H AND HAVE_LIBBZ2)
ENDIF(WITH_BZIP)
IF(WITH_ZLIB)
CHECK_INCLUDE_FILES(zlib.h HAVE_ZLIB_H)
CHECK_LIBRARY_EXISTS(z deflate "" HAVE_LIBZ)
IF(HAVE_ZLIB_H AND HAVE_LIBZ)
SET(ZLIB_LDFLAGS "-lz")
SET(ZLIB_CFLAGS "")
SET(HAVE_ZLIB 1)
ENDIF(HAVE_ZLIB_H AND HAVE_LIBZ)
ENDIF(WITH_ZLIB)
IF(WITH_PROFILER)
CHECK_INCLUDE_FILES(execinfo.h HAVE_EXECINFO_H)
ENDIF(WITH_PROFILER)
IF(NOT BUILD_STATIC)
CHECK_INCLUDE_FILES(dlfcn.h HAVE_DLFCN_H)
ENDIF(NOT BUILD_STATIC)
IF(NOT SBINDIR)
SET(SBINDIR "sbin")
ENDIF(NOT SBINDIR)
IF(NOT LIGHTTPD_MODULES_DIR)
SET(LIGHTTPD_MODULES_DIR "lib${LIB_SUFFIX}/lighttpd")
ENDIF(NOT LIGHTTPD_MODULES_DIR)
IF(NOT WIN32)
ADD_DEFINITIONS(
-DLIBRARY_DIR="\\"${CMAKE_INSTALL_PREFIX}/${LIGHTTPD_MODULES_DIR}\\""
)
ELSE(NOT WIN32)
## We use relative path in windows
ADD_DEFINITIONS(
-DLIBRARY_DIR="\\"lib\\""
)
ENDIF(NOT WIN32)
## Write out config.h
CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/config.h.cmake ${CMAKE_BINARY_DIR}/include/lighttpd/config.h)
ADD_DEFINITIONS(-DHAVE_CONFIG_H)
INCLUDE_DIRECTORIES(${CMAKE_CURRENT_BINARY_DIR} ${CMAKE_CURRENT_SOURCE_DIR} ${CMAKE_SOURCE_DIR}/include ${CMAKE_BINARY_DIR}/include)
SET(COMMON_SRC
angel_connection.c
angel_data.c
buffer.c
encoding.c
events.c
fetch.c
idlist.c
ip_parsers.c
jobqueue.c
memcached.c
mempool.c
module.c
radix.c
sys_memory.c
sys_socket.c
tasklet.c
utils.c
value.c
waitqueue.c
)
IF(WITH_PROFILER)
SET(COMMON_SRC ${COMMON_SRC}
profiler.c
)
ENDIF(WITH_PROFILER)
ADD_PREFIX(COMMON_SRC common/)
SET(LIGHTTPD_SHARED_SRC
angel.c
angel_fake.c
actions.c
base_lua.c
backends.c
chunk.c
chunk_parser.c
collect.c
condition.c
connection.c
environment.c
etag.c
filter.c
filter_chunked.c
filter_buffer_on_disk.c
http_headers.c
http_range_parser.c
http_request_parser.c
http_response_parser.c
lighttpd_glue.c
log.c
mimetype.c
network.c
network_write.c network_writev.c
network_sendfile.c
options.c
pattern.c
plugin.c
request.c
response.c
server.c
stat_cache.c
stream.c
stream_http_response.c
stream_simple_socket.c
throttle.c
url_parser.c
value.c
virtualrequest.c
worker.c
plugin_core.c
)
IF(NOT WITHOUT_CONFIG_PARSER)
SET(LIGHTTPD_SHARED_SRC ${LIGHTTPD_SHARED_SRC}
config_parser.c
)
ENDIF(NOT WITHOUT_CONFIG_PARSER)
IF(WITH_LUA)
SET(LIGHTTPD_SHARED_SRC ${LIGHTTPD_SHARED_SRC}
actions_lua.c
condition_lua.c
config_lua.c
value_lua.c
chunk_lua.c
core_lua.c
environment_lua.c
filters_lua.c
http_headers_lua.c
physical_lua.c
request_lua.c
response_lua.c
stat_lua.c
subrequest_lua.c
virtualrequest_lua.c
)
ENDIF(WITH_LUA)
ADD_PREFIX(LIGHTTPD_SHARED_SRC main/)
SET(ANGEL_SHARED_SRC
angel_config_parser.c
angel_log.c
angel_plugin.c
angel_plugin_core.c
angel_proc.c
angel_server.c
angel_value.c
)
ADD_PREFIX(ANGEL_SHARED_SRC angel/)
## Build parsers by using ragel...
RAGEL_PARSER(main/config_parser.rl -T0)
RAGEL_PARSER(main/http_range_parser.rl)
RAGEL_PARSER(main/http_request_parser.rl)
RAGEL_PARSER(main/http_response_parser.rl)
RAGEL_PARSER(common/ip_parsers.rl)
RAGEL_PARSER(main/url_parser.rl)
RAGEL_PARSER(angel/angel_config_parser.rl)
SET(L_INSTALL_TARGETS)
ADD_LIBRARY(lighttpd-${PACKAGE_VERSION}-common SHARED
${COMMON_SRC}
)
ADD_LIBRARY(lighttpd-${PACKAGE_VERSION}-shared SHARED
${LIGHTTPD_SHARED_SRC}
)
TARGET_LINK_LIBRARIES(lighttpd-${PACKAGE_VERSION}-shared lighttpd-${PACKAGE_VERSION}-common)
ADD_LIBRARY(lighttpd-${PACKAGE_VERSION}-sharedangel SHARED
${ANGEL_SHARED_SRC}
)
TARGET_LINK_LIBRARIES(lighttpd-${PACKAGE_VERSION}-sharedangel lighttpd-${PACKAGE_VERSION}-common)
ADD_EXECUTABLE(lighttpd2-worker
main/lighttpd_worker.c
)
TARGET_LINK_LIBRARIES(lighttpd2-worker lighttpd-${PACKAGE_VERSION}-common lighttpd-${PACKAGE_VERSION}-shared)
ADD_EXECUTABLE(lighttpd2
angel/angel_main.c
)
TARGET_LINK_LIBRARIES(lighttpd2 lighttpd-${PACKAGE_VERSION}-common lighttpd-${PACKAGE_VERSION}-sharedangel)
SET(L_INSTALL_TARGETS ${L_INSTALL_TARGETS} lighttpd2-worker lighttpd2 lighttpd-${PACKAGE_VERSION}-common lighttpd-${PACKAGE_VERSION}-shared lighttpd-${PACKAGE_VERSION}-sharedangel)
IF(BUILD_EXTRA_WARNINGS)
SET(WARN_CFLAGS " -g -O2 -g2 -Wall -Wmissing-declarations -Wdeclaration-after-statement -Wcast-align -Wsign-compare -Wnested-externs -Wpointer-arith -Wmissing-prototypes -Wshadow -Wno-pointer-sign -Wformat-security")
SET(WARN_LDFLAGS " -g -O2 -g2 -Wall -Wl,--as-needed -Wl,--no-undefined")
# -Werror
ELSE(BUILD_EXTRA_WARNINGS)
SET(WARN_CFLAGS "")
SET(WARN_LDFLAGS "")
ENDIF(BUILD_EXTRA_WARNINGS)
SET(COMMON_LDFLAGS "${LUA_LDFLAGS} ${LIBEV_LDFLAGS} ${GTHREAD_LDFLAGS} ${GMODULE_LDFLAGS}${WARN_LDFLAGS}")
SET(COMMON_CFLAGS "${LUA_CFLAGS_OTHER} ${LIBEV_CFLAGS_OTHER} ${GTHREAD_CFLAGS_OTHER} ${GMODULE_CFLAGS_OTHER}${WARN_CFLAGS}")
SET(COMMON_INCLUDE_DIRECTORIES ${LUA_INCLUDE_DIRS} ${LIBEV_INCLUDE_DIRS} ${GTHREAD_INCLUDE_DIRS} ${GMODULE_INCLUDE_DIRS})
ADD_AND_INSTALL_LIBRARY(mod_access "modules/mod_access.c")
ADD_AND_INSTALL_LIBRARY(mod_accesslog "modules/mod_accesslog.c")
ADD_AND_INSTALL_LIBRARY(mod_auth "modules/mod_auth.c")
ADD_AND_INSTALL_LIBRARY(mod_balance "modules/mod_balance.c")
ADD_AND_INSTALL_LIBRARY(mod_cache_disk_etag "modules/mod_cache_disk_etag.c")
ADD_AND_INSTALL_LIBRARY(mod_debug "modules/mod_debug.c")
ADD_AND_INSTALL_LIBRARY(mod_dirlist "modules/mod_dirlist.c")
ADD_AND_INSTALL_LIBRARY(mod_expire "modules/mod_expire.c")
ADD_AND_INSTALL_LIBRARY(mod_fastcgi "modules/mod_fastcgi.c;modules/fastcgi_stream.c")
ADD_AND_INSTALL_LIBRARY(mod_flv "modules/mod_flv.c")
ADD_AND_INSTALL_LIBRARY(mod_fortune "modules/mod_fortune.c")
ADD_AND_INSTALL_LIBRARY(mod_limit "modules/mod_limit.c")
ADD_AND_INSTALL_LIBRARY(mod_memcached "modules/mod_memcached.c")
ADD_AND_INSTALL_LIBRARY(mod_progress "modules/mod_progress.c")
ADD_AND_INSTALL_LIBRARY(mod_proxy "modules/mod_proxy.c")
ADD_AND_INSTALL_LIBRARY(mod_redirect "modules/mod_redirect.c")
ADD_AND_INSTALL_LIBRARY(mod_rewrite "modules/mod_rewrite.c")
ADD_AND_INSTALL_LIBRARY(mod_scgi "modules/mod_scgi.c")
ADD_AND_INSTALL_LIBRARY(mod_status "modules/mod_status.c")
ADD_AND_INSTALL_LIBRARY(mod_throttle "modules/mod_throttle.c")
ADD_AND_INSTALL_LIBRARY(mod_userdir "modules/mod_userdir.c")
ADD_AND_INSTALL_LIBRARY(mod_vhost "modules/mod_vhost.c")
IF(HAVE_ZLIB OR HAVE_BZIP)
ADD_AND_INSTALL_LIBRARY(mod_deflate "modules/mod_deflate.c")
TARGET_LINK_LIBRARIES(mod_deflate ${BZIP_LDFLAGS} ${ZLIB_LDFLAGS})
ADD_TARGET_PROPERTIES(mod_deflate COMPILE_FLAGS ${BZIP_CFLAGS} ${ZLIB_CFLAGS})
ENDIF(HAVE_ZLIB OR HAVE_BZIP)
IF(WITH_LUA)
ADD_AND_INSTALL_LIBRARY(mod_lua "modules/mod_lua.c")
ENDIF(WITH_LUA)
IF(WITH_GNUTLS)
ADD_AND_INSTALL_LIBRARY(mod_gnutls "modules/mod_gnutls.c;modules/gnutls_filter.c;modules/gnutls_ocsp.c")
TARGET_LINK_LIBRARIES(mod_gnutls ${GNUTLS_LDFLAGS} ${IDN_LDFLAGS})
ADD_TARGET_PROPERTIES(mod_gnutls COMPILE_FLAGS ${GNUTLS_CFLAGS} ${IDN_CFLAGS})
ENDIF(WITH_GNUTLS)
IF(WITH_OPENSSL)
ADD_AND_INSTALL_LIBRARY(mod_openssl "modules/mod_openssl.c;modules/openssl_filter.c")
TARGET_LINK_LIBRARIES(mod_openssl ssl crypto ${IDN_LDFLAGS})
ADD_TARGET_PROPERTIES(mod_openssl COMPILE_FLAGS ${IDN_CFLAGS})
ENDIF(WITH_OPENSSL)
TARGET_LINK_LIBRARIES(lighttpd-${PACKAGE_VERSION}-common ${COMMON_LDFLAGS} ${UNWIND_LDFLAGS})
ADD_TARGET_PROPERTIES(lighttpd-${PACKAGE_VERSION}-common COMPILE_FLAGS ${COMMON_CFLAGS} ${UNWIND_CFLAGS})
TARGET_INCLUDE_DIRECTORIES(lighttpd-${PACKAGE_VERSION}-common PUBLIC ${COMMON_INCLUDE_DIRECTORIES})
TARGET_LINK_LIBRARIES(lighttpd-${PACKAGE_VERSION}-shared ${COMMON_LDFLAGS} m)
ADD_TARGET_PROPERTIES(lighttpd-${PACKAGE_VERSION}-shared COMPILE_FLAGS ${COMMON_CFLAGS})
TARGET_INCLUDE_DIRECTORIES(lighttpd-${PACKAGE_VERSION}-shared PUBLIC ${COMMON_INCLUDE_DIRECTORIES})
TARGET_LINK_LIBRARIES(lighttpd-${PACKAGE_VERSION}-sharedangel ${COMMON_LDFLAGS})
ADD_TARGET_PROPERTIES(lighttpd-${PACKAGE_VERSION}-sharedangel COMPILE_FLAGS ${COMMON_CFLAGS})
TARGET_INCLUDE_DIRECTORIES(lighttpd-${PACKAGE_VERSION}-sharedangel PUBLIC ${COMMON_INCLUDE_DIRECTORIES})
TARGET_LINK_LIBRARIES(lighttpd2-worker ${COMMON_LDFLAGS})
ADD_TARGET_PROPERTIES(lighttpd2-worker COMPILE_FLAGS ${COMMON_CFLAGS})
TARGET_INCLUDE_DIRECTORIES(lighttpd2-worker PUBLIC ${COMMON_INCLUDE_DIRECTORIES})
TARGET_LINK_LIBRARIES(lighttpd2 ${COMMON_LDFLAGS})
ADD_TARGET_PROPERTIES(lighttpd2 COMPILE_FLAGS ${COMMON_CFLAGS})
TARGET_INCLUDE_DIRECTORIES(lighttpd2 PUBLIC ${COMMON_INCLUDE_DIRECTORIES})
IF(HAVE_LIBCRYPT)
TARGET_LINK_LIBRARIES(lighttpd-${PACKAGE_VERSION}-common crypt)
ENDIF(HAVE_LIBCRYPT)
IF(HAVE_LIBKVM)
TARGET_LINK_LIBRARIES(lighttpd-${PACKAGE_VERSION}-common kvm)
ENDIF(HAVE_LIBKVM)
IF(CMAKE_COMPILER_IS_GNUCC)
SET(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -std=gnu99 -Wall -g -Wshadow -W -pedantic")
SET(CMAKE_C_FLAGS_RELEASE "${CMAKE_C_FLAGS_RELEASE} -O2")
SET(CMAKE_C_FLAGS_DEBUG "${CMAKE_C_FLAGS_DEBUG} -O0")
SET(CMAKE_C_FLAGS_RELWITHDEBINFO "${CMAKE_C_FLAGS_WITHDEBINFO} -O2")
ENDIF(CMAKE_COMPILER_IS_GNUCC)
SET_TARGET_PROPERTIES(lighttpd2-worker PROPERTIES CMAKE_INSTALL_PREFIX "${CMAKE_INSTALL_PREFIX}")
IF(WIN32)
SET(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -DNVALGRIND")
ADD_TARGET_PROPERTIES(lighttpd2-worker COMPILE_FLAGS "-DLI_DECLARE_EXPORTS")
TARGET_LINK_LIBRARIES(lighttpd2-worker ws2_32)
IF(MINGW)
TARGET_LINK_LIBRARIES(lighttpd2-worker msvcr70)
ADD_TARGET_PROPERTIES(lighttpd2-worker LINK_FLAGS "-Wl,-subsystem,console")
ENDIF(MINGW)
ENDIF(WIN32)
IF(NOT WIN32)
INSTALL(TARGETS ${L_INSTALL_TARGETS}
RUNTIME DESTINATION ${SBINDIR}
LIBRARY DESTINATION ${LIGHTTPD_MODULES_DIR}
ARCHIVE DESTINATION ${LIGHTTPD_MODULES_DIR}/static)
ELSE(NOT WIN32)
## HACK to make win32 to install our libraries in desired directory..
INSTALL(TARGETS lighttpd2-worker
RUNTIME DESTINATION ${SBINDIR}
ARCHIVE DESTINATION lib/static)
LIST(REMOVE_ITEM L_INSTALL_TARGETS lighttpd2-worker)
INSTALL(TARGETS ${L_INSTALL_TARGETS}
RUNTIME DESTINATION ${SBINDIR}/lib
LIBRARY DESTINATION lib
ARCHIVE DESTINATION lib/static)
ENDIF(NOT WIN32)
IF(BUILD_UNIT_TESTS)
MACRO(ADD_TEST_BINARY TESTNAME EXENAME SRCFILES)
ADD_EXECUTABLE(${EXENAME} ${SRCFILES})
TARGET_LINK_LIBRARIES(${EXENAME} ${COMMON_LDFLAGS})
ADD_TARGET_PROPERTIES(${EXENAME} COMPILE_FLAGS ${COMMON_CFLAGS})
TARGET_INCLUDE_DIRECTORIES(${EXENAME} PUBLIC ${COMMON_INCLUDE_DIRECTORIES})
TARGET_LINK_LIBRARIES(${EXENAME} lighttpd-${PACKAGE_VERSION}-common lighttpd-${PACKAGE_VERSION}-shared)
ADD_TEST(${TESTNAME} ${EXENAME})
ENDMACRO(ADD_TEST_BINARY)
ADD_TEST_BINARY(Chunk-UnitTest test-chunk unittests/test-chunk.c)
ADD_TEST_BINARY(HttpRequestParser-UnitTest test-http-request-parser unittests/test-http-request-parser.c)
ADD_TEST_BINARY(IpParser-UnitTest test-ip-parser unittests/test-ip-parser.c)
ADD_TEST_BINARY(Radix-UnitTest test-radix unittests/test-radix.c)
ADD_TEST_BINARY(RangeParser-UnitTest test-range-parser unittests/test-range-parser.c)
ADD_TEST_BINARY(Utils-UnitTest test-utils unittests/test-utils.c)
ENDIF(BUILD_UNIT_TESTS)

9
src/Makefile.am Normal file
View File

@ -0,0 +1,9 @@
SUBDIRS=common main modules angel unittests
EXTRA_DIST=CMakeLists.txt config.h.cmake lighttpd2.pc.in
pkgconfigdir = $(libdir)/pkgconfig
pkgconfig_DATA = lighttpd2.pc
$(pkgconfig_DATA): ../config.status

36
src/angel/Makefile.am Normal file
View File

@ -0,0 +1,36 @@
sbin_PROGRAMS=lighttpd2
lib_LTLIBRARIES=liblighttpd2-sharedangel.la
common_cflags=-I$(top_srcdir)/include -I$(top_builddir)/include
lighttpd_angel_shared_src= \
angel_log.c \
angel_plugin.c \
angel_plugin_core.c \
angel_proc.c \
angel_server.c \
angel_value.c
parsers= \
angel_config_parser.c
nodist_lighttpd_angel_shared_src=$(parsers)
BUILT_SOURCES=$(parsers)
CLEANFILES=$(parsers)
EXTRA_DIST=angel_config_parser.rl
angel_config_parser.c: angel_config_parser.rl
$(RAGEL) -C -T1 -o $@ $<
liblighttpd2_sharedangel_la_SOURCES=$(lighttpd_angel_shared_src)
nodist_liblighttpd2_sharedangel_la_SOURCES=$(nodist_lighttpd_angel_shared_src)
liblighttpd2_sharedangel_la_CPPFLAGS=$(common_cflags) $(GTHREAD_CFLAGS) $(GMODULE_CFLAGS) $(LIBEV_CFLAGS) $(LUA_CFLAGS) -DDEFAULT_LIBEXECDIR='"$(libexecdir)"'
liblighttpd2_sharedangel_la_LDFLAGS=-release $(PACKAGE_VERSION) -export-dynamic $(GTHREAD_LIBS) $(GMODULE_LIBS) $(LIBEV_LIBS)
liblighttpd2_sharedangel_la_LIBADD=../common/liblighttpd2-common.la
lighttpd2_SOURCES=angel_main.c
lighttpd2_CPPFLAGS=$(common_cflags) $(GTHREAD_CFLAGS) $(GMODULE_CFLAGS) $(LIBEV_CFLAGS) $(LUA_CFLAGS) -DDEFAULT_LIBDIR='"$(pkglibdir)"'
lighttpd2_LDFLAGS=-export-dynamic $(GTHREAD_LIBS) $(GMODULE_LIBS) $(LIBEV_LIBS) $(LUA_LIBS)
lighttpd2_LDADD=../common/liblighttpd2-common.la liblighttpd2-sharedangel.la

43
src/common/Makefile.am Normal file
View File

@ -0,0 +1,43 @@
lib_LTLIBRARIES=liblighttpd2-common.la
common_cflags=-I$(top_builddir)/include -I$(top_srcdir)/include
common_src= \
angel_connection.c \
angel_data.c \
buffer.c \
encoding.c \
events.c \
fetch.c \
idlist.c \
jobqueue.c \
memcached.c \
mempool.c \
module.c \
radix.c \
sys_memory.c \
sys_socket.c \
tasklet.c \
utils.c \
value.c \
waitqueue.c
parsers=ip_parsers.c
nodist_common_src=$(parsers)
if WITH_PROFILER
common_src+= profiler.c
endif
EXTRA_liblighttpd2_common_la_SOURCES=profiler.c
BUILT_SOURCES=$(parsers)
CLEANFILES=$(parsers)
EXTRA_DIST=ip_parsers.rl value_impl.c
ip_parsers.c: ip_parsers.rl
$(RAGEL) -C -T1 -o $@ $<
liblighttpd2_common_la_SOURCES=$(common_src)
nodist_liblighttpd2_common_la_SOURCES=$(nodist_common_src)
liblighttpd2_common_la_CPPFLAGS=$(common_cflags) $(GTHREAD_CFLAGS) $(GMODULE_CFLAGS) $(LIBEV_CFLAGS) $(LIBUNWIND_CFLAGS)
liblighttpd2_common_la_LDFLAGS=-release $(PACKAGE_VERSION) -export-dynamic $(GTHREAD_LIBS) $(GMODULE_LIBS) $(LIBEV_LIBS) $(CRYPT_LIB) $(LIBUNWIND_LIBS)

163
src/config.h.cmake Normal file
View File

@ -0,0 +1,163 @@
/*
CMake autogenerated config.h file. Do not edit!
*/
/* Package data */
#define PACKAGE_NAME "${PACKAGE_NAME}"
#define PACKAGE_VERSION "${PACKAGE_VERSION}"
/* System */
#cmakedefine HAVE_SYS_DEVPOLL_H
#cmakedefine HAVE_SYS_EPOLL_H
#cmakedefine HAVE_SYS_EVENT_H
#cmakedefine HAVE_SYS_MMAN_H
#cmakedefine HAVE_SYS_POLL_H
#cmakedefine HAVE_SYS_PORT_H
#cmakedefine HAVE_SYS_PRCTL_H
#cmakedefine HAVE_SYS_RESOURCE_H
#cmakedefine HAVE_SYS_SENDFILE_H
#cmakedefine HAVE_SYS_SELECT_H
#cmakedefine HAVE_SYS_SYSLIMITS_H
#cmakedefine HAVE_SYS_TYPES_H
#cmakedefine HAVE_SYS_UIO_H
#cmakedefine HAVE_SYS_UN_H
#cmakedefine HAVE_SYS_WAIT_H
#cmakedefine HAVE_UNISTD_H
#cmakedefine HAVE_PTHREAD_H
#cmakedefine HAVE_INET_ATON
#cmakedefine HAVE_IPV6
#cmakedefine HAVE_SOCKADDR_STORAGE
#cmakedefine HAVE_EXECINFO_H
/* XATTR */
#cmakedefine HAVE_ATTR_ATTRIBUTES_H
/* mySQL */
#cmakedefine HAVE_MYSQL_H
#cmakedefine HAVE_LIBMYSQL
/* postgresql */
#cmakedefine HAVE_LIBPQ_FE_H
#cmakedefine HAVE_LIBPQ
/* OpenSSL */
#cmakedefine HAVE_OPENSSL_SSL_H
#cmakedefine HAVE_LIBCRYPTO
#cmakedefine OPENSSL_NO_KRB5
#cmakedefine HAVE_LIBSSL
#cmakedefine HAVE_AIO_H
/* FAM */
#cmakedefine HAVE_FAM_H
/* getopt */
#cmakedefine HAVE_GETOPT_H
#cmakedefine HAVE_INTTYPES_H
/* LDAP */
#cmakedefine HAVE_LDAP_H
#cmakedefine HAVE_LIBLDAP
/* libaio */
#cmakedefine HAVE_LIBAIO_H
#cmakedefine HAVE_LIBAIO
/* XML */
#cmakedefine HAVE_LIBXML_H
#cmakedefine HAVE_LIBXML
/* PCRE */
/* We use pcre through glib */
/* #cmakedefine HAVE_PCRE_H */
/* #cmakedefine HAVE_LIBPCRE */
#cmakedefine HAVE_POLL_H
#cmakedefine HAVE_PWD_H
/* sqlite3 */
#cmakedefine HAVE_SQLITE3_H
#cmakedefine HAVE_LIBPCRE
#cmakedefine HAVE_STDDEF_H
#cmakedefine HAVE_STDINT_H
#cmakedefine HAVE_SYSLOG_H
/* UUID */
#cmakedefine HAVE_UUID_H
#cmakedefine HAVE_LIBUUID
/* BZip */
#cmakedefine HAVE_BZIP
/* ZLIB */
#cmakedefine HAVE_ZLIB
/* GLIB */
#cmakedefine HAVE_GLIB_H
#cmakedefine HAVE_GLIB
/* lua */
#cmakedefine HAVE_LUA_H
#cmakedefine HAVE_LIBLUA
/* libunwind */
#cmakedefine HAVE_LIBUNWIND
/* inotify */
#cmakedefine HAVE_INOTIFY_INIT
#cmakedefine HAVE_SYS_INOTIFY_H
/* Types */
#cmakedefine HAVE_SOCKLEN_T
#cmakedefine SIZEOF_LONG ${SIZEOF_LONG}
#cmakedefine SIZEOF_OFF_T ${SIZEOF_OFF_T}
/* Functions */
#cmakedefine HAVE_CHROOT
#cmakedefine HAVE_CRYPT_R
#cmakedefine HAVE_EPOLL_CTL
#cmakedefine HAVE_FORK
#cmakedefine HAVE_GETRLIMIT
#cmakedefine HAVE_GETUID
#cmakedefine HAVE_GMTIME_R
#cmakedefine HAVE_INET_NTOP
#cmakedefine HAVE_KQUEUE
#cmakedefine HAVE_LOCALTIME_R
#cmakedefine HAVE_LSTAT
#cmakedefine HAVE_MADVISE
#cmakedefine HAVE_MEMCPY
#cmakedefine HAVE_MEMSET
#cmakedefine HAVE_MMAP
#cmakedefine HAVE_PATHCONF
#cmakedefine HAVE_POLL
#cmakedefine HAVE_PORT_CREATE
#cmakedefine HAVE_PRCTL
#cmakedefine HAVE_PREAD
#cmakedefine HAVE_POSIX_FADVISE
#cmakedefine HAVE_SELECT
#cmakedefine HAVE_SENDFILE
#cmakedefine HAVE_SENDFILE64
#cmakedefine HAVE_SENDFILEV
#cmakedefine HAVE_SIGACTION
#cmakedefine HAVE_SIGNAL
#cmakedefine HAVE_SIGTIMEDWAIT
#cmakedefine HAVE_STRPTIME
#cmakedefine HAVE_SYSLOG
#cmakedefine HAVE_WRITEV
#cmakedefine HAVE_ACCEPT4
/* libcrypt */
#cmakedefine HAVE_LIBCRYPT
#cmakedefine HAVE_CRYPT_H
/* fastcgi */
#cmakedefine HAVE_FASTCGI_H
#cmakedefine HAVE_FASTCGI_FASTCGI_H
/* features */
#cmakedefine WITHOUT_CONFIG_PARSER
#cmakedefine LIGHTTPD_STATIC
#cmakedefine WITH_PROFILER

103
src/main/Makefile.am Normal file
View File

@ -0,0 +1,103 @@
libexec_PROGRAMS=lighttpd2-worker
lib_LTLIBRARIES=liblighttpd2-shared.la
common_cflags=-I$(top_builddir)/include -I$(top_srcdir)/include
lighttpd_shared_src= \
angel.c \
angel_fake.c \
actions.c \
base_lua.c \
backends.c \
chunk.c \
chunk_parser.c \
collect.c \
condition.c \
connection.c \
environment.c \
etag.c \
filter.c \
filter_chunked.c \
filter_buffer_on_disk.c \
http_headers.c \
lighttpd_glue.c \
log.c \
mimetype.c \
network.c \
network_write.c network_writev.c \
network_sendfile.c \
options.c \
pattern.c \
plugin.c \
request.c \
response.c \
server.c \
stat_cache.c \
stream.c \
stream_http_response.c \
stream_simple_socket.c \
throttle.c \
value.c \
virtualrequest.c \
worker.c \
\
plugin_core.c
parsers= \
config_parser.c \
http_range_parser.c \
http_request_parser.c \
http_response_parser.c \
url_parser.c
nodist_lighttpd_shared_src=$(parsers)
lua_src= \
actions_lua.c \
condition_lua.c \
config_lua.c \
value_lua.c \
\
chunk_lua.c \
core_lua.c \
environment_lua.c \
filters_lua.c \
http_headers_lua.c \
physical_lua.c \
request_lua.c \
response_lua.c \
stat_lua.c \
subrequest_lua.c \
virtualrequest_lua.c
if USE_LUA
lighttpd_shared_src+=$(lua_src)
endif
BUILT_SOURCES=$(parsers)
CLEANFILES=$(parsers)
EXTRA_DIST=config_parser.rl http_range_parser.rl http_request_parser.rl http_response_parser.rl url_parser.rl
config_parser.c: config_parser.rl
$(RAGEL) -C -T0 -o $@ $<
http_range_parser.c: http_range_parser.rl
$(RAGEL) -C -T1 -o $@ $<
http_request_parser.c: http_request_parser.rl
$(RAGEL) -C -T1 -o $@ $<
http_response_parser.c: http_response_parser.rl
$(RAGEL) -C -T1 -o $@ $<
url_parser.c: url_parser.rl
$(RAGEL) -C -T1 -o $@ $<
liblighttpd2_shared_la_SOURCES=$(lighttpd_shared_src)
nodist_liblighttpd2_shared_la_SOURCES=$(nodist_lighttpd_shared_src)
liblighttpd2_shared_la_CPPFLAGS=$(common_cflags) $(GTHREAD_CFLAGS) $(GMODULE_CFLAGS) $(LIBEV_CFLAGS) $(LUA_CFLAGS)
liblighttpd2_shared_la_LDFLAGS=-release $(PACKAGE_VERSION) -export-dynamic $(GTHREAD_LIBS) $(GMODULE_LIBS) $(LIBEV_LIBS) $(LUA_LIBS)
liblighttpd2_shared_la_LIBADD=../common/liblighttpd2-common.la
lighttpd2_worker_SOURCES=lighttpd_worker.c
lighttpd2_worker_CPPFLAGS=$(common_cflags) $(GTHREAD_CFLAGS) $(GMODULE_CFLAGS) $(LIBEV_CFLAGS) $(LUA_CFLAGS) -DDEFAULT_LIBDIR='"$(pkglibdir)"'
lighttpd2_worker_LDFLAGS=-export-dynamic $(GTHREAD_LIBS) $(GMODULE_LIBS) $(LIBEV_LIBS) $(LUA_LIBS)
lighttpd2_worker_LDADD=../common/liblighttpd2-common.la liblighttpd2-shared.la

158
src/modules/Makefile.am Normal file
View File

@ -0,0 +1,158 @@
install_libs =
common_cflags = -I$(top_srcdir)/include -I$(top_builddir)/include
common_cflags += $(GTHREAD_CFLAGS) $(LIBEV_CFLAGS) $(LUA_CFLAGS)
common_libs = $(GTHREAD_LIBS) $(LIBEV_LIBS) $(LUA_LIBS)
common_ldflags = -module -export-dynamic -avoid-version -no-undefined $(common_libs)
common_libadd = ../common/liblighttpd2-common.la ../main/liblighttpd2-shared.la
EXTRA_DIST=ssl-session-db.h ssl_client_hello_parser.h
luadir = $(datarootdir)/lighttpd2/lua
AM_CPPFLAGS = $(common_cflags)
install_libs += libmod_access.la
libmod_access_la_SOURCES = mod_access.c
libmod_access_la_LDFLAGS = $(common_ldflags)
libmod_access_la_LIBADD = $(common_libadd)
install_libs += libmod_accesslog.la
libmod_accesslog_la_SOURCES = mod_accesslog.c
libmod_accesslog_la_LDFLAGS = $(common_ldflags)
libmod_accesslog_la_LIBADD = $(common_libadd)
install_libs += libmod_auth.la
libmod_auth_la_SOURCES = mod_auth.c
libmod_auth_la_LDFLAGS = $(common_ldflags)
libmod_auth_la_LIBADD = $(common_libadd)
install_libs += libmod_balance.la
libmod_balance_la_SOURCES = mod_balance.c
libmod_balance_la_LDFLAGS = $(common_ldflags)
libmod_balance_la_LIBADD = $(common_libadd)
install_libs += libmod_cache_disk_etag.la
libmod_cache_disk_etag_la_SOURCES = mod_cache_disk_etag.c
libmod_cache_disk_etag_la_LDFLAGS = $(common_ldflags)
libmod_cache_disk_etag_la_LIBADD = $(common_libadd)
install_libs += libmod_debug.la
libmod_debug_la_SOURCES = mod_debug.c
libmod_debug_la_LDFLAGS = $(common_ldflags)
libmod_debug_la_LIBADD = $(common_libadd)
if USE_MOD_DEFLATE
install_libs += libmod_deflate.la
libmod_deflate_la_SOURCES = mod_deflate.c
libmod_deflate_la_LDFLAGS = $(common_ldflags)
libmod_deflate_la_LIBADD = $(common_libadd) $(Z_LIB) $(BZ_LIB)
endif
install_libs += libmod_dirlist.la
libmod_dirlist_la_SOURCES = mod_dirlist.c
libmod_dirlist_la_LDFLAGS = $(common_ldflags)
libmod_dirlist_la_LIBADD = $(common_libadd)
install_libs += libmod_expire.la
libmod_expire_la_SOURCES = mod_expire.c
libmod_expire_la_LDFLAGS = $(common_ldflags)
libmod_expire_la_LIBADD = $(common_libadd)
install_libs += libmod_fastcgi.la
libmod_fastcgi_la_SOURCES = mod_fastcgi.c fastcgi_stream.c
libmod_fastcgi_la_LDFLAGS = $(common_ldflags)
libmod_fastcgi_la_LIBADD = $(common_libadd)
EXTRA_DIST += fastcgi_stream.h
install_libs += libmod_flv.la
libmod_flv_la_SOURCES = mod_flv.c
libmod_flv_la_LDFLAGS = $(common_ldflags)
libmod_flv_la_LIBADD = $(common_libadd)
install_libs += libmod_fortune.la
libmod_fortune_la_SOURCES = mod_fortune.c
libmod_fortune_la_LDFLAGS = $(common_ldflags)
libmod_fortune_la_LIBADD = $(common_libadd)
if USE_GNUTLS
install_libs += libmod_gnutls.la
libmod_gnutls_la_CPPFLAGS = $(AM_CPPFLAGS) $(GNUTLS_CFLAGS) $(IDN_FLAGS)
libmod_gnutls_la_SOURCES = mod_gnutls.c gnutls_filter.c gnutls_ocsp.c
libmod_gnutls_la_LDFLAGS = $(common_ldflags)
libmod_gnutls_la_LIBADD = $(common_libadd) $(GNUTLS_LIBS) $(IDN_LIBS)
endif
EXTRA_DIST += gnutls_filter.h gnutls_ocsp.h
install_libs += libmod_limit.la
libmod_limit_la_SOURCES = mod_limit.c
libmod_limit_la_LDFLAGS = $(common_ldflags)
libmod_limit_la_LIBADD = $(common_libadd)
if USE_LUA
install_libs += libmod_lua.la
libmod_lua_la_CPPFLAGS = $(AM_CPPFLAGS) -DDEFAULT_LUADIR='"$(luadir)"'
libmod_lua_la_SOURCES = mod_lua.c
libmod_lua_la_LDFLAGS = $(common_ldflags)
libmod_lua_la_LIBADD = $(common_libadd)
endif
install_libs += libmod_memcached.la
libmod_memcached_la_SOURCES = mod_memcached.c
libmod_memcached_la_LDFLAGS = $(common_ldflags)
libmod_memcached_la_LIBADD = $(common_libadd)
if USE_OPENSSL
install_libs += libmod_openssl.la
libmod_openssl_la_CPPFLAGS = $(AM_CPPFLAGS) $(OPENSSL_CFLAGS) $(IDN_FLAGS)
libmod_openssl_la_SOURCES = mod_openssl.c openssl_filter.c
libmod_openssl_la_LDFLAGS = $(common_ldflags)
libmod_openssl_la_LIBADD = $(common_libadd) $(OPENSSL_LIBS) $(IDN_LIBS)
endif
EXTRA_DIST += openssl_filter.h
install_libs += libmod_progress.la
libmod_progress_la_SOURCES = mod_progress.c
libmod_progress_la_LDFLAGS = $(common_ldflags)
libmod_progress_la_LIBADD = $(common_libadd)
install_libs += libmod_proxy.la
libmod_proxy_la_SOURCES = mod_proxy.c
libmod_proxy_la_LDFLAGS = $(common_ldflags)
libmod_proxy_la_LIBADD = $(common_libadd)
install_libs += libmod_redirect.la
libmod_redirect_la_SOURCES = mod_redirect.c
libmod_redirect_la_LDFLAGS = $(common_ldflags)
libmod_redirect_la_LIBADD = $(common_libadd)
install_libs += libmod_rewrite.la
libmod_rewrite_la_SOURCES = mod_rewrite.c
libmod_rewrite_la_LDFLAGS = $(common_ldflags)
libmod_rewrite_la_LIBADD = $(common_libadd)
install_libs += libmod_scgi.la
libmod_scgi_la_SOURCES = mod_scgi.c
libmod_scgi_la_LDFLAGS = $(common_ldflags)
libmod_scgi_la_LIBADD = $(common_libadd)
install_libs += libmod_status.la
libmod_status_la_SOURCES = mod_status.c
libmod_status_la_LDFLAGS = $(common_ldflags)
libmod_status_la_LIBADD = $(common_libadd)
install_libs += libmod_throttle.la
libmod_throttle_la_SOURCES = mod_throttle.c
libmod_throttle_la_LDFLAGS = $(common_ldflags)
libmod_throttle_la_LIBADD = $(common_libadd)
install_libs += libmod_userdir.la
libmod_userdir_la_SOURCES = mod_userdir.c
libmod_userdir_la_LDFLAGS = $(common_ldflags)
libmod_userdir_la_LIBADD = $(common_libadd)
install_libs += libmod_vhost.la
libmod_vhost_la_SOURCES = mod_vhost.c
libmod_vhost_la_LDFLAGS = $(common_ldflags)
libmod_vhost_la_LIBADD = $(common_libadd)
pkglib_LTLIBRARIES=$(install_libs)

View File

@ -15,20 +15,19 @@
#include <openssl/err.h> #include <openssl/err.h>
#include <openssl/rand.h> #include <openssl/rand.h>
#ifndef OPENSSL_NO_DH # ifndef OPENSSL_NO_DH
# include <openssl/dh.h> # include <openssl/dh.h>
#endif # define USE_OPENSSL_DH
static DH* load_dh_params_4096(void);
# endif
#ifndef OPENSSL_NO_ECDH #if OPENSSL_VERSION_NUMBER >= 0x0090800fL
# ifndef OPENSSL_NO_ECDH
# include <openssl/ecdh.h> # include <openssl/ecdh.h>
# define USE_OPENSSL_ECDH
# endif
#endif #endif
#if OPENSSL_VERSION_NUMBER >= 0x30000000L
# include <openssl/store.h>
#endif
static gboolean init_dh_params(liServer *srv, SSL_CTX *ssl_ctx, const char* dh_params_file);
static gboolean init_ecdh_curve(liServer *srv, SSL_CTX *ssl_ctx, const char *ecdh_curve);
LI_API gboolean mod_openssl_init(liModules *mods, liModule *mod); LI_API gboolean mod_openssl_init(liModules *mods, liModule *mod);
LI_API gboolean mod_openssl_free(liModules *mods, liModule *mod); LI_API gboolean mod_openssl_free(liModules *mods, liModule *mod);
@ -506,7 +505,9 @@ static gboolean openssl_setup(liServer *srv, liPlugin* p, liValue *val, gpointer
openssl_context *ctx; openssl_context *ctx;
STACK_OF(X509_NAME) *client_ca_list; STACK_OF(X509_NAME) *client_ca_list;
const char *default_ciphers = "HIGH !aNULL !3DES +kEDH +kRSA !kSRP !kPSK"; const char
*default_ciphers = "HIGH !aNULL !3DES +kEDH +kRSA !kSRP !kPSK",
*default_ecdh_curve = "prime256v1";
/* setup defaults */ /* setup defaults */
gboolean gboolean
@ -523,7 +524,7 @@ static gboolean openssl_setup(liServer *srv, liPlugin* p, liValue *val, gpointer
#ifdef SSL_OP_NO_COMPRESSION #ifdef SSL_OP_NO_COMPRESSION
| SSL_OP_NO_COMPRESSION | SSL_OP_NO_COMPRESSION
#endif #endif
#if !defined(OPENSSL_NO_ECDH) #ifdef USE_OPENSSL_ECDH
| SSL_OP_SINGLE_ECDH_USE | SSL_OP_SINGLE_ECDH_USE
#endif #endif
; ;
@ -589,6 +590,9 @@ static gboolean openssl_setup(liServer *srv, liPlugin* p, liValue *val, gpointer
} }
ciphers = entryValue->data.string->str; ciphers = entryValue->data.string->str;
} else if (g_str_equal(entryKeyStr->str, "dh-params")) { } else if (g_str_equal(entryKeyStr->str, "dh-params")) {
#ifndef USE_OPENSSL_DH
WARNING(srv, "%s", "the openssl library in use doesn't support DH => dh-params has no effect");
#endif
if (LI_VALUE_STRING != li_value_type(entryValue)) { if (LI_VALUE_STRING != li_value_type(entryValue)) {
ERROR(srv, "%s", "openssl dh-params expects a string as parameter"); ERROR(srv, "%s", "openssl dh-params expects a string as parameter");
return FALSE; return FALSE;
@ -599,6 +603,9 @@ static gboolean openssl_setup(liServer *srv, liPlugin* p, liValue *val, gpointer
} }
dh_params_file = entryValue->data.string->str; dh_params_file = entryValue->data.string->str;
} else if (g_str_equal(entryKeyStr->str, "ecdh-curve")) { } else if (g_str_equal(entryKeyStr->str, "ecdh-curve")) {
#ifndef USE_OPENSSL_ECDH
WARNING(srv, "%s", "the openssl library in use doesn't support ECDH => ecdh-curve has no effect");
#endif
if (LI_VALUE_STRING != li_value_type(entryValue)) { if (LI_VALUE_STRING != li_value_type(entryValue)) {
ERROR(srv, "%s", "openssl ecdh-curve expects a string as parameter"); ERROR(srv, "%s", "openssl ecdh-curve expects a string as parameter");
return FALSE; return FALSE;
@ -721,13 +728,60 @@ static gboolean openssl_setup(liServer *srv, liPlugin* p, liValue *val, gpointer
goto error_free_socket; goto error_free_socket;
} }
if (!init_dh_params(srv, ctx->ssl_ctx, dh_params_file)) { #ifdef USE_OPENSSL_DH
{
DH *dh;
BIO *bio;
/* Support for Diffie-Hellman key exchange */
if (NULL != dh_params_file) {
/* DH parameters from file */
bio = BIO_new_file(dh_params_file, "r");
if (bio == NULL) {
ERROR(srv,"SSL: BIO_new_file('%s'): unable to open file", dh_params_file);
goto error_free_socket;
}
dh = PEM_read_bio_DHparams(bio, NULL, NULL, NULL);
BIO_free(bio);
if (NULL == dh) {
ERROR(srv, "SSL: PEM_read_bio_DHparams failed (for file '%s')", dh_params_file);
goto error_free_socket;
}
} else {
dh = load_dh_params_4096();
if (NULL == dh) {
ERROR(srv, "%s", "SSL: loading default DH parameters failed");
goto error_free_socket;
}
}
SSL_CTX_set_tmp_dh(ctx->ssl_ctx, dh);
DH_free(dh);
}
#endif
#ifdef USE_OPENSSL_ECDH
{
EC_KEY *ecdh;
int ecdh_nid;
if (NULL == ecdh_curve) ecdh_curve = default_ecdh_curve;
ecdh_nid = OBJ_sn2nid(ecdh_curve);
if (NID_undef == ecdh_nid) {
ERROR(srv, "SSL: Unknown curve name '%s'", ecdh_curve);
goto error_free_socket; goto error_free_socket;
} }
if (!init_ecdh_curve(srv, ctx->ssl_ctx, ecdh_curve)) { ecdh = EC_KEY_new_by_curve_name(ecdh_nid);
if (NULL == ecdh) {
ERROR(srv, "SSL: Unable to create curve '%s'", ecdh_curve);
goto error_free_socket; goto error_free_socket;
} }
SSL_CTX_set_tmp_ecdh(ctx->ssl_ctx, ecdh);
EC_KEY_free(ecdh);
}
#else
UNUSED(default_ecdh_curve);
#endif
if (NULL != ca_file) { if (NULL != ca_file) {
if (1 != SSL_CTX_load_verify_locations(ctx->ssl_ctx, ca_file, NULL)) { if (1 != SSL_CTX_load_verify_locations(ctx->ssl_ctx, ca_file, NULL)) {
@ -828,9 +882,61 @@ static void plugin_init(liServer *srv, liPlugin *p, gpointer userdata) {
p->setups = setups; p->setups = setups;
} }
#if OPENSSL_VERSION_NUMBER < 0x10100000L || defined(LIBRESSL_VERSION_NUMBER)
static GMutex** ssl_locks;
static void ssl_lock_cb(int mode, int n, const char *file, int line) {
UNUSED(file);
UNUSED(line);
if (mode & CRYPTO_LOCK) {
g_mutex_lock(ssl_locks[n]);
} else if (mode & CRYPTO_UNLOCK) {
g_mutex_unlock(ssl_locks[n]);
}
}
static unsigned long ssl_id_cb(void) {
return (intptr_t) g_thread_self();
}
static void sslthread_init(void) {
int n = CRYPTO_num_locks(), i;
ssl_locks = g_slice_alloc0(sizeof(GMutex*) * n);
for (i = 0; i < n; i++) {
ssl_locks[i] = g_mutex_new();
}
CRYPTO_set_locking_callback(ssl_lock_cb);
CRYPTO_set_id_callback(ssl_id_cb);
}
static void sslthread_free(void) {
int n = CRYPTO_num_locks(), i;
for (i = 0; i < n; i++) {
g_mutex_free(ssl_locks[i]);
}
g_slice_free1(sizeof(GMutex*) * n, ssl_locks);
}
#else
static void sslthread_init(void) {
}
static void sslthread_free(void) {
}
#endif
gboolean mod_openssl_init(liModules *mods, liModule *mod) { gboolean mod_openssl_init(liModules *mods, liModule *mod) {
MODULE_VERSION_CHECK(mods); MODULE_VERSION_CHECK(mods);
sslthread_init();
SSL_load_error_strings(); SSL_load_error_strings();
SSL_library_init(); SSL_library_init();
OpenSSL_add_all_algorithms(); OpenSSL_add_all_algorithms();
@ -851,104 +957,12 @@ gboolean mod_openssl_free(liModules *mods, liModule *mod) {
ERR_free_strings(); ERR_free_strings();
sslthread_free();
return TRUE; return TRUE;
} }
#if !defined(OPENSSL_NO_DH) #ifdef USE_OPENSSL_DH
#if OPENSSL_VERSION_NUMBER >= 0x30000000L
static gboolean init_dh_params(liServer *srv, SSL_CTX *ssl_ctx, const char* dh_params_file) {
OSSL_STORE_CTX *store_ctx = NULL;
EVP_PKEY *dh_pkey = NULL;
BIO *dh_file_bio = NULL;
gboolean res = TRUE;
if (!dh_params_file) {
SSL_CTX_set_dh_auto(ssl_ctx, 1);
return TRUE;
}
/* not using `OSSL_STORE_open`, as it expects a URI, and filenames should
* use the file: scheme, but that doesn't support relative paths (yet).
* It only interprets the URI as a (possibly relative) path if it doesn't
* detect a scheme, but the error message for not existing files is too cryptic.
*/
dh_file_bio = BIO_new_file(dh_params_file, "r");
if (dh_file_bio == NULL) {
ERROR(
srv,
"Error opening DH parameters from '%s': %s",
dh_params_file,
ERR_error_string(ERR_get_error(), NULL)
);
return FALSE;
}
store_ctx = OSSL_STORE_attach(
/* bio */ dh_file_bio, /* scheme */ "file",
/* libctx */ NULL, /* propq */ NULL,
/* ui_method */ NULL, /* ui_data */ NULL,
/* params */ NULL,
/* post_process */ NULL, /* post_process_data */ NULL
);
BIO_free(dh_file_bio);
if (!store_ctx || !OSSL_STORE_expect(store_ctx, OSSL_STORE_INFO_PARAMS)) {
ERROR(
srv,
"Error while loading DH parameters from '%s': %s",
dh_params_file,
ERR_error_string(ERR_get_error(), NULL)
);
OSSL_STORE_close(store_ctx);
return FALSE;
}
for (;;) {
OSSL_STORE_INFO *store_info = OSSL_STORE_load(store_ctx);
if (store_info == NULL) {
if (OSSL_STORE_eof(store_ctx)) {
ERROR(srv, "No DH parameters found in '%s'", dh_params_file);
OSSL_STORE_close(store_ctx);
return FALSE;
}
WARNING(
srv,
"Error while trying to find DH parameters from '%s': %s",
dh_params_file,
ERR_error_string(ERR_get_error(), NULL)
);
continue;
}
dh_pkey = OSSL_STORE_INFO_get1_PARAMS(store_info);
if (!EVP_PKEY_is_a(dh_pkey, "DH")) {
EVP_PKEY_free(dh_pkey);
OSSL_STORE_INFO_free(store_info);
continue; /* skip non-DH entries */
}
if (!SSL_CTX_set0_tmp_dh_pkey(ssl_ctx, dh_pkey)) {
WARNING(
srv,
"Failed to set DH parameters from '%s': %s",
dh_params_file,
ERR_error_string(ERR_get_error(), NULL)
);
EVP_PKEY_free(dh_pkey); /* ownership passed only on success */
res = FALSE;
}
OSSL_STORE_INFO_free(store_info);
OSSL_STORE_close(store_ctx);
return res;
}
}
#else /* not openssl >= 3.0 */
static DH* load_dh_params_4096(void) { static DH* load_dh_params_4096(void) {
static const unsigned char dh4096_p[]={ static const unsigned char dh4096_p[]={
0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xC9,0x0F,0xDA,0xA2, 0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xC9,0x0F,0xDA,0xA2,
@ -1015,111 +1029,13 @@ static DH* load_dh_params_4096(void) {
return NULL; return NULL;
} }
#if OPENSSL_VERSION_NUMBER < 0x10100000L || defined(LIBRESSL_VERSION_NUMBER)
dh->p = dh_p;
dh->g = dh_g;
#else
DH_set0_pqg(dh, dh_p, NULL, dh_g); DH_set0_pqg(dh, dh_p, NULL, dh_g);
#endif
return dh; return dh;
} }
#endif
static gboolean init_dh_params(liServer *srv, SSL_CTX *ssl_ctx, const char* dh_params_file) {
DH *dh;
BIO *bio;
/* Support for Diffie-Hellman key exchange */
if (NULL != dh_params_file) {
/* DH parameters from file */
bio = BIO_new_file(dh_params_file, "r");
if (bio == NULL) {
ERROR(srv,"SSL: BIO_new_file('%s'): unable to open file", dh_params_file);
return FALSE;
}
dh = PEM_read_bio_DHparams(bio, NULL, NULL, NULL);
BIO_free(bio);
if (NULL == dh) {
ERROR(srv, "SSL: PEM_read_bio_DHparams failed (for file '%s')", dh_params_file);
return FALSE;
}
} else {
dh = load_dh_params_4096();
if (NULL == dh) {
ERROR(srv, "%s", "SSL: loading default DH parameters failed");
return FALSE;
}
}
SSL_CTX_set_tmp_dh(ssl_ctx, dh);
DH_free(dh);
return TRUE;
}
#endif /* (not) openssl >= 3.0 */
#else /* (not) !defined(OPENSSL_NO_DH) */
static gboolean init_dh_params(liServer *srv, SSL_CTX *ssl_ctx, const char *dh_params_file) {
UNUSED(ssl_ctx);
if (dh_params_file) {
WARNING(srv, "%s", "the openssl library in use doesn't support DH => dh-params has no effect");
}
return TRUE;
}
#endif /* (not) !defined(OPENSSL_NO_DH) */
#if !defined(OPENSSL_NO_ECDH)
#define DEFAULT_ECDH_CURVE "prime256v1"
static gboolean init_ecdh_curve(liServer *srv, SSL_CTX *ssl_ctx, const char *ecdh_curve) {
int ecdh_nid;
if (NULL == ecdh_curve) ecdh_curve = DEFAULT_ECDH_CURVE;
ecdh_nid = OBJ_sn2nid(ecdh_curve);
if (NID_undef == ecdh_nid) {
ERROR(srv, "SSL: Unknown curve name '%s'", ecdh_curve);
return FALSE;
}
#if OPENSSL_VERSION_NUMBER >= 0x30000000L
if (!SSL_CTX_set1_groups(ssl_ctx, &ecdh_nid, 1)) {
ERROR(
srv,
"SSL_CTX_set1_groups failed to set curve '%s': %s",
ecdh_curve,
ERR_error_string(ERR_get_error(), NULL)
);
return FALSE;
}
#else /* (not) openssl >= 3.0 */
{
ecdh = EC_KEY_new_by_curve_name(ecdh_nid);
if (NULL == ecdh) {
ERROR(srv, "SSL: Unable to create curve '%s'", ecdh_curve);
return FALSE;
}
SSL_CTX_set_tmp_ecdh(ssl_ctx, ecdh);
EC_KEY_free(ecdh);
}
#endif /* (not) openssl >= 3.0 */
return TRUE;
}
#else /* (not) !defined(OPENSSL_NO_ECDH) */
static gboolean init_ecdh_curve(liServer *srv, SSL_CTX *ssl_ctx, const char *ecdh_curve) {
UNUSED(ssl_ctx);
if (ecdh_curve) {
WARNING(srv, "%s", "the openssl library in use doesn't support ECDH => ecdh-curve has no effect");
}
return TRUE;
}
#endif /* (not) !defined(OPENSSL_NO_ECDH) */

View File

@ -32,6 +32,111 @@ struct liOpenSSLFilter {
#define BIO_TYPE_LI_STREAM (127|BIO_TYPE_SOURCE_SINK) #define BIO_TYPE_LI_STREAM (127|BIO_TYPE_SOURCE_SINK)
#if OPENSSL_VERSION_NUMBER < 0x10100000L || defined(LIBRESSL_VERSION_NUMBER)
static int stream_bio_write(BIO *bio, const char *buf, int len) {
liOpenSSLFilter *f = bio->ptr;
liChunkQueue *cq;
errno = ECONNRESET;
if (NULL == f || NULL == f->crypt_source.out) return -1;
cq = f->crypt_source.out;
if (cq->is_closed) return -1;
li_chunkqueue_append_mem(cq, buf, len);
li_stream_notify_later(&f->crypt_source);
errno = 0;
return len;
}
static int stream_bio_read(BIO *bio, char *buf, int len) {
liOpenSSLFilter *f = bio->ptr;
liChunkQueue *cq;
errno = ECONNRESET;
BIO_clear_retry_flags(bio);
if (NULL == f || NULL == f->crypt_drain.out) return -1;
cq = f->crypt_drain.out;
if (0 == cq->length) {
if (cq->is_closed) {
errno = 0;
return 0;
} else {
errno = EAGAIN;
BIO_set_retry_read(bio);
return -1;
}
}
if (len > cq->length) len = cq->length;
if (!li_chunkqueue_extract_to_memory(cq, len, buf, NULL)) return -1;
li_chunkqueue_skip(cq, len);
errno = 0;
return len;
}
static int stream_bio_puts(BIO *bio, const char *str) {
return stream_bio_write(bio, str, strlen(str));
}
static int stream_bio_gets(BIO *bio, char *str, int len) {
UNUSED(bio); UNUSED(str); UNUSED(len);
return -1;
}
static long stream_bio_ctrl(BIO *bio, int cmd, long num, void *ptr) {
liOpenSSLFilter *f = bio->ptr;
UNUSED(num); UNUSED(ptr);
switch (cmd) {
case BIO_CTRL_FLUSH:
return 1;
case BIO_CTRL_PENDING:
if (NULL == f || NULL == f->crypt_drain.out) return 0;
return f->crypt_drain.out->length;
default:
return 0;
}
}
static int stream_bio_create(BIO *bio) {
bio->ptr = NULL;
bio->init = 1;
bio->shutdown = 1;
bio->num = 0;
bio->flags = 0;
return 1;
}
static int stream_bio_destroy(BIO *bio) {
liOpenSSLFilter *f = bio->ptr;
bio->ptr = NULL;
if (NULL != f) f->bio = NULL;
bio->init = 0;
return 1;
}
static BIO_METHOD chunkqueue_bio_method = {
BIO_TYPE_LI_STREAM,
"lighttpd stream glue",
stream_bio_write,
stream_bio_read,
stream_bio_puts,
stream_bio_gets,
stream_bio_ctrl,
stream_bio_create,
stream_bio_destroy,
NULL
};
static BIO* new_cq_bio(liOpenSSLFilter *f) {
BIO *bio = BIO_new(&chunkqueue_bio_method);
bio->ptr = f;
return bio;
}
#else
static int stream_bio_write(BIO *bio, const char *buf, int len) { static int stream_bio_write(BIO *bio, const char *buf, int len) {
liOpenSSLFilter *f = BIO_get_data(bio); liOpenSSLFilter *f = BIO_get_data(bio);
liChunkQueue *cq; liChunkQueue *cq;
@ -143,6 +248,8 @@ static BIO* new_cq_bio(liOpenSSLFilter *f) {
return bio; return bio;
} }
#endif
static void f_close_ssl(liOpenSSLFilter *f) { static void f_close_ssl(liOpenSSLFilter *f) {
if (NULL != f->ssl && !f->closing) { if (NULL != f->ssl && !f->closing) {
SSL *ssl; SSL *ssl;
@ -281,6 +388,11 @@ static gboolean do_ssl_handshake(liOpenSSLFilter *f, gboolean writing) {
int r = SSL_do_handshake(f->ssl); int r = SSL_do_handshake(f->ssl);
if (1 == r) { if (1 == r) {
f->initial_handshaked_finished = 1; f->initial_handshaked_finished = 1;
#if OPENSSL_VERSION_NUMBER < 0x10100000L || defined(LIBRESSL_VERSION_NUMBER)
f->ssl->s3->flags |= SSL3_FLAGS_NO_RENEGOTIATE_CIPHERS;
#else
/* hopefully openssl_info_callback catches this... */
#endif
li_stream_acquire(&f->plain_source); li_stream_acquire(&f->plain_source);
li_stream_acquire(&f->plain_drain); li_stream_acquire(&f->plain_drain);
f->callbacks->handshake_cb(f, f->callback_data, &f->plain_source, &f->plain_drain); f->callbacks->handshake_cb(f, f->callback_data, &f->plain_source, &f->plain_drain);

14
src/unittests/Makefile.am Normal file
View File

@ -0,0 +1,14 @@
include $(top_srcdir)/build-helpers/glib-tap.mk
AM_CFLAGS = -I$(top_builddir)/include -I$(top_srcdir)/include
AM_CFLAGS += $(GTHREAD_CFLAGS) $(GMODULE_CFLAGS) $(LIBEV_CFLAGS) $(LUA_CFLAGS)
AM_LDFLAGS = -export-dynamic -avoid-version -no-undefined $(GTHREAD_LIBS) $(GMODULE_LIBS) $(LIBEV_LIBS) $(LUA_LIBS)
LDADD = ../common/liblighttpd2-common.la ../main/liblighttpd2-shared.la
test_programs=\
test-chunk \
test-http-request-parser \
test-ip-parser \
test-range-parser \
test-utils \
test-radix

4
tests/CMakeLists.txt Normal file
View File

@ -0,0 +1,4 @@
cmake_policy(VERSION 2.6.4)
add_test(NAME http COMMAND ${CMAKE_CURRENT_SOURCE_DIR}/runtests.py --angel $<TARGET_FILE:lighttpd2> --worker $<TARGET_FILE:lighttpd2-worker> --plugindir $<TARGET_FILE_DIR:lighttpd2>)

5
tests/Makefile.am Normal file
View File

@ -0,0 +1,5 @@
EXTRA_DIST=CMakeLists.txt CONTRIBUTE.md $(wildcard $(srcdir)/*.py) autowrapper.sh ca pylt
TESTS_ENVIRONMENT=$(srcdir)/autowrapper.sh $(srcdir) $(top_builddir)
TESTS=runtests.py