Merge branch 'master' of ssh://git.privoxy.org:23/git/privoxy
authorLee <ler762@users.sourceforge.net>
Mon, 23 Nov 2020 00:15:30 +0000 (19:15 -0500)
committerLee <ler762@users.sourceforge.net>
Mon, 23 Nov 2020 00:15:30 +0000 (19:15 -0500)
42 files changed:
AUTHORS
GNUmakefile.in
README
TODO
cgi.c
cgiedit.c
cgisimple.c
config
configure.in
default.action.master
doc/source/faq.sgml
doc/source/license.sgml
doc/source/p-authors.sgml
doc/source/p-config.sgml
doc/source/user-manual.sgml
doc/webserver/faq/configuration.html
doc/webserver/faq/copyright.html
doc/webserver/faq/general.html
doc/webserver/faq/index.html
doc/webserver/user-manual/actions-file.html
doc/webserver/user-manual/appendix.html
doc/webserver/user-manual/config.html
doc/webserver/user-manual/configuration.html
doc/webserver/user-manual/copyright.html
doc/webserver/user-manual/index.html
filters.c
gateway.c
jcc.c
loadcfg.c
miscutil.c
miscutil.h
openssl.c
parsers.c
parsers.h
pcrs.c
pcrs.h
project.h
ssl.c
ssl_common.c
templates/show-status
tools/privoxy-log-parser.pl
urlmatch.c

diff --git a/AUTHORS b/AUTHORS
index f42b0b7..cc4c11c 100644 (file)
--- a/AUTHORS
+++ b/AUTHORS
@@ -88,6 +88,7 @@ include (in alphabetical order):
  Magnus Holmgren
  Eric M. Hopper
  Ralf Horstmann
+ Ho+ Ho+ Ho+
  Nedžad Hrnjica
  Stefan Huehner
  Basil Hussain
@@ -161,6 +162,7 @@ include (in alphabetical order):
  Jörg Weinmann
  Darren Wiebe
  Anduin Withers
+ withoutname
  Eduard Wulff
  Yang Xia
  Jarry Xu
@@ -176,9 +178,8 @@ Privoxy heavily relies on Philip Hazel's PCRE.
 The code to filter compressed content makes use of zlib which is written by
 Jean-loup Gailly and Mark Adler.
 
-On systems that lack snprintf(), Privoxy is using a version written by Mark
-Martinec. On systems that lack strptime(), Privoxy is using the one from the
-GNU C Library written by Ulrich Drepper.
+On systems that lack strptime(), Privoxy is using the one from the GNU C
+Library written by Ulrich Drepper.
 
 If we've missed you off this list, please let us know!
 
index b9bdb90..50b10e1 100644 (file)
@@ -42,7 +42,7 @@ CODE_STATUS   = @CODE_STATUS@
 VERSION       = $(VERSION_MAJOR).$(VERSION_MINOR).$(VERSION_POINT)
 SNAPVERSION   = $(VERSION)-$(shell date "+%Y%m%d")
 
-SOURCE_DATE_EPOCH = @SOURCE_DATE_EPOCH@
+SOURCE_DATE_EPOCH ?= @SOURCE_DATE_EPOCH@
 MTREE_SPEC_FILE = privoxy-$(VERSION)-$(CODE_STATUS).spec
 
 #############################################################################
@@ -743,7 +743,9 @@ ssplit.@OBJEXT@:    ssplit.c    ssplit.h    config.h miscutil.h
 urlmatch.@OBJEXT@:  urlmatch.c  urlmatch.h  config.h $(PROJECT_H_DEPS) errlog.h miscutil.h ssplit.h
 client-tags.@OBJEXT@: client-tags.c client-tags.h config.h $(PROJECT_H_DEPS) errlog.h miscutil.h ssplit.h
 fuzz.@OBJEXT@: fuzz.c config.h $(PROJECT_H_DEPS) errlog.h miscutil.h ssplit.h
-ssl.@OBJEXT@: ssl.c ssl.h config.h $(PROJECT_H_DEPS) encode.h errlog.h jcc.h miscutil.h
+ssl.@OBJEXT@: ssl.c ssl.h ssl_common.h config.h $(PROJECT_H_DEPS) encode.h errlog.h jcc.h miscutil.h
+openssl.@OBJEXT@: openssl.c ssl.h ssl_common.h config.h $(PROJECT_H_DEPS) encode.h errlog.h jcc.h miscutil.h
+ssl_common.@OBJEXT@: ssl_common.c ssl.h ssl_common.h config.h $(PROJECT_H_DEPS) errlog.h miscutil.h
 
 # GNU regex
 gnu_regex.@OBJEXT@: gnu_regex.c gnu_regex.h config.h
diff --git a/README b/README
index d642c69..07db031 100644 (file)
--- a/README
+++ b/README
@@ -4,7 +4,7 @@
  *
  * Purpose     :  README file to give a short intro.
  *
- * Copyright   :  Written by and Copyright (C) 2001-2018 the
+ * Copyright   :  Written by and Copyright (C) 2001-2020 the
  *                Privoxy team. https://www.privoxy.org/
  *
  *                Based on the Internet Junkbuster originally written
diff --git a/TODO b/TODO
index 8344252..d258cf5 100644 (file)
--- a/TODO
+++ b/TODO
@@ -292,8 +292,6 @@ https://www.privoxy.org/faq/general.html#DONATE
 118) There should be "escaped" dynamic variables that are guaranteed
      not to break filters.
 
-119) Evaluate using pcre's jit mode.
-
 120) Add an option to limit pcre's recursion limit below the default.
      On some platforms the recursion limit doesn't prevent pcre from
      running out of stack space, causing the kernel to kill Privoxy
@@ -423,6 +421,19 @@ https://www.privoxy.org/faq/general.html#DONATE
      memory footprint a bit which may be noticeable in case of multi-user setups
      with hundreds of idle connections.
 
