Am Donnerstag, 26. Dezember 2019 14:57 CET, [email protected] schrieb:
> Does Pound support HSTS ?
>
> Does Pound support adding headers to the outgong web response?
> I see the "AddHeader" option which apparently adds headers to the
> incoming request (to the back-end server), but I don't see any options
> that let me add headers to the outgoing response (back to the client).

I've attached the HSTS patch I posted years ago (updated to pound 2.8). With 
the patch you can add the following directive to your config at service level:
StrictTransportSecurity <SECONDS>

Best regards,
Frank
diff -ur Pound-2.8.orig/config.c Pound-2.8/config.c
--- Pound-2.8.orig/config.c	2018-05-11 12:16:05.000000000 +0200
+++ Pound-2.8/config.c	2019-12-30 08:58:35.494682825 +0100
@@ -76,7 +76,7 @@
 static regex_t  Empty, Comment, User, Group, RootJail, Daemon, LogFacility, LogLevel, Alive, SSLEngine, Control;
 static regex_t  ListenHTTP, ListenHTTPS, End, Address, Port, Cert, xHTTP, Client, CheckURL;
 static regex_t  Err414, Err500, Err501, Err503, MaxRequest, HeadRemove, RewriteLocation, RewriteDestination;
-static regex_t  Service, ServiceName, URL, HeadRequire, HeadDeny, BackEnd, Emergency, Priority, HAport, HAportAddr;
+static regex_t  Service, ServiceName, URL, HeadRequire, HeadDeny, BackEnd, Emergency, Priority, HAport, HAportAddr, StrictTransportSecurity;
 static regex_t  Redirect, RedirectN, TimeOut, Session, Type, TTL, ID;
 static regex_t  ClientCert, AddHeader, DisableProto, SSLAllowClientRenegotiation, SSLHonorCipherOrder, Ciphers;
 static regex_t  CAlist, VerifyList, CRLlist, NoHTTPS11, Grace, Include, ConnTO, IgnoreCase, HTTPS;
@@ -562,6 +562,7 @@
         conf_err("Service config: out of memory - aborted");
     memset(res, 0, sizeof(SERVICE));
     res->sess_type = SESS_NONE;
+    res->sts = -1;
     pthread_mutex_init(&res->mut, NULL);
     if(svc_name)
         strncpy(res->name, svc_name, KEY_SIZE);
@@ -591,6 +592,8 @@
             lin[matches[1].rm_eo] = '\0';
             if(regcomp(&m->pat, lin + matches[1].rm_so, REG_NEWLINE | REG_EXTENDED | (ign_case? REG_ICASE: 0)))
                 conf_err("URL bad pattern - aborted");
+        } else if(!regexec(&StrictTransportSecurity, lin, 4, matches, 0)) {
+            res->sts = atoi(lin + matches[1].rm_so);
         } else if(!regexec(&HeadRequire, lin, 4, matches, 0)) {
             if(res->req_head) {
                 for(m = res->req_head; m->next; m = m->next)
@@ -847,12 +850,16 @@
         } else if(!regexec(&LogLevel, lin, 4, matches, 0)) {
             res->log_level = atoi(lin + matches[1].rm_so);
         } else if(!regexec(&Service, lin, 4, matches, 0)) {
-            if(res->services == NULL)
+            if(res->services == NULL) {
                 res->services = parse_service(NULL);
-            else {
+                if(res->services->sts >= 0)
+                    conf_err("StrictTransportSecurity not allowed in HTTP listener - aborted");
+            } else {
                 for(svc = res->services; svc->next; svc = svc->next)
                     ;
                 svc->next = parse_service(NULL);
+                if(svc->next->sts >= 0)
+                    conf_err("StrictTransportSecurity not allowed in HTTP listener - aborted");
             }
         } else if(!regexec(&ServiceName, lin, 4, matches, 0)) {
             lin[matches[1].rm_eo] = '\0';
@@ -1461,6 +1468,7 @@
     || regcomp(&Service, "^[ \t]*Service[ \t]*$", REG_ICASE | REG_NEWLINE | REG_EXTENDED)
     || regcomp(&ServiceName, "^[ \t]*Service[ \t]+\"(.+)\"[ \t]*$", REG_ICASE | REG_NEWLINE | REG_EXTENDED)
     || regcomp(&URL, "^[ \t]*URL[ \t]+\"(.+)\"[ \t]*$", REG_ICASE | REG_NEWLINE | REG_EXTENDED)
+    || regcomp(&StrictTransportSecurity, "^[ \t]*StrictTransportSecurity[ \t]+([0-9]+)[ \t]*$", REG_ICASE | REG_NEWLINE | REG_EXTENDED)
     || regcomp(&HeadRequire, "^[ \t]*HeadRequire[ \t]+\"(.+)\"[ \t]*$", REG_ICASE | REG_NEWLINE | REG_EXTENDED)
     || regcomp(&HeadDeny, "^[ \t]*HeadDeny[ \t]+\"(.+)\"[ \t]*$", REG_ICASE | REG_NEWLINE | REG_EXTENDED)
     || regcomp(&BackEnd, "^[ \t]*BackEnd[ \t]*$", REG_ICASE | REG_NEWLINE | REG_EXTENDED)
@@ -1626,6 +1634,7 @@
     regfree(&Service);
     regfree(&ServiceName);
     regfree(&URL);
+    regfree(&StrictTransportSecurity);
     regfree(&HeadRequire);
     regfree(&HeadDeny);
     regfree(&BackEnd);
diff -ur Pound-2.8.orig/http.c Pound-2.8/http.c
--- Pound-2.8.orig/http.c	2018-05-11 12:16:05.000000000 +0200
+++ Pound-2.8/http.c	2019-12-30 08:58:35.494682825 +0100
@@ -1403,6 +1403,8 @@
             if(!no_cont && !regexec(&RESP_IGN, response, 0, NULL, 0))
                 no_cont = 1;
 
+            for(n = 0; n < MAXHEADERS; n++)
+                headers_ok[n] = 1;
             for(chunked = 0, cont = -1L, n = 1; n < MAXHEADERS && headers[n]; n++) {
                 switch(check_header(headers[n], buf)) {
                 case HEADER_CONNECTION:
@@ -1453,6 +1455,11 @@
                         }
                     }
                     break;
+                case HEADER_STRICT_TRANSPORT_SECURITY:
+                    /* enforce pound's STS header */
+                    if(svc->sts >= 0)
+                        headers_ok[n] = 0;
+                    break;
                 }
             }
 
@@ -1462,6 +1469,8 @@
             /* send the response */
             if(!skip)
                 for(n = 0; n < MAXHEADERS && headers[n]; n++) {
+                    if(!headers_ok[n])
+                        continue;
                     if(BIO_printf(cl, "%s\r\n", headers[n]) <= 0) {
                         if(errno) {
                             addr2str(caddr, MAXBUF - 1, &from_host, 1);
@@ -1473,6 +1482,8 @@
                     }
                 }
             free_headers(headers);
+            if(!skip && ssl && svc->sts >= 0)
+                BIO_printf(cl, "Strict-Transport-Security: max-age=%d\r\n", svc->sts);
 
             /* final CRLF */
             if(!skip)
diff -ur Pound-2.8.orig/pound.h Pound-2.8/pound.h
--- Pound-2.8.orig/pound.h	2018-05-11 12:16:05.000000000 +0200
+++ Pound-2.8/pound.h	2019-12-30 08:58:35.494682825 +0100
@@ -369,6 +369,7 @@
     LHASH               *sessions;  /* currently active sessions */
 #endif
     int                 disabled;   /* true if the service is disabled */
+    int                 sts;        /* strict transport security */
     struct _service     *next;
 }   SERVICE;
 
@@ -440,6 +441,7 @@
 #define HEADER_URI                  9
 #define HEADER_DESTINATION          10
 #define HEADER_EXPECT               11
+#define HEADER_STRICT_TRANSPORT_SECURITY 12
 
 /* control request stuff */
 typedef enum    {
diff -ur Pound-2.8.orig/svc.c Pound-2.8/svc.c
--- Pound-2.8.orig/svc.c	2018-05-11 12:16:05.000000000 +0200
+++ Pound-2.8/svc.c	2019-12-30 08:58:35.494682825 +0100
@@ -395,6 +395,7 @@
         { "User-agent",         10, HEADER_USER_AGENT },
         { "Destination",        11, HEADER_DESTINATION },
         { "Expect",             6,  HEADER_EXPECT },
+        { "Strict-Transport-Security", 25, HEADER_STRICT_TRANSPORT_SECURITY },
         { "",                   0,  HEADER_OTHER },
     };
     int i;
-- 
pound mailing list
[email protected]
https://admin.hostpoint.ch/mailman/listinfo/pound_apsis.ch

Reply via email to