diff --git a/.gitignore b/.gitignore index 260a2d6..9969f1d 100644 --- a/.gitignore +++ b/.gitignore @@ -1,2 +1 @@ SOURCES/httpd-2.4.6.tar.bz2 -SOURCES/centos-noindex.tar.gz diff --git a/.httpd.metadata b/.httpd.metadata index 17ede1b..d335a99 100644 --- a/.httpd.metadata +++ b/.httpd.metadata @@ -1,2 +1 @@ 16d8ec72535ded65d035122b0d944b0e64eaa2a2 SOURCES/httpd-2.4.6.tar.bz2 -6ce5ab3c765b9efeceb2e636e32373bc6e6ed489 SOURCES/centos-noindex.tar.gz diff --git a/SOURCES/httpd-2.4.6-mod_authz_dbd-missing-query.patch b/SOURCES/httpd-2.4.6-mod_authz_dbd-missing-query.patch new file mode 100644 index 0000000..a763f89 --- /dev/null +++ b/SOURCES/httpd-2.4.6-mod_authz_dbd-missing-query.patch @@ -0,0 +1,55 @@ +diff --git a/modules/aaa/mod_authz_dbd.c b/modules/aaa/mod_authz_dbd.c +index 1a456fe..6a0f705 100644 +--- a/modules/aaa/mod_authz_dbd.c ++++ b/modules/aaa/mod_authz_dbd.c +@@ -116,7 +116,7 @@ static int authz_dbd_login(request_rec *r, authz_dbd_cfg *cfg, + const char *newuri = NULL; + int nrows; + const char *message; +- ap_dbd_t *dbd = dbd_handle(r); ++ ap_dbd_t *dbd; + apr_dbd_prepared_t *query; + apr_dbd_results_t *res = NULL; + apr_dbd_row_t *row = NULL; +@@ -126,6 +126,16 @@ static int authz_dbd_login(request_rec *r, authz_dbd_cfg *cfg, + "No query configured for %s!", action); + return HTTP_INTERNAL_SERVER_ERROR; + } ++ ++ dbd = dbd_handle(r); ++ if (dbd == NULL) { ++ ap_log_rerror(APLOG_MARK, APLOG_ERR, 0, r, APLOGNO(02902) ++ "No db handle available for %s! " ++ "Check your database access", ++ action); ++ return HTTP_INTERNAL_SERVER_ERROR; ++ } ++ + query = apr_hash_get(dbd->prepared, cfg->query, APR_HASH_KEY_STRING); + if (query == NULL) { + ap_log_rerror(APLOG_MARK, APLOG_ERR, 0, r, APLOGNO(01643) +@@ -202,7 +212,7 @@ static int authz_dbd_group_query(request_rec *r, authz_dbd_cfg *cfg, + /* SELECT group FROM authz WHERE user = %s */ + int rv; + const char *message; +- ap_dbd_t *dbd = dbd_handle(r); ++ ap_dbd_t *dbd; + apr_dbd_prepared_t *query; + apr_dbd_results_t *res = NULL; + apr_dbd_row_t *row = NULL; +@@ -212,6 +222,15 @@ static int authz_dbd_group_query(request_rec *r, authz_dbd_cfg *cfg, + "No query configured for dbd-group!"); + return HTTP_INTERNAL_SERVER_ERROR; + } ++ ++ dbd = dbd_handle(r); ++ if (dbd == NULL) { ++ ap_log_rerror(APLOG_MARK, APLOG_ERR, 0, r, APLOGNO(02903) ++ "No db handle available for dbd-query! " ++ "Check your database access"); ++ return HTTP_INTERNAL_SERVER_ERROR; ++ } ++ + query = apr_hash_get(dbd->prepared, cfg->query, APR_HASH_KEY_STRING); + if (query == NULL) { + ap_log_rerror(APLOG_MARK, APLOG_ERR, 0, r, APLOGNO(01650) diff --git a/SOURCES/httpd-2.4.6-r1650310.patch b/SOURCES/httpd-2.4.6-r1650310.patch new file mode 100644 index 0000000..1561282 --- /dev/null +++ b/SOURCES/httpd-2.4.6-r1650310.patch @@ -0,0 +1,132 @@ +diff --git a/docs/manual/mod/mod_ssl.html.en b/docs/manual/mod/mod_ssl.html.en +index ca178ab..4580f1c 100644 +--- a/docs/manual/mod/mod_ssl.html.en ++++ b/docs/manual/mod/mod_ssl.html.en +@@ -57,6 +57,7 @@ to provide the cryptography engine.

+
  • SSLCertificateKeyFile
  • +
  • SSLCipherSuite
  • +
  • SSLCompression
  • ++
  • SSLSessionTickets
  • +
  • SSLCryptoDevice
  • +
  • SSLEngine
  • +
  • SSLFIPS
  • +@@ -797,6 +798,26 @@ CRIME attack).

    + + + ++ ++
    top
    ++

    SSLSessionTickets Directive

    ++ ++ ++ ++ ++ ++ ++ ++ ++
    Description:Enable or disable use of TLS session tickets
    Syntax:SSLSessionTickets on|off
    Default:SSLCompression on
    Context:server config, virtual host
    Status:Extension
    Module:mod_ssl
    Compatibility:Available.
    ++

    This directive allows to enable or disable the use of TLS session tickets(RFC 5077).

    ++
    ++

    TLS session tickets are enabled by default. Using them without restarting ++the web server with an appropriate frequency (e.g. daily) compromises perfect ++forward secrecy.

    ++
    ++ ++
    +
    top
    +

    SSLCryptoDevice Directive

    + +diff --git a/modules/ssl/mod_ssl.c b/modules/ssl/mod_ssl.c +index bbe1d20..4a8b661 100644 +--- a/modules/ssl/mod_ssl.c ++++ b/modules/ssl/mod_ssl.c +@@ -141,6 +141,9 @@ static const command_rec ssl_config_cmds[] = { + SSL_CMD_SRV(Compression, FLAG, + "Enable SSL level compression" + "(`on', `off')") ++ SSL_CMD_SRV(SessionTickets, FLAG, ++ "Enable or disable TLS session tickets" ++ "(`on', `off')") + SSL_CMD_SRV(InsecureRenegotiation, FLAG, + "Enable support for insecure renegotiation") + SSL_CMD_ALL(UserName, TAKE1, +diff --git a/modules/ssl/ssl_engine_config.c b/modules/ssl/ssl_engine_config.c +index 9530fcc..86a7f0f 100644 +--- a/modules/ssl/ssl_engine_config.c ++++ b/modules/ssl/ssl_engine_config.c +@@ -216,6 +216,7 @@ static SSLSrvConfigRec *ssl_config_server_new(apr_pool_t *p) + #ifndef OPENSSL_NO_COMP + sc->compression = UNSET; + #endif ++ sc->session_tickets = UNSET; + + modssl_ctx_init_proxy(sc, p); + +@@ -346,6 +347,7 @@ void *ssl_config_server_merge(apr_pool_t *p, void *basev, void *addv) + #ifndef OPENSSL_NO_COMP + cfgMergeBool(compression); + #endif ++ cfgMergeBool(session_tickets); + + modssl_ctx_cfg_merge_proxy(base->proxy, add->proxy, mrg->proxy); + +@@ -720,6 +722,17 @@ const char *ssl_cmd_SSLHonorCipherOrder(cmd_parms *cmd, void *dcfg, int flag) + #endif + } + ++const char *ssl_cmd_SSLSessionTickets(cmd_parms *cmd, void *dcfg, int flag) ++{ ++ SSLSrvConfigRec *sc = mySrvConfig(cmd->server); ++#ifndef SSL_OP_NO_TICKET ++ return "This version of OpenSSL does not support using " ++ "SSLSessionTickets."; ++#endif ++ sc->session_tickets = flag ? TRUE : FALSE; ++ return NULL; ++} ++ + const char *ssl_cmd_SSLInsecureRenegotiation(cmd_parms *cmd, void *dcfg, int flag) + { + #ifdef SSL_OP_ALLOW_UNSAFE_LEGACY_RENEGOTIATION +diff --git a/modules/ssl/ssl_engine_init.c b/modules/ssl/ssl_engine_init.c +index 568627f..672760c 100644 +--- a/modules/ssl/ssl_engine_init.c ++++ b/modules/ssl/ssl_engine_init.c +@@ -566,6 +566,16 @@ static void ssl_init_ctx_protocol(server_rec *s, + } + #endif + ++#ifdef SSL_OP_NO_TICKET ++ /* ++ * Configure using RFC 5077 TLS session tickets ++ * for session resumption. ++ */ ++ if (sc->session_tickets == FALSE) { ++ SSL_CTX_set_options(ctx, SSL_OP_NO_TICKET); ++ } ++#endif ++ + #ifdef SSL_OP_ALLOW_UNSAFE_LEGACY_RENEGOTIATION + if (sc->insecure_reneg == TRUE) { + SSL_CTX_set_options(ctx, SSL_OP_ALLOW_UNSAFE_LEGACY_RENEGOTIATION); +diff --git a/modules/ssl/ssl_private.h b/modules/ssl/ssl_private.h +index 0cc6d3f..b601316 100644 +--- a/modules/ssl/ssl_private.h ++++ b/modules/ssl/ssl_private.h +@@ -701,6 +701,7 @@ struct SSLSrvConfigRec { + #ifndef OPENSSL_NO_COMP + BOOL compression; + #endif ++ BOOL session_tickets; + }; + + /** +@@ -756,6 +757,7 @@ const char *ssl_cmd_SSLCARevocationFile(cmd_parms *, void *, const char *); + const char *ssl_cmd_SSLCARevocationCheck(cmd_parms *, void *, const char *); + const char *ssl_cmd_SSLHonorCipherOrder(cmd_parms *cmd, void *dcfg, int flag); + const char *ssl_cmd_SSLCompression(cmd_parms *, void *, int flag); ++const char *ssl_cmd_SSLSessionTickets(cmd_parms *, void *, int flag); + const char *ssl_cmd_SSLVerifyClient(cmd_parms *, void *, const char *); + const char *ssl_cmd_SSLVerifyDepth(cmd_parms *, void *, const char *); + const char *ssl_cmd_SSLSessionCache(cmd_parms *, void *, const char *); diff --git a/SOURCES/httpd-2.4.6-r1668532.patch b/SOURCES/httpd-2.4.6-r1668532.patch new file mode 100644 index 0000000..6973eeb --- /dev/null +++ b/SOURCES/httpd-2.4.6-r1668532.patch @@ -0,0 +1,67 @@ +diff --git a/server/scoreboard.c b/server/scoreboard.c +index a2e5daf..f989b99 100644 +--- a/server/scoreboard.c ++++ b/server/scoreboard.c +@@ -138,8 +138,6 @@ AP_DECLARE(int) ap_calc_scoreboard_size(void) + scoreboard_size += sizeof(process_score) * server_limit; + scoreboard_size += sizeof(worker_score) * server_limit * thread_limit; + +- pfn_ap_logio_get_last_bytes = APR_RETRIEVE_OPTIONAL_FN(ap_logio_get_last_bytes); +- + return scoreboard_size; + } + +@@ -148,6 +146,11 @@ AP_DECLARE(void) ap_init_scoreboard(void *shared_score) + char *more_storage; + int i; + ++ pfn_ap_logio_get_last_bytes = APR_RETRIEVE_OPTIONAL_FN(ap_logio_get_last_bytes); ++ if (!shared_score) { ++ return; ++ } ++ + ap_calc_scoreboard_size(); + ap_scoreboard_image = + ap_calloc(1, sizeof(scoreboard) + server_limit * sizeof(worker_score *)); +@@ -299,8 +302,6 @@ int ap_create_scoreboard(apr_pool_t *p, ap_scoreboard_e sb_type) + apr_status_t rv; + #endif + +- pfn_ap_logio_get_last_bytes = APR_RETRIEVE_OPTIONAL_FN(ap_logio_get_last_bytes); +- + if (ap_scoreboard_image) { + ap_scoreboard_image->global->restart_time = apr_time_now(); + memset(ap_scoreboard_image->parent, 0, +@@ -309,6 +310,7 @@ int ap_create_scoreboard(apr_pool_t *p, ap_scoreboard_e sb_type) + memset(ap_scoreboard_image->servers[i], 0, + sizeof(worker_score) * thread_limit); + } ++ ap_init_scoreboard(NULL); + return OK; + } + +diff --git a/server/core.c b/server/core.c +index c125015..eaa81a6 100644 +--- a/server/core.c ++++ b/server/core.c +@@ -4843,6 +4843,11 @@ static void core_child_init(apr_pool_t *pchild, server_rec *s) + apr_random_after_fork(&proc); + } + ++static void core_optional_fn_retrieve(void) ++{ ++ ap_init_scoreboard(NULL); ++} ++ + AP_CORE_DECLARE(void) ap_random_parent_after_fork(void) + { + /* +@@ -5022,6 +5027,8 @@ static void register_hooks(apr_pool_t *p) + APR_HOOK_REALLY_LAST); + ap_hook_dirwalk_stat(core_dirwalk_stat, NULL, NULL, APR_HOOK_REALLY_LAST); + ap_hook_open_htaccess(ap_open_htaccess, NULL, NULL, APR_HOOK_REALLY_LAST); ++ ap_hook_optional_fn_retrieve(core_optional_fn_retrieve, NULL, NULL, ++ APR_HOOK_MIDDLE); + + /* register the core's insert_filter hook and register core-provided + * filters diff --git a/SOURCES/httpd-2.4.6-r1681289.patch b/SOURCES/httpd-2.4.6-r1681289.patch new file mode 100644 index 0000000..f4f63ac --- /dev/null +++ b/SOURCES/httpd-2.4.6-r1681289.patch @@ -0,0 +1,19 @@ +diff --git a/modules/proxy/proxy_util.c b/modules/proxy/proxy_util.c +index a78224b..e672e4a 100644 +--- a/modules/proxy/proxy_util.c ++++ b/modules/proxy/proxy_util.c +@@ -2260,8 +2260,12 @@ ap_proxy_determine_connection(apr_pool_t *p, request_rec *r, + * The scheme handler decides if this is permanent or + * short living pool. + */ +- /* are we connecting directly, or via a proxy? */ +- if (!proxyname) { ++ /* Unless we are connecting the backend via a (forward Proxy)Remote, we ++ * have to use the original form of the URI (non absolute), but this is ++ * also the case via a remote proxy using the CONNECT method since the ++ * original request (and URI) is to be embedded in the body. ++ */ ++ if (!proxyname || conn->is_ssl) { + *url = apr_pstrcat(p, uri->path, uri->query ? "?" : "", + uri->query ? uri->query : "", + uri->fragment ? "#" : "", diff --git a/SOURCES/httpd-2.4.6-r1805099.patch b/SOURCES/httpd-2.4.6-r1805099.patch new file mode 100644 index 0000000..4d7f419 --- /dev/null +++ b/SOURCES/httpd-2.4.6-r1805099.patch @@ -0,0 +1,46 @@ +diff --git a/modules/proxy/mod_proxy.c b/modules/proxy/mod_proxy.c +index b10be15..506a046 100644 +--- a/modules/proxy/mod_proxy.c ++++ b/modules/proxy/mod_proxy.c +@@ -1320,6 +1320,7 @@ static void *create_proxy_dir_config(apr_pool_t *p, char *dummy) + new->error_override = 0; + new->error_override_set = 0; + new->add_forwarded_headers = 1; ++ new->add_forwarded_headers_set = 0; + + return (void *) new; + } +@@ -1350,7 +1351,12 @@ static void *merge_proxy_dir_config(apr_pool_t *p, void *basev, void *addv) + new->error_override_set = add->error_override_set || base->error_override_set; + new->alias = (add->alias_set == 0) ? base->alias : add->alias; + new->alias_set = add->alias_set || base->alias_set; +- new->add_forwarded_headers = add->add_forwarded_headers; ++ new->add_forwarded_headers = ++ (add->add_forwarded_headers_set == 0) ? base->add_forwarded_headers ++ : add->add_forwarded_headers; ++ new->add_forwarded_headers_set = add->add_forwarded_headers_set ++ || base->add_forwarded_headers_set; ++ + return new; + } + +@@ -1837,6 +1843,7 @@ static const char * + { + proxy_dir_conf *conf = dconf; + conf->add_forwarded_headers = flag; ++ conf->add_forwarded_headers_set = 1; + return NULL; + } + static const char * +diff --git a/modules/proxy/mod_proxy.h b/modules/proxy/mod_proxy.h +index 06f2b17..8c76d4c 100644 +--- a/modules/proxy/mod_proxy.h ++++ b/modules/proxy/mod_proxy.h +@@ -219,6 +219,7 @@ typedef struct { + unsigned int error_override_set:1; + unsigned int alias_set:1; + unsigned int add_forwarded_headers:1; ++ unsigned int add_forwarded_headers_set:1; + } proxy_dir_conf; + + /* if we interpolate env vars per-request, we'll need a per-request diff --git a/SOURCES/httpd-2.4.6-r1811746.patch b/SOURCES/httpd-2.4.6-r1811746.patch new file mode 100644 index 0000000..6dc47bf --- /dev/null +++ b/SOURCES/httpd-2.4.6-r1811746.patch @@ -0,0 +1,128 @@ +--- a/server/protocol.c 2017/10/10 17:47:25 1811745 ++++ b/server/protocol.c 2017/10/10 17:51:13 1811746 +@@ -1674,62 +1674,88 @@ + ctx->tmpbb = apr_brigade_create(r->pool, r->connection->bucket_alloc); + } + +- /* Loop through this set of buckets to compute their length +- */ ++ /* Loop through the brigade to count the length. To avoid ++ * arbitrary memory consumption with morphing bucket types, this ++ * loop will stop and pass on the brigade when necessary. */ + e = APR_BRIGADE_FIRST(b); + while (e != APR_BRIGADE_SENTINEL(b)) { ++ apr_status_t rv; ++ + if (APR_BUCKET_IS_EOS(e)) { + eos = 1; + break; + } +- if (e->length == (apr_size_t)-1) { ++ /* For a flush bucket, fall through to pass the brigade and ++ * flush now. */ ++ else if (APR_BUCKET_IS_FLUSH(e)) { ++ e = APR_BUCKET_NEXT(e); ++ } ++ /* For metadata bucket types other than FLUSH, loop. */ ++ else if (APR_BUCKET_IS_METADATA(e)) { ++ e = APR_BUCKET_NEXT(e); ++ continue; ++ } ++ /* For determinate length data buckets, count the length and ++ * continue. */ ++ else if (e->length != (apr_size_t)-1) { ++ r->bytes_sent += e->length; ++ e = APR_BUCKET_NEXT(e); ++ continue; ++ } ++ /* For indeterminate length data buckets, perform one read. */ ++ else /* e->length == (apr_size_t)-1 */ { + apr_size_t len; + const char *ignored; +- apr_status_t rv; +- +- /* This is probably a pipe bucket. Send everything +- * prior to this, and then read the data for this bucket. +- */ ++ + rv = apr_bucket_read(e, &ignored, &len, eblock); ++ if ((rv != APR_SUCCESS) && !APR_STATUS_IS_EAGAIN(rv)) { ++ ap_log_rerror(APLOG_MARK, APLOG_ERR, rv, r, APLOGNO(00574) ++ "ap_content_length_filter: " ++ "apr_bucket_read() failed"); ++ return rv; ++ } + if (rv == APR_SUCCESS) { +- /* Attempt a nonblocking read next time through */ + eblock = APR_NONBLOCK_READ; ++ e = APR_BUCKET_NEXT(e); + r->bytes_sent += len; + } + else if (APR_STATUS_IS_EAGAIN(rv)) { +- /* Output everything prior to this bucket, and then +- * do a blocking read on the next batch. +- */ +- if (e != APR_BRIGADE_FIRST(b)) { +- apr_bucket *flush; +- apr_brigade_split_ex(b, e, ctx->tmpbb); +- flush = apr_bucket_flush_create(r->connection->bucket_alloc); +- +- APR_BRIGADE_INSERT_TAIL(b, flush); +- rv = ap_pass_brigade(f->next, b); +- if (rv != APR_SUCCESS || f->c->aborted) { +- return rv; +- } +- apr_brigade_cleanup(b); +- APR_BRIGADE_CONCAT(b, ctx->tmpbb); +- e = APR_BRIGADE_FIRST(b); ++ apr_bucket *flush; + +- ctx->data_sent = 1; +- } ++ /* Next read must block. */ + eblock = APR_BLOCK_READ; +- continue; +- } +- else { +- ap_log_rerror(APLOG_MARK, APLOG_ERR, rv, r, APLOGNO(00574) +- "ap_content_length_filter: " +- "apr_bucket_read() failed"); +- return rv; ++ ++ /* Ensure the last bucket to pass down is a flush if ++ * the next read will block. */ ++ flush = apr_bucket_flush_create(f->c->bucket_alloc); ++ APR_BUCKET_INSERT_BEFORE(e, flush); + } + } +- else { +- r->bytes_sent += e->length; ++ ++ /* Optimization: if the next bucket is EOS (directly after a ++ * bucket morphed to the heap, or a flush), short-cut to ++ * handle EOS straight away - allowing C-L to be determined ++ * for content which is already entirely in memory. */ ++ if (e != APR_BRIGADE_SENTINEL(b) && APR_BUCKET_IS_EOS(e)) { ++ continue; ++ } ++ ++ /* On reaching here, pass on everything in the brigade up to ++ * this point. */ ++ apr_brigade_split_ex(b, e, ctx->tmpbb); ++ ++ rv = ap_pass_brigade(f->next, b); ++ if (rv != APR_SUCCESS) { ++ return rv; ++ } ++ else if (f->c->aborted) { ++ return APR_ECONNABORTED; + } +- e = APR_BUCKET_NEXT(e); ++ apr_brigade_cleanup(b); ++ APR_BRIGADE_CONCAT(b, ctx->tmpbb); ++ e = APR_BRIGADE_FIRST(b); ++ ++ ctx->data_sent = 1; + } + + /* If we've now seen the entire response and it's otherwise diff --git a/SOURCES/httpd-2.4.6-r1811831.patch b/SOURCES/httpd-2.4.6-r1811831.patch new file mode 100644 index 0000000..1f63e14 --- /dev/null +++ b/SOURCES/httpd-2.4.6-r1811831.patch @@ -0,0 +1,79 @@ +--- a/server/util_script.c 2017/10/11 14:41:00 1811830 ++++ b/server/util_script.c 2017/10/11 14:48:55 1811831 +@@ -92,9 +92,21 @@ + } + } + +-static void env2env(apr_table_t *table, const char *name) ++/* Sets variable @name in table @dest from r->subprocess_env if ++ * available, else from the environment, else from @fallback if ++ * non-NULL. */ ++static void env2env(apr_table_t *dest, request_rec *r, ++ const char *name, const char *fallback) + { +- add_unless_null(table, name, getenv(name)); ++ const char *val; ++ ++ val = apr_table_get(r->subprocess_env, name); ++ if (!val) ++ val = apr_pstrdup(r->pool, getenv(name)); ++ if (!val) ++ val = apr_pstrdup(r->pool, fallback); ++ if (val) ++ apr_table_addn(dest, name, val); + } + + AP_DECLARE(char **) ap_create_environment(apr_pool_t *p, apr_table_t *t) +@@ -211,37 +223,29 @@ + add_unless_null(e, http2env(r, hdrs[i].key), hdrs[i].val); + } + +- env_temp = apr_table_get(r->subprocess_env, "PATH"); +- if (env_temp == NULL) { +- env_temp = getenv("PATH"); +- } +- if (env_temp == NULL) { +- env_temp = DEFAULT_PATH; +- } +- apr_table_addn(e, "PATH", apr_pstrdup(r->pool, env_temp)); +- ++ env2env(e, r, "PATH", DEFAULT_PATH); + #if defined(WIN32) +- env2env(e, "SystemRoot"); +- env2env(e, "COMSPEC"); +- env2env(e, "PATHEXT"); +- env2env(e, "WINDIR"); ++ env2env(e, r, "SystemRoot", NULL); ++ env2env(e, r, "COMSPEC", NULL); ++ env2env(e, r, "PATHEXT", NULL); ++ env2env(e, r, "WINDIR", NULL); + #elif defined(OS2) +- env2env(e, "COMSPEC"); +- env2env(e, "ETC"); +- env2env(e, "DPATH"); +- env2env(e, "PERLLIB_PREFIX"); ++ env2env(e, r, "COMSPEC", NULL); ++ env2env(e, r, "ETC", NULL); ++ env2env(e, r, "DPATH", NULL); ++ env2env(e, r, "PERLLIB_PREFIX", NULL); + #elif defined(BEOS) +- env2env(e, "LIBRARY_PATH"); ++ env2env(e, r, "LIBRARY_PATH", NULL); + #elif defined(DARWIN) +- env2env(e, "DYLD_LIBRARY_PATH"); ++ env2env(e, r, "DYLD_LIBRARY_PATH", NULL); + #elif defined(_AIX) +- env2env(e, "LIBPATH"); ++ env2env(e, r, "LIBPATH", NULL); + #elif defined(__HPUX__) + /* HPUX PARISC 2.0W knows both, otherwise redundancy is harmless */ +- env2env(e, "SHLIB_PATH"); +- env2env(e, "LD_LIBRARY_PATH"); ++ env2env(e, r, "SHLIB_PATH", NULL); ++ env2env(e, r, "LD_LIBRARY_PATH", NULL); + #else /* Some Unix */ +- env2env(e, "LD_LIBRARY_PATH"); ++ env2env(e, r, "LD_LIBRARY_PATH", NULL); + #endif + + apr_table_addn(e, "SERVER_SIGNATURE", ap_psignature("", r)); diff --git a/SOURCES/httpd-2.4.6-r1811976.patch b/SOURCES/httpd-2.4.6-r1811976.patch new file mode 100644 index 0000000..166cc9e --- /dev/null +++ b/SOURCES/httpd-2.4.6-r1811976.patch @@ -0,0 +1,156 @@ +diff --git a/docs/manual/mod/mod_ssl.html.en b/docs/manual/mod/mod_ssl.html.en +index 98540cd..4580f1c 100644 +--- a/docs/manual/mod/mod_ssl.html.en ++++ b/docs/manual/mod/mod_ssl.html.en +@@ -197,6 +197,12 @@ the SSLOptions directiv + first (or only) attribute of any DN is added only under a non-suffixed + name; i.e. no _0 suffixed entries are added.

    + ++

    The _RAW suffix may now be added to mod_ssl DN variable names ++(such as SSL_CLIENT_I_O_RAW). When this suffix is used, conversion ++of certificate name attributes to UTF-8 is omitted. This allows variable ++lookups and comparisons for certificates with incorrectly tagged name ++attributes.

    ++ +

    The format of the *_DN variables has changed in Apache HTTPD + 2.3.11. See the LegacyDNStringFormat option for + SSLOptions for details.

    +@@ -861,7 +867,7 @@ SSLEngine on + </VirtualHost> + + +-

    In Apache 2.1 and later, SSLEngine can be set to ++

    In httpd 2.2.0 and later, SSLEngine can be set to + optional. This enables support for + RFC 2817, Upgrading to TLS + Within HTTP/1.1. At this time no web browsers support RFC 2817.

    +diff --git a/modules/ssl/ssl_engine_vars.c b/modules/ssl/ssl_engine_vars.c +index 2b7c9ba..e25a6d4 100644 +--- a/modules/ssl/ssl_engine_vars.c ++++ b/modules/ssl/ssl_engine_vars.c +@@ -41,7 +41,7 @@ + + static char *ssl_var_lookup_ssl(apr_pool_t *p, conn_rec *c, request_rec *r, char *var); + static char *ssl_var_lookup_ssl_cert(apr_pool_t *p, request_rec *r, X509 *xs, char *var); +-static char *ssl_var_lookup_ssl_cert_dn(apr_pool_t *p, X509_NAME *xsname, char *var); ++static char *ssl_var_lookup_ssl_cert_dn(apr_pool_t *p, X509_NAME *xsname, const char *var); + static char *ssl_var_lookup_ssl_cert_san(apr_pool_t *p, X509 *xs, char *var); + static char *ssl_var_lookup_ssl_cert_valid(apr_pool_t *p, ASN1_TIME *tm); + static char *ssl_var_lookup_ssl_cert_remain(apr_pool_t *p, ASN1_TIME *tm); +@@ -562,15 +562,23 @@ static const struct { + { NULL, 0, 0 } + }; + +-static char *ssl_var_lookup_ssl_cert_dn(apr_pool_t *p, X509_NAME *xsname, char *var) ++static char *ssl_var_lookup_ssl_cert_dn(apr_pool_t *p, X509_NAME *xsname, ++ const char *var) + { +- char *result, *ptr; ++ const char *ptr; ++ char *result; + X509_NAME_ENTRY *xsne; +- int i, j, n, idx = 0; ++ int i, j, n, idx = 0, raw = 0; + apr_size_t varlen; + ++ ptr = ap_strrchr_c(var, '_'); ++ if (ptr && ptr > var && strcmp(ptr + 1, "RAW") == 0) { ++ var = apr_pstrmemdup(p, var, ptr - var); ++ raw = 1; ++ } ++ + /* if an _N suffix is used, find the Nth attribute of given name */ +- ptr = strchr(var, '_'); ++ ptr = ap_strchr_c(var, '_'); + if (ptr != NULL && strspn(ptr + 1, "0123456789") == strlen(ptr + 1)) { + idx = atoi(ptr + 1); + varlen = ptr - var; +@@ -592,7 +600,7 @@ static char *ssl_var_lookup_ssl_cert_dn(apr_pool_t *p, X509_NAME *xsname, char * + n =OBJ_obj2nid((ASN1_OBJECT *)X509_NAME_ENTRY_get_object(xsne)); + + if (n == ssl_var_lookup_ssl_cert_dn_rec[i].nid && idx-- == 0) { +- result = SSL_X509_NAME_ENTRY_to_string(p, xsne); ++ result = SSL_X509_NAME_ENTRY_to_string(p, xsne, raw); + break; + } + } +@@ -897,7 +905,7 @@ static void extract_dn(apr_table_t *t, apr_hash_t *nids, const char *pfx, + apr_hash_set(count, &nid, sizeof nid, dup); + key = apr_pstrcat(p, pfx, tag, NULL); + } +- value = SSL_X509_NAME_ENTRY_to_string(p, xsne); ++ value = SSL_X509_NAME_ENTRY_to_string(p, xsne, 0); + apr_table_setn(t, key, value); + } + } +diff --git a/modules/ssl/ssl_util_ssl.c b/modules/ssl/ssl_util_ssl.c +index 09a9877..fbd701f 100644 +--- a/modules/ssl/ssl_util_ssl.c ++++ b/modules/ssl/ssl_util_ssl.c +@@ -236,18 +236,21 @@ BOOL SSL_X509_getBC(X509 *cert, int *ca, int *pathlen) + return TRUE; + } + +-/* convert an ASN.1 string to a UTF-8 string (escaping control characters) */ +-char *SSL_ASN1_STRING_to_utf8(apr_pool_t *p, ASN1_STRING *asn1str) ++/* Convert ASN.1 string to a pool-allocated char * string, escaping ++ * control characters. If raw is zero, convert to UTF-8, otherwise ++ * unchanged from the character set. */ ++char *SSL_ASN1_STRING_convert(apr_pool_t *p, ASN1_STRING *asn1str, int raw) + { + char *result = NULL; + BIO *bio; +- int len; ++ int len, flags = ASN1_STRFLGS_ESC_CTRL; + + if ((bio = BIO_new(BIO_s_mem())) == NULL) + return NULL; + +- ASN1_STRING_print_ex(bio, asn1str, ASN1_STRFLGS_ESC_CTRL| +- ASN1_STRFLGS_UTF8_CONVERT); ++ if (!raw) flags |= ASN1_STRFLGS_UTF8_CONVERT; ++ ++ ASN1_STRING_print_ex(bio, asn1str, flags); + len = BIO_pending(bio); + if (len > 0) { + result = apr_palloc(p, len+1); +@@ -258,10 +261,13 @@ char *SSL_ASN1_STRING_to_utf8(apr_pool_t *p, ASN1_STRING *asn1str) + return result; + } + ++#define SSL_ASN1_STRING_to_utf8(p, a) SSL_ASN1_STRING_convert(p, a, 0) ++ + /* convert a NAME_ENTRY to UTF8 string */ +-char *SSL_X509_NAME_ENTRY_to_string(apr_pool_t *p, X509_NAME_ENTRY *xsne) ++char *SSL_X509_NAME_ENTRY_to_string(apr_pool_t *p, X509_NAME_ENTRY *xsne, ++ int raw) + { +- char *result = SSL_ASN1_STRING_to_utf8(p, X509_NAME_ENTRY_get_data(xsne)); ++ char *result = SSL_ASN1_STRING_convert(p, X509_NAME_ENTRY_get_data(xsne), raw); + ap_xlate_proto_from_ascii(result, len); + return result; + } +@@ -414,7 +420,7 @@ BOOL SSL_X509_getIDs(apr_pool_t *p, X509 *x509, apr_array_header_t **ids) + subj = X509_get_subject_name(x509); + while ((i = X509_NAME_get_index_by_NID(subj, NID_commonName, i)) != -1) { + APR_ARRAY_PUSH(*ids, const char *) = +- SSL_X509_NAME_ENTRY_to_string(p, X509_NAME_get_entry(subj, i)); ++ SSL_X509_NAME_ENTRY_to_string(p, X509_NAME_get_entry(subj, i), 0); + } + + return apr_is_empty_array(*ids) ? FALSE : TRUE; +diff --git a/modules/ssl/ssl_util_ssl.h b/modules/ssl/ssl_util_ssl.h +index be07ab7..611957e 100644 +--- a/modules/ssl/ssl_util_ssl.h ++++ b/modules/ssl/ssl_util_ssl.h +@@ -65,8 +65,8 @@ EVP_PKEY *SSL_read_PrivateKey(char *, EVP_PKEY **, pem_password_cb *, void *); + int SSL_smart_shutdown(SSL *ssl); + BOOL SSL_X509_isSGC(X509 *); + BOOL SSL_X509_getBC(X509 *, int *, int *); +-char *SSL_ASN1_STRING_to_utf8(apr_pool_t *, ASN1_STRING *); +-char *SSL_X509_NAME_ENTRY_to_string(apr_pool_t *p, X509_NAME_ENTRY *xsne); ++char *SSL_ASN1_STRING_to_utf8(apr_pool_t *, ASN1_STRING *, int raw); ++char *SSL_X509_NAME_ENTRY_to_string(apr_pool_t *p, X509_NAME_ENTRY *xsne, int raw); + char *SSL_X509_NAME_to_string(apr_pool_t *, X509_NAME *, int); + BOOL SSL_X509_getSAN(apr_pool_t *, X509 *, int, const char *, int, apr_array_header_t **); + BOOL SSL_X509_getIDs(apr_pool_t *, X509 *, apr_array_header_t **); diff --git a/SOURCES/ssl.conf b/SOURCES/ssl.conf index 58eaf3b..5283a93 100644 --- a/SOURCES/ssl.conf +++ b/SOURCES/ssl.conf @@ -72,12 +72,12 @@ SSLEngine on # SSL Protocol support: # List the enable protocol levels with which clients will be able to # connect. Disable SSLv2 access by default: -SSLProtocol all -SSLv2 +SSLProtocol all -SSLv2 -SSLv3 # SSL Cipher Suite: # List the ciphers that the client is permitted to negotiate. # See the mod_ssl documentation for a complete list. -SSLCipherSuite HIGH:MEDIUM:!aNULL:!MD5:!SEED:!IDEA +SSLCipherSuite HIGH:3DES:!aNULL:!MD5:!SEED:!IDEA # Speed-optimized SSL Cipher configuration: # If speed is your main concern (on busy HTTPS servers e.g.), diff --git a/SOURCES/welcome.conf b/SOURCES/welcome.conf index c1b6c11..5d1e452 100644 --- a/SOURCES/welcome.conf +++ b/SOURCES/welcome.conf @@ -16,7 +16,3 @@ Alias /.noindex.html /usr/share/httpd/noindex/index.html -Alias /noindex/css/bootstrap.min.css /usr/share/httpd/noindex/css/bootstrap.min.css -Alias /noindex/css/open-sans.css /usr/share/httpd/noindex/css/open-sans.css -Alias /images/apache_pb.gif /usr/share/httpd/noindex/images/apache_pb.gif -Alias /images/poweredby.png /usr/share/httpd/noindex/images/poweredby.png diff --git a/SPECS/httpd.spec b/SPECS/httpd.spec index 2015cf3..96c6b3a 100644 --- a/SPECS/httpd.spec +++ b/SPECS/httpd.spec @@ -4,7 +4,7 @@ %define mmn 20120211 %define oldmmnisa %{mmn}-%{__isa_name}-%{__isa_bits} %define mmnisa %{mmn}%{__isa_name}%{__isa_bits} -%define vstring CentOS +%define vstring %(source /etc/os-release; echo ${REDHAT_SUPPORT_PRODUCT}) # Drop automatic provides for module DSOs %{?filter_setup: @@ -15,10 +15,10 @@ Summary: Apache HTTP Server Name: httpd Version: 2.4.6 -Release: 67%{?dist}.6 +Release: 80%{?dist} URL: http://httpd.apache.org/ Source0: http://www.apache.org/dist/httpd/httpd-%{version}.tar.bz2 -Source1: centos-noindex.tar.gz +Source1: index.html Source2: httpd.logrotate Source3: httpd.sysconf Source4: httpd-ssl-pass-dialog @@ -154,8 +154,24 @@ Patch120: httpd-2.4.6-r1738878.patch Patch121: httpd-2.4.6-http-protocol-options-define.patch # https://bugzilla.redhat.com/show_bug.cgi?id=1332242 Patch122: httpd-2.4.6-statements-comment.patch -# https://bugzilla.redhat.com/show_bug.cgi?id=1467402 +# https://bugzilla.redhat.com/show_bug.cgi?id=1451333 Patch123: httpd-2.4.6-rotatelogs-zombie.patch +# https://bugzilla.redhat.com/show_bug.cgi?id=1368491 +Patch124: httpd-2.4.6-mod_authz_dbd-missing-query.patch +# https://bugzilla.redhat.com/show_bug.cgi?id=1288395 +Patch125: httpd-2.4.6-r1668532.patch +# https://bugzilla.redhat.com/show_bug.cgi?id=1499253 +Patch126: httpd-2.4.6-r1681289.patch +# https://bugzilla.redhat.com/show_bug.cgi?id=1430640 +Patch127: httpd-2.4.6-r1805099.patch +# https://bugzilla.redhat.com/show_bug.cgi?id=1448892 +Patch128: httpd-2.4.6-r1811831.patch +# https://bugzilla.redhat.com/show_bug.cgi?id=1464406 +Patch129: httpd-2.4.6-r1811746.patch +# https://bugzilla.redhat.com/show_bug.cgi?id=1440590 +Patch130: httpd-2.4.6-r1811976.patch +# https://bugzilla.redhat.com/show_bug.cgi?id=1506392 +Patch131: httpd-2.4.6-r1650310.patch # Security fixes Patch200: httpd-2.4.6-CVE-2013-6438.patch @@ -383,6 +399,14 @@ rm modules/ssl/ssl_engine_dh.c %patch121 -p1 -b .httpprotdefine %patch122 -p1 -b .statement-comment %patch123 -p1 -b .logrotate-zombie +%patch124 -p1 -b .modauthzdbd-segfault +%patch125 -p1 -b .r1668532 +%patch126 -p1 -b .r1681289 +%patch127 -p1 -b .r1805099 +%patch128 -p1 -b .r1811831 +%patch129 -p1 -b .r1811746 +%patch130 -p1 -b .r1811976 +%patch131 -p1 -b .r1650310 %patch200 -p1 -b .cve6438 %patch201 -p1 -b .cve0098 @@ -558,10 +582,8 @@ EOF # Handle contentdir mkdir $RPM_BUILD_ROOT%{contentdir}/noindex -tar xzf $RPM_SOURCE_DIR/centos-noindex.tar.gz \ - -C $RPM_BUILD_ROOT%{contentdir}/noindex/ \ - --strip-components=1 - +install -m 644 -p $RPM_SOURCE_DIR/index.html \ + $RPM_BUILD_ROOT%{contentdir}/noindex/index.html rm -rf %{contentdir}/htdocs # remove manual sources @@ -584,7 +606,7 @@ rm -v $RPM_BUILD_ROOT%{docroot}/html/*.html \ $RPM_BUILD_ROOT%{docroot}/cgi-bin/* # Symlink for the powered-by-$DISTRO image: -ln -s ../noindex/images/poweredby.png \ +ln -s ../../pixmaps/poweredby.png \ $RPM_BUILD_ROOT%{contentdir}/icons/poweredby.png # symlinks for /etc/httpd @@ -770,7 +792,7 @@ rm -rf $RPM_BUILD_ROOT %{contentdir}/error/README %{contentdir}/error/*.var %{contentdir}/error/include/*.html -%{contentdir}/noindex/* +%{contentdir}/noindex/index.html %dir %{docroot} %dir %{docroot}/cgi-bin @@ -836,20 +858,48 @@ rm -rf $RPM_BUILD_ROOT %{_sysconfdir}/rpm/macros.httpd %changelog -* Thu Oct 19 2017 CentOS Sources - 2.4.6-67.el7.centos.6 -- Remove index.html, add centos-noindex.tar.gz -- change vstring -- change symlink for poweredby.png -- update welcome.conf with proper aliases +* Mon Jan 08 2018 Luboš Uhliarik - 2.4.6-80 +- Related: #1288395 - httpd segfault when logrotate invoked + +* Wed Nov 01 2017 Luboš Uhliarik - 2.4.6-79 +- Resolves: #1274890 - mod_ssl config: tighten defaults + +* Tue Oct 31 2017 Luboš Uhliarik - 2.4.6-78 +- Resolves: #1506392 - Backport: SSLSessionTickets directive support + +* Mon Oct 16 2017 Luboš Uhliarik - 2.4.6-77 +- Resolves: #1440590 - Need an option to disable UTF8-conversion + of certificate DN + +* Thu Oct 12 2017 Luboš Uhliarik - 2.4.6-76 +- Resolves: #1464406 - Apache consumes too much memory for CGI output + +* Thu Oct 12 2017 Luboš Uhliarik - 2.4.6-75 +- Resolves: #1448892 - Cannot override LD_LIBARY_PATH in Apache HTTPD + using SetEnv or PassEnv. Needs documentation. + +* Mon Oct 09 2017 Luboš Uhliarik - 2.4.6-74 +- Resolves: #1430640 - "ProxyAddHeaders Off" does not become effective + when it's defined outside setting + +* Fri Oct 06 2017 Luboš Uhliarik - 2.4.6-73 +- Resolves: #1499253 - ProxyRemote with HTTPS backend sends requests + with absoluteURI instead of abs_path + +* Tue Oct 03 2017 Luboš Uhliarik - 2.4.6-72 +- Resolves: #1288395 - httpd segfault when logrotate invoked + +* Tue Oct 03 2017 Luboš Uhliarik - 2.4.6-71 +- Resolves: #1368491 - mod_authz_dbd segfaults when AuthzDBDQuery missing -* Tue Oct 03 2017 Luboš Uhliarik - 2.4.6-67.6 -- Resolves: #1498020 - rotatelogs: creation of zombie processes when -p is used +* Mon Oct 02 2017 Luboš Uhliarik - 2.4.6-70 +- Resolves: #1467402 - rotatelogs: creation of zombie processes when -p is used -* Tue Sep 19 2017 Luboš Uhliarik - 2.4.6-67.5 -- Resolves: #1493064 - CVE-2017-9798 httpd: Use-after-free by limiting +* Tue Sep 19 2017 Luboš Uhliarik - 2.4.6-69 +- Resolves: #1493065 - CVE-2017-9798 httpd: Use-after-free by limiting unregistered HTTP method -* Wed Jul 26 2017 Luboš Uhliarik - 2.4.6-67.2 +* Tue Jul 25 2017 Luboš Uhliarik - 2.4.6-68 - Resolves: #1463194 - CVE-2017-3167 httpd: ap_get_basic_auth_pw() authentication bypass - Resolves: #1463197 - CVE-2017-3169 httpd: mod_ssl NULL pointer dereference