+161) Properly support requests with chunked transfer-encoding with https inspection.
+
+162) When https inspecting, delete generated keys and certificates if
+     the connection to the destination could not be established.
+     Makes silly DoS attacks slightly more complicated.
+
+163) Use subdirectories in the certificate-directory to lower the number
+     of files per directory.
+
+164) Evaluate switching from pcreposix(3) to pcre's native api
+     for URL matching which allows to compile the patterns once
+     at load-time.
+
 ##########################################################################
 
 Hosting wish list (relevant for #53)
diff --git a/cgi.c b/cgi.c
index 0241ebf..7518219 100644 (file)
--- a/cgi.c
+++ b/cgi.c
@@ -106,7 +106,7 @@ static const struct cgi_dispatcher cgi_dispatchers[] = {
     */
    { "client-tags",
          cgi_show_client_tags,
-         "View or toggle the tags that can be set based on the clients address",
+         "View or toggle the tags that can be set based on the client&#39;s address",
          TRUE },
 #endif
    { "show-request",
index a9e4b0e..64c8dc1 100644 (file)
--- a/cgiedit.c
+++ b/cgiedit.c
@@ -2940,6 +2940,51 @@ jb_err cgi_edit_actions_for_url(struct client_state *csp,
 }
 
 
+/*********************************************************************
+ *
+ * Function    :  get_number_of_filters
+ *
+ * Description :  Counts the number of filter available.
+ *
+ * Parameters  :
+ *          1  :  csp = Current client state (buffers, headers, etc...)
+ *
+ * Returns     :  Number of filters available.
+ *
+ *********************************************************************/
+static int get_number_of_filters(const struct client_state *csp)
+{
+   int i;
+   struct re_filterfile_spec *b;
+   struct file_list *fl;
+   int number_of_filters = 0;
+
+   for (i = 0; i < MAX_AF_FILES; i++)
+   {
+     fl = csp->rlist[i];
+     if ((NULL == fl) || (NULL == fl->f))
+     {
+        /*
+         * Either there are no filter files left or this
+         * filter file just contains no valid filters.
+         *
+         * Continue to be sure we don't miss valid filter
+         * files that are chained after empty or invalid ones.
+         */
+        continue;
+     }
+
+     for (b = fl->f; b != NULL; b = b->next)
+     {
+        number_of_filters++;
+     }
+   }
+
+   return number_of_filters;
+
+}
+
+
 /*********************************************************************
  *
  * Function    :  cgi_edit_actions_submit
@@ -2978,6 +3023,7 @@ jb_err cgi_edit_actions_submit(struct client_state *csp,
    const char * action_set_name;
    struct file_list * fl;
    struct url_actions * b;
+   int number_of_filters;
 
    if (0 == (csp->config->feature_flags & RUNTIME_FEATURE_CGI_EDIT_ACTIONS))
    {
@@ -3066,7 +3112,9 @@ jb_err cgi_edit_actions_submit(struct client_state *csp,
       }
    }
 
-   for (filter_identifier = 0; !err; filter_identifier++)
+   number_of_filters = get_number_of_filters(csp);
+
+   for (filter_identifier = 0; filter_identifier < number_of_filters && !err; filter_identifier++)
    {
       char key_value[30];
       char key_name[30];
@@ -3095,8 +3143,8 @@ jb_err cgi_edit_actions_submit(struct client_state *csp,
 
       if (name == NULL)
       {
-         /* End of list */
-         break;
+         /* The filter identifier isn't present. Try the next one. */
+         continue;
       }
 
       type = get_char_param(parameters, key_type);
index 4339ecd..cdb959a 100644 (file)
@@ -404,6 +404,7 @@ jb_err cgi_show_client_tags(struct client_state *csp,
       snprintf(buf, sizeof(buf), "%u", csp->config->client_tag_lifetime);
       if (map(exports, "refresh-delay", 1, buf, 1))
       {
+         freez(client_tag_status);
          free_map(exports);
          return JB_ERR_MEMORY;
       }
@@ -413,6 +414,7 @@ jb_err cgi_show_client_tags(struct client_state *csp,
       err = map_block_killer(exports, "tags-expire");
       if (err != JB_ERR_OK)
       {
+         freez(client_tag_status);
          return err;
       }
    }
@@ -1280,26 +1282,28 @@ jb_err cgi_show_status(struct client_state *csp,
 #endif /* ndef FEATURE_STATISTICS */
 
 #ifdef FEATURE_EXTENDED_STATISTICS
+   if (!err)
    {
       char *block_reason_statistics = get_block_reason_statistics_table(csp);
       if (block_reason_statistics != NULL)
       {
-         if (!err) err = map(exports, "block-reason-statistics", 1, block_reason_statistics, 0);
+         err = map(exports, "block-reason-statistics", 1, block_reason_statistics, 0);
       }
       else
       {
-         if (!err) err = map_block_killer(exports, "extended-statistics");
+         err = map_block_killer(exports, "extended-statistics");
       }
    }
+   if (!err)
    {
       char *filter_statistics = get_filter_statistics_table(csp);
       if (filter_statistics != NULL)
       {
-         if (!err) err = map(exports, "filter-statistics", 1, filter_statistics, 0);
+         err = map(exports, "filter-statistics", 1, filter_statistics, 0);
       }
       else
       {
-         if (!err) err = map_block_killer(exports, "extended-statistics");
+         err = map_block_killer(exports, "extended-statistics");
       }
    }
 #else /* ndef FEATURE_EXTENDED_STATISTICS */
@@ -1346,9 +1350,9 @@ jb_err cgi_show_status(struct client_state *csp,
          if (!err) err = string_append(&s, "</td></tr>\n");
       }
    }
-   if (*s != '\0')
+   if (!err && *s != '\0')
    {
-      if (!err) err = map(exports, "actions-filenames", 1, s, 0);
+      err = map(exports, "actions-filenames", 1, s, 0);
    }
    else
    {
@@ -1373,9 +1377,9 @@ jb_err cgi_show_status(struct client_state *csp,
          if (!err) err = string_append(&s, "</td></tr>\n");
       }
    }
-   if (*s != '\0')
+   if (!err && *s != '\0')
    {
-      if (!err) err = map(exports, "re-filter-filenames", 1, s, 0);
+      err = map(exports, "re-filter-filenames", 1, s, 0);
    }
    else
    {
diff --git a/config b/config
index 8be4fb2..424ca3d 100644 (file)
--- a/config
+++ b/config
@@ -975,7 +975,7 @@ enable-edit-actions 0
 #      link. If the user adds the force prefix by hand, it will not
 #      be accepted and the circumvention attempt is logged.
 #
-#  Examples:
+#  Example:
 #
 #      enforce-blocks 1
 #
@@ -1515,7 +1515,7 @@ enable-proxy-authentication-forwarding 0
 #      logfile from time to time, to see how many retries are usually
 #      needed.
 #
-#  Examples:
+#  Example:
 #
 #      forwarded-connect-retries 1
 #
@@ -1564,7 +1564,7 @@ forwarded-connect-retries  0
 #      the CGI templates to make sure they don't reference content
 #      from config.privoxy.org.
 #
-#  Examples:
+#  Example:
 #
 #      accept-intercepted-requests 1
 #
@@ -1601,7 +1601,7 @@ accept-intercepted-requests 0
 #      Don't enable this option unless you're sure that you really
 #      need it.
 #
-#  Examples:
+#  Example:
 #
 #      allow-cgi-request-crunching 1
 #
@@ -1643,7 +1643,7 @@ allow-cgi-request-crunching 0
 #      to enable this option, but if one of the submit buttons
 #      appears to be broken, you should give it a try.
 #
-#  Examples:
+#  Example:
 #
 #      split-large-forms 1
 #
@@ -1699,7 +1699,7 @@ split-large-forms 0
 #      seconds or even more if you think your browser can handle it.
 #      If your browser appears to be hanging, it probably can't.
 #
-#  Examples:
+#  Example:
 #
 #      keep-alive-timeout 300
 #
@@ -1742,7 +1742,7 @@ keep-alive-timeout 5
 #      If you are seeing problems with pages not properly loading,
 #      disabling this option could work around the problem.
 #
-#  Examples:
+#  Example:
 #
 #      tolerate-pipelining 1
 #
@@ -1793,7 +1793,7 @@ tolerate-pipelining 1
 #      This option has no effect if Privoxy has been compiled without
 #      keep-alive support.
 #
-#  Examples:
+#  Example:
 #
 #      default-server-timeout 60
 #
@@ -1863,7 +1863,7 @@ tolerate-pipelining 1
 #      This option should only be used by experienced users who
 #      understand the risks and can weight them against the benefits.
 #
-#  Examples:
+#  Example:
 #
 #      connection-sharing 1
 #
@@ -1895,7 +1895,7 @@ tolerate-pipelining 1
 #      If you aren't using an occasionally slow proxy like Tor,
 #      reducing it to a few seconds should be fine.
 #
-#  Examples:
+#  Example:
 #
 #      socket-timeout 300
 #
@@ -1957,7 +1957,7 @@ socket-timeout 300
 #      limit can't be increased without recompiling Privoxy with a
 #      different FD_SETSIZE limit.
 #
-#  Examples:
+#  Example:
 #
 #      max-client-connections 256
 #
@@ -2011,7 +2011,7 @@ socket-timeout 300
 #      the system configuration as well. On FreeBSD-based system the
 #      limit is controlled by the kern.ipc.soacceptqueue sysctl.
 #
-#  Examples:
+#  Example:
 #
 #      listen-backlog 4096
 #
@@ -2053,7 +2053,7 @@ socket-timeout 300
 #      systems. Check the accf_http(9) man page to learn how to
 #      enable the support in the operating system.
 #
-#  Examples:
+#  Example:
 #
 #      enable-accept-filter 1
 #
@@ -2331,7 +2331,7 @@ socket-timeout 300
 #      it is used, the tag will be set until the client-tag-lifetime
 #      is over.
 #
-#  Examples:
+#  Example:
 #
 #            # Increase the time to life for temporarily enabled tags to 3 minutes
 #            client-tag-lifetime 180
@@ -2385,7 +2385,7 @@ socket-timeout 300
 #      registering lots of client tag settings for clients that don't
 #      exist.
 #
-#  Examples:
+#  Example:
 #
 #            # Allow systems that can reach Privoxy to provide the client
 #            # IP address with a X-Forwarded-For header.
@@ -2433,14 +2433,14 @@ socket-timeout 300
 #      cleared before using it, a buffer that is too large can
 #      actually reduce the throughput.
 #
-#  Examples:
+#  Example:
 #
 #            # Increase the receive buffer size
 #            receive-buffer-size 32768
 #
 #
-#  7. TLS/SSL INSPECTION
-#  ======================
+#  7. TLS/SSL INSPECTION (EXPERIMENTAL)
+#  =====================================
 #
 #  7.1. ca-directory
 #  ==================
@@ -2470,7 +2470,7 @@ socket-timeout 300
 #      The permissions should only let Privoxy and the Privoxy admin
 #      access the directory.
 #
-#  Examples:
+#  Example:
 #
 #      ca-directory /usr/local/etc/privoxy/CA
 #
@@ -2510,7 +2510,7 @@ socket-timeout 300
 #      The file can be generated with: openssl req -new -x509
 #      -extensions v3_ca -keyout cakey.pem -out cacert.crt -days 3650
 #
-#  Examples:
+#  Example:
 #
 #      ca-cert-file root.crt
 #
@@ -2540,7 +2540,7 @@ socket-timeout 300
 #      This directive specifies the name of the CA key file in ".pem"
 #      format. See the ca-cert-file for a command to generate it.
 #
-#  Examples:
+#  Example:
 #
 #      ca-key-file cakey.pem
 #
@@ -2574,7 +2574,7 @@ socket-timeout 300
 #      Note that the password is shown on the CGI page so don't reuse
 #      an important one.
 #
-#  Examples:
+#  Example:
 #
 #      ca-password blafasel
 #
@@ -2611,13 +2611,124 @@ socket-timeout 300
 #      The permissions should only let Privoxy and the Privoxy admin
 #      access the directory.
 #
-#  Examples:
+#      +-----------------------------------------------------+
+#      |                       Warning                       |
+#      |-----------------------------------------------------|
+#      |Privoxy currently does not garbage-collect obsolete  |
+#      |keys and certificates and does not keep track of how |
+#      |may keys and certificates exist.                     |
+#      |                                                     |
+#      |Privoxy admins should monitor the size of the        |
+#      |directory and/or make sure there is sufficient space |
+#      |available. A cron job to limit the number of keys and|
+#      |certificates to a certain number may be worth        |
+#      |considering.                                         |
+#      +-----------------------------------------------------+
+#  Example:
 #
 #      certificate-directory /usr/local/var/privoxy/certs
 #
 #certificate-directory /usr/local/var/privoxy/certs
 #
-#  7.6. trusted-cas-file
+#  7.6. cipher-list
+#  =================
+#
+#  Specifies:
+#
+#      A list of ciphers to use in TLS handshakes
+#
+#  Type of value:
+#
+#      Text
+#
+#  Default value:
+#
+#      None
+#
+#  Effect if unset:
+#
+#      A default value is inherited from the TLS library.
+#
+#  Notes:
+#
+#      This directive allows to specify a non-default list of ciphers
+#      to use in TLS handshakes with clients and servers.
+#
+#      Ciphers are separated by colons. Which ciphers are supported
+#      depends on the TLS library. When using OpenSSL, unsupported
+#      ciphers are skipped. When using MbedTLS they are rejected.
+#
+#      +-----------------------------------------------------+
+#      |                       Warning                       |
+#      |-----------------------------------------------------|
+#      |Specifying an unusual cipher list makes              |
+#      |fingerprinting easier. Note that the default list    |
+#      |provided by the TLS library may be unusual when      |
+#      |compared to the one used by modern browsers as well. |
+#      +-----------------------------------------------------+
+#  Examples:
+#
+#          # Explicitly set a couple of ciphers with names used by MbedTLS
+#          cipher-list cipher-list TLS-ECDHE-RSA-WITH-CHACHA20-POLY1305-SHA256:\
+#          TLS-ECDHE-ECDSA-WITH-CHACHA20-POLY1305-SHA256:\
+#          TLS-DHE-RSA-WITH-CHACHA20-POLY1305-SHA256:\
+#          TLS-ECDHE-ECDSA-WITH-AES-128-GCM-SHA256:\
+#          TLS-ECDHE-ECDSA-WITH-AES-256-GCM-SHA384:\
+#          TLS-ECDHE-ECDSA-WITH-AES-256-CCM:\
+#          TLS-ECDHE-ECDSA-WITH-AES-256-CCM-8:\
+#          TLS-ECDHE-ECDSA-WITH-AES-128-CCM:\
+#          TLS-ECDHE-ECDSA-WITH-AES-128-CCM-8:\
+#          TLS-ECDHE-ECDSA-WITH-CAMELLIA-128-GCM-SHA256:\
+#          TLS-ECDHE-ECDSA-WITH-CAMELLIA-256-GCM-SHA384:\
+#          TLS-ECDHE-RSA-WITH-AES-128-GCM-SHA256:\
+#          TLS-ECDHE-RSA-WITH-AES-256-GCM-SHA384:\
+#          TLS-ECDHE-RSA-WITH-CAMELLIA-128-GCM-SHA256:\
+#          TLS-ECDHE-RSA-WITH-CAMELLIA-256-GCM-SHA384:\
+#          TLS-DHE-RSA-WITH-AES-256-GCM-SHA384:\
+#          TLS-DHE-RSA-WITH-AES-128-GCM-SHA256:\
+#          TLS-DHE-RSA-WITH-AES-256-CCM:\
+#          TLS-DHE-RSA-WITH-AES-256-CCM-8:\
+#          TLS-DHE-RSA-WITH-AES-128-CCM:\
+#          TLS-DHE-RSA-WITH-AES-128-CCM-8:\
+#          TLS-DHE-RSA-WITH-CAMELLIA-128-GCM-SHA256:\
+#          TLS-DHE-RSA-WITH-CAMELLIA-256-GCM-SHA384:\
+#          TLS-ECDH-RSA-WITH-AES-128-GCM-SHA256:\
+#          TLS-ECDH-RSA-WITH-AES-256-GCM-SHA384:\
+#          TLS-ECDH-RSA-WITH-CAMELLIA-128-GCM-SHA256:\
+#          TLS-ECDH-RSA-WITH-CAMELLIA-256-GCM-SHA384:\
+#          TLS-ECDH-ECDSA-WITH-AES-128-GCM-SHA256:\
+#          TLS-ECDH-ECDSA-WITH-AES-256-GCM-SHA384:\
+#          TLS-ECDH-ECDSA-WITH-CAMELLIA-128-GCM-SHA256:\
+#          TLS-ECDH-ECDSA-WITH-CAMELLIA-256-GCM-SHA384
+#
+#
+#          # Explicitly set a couple of ciphers with names used by OpenSSL
+#          cipher-list ECDHE-RSA-AES256-GCM-SHA384:\
+#          ECDHE-ECDSA-AES256-GCM-SHA384:\
+#          DH-DSS-AES256-GCM-SHA384:\
+#          DHE-DSS-AES256-GCM-SHA384:\
+#          DH-RSA-AES256-GCM-SHA384:\
+#          DHE-RSA-AES256-GCM-SHA384:\
+#          ECDH-RSA-AES256-GCM-SHA384:\
+#          ECDH-ECDSA-AES256-GCM-SHA384:\
+#          ECDHE-RSA-AES128-GCM-SHA256:\
+#          ECDHE-ECDSA-AES128-GCM-SHA256:\
+#          DH-DSS-AES128-GCM-SHA256:\
+#          DHE-DSS-AES128-GCM-SHA256:\
+#          DH-RSA-AES128-GCM-SHA256:\
+#          DHE-RSA-AES128-GCM-SHA256:\
+#          ECDH-RSA-AES128-GCM-SHA256:\
+#          ECDH-ECDSA-AES128-GCM-SHA256:\
+#          ECDHE-RSA-AES256-GCM-SHA384:\
+#          AES128-SHA
+#
+#
+#          # Use keywords instead of explicity naming the ciphers (Does not work with MbedTLS)
+#          cipher-list ALL:!EXPORT:!EXPORT40:!EXPORT56:!aNULL:!LOW:!RC4:@STRENGTH
+#
+#
+#
+#  7.7. trusted-cas-file
 #  ======================
 #
 #  Specifies:
@@ -2644,7 +2755,7 @@ socket-timeout 300
 #      An example file can be downloaded from https://curl.haxx.se/ca
 #      /cacert.pem.
 #
-#  Examples:
+#  Example:
 #
 #      trusted-cas-file trusted_cas_file.pem
 #
index c542038..7d3341d 100644 (file)
@@ -81,7 +81,7 @@ CODE_STATUS="UNRELEASED"
 
 dnl Timestamp (date +%s) used by the mtree-spec target.
 dnl Should be updated before releases but forgetting it isn't critical.
-SOURCE_DATE_EPOCH=1545411710
+SOURCE_DATE_EPOCH=1605695571
 
 dnl CODE_STATUS can be "alpha", "beta", "stable" or "UNRELEASED",
 dnl and will be used for CGI output. Increment version number and
@@ -1166,14 +1166,14 @@ if test X"$OPT_MBEDTLS" != Xno; then
 fi
 AC_SUBST(FEATURE_HTTPS_INSPECTION_ONLY_MBEDTLS)
 
-dnl ========================================================
-dnl check for OpenSSL which is required for https inspection
-dnl ========================================================
+dnl =================================================================
+dnl check for OpenSSL/LibreSSL which is required for https inspection
+dnl =================================================================
 FEATURE_HTTPS_INSPECTION_ONLY_OPENSSL=#
 OPT_OPENSSL=no
 AC_ARG_WITH(openssl,dnl
-AC_HELP_STRING([--with-openssl], [Enable OpenSSL detection for https inspection.])
-AC_HELP_STRING([--without-openssl], [Disable OpenSSL detection]),
+AC_HELP_STRING([--with-openssl], [Enable OpenSSL/LibreSSL detection for https inspection.])
+AC_HELP_STRING([--without-openssl], [Disable OpenSSL/LibreSSL detection]),
   OPT_OPENSSL=$withval)
 
 if test X"$OPT_OPENSSL" != Xno; then
index b041a16..467b0f3 100644 (file)
@@ -732,6 +732,10 @@ ada*.
 # Blocked URL = http://bilder.augsburger-allgemeine.de/img/incoming/orig30444932/2560007661/DigiAd-Zeopexx-03072014.gif
 # Blocked URL = http://bilder.augsburger-allgemeine.de/img/incoming/orig30463337/9180008457/DigiAd-AugenblickOptik-04072014.gif
 /.*DigiAd
+# Blocked URL = http://web-t.9gag.com/piwik.php?e_c=PostImpression&e_a=ViewPostForOneSecond&e_n=Hot&e_v=1&idsite=7&rec=1&r=438977&h=14&m=13&s=9&url=https%3A%2F%2F9gag.com%2F&_id=780f7a6cf105beed&_idts=1600003135&_idvc=3&_idn=0&_refts=0&_viewts=1600255370&send_image=0&pdf=1&qt=0&realp=0&wma=0&dir=0&fla=0&java=0&gears=0&ag=0&cookie=1&res=1366x768&e_cvar=%7B%221%22%3A%5B%22PostKey%22%2C%22aR72ZBQ%22%5D%2C%222%22%3A%5B%22TriggeredPage%22%2C%22PostList%22%5D%2C%223%22%3A%5B%22TriggeredPageKey%22%2C%22Hot%22%5D%2C%224%22%3A%5B%22Position%22%2C%22343%22%5D%7D&_cvar=%7B%221%22%3A%5B%22AppVersion%22%2C%2200000%22%5D%7D&gt_ms=222
+# Blocked URL = http://piwik.peta.de/piwik.php?idsite=2
+# Blocked URL = http://www.attac.de/piwik/piwik.php?idsite=1
+/(.*/)?piwik\.php
 
 #############################################################################
 # Generic unblockers by path:
@@ -920,6 +924,14 @@ oskar.tradera.com/
 #MASTER# BLOCK-REFERRER: http://www12.zippyshare.com/v/64444425/file.html
 # Blocked URL = http://www.adcash.com/script/java.php?option=rotateur&rotateur=146355
 .adcash.com/script/
+#MASTER# BLOCK-REFERRER: https://www.tagesschau.de/inland/wolfgang-clement-103.html
+# Blocked URL = http://de.ioam.de/tx.io?st=tagessch&cp=tagesschstat&pt=CP&ps=lin&er=N22&rf=&r2=&ur=www.tagesschau.de&xy=1366x768x24&lo=FR%2Fn.a.&cb=001e&i2=001e3e01eacf383955f7084ae&ep=1632541316&vr=416&id=7wvnfq&i3=nocookie&n1=27&dntt=0&lt=1601209524382&ev=&cs=oegxy9&mo=1&sr=71
+# Blocked URL = http://script.ioam.de/iam.js
+.ioam.de/
+# Blocked URL = http://t.vi-serve.com/?event=ERROR&page_url=https%3A%2F%2F9gag.com%2F&pub_id=576566800037402&channel_id=5ea98ccc02abaa4068798df6&placement_id=pltlhqRgj1oCSlyn51S&ad_unit_type=2&session_id=e4xr60mlvsol&focus=false&player=playerVI&pageLanguage=en&placement_w=0&placement_h=0&time_delta=20700&error_msg=script%20tag%20placed%20in%20non-displayed%20Element&playlist_pos=1&mobile=false&floating=false&cb=f43f
+t.vi-serve.com/
+# Blocked URL = http://pixel.inforsea.com/server/log
+pixel.inforsea.com/
 
 {+block{Might be a web-bug that is an image.} -handle-as-empty-document +handle-as-image}
 #MASTER# BLOCK-REFERRER: http://versiontracker.com and many others. 10/20/06
@@ -960,10 +972,14 @@ go.idmnet.bbelements.com/please/showit/
 gm-link.com/
 # Blocked URL = https://collector.githubapp.com/github/page_view?dimensions[page]=https%3A%2F%2Fgithub.com%2Fopenbsd%2Fsrc%2Fblob%2F5ecdd0566b441ae0b99e73f410875e05dc0fa5b7%2Flib%2Flibc%2Finclude%2Fthread_private.h&dimensions[title]=src%2Fthread_private.h%20at%205ecdd0566b441ae0b99e73f410875e05dc0fa5b7%20%C2%B7%20openbsd%2Fsrc%20%C2%B7%20GitHub&dimensions[referrer]=https%3A%2F%2Fgithub.com%2Fopenbsd%2Fsrc%2Fsearch%3Fq%3D_MUTEX_LOCK%26unscoped_q%3D_MUTEX_LOCK&dimensions[user_agent]=Mozilla%2F5.0%20(X11%3B%20ElectroBSD%20amd64%3B%20rv%3A68.0)%20Gecko%2F20100101%20Firefox%2F68.0&dimensions[screen_resolution]=1366x768&dimensions[pixel_ratio]=1&dimensions[browser_resolution]=1362x636&dimensions[tz_seconds]=7200&dimensions[timestamp]=1591515169218&dimensions[referrer]=&dimensions[request_id]=22CA%3AE6F6%3A271ED2A%3A3839C5D%3A5EDB8295&dimensions[visitor_id]=5184934927058829974&dimensions[region_edge]=ams&dimensions[region_render]=ams&dimensions[user_id]=929183&dimensions[user_login]=openbsd&dimensions[repository_id]=66966208&dimensions[repository_nwo]=openbsd%2Fsrc&dimensions[repository_public]=true&dimensions[repository_is_fork]=false&dimensions[repository_network_root_id]=66966208&dimensions[repository_network_root_nwo]=openbsd%2Fsrc&dimensions[repository_explore_github_marketplace_ci_cta_shown]=false&&measures[performance_timing]=1-172-172-13996-12735-12426-12394-3858-172-172-172--13996-0---172-3853-3412-0--&&&dimensions[cid]=268614077.1591515169
 collector.githubapp.com/
-# Blocked URL = https://consentmanager.mgr.consensu.org/delivery/pixel.php?id=11319&did=0&cfdid=0&t=pv&h=https%3A%2F%2Fsourceforge.net%2Fp%2Fijbswa%2Ffeature-requests%2F535%2F&o=1591880198219&l=EN&lv=0&d=0&ct=14&e=&e2=&e3=&i=&sv=0&dv=0
+# Blocked URL = http://consentmanager.mgr.consensu.org/delivery/pixel.php?id=11319&did=0&cfdid=0&t=pv&h=https%3A%2F%2Fsourceforge.net%2Fp%2Fijbswa%2Ffeature-requests%2F535%2F&o=1591880198219&l=EN&lv=0&d=0&ct=14&e=&e2=&e3=&i=&sv=0&dv=0
 .consensu.org/delivery/pixel\.php
 # Blocked URL = https://srv-2020-08-22-20.pixel.parsely.com/plogger/?rand=1598128327825&plid=94157330&idsite=theverge.com&url=https%3A%2F%2Fwww.theverge.com%2F2020%2F8%2F21%2F21396316%2Fapple-wordpress-in-app-purchase-tax-update-store&urlref=&screen=1366x768%7C1366x768%7C24&data=%7B%7D&sid=1&surl=https%3A%2F%2Fwww.theverge.com%2F2020%2F8%2F21%2F21396316%2Fapple-wordpress-in-app-purchase-tax-update-store&sref=&sts=1598128167510&slts=0&date=Sat+Aug+22+2020+22%3A32%3A07+GMT%2B0200+(CEST)&action=heartbeat&inc=6&tt=140923&pvid=91707838&u=pid%3D72b66a2ec3c73c8fbf8c925f679fcbd9
 .pixel.parsely.com/
+# Blocked URL = http://t.9gag.com/img.gif?a=unique-viewed&v=v&ref=&lbl=&lblv=&p=d&e=aD4X2GG&u=&w=l&url=https%3A%2F%2F9gag.com%2F&referrer=&t=1600253599&
+t.9gag.com/img\.gif
+# Blocked URL = http://t.lto.connectaserver.de/t.php?ht=e&in=Verweildauer%7C%7CTimeOnPage%7C%7C1m%2030s&pp=https%3A%2F%2Fwww.lto.de%2Frecht%2Fhintergruende%2Fh%2Feugh-c62317-vorratsdatenspeicherung-internet-telefon-eu-staaten-sicherheit-terrorismus-datenschutz-speichern-deutschland-kinderpornographie%2F&sr=1366x768&vp=1362x676&cid=602d486b-9a75-4ea2-99d3-ebfb063e1be8&dt=Vorratsdatenspeicherung:%20Was%20bedeutet%20das%20EuGH-Urteil?&rf=&z=1602062648454
+.connectaserver.de/
 
 
 #############################################################################
@@ -1518,6 +1534,8 @@ b.collective-media.net/
 #MASTER# BLOCK-REFERRER: http://www.heise.de/
 # Blocked URL = http://heise.ivwbox.de/2004/01/survey.js
 .ivwbox.de/
+# Blocked URL = https://pixel.wp.com/g.gif?v=ext&j=1%3A7.8&blog=44083982&post=2542&tz=1&srv=www.geeklan.co.uk&host=www.geeklan.co.uk&ref=&fcp=0&rand=0.34473017357614855
+pixel.wp.com/
 
 #----------------------------------------------------------------------------
 # Specific counters (see above for generic patterns)
@@ -1971,6 +1989,10 @@ msdn.microsoft.com/
 .golang.org/
 # URL = http://adaway.org/
 adaway.org/
+# URL = https://belco24.de/bilder/banner/Bildschirmfoto%202018-08-21%20um%2015.20.01.png
+belco24.de/
+# URL = https://www.tagesschau.de/multimedia/bilder/banner-zak-kostopoulos-101~_v-mittel16x9.jpg
+.tagesschau.de/
 
 
 #############################################################################
@@ -2171,6 +2193,12 @@ collector.githubapp.com/
 .consensu.org/delivery/pixel\.php
 # URL = https://de.wikipedia.org/beacon/event?%7B%22event%22%3A%7B%22source_page_id%22%3A1501869%2C%22source_namespace%22%3A0%2C%22source_title%22%3A%22Primat%22%2C%22source_url%22%3A%22https%3A%2F%2Fde.wikipedia.org%2Fwiki%2FPrimat%22%2C%22page_title%22%3A%22Primaten%22%2C%22page_id%22%3A4022%2C%22page_namespace%22%3A0%7D%2C%22schema%22%3A%22VirtualPageView%22%2C%22webHost%22%3A%22de.wikipedia.org%22%2C%22wiki%22%3A%22dewiki%22%2C%22revision%22%3A17780078%7D;
 .wikipedia.org/
+# URL = http://platform.twitter.com/widgets/widget_iframe.2d7d9a6d04538bf11c7b23641e75738c.html?origin=https%3A%2F%2F9gag.com
+.twitter.com/.*origin=http
+# URL = http://issue.freebsdfoundation.org/html5_viewer/index.html?issue_id=673890&publication_id=&parentUrl=https%3A%2F%2Fissue.freebsdfoundation.org%2Fpublication%2F%3Fi%3D673890
+issue.freebsdfoundation.org/
+# URL = http://ltfl.librarything.com//forlibraries/widget_response.php?id=1477&isbns=9780062279194&divs=ltfl_tagbrowse%2Cltfl_related%2Cltfl_similars%2Cltfl_series%2Cltfl_awards&lccn=&oclc=&t=1602093207304&systype=zones&pagetype=full&catalog_url=https%3A%2F%2Fkatalog.stbib-koeln.de%2Falswww2.dll%2FAPS_PRESENT_BIB%3FStyle%3DPortal3%26SubStyle%3D%26Lang%3DGER%26ResponseEncoding%3Dutf-8%26no%3DT011006751%26Via%3DZ3950%26View%3DAnnotated%26Parent%3DObj_482831602093137%26SearchBrowseList%3DObj_482831602093137%26SearchBrowseListItem%3D71831%26BrowseList%3DObj_482831602093137%3FStyle%3DPortal3%26SubStyle%3D%26Lang%3DGER%26ResponseEncoding%3Dutf-8%26BrowseListItem%3D71831%26QueryObject%3DObj_482811602093136&title=Think%20like%20a%20freak&author=Levitt%2C%20Steven%20D.&accession=T011006751&locations=&widget_response_loaded_after=764&container_widthAAS={%22body%22:{%22cw%22:1350,%22ch%22:946},%22ltfl_tagbrowse%22:{%22cw%22:614,%22ch%22:0},%22ltfl_related%22:{%22cw%22:614,%22ch%22:0},%22ltfl_similars%22:{%22cw%22:614,%22ch%22:0},%22ltfl_series%22:{%22cw%22:614,%22ch%22:0},%22ltfl_awards%22:{%22cw%22:614,%22ch%22:0}}
+.librarything.com/
 
 {+redirect{s@.*url=@http://@} -block}
 # Sticky Actions = +redirect -block
index 14a4d6e..c84e00f 100644 (file)
@@ -508,31 +508,6 @@ warranty? Registration?</title>
  <ulink url="https://www.spi-inc.org/donations">SPI's general donation page</ulink>.
 </para>
 
-<para>
- You can also donate to Privoxy using a bank account or a "Paypal" address:
-</para>
-<literallayout>
- Name on account: <ulink url="https://www.zwiebelfreunde.de/">Zwiebelfreunde e.V.</ulink>
- IBAN: DE95430609671126825604
- BIC: GENODEM1GLS
- Bank: GLS Bank
-</literallayout>
-<literallayout>
- "Paypal" address: privoxy@zwiebelfreunde.de
-</literallayout>
-<para>
- Donations made through Zwiebelfreunde e.V. are tax-deductible in Germany
- and other countries that recognize German charitable clubs. Feel free to
- use the Subject field to provide a name to be credited and a list of TODO
- list items you are interested in the most. For example: Max Mustermann: #16, #1, #14.
-</para>
-
-<para>
- Note that donations made through Zwiebelfreunde e.V. currently can't be checked
- automatically so you may not get credited right away. The credits currently
- reflect donations received before 2016-01-14.
-</para>
-
 <para>
  If you have any questions regarding donations please mail to either the
  public user mailing list or, if it's a private matter, to
index 57f9f1f..6015748 100644 (file)
 
 <para>
  The same is true for <application>Privoxy</application> binaries
- unless they are linked with
- <ulink url="https://tls.mbed.org/">mbed TLS</ulink> in which
- case you can redistribute them and/or modify them under the terms
- of the <citetitle>GNU General Public License</citetitle>
+ unless they are linked with a
+ <ulink url="https://tls.mbed.org/">mbed TLS</ulink> version
+ that is licensed under the Apache 2.0 license in which
+ case you can redistribute and/or modify the <application>Privoxy</application>
+ binaries under the terms of the <citetitle>GNU General Public License</citetitle>
  as published by the Free Software Foundation, either version 3
  of the license, or (at your option) any later version.
 </para>
index 15f23fa..a3df099 100644 (file)
@@ -122,6 +122,7 @@ Current Privoxy Team:
  Magnus Holmgren
  Eric M. Hopper
  Ralf Horstmann
+ Ho+ Ho+ Ho+
  Ned&zcaron;ad Hrnjica
  Stefan Huehner
  Basil Hussain
@@ -195,6 +196,7 @@ Current Privoxy Team:
  J&ouml;rg Weinmann
  Darren Wiebe
  Anduin Withers
+ withoutname
  Eduard Wulff
  Yang Xia
  Jarry Xu
index d1fbf29..8a33783 100644 (file)
@@ -1630,7 +1630,7 @@ actionsfile
   </listitem>
  </varlistentry>
  <varlistentry>
-  <term>Examples:</term>
+  <term>Example:</term>
   <listitem>
    <para>
     enforce-blocks 1
@@ -2508,7 +2508,7 @@ forward-socks4, forward-socks4a, forward-socks5 and forward-socks5t</title>
   </listitem>
  </varlistentry>
  <varlistentry>
-  <term>Examples:</term>
+  <term>Example:</term>
   <listitem>
    <para>
     forwarded-connect-retries 1
@@ -2585,7 +2585,7 @@ forward-socks4, forward-socks4a, forward-socks5 and forward-socks5t</title>
   </listitem>
  </varlistentry>
  <varlistentry>
-  <term>Examples:</term>
+  <term>Example:</term>
   <listitem>
    <para>
     accept-intercepted-requests 1
@@ -2643,7 +2643,7 @@ forward-socks4, forward-socks4a, forward-socks5 and forward-socks5t</title>
   </listitem>
  </varlistentry>
  <varlistentry>
-  <term>Examples:</term>
+  <term>Example:</term>
   <listitem>
    <para>
     allow-cgi-request-crunching 1
@@ -2710,7 +2710,7 @@ forward-socks4, forward-socks4a, forward-socks5 and forward-socks5t</title>
   </listitem>
  </varlistentry>
  <varlistentry>
-  <term>Examples:</term>
+  <term>Example:</term>
   <listitem>
    <para>
     split-large-forms 1
@@ -2793,7 +2793,7 @@ forward-socks4, forward-socks4a, forward-socks5 and forward-socks5t</title>
   </listitem>
  </varlistentry>
  <varlistentry>
-  <term>Examples:</term>
+  <term>Example:</term>
   <listitem>
    <para>
     keep-alive-timeout 300
@@ -2862,7 +2862,7 @@ forward-socks4, forward-socks4a, forward-socks5 and forward-socks5t</title>
   </listitem>
  </varlistentry>
  <varlistentry>
-  <term>Examples:</term>
+  <term>Example:</term>
   <listitem>
    <para>
     tolerate-pipelining 1
@@ -2943,7 +2943,7 @@ forward-socks4, forward-socks4a, forward-socks5 and forward-socks5t</title>
   </listitem>
  </varlistentry>
  <varlistentry>
-  <term>Examples:</term>
+  <term>Example:</term>
   <listitem>
    <para>
     default-server-timeout 60
@@ -3042,7 +3042,7 @@ forward-socks4, forward-socks4a, forward-socks5 and forward-socks5t</title>
   </listitem>
  </varlistentry>
  <varlistentry>
-  <term>Examples:</term>
+  <term>Example:</term>
   <listitem>
    <para>
     connection-sharing 1
@@ -3098,7 +3098,7 @@ forward-socks4, forward-socks4a, forward-socks5 and forward-socks5t</title>
   </listitem>
  </varlistentry>
  <varlistentry>
-  <term>Examples:</term>
+  <term>Example:</term>
   <listitem>
    <para>
     socket-timeout 300
@@ -3186,7 +3186,7 @@ forward-socks4, forward-socks4a, forward-socks5 and forward-socks5t</title>
   </listitem>
  </varlistentry>
  <varlistentry>
-  <term>Examples:</term>
+  <term>Example:</term>
   <listitem>
    <para>
     max-client-connections 256
@@ -3265,7 +3265,7 @@ forward-socks4, forward-socks4a, forward-socks5 and forward-socks5t</title>
   </listitem>
  </varlistentry>
  <varlistentry>
-  <term>Examples:</term>
+  <term>Example:</term>
   <listitem>
    <para>
     listen-backlog 4096
@@ -3336,7 +3336,7 @@ forward-socks4, forward-socks4a, forward-socks5 and forward-socks5t</title>
   </listitem>
  </varlistentry>
  <varlistentry>
-  <term>Examples:</term>
+  <term>Example:</term>
   <listitem>
    <para>
     enable-accept-filter 1
@@ -3739,7 +3739,7 @@ forward-socks4, forward-socks4a, forward-socks5 and forward-socks5t</title>
   </listitem>
  </varlistentry>
  <varlistentry>
-  <term>Examples:</term>
+  <term>Example:</term>
   <listitem>
     <screen>
       # Increase the time to life for temporarily enabled tags to 3 minutes
@@ -3811,7 +3811,7 @@ forward-socks4, forward-socks4a, forward-socks5 and forward-socks5t</title>
   </listitem>
  </varlistentry>
  <varlistentry>
-  <term>Examples:</term>
+  <term>Example:</term>
   <listitem>
     <screen>
       # Allow systems that can reach Privoxy to provide the client
@@ -3884,7 +3884,7 @@ forward-socks4, forward-socks4a, forward-socks5 and forward-socks5t</title>
   </listitem>
  </varlistentry>
  <varlistentry>
-  <term>Examples:</term>
+  <term>Example:</term>
   <listitem>
     <screen>
       # Increase the receive buffer size
@@ -3901,7 +3901,7 @@ forward-socks4, forward-socks4a, forward-socks5 and forward-socks5t</title>
 
 
 <sect2 id="tls">
-<title>TLS/SSL Inspection</title>
+<title>TLS/SSL Inspection (Experimental)</title>
 
 <!--   ~~~~~       New section      ~~~~~     -->
 
@@ -3952,7 +3952,7 @@ forward-socks4, forward-socks4a, forward-socks5 and forward-socks5t</title>
   </listitem>
  </varlistentry>
  <varlistentry>
-  <term>Examples:</term>
+  <term>Example:</term>
   <listitem>
    <para>
     ca-directory /usr/local/etc/privoxy/CA
@@ -4023,7 +4023,7 @@ forward-socks4, forward-socks4a, forward-socks5 and forward-socks5t</title>
   </listitem>
  </varlistentry>
  <varlistentry>
-  <term>Examples:</term>
+  <term>Example:</term>
   <listitem>
    <para>
     ca-cert-file root.crt
@@ -4081,7 +4081,7 @@ forward-socks4, forward-socks4a, forward-socks5 and forward-socks5t</title>
   </listitem>
  </varlistentry>
  <varlistentry>
-  <term>Examples:</term>
+  <term>Example:</term>
   <listitem>
    <para>
     ca-key-file cakey.pem
@@ -4143,7 +4143,7 @@ forward-socks4, forward-socks4a, forward-socks5 and forward-socks5t</title>
   </listitem>
  </varlistentry>
  <varlistentry>
-  <term>Examples:</term>
+  <term>Example:</term>
   <listitem>
    <para>
     ca-password blafasel
@@ -4206,13 +4206,26 @@ forward-socks4, forward-socks4a, forward-socks5 and forward-socks5t</title>
     and the <ulink url="#CA-CERT-KEY">ca-cert-key</ulink>.
    </para>
    <para>
-    The permissions should only let &my-app; and the  &my-app;
+    The permissions should only let &my-app; and the &my-app;
     admin access the directory.
    </para>
+   <warning>
+    <para>
+     &my-app; currently does not garbage-collect obsolete keys
+     and certificates and does not keep track of how may keys
+     and certificates exist.
+    </para>
+    <para>
+     &my-app; admins should monitor the size of the directory
+     and/or make sure there is sufficient space available.
+     A cron job to limit the number of keys and certificates
+     to a certain number may be worth considering.
+    </para>
+   </warning>
   </listitem>
  </varlistentry>
  <varlistentry>
-  <term>Examples:</term>
+  <term>Example:</term>
   <listitem>
    <para>
     certificate-directory /usr/local/var/privoxy/certs
@@ -4227,6 +4240,131 @@ forward-socks4, forward-socks4a, forward-socks5 and forward-socks5t</title>
 
 <!--   ~~~~~       New section      ~~~~~     -->
 
+<sect3 renderas="sect4" id="cipher-list"><title>cipher-list</title>
+<variablelist>
+ <varlistentry>
+  <term>Specifies:</term>
+  <listitem>
+   <para>
+    A list of ciphers to use in TLS handshakes
+   </para>
+  </listitem>
+ </varlistentry>
+ <varlistentry>
+  <term>Type of value:</term>
+  <listitem>
+   <para>
+    Text
+   </para>
+  </listitem>
+ </varlistentry>
+ <varlistentry>
+  <term>Default value:</term>
+  <listitem>
+   <para>None</para>
+  </listitem>
+ </varlistentry>
+ <varlistentry>
+  <term>Effect if unset:</term>
+  <listitem>
+   <para>
+    A default value is inherited from the TLS library.
+   </para>
+  </listitem>
+ </varlistentry>
+ <varlistentry>
+  <term>Notes:</term>
+  <listitem>
+   <para>
+    This directive allows to specify a non-default list of ciphers to use
+    in TLS handshakes with clients and servers.
+   </para>
+   <para>
+    Ciphers are separated by colons. Which ciphers are supported
+    depends on the TLS library. When using OpenSSL, unsupported ciphers
+    are skipped. When using MbedTLS they are rejected.
+   </para>
+   <warning>
+    <para>
+     Specifying an unusual cipher list makes fingerprinting easier.
+     Note that the default list provided by the TLS library may
+     be unusual when compared to the one used by modern browsers
+     as well.
+    </para>
+   </warning>
+  </listitem>
+ </varlistentry>
+ <varlistentry>
+  <term>Examples:</term>
+  <listitem>
+   <screen>
+    # Explicitly set a couple of ciphers with names used by MbedTLS
+    cipher-list cipher-list TLS-ECDHE-RSA-WITH-CHACHA20-POLY1305-SHA256:\
+TLS-ECDHE-ECDSA-WITH-CHACHA20-POLY1305-SHA256:\
+TLS-DHE-RSA-WITH-CHACHA20-POLY1305-SHA256:\
+TLS-ECDHE-ECDSA-WITH-AES-128-GCM-SHA256:\
+TLS-ECDHE-ECDSA-WITH-AES-256-GCM-SHA384:\
+TLS-ECDHE-ECDSA-WITH-AES-256-CCM:\
+TLS-ECDHE-ECDSA-WITH-AES-256-CCM-8:\
+TLS-ECDHE-ECDSA-WITH-AES-128-CCM:\
+TLS-ECDHE-ECDSA-WITH-AES-128-CCM-8:\
+TLS-ECDHE-ECDSA-WITH-CAMELLIA-128-GCM-SHA256:\
+TLS-ECDHE-ECDSA-WITH-CAMELLIA-256-GCM-SHA384:\
+TLS-ECDHE-RSA-WITH-AES-128-GCM-SHA256:\
+TLS-ECDHE-RSA-WITH-AES-256-GCM-SHA384:\
+TLS-ECDHE-RSA-WITH-CAMELLIA-128-GCM-SHA256:\
+TLS-ECDHE-RSA-WITH-CAMELLIA-256-GCM-SHA384:\
+TLS-DHE-RSA-WITH-AES-256-GCM-SHA384:\
+TLS-DHE-RSA-WITH-AES-128-GCM-SHA256:\
+TLS-DHE-RSA-WITH-AES-256-CCM:\
+TLS-DHE-RSA-WITH-AES-256-CCM-8:\
+TLS-DHE-RSA-WITH-AES-128-CCM:\
+TLS-DHE-RSA-WITH-AES-128-CCM-8:\
+TLS-DHE-RSA-WITH-CAMELLIA-128-GCM-SHA256:\
+TLS-DHE-RSA-WITH-CAMELLIA-256-GCM-SHA384:\
+TLS-ECDH-RSA-WITH-AES-128-GCM-SHA256:\
+TLS-ECDH-RSA-WITH-AES-256-GCM-SHA384:\
+TLS-ECDH-RSA-WITH-CAMELLIA-128-GCM-SHA256:\
+TLS-ECDH-RSA-WITH-CAMELLIA-256-GCM-SHA384:\
+TLS-ECDH-ECDSA-WITH-AES-128-GCM-SHA256:\
+TLS-ECDH-ECDSA-WITH-AES-256-GCM-SHA384:\
+TLS-ECDH-ECDSA-WITH-CAMELLIA-128-GCM-SHA256:\
+TLS-ECDH-ECDSA-WITH-CAMELLIA-256-GCM-SHA384
+   </screen>
+   <screen>
+    # Explicitly set a couple of ciphers with names used by OpenSSL
+cipher-list ECDHE-RSA-AES256-GCM-SHA384:\
+ECDHE-ECDSA-AES256-GCM-SHA384:\
+DH-DSS-AES256-GCM-SHA384:\
+DHE-DSS-AES256-GCM-SHA384:\
+DH-RSA-AES256-GCM-SHA384:\
+DHE-RSA-AES256-GCM-SHA384:\
+ECDH-RSA-AES256-GCM-SHA384:\
+ECDH-ECDSA-AES256-GCM-SHA384:\
+ECDHE-RSA-AES128-GCM-SHA256:\
+ECDHE-ECDSA-AES128-GCM-SHA256:\
+DH-DSS-AES128-GCM-SHA256:\
+DHE-DSS-AES128-GCM-SHA256:\
+DH-RSA-AES128-GCM-SHA256:\
+DHE-RSA-AES128-GCM-SHA256:\
+ECDH-RSA-AES128-GCM-SHA256:\
+ECDH-ECDSA-AES128-GCM-SHA256:\
+ECDHE-RSA-AES256-GCM-SHA384:\
+AES128-SHA
+   </screen>
+   <screen>
+    # Use keywords instead of explicity naming the ciphers (Does not work with MbedTLS)
+    cipher-list ALL:!EXPORT:!EXPORT40:!EXPORT56:!aNULL:!LOW:!RC4:@STRENGTH
+   </screen>
+  </listitem>
+ </varlistentry>
+</variablelist>
+</sect3>
+
+<!--  ~  End section  ~  -->
+
+<!--   ~~~~~       New section      ~~~~~     -->
+
 <sect3 renderas="sect4" id="trusted-cas-file"><title>trusted-cas-file</title>
 <variablelist>
  <varlistentry>
@@ -4273,7 +4411,7 @@ forward-socks4, forward-socks4a, forward-socks5 and forward-socks5t</title>
   </listitem>
  </varlistentry>
  <varlistentry>
-  <term>Examples:</term>
+  <term>Example:</term>
   <listitem>
    <para>
     trusted-cas-file trusted_cas_file.pem
index c2147e0..344fbd6 100644 (file)
@@ -1483,7 +1483,7 @@ for details.
   &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&squf;&nbsp;&nbsp;<ulink url="http://config.privoxy.org/show-status">View & change the current configuration</ulink>
  </member>
  <member>
-  &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&squf;&nbsp;&nbsp;<ulink url="http://config.privoxy.org/client-tags">View or toggle the tags that can be set based on the clients address</ulink>
+  &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&squf;&nbsp;&nbsp;<ulink url="http://config.privoxy.org/client-tags">View or toggle the tags that can be set based on the client's address</ulink>
  </member>
  <member>
   &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&squf;&nbsp;&nbsp;<ulink url="http://config.privoxy.org/show-request">View the request headers.</ulink>
@@ -5176,6 +5176,9 @@ new action
     a pattern with path doesn't work as the path is only seen
     by &my-app; if the action is already enabled.
    </para>
+   <para>
+    This is an experimental feature.
+   </para>
   </listitem>
  </varlistentry>
 
@@ -7848,10 +7851,11 @@ Requests</title>
 
 <para>
  The same is true for <application>Privoxy</application> binaries
- unless they are linked with
- <ulink url="https://tls.mbed.org/">mbed TLS</ulink> in which
- case you can redistribute them and/or modify them under the terms
- of the <citetitle>GNU General Public License</citetitle>
+ unless they are linked with a
+ <ulink url="https://tls.mbed.org/">mbed TLS</ulink> version
+ that is licensed under the Apache 2.0 license in which
+ case you can redistribute and/or modify the <application>Privoxy</application>
+ binaries under the terms of the <citetitle>GNU General Public License</citetitle>
  as published by the Free Software Foundation, either version 3
  of the license, or (at your option) any later version.
 </para>
index 9c30195..f9c4c4d 100644 (file)
@@ -66,7 +66,7 @@
       "../user-manual/config.html#ENABLE-EDIT-ACTIONS" target="_top">enable-edit-actions</a>).</p>
     </div>
     <div class="SECT2">
-      <h3 class="SECT2"><a name="AEN417" id="AEN417">3.4. There are several different <span class=
+      <h3 class="SECT2"><a name="AEN411" id="AEN411">3.4. There are several different <span class=
       "QUOTE">"actions"</span> files. What are the differences?</a></h3>
       <p>Please have a look at the <a href="../user-manual/actions-file.html" target="_top">the actions chapter</a> in
       the <a href="../user-manual/index.html" target="_top">User Manual</a> for a detailed explanation.</p>
index a5e3956..09f6964 100644 (file)
     "APPLICATION">Junkbuster</span> (tm) FAQ, and modified as appropriate for <span class=
     "APPLICATION">Privoxy</span>.</p>
     <div class="SECT2">
-      <h2 class="SECT2"><a name="AEN1504" id="AEN1504">7.1. License</a></h2>
+      <h2 class="SECT2"><a name="AEN1498" id="AEN1498">7.1. License</a></h2>
       <p><span class="APPLICATION">Privoxy</span> is free software; you can redistribute and/or modify its source code
       under the terms of the <i class="CITETITLE">GNU General Public License</i> as published by the Free Software
       Foundation, either version 2 of the license, or (at your option) any later version.</p>
-      <p>The same is true for <span class="APPLICATION">Privoxy</span> binaries unless they are linked with <a href=
-      "https://tls.mbed.org/" target="_top">mbed TLS</a> in which case you can redistribute them and/or modify them
-      under the terms of the <i class="CITETITLE">GNU General Public License</i> as published by the Free Software
-      Foundation, either version 3 of the license, or (at your option) any later version.</p>
+      <p>The same is true for <span class="APPLICATION">Privoxy</span> binaries unless they are linked with a <a href=
+      "https://tls.mbed.org/" target="_top">mbed TLS</a> version that is licensed under the Apache 2.0 license in which
+      case you can redistribute and/or modify the <span class="APPLICATION">Privoxy</span> binaries under the terms of
+      the <i class="CITETITLE">GNU General Public License</i> as published by the Free Software Foundation, either
+      version 3 of the license, or (at your option) any later version.</p>
       <p><span class="APPLICATION">Privoxy</span> 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
       <a href="https://www.privoxy.org/user-manual/copyright.html#LICENSE" target="_top"><i class=
       "CITETITLE">license</i></a> for details.</p>
     </div>
     <div class="SECT2">
-      <h2 class="SECT2"><a name="AEN1517" id="AEN1517">7.2. History</a></h2>
+      <h2 class="SECT2"><a name="AEN1512" id="AEN1512">7.2. History</a></h2>
       <p>A long time ago, there was the <span class="APPLICATION">Internet Junkbuster</span>, by Anonymous Coders and
       Junkbusters Corporation. This saved many users a lot of pain in the early days of web advertising and user
       tracking.</p>
index 93ce92f..e4cf8d4 100644 (file)
         Paypal</a> and <a href="https://co.clickandpledge.com/advanced/default.aspx?wid=34115" target="_top">Click
         &#38; Pledge</a>. For details, please have a look at <a href="https://www.spi-inc.org/donations" target=
         "_top">SPI's general donation page</a>.</p>
-        <p>You can also donate to Privoxy using a bank account or a "Paypal" address:</p>
-        <p class="LITERALLAYOUT">&nbsp;Name&nbsp;on&nbsp;account:&nbsp;<a href="https://www.zwiebelfreunde.de/" target=
-        "_top">Zwiebelfreunde e.V.</a><br>
-        &nbsp;IBAN:&nbsp;DE95430609671126825604<br>
-        &nbsp;BIC:&nbsp;GENODEM1GLS<br>
-        &nbsp;Bank:&nbsp;GLS&nbsp;Bank</p>
-        <p class="LITERALLAYOUT">&nbsp;"Paypal"&nbsp;address:&nbsp;privoxy@zwiebelfreunde.de</p>
-        <p>Donations made through Zwiebelfreunde e.V. are tax-deductible in Germany and other countries that recognize
-        German charitable clubs. Feel free to use the Subject field to provide a name to be credited and a list of TODO
-        list items you are interested in the most. For example: Max Mustermann: #16, #1, #14.</p>
-        <p>Note that donations made through Zwiebelfreunde e.V. currently can't be checked automatically so you may not
-        get credited right away. The credits currently reflect donations received before 2016-01-14.</p>
         <p>If you have any questions regarding donations please mail to either the public user mailing list or, if it's
         a private matter, to <a href="mailto:fk@fabiankeil.de" target="_top">Fabian Keil</a> (Privoxy's SPI liaison)
         directly.</p>
index 5c429dd..c576a21 100644 (file)
             me. Please list some of these <span class="QUOTE">"actions"</span>.</a></dt>
             <dt>3.3. <a href="configuration.html#ACTCONFIG">How are actions files configured? What is the easiest way
             to do this?</a></dt>
-            <dt>3.4. <a href="configuration.html#AEN417">There are several different <span class=
+            <dt>3.4. <a href="configuration.html#AEN411">There are several different <span class=
             "QUOTE">"actions"</span> files. What are the differences?</a></dt>
             <dt>3.5. <a href="configuration.html#GETUPDATES">Where can I get updated Actions Files?</a></dt>
             <dt>3.6. <a href="configuration.html#NEWCONFIG">Can I use my old config files?</a></dt>
         <dt>7. <a href="copyright.html">Privoxy Copyright, License and History</a></dt>
         <dd>
           <dl>
-            <dt>7.1. <a href="copyright.html#AEN1504">License</a></dt>
-            <dt>7.2. <a href="copyright.html#AEN1517">History</a></dt>
+            <dt>7.1. <a href="copyright.html#AEN1498">License</a></dt>
+            <dt>7.2. <a href="copyright.html#AEN1512">History</a></dt>
           </dl>
         </dd>
       </dl>
index d1b6567..68c0b5e 100644 (file)
@@ -73,7 +73,7 @@
         <p>The default profiles, and their associated actions, as pre-defined in <tt class=
         "FILENAME">default.action</tt> are:</p>
         <div class="TABLE">
-          <a name="AEN3087" id="AEN3087"></a>
+          <a name="AEN3124" id="AEN3124"></a>
           <p><b>Table 1. Default Configurations</b></p>
           <table border="1" frame="border" rules="all" class="CALSTABLE">
             <col width="1*" title="C1">
@@ -2531,6 +2531,7 @@ nasty-banner-server.example.com/junk.cgi\?output=trash</pre>
               <p>Note that the action has to be enabled based on the CONNECT request which doesn't contain a path.
               Enabling it based on a pattern with path doesn't work as the path is only seen by <span class=
               "APPLICATION">Privoxy</span> if the action is already enabled.</p>
+              <p>This is an experimental feature.</p>
             </dd>
             <dt>Example usage (section):</dt>
             <dd>
index 60324e0..d809b3e 100644 (file)
       these. If not, you will get a friendly error message. Internet access is not necessary either.</p>
       <ul>
         <li>
-          <p>Privoxy main page:</p><a name="AEN6286" id="AEN6286"></a>
+          <p>Privoxy main page:</p><a name="AEN6325" id="AEN6325"></a>
           <blockquote class="BLOCKQUOTE">
             <p><a href="http://config.privoxy.org/" target="_top">http://config.privoxy.org/</a></p>
           </blockquote>
           "APPLICATION">Privoxy</span>)</p>
         </li>
         <li>
-          <p>View and toggle client tags:</p><a name="AEN6294" id="AEN6294"></a>
+          <p>View and toggle client tags:</p><a name="AEN6333" id="AEN6333"></a>
           <blockquote class="BLOCKQUOTE">
             <p><a href="http://config.privoxy.org/client-tags" target=
             "_top">http://config.privoxy.org/client-tags</a></p>
         </li>
         <li>
           <p>Show information about the current configuration, including viewing and editing of actions
-          files:</p><a name="AEN6299" id="AEN6299"></a>
+          files:</p><a name="AEN6338" id="AEN6338"></a>
           <blockquote class="BLOCKQUOTE">
             <p><a href="http://config.privoxy.org/show-status" target=
             "_top">http://config.privoxy.org/show-status</a></p>
           </blockquote>
         </li>
         <li>
-          <p>Show the browser's request headers:</p><a name="AEN6304" id="AEN6304"></a>
+          <p>Show the browser's request headers:</p><a name="AEN6343" id="AEN6343"></a>
           <blockquote class="BLOCKQUOTE">
             <p><a href="http://config.privoxy.org/show-request" target=
             "_top">http://config.privoxy.org/show-request</a></p>
           </blockquote>
         </li>
         <li>
-          <p>Show which actions apply to a URL and why:</p><a name="AEN6309" id="AEN6309"></a>
+          <p>Show which actions apply to a URL and why:</p><a name="AEN6348" id="AEN6348"></a>
           <blockquote class="BLOCKQUOTE">
             <p><a href="http://config.privoxy.org/show-url-info" target=
             "_top">http://config.privoxy.org/show-url-info</a></p>
         <li>
           <p>Toggle Privoxy on or off. This feature can be turned off/on in the main <tt class="FILENAME">config</tt>
           file. When toggled <span class="QUOTE">"off"</span>, <span class="QUOTE">"Privoxy"</span> continues to run,
-          but only as a pass-through proxy, with no actions taking place:</p><a name="AEN6317" id="AEN6317"></a>
+          but only as a pass-through proxy, with no actions taking place:</p><a name="AEN6356" id="AEN6356"></a>
           <blockquote class="BLOCKQUOTE">
             <p><a href="http://config.privoxy.org/toggle" target="_top">http://config.privoxy.org/toggle</a></p>
           </blockquote>
-          <p>Short cuts. Turn off, then on:</p><a name="AEN6321" id="AEN6321"></a>
+          <p>Short cuts. Turn off, then on:</p><a name="AEN6360" id="AEN6360"></a>
           <blockquote class="BLOCKQUOTE">
             <p><a href="http://config.privoxy.org/toggle?set=disable" target=
             "_top">http://config.privoxy.org/toggle?set=disable</a></p>
-          </blockquote><a name="AEN6324" id="AEN6324"></a>
+          </blockquote><a name="AEN6363" id="AEN6363"></a>
           <blockquote class="BLOCKQUOTE">
             <p><a href="http://config.privoxy.org/toggle?set=enable" target=
             "_top">http://config.privoxy.org/toggle?set=enable</a></p>
index 83c92b8..016c04a 100644 (file)
               hides the <span class="QUOTE">"go there anyway"</span> link. If the user adds the force prefix by hand,
               it will not be accepted and the circumvention attempt is logged.</p>
             </dd>
-            <dt>Examples:</dt>
+            <dt>Example:</dt>
             <dd>
               <p>enforce-blocks 1</p>
             </dd>
               you try again manually. Start with a small value and check Privoxy's logfile from time to time, to see
               how many retries are usually needed.</p>
             </dd>
-            <dt>Examples:</dt>
+            <dt>Example:</dt>
             <dd>
               <p>forwarded-connect-retries 1</p>
             </dd>
               you may want to adjust the CGI templates to make sure they don't reference content from
               config.privoxy.org.</p>
             </dd>
-            <dt>Examples:</dt>
+            <dt>Example:</dt>
             <dd>
               <p>accept-intercepted-requests 1</p>
             </dd>
               done without care.</p>
               <p>Don't enable this option unless you're sure that you really need it.</p>
             </dd>
-            <dt>Examples:</dt>
+            <dt>Example:</dt>
             <dd>
               <p>allow-cgi-request-crunching 1</p>
             </dd>
               <p>If you don't notice any editing problems, there is no reason to enable this option, but if one of the
               submit buttons appears to be broken, you should give it a try.</p>
             </dd>
-            <dt>Examples:</dt>
+            <dt>Example:</dt>
             <dd>
               <p>split-large-forms 1</p>
             </dd>
               increasing it to 300 seconds or even more if you think your browser can handle it. If your browser
               appears to be hanging, it probably can't.</p>
             </dd>
-            <dt>Examples:</dt>
+            <dt>Example:</dt>
             <dd>
               <p>keep-alive-timeout 300</p>
             </dd>
               <p>If you are seeing problems with pages not properly loading, disabling this option could work around
               the problem.</p>
             </dd>
-            <dt>Examples:</dt>
+            <dt>Example:</dt>
             <dd>
               <p>tolerate-pipelining 1</p>
             </dd>
               <p>This option has no effect if <span class="APPLICATION">Privoxy</span> has been compiled without
               keep-alive support.</p>
             </dd>
-            <dt>Examples:</dt>
+            <dt>Example:</dt>
             <dd>
               <p>default-server-timeout 60</p>
             </dd>
               <p>This option should only be used by experienced users who understand the risks and can weight them
               against the benefits.</p>
             </dd>
-            <dt>Examples:</dt>
+            <dt>Example:</dt>
             <dd>
               <p>connection-sharing 1</p>
             </dd>
               <p>The default is quite high and you probably want to reduce it. If you aren't using an occasionally slow
               proxy like Tor, reducing it to a few seconds should be fine.</p>
             </dd>
-            <dt>Examples:</dt>
+            <dt>Example:</dt>
             <dd>
               <p>socket-timeout 300</p>
             </dd>
               reached. This will likely change in a future version, but currently this limit can't be increased without
               recompiling <span class="APPLICATION">Privoxy</span> with a different FD_SETSIZE limit.</p>
             </dd>
-            <dt>Examples:</dt>
+            <dt>Example:</dt>
             <dd>
               <p>max-client-connections 256</p>
             </dd>
               <p>Effectively using a value above 128 usually requires changing the system configuration as well. On
               FreeBSD-based system the limit is controlled by the kern.ipc.soacceptqueue sysctl.</p>
             </dd>
-            <dt>Examples:</dt>
+            <dt>Example:</dt>
             <dd>
               <p>listen-backlog 4096</p>
             </dd>
               "https://www.freebsd.org/cgi/man.cgi?query=accf_http" target="_top">accf_http(9) man page</a> to learn
               how to enable the support in the operating system.</p>
             </dd>
-            <dt>Examples:</dt>
+            <dt>Example:</dt>
             <dd>
               <p>enable-accept-filter 1</p>
             </dd>
               "_top">http://config.privoxy.org/client-tags</a> therefore provides a "enable this tag temporarily"
               option. If it is used, the tag will be set until the client-tag-lifetime is over.</p>
             </dd>
-            <dt>Examples:</dt>
+            <dt>Example:</dt>
             <dd>
               <table border="0" bgcolor="#E0E0E0" width="90%">
                 <tr>
               change the client tags for other clients or increase Privoxy's memory requirements by registering lots of
               client tag settings for clients that don't exist.</p>
             </dd>
-            <dt>Examples:</dt>
+            <dt>Example:</dt>
             <dd>
               <table border="0" bgcolor="#E0E0E0" width="90%">
                 <tr>
               memory is (currently) cleared before using it, a buffer that is too large can actually reduce the
               throughput.</p>
             </dd>
-            <dt>Examples:</dt>
+            <dt>Example:</dt>
             <dd>
               <table border="0" bgcolor="#E0E0E0" width="90%">
                 <tr>
       </div>
     </div>
     <div class="SECT2">
-      <h2 class="SECT2"><a name="TLS" id="TLS">7.7. TLS/SSL Inspection</a></h2>
+      <h2 class="SECT2"><a name="TLS" id="TLS">7.7. TLS/SSL Inspection (Experimental)</a></h2>
       <div class="SECT3">
         <h4 class="SECT3"><a name="CA-DIRECTORY" id="CA-DIRECTORY">7.7.1. ca-directory</a></h4>
         <div class="VARIABLELIST">
               <p>The permissions should only let <span class="APPLICATION">Privoxy</span> and the <span class=
               "APPLICATION">Privoxy</span> admin access the directory.</p>
             </dd>
-            <dt>Examples:</dt>
+            <dt>Example:</dt>
             <dd>
               <p>ca-directory /usr/local/etc/privoxy/CA</p>
             </dd>
               <p>The file can be generated with: openssl req -new -x509 -extensions v3_ca -keyout cakey.pem -out
               cacert.crt -days 3650</p>
             </dd>
-            <dt>Examples:</dt>
+            <dt>Example:</dt>
             <dd>
               <p>ca-cert-file root.crt</p>
             </dd>
               <p>This directive specifies the name of the CA key file in ".pem" format. See the <a href="#CA-CERT-FILE"
               target="_top">ca-cert-file</a> for a command to generate it.</p>
             </dd>
-            <dt>Examples:</dt>
+            <dt>Example:</dt>
             <dd>
               <p>ca-key-file cakey.pem</p>
             </dd>
               certificates for intercepted requests.</p>
               <p>Note that the password is shown on the CGI page so don't reuse an important one.</p>
             </dd>
-            <dt>Examples:</dt>
+            <dt>Example:</dt>
             <dd>
               <p>ca-password blafasel</p>
             </dd>
               "_top">ca-cert-key</a>.</p>
               <p>The permissions should only let <span class="APPLICATION">Privoxy</span> and the <span class=
               "APPLICATION">Privoxy</span> admin access the directory.</p>
+              <div class="WARNING">
+                <table class="WARNING" border="1" width="90%">
+                  <tr>
+                    <td align="center"><b>Warning</b></td>
+                  </tr>
+                  <tr>
+                    <td align="left">
+                      <p><span class="APPLICATION">Privoxy</span> currently does not garbage-collect obsolete keys and
+                      certificates and does not keep track of how may keys and certificates exist.</p>
+                      <p><span class="APPLICATION">Privoxy</span> admins should monitor the size of the directory
+                      and/or make sure there is sufficient space available. A cron job to limit the number of keys and
+                      certificates to a certain number may be worth considering.</p>
+                    </td>
+                  </tr>
+                </table>
+              </div>
             </dd>
-            <dt>Examples:</dt>
+            <dt>Example:</dt>
             <dd>
               <p>certificate-directory /usr/local/var/privoxy/certs</p>
             </dd>
         </div>
       </div>
       <div class="SECT3">
-        <h4 class="SECT3"><a name="TRUSTED-CAS-FILE" id="TRUSTED-CAS-FILE">7.7.6. trusted-cas-file</a></h4>
+        <h4 class="SECT3"><a name="CIPHER-LIST" id="CIPHER-LIST">7.7.6. cipher-list</a></h4>
+        <div class="VARIABLELIST">
+          <dl>
+            <dt>Specifies:</dt>
+            <dd>
+              <p>A list of ciphers to use in TLS handshakes</p>
+            </dd>
+            <dt>Type of value:</dt>
+            <dd>
+              <p>Text</p>
+            </dd>
+            <dt>Default value:</dt>
+            <dd>
+              <p>None</p>
+            </dd>
+            <dt>Effect if unset:</dt>
+            <dd>
+              <p>A default value is inherited from the TLS library.</p>
+            </dd>
+            <dt>Notes:</dt>
+            <dd>
+              <p>This directive allows to specify a non-default list of ciphers to use in TLS handshakes with clients
+              and servers.</p>
+              <p>Ciphers are separated by colons. Which ciphers are supported depends on the TLS library. When using
+              OpenSSL, unsupported ciphers are skipped. When using MbedTLS they are rejected.</p>
+              <div class="WARNING">
+                <table class="WARNING" border="1" width="90%">
+                  <tr>
+                    <td align="center"><b>Warning</b></td>
+                  </tr>
+                  <tr>
+                    <td align="left">
+                      <p>Specifying an unusual cipher list makes fingerprinting easier. Note that the default list
+                      provided by the TLS library may be unusual when compared to the one used by modern browsers as
+                      well.</p>
+                    </td>
+                  </tr>
+                </table>
+              </div>
+            </dd>
+            <dt>Examples:</dt>
+            <dd>
+              <table border="0" bgcolor="#E0E0E0" width="90%">
+                <tr>
+                  <td>
+                    <pre class="SCREEN">    # Explicitly set a couple of ciphers with names used by MbedTLS
+    cipher-list cipher-list TLS-ECDHE-RSA-WITH-CHACHA20-POLY1305-SHA256:\
+TLS-ECDHE-ECDSA-WITH-CHACHA20-POLY1305-SHA256:\
+TLS-DHE-RSA-WITH-CHACHA20-POLY1305-SHA256:\
+TLS-ECDHE-ECDSA-WITH-AES-128-GCM-SHA256:\
+TLS-ECDHE-ECDSA-WITH-AES-256-GCM-SHA384:\
+TLS-ECDHE-ECDSA-WITH-AES-256-CCM:\
+TLS-ECDHE-ECDSA-WITH-AES-256-CCM-8:\
+TLS-ECDHE-ECDSA-WITH-AES-128-CCM:\
+TLS-ECDHE-ECDSA-WITH-AES-128-CCM-8:\
+TLS-ECDHE-ECDSA-WITH-CAMELLIA-128-GCM-SHA256:\
+TLS-ECDHE-ECDSA-WITH-CAMELLIA-256-GCM-SHA384:\
+TLS-ECDHE-RSA-WITH-AES-128-GCM-SHA256:\
+TLS-ECDHE-RSA-WITH-AES-256-GCM-SHA384:\
+TLS-ECDHE-RSA-WITH-CAMELLIA-128-GCM-SHA256:\
+TLS-ECDHE-RSA-WITH-CAMELLIA-256-GCM-SHA384:\
+TLS-DHE-RSA-WITH-AES-256-GCM-SHA384:\
+TLS-DHE-RSA-WITH-AES-128-GCM-SHA256:\
+TLS-DHE-RSA-WITH-AES-256-CCM:\
+TLS-DHE-RSA-WITH-AES-256-CCM-8:\
+TLS-DHE-RSA-WITH-AES-128-CCM:\
+TLS-DHE-RSA-WITH-AES-128-CCM-8:\
+TLS-DHE-RSA-WITH-CAMELLIA-128-GCM-SHA256:\
+TLS-DHE-RSA-WITH-CAMELLIA-256-GCM-SHA384:\
+TLS-ECDH-RSA-WITH-AES-128-GCM-SHA256:\
+TLS-ECDH-RSA-WITH-AES-256-GCM-SHA384:\
+TLS-ECDH-RSA-WITH-CAMELLIA-128-GCM-SHA256:\
+TLS-ECDH-RSA-WITH-CAMELLIA-256-GCM-SHA384:\
+TLS-ECDH-ECDSA-WITH-AES-128-GCM-SHA256:\
+TLS-ECDH-ECDSA-WITH-AES-256-GCM-SHA384:\
+TLS-ECDH-ECDSA-WITH-CAMELLIA-128-GCM-SHA256:\
+TLS-ECDH-ECDSA-WITH-CAMELLIA-256-GCM-SHA384
+   </pre>
+                  </td>
+                </tr>
+              </table>
+              <table border="0" bgcolor="#E0E0E0" width="90%">
+                <tr>
+                  <td>
+                    <pre class="SCREEN">    # Explicitly set a couple of ciphers with names used by OpenSSL
+cipher-list ECDHE-RSA-AES256-GCM-SHA384:\
+ECDHE-ECDSA-AES256-GCM-SHA384:\
+DH-DSS-AES256-GCM-SHA384:\
+DHE-DSS-AES256-GCM-SHA384:\
+DH-RSA-AES256-GCM-SHA384:\
+DHE-RSA-AES256-GCM-SHA384:\
+ECDH-RSA-AES256-GCM-SHA384:\
+ECDH-ECDSA-AES256-GCM-SHA384:\
+ECDHE-RSA-AES128-GCM-SHA256:\
+ECDHE-ECDSA-AES128-GCM-SHA256:\
+DH-DSS-AES128-GCM-SHA256:\
+DHE-DSS-AES128-GCM-SHA256:\
+DH-RSA-AES128-GCM-SHA256:\
+DHE-RSA-AES128-GCM-SHA256:\
+ECDH-RSA-AES128-GCM-SHA256:\
+ECDH-ECDSA-AES128-GCM-SHA256:\
+ECDHE-RSA-AES256-GCM-SHA384:\
+AES128-SHA
+   </pre>
+                  </td>
+                </tr>
+              </table>
+              <table border="0" bgcolor="#E0E0E0" width="90%">
+                <tr>
+                  <td>
+                    <pre class=
+                    "SCREEN">    # Use keywords instead of explicity naming the ciphers (Does not work with MbedTLS)
+    cipher-list ALL:!EXPORT:!EXPORT40:!EXPORT56:!aNULL:!LOW:!RC4:@STRENGTH
+   </pre>
+                  </td>
+                </tr>
+              </table>
+            </dd>
+          </dl>
+        </div>
+      </div>
+      <div class="SECT3">
+        <h4 class="SECT3"><a name="TRUSTED-CAS-FILE" id="TRUSTED-CAS-FILE">7.7.7. trusted-cas-file</a></h4>
         <div class="VARIABLELIST">
           <dl>
             <dt>Specifies:</dt>
               <p>An example file can be downloaded from <a href="https://curl.haxx.se/ca/cacert.pem" target=
               "_top">https://curl.haxx.se/ca/cacert.pem</a>.</p>
             </dd>
-            <dt>Examples:</dt>
+            <dt>Example:</dt>
             <dd>
               <p>trusted-cas-file trusted_cas_file.pem</p>
             </dd>
index 0dd6d07..8460cb1 100644 (file)
@@ -52,7 +52,7 @@
                 <tr>
                   <td>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&squf;&nbsp;&nbsp;<a href=
                   "http://config.privoxy.org/client-tags" target="_top">View or toggle the tags that can be set based
-                  on the clients address</a></td>
+                  on the client's address</a></td>
                 </tr>
                 <tr>
                   <td>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&squf;&nbsp;&nbsp;<a href=
index a455bb4..647a0fd 100644 (file)
     <p><span class="APPLICATION">Privoxy</span> is free software; you can redistribute and/or modify its source code
     under the terms of the <i class="CITETITLE">GNU General Public License</i> as published by the Free Software
     Foundation, either version 2 of the license, or (at your option) any later version.</p>
-    <p>The same is true for <span class="APPLICATION">Privoxy</span> binaries unless they are linked with <a href=
-    "https://tls.mbed.org/" target="_top">mbed TLS</a> in which case you can redistribute them and/or modify them under
-    the terms of the <i class="CITETITLE">GNU General Public License</i> as published by the Free Software Foundation,
-    either version 3 of the license, or (at your option) any later version.</p>
+    <p>The same is true for <span class="APPLICATION">Privoxy</span> binaries unless they are linked with a <a href=
+    "https://tls.mbed.org/" target="_top">mbed TLS</a> version that is licensed under the Apache 2.0 license in which
+    case you can redistribute and/or modify the <span class="APPLICATION">Privoxy</span> binaries under the terms of
+    the <i class="CITETITLE">GNU General Public License</i> as published by the Free Software Foundation, either
+    version 3 of the license, or (at your option) any later version.</p>
     <p>Both licenses are included in the next section.</p>
     <div class="SECT2">
       <h2 class="SECT2"><a name="LICENSE">12.1. License</a></h2>
@@ -1183,6 +1184,7 @@ Public License instead of this License.  But first, please read
       &nbsp;Magnus&nbsp;Holmgren<br>
       &nbsp;Eric&nbsp;M.&nbsp;Hopper<br>
       &nbsp;Ralf&nbsp;Horstmann<br>
+      &nbsp;Ho+&nbsp;Ho+&nbsp;Ho+<br>
       &nbsp;Ned&zcaron;ad&nbsp;Hrnjica<br>
       &nbsp;Stefan&nbsp;Huehner<br>
       &nbsp;Basil&nbsp;Hussain<br>
@@ -1256,6 +1258,7 @@ Public License instead of this License.  But first, please read
       &nbsp;J&ouml;rg&nbsp;Weinmann<br>
       &nbsp;Darren&nbsp;Wiebe<br>
       &nbsp;Anduin&nbsp;Withers<br>
+      &nbsp;withoutname<br>
       &nbsp;Eduard&nbsp;Wulff<br>
       &nbsp;Yang&nbsp;Xia<br>
       &nbsp;Jarry&nbsp;Xu<br>
@@ -1266,8 +1269,8 @@ Public License instead of this License.  But first, please read
       <p>Privoxy heavily relies on Philip Hazel's PCRE.</p>
       <p>The code to filter compressed content makes use of zlib which is written by Jean-loup Gailly and Mark
       Adler.</p>
-      <p>On systems that lack snprintf(), Privoxy is using a version written by Mark Martinec. On systems that lack
-      strptime(), Privoxy is using the one from the GNU C Library written by Ulrich Drepper.</p>
+      <p>On systems that lack strptime(), Privoxy is using the one from the GNU C Library written by Ulrich
+      Drepper.</p>
     </div>
   </div>
   <div class="NAVFOOTER">
index eb00d89..082b58a 100644 (file)
                 <dt>7.6.19. <a href="config.html#RECEIVE-BUFFER-SIZE">receive-buffer-size</a></dt>
               </dl>
             </dd>
-            <dt>7.7. <a href="config.html#TLS">TLS/SSL Inspection</a></dt>
+            <dt>7.7. <a href="config.html#TLS">TLS/SSL Inspection (Experimental)</a></dt>
             <dd>
               <dl>
                 <dt>7.7.1. <a href="config.html#CA-DIRECTORY">ca-directory</a></dt>
                 <dt>7.7.3. <a href="config.html#CA-KEY-FILE">ca-key-file</a></dt>
                 <dt>7.7.4. <a href="config.html#CA-PASSWORD">ca-password</a></dt>
                 <dt>7.7.5. <a href="config.html#CERTIFICATE-DIRECTORY">certificate-directory</a></dt>
-                <dt>7.7.6. <a href="config.html#TRUSTED-CAS-FILE">trusted-cas-file</a></dt>
+                <dt>7.7.6. <a href="config.html#CIPHER-LIST">cipher-list</a></dt>
+                <dt>7.7.7. <a href="config.html#TRUSTED-CAS-FILE">trusted-cas-file</a></dt>
               </dl>
             </dd>
             <dt>7.8. <a href="config.html#WINDOWS-GUI">Windows GUI Options</a></dt>
index 13cba16..7b586bc 100644 (file)
--- a/filters.c
+++ b/filters.c
@@ -1671,6 +1671,10 @@ static char *pcrs_filter_response(struct client_state *csp)
     */
    if (!hits)
    {
+      if (old != csp->iob->cur && old != new)
+      {
+         freez(old);
+      }
       freez(new);
       return(NULL);
    }
index 4207cb7..b341ae9 100644 (file)
--- a/gateway.c
+++ b/gateway.c
@@ -6,7 +6,7 @@
  *                using a "forwarder" (i.e. HTTP proxy and/or a SOCKS4
  *                or SOCKS5 proxy).
  *
- * Copyright   :  Written by and Copyright (C) 2001-2017 the
+ * Copyright   :  Written by and Copyright (C) 2001-2020 the
  *                Privoxy team. https://www.privoxy.org/
  *
  *                Based on the Internet Junkbuster originally written
@@ -231,6 +231,8 @@ void remember_connection(const struct reusable_connection *connection)
 
    assert(reusable_connection[slot].gateway_host == NULL);
    assert(reusable_connection[slot].gateway_port == 0);
+   assert(reusable_connection[slot].auth_username == NULL);
+   assert(reusable_connection[slot].auth_password == NULL);
    assert(reusable_connection[slot].forwarder_type == SOCKS_NONE);
    assert(reusable_connection[slot].forward_host == NULL);
    assert(reusable_connection[slot].forward_port == 0);
@@ -245,6 +247,22 @@ void remember_connection(const struct reusable_connection *connection)
       reusable_connection[slot].gateway_host = NULL;
    }
    reusable_connection[slot].gateway_port = connection->gateway_port;
+   if (NULL != connection->auth_username)
+   {
+      reusable_connection[slot].auth_username = strdup_or_die(connection->auth_username);
+   }
+   else
+   {
+      reusable_connection[slot].auth_username = NULL;
+   }
+   if (NULL != connection->auth_password)
+   {
+      reusable_connection[slot].auth_password = strdup_or_die(connection->auth_password);
+   }
+   else
+   {
+      reusable_connection[slot].auth_password = NULL;
+   }
 
    if (NULL != connection->forward_host)
    {
@@ -287,6 +305,8 @@ void mark_connection_closed(struct reusable_connection *closed_connection)
    closed_connection->forwarder_type = SOCKS_NONE;
    freez(closed_connection->gateway_host);
    closed_connection->gateway_port = 0;
+   freez(closed_connection->auth_username);
+   freez(closed_connection->auth_password);
    freez(closed_connection->forward_host);
    closed_connection->forward_port = 0;
 }
@@ -336,6 +356,62 @@ void forget_connection(jb_socket sfd)
 
 
 #ifdef FEATURE_CONNECTION_KEEP_ALIVE
+/*********************************************************************
+ *
+ * Function    :  string_or_none
+ *
+ * Description :  Returns a given string or "none" if a NULL pointer
+ *                is given.
+ *                Helper function for connection_destination_matches().
+ *
+ * Parameters  :
+ *          1  :  string = The string to check.
+ *
+ * Returns     :  The string if non-NULL, "none" otherwise.
+ *
+ *********************************************************************/
+static const char *string_or_none(const char *string)
+{
+   return(string != NULL ? string : "none");
+}
+
+
+/*********************************************************************
+ *
+ * Function    :  connection_detail_matches
+ *
+ * Description :  Helper function for connection_destination_matches().
+ *                Compares strings which can be NULL.
+ *
+ * Parameters  :
+ *          1  :  connection_detail = The connection detail to compare.
+ *          2  :  fowarder_detail = The forwarder detail to compare.
+ *
+ * Returns     :  TRUE for yes, FALSE otherwise.
+ *
+ *********************************************************************/
+static int connection_detail_matches(const char *connection_detail,
+                                     const char *forwarder_detail)
+{
+   if (connection_detail == NULL && forwarder_detail == NULL)
+   {
+      /* Both details are unset. */
+      return TRUE;
+   }
+
+   if ((connection_detail == NULL && forwarder_detail != NULL)
+    || (connection_detail != NULL && forwarder_detail == NULL))
+   {
+      /* Only one detail isn't set. */
+      return FALSE;
+   }
+
+   /* Both details are set, but do they match? */
+   return(!strcmpic(connection_detail, forwarder_detail));
+
+}
+
+
 /*********************************************************************
  *
  * Function    :  connection_destination_matches
@@ -364,25 +440,39 @@ int connection_destination_matches(const struct reusable_connection *connection,
       return FALSE;
    }
 
-   if ((    (NULL != connection->gateway_host)
-         && (NULL != fwd->gateway_host)
-         && strcmpic(connection->gateway_host, fwd->gateway_host))
-       && (connection->gateway_host != fwd->gateway_host))
+   if (!connection_detail_matches(connection->gateway_host, fwd->gateway_host))
    {
       log_error(LOG_LEVEL_CONNECT,
          "Gateway mismatch. Previous gateway: %s. Current gateway: %s",
-         connection->gateway_host, fwd->gateway_host);
+         string_or_none(connection->gateway_host),
+         string_or_none(fwd->gateway_host));
+      return FALSE;
+   }
+
+   if (!connection_detail_matches(connection->auth_username, fwd->auth_username))
+   {
+      log_error(LOG_LEVEL_CONNECT, "Socks user name mismatch. "
+         "Previous user name: %s. Current user name: %s",
+         string_or_none(connection->auth_username),
+         string_or_none(fwd->auth_username));
+      return FALSE;
+   }
+
+   if (!connection_detail_matches(connection->auth_password, fwd->auth_password))
+   {
+      log_error(LOG_LEVEL_CONNECT, "Socks user name mismatch. "
+         "Previous password: %s. Current password: %s",
+         string_or_none(connection->auth_password),
+         string_or_none(fwd->auth_password));
       return FALSE;
    }
 
-   if ((    (NULL != connection->forward_host)
-         && (NULL != fwd->forward_host)
-         && strcmpic(connection->forward_host, fwd->forward_host))
-      && (connection->forward_host != fwd->forward_host))
+   if (!connection_detail_matches(connection->forward_host, fwd->forward_host))
    {
       log_error(LOG_LEVEL_CONNECT,
          "Forwarding proxy mismatch. Previous proxy: %s. Current proxy: %s",
-         connection->forward_host, fwd->forward_host);
+         string_or_none(connection->forward_host),
+         string_or_none(fwd->forward_host));
       return FALSE;
    }
 
diff --git a/jcc.c b/jcc.c
index 581768f..2a8c166 100644 (file)
--- a/jcc.c
+++ b/jcc.c
@@ -559,8 +559,6 @@ static int client_has_unsupported_expectations(const struct client_state *csp)
  *********************************************************************/
 static jb_err get_request_destination_elsewhere(struct client_state *csp, struct list *headers)
 {
-   char *req;
-
    if (!(csp->config->feature_flags & RUNTIME_FEATURE_ACCEPT_INTERCEPTED_REQUESTS))
    {
       log_error(LOG_LEVEL_ERROR, "%s's request: \'%s\' is invalid."
@@ -587,15 +585,12 @@ static jb_err get_request_destination_elsewhere(struct client_state *csp, struct
    {
       /* We can't work without destination. Go spread the news.*/
 
-      req = list_to_text(headers);
-      chomp(req);
       /* XXX: Use correct size */
       log_error(LOG_LEVEL_CLF, "%s - - [%T] \"%s\" 400 0",
          csp->ip_addr_str, csp->http->cmd);
       log_error(LOG_LEVEL_ERROR,
-         "Privoxy was unable to get the destination for %s's request:\n%s\n%s",
-         csp->ip_addr_str, csp->http->cmd, req);
-      freez(req);
+         "Privoxy was unable to get the destination for %s's request: %s",
+         csp->ip_addr_str, csp->http->cmd);
 
       write_socket_delayed(csp->cfd, MISSING_DESTINATION_RESPONSE,
          strlen(MISSING_DESTINATION_RESPONSE), get_write_delay(csp));
@@ -1176,6 +1171,22 @@ void save_connection_destination(jb_socket sfd,
       server_connection->gateway_host = NULL;
    }
    server_connection->gateway_port = fwd->gateway_port;
+   if (NULL != fwd->auth_username)
+   {
+      server_connection->auth_username = strdup_or_die(fwd->auth_username);
+   }
+   else
+   {
+      server_connection->auth_username = NULL;
+   }
+   if (NULL != fwd->auth_password)
+   {
+      server_connection->auth_password = strdup_or_die(fwd->auth_password);
+   }
+   else
+   {
+      server_connection->auth_password = NULL;
+   }
 
    if (NULL != fwd->forward_host)
    {
@@ -2152,7 +2163,7 @@ static int send_https_request(struct client_state *csp)
          csp->http->hostport);
       return 1;
    }
-   if (flushed != 0)
+   if (flushed != 0 || csp->expected_client_content_length != 0)
    {
       if (csp->expected_client_content_length != 0)
       {
@@ -2276,7 +2287,8 @@ static jb_err process_encrypted_request(struct client_state *csp)
    err = receive_encrypted_request(csp);
    if (err != JB_ERR_OK)
    {
-      if (csp->client_iob->cur == NULL)
+      if (csp->client_iob->cur == NULL ||
+          csp->client_iob->cur == csp->client_iob->eod)
       {
          /*
           * We did not receive any data, most likely because the
@@ -2824,6 +2836,37 @@ static void handle_established_connection(struct client_state *csp)
 #ifdef FEATURE_HTTPS_INSPECTION
          if (client_use_ssl(csp))
          {
+            if (csp->http->status == 101)
+            {
+               len = ssl_recv_data(&(csp->ssl_client_attr),
+                  (unsigned char *)csp->receive_buffer,
+                  (size_t)max_bytes_to_read);
+               if (len == -1)
+               {
+                  log_error(LOG_LEVEL_ERROR, "Failed to receive data "
+                     "on client socket %d for an upgraded connection",
+                     csp->cfd);
+                  break;
+               }
+               if (len == 0)
+               {
+                  log_error(LOG_LEVEL_CONNECT, "Done receiving data "
+                     "on client socket %d for an upgraded connection",
+                     csp->cfd);
+                  break;
+               }
+               byte_count += (unsigned long long)len;
+               len = ssl_send_data(&(csp->ssl_server_attr),
+                  (unsigned char *)csp->receive_buffer, (size_t)len);
+               if (len == -1)
+               {
+                  log_error(LOG_LEVEL_ERROR, "Failed to send data "
+                     "on server socket %d for an upgraded connection",
+                     csp->server_connection.sfd);
+                  break;
+               }
+               continue;
+            }
             log_error(LOG_LEVEL_CONNECT, "Breaking with TLS/SSL.");
             break;
          }
@@ -4102,10 +4145,12 @@ static void chat(struct client_state *csp)
       else
       {
          /*
-          * If server certificate is invalid, we must inform client and then
-          * close connection with client.
+          * If server certificate has been verified and is invalid,
+          * we must inform the client and then close the connection
+          * with client and server.
           */
-         if (csp->server_cert_verification_result != SSL_CERT_VALID)
+         if (csp->server_cert_verification_result != SSL_CERT_VALID &&
+             csp->server_cert_verification_result != SSL_CERT_NOT_VERIFIED)
          {
             ssl_send_certificate_error(csp);
             close_client_and_server_ssl_connections(csp);
@@ -4487,6 +4532,20 @@ static void serve(struct client_state *csp)
    chat(csp);
 #endif /* def FEATURE_CONNECTION_KEEP_ALIVE */
 
+   if (csp->cfd != JB_INVALID_SOCKET)
+   {
+      log_error(LOG_LEVEL_CONNECT, "Closing client socket %d. "
+         "Keep-alive: %u. Socket alive: %u. Data available: %u. "
+         "Configuration file change detected: %u. Requests received: %u.",
+         csp->cfd, 0 != (csp->flags & CSP_FLAG_CLIENT_CONNECTION_KEEP_ALIVE),
+         socket_is_still_alive(csp->cfd), data_is_available(csp->cfd, 0),
+         config_file_change_detected, csp->requests_received_total);
+#ifdef FEATURE_HTTPS_INSPECTION
+      close_client_ssl_connection(csp);
+#endif
+      drain_and_close_socket(csp->cfd);
+   }
+
    if (csp->server_connection.sfd != JB_INVALID_SOCKET)
    {
 #ifdef FEATURE_CONNECTION_SHARING
@@ -4507,20 +4566,6 @@ static void serve(struct client_state *csp)
    mark_connection_closed(&csp->server_connection);
 #endif
 
-   if (csp->cfd != JB_INVALID_SOCKET)
-   {
-      log_error(LOG_LEVEL_CONNECT, "Closing client socket %d. "
-         "Keep-alive: %u. Socket alive: %u. Data available: %u. "
-         "Configuration file change detected: %u. Requests received: %u.",
-         csp->cfd, 0 != (csp->flags & CSP_FLAG_CLIENT_CONNECTION_KEEP_ALIVE),
-         socket_is_still_alive(csp->cfd), data_is_available(csp->cfd, 0),
-         config_file_change_detected, csp->requests_received_total);
-#ifdef FEATURE_HTTPS_INSPECTION
-      close_client_ssl_connection(csp);
-#endif
-      drain_and_close_socket(csp->cfd);
-   }
-
    free_csp_resources(csp);
 
    csp->flags &= ~CSP_FLAG_ACTIVE;
@@ -5496,7 +5541,7 @@ static void listen_loop(void)
       csp = &csp_list->csp;
 
       log_error(LOG_LEVEL_CONNECT,
-         "Waiting for the next client connection. Currently active threads: %d",
+         "Waiting for the next client connection. Currently active threads: %u",
          active_threads);
 
       /*
@@ -5713,7 +5758,7 @@ static void listen_loop(void)
              * XXX: If you assume ...
              */
             log_error(LOG_LEVEL_ERROR,
-               "Unable to take any additional connections: %E. Active threads: %d",
+               "Unable to take any additional connections: %E. Active threads: %u",
                active_threads);
             write_socket_delayed(csp->cfd, TOO_MANY_CONNECTIONS_RESPONSE,
                strlen(TOO_MANY_CONNECTIONS_RESPONSE), get_write_delay(csp));
index ad15c64..dbed0a3 100644 (file)
--- a/loadcfg.c
+++ b/loadcfg.c
@@ -120,9 +120,8 @@ static struct file_list *current_configfile = NULL;
  * This takes the "cryptic" hash of each keyword and aliases them to
  * something a little more readable.  This also makes changing the
  * hash values easier if they should change or the hash algorithm changes.
- * Use the included "hash" program to find out what the hash will be
- * for any string supplied on the command line.  (Or just put it in the
- * config file and read the number from the error message in the log).
+ * To find out the hash for a new directive put it in the config file
+ * and read the number from the error message in the log).
  *
  * Please keep this list sorted alphabetically (but with the Windows
  * console and GUI specific options last).
@@ -138,6 +137,7 @@ static struct file_list *current_configfile = NULL;
 #define hash_ca_key_file                 1184187891U /* "ca-key-file" */
 #define hash_ca_password                 1184543320U /* "ca-password" */
 #define hash_certificate_directory       1367994217U /* "certificate-directory" */
+#define hash_cipher_list                 1225729316U /* "cipher-list" */
 #define hash_client_header_order         2701453514U /* "client-header-order" */
 #define hash_client_specific_tag         3353703383U /* "client-specific-tag" */
 #define hash_client_tag_lifetime          647957580U /* "client-tag-lifetime" */
@@ -281,6 +281,7 @@ static void unload_configfile (void * data)
    freez(config->ca_cert_file);
    freez(config->ca_key_file);
    freez(config->certificate_directory);
+   freez(config->cipher_list);
    freez(config->trusted_cas_file);
 #endif
 
@@ -1796,6 +1797,15 @@ struct configuration_spec * load_config(void)
 
             break;
 
+/* *************************************************************************
+ * cipher-list list-of-ciphers
+ * *************************************************************************/
+         case hash_cipher_list:
+            freez(config->cipher_list);
+            config->cipher_list = strdup_or_die(arg);
+
+            break;
+
 /* *************************************************************************
  * trusted CAs file name trusted-cas-file
  * *************************************************************************/
index 499579f..9d1226b 100644 (file)
@@ -560,6 +560,43 @@ char *string_toupper(const char *string)
 }
 
 
+/*********************************************************************
+ *
+ * Function    :  string_tolower
+ *
+ * Description :  Produce a copy of string with all convertible
+ *                characters converted to lowercase.
+ *
+ * Parameters  :
+ *          1  :  string = string to convert
+ *
+ * Returns     :  Lowercase copy of string if possible,
+ *                NULL on out-of-memory or if string was NULL.
+ *
+ *********************************************************************/
+char *string_tolower(const char *string)
+{
+   char *result, *p;
+   const char *q;
+
+   if (!string || ((result = (char *)zalloc(strlen(string) + 1)) == NULL))
+   {
+      return NULL;
+   }
+
+   q = string;
+   p = result;
+
+   while (*q != '\0')
+   {
+      *p++ = (char)privoxy_tolower(*q++);
+   }
+
+   return result;
+
+}
+
+
 /*********************************************************************
  *
  * Function    :  string_move
index 04050f0..7c5f7df 100644 (file)
@@ -61,6 +61,7 @@ extern int strncmpic(const char *s1, const char *s2, size_t n);
 extern jb_err string_append(char **target_string, const char *text_to_append);
 extern jb_err string_join  (char **target_string,       char *text_to_append);
 extern char *string_toupper(const char *string);
+extern char *string_tolower(const char *string);
 extern void string_move(char *dst, char *src);
 
 extern char *chomp(char *string);
index 56dc52a..2c065cc 100644 (file)
--- a/openssl.c
+++ b/openssl.c
@@ -55,7 +55,7 @@
 #define CERTIFICATE_AUTHORITY_KEY                "keyid:always"
 #define CERTIFICATE_ALT_NAME_PREFIX              "DNS:"
 #define CERTIFICATE_VERSION                      2
-#define VALID_DATETIME_FMT                       "%Y%m%d%H%M%SZ"
+#define VALID_DATETIME_FMT                       "%y%m%d%H%M%SZ"
 #define VALID_DATETIME_BUFLEN                    16
 
 static int generate_webpage_certificate(struct client_state *csp);
@@ -152,19 +152,27 @@ extern size_t is_ssl_pending(struct ssl_attr *ssl_attr)
 extern int ssl_send_data(struct ssl_attr *ssl_attr, const unsigned char *buf, size_t len)
 {
    BIO *bio = ssl_attr->openssl_attr.bio;
+   SSL *ssl;
    int ret = 0;
    int pos = 0; /* Position of unsent part in buffer */
+   int fd = -1;
 
    if (len == 0)
    {
       return 0;
    }
 
+   if (BIO_get_ssl(bio, &ssl) == 1)
+   {
+      fd = SSL_get_fd(ssl);
+   }
+
    while (pos < len)
    {
       int send_len = (int)len - pos;
 
-      log_error(LOG_LEVEL_WRITING, "TLS: %N", send_len, buf+pos);
+      log_error(LOG_LEVEL_WRITING, "TLS on socket %d: %N",
+         fd, send_len, buf+pos);
 
       /*
        * Sending one part of the buffer
@@ -176,7 +184,7 @@ extern int ssl_send_data(struct ssl_attr *ssl_attr, const unsigned char *buf, si
          if (!BIO_should_retry(bio))
          {
             log_ssl_errors(LOG_LEVEL_ERROR,
-               "Sending data over TLS/SSL failed");
+               "Sending data on socket %d over TLS/SSL failed", fd);
             return -1;
          }
       }
@@ -207,7 +215,10 @@ extern int ssl_send_data(struct ssl_attr *ssl_attr, const unsigned char *buf, si
 extern int ssl_recv_data(struct ssl_attr *ssl_attr, unsigned char *buf, size_t max_length)
 {
    BIO *bio = ssl_attr->openssl_attr.bio;
+   SSL *ssl;
    int ret = 0;
+   int fd = -1;
+
    memset(buf, 0, max_length);
 
    /*
@@ -221,12 +232,18 @@ extern int ssl_recv_data(struct ssl_attr *ssl_attr, unsigned char *buf, size_t m
    if (ret < 0)
    {
       log_ssl_errors(LOG_LEVEL_ERROR,
-         "Receiving data over TLS/SSL failed");
+         "Receiving data on socket %d over TLS/SSL failed", fd);
 
       return -1;
    }
 
-   log_error(LOG_LEVEL_RECEIVED, "TLS: %N", ret, buf);
+   if (BIO_get_ssl(bio, &ssl) == 1)
+   {
+      fd = SSL_get_fd(ssl);
+   }
+
+   log_error(LOG_LEVEL_RECEIVED, "TLS from socket %d: %N",
+      fd, ret, buf);
 
    return ret;
 }
@@ -721,7 +738,7 @@ extern int create_client_ssl_connection(struct client_state *csp)
    char *ca_file   = NULL;
    char *cert_file = NULL;
    int ret = 0;
-   SSLssl;
+   SSL *ssl;
 
    /*
     * Initializing OpenSSL structures for TLS/SSL connection
@@ -820,6 +837,18 @@ extern int create_client_ssl_connection(struct client_state *csp)
       goto exit;
    }
 
+   if (csp->config->cipher_list != NULL)
+   {
+      if (!SSL_set_cipher_list(ssl, csp->config->cipher_list))
+      {
+         log_ssl_errors(LOG_LEVEL_ERROR,
+            "Setting the cipher list '%s' for the client connection failed",
+            csp->config->cipher_list);
+         ret = -1;
+         goto exit;
+      }
+   }
+
    /*
     *  Handshake with client
     */
@@ -870,6 +899,7 @@ exit:
 extern void close_client_ssl_connection(struct client_state *csp)
 {
    struct ssl_attr *ssl_attr = &csp->ssl_client_attr;
+   SSL *ssl;
 
    if (csp->ssl_with_client_is_opened == 0)
    {
@@ -880,6 +910,20 @@ extern void close_client_ssl_connection(struct client_state *csp)
     * Notifying the peer that the connection is being closed.
     */
    BIO_ssl_shutdown(ssl_attr->openssl_attr.bio);
+   if (BIO_get_ssl(ssl_attr->openssl_attr.bio, &ssl) != 1)
+   {
+      log_ssl_errors(LOG_LEVEL_ERROR,
+         "BIO_get_ssl() failed in close_client_ssl_connection()");
+   }
+   else
+   {
+      /*
+       * Pretend we received a shutdown alert so
+       * the BIO_free_all() call later on returns
+       * quickly.
+       */
+      SSL_set_shutdown(ssl, SSL_RECEIVED_SHUTDOWN);
+   }
    free_client_ssl_structures(csp);
    csp->ssl_with_client_is_opened = 0;
 }
@@ -929,6 +973,7 @@ static void free_client_ssl_structures(struct client_state *csp)
 extern void close_server_ssl_connection(struct client_state *csp)
 {
    struct ssl_attr *ssl_attr = &csp->ssl_server_attr;
+   SSL *ssl;
 
    if (csp->ssl_with_server_is_opened == 0)
    {
@@ -939,6 +984,20 @@ extern void close_server_ssl_connection(struct client_state *csp)
    * Notifying the peer that the connection is being closed.
    */
    BIO_ssl_shutdown(ssl_attr->openssl_attr.bio);
+   if (BIO_get_ssl(ssl_attr->openssl_attr.bio, &ssl) != 1)
+   {
+      log_ssl_errors(LOG_LEVEL_ERROR,
+         "BIO_get_ssl() failed in close_server_ssl_connection()");
+   }
+   else
+   {
+      /*
+       * Pretend we received a shutdown alert so
+       * the BIO_free_all() call later on returns
+       * quickly.
+       */
+      SSL_set_shutdown(ssl, SSL_RECEIVED_SHUTDOWN);
+   }
    free_server_ssl_structures(csp);
    csp->ssl_with_server_is_opened = 0;
 }
@@ -1014,6 +1073,18 @@ extern int create_server_ssl_connection(struct client_state *csp)
       goto exit;
    }
 
+   if (csp->config->cipher_list != NULL)
+   {
+      if (!SSL_set_cipher_list(ssl, csp->config->cipher_list))
+      {
+         log_ssl_errors(LOG_LEVEL_ERROR,
+            "Setting the cipher list '%s' for the server connection failed",
+            csp->config->cipher_list);
+         ret = -1;
+         goto exit;
+      }
+   }
+
    /*
     * Set the hostname to check against the received server certificate
     */
@@ -1548,6 +1619,7 @@ static int ssl_certificate_is_invalid(const char *cert_file)
    {
       log_ssl_errors(LOG_LEVEL_ERROR,
          "Error checking certificate %s validity", cert_file);
+      ret = -1;
    }
 
    X509_free(cert);
@@ -2148,12 +2220,14 @@ extern void ssl_release(void)
 {
    if (ssl_inited == 1)
    {
+#ifndef OPENSSL_NO_COMP
       SSL_COMP_free_compression_methods();
-
+#endif
       CONF_modules_free();
       CONF_modules_unload(1);
-
+#ifndef OPENSSL_NO_COMP
       COMP_zlib_cleanup();
+#endif
 
       ERR_free_strings();
       EVP_cleanup();
index 06f1ae8..eab5e76 100644 (file)
--- a/parsers.c
+++ b/parsers.c
@@ -4067,7 +4067,8 @@ static jb_err server_http(struct client_state *csp, char **header)
       return JB_ERR_PARSE;
    }
 
-   if (csp->http->status == 206)
+   if (csp->http->status == 101 ||
+       csp->http->status == 206)
    {
       csp->content_type = CT_TABOO;
    }
@@ -4586,7 +4587,11 @@ jb_err get_destination_from_headers(const struct list *headers, struct http_requ
       return JB_ERR_PARSE;
    }
 
-   p = strdup_or_die(host);
+   p = string_tolower(host);
+   if (p == NULL)
+   {
+      return JB_ERR_MEMORY;
+   }
    chomp(p);
    q = strdup_or_die(p);
 
@@ -4673,7 +4678,11 @@ jb_err get_destination_from_https_headers(const struct list *headers, struct htt
       return JB_ERR_PARSE;
    }
 
-   p = strdup_or_die(host);
+   p = string_tolower(host);
+   if (p == NULL)
+   {
+      return JB_ERR_MEMORY;
+   }
    chomp(p);
    q = strdup_or_die(p);
 
index 1869ea4..9d91022 100644 (file)
--- a/parsers.h
+++ b/parsers.h
@@ -12,7 +12,7 @@
  *                   `client_x_forwarded_adder', `client_xtra_adder',
  *                   `content_type', `crumble', `destroy_list', `enlist',
  *                   `flush_socket', `free_http_request', `get_header',
- *                   `list_to_text', `parse_http_request', `sed',
+ *                   `parse_http_request', `sed',
  *                   and `server_set_cookie'.
  *
  * Copyright   :  Written by and Copyright (C) 2001 members of the
diff --git a/pcrs.c b/pcrs.c
index 6da8225..ca6ba68 100644 (file)
--- a/pcrs.c
+++ b/pcrs.c
@@ -168,6 +168,7 @@ static int pcrs_parse_perl_options(const char *optstring, int *flags)
          case 'o': break;
          case 's': rc |= PCRE_DOTALL; break;
          case 'x': rc |= PCRE_EXTENDED; break;
+         case 'D': *flags |= PCRS_DYNAMIC; break;
          case 'U': rc |= PCRE_UNGREEDY; break;
          case 'T': *flags |= PCRS_TRIVIAL; break;
          default: break;
@@ -471,7 +472,14 @@ pcrs_job *pcrs_free_job(pcrs_job *job)
    {
       next = job->next;
       if (job->pattern != NULL) free(job->pattern);
-      if (job->hints != NULL) free(job->hints);
+      if (job->hints != NULL)
+      {
+#ifdef PCRE_CONFIG_JIT
+         pcre_free_study(job->hints);
+#else
+         free(job->hints);
+#endif
+      }
       if (job->substitute != NULL)
       {
          if (job->substitute->text != NULL) free(job->substitute->text);
@@ -621,6 +629,7 @@ pcrs_job *pcrs_compile(const char *pattern, const char *substitute, const char *
    int flags;
    int capturecount;
    const char *error;
+   int pcre_study_options = 0;
 
    *errptr = 0;
 
@@ -660,11 +669,18 @@ pcrs_job *pcrs_compile(const char *pattern, const char *substitute, const char *
    }
 
 
+#ifdef PCRE_STUDY_JIT_COMPILE
+   if (!(flags & PCRS_DYNAMIC))
+   {
+      pcre_study_options = PCRE_STUDY_JIT_COMPILE;
+   }
+#endif
+
    /*
     * Generate hints. This has little overhead, since the
     * hints will be NULL for a boring pattern anyway.
     */
-   newjob->hints = pcre_study(newjob->pattern, 0, &error);
+   newjob->hints = pcre_study(newjob->pattern, pcre_study_options, &error);
    if (error != NULL)
    {
       *errptr = PCRS_ERR_STUDY;
@@ -995,7 +1011,7 @@ static int is_hex_sequence(const char *sequence)
  *                FALSE
  *
  *********************************************************************/
-int pcrs_job_is_dynamic (char *job)
+int pcrs_job_is_dynamic(char *job)
 {
    const char delimiter = job[1];
    const size_t length = strlen(job);
@@ -1106,7 +1122,6 @@ char *pcrs_execute_single_command(const char *subject, const char *pcrs_command,
 }
 
 
-static const char warning[] = "... [too long, truncated]";
 /*********************************************************************
  *
  * Function    :  pcrs_compile_dynamic_command
@@ -1163,7 +1178,7 @@ pcrs_job *pcrs_compile_dynamic_command(char *pcrs_command, const struct pcrs_var
        */
       assert(NULL == strchr(v->name, d));
 
-      ret = snprintf(buf, sizeof(buf), "s%c\\$%s%c%s%cgT", d, v->name, d, v->value, d);
+      ret = snprintf(buf, sizeof(buf), "s%c\\$%s%c%s%cDgT", d, v->name, d, v->value, d);
       assert(ret >= 0);
       if (ret >= sizeof(buf))
       {
@@ -1173,10 +1188,11 @@ pcrs_job *pcrs_compile_dynamic_command(char *pcrs_command, const struct pcrs_var
           * with a truncation message and close the pattern
           * properly.
           */
-         const size_t trailer_size = sizeof(warning) + 3; /* 3 for d + "gT" */
+         static const char warning[] = "... [too long, truncated]";
+         const size_t trailer_size = sizeof(warning) + 4; /* 4 for d + "DgT" */
          char *trailer_start = buf + sizeof(buf) - trailer_size;
 
-         ret = snprintf(trailer_start, trailer_size, "%s%cgT", warning, d);
+         ret = snprintf(trailer_start, trailer_size, "%s%cDgT", warning, d);
          assert(ret == trailer_size - 1);
          assert(sizeof(buf) == strlen(buf) + 1);
          truncation = 1;
diff --git a/pcrs.h b/pcrs.h
index e7699ab..abff3ca 100644 (file)
--- a/pcrs.h
+++ b/pcrs.h
@@ -70,6 +70,7 @@
 #define PCRS_GLOBAL          1      /* Job should be applied globally, as with perl's g option */
 #define PCRS_TRIVIAL         2      /* Backreferences in the substitute are ignored */
 #define PCRS_SUCCESS         4      /* Job did previously match */
+#define PCRS_DYNAMIC         8      /* Job is dynamic (used to disable JIT compilation) */
 
 
 /*
index 6821aa0..ec3c155 100644 (file)
--- a/project.h
+++ b/project.h
 #endif /* FEATURE_HTTPS_INSPECTION_MBEDTLS */
 
 #ifdef FEATURE_HTTPS_INSPECTION_OPENSSL
+#ifdef _WIN32
+#include <wincrypt.h>
+#undef X509_NAME
+#undef X509_EXTENSIONS
+#endif
 #include <openssl/ssl.h>
 #include <openssl/bio.h>
 #include <openssl/err.h>
@@ -306,6 +311,7 @@ typedef struct {
    mbedtls_x509_crt         server_cert;
    mbedtls_x509_crt         ca_cert;
    mbedtls_pk_context       prim_key;
+   int                     *ciphersuites_list;
 
    #if defined(MBEDTLS_SSL_CACHE_C)
       mbedtls_ssl_cache_context cache;
@@ -318,7 +324,7 @@ typedef struct {
  * Struct of attributes necessary for TLS/SSL connection
  */
 typedef struct {
-   SSL_CTXctx;
+   SSL_CTX *ctx;
    BIO *bio;
 } openssl_connection_attr;
 #endif /* FEATURE_HTTPS_INSPECTION_OPENSSL */
@@ -766,6 +772,9 @@ struct reusable_connection
    enum forwarder_type forwarder_type;
    char *gateway_host;
    int  gateway_port;
+   char *auth_username;
+   char *auth_password;
+
    char *forward_host;
    int  forward_port;
 };
@@ -1580,6 +1589,9 @@ struct configuration_spec
    /** Directory for saving certificates and keys for each webpage **/
    char *certificate_directory;
 
+   /** Cipher list to use **/
+   char *cipher_list;
+
    /** Filename of trusted CAs certificates **/
    char * trusted_cas_file;
 #endif
diff --git a/ssl.c b/ssl.c
index bc4c5af..46b8fd4 100644 (file)
--- a/ssl.c
+++ b/ssl.c
@@ -5,7 +5,7 @@
  * Purpose     :  File with TLS/SSL extension. Contains methods for
  *                creating, using and closing TLS/SSL connections.
  *
- * Copyright   :  Written by and Copyright (c) 2017 Vaclav Svec. FIT CVUT.
+ * Copyright   :  Written by and Copyright (c) 2017-2020 Vaclav Svec. FIT CVUT.
  *                Copyright (C) 2018-2020 by Fabian Keil <fk@fabiankeil.de>
  *
  *                This program is free software; you can redistribute it
@@ -94,6 +94,7 @@ static int ssl_verify_callback(void *data, mbedtls_x509_crt *crt, int depth, uin
 static void free_client_ssl_structures(struct client_state *csp);
 static void free_server_ssl_structures(struct client_state *csp);
 static int seed_rng(struct client_state *csp);
+static int *get_ciphersuites_from_string(const char *ciphersuites_string);
 
 /*********************************************************************
  *
@@ -170,7 +171,8 @@ extern int ssl_send_data(struct ssl_attr *ssl_attr, const unsigned char *buf, si
          send_len = (int)max_fragment_size;
       }
 
-      log_error(LOG_LEVEL_WRITING, "TLS: %N", send_len, buf+pos);
+      log_error(LOG_LEVEL_WRITING, "TLS on socket %d: %N",
+         ssl_attr->mbedtls_attr.socket_fd.fd, send_len, buf+pos);
 
       /*
        * Sending one part of the buffer
@@ -186,7 +188,8 @@ extern int ssl_send_data(struct ssl_attr *ssl_attr, const unsigned char *buf, si
 
             mbedtls_strerror(ret, err_buf, sizeof(err_buf));
             log_error(LOG_LEVEL_ERROR,
-               "Sending data over TLS/SSL failed: %s", err_buf);
+               "Sending data on socket %d over TLS/SSL failed: %s",
+               ssl_attr->mbedtls_attr.socket_fd.fd, err_buf);
             return -1;
          }
       }
@@ -235,18 +238,21 @@ extern int ssl_recv_data(struct ssl_attr *ssl_attr, unsigned char *buf, size_t m
 
       if (ret == MBEDTLS_ERR_SSL_PEER_CLOSE_NOTIFY)
       {
-         log_error(LOG_LEVEL_CONNECT,
-            "The peer notified us that the connection is going to be closed");
+         log_error(LOG_LEVEL_CONNECT, "The peer notified us that "
+            "the connection on socket %d is going to be closed",
+            ssl_attr->mbedtls_attr.socket_fd.fd);
          return 0;
       }
       mbedtls_strerror(ret, err_buf, sizeof(err_buf));
       log_error(LOG_LEVEL_ERROR,
-         "Receiving data over TLS/SSL failed: %s", err_buf);
+         "Receiving data on socket %d over TLS/SSL failed: %s",
+         ssl_attr->mbedtls_attr.socket_fd.fd, err_buf);
 
       return -1;
    }
 
-   log_error(LOG_LEVEL_RECEIVED, "TLS: %N", ret, buf);
+   log_error(LOG_LEVEL_RECEIVED, "TLS from socket %d: %N",
+      ssl_attr->mbedtls_attr.socket_fd.fd, ret, buf);
 
    return ret;
 }
@@ -416,6 +422,22 @@ extern int create_client_ssl_connection(struct client_state *csp)
       goto exit;
    }
 
+   if (csp->config->cipher_list != NULL)
+   {
+      ssl_attr->mbedtls_attr.ciphersuites_list =
+         get_ciphersuites_from_string(csp->config->cipher_list);
+      if (ssl_attr->mbedtls_attr.ciphersuites_list == NULL)
+      {
+         log_error(LOG_LEVEL_ERROR,
+            "Setting the cipher list '%s' for the client connection failed",
+            csp->config->cipher_list);
+         ret = -1;
+         goto exit;
+      }
+      mbedtls_ssl_conf_ciphersuites(&(ssl_attr->mbedtls_attr.conf),
+         ssl_attr->mbedtls_attr.ciphersuites_list);
+   }
+
    ret = mbedtls_ssl_setup(&(ssl_attr->mbedtls_attr.ssl),
       &(ssl_attr->mbedtls_attr.conf));
    if (ret != 0)
@@ -539,6 +561,7 @@ static void free_client_ssl_structures(struct client_state *csp)
    mbedtls_x509_crt_free(&(ssl_attr->mbedtls_attr.server_cert));
    mbedtls_pk_free(&(ssl_attr->mbedtls_attr.prim_key));
    mbedtls_ssl_free(&(ssl_attr->mbedtls_attr.ssl));
+   freez(ssl_attr->mbedtls_attr.ciphersuites_list);
    mbedtls_ssl_config_free(&(ssl_attr->mbedtls_attr.conf));
 #if defined(MBEDTLS_SSL_CACHE_C)
    mbedtls_ssl_cache_free(&(ssl_attr->mbedtls_attr.cache));
@@ -648,6 +671,22 @@ extern int create_server_ssl_connection(struct client_state *csp)
    mbedtls_ssl_conf_rng(&(ssl_attr->mbedtls_attr.conf),
       mbedtls_ctr_drbg_random, &ctr_drbg);
 
+   if (csp->config->cipher_list != NULL)
+   {
+      ssl_attr->mbedtls_attr.ciphersuites_list =
+         get_ciphersuites_from_string(csp->config->cipher_list);
+      if (ssl_attr->mbedtls_attr.ciphersuites_list == NULL)
+      {
+         log_error(LOG_LEVEL_ERROR,
+            "Setting the cipher list '%s' for the server connection failed",
+            csp->config->cipher_list);
+         ret = -1;
+         goto exit;
+      }
+      mbedtls_ssl_conf_ciphersuites(&(ssl_attr->mbedtls_attr.conf),
+         ssl_attr->mbedtls_attr.ciphersuites_list);
+   }
+
    ret = mbedtls_ssl_setup(&(ssl_attr->mbedtls_attr.ssl),
       &(ssl_attr->mbedtls_attr.conf));
    if (ret != 0)
@@ -798,6 +837,7 @@ static void free_server_ssl_structures(struct client_state *csp)
 
    mbedtls_x509_crt_free(&(ssl_attr->mbedtls_attr.ca_cert));
    mbedtls_ssl_free(&(ssl_attr->mbedtls_attr.ssl));
+   freez(ssl_attr->mbedtls_attr.ciphersuites_list);
    mbedtls_ssl_config_free(&(ssl_attr->mbedtls_attr.conf));
 }
 
@@ -1855,3 +1895,73 @@ extern void ssl_release(void)
       mbedtls_entropy_free(&entropy);
    }
 }
+
+
+/*********************************************************************
+ *
+ * Function    :  get_ciphersuites_from_string
+ *
+ * Description :  Converts a string of ciphersuite names to
+ *                an array of ciphersuite ids.
+ *
+ * Parameters  :
+ *          1  :  ciphersuites_string = String containing allowed
+ *                ciphersuites.
+ *
+ * Returns     :  Array of ciphersuite ids
+ *
+ *********************************************************************/
+static int *get_ciphersuites_from_string(const char *parameter_string)
+{
+   char *ciphersuites_index;
+   char *item_end;
+   char *ciphersuites_string;
+   int *ciphersuite_ids;
+   size_t count = 2;
+   int index = 0;
+   const char separator = ':';
+   size_t parameter_len = strlen(parameter_string);
+
+   ciphersuites_string = zalloc_or_die(parameter_len + 1);
+   strncpy(ciphersuites_string, parameter_string, parameter_len);
+   ciphersuites_index = ciphersuites_string;
+
+   while (*ciphersuites_index)
+   {
+      if (*ciphersuites_index++ == separator)
+      {
+         ++count;
+      }
+   }
+
+   ciphersuite_ids = zalloc_or_die(count * sizeof(int));
+
+   ciphersuites_index = ciphersuites_string;
+   do
+   {
+      item_end = strchr(ciphersuites_index, separator);
+      if (item_end != NULL)
+      {
+         *item_end = '\0';
+      }
+
+      ciphersuite_ids[index] =
+         mbedtls_ssl_get_ciphersuite_id(ciphersuites_index);
+      if (ciphersuite_ids[index] == 0)
+      {
+         log_error(LOG_LEVEL_ERROR,
+            "Failed to get ciphersuite id for %s", ciphersuites_index);
+         freez(ciphersuite_ids);
+         freez(ciphersuites_string);
+         return NULL;
+      }
+      ciphersuites_index = item_end + 1;
+      index++;
+   } while (item_end != NULL);
+
+   ciphersuite_ids[index] = 0;
+   freez(ciphersuites_string);
+
+   return ciphersuite_ids;
+
+}
index c7bd538..41f0575 100644 (file)
@@ -407,7 +407,7 @@ extern void ssl_send_certificate_error(struct client_state *csp)
    /*
     * Sending final message to client
     */
-   ssl_send_data(ssl_attr, (const unsigned char *)message, strlen(message));
+   (void)ssl_send_data(ssl_attr, (const unsigned char *)message, strlen(message));
 
    free_certificate_chain(csp);
 
index a4c15e4..73a7d3a 100644 (file)
             <tr>
               <td><code>FEATURE_HTTPS_INSPECTION</code></td>
               <td>@if-FEATURE_HTTPS_INSPECTION-then@ Yes @else-not-FEATURE_HTTPS_INSPECTION@ No @endif-FEATURE_HTTPS_INSPECTION@</td>
-              <td>Allows to intercept and filter HTTPS traffic.</td>
+              <td>Allows to intercept and filter HTTPS traffic. Experimental.</td>
             </tr>
             <tr>
               <td><code>FEATURE_IMAGE_BLOCKING</code></td>
index b43dfe1..c7312e8 100755 (executable)
@@ -52,6 +52,7 @@ use constant {
 
     CLI_OPTION_DEFAULT_TO_HTML_OUTPUT => 0,
     CLI_OPTION_TITLE => 'Privoxy-Log-Parser in da house',
+    CLI_OPTION_KEEP_DATE => 0,
     CLI_OPTION_NO_EMBEDDED_CSS => 0,
     CLI_OPTION_NO_MSECS => 0,
     CLI_OPTION_NO_SYNTAX_HIGHLIGHTING => 0,
@@ -107,6 +108,7 @@ my %h_colours;
 my $header_highlight_regex = '';
 
 my $html_output_mode;
+my $keep_date_mode;
 my $no_msecs_mode; # XXX: should probably be removed
 my $shorten_thread_ids;
 my $line_end;
@@ -1633,6 +1635,7 @@ sub handle_loglevel_connect($) {
         # Reusing server socket 7 connected to www.privoxy.org. Total requests: 2.
         # Closing server socket 6 connected to d.asset.soup.io. Keep-alive: 0.\
         #  Tainted: 1. Socket alive: 1. Timeout: 60. Configuration file change detected: 0.
+        # Reusing server socket 35 connected to nl.wikipedia.org. Requests already sent: 5.
 
         $c =~ s@(?<= socket )(\d+)@$h{'Number'}$1$h{'Standard'}@;
         $c = highlight_matched_host($c, '(?<=for )[^\s]+(?=\.)');
@@ -1640,6 +1643,7 @@ sub handle_loglevel_connect($) {
         for my $number_pattern ('requests', 'Keep-alive', 'Tainted', ' alive', 'Timeout', 'detected') {
             $c = highlight_matched_pattern($c, 'Number', '(?<='. $number_pattern . ': )\d+');
         }
+        $c =~ s@(?<=already sent: )(\d+)@$h{'Number'}$1$h{'Standard'}@;
 
     } elsif ($c =~ m/^Connected to /) {
 
@@ -1776,6 +1780,17 @@ sub handle_loglevel_connect($) {
         $c =~ s@(?<=client socket )(\d+)@$h{'Number'}$1$h{'Standard'}@;
         $c =~ s@(?<=Requests so far: )(\d+)@$h{'Number'}$1$h{'Standard'}@;
 
+    } elsif ($c =~ m/^Dropping the client connection on socket/) {
+
+        # Dropping the client connection on socket 71. The server connection has not been established yet.
+        $c =~ s@(?<=on socket )(\d+)@$h{'Number'}$1$h{'Standard'}@;
+
+    } elsif ($c =~ m/^The client socket \d+ has become unusable while the server/) {
+
+        # The client socket 16 has become unusable while the server socket 24 is still open.
+        $c =~ s@(?<=client socket )(\d+)@$h{'Number'}$1$h{'Standard'}@;
+        $c =~ s@(?<=server socket )(\d+)@$h{'Number'}$1$h{'Standard'}@;
+
     } elsif ($c =~ m/^Looks like we / or
              $c =~ m/^Unsetting keep-alive flag/ or
              $c =~ m/^No connections to wait/ or
@@ -2375,12 +2390,14 @@ sub print_clf_message() {
 sub print_non_clf_message($) {
 
     my $content = shift;
+    my $date_string = $keep_date_mode ? $req{$t}{'day'} . ' ' : '';
     my $msec_string = $no_msecs_mode ? '' : '.' . $req{$t}{'msecs'};
     my $line_start = $html_output_mode ? '' : $h{"Standard"};
 
     return if DEBUG_SUPPRESS_LOG_MESSAGES;
 
     print $line_start
+        . $date_string
         . $time_colours[$time_colour_index % 2]
         . $req{$t}{'time-stamp'}
         . $msec_string
@@ -2598,6 +2615,7 @@ sub get_cli_options() {
     our %cli_options = (
         'html-output'              => CLI_OPTION_DEFAULT_TO_HTML_OUTPUT,
         'title'                    => CLI_OPTION_TITLE,
+        'keep-date'                => CLI_OPTION_KEEP_DATE,
         'no-syntax-highlighting'   => CLI_OPTION_NO_SYNTAX_HIGHLIGHTING,
         'no-embedded-css'          => CLI_OPTION_NO_EMBEDDED_CSS,
         'no-msecs'                 => CLI_OPTION_NO_MSECS,
@@ -2614,6 +2632,7 @@ sub get_cli_options() {
     GetOptions (
         'html-output'              => \$cli_options{'html-output'},
         'title'                    => \$cli_options{'title'},
+        'keep-date'                => \$cli_options{'keep-date'},
         'no-syntax-highlighting'   => \$cli_options{'no-syntax-highlighting'},
         'no-embedded-css'          => \$cli_options{'no-embedded-css'},
         'no-msecs'                 => \$cli_options{'no-msecs'},
@@ -2631,6 +2650,7 @@ sub get_cli_options() {
 
    $html_output_mode = cli_option_is_set('html-output');
    $no_msecs_mode = cli_option_is_set('no-msecs');
+   $keep_date_mode = cli_option_is_set('keep-date');
    $shorten_thread_ids = cli_option_is_set('shorten-thread-ids');
    $line_end = get_line_end();
 }
@@ -2730,6 +2750,9 @@ omitted, ANSI escape sequences are used unless B<--no-syntax-highlighting> is ac
 This option is only intended to make embedding log excerpts in web pages easier.
 It does not escape any input!
 
+[B<--keep-date>] Don't remove the date when printing highlighted log messages.
+Useful when parsing multiple log files at once.
+
 [B<--no-msecs>] Don't expect milisecond resolution
 
 [B<--no-syntax-highlighting>] Disable syntax-highlighting. Useful when
index 4886e4c..23a6b54 100644 (file)
@@ -302,7 +302,7 @@ jb_err parse_http_url(const char *url, struct http_request *http, int require_pr
             url_path
          );
          *url_path = '\0';
-         http->hostport = strdup_or_die(url_noproto);
+         http->hostport = string_tolower(url_noproto);
       }
       else
       {
@@ -311,10 +311,15 @@ jb_err parse_http_url(const char *url, struct http_request *http, int require_pr
           * or CONNECT requests
           */
          http->path = strdup_or_die("/");
-         http->hostport = strdup_or_die(url_noproto);
+         http->hostport = string_tolower(url_noproto);
       }
 
       freez(buf);
+
+      if (http->hostport == NULL)
+      {
+         return JB_ERR_PARSE;
+      }
    }
 
    if (!host_available)