Browse Source

httpd package update

Signed-off-by: webbuilder_pel7ppc64lebuilder0 <webbuilder@powerel.org>
master
webbuilder_pel7ppc64lebuilder0 5 years ago
parent
commit
436fa04fbf
  1. 399
      SOURCES/httpd-2.4.6-CVE-2018-1312.patch
  2. 113
      SOURCES/httpd-2.4.6-CVE-2019-0217.patch
  3. 244
      SOURCES/httpd-2.4.6-CVE-2019-0220.patch
  4. 13
      SOURCES/httpd-2.4.6-default-port-worker.patch
  5. 11
      SOURCES/httpd-2.4.6-mpm-segfault.patch
  6. 11
      SOURCES/httpd-2.4.6-r1515372.patch
  7. 265
      SOURCES/httpd-2.4.6-r1555539.patch
  8. 26
      SOURCES/httpd-2.4.6-r1737363.patch
  9. 25
      SOURCES/httpd-2.4.6-r1824872.patch
  10. 96
      SOURCES/httpd-2.4.6-r1825120.patch
  11. 198
      SOURCES/httpd-2.4.6-r1826995.patch
  12. 83
      SOURCES/httpd-2.4.6-r1833014.patch
  13. 35
      SPECS/httpd.spec

399
SOURCES/httpd-2.4.6-CVE-2018-1312.patch

@ -0,0 +1,399 @@ @@ -0,0 +1,399 @@
diff --git a/modules/aaa/mod_auth_digest.c b/modules/aaa/mod_auth_digest.c
index cbb4434..b50bcf9 100644
--- a/modules/aaa/mod_auth_digest.c
+++ b/modules/aaa/mod_auth_digest.c
@@ -26,20 +26,13 @@
* reports to the Apache bug-database, or send them directly to me
* at ronald@innovation.ch.
*
- * Requires either /dev/random (or equivalent) or the truerand library,
- * available for instance from
- * ftp://research.att.com/dist/mab/librand.shar
- *
* Open Issues:
* - qop=auth-int (when streams and trailer support available)
* - nonce-format configurability
* - Proxy-Authorization-Info header is set by this module, but is
* currently ignored by mod_proxy (needs patch to mod_proxy)
- * - generating the secret takes a while (~ 8 seconds) if using the
- * truerand library
* - The source of the secret should be run-time directive (with server
- * scope: RSRC_CONF). However, that could be tricky when trying to
- * choose truerand vs. file...
+ * scope: RSRC_CONF)
* - shared-mem not completely tested yet. Seems to work ok for me,
* but... (definitely won't work on Windoze)
* - Sharing a realm among multiple servers has following problems:
@@ -52,6 +45,8 @@
* captures a packet sent to one server and sends it to another
* one. Should we add "AuthDigestNcCheck Strict"?
* - expired nonces give amaya fits.
+ * - MD5-sess and auth-int are not yet implemented. An incomplete
+ * implementation has been removed and can be retrieved from svn history.
*/
#include "apr_sha1.h"
@@ -94,7 +89,6 @@ typedef struct digest_config_struct {
apr_array_header_t *qop_list;
apr_sha1_ctx_t nonce_ctx;
apr_time_t nonce_lifetime;
- const char *nonce_format;
int check_nc;
const char *algorithm;
char *uri_list;
@@ -112,7 +106,8 @@ typedef struct digest_config_struct {
#define NONCE_HASH_LEN (2*APR_SHA1_DIGESTSIZE)
#define NONCE_LEN (int )(NONCE_TIME_LEN + NONCE_HASH_LEN)
-#define SECRET_LEN 20
+#define SECRET_LEN 20
+#define RETAINED_DATA_ID "mod_auth_digest"
/* client list definitions */
@@ -121,7 +116,6 @@ typedef struct hash_entry {
unsigned long key; /* the key for this entry */
struct hash_entry *next; /* next entry in the bucket */
unsigned long nonce_count; /* for nonce-count checking */
- char ha1[2*APR_MD5_DIGESTSIZE+1]; /* for algorithm=MD5-sess */
char last_nonce[NONCE_LEN+1]; /* for one-time nonce's */
} client_entry;
@@ -170,7 +164,7 @@ typedef union time_union {
unsigned char arr[sizeof(apr_time_t)];
} time_rec;
-static unsigned char secret[SECRET_LEN];
+static unsigned char *secret;
/* client-list, opaque, and one-time-nonce stuff */
@@ -228,35 +222,11 @@ static apr_status_t cleanup_tables(void *not_used)
return APR_SUCCESS;
}
-static apr_status_t initialize_secret(server_rec *s)
-{
- apr_status_t status;
-
- ap_log_error(APLOG_MARK, APLOG_NOTICE, 0, s, APLOGNO(01757)
- "generating secret for digest authentication ...");
-
-#if APR_HAS_RANDOM
- status = apr_generate_random_bytes(secret, sizeof(secret));
-#else
-#error APR random number support is missing; you probably need to install the truerand library.
-#endif
-
- if (status != APR_SUCCESS) {
- ap_log_error(APLOG_MARK, APLOG_CRIT, status, s, APLOGNO(01758)
- "error generating secret");
- return status;
- }
-
- ap_log_error(APLOG_MARK, APLOG_DEBUG, 0, s, APLOGNO(01759) "done");
-
- return APR_SUCCESS;
-}
-
static void log_error_and_cleanup(char *msg, apr_status_t sts, server_rec *s)
{
ap_log_error(APLOG_MARK, APLOG_ERR, sts, s, APLOGNO(01760)
- "%s - all nonce-count checking, one-time nonces, and "
- "MD5-sess algorithm disabled", msg);
+ "%s - all nonce-count checking and one-time nonces"
+ "disabled", msg);
cleanup_tables(NULL);
}
@@ -377,16 +347,32 @@ static int initialize_tables(server_rec *s, apr_pool_t *ctx)
static int pre_init(apr_pool_t *pconf, apr_pool_t *plog, apr_pool_t *ptemp)
{
apr_status_t rv;
+ void *retained;
rv = ap_mutex_register(pconf, client_mutex_type, NULL, APR_LOCK_DEFAULT, 0);
- if (rv == APR_SUCCESS) {
- rv = ap_mutex_register(pconf, opaque_mutex_type, NULL, APR_LOCK_DEFAULT,
- 0);
- }
- if (rv != APR_SUCCESS) {
- return rv;
- }
+ if (rv != APR_SUCCESS)
+ return !OK;
+ rv = ap_mutex_register(pconf, opaque_mutex_type, NULL, APR_LOCK_DEFAULT, 0);
+ if (rv != APR_SUCCESS)
+ return !OK;
+ retained = ap_retained_data_get(RETAINED_DATA_ID);
+ if (retained == NULL) {
+ retained = ap_retained_data_create(RETAINED_DATA_ID, SECRET_LEN);
+ ap_log_error(APLOG_MARK, APLOG_DEBUG, 0, NULL, APLOGNO(01757)
+ "generating secret for digest authentication");
+#if APR_HAS_RANDOM
+ rv = apr_generate_random_bytes(retained, SECRET_LEN);
+#else
+#error APR random number support is missing
+#endif
+ if (rv != APR_SUCCESS) {
+ ap_log_error(APLOG_MARK, APLOG_CRIT, rv, NULL, APLOGNO(01758)
+ "error generating secret");
+ return !OK;
+ }
+ }
+ secret = retained;
return OK;
}
@@ -399,10 +385,6 @@ static int initialize_module(apr_pool_t *p, apr_pool_t *plog,
if (ap_state_query(AP_SQ_MAIN_STATE) == AP_SQ_MS_CREATE_PRE_CONFIG)
return OK;
- if (initialize_secret(s) != APR_SUCCESS) {
- return !OK;
- }
-
#if APR_HAS_SHARED_MEMORY
/* Note: this stuff is currently fixed for the lifetime of the server,
* i.e. even across restarts. This means that A) any shmem-size
@@ -483,6 +465,16 @@ static void *create_digest_dir_config(apr_pool_t *p, char *dir)
static const char *set_realm(cmd_parms *cmd, void *config, const char *realm)
{
digest_config_rec *conf = (digest_config_rec *) config;
+#ifdef AP_DEBUG
+ int i;
+
+ /* check that we got random numbers */
+ for (i = 0; i < SECRET_LEN; i++) {
+ if (secret[i] != 0)
+ break;
+ }
+ ap_assert(i < SECRET_LEN);
+#endif
/* The core already handles the realm, but it's just too convenient to
* grab it ourselves too and cache some setups. However, we need to
@@ -496,7 +488,7 @@ static const char *set_realm(cmd_parms *cmd, void *config, const char *realm)
* and directives outside a virtual host section)
*/
apr_sha1_init(&conf->nonce_ctx);
- apr_sha1_update_binary(&conf->nonce_ctx, secret, sizeof(secret));
+ apr_sha1_update_binary(&conf->nonce_ctx, secret, SECRET_LEN);
apr_sha1_update_binary(&conf->nonce_ctx, (const unsigned char *) realm,
strlen(realm));
@@ -590,8 +582,7 @@ static const char *set_nonce_lifetime(cmd_parms *cmd, void *config,
static const char *set_nonce_format(cmd_parms *cmd, void *config,
const char *fmt)
{
- ((digest_config_rec *) config)->nonce_format = fmt;
- return "AuthDigestNonceFormat is not implemented (yet)";
+ return "AuthDigestNonceFormat is not implemented";
}
static const char *set_nc_check(cmd_parms *cmd, void *config, int flag)
@@ -612,7 +603,7 @@ static const char *set_algorithm(cmd_parms *cmd, void *config, const char *alg)
{
if (!strcasecmp(alg, "MD5-sess")) {
return "AuthDigestAlgorithm: ERROR: algorithm `MD5-sess' "
- "is not fully implemented";
+ "is not implemented";
}
else if (strcasecmp(alg, "MD5")) {
return apr_pstrcat(cmd->pool, "Invalid algorithm in AuthDigestAlgorithm: ", alg, NULL);
@@ -1138,7 +1129,7 @@ static const char *gen_nonce(apr_pool_t *p, apr_time_t now, const char *opaque,
static client_entry *gen_client(const request_rec *r)
{
unsigned long op;
- client_entry new_entry = { 0, NULL, 0, "", "" }, *entry;
+ client_entry new_entry = { 0, NULL, 0, "" }, *entry;
if (!opaque_cntr) {
return NULL;
@@ -1158,92 +1149,6 @@ static client_entry *gen_client(const request_rec *r)
}
-/*
- * MD5-sess code.
- *
- * If you want to use algorithm=MD5-sess you must write get_userpw_hash()
- * yourself (see below). The dummy provided here just uses the hash from
- * the auth-file, i.e. it is only useful for testing client implementations
- * of MD5-sess .
- */
-
-/*
- * get_userpw_hash() will be called each time a new session needs to be
- * generated and is expected to return the equivalent of
- *
- * h_urp = ap_md5(r->pool,
- * apr_pstrcat(r->pool, username, ":", ap_auth_name(r), ":", passwd))
- * ap_md5(r->pool,
- * (unsigned char *) apr_pstrcat(r->pool, h_urp, ":", resp->nonce, ":",
- * resp->cnonce, NULL));
- *
- * or put differently, it must return
- *
- * MD5(MD5(username ":" realm ":" password) ":" nonce ":" cnonce)
- *
- * If something goes wrong, the failure must be logged and NULL returned.
- *
- * You must implement this yourself, which will probably consist of code
- * contacting the password server with the necessary information (typically
- * the username, realm, nonce, and cnonce) and receiving the hash from it.
- *
- * TBD: This function should probably be in a separate source file so that
- * people need not modify mod_auth_digest.c each time they install a new
- * version of apache.
- */
-static const char *get_userpw_hash(const request_rec *r,
- const digest_header_rec *resp,
- const digest_config_rec *conf)
-{
- return ap_md5(r->pool,
- (unsigned char *) apr_pstrcat(r->pool, conf->ha1, ":", resp->nonce,
- ":", resp->cnonce, NULL));
-}
-
-
-/* Retrieve current session H(A1). If there is none and "generate" is
- * true then a new session for MD5-sess is generated and stored in the
- * client struct; if generate is false, or a new session could not be
- * generated then NULL is returned (in case of failure to generate the
- * failure reason will have been logged already).
- */
-static const char *get_session_HA1(const request_rec *r,
- digest_header_rec *resp,
- const digest_config_rec *conf,
- int generate)
-{
- const char *ha1 = NULL;
-
- /* return the current sessions if there is one */
- if (resp->opaque && resp->client && resp->client->ha1[0]) {
- return resp->client->ha1;
- }
- else if (!generate) {
- return NULL;
- }
-
- /* generate a new session */
- if (!resp->client) {
- resp->client = gen_client(r);
- }
- if (resp->client) {
- ha1 = get_userpw_hash(r, resp, conf);
- if (ha1) {
- memcpy(resp->client->ha1, ha1, sizeof(resp->client->ha1));
- }
- }
-
- return ha1;
-}
-
-
-static void clear_session(const digest_header_rec *resp)
-{
- if (resp->client) {
- resp->client->ha1[0] = '\0';
- }
-}
-
/*
* Authorization challenge generation code (for WWW-Authenticate)
*/
@@ -1282,8 +1187,7 @@ static void note_digest_auth_failure(request_rec *r,
if (resp->opaque == NULL) {
/* new client */
- if ((conf->check_nc || conf->nonce_lifetime == 0
- || !strcasecmp(conf->algorithm, "MD5-sess"))
+ if ((conf->check_nc || conf->nonce_lifetime == 0)
&& (resp->client = gen_client(r)) != NULL) {
opaque = ltox(r->pool, resp->client->key);
}
@@ -1323,15 +1227,6 @@ static void note_digest_auth_failure(request_rec *r,
memcpy(resp->client->last_nonce, nonce, NONCE_LEN+1);
}
- /* Setup MD5-sess stuff. Note that we just clear out the session
- * info here, since we can't generate a new session until the request
- * from the client comes in with the cnonce.
- */
-
- if (!strcasecmp(conf->algorithm, "MD5-sess")) {
- clear_session(resp);
- }
-
/* setup domain attribute. We want to send this attribute wherever
* possible so that the client won't send the Authorization header
* unnecessarily (it's usually > 200 bytes!).
@@ -1597,24 +1492,9 @@ static const char *new_digest(const request_rec *r,
{
const char *ha1, *ha2, *a2;
- if (resp->algorithm && !strcasecmp(resp->algorithm, "MD5-sess")) {
- ha1 = get_session_HA1(r, resp, conf, 1);
- if (!ha1) {
- return NULL;
- }
- }
- else {
- ha1 = conf->ha1;
- }
+ ha1 = conf->ha1;
- if (resp->message_qop && !strcasecmp(resp->message_qop, "auth-int")) {
- a2 = apr_pstrcat(r->pool, resp->method, ":", resp->uri, ":",
- ap_md5(r->pool, (const unsigned char*) ""), NULL);
- /* TBD */
- }
- else {
- a2 = apr_pstrcat(r->pool, resp->method, ":", resp->uri, NULL);
- }
+ a2 = apr_pstrcat(r->pool, resp->method, ":", resp->uri, NULL);
ha2 = ap_md5(r->pool, (const unsigned char *)a2);
return ap_md5(r->pool,
@@ -1854,8 +1734,7 @@ static int authenticate_digest_user(request_rec *r)
}
if (resp->algorithm != NULL
- && strcasecmp(resp->algorithm, "MD5")
- && strcasecmp(resp->algorithm, "MD5-sess")) {
+ && strcasecmp(resp->algorithm, "MD5")) {
ap_log_rerror(APLOG_MARK, APLOG_ERR, 0, r, APLOGNO(01789)
"unknown algorithm `%s' received: %s",
resp->algorithm, r->uri);
@@ -2007,27 +1886,9 @@ static int add_auth_info(request_rec *r)
/* calculate rspauth attribute
*/
- if (resp->algorithm && !strcasecmp(resp->algorithm, "MD5-sess")) {
- ha1 = get_session_HA1(r, resp, conf, 0);
- if (!ha1) {
- ap_log_rerror(APLOG_MARK, APLOG_ERR, 0, r, APLOGNO(01795)
- "internal error: couldn't find session "
- "info for user %s", resp->username);
- return !OK;
- }
- }
- else {
- ha1 = conf->ha1;
- }
+ ha1 = conf->ha1;
- if (resp->message_qop && !strcasecmp(resp->message_qop, "auth-int")) {
- a2 = apr_pstrcat(r->pool, ":", resp->uri, ":",
- ap_md5(r->pool,(const unsigned char *) ""), NULL);
- /* TBD */
- }
- else {
- a2 = apr_pstrcat(r->pool, ":", resp->uri, NULL);
- }
+ a2 = apr_pstrcat(r->pool, ":", resp->uri, NULL);
ha2 = ap_md5(r->pool, (const unsigned char *)a2);
resp_dig = ap_md5(r->pool,

113
SOURCES/httpd-2.4.6-CVE-2019-0217.patch

@ -0,0 +1,113 @@ @@ -0,0 +1,113 @@
diff --git a/modules/aaa/mod_auth_digest.c b/modules/aaa/mod_auth_digest.c
index b50bcf9..5bfec82 100644
--- a/modules/aaa/mod_auth_digest.c
+++ b/modules/aaa/mod_auth_digest.c
@@ -92,7 +92,6 @@ typedef struct digest_config_struct {
int check_nc;
const char *algorithm;
char *uri_list;
- const char *ha1;
} digest_config_rec;
@@ -153,6 +152,7 @@ typedef struct digest_header_struct {
apr_time_t nonce_time;
enum hdr_sts auth_hdr_sts;
int needed_auth;
+ const char *ha1;
client_entry *client;
} digest_header_rec;
@@ -1295,7 +1295,7 @@ static int hook_note_digest_auth_failure(request_rec *r, const char *auth_type)
*/
static authn_status get_hash(request_rec *r, const char *user,
- digest_config_rec *conf)
+ digest_config_rec *conf, const char **rethash)
{
authn_status auth_result;
char *password;
@@ -1347,7 +1347,7 @@ static authn_status get_hash(request_rec *r, const char *user,
} while (current_provider);
if (auth_result == AUTH_USER_FOUND) {
- conf->ha1 = password;
+ *rethash = password;
}
return auth_result;
@@ -1474,25 +1474,24 @@ static int check_nonce(request_rec *r, digest_header_rec *resp,
/* RFC-2069 */
static const char *old_digest(const request_rec *r,
- const digest_header_rec *resp, const char *ha1)
+ const digest_header_rec *resp)
{
const char *ha2;
ha2 = ap_md5(r->pool, (unsigned char *)apr_pstrcat(r->pool, resp->method, ":",
resp->uri, NULL));
return ap_md5(r->pool,
- (unsigned char *)apr_pstrcat(r->pool, ha1, ":", resp->nonce,
- ":", ha2, NULL));
+ (unsigned char *)apr_pstrcat(r->pool, resp->ha1, ":",
+ resp->nonce, ":", ha2, NULL));
}
/* RFC-2617 */
static const char *new_digest(const request_rec *r,
- digest_header_rec *resp,
- const digest_config_rec *conf)
+ digest_header_rec *resp)
{
const char *ha1, *ha2, *a2;
- ha1 = conf->ha1;
+ ha1 = resp->ha1;
a2 = apr_pstrcat(r->pool, resp->method, ":", resp->uri, NULL);
ha2 = ap_md5(r->pool, (const unsigned char *)a2);
@@ -1505,7 +1504,6 @@ static const char *new_digest(const request_rec *r,
NULL));
}
-
static void copy_uri_components(apr_uri_t *dst,
apr_uri_t *src, request_rec *r) {
if (src->scheme && src->scheme[0] != '\0') {
@@ -1742,7 +1740,7 @@ static int authenticate_digest_user(request_rec *r)
return HTTP_UNAUTHORIZED;
}
- return_code = get_hash(r, r->user, conf);
+ return_code = get_hash(r, r->user, conf, &resp->ha1);
if (return_code == AUTH_USER_NOT_FOUND) {
ap_log_rerror(APLOG_MARK, APLOG_ERR, 0, r, APLOGNO(01790)
@@ -1772,7 +1770,7 @@ static int authenticate_digest_user(request_rec *r)
if (resp->message_qop == NULL) {
/* old (rfc-2069) style digest */
- if (strcmp(resp->digest, old_digest(r, resp, conf->ha1))) {
+ if (strcmp(resp->digest, old_digest(r, resp))) {
ap_log_rerror(APLOG_MARK, APLOG_ERR, 0, r, APLOGNO(01792)
"user %s: password mismatch: %s", r->user,
r->uri);
@@ -1802,7 +1800,7 @@ static int authenticate_digest_user(request_rec *r)
return HTTP_UNAUTHORIZED;
}
- exp_digest = new_digest(r, resp, conf);
+ exp_digest = new_digest(r, resp);
if (!exp_digest) {
/* we failed to allocate a client struct */
return HTTP_INTERNAL_SERVER_ERROR;
@@ -1886,7 +1884,7 @@ static int add_auth_info(request_rec *r)
/* calculate rspauth attribute
*/
- ha1 = conf->ha1;
+ ha1 = resp->ha1;
a2 = apr_pstrcat(r->pool, ":", resp->uri, NULL);
ha2 = ap_md5(r->pool, (const unsigned char *)a2);

244
SOURCES/httpd-2.4.6-CVE-2019-0220.patch

@ -0,0 +1,244 @@ @@ -0,0 +1,244 @@
diff --git a/docs/manual/mod/core.html.en b/docs/manual/mod/core.html.en
index 86d9bee..e08034b 100644
--- a/docs/manual/mod/core.html.en
+++ b/docs/manual/mod/core.html.en
@@ -90,6 +90,7 @@ available</td></tr>
<li><img alt="" src="../images/down.gif" /> <a href="#maxrangeoverlaps">MaxRangeOverlaps</a></li>
<li><img alt="" src="../images/down.gif" /> <a href="#maxrangereversals">MaxRangeReversals</a></li>
<li><img alt="" src="../images/down.gif" /> <a href="#maxranges">MaxRanges</a></li>
+<li><img alt="" src="../images/down.gif" /> <a href="#mergeslashes">MergeSlashes</a></li>
<li><img alt="" src="../images/down.gif" /> <a href="#mutex">Mutex</a></li>
<li><img alt="" src="../images/down.gif" /> <a href="#namevirtualhost">NameVirtualHost</a></li>
<li><img alt="" src="../images/down.gif" /> <a href="#options">Options</a></li>
@@ -3170,6 +3171,30 @@ resource </td></tr>
</div>
<div class="top"><a href="#page-header"><img alt="top" src="../images/up.gif" /></a></div>
+<div class="directive-section"><h2><a name="MergeSlashes" id="MergeSlashes">MergeSlashes</a> <a name="mergeslashes" id="mergeslashes">Directive</a></h2>
+<table class="directive">
+<tr><th><a href="directive-dict.html#Description">Description:</a></th><td>Controls whether the server merges consecutive slashes in URLs. </td></tr>
+<tr><th><a href="directive-dict.html#Syntax">Syntax:</a></th><td><code>MergeSlashes ON | OFF</code></td></tr>
+<tr><th><a href="directive-dict.html#Default">Default:</a></th><td><code>MergeSlashes ON</code></td></tr>
+<tr><th><a href="directive-dict.html#Context">Context:</a></th><td>server config, virtual host</td></tr>
+<tr><th><a href="directive-dict.html#Status">Status:</a></th><td>Core</td></tr>
+<tr><th><a href="directive-dict.html#Module">Module:</a></th><td>core</td></tr>
+<tr><th><a href="directive-dict.html#Compatibility">Compatibility:</a></th><td>Available in Apache HTTP Server 2.4.6 in Red Hat Enterprise Linux 7</td></tr>
+</table>
+ <p>By default, the server merges (or collapses) multiple consecutive slash
+ ('/') characters in the path component of the request URL.</p>
+
+ <p>When mapping URL's to the filesystem, these multiple slashes are not
+ significant. However, URL's handled other ways, such as by CGI or proxy,
+ might prefer to retain the significance of multiple consecutive slashes.
+ In these cases <code class="directive">MergeSlashes</code> can be set to
+ <em>OFF</em> to retain the multiple consecutive slashes. In these
+ configurations, regular expressions used in the configuration file that match
+ the path component of the URL (<code class="directive">LocationMatch</code>,
+ <code class="directive">RewriteRule</code>, ...) need to take into account multiple
+ consecutive slashes.</p>
+</div>
+<div class="top"><a href="#page-header"><img alt="top" src="../images/up.gif" /></a></div>
<div class="directive-section"><h2><a name="Mutex" id="Mutex">Mutex</a> <a name="mutex" id="mutex">Directive</a></h2>
<table class="directive">
<tr><th><a href="directive-dict.html#Description">Description:</a></th><td>Configures mutex mechanism and lock file directory for all
diff --git a/include/http_core.h b/include/http_core.h
index c05d06e..76bf5a4 100644
--- a/include/http_core.h
+++ b/include/http_core.h
@@ -465,6 +465,17 @@ typedef unsigned long etag_components_t;
/* This is the default value used */
#define ETAG_BACKWARD (ETAG_MTIME | ETAG_SIZE)
+/* Generic ON/OFF/UNSET for unsigned int foo :2 */
+#define AP_CORE_CONFIG_OFF (0)
+#define AP_CORE_CONFIG_ON (1)
+#define AP_CORE_CONFIG_UNSET (2)
+
+/* Generic merge of flag */
+#define AP_CORE_MERGE_FLAG(field, to, base, over) to->field = \
+ over->field != AP_CORE_CONFIG_UNSET \
+ ? over->field \
+ : base->field
+
/**
* @brief Server Signature Enumeration
*/
@@ -682,7 +693,7 @@ typedef struct {
#define AP_HTTP_METHODS_LENIENT 1
#define AP_HTTP_METHODS_REGISTERED 2
char http_methods;
-
+ unsigned int merge_slashes;
} core_server_config;
/* for AddOutputFiltersByType in core.c */
diff --git a/include/httpd.h b/include/httpd.h
index 176ef5e..a552358 100644
--- a/include/httpd.h
+++ b/include/httpd.h
@@ -1622,11 +1622,21 @@ AP_DECLARE(int) ap_unescape_url_keep2f(char *url, int decode_slashes);
AP_DECLARE(int) ap_unescape_urlencoded(char *query);
/**
- * Convert all double slashes to single slashes
- * @param name The string to convert
+ * Convert all double slashes to single slashes, except where significant
+ * to the filesystem on the current platform.
+ * @param name The string to convert, assumed to be a filesystem path
*/
AP_DECLARE(void) ap_no2slash(char *name);
+/**
+ * Convert all double slashes to single slashes, except where significant
+ * to the filesystem on the current platform.
+ * @param name The string to convert
+ * @param is_fs_path if set to 0, the significance of any double-slashes is
+ * ignored.
+ */
+AP_DECLARE(void) ap_no2slash_ex(char *name, int is_fs_path);
+
/**
* Remove all ./ and xx/../ substrings from a file name. Also remove
* any leading ../ or /../ substrings.
diff --git a/server/core.c b/server/core.c
index 0e69f8c..67efd7e 100644
--- a/server/core.c
+++ b/server/core.c
@@ -476,6 +476,7 @@ static void *create_core_server_config(apr_pool_t *a, server_rec *s)
*/
conf->trace_enable = AP_TRACE_UNSET;
+ conf->merge_slashes = AP_CORE_CONFIG_UNSET;
return (void *)conf;
}
@@ -536,6 +537,8 @@ static void *merge_core_server_configs(apr_pool_t *p, void *basev, void *virtv)
? virt->merge_trailers
: base->merge_trailers;
+ AP_CORE_MERGE_FLAG(merge_slashes, conf, base, virt);
+
return conf;
}
@@ -1673,6 +1676,13 @@ static const char *set_override(cmd_parms *cmd, void *d_, const char *l)
return NULL;
}
+static const char *set_core_server_flag(cmd_parms *cmd, void *s_, int flag)
+{
+ core_server_config *conf =
+ ap_get_core_module_config(cmd->server->module_config);
+ return ap_set_flag_slot(cmd, conf, flag);
+}
+
static const char *set_override_list(cmd_parms *cmd, void *d_, int argc, char *const argv[])
{
core_dir_config *d = d_;
@@ -4216,6 +4226,10 @@ AP_INIT_ITERATE("HttpProtocolOptions", set_http_protocol_options, NULL, RSRC_CON
,
AP_INIT_ITERATE("RegisterHttpMethod", set_http_method, NULL, RSRC_CONF,
"Registers non-standard HTTP methods"),
+AP_INIT_FLAG("MergeSlashes", set_core_server_flag,
+ (void *)APR_OFFSETOF(core_server_config, merge_slashes),
+ RSRC_CONF,
+ "Controls whether consecutive slashes in the URI path are merged"),
{ NULL }
};
diff --git a/server/request.c b/server/request.c
index 4eef097..cba3891 100644
--- a/server/request.c
+++ b/server/request.c
@@ -167,6 +167,8 @@ AP_DECLARE(int) ap_process_request_internal(request_rec *r)
int file_req = (r->main && r->filename);
int access_status;
core_dir_config *d;
+ core_server_config *sconf =
+ ap_get_core_module_config(r->server->module_config);
/* Ignore embedded %2F's in path for proxy requests */
if (!r->proxyreq && r->parsed_uri.path) {
@@ -191,6 +193,12 @@ AP_DECLARE(int) ap_process_request_internal(request_rec *r)
}
ap_getparents(r->uri); /* OK --- shrinking transformations... */
+ if (sconf->merge_slashes != AP_CORE_CONFIG_OFF) {
+ ap_no2slash(r->uri);
+ if (r->parsed_uri.path) {
+ ap_no2slash(r->parsed_uri.path);
+ }
+ }
/* All file subrequests are a huge pain... they cannot bubble through the
* next several steps. Only file subrequests are allowed an empty uri,
@@ -1383,20 +1391,7 @@ AP_DECLARE(int) ap_location_walk(request_rec *r)
cache = prep_walk_cache(AP_NOTE_LOCATION_WALK, r);
cached = (cache->cached != NULL);
-
- /* Location and LocationMatch differ on their behaviour w.r.t. multiple
- * slashes. Location matches multiple slashes with a single slash,
- * LocationMatch doesn't. An exception, for backwards brokenness is
- * absoluteURIs... in which case neither match multiple slashes.
- */
- if (r->uri[0] != '/') {
- entry_uri = r->uri;
- }
- else {
- char *uri = apr_pstrdup(r->pool, r->uri);
- ap_no2slash(uri);
- entry_uri = uri;
- }
+ entry_uri = r->uri;
/* If we have an cache->cached location that matches r->uri,
* and the vhost's list of locations hasn't changed, we can skip
@@ -1449,7 +1444,7 @@ AP_DECLARE(int) ap_location_walk(request_rec *r)
* terminated (or at the end of the string) to match.
*/
if (entry_core->r
- ? ap_regexec(entry_core->r, r->uri, 0, NULL, 0)
+ ? ap_regexec(entry_core->r, entry_uri, 0, NULL, 0)
: (entry_core->d_is_fnmatch
? apr_fnmatch(entry_core->d, cache->cached, APR_FNM_PATHNAME)
: (strncmp(entry_core->d, cache->cached, len)
diff --git a/server/util.c b/server/util.c
index f9e3b51..4eac462 100644
--- a/server/util.c
+++ b/server/util.c
@@ -561,16 +561,20 @@ AP_DECLARE(void) ap_getparents(char *name)
name[l] = '\0';
}
}
-
-AP_DECLARE(void) ap_no2slash(char *name)
+AP_DECLARE(void) ap_no2slash_ex(char *name, int is_fs_path)
{
+
char *d, *s;
+ if (!*name) {
+ return;
+ }
+
s = d = name;
#ifdef HAVE_UNC_PATHS
/* Check for UNC names. Leave leading two slashes. */
- if (s[0] == '/' && s[1] == '/')
+ if (is_fs_path && s[0] == '/' && s[1] == '/')
*d++ = *s++;
#endif
@@ -587,6 +591,10 @@ AP_DECLARE(void) ap_no2slash(char *name)
*d = '\0';
}
+AP_DECLARE(void) ap_no2slash(char *name)
+{
+ ap_no2slash_ex(name, 1);
+}
/*
* copy at most n leading directories of s into d

13
SOURCES/httpd-2.4.6-default-port-worker.patch

@ -0,0 +1,13 @@ @@ -0,0 +1,13 @@
diff --git a/modules/proxy/proxy_util.c b/modules/proxy/proxy_util.c
index e672e4a..8be833a 100644
--- a/modules/proxy/proxy_util.c
+++ b/modules/proxy/proxy_util.c
@@ -3557,6 +3557,8 @@ static proxy_schemes_t pschemes[] =
{"fcgi", 8000},
{"ajp", AJP13_DEF_PORT},
{"scgi", 4000},
+ {"ws", 80},
+ {"wss", 443},
{ NULL, 0xFFFF } /* unknown port */
};

11
SOURCES/httpd-2.4.6-mpm-segfault.patch

@ -8,3 +8,14 @@ @@ -8,3 +8,14 @@
if (one_process) {
/* not worth thinking about */

--- a/server/mpm/worker/worker.c
+++ b/server/mpm/worker/worker.c
@@ -1902,6 +1902,7 @@ static int worker_run(apr_pool_t *_pconf, apr_pool_t *plog, server_rec *s)
/* we've been told to restart */
apr_signal(SIGHUP, SIG_IGN);
+ apr_signal(AP_SIG_GRACEFUL, SIG_IGN);
if (one_process) {
/* not worth thinking about */

11
SOURCES/httpd-2.4.6-r1515372.patch

@ -0,0 +1,11 @@ @@ -0,0 +1,11 @@
--- a/modules/ldap/util_ldap_cache.c 2013/08/19 11:41:29 1515371
+++ b/modules/ldap/util_ldap_cache.c 2013/08/19 11:45:19 1515372
@@ -52,7 +52,7 @@
if (node) {
if (!(node->url = util_ald_strdup(cache, n->url))) {
- util_ald_free(cache, node->url);
+ util_ald_free(cache, node);
return NULL;
}
node->search_cache = n->search_cache;

265
SOURCES/httpd-2.4.6-r1555539.patch

@ -0,0 +1,265 @@ @@ -0,0 +1,265 @@
diff --git a/docs/manual/expr.html.en b/docs/manual/expr.html.en
index 5c3ae45..8bd941a 100644
--- a/docs/manual/expr.html.en
+++ b/docs/manual/expr.html.en
@@ -46,7 +46,7 @@
<li><img alt="" src="./images/down.gif" /> <a href="#other">Other</a></li>
<li><img alt="" src="./images/down.gif" /> <a href="#sslrequire">Comparison with SSLRequire</a></li>
<li><img alt="" src="./images/down.gif" /> <a href="#compatibility">Version History</a></li>
-</ul><h3>See also</h3><ul class="seealso"><li><code class="directive"><a href="./mod/core.html#if">&lt;If&gt;</a></code></li><li><code class="directive"><a href="./mod/core.html#elseif">&lt;ElseIf&gt;</a></code></li><li><code class="directive"><a href="./mod/core.html#else">&lt;Else&gt;</a></code></li><li><code class="directive"><a href="./mod/mod_auth_basic.html#authbasicfake">AuthBasicFake</a></code></li><li><code class="directive"><a href="./mod/mod_auth_form.html#authformloginrequiredlocation">AuthFormLoginRequiredLocation</a></code></li><li><code class="directive"><a href="./mod/mod_auth_form.html#authformloginsuccesslocation">AuthFormLoginSuccessLocation</a></code></li><li><code class="directive"><a href="./mod/mod_auth_form.html#authformlogoutlocation">AuthFormLogoutLocation</a></code></li><li><code class="directive"><a href="./mod/mod_rewrite.html#rewritecond">RewriteCond</a></code></li><li><code class="directive"><a href="./mod/mod_setenvif.html#setenvifexpr">SetEnvIfExpr</a></code></li><li><code class="directive"><a href="./mod/mod_headers.html#header">Header</a></code></li><li><code class="directive"><a href="./mod/mod_headers.html#requestheader">RequestHeader</a></code></li><li><code class="directive"><a href="./mod/mod_filter.html#filterprovider">FilterProvider</a></code></li><li><a href="mod/mod_authz_core.html#reqexpr">Require expr</a></li><li><code class="directive"><a href="./mod/mod_ssl.html#sslrequire">SSLRequire</a></code></li><li><code class="directive"><a href="./mod/mod_log_debug.html#logmessage">LogMessage</a></code></li><li><code class="module"><a href="./mod/mod_include.html">mod_include</a></code></li></ul><ul class="seealso"><li><a href="#comments_section">Comments</a></li></ul></div>
+</ul><h3>See also</h3><ul class="seealso"><li><code class="directive"><a href="./mod/core.html#if">&lt;If&gt;</a></code></li><li><code class="directive"><a href="./mod/core.html#elseif">&lt;ElseIf&gt;</a></code></li><li><code class="directive"><a href="./mod/core.html#else">&lt;Else&gt;</a></code></li><li><code class="directive"><a href="./mod/mod_auth_basic.html#authbasicfake">AuthBasicFake</a></code></li><li><code class="directive"><a href="./mod/mod_auth_form.html#authformloginrequiredlocation">AuthFormLoginRequiredLocation</a></code></li><li><code class="directive"><a href="./mod/mod_auth_form.html#authformloginsuccesslocation">AuthFormLoginSuccessLocation</a></code></li><li><code class="directive"><a href="./mod/mod_auth_form.html#authformlogoutlocation">AuthFormLogoutLocation</a></code></li><li><code class="directive"><a href="./mod/mod_rewrite.html#rewritecond">RewriteCond</a></code></li><li><code class="directive"><a href="./mod/mod_setenvif.html#setenvifexpr">SetEnvIfExpr</a></code></li><li><code class="directive"><a href="./mod/mod_headers.html#header">Header</a></code></li><li><code class="directive"><a href="./mod/mod_headers.html#requestheader">RequestHeader</a></code></li><li><code class="directive"><a href="./mod/mod_filter.html#filterprovider">FilterProvider</a></code></li><li><a href="mod/mod_authz_core.html#reqexpr">Require expr</a></li><li><code class="directive"><a href="mod/mod_authnz_ldap.html#requser">Require ldap-user</a></code></li><li><code class="directive"><a href="mod/mod_authnz_ldap.html#reqgroup">Require ldap-group</a></code></li><li><code class="directive"><a href="mod/mod_authnz_ldap.html#reqdn">Require ldap-dn</a></code></li><li><code class="directive"><a href="mod/mod_authnz_ldap.html#reqattribute">Require ldap-attribute</a></code></li><li><code class="directive"><a href="mod/mod_authnz_ldap.html#reqfilter">Require ldap-filter</a></code></li><li><code class="directive"><a href="./mod/mod_ssl.html#sslrequire">SSLRequire</a></code></li><li><code class="directive"><a href="./mod/mod_log_debug.html#logmessage">LogMessage</a></code></li><li><code class="module"><a href="./mod/mod_include.html">mod_include</a></code></li></ul><ul class="seealso"><li><a href="#comments_section">Comments</a></li></ul></div>
<div class="top"><a href="#page-header"><img alt="top" src="./images/up.gif" /></a></div>
<div class="section">
<h2><a name="grammar" id="grammar">Grammar in Backus-Naur Form notation</a></h2>
diff --git a/docs/manual/mod/mod_authnz_ldap.html.en b/docs/manual/mod/mod_authnz_ldap.html.en
index 7199052..c86dc8a 100644
--- a/docs/manual/mod/mod_authnz_ldap.html.en
+++ b/docs/manual/mod/mod_authnz_ldap.html.en
@@ -350,6 +350,9 @@ for HTTP Basic authentication.</td></tr>
<code>ldap-filter</code>. Other authorization types may also be
used but may require that additional authorization modules be loaded.</p>
+ <p>Since v2.5.0, <a href="../expr.html">expressions</a> are supported
+ within the LDAP require directives.</p>
+
<h3><a name="requser" id="requser">Require ldap-user</a></h3>
<p>The <code>Require ldap-user</code> directive specifies what
@@ -576,6 +579,16 @@ Require ldap-group cn=Administrators, o=Example
</li>
<li>
+ Grant access to anybody in the group whose name matches the
+ hostname of the virtual host. In this example an
+ <a href="../expr.html">expression</a> is used to build the filter.
+<highlight language="config">
+AuthLDAPURL ldap://ldap.example.com/o=Example?uid
+Require ldap-group cn=%{SERVER_NAME}, o=Example
+</highlight>
+ </li>
+
+ <li>
The next example assumes that everyone at Example who
carries an alphanumeric pager will have an LDAP attribute
of <code>qpagePagerID</code>. The example will grant access
diff --git a/modules/aaa/mod_authnz_ldap.c b/modules/aaa/mod_authnz_ldap.c
index 2c25dbc..063debe 100644
--- a/modules/aaa/mod_authnz_ldap.c
+++ b/modules/aaa/mod_authnz_ldap.c
@@ -607,6 +607,10 @@ static authz_status ldapuser_check_authorization(request_rec *r,
util_ldap_connection_t *ldc = NULL;
+ const char *err = NULL;
+ const ap_expr_info_t *expr = parsed_require_args;
+ const char *require;
+
const char *t;
char *w;
@@ -680,11 +684,19 @@ static authz_status ldapuser_check_authorization(request_rec *r,
return AUTHZ_DENIED;
}
+ require = ap_expr_str_exec(r, expr, &err);
+ if (err) {
+ ap_log_rerror(APLOG_MARK, APLOG_ERR, 0, r, APLOGNO(02585)
+ "auth_ldap authorize: require user: Can't evaluate expression: %s",
+ err);
+ return AUTHZ_DENIED;
+ }
+
/*
* First do a whole-line compare, in case it's something like
* require user Babs Jensen
*/
- result = util_ldap_cache_compare(r, ldc, sec->url, req->dn, sec->attribute, require_args);
+ result = util_ldap_cache_compare(r, ldc, sec->url, req->dn, sec->attribute, require);
switch(result) {
case LDAP_COMPARE_TRUE: {
ap_log_rerror(APLOG_MARK, APLOG_DEBUG, 0, r, APLOGNO(01703)
@@ -704,7 +716,7 @@ static authz_status ldapuser_check_authorization(request_rec *r,
/*
* Now break apart the line and compare each word on it
*/
- t = require_args;
+ t = require;
while ((w = ap_getword_conf(r->pool, &t)) && w[0]) {
result = util_ldap_cache_compare(r, ldc, sec->url, req->dn, sec->attribute, w);
switch(result) {
@@ -744,6 +756,10 @@ static authz_status ldapgroup_check_authorization(request_rec *r,
util_ldap_connection_t *ldc = NULL;
+ const char *err = NULL;
+ const ap_expr_info_t *expr = parsed_require_args;
+ const char *require;
+
const char *t;
char filtbuf[FILTER_LENGTH];
@@ -863,7 +879,15 @@ static authz_status ldapgroup_check_authorization(request_rec *r,
}
}
- t = require_args;
+ require = ap_expr_str_exec(r, expr, &err);
+ if (err) {
+ ap_log_rerror(APLOG_MARK, APLOG_ERR, 0, r, APLOGNO(02586)
+ "auth_ldap authorize: require group: Can't evaluate expression: %s",
+ err);
+ return AUTHZ_DENIED;
+ }
+
+ t = require;
ap_log_rerror(APLOG_MARK, APLOG_DEBUG, 0, r, APLOGNO(01713)
"auth_ldap authorize: require group: testing for group "
@@ -959,6 +983,10 @@ static authz_status ldapdn_check_authorization(request_rec *r,
util_ldap_connection_t *ldc = NULL;
+ const char *err = NULL;
+ const ap_expr_info_t *expr = parsed_require_args;
+ const char *require;
+
const char *t;
char filtbuf[FILTER_LENGTH];
@@ -1021,7 +1049,15 @@ static authz_status ldapdn_check_authorization(request_rec *r,
req->user = r->user;
}
- t = require_args;
+ require = ap_expr_str_exec(r, expr, &err);
+ if (err) {
+ ap_log_rerror(APLOG_MARK, APLOG_ERR, 0, r, APLOGNO(02587)
+ "auth_ldap authorize: require dn: Can't evaluate expression: %s",
+ err);
+ return AUTHZ_DENIED;
+ }
+
+ t = require;
if (req->dn == NULL || strlen(req->dn) == 0) {
ap_log_rerror(APLOG_MARK, APLOG_DEBUG, 0, r, APLOGNO(01725)
@@ -1068,6 +1104,10 @@ static authz_status ldapattribute_check_authorization(request_rec *r,
util_ldap_connection_t *ldc = NULL;
+ const char *err = NULL;
+ const ap_expr_info_t *expr = parsed_require_args;
+ const char *require;
+
const char *t;
char *w, *value;
@@ -1138,7 +1178,16 @@ static authz_status ldapattribute_check_authorization(request_rec *r,
return AUTHZ_DENIED;
}
- t = require_args;
+ require = ap_expr_str_exec(r, expr, &err);
+ if (err) {
+ ap_log_rerror(APLOG_MARK, APLOG_ERR, 0, r, APLOGNO(02588)
+ "auth_ldap authorize: require ldap-attribute: Can't "
+ "evaluate expression: %s", err);
+ return AUTHZ_DENIED;
+ }
+
+ t = require;
+
while (t[0]) {
w = ap_getword(r->pool, &t, '=');
value = ap_getword_conf(r->pool, &t);
@@ -1183,6 +1232,11 @@ static authz_status ldapfilter_check_authorization(request_rec *r,
(authn_ldap_config_t *)ap_get_module_config(r->per_dir_config, &authnz_ldap_module);
util_ldap_connection_t *ldc = NULL;
+
+ const char *err = NULL;
+ const ap_expr_info_t *expr = parsed_require_args;
+ const char *require;
+
const char *t;
char filtbuf[FILTER_LENGTH];
@@ -1252,7 +1306,15 @@ static authz_status ldapfilter_check_authorization(request_rec *r,
return AUTHZ_DENIED;
}
- t = require_args;
+ require = ap_expr_str_exec(r, expr, &err);
+ if (err) {
+ ap_log_rerror(APLOG_MARK, APLOG_ERR, 0, r, APLOGNO(02589)
+ "auth_ldap authorize: require ldap-filter: Can't "
+ "evaluate require expression: %s", err);
+ return AUTHZ_DENIED;
+ }
+
+ t = require;
if (t[0]) {
ap_log_rerror(APLOG_MARK, APLOG_DEBUG, 0, r, APLOGNO(01743)
@@ -1311,6 +1373,25 @@ static authz_status ldapfilter_check_authorization(request_rec *r,
return AUTHZ_DENIED;
}
+static const char *ldap_parse_config(cmd_parms *cmd, const char *require_line,
+ const void **parsed_require_line)
+{
+ const char *expr_err = NULL;
+ ap_expr_info_t *expr;
+
+ expr = ap_expr_parse_cmd(cmd, require_line, AP_EXPR_FLAG_STRING_RESULT,
+ &expr_err, NULL);
+
+ if (expr_err)
+ return apr_pstrcat(cmd->temp_pool,
+ "Cannot parse expression in require line: ",
+ expr_err, NULL);
+
+ *parsed_require_line = expr;
+
+ return NULL;
+}
+
/*
* Use the ldap url parsing routines to break up the ldap url into
@@ -1769,30 +1850,30 @@ static const authn_provider authn_ldap_provider =
static const authz_provider authz_ldapuser_provider =
{
&ldapuser_check_authorization,
- NULL,
+ &ldap_parse_config,
};
static const authz_provider authz_ldapgroup_provider =
{
&ldapgroup_check_authorization,
- NULL,
+ &ldap_parse_config,
};
static const authz_provider authz_ldapdn_provider =
{
&ldapdn_check_authorization,
- NULL,
+ &ldap_parse_config,
};
static const authz_provider authz_ldapattribute_provider =
{
&ldapattribute_check_authorization,
- NULL,
+ &ldap_parse_config,
};
static const authz_provider authz_ldapfilter_provider =
{
&ldapfilter_check_authorization,
- NULL,
+ &ldap_parse_config,
};
static void ImportULDAPOptFn(void)

26
SOURCES/httpd-2.4.6-r1737363.patch

@ -0,0 +1,26 @@ @@ -0,0 +1,26 @@
# ./pullrev.sh 1737363
http://svn.apache.org/viewvc?view=revision&revision=1737363

--- httpd-2.4.6/modules/proxy/mod_proxy_express.c
+++ httpd-2.4.6/modules/proxy/mod_proxy_express.c
@@ -145,16 +145,14 @@
key.dsize = strlen(key.dptr);
rv = apr_dbm_fetch(db, key, &val);
+ if (rv == APR_SUCCESS) {
+ backend = apr_pstrmemdup(r->pool, val.dptr, val.dsize);
+ }
apr_dbm_close(db);
- if (rv != APR_SUCCESS) {
+ if (rv != APR_SUCCESS || !backend) {
return DECLINED;
}
- backend = apr_pstrmemdup(r->pool, val.dptr, val.dsize);
- if (!backend) {
- return DECLINED;
- }
-
ap_log_rerror(APLOG_MARK, APLOG_DEBUG, 0, r, APLOGNO(01004)
"proxy_express: found %s -> %s", name, backend);
r->filename = apr_pstrcat(r->pool, "proxy:", backend, r->uri, NULL);

25
SOURCES/httpd-2.4.6-r1824872.patch

@ -0,0 +1,25 @@ @@ -0,0 +1,25 @@
--- a/modules/ldap/util_ldap.c 2018/02/20 13:00:39 1824871
+++ b/modules/ldap/util_ldap.c 2018/02/20 13:02:54 1824872
@@ -2858,7 +2858,6 @@
st->search_cache_size = base->search_cache_size;
st->compare_cache_ttl = base->compare_cache_ttl;
st->compare_cache_size = base->compare_cache_size;
- st->util_ldap_cache_lock = base->util_ldap_cache_lock;
st->connections = NULL;
st->ssl_supported = 0; /* not known until post-config and re-merged */
@@ -2977,12 +2976,12 @@
st_vhost = (util_ldap_state_t *)
ap_get_module_config(s_vhost->module_config,
&ldap_module);
-
+ st_vhost->util_ldap_cache = st->util_ldap_cache;
+ st_vhost->util_ldap_cache_lock = st->util_ldap_cache_lock;
#if APR_HAS_SHARED_MEMORY
st_vhost->cache_shm = st->cache_shm;
st_vhost->cache_rmm = st->cache_rmm;
st_vhost->cache_file = st->cache_file;
- st_vhost->util_ldap_cache = st->util_ldap_cache;
ap_log_error(APLOG_MARK, APLOG_DEBUG, result, s, APLOGNO(01316)
"LDAP merging Shared Cache conf: shm=0x%pp rmm=0x%pp "
"for VHOST: %s", st->cache_shm, st->cache_rmm,

96
SOURCES/httpd-2.4.6-r1825120.patch

@ -0,0 +1,96 @@ @@ -0,0 +1,96 @@
diff --git a/modules/ssl/ssl_engine_init.c b/modules/ssl/ssl_engine_init.c
index 57b76c0..814ec4f 100644
--- a/modules/ssl/ssl_engine_init.c
+++ b/modules/ssl/ssl_engine_init.c
@@ -1522,70 +1522,18 @@ void ssl_init_CheckServers(SSLModConfigRec *mc, server_rec *base_server, apr_poo
}
}
-static int ssl_init_FindCAList_X509NameCmp(const X509_NAME * const *a,
- const X509_NAME * const *b)
-{
- return(X509_NAME_cmp(*a, *b));
-}
-
-static void ssl_init_PushCAList(STACK_OF(X509_NAME) *ca_list,
- server_rec *s, apr_pool_t *ptemp,
- const char *file)
-{
- int n;
- STACK_OF(X509_NAME) *sk;
-
- sk = (STACK_OF(X509_NAME) *)
- SSL_load_client_CA_file(file);
-
- if (!sk) {
- return;
- }
-
- for (n = 0; n < sk_X509_NAME_num(sk); n++) {
- X509_NAME *name = sk_X509_NAME_value(sk, n);
-
- ap_log_error(APLOG_MARK, APLOG_DEBUG, 0, s, APLOGNO(02209)
- "CA certificate: %s",
- SSL_X509_NAME_to_string(ptemp, name, 0));
-
- /*
- * note that SSL_load_client_CA_file() checks for duplicates,
- * but since we call it multiple times when reading a directory
- * we must also check for duplicates ourselves.
- */
-
- if (sk_X509_NAME_find(ca_list, name) < 0) {
- /* this will be freed when ca_list is */
- sk_X509_NAME_push(ca_list, name);
- }
- else {
- /* need to free this ourselves, else it will leak */
- X509_NAME_free(name);
- }
- }
-
- sk_X509_NAME_free(sk);
-}
-
STACK_OF(X509_NAME) *ssl_init_FindCAList(server_rec *s,
apr_pool_t *ptemp,
const char *ca_file,
const char *ca_path)
{
- STACK_OF(X509_NAME) *ca_list;
-
- /*
- * Start with a empty stack/list where new
- * entries get added in sorted order.
- */
- ca_list = sk_X509_NAME_new(ssl_init_FindCAList_X509NameCmp);
+ STACK_OF(X509_NAME) *ca_list = sk_X509_NAME_new_null();;
/*
* Process CA certificate bundle file
*/
if (ca_file) {
- ssl_init_PushCAList(ca_list, s, ptemp, ca_file);
+ SSL_add_file_cert_subjects_to_stack(ca_list, ca_file);
/*
* If ca_list is still empty after trying to load ca_file
* then the file failed to load, and users should hear about that.
@@ -1619,17 +1567,12 @@ STACK_OF(X509_NAME) *ssl_init_FindCAList(server_rec *s,
continue; /* don't try to load directories */
}
file = apr_pstrcat(ptemp, ca_path, "/", direntry.name, NULL);
- ssl_init_PushCAList(ca_list, s, ptemp, file);
+ SSL_add_file_cert_subjects_to_stack(ca_list, file);
}
apr_dir_close(dir);
}
- /*
- * Cleanup
- */
- (void) sk_X509_NAME_set_cmp_func(ca_list, NULL);
-
return ca_list;
}

198
SOURCES/httpd-2.4.6-r1826995.patch

@ -0,0 +1,198 @@ @@ -0,0 +1,198 @@
diff --git a/docs/manual/mod/mod_ssl.html.en b/docs/manual/mod/mod_ssl.html.en
index 4580f1c..fb8202e 100644
--- a/docs/manual/mod/mod_ssl.html.en
+++ b/docs/manual/mod/mod_ssl.html.en
@@ -991,7 +991,8 @@ the certificate being verified.</p>
<p>This option enables OCSP validation of the client certificate
chain. If this option is enabled, certificates in the client's
certificate chain will be validated against an OCSP responder after
-normal verification (including CRL checks) have taken place.</p>
+normal verification (including CRL checks) have taken place. In
+mode 'leaf', only the client certificate itself will be validated.</p>
<p>The OCSP responder used is either extracted from the certificate
itself, or derived by configuration; see the
diff --git a/modules/ssl/mod_ssl.c b/modules/ssl/mod_ssl.c
index 4a8b661..e637a9d 100644
--- a/modules/ssl/mod_ssl.c
+++ b/modules/ssl/mod_ssl.c
@@ -227,8 +227,8 @@ static const command_rec ssl_config_cmds[] = {
"request body if a per-location SSL renegotiation is required due to "
"changed access control requirements")
- SSL_CMD_SRV(OCSPEnable, FLAG,
- "Enable use of OCSP to verify certificate revocation ('on', 'off')")
+ SSL_CMD_SRV(OCSPEnable, RAW_ARGS,
+ "Enable use of OCSP to verify certificate revocation mode ('on', 'leaf', 'off')")
SSL_CMD_SRV(OCSPDefaultResponder, TAKE1,
"URL of the default OCSP Responder")
SSL_CMD_SRV(OCSPOverrideResponder, FLAG,
diff --git a/modules/ssl/ssl_engine_config.c b/modules/ssl/ssl_engine_config.c
index 86a7f0f..714aee9 100644
--- a/modules/ssl/ssl_engine_config.c
+++ b/modules/ssl/ssl_engine_config.c
@@ -130,7 +130,7 @@ static void modssl_ctx_init(modssl_ctx_t *mctx)
mctx->auth.verify_depth = UNSET;
mctx->auth.verify_mode = SSL_CVERIFY_UNSET;
- mctx->ocsp_enabled = FALSE;
+ mctx->ocsp_mask = UNSET;
mctx->ocsp_force_default = FALSE;
mctx->ocsp_responder = NULL;
mctx->ocsp_resptime_skew = UNSET;
@@ -264,7 +264,7 @@ static void modssl_ctx_cfg_merge(modssl_ctx_t *base,
cfgMergeInt(auth.verify_depth);
cfgMerge(auth.verify_mode, SSL_CVERIFY_UNSET);
- cfgMergeBool(ocsp_enabled);
+ cfgMergeInt(ocsp_mask);
cfgMergeBool(ocsp_force_default);
cfgMerge(ocsp_responder, NULL);
cfgMergeInt(ocsp_resptime_skew);
@@ -1575,11 +1575,46 @@ const char *ssl_cmd_SSLUserName(cmd_parms *cmd, void *dcfg,
return NULL;
}
-const char *ssl_cmd_SSLOCSPEnable(cmd_parms *cmd, void *dcfg, int flag)
+static const char *ssl_cmd_ocspcheck_parse(cmd_parms *parms,
+ const char *arg,
+ int *mask)
{
- SSLSrvConfigRec *sc = mySrvConfig(cmd->server);
+ const char *w;
+
+ w = ap_getword_conf(parms->temp_pool, &arg);
+ if (strcEQ(w, "off")) {
+ *mask = SSL_OCSPCHECK_NONE;
+ }
+ else if (strcEQ(w, "leaf")) {
+ *mask = SSL_OCSPCHECK_LEAF;
+ }
+ else if (strcEQ(w, "on")) {
+ *mask = SSL_OCSPCHECK_CHAIN;
+ }
+ else {
+ return apr_pstrcat(parms->temp_pool, parms->cmd->name,
+ ": Invalid argument '", w, "'",
+ NULL);
+ }
+
+ while (*arg) {
+ w = ap_getword_conf(parms->temp_pool, &arg);
+ if (strcEQ(w, "no_ocsp_for_cert_ok")) {
+ *mask |= SSL_OCSPCHECK_NO_OCSP_FOR_CERT_OK;
+ }
+ else {
+ return apr_pstrcat(parms->temp_pool, parms->cmd->name,
+ ": Invalid argument '", w, "'",
+ NULL);
+ }
+ }
- sc->server->ocsp_enabled = flag ? TRUE : FALSE;
+ return NULL;
+}
+
+const char *ssl_cmd_SSLOCSPEnable(cmd_parms *cmd, void *dcfg, const char *arg)
+{
+ SSLSrvConfigRec *sc = mySrvConfig(cmd->server);
#ifdef OPENSSL_NO_OCSP
if (flag) {
@@ -1588,7 +1623,7 @@ const char *ssl_cmd_SSLOCSPEnable(cmd_parms *cmd, void *dcfg, int flag)
}
#endif
- return NULL;
+ return ssl_cmd_ocspcheck_parse(cmd, arg, &sc->server->ocsp_mask);
}
const char *ssl_cmd_SSLOCSPOverrideResponder(cmd_parms *cmd, void *dcfg, int flag)
diff --git a/modules/ssl/ssl_engine_init.c b/modules/ssl/ssl_engine_init.c
index 672760c..57b76c0 100644
--- a/modules/ssl/ssl_engine_init.c
+++ b/modules/ssl/ssl_engine_init.c
@@ -762,6 +762,10 @@ static void ssl_init_ctx_crl(server_rec *s,
unsigned long crlflags = 0;
char *cfgp = mctx->pkp ? "SSLProxy" : "SSL";
+ if (mctx->ocsp_mask == UNSET) {
+ mctx->ocsp_mask = SSL_OCSPCHECK_NONE;
+ }
+
/*
* Configure Certificate Revocation List (CRL) Details
*/
diff --git a/modules/ssl/ssl_engine_kernel.c b/modules/ssl/ssl_engine_kernel.c
index 5ff35f5..9dc236c 100644
--- a/modules/ssl/ssl_engine_kernel.c
+++ b/modules/ssl/ssl_engine_kernel.c
@@ -1416,7 +1416,8 @@ int ssl_callback_SSLVerify(int ok, X509_STORE_CTX *ctx)
/*
* Perform OCSP-based revocation checks
*/
- if (ok && sc->server->ocsp_enabled) {
+ if (ok && ((sc->server->ocsp_mask & SSL_OCSPCHECK_CHAIN) ||
+ (errdepth == 0 && (sc->server->ocsp_mask & SSL_OCSPCHECK_LEAF)))) {
/* If there was an optional verification error, it's not
* possible to perform OCSP validation since the issuer may be
* missing/untrusted. Fail in that case. */
diff --git a/modules/ssl/ssl_engine_ocsp.c b/modules/ssl/ssl_engine_ocsp.c
index 90da5c2..58d267b 100644
--- a/modules/ssl/ssl_engine_ocsp.c
+++ b/modules/ssl/ssl_engine_ocsp.c
@@ -136,7 +136,14 @@ static int verify_ocsp_status(X509 *cert, X509_STORE_CTX *ctx, conn_rec *c,
ruri = determine_responder_uri(sc, cert, c, pool);
if (!ruri) {
- return V_OCSP_CERTSTATUS_UNKNOWN;
+ if (sc->server->ocsp_mask & SSL_OCSPCHECK_NO_OCSP_FOR_CERT_OK) {
+ ap_log_cerror(APLOG_MARK, APLOG_TRACE2, 0, c,
+ "Skipping OCSP check for certificate cos no OCSP URL"
+ " found and no_ocsp_for_cert_ok is set");
+ return V_OCSP_CERTSTATUS_GOOD;
+ } else {
+ return V_OCSP_CERTSTATUS_UNKNOWN;
+ }
}
request = create_request(ctx, cert, &certID, s, pool);
diff --git a/modules/ssl/ssl_private.h b/modules/ssl/ssl_private.h
index b601316..2d505f9 100644
--- a/modules/ssl/ssl_private.h
+++ b/modules/ssl/ssl_private.h
@@ -379,6 +379,16 @@ typedef enum {
} ssl_crlcheck_t;
/**
+ * OCSP checking mask (mode | flags)
+ */
+typedef enum {
+ SSL_OCSPCHECK_NONE = (0),
+ SSL_OCSPCHECK_LEAF = (1 << 0),
+ SSL_OCSPCHECK_CHAIN = (1 << 1),
+ SSL_OCSPCHECK_NO_OCSP_FOR_CERT_OK = (1 << 2)
+} ssl_ocspcheck_t;
+
+/**
* Define the SSL pass phrase dialog types
*/
typedef enum {
@@ -668,7 +678,7 @@ typedef struct {
modssl_auth_ctx_t auth;
- BOOL ocsp_enabled; /* true if OCSP verification enabled */
+ int ocsp_mask;
BOOL ocsp_force_default; /* true if the default responder URL is
* used regardless of per-cert URL */
const char *ocsp_responder; /* default responder URL */
@@ -796,7 +806,7 @@ const char *ssl_cmd_SSLOCSPDefaultResponder(cmd_parms *cmd, void *dcfg, const ch
const char *ssl_cmd_SSLOCSPResponseTimeSkew(cmd_parms *cmd, void *dcfg, const char *arg);
const char *ssl_cmd_SSLOCSPResponseMaxAge(cmd_parms *cmd, void *dcfg, const char *arg);
const char *ssl_cmd_SSLOCSPResponderTimeout(cmd_parms *cmd, void *dcfg, const char *arg);
-const char *ssl_cmd_SSLOCSPEnable(cmd_parms *cmd, void *dcfg, int flag);
+const char *ssl_cmd_SSLOCSPEnable(cmd_parms *cmd, void *dcfg, const char *flag);
#ifndef OPENSSL_NO_SRP
const char *ssl_cmd_SSLSRPVerifierFile(cmd_parms *cmd, void *dcfg, const char *arg);

83
SOURCES/httpd-2.4.6-r1833014.patch

@ -0,0 +1,83 @@ @@ -0,0 +1,83 @@
diff --git a/modules/http/http_request.c b/modules/http/http_request.c
index c97dc77..9885de4 100644
--- a/modules/http/http_request.c
+++ b/modules/http/http_request.c
@@ -227,11 +227,21 @@ AP_DECLARE(void) ap_die(int type, request_rec *r)
ap_die_r(type, r, r->status);
}
-static void check_pipeline(conn_rec *c)
+#define RETRIEVE_BRIGADE_FROM_POOL(bb, key, pool, allocator) do { \
+ apr_pool_userdata_get((void **)&bb, key, pool); \
+ if (bb == NULL) { \
+ bb = apr_brigade_create(pool, allocator); \
+ apr_pool_userdata_setn((const void *)bb, key, NULL, pool); \
+ } \
+ else { \
+ apr_brigade_cleanup(bb); \
+ } \
+} while(0)
+
+static void check_pipeline(conn_rec *c, apr_bucket_brigade *bb)
{
if (c->keepalive != AP_CONN_CLOSE) {
apr_status_t rv;
- apr_bucket_brigade *bb = apr_brigade_create(c->pool, c->bucket_alloc);
rv = ap_get_brigade(c->input_filters, bb, AP_MODE_SPECULATIVE,
APR_NONBLOCK_READ, 1);
@@ -245,11 +255,10 @@ static void check_pipeline(conn_rec *c)
else {
c->data_in_input_filters = 1;
}
- apr_brigade_destroy(bb);
+ apr_brigade_cleanup(bb);
}
}
-
AP_DECLARE(void) ap_process_request_after_handler(request_rec *r)
{
apr_bucket_brigade *bb;
@@ -260,11 +269,13 @@ AP_DECLARE(void) ap_process_request_after_handler(request_rec *r)
* this bucket is destroyed, the request will be logged and
* its pool will be freed
*/
- bb = apr_brigade_create(r->connection->pool, r->connection->bucket_alloc);
+ RETRIEVE_BRIGADE_FROM_POOL(bb, "ap_process_request_after_handler_brigade",
+ c->pool, c->bucket_alloc);
b = ap_bucket_eor_create(r->connection->bucket_alloc, r);
APR_BRIGADE_INSERT_HEAD(bb, b);
ap_pass_brigade(r->connection->output_filters, bb);
+ apr_brigade_cleanup(bb);
/* From here onward, it is no longer safe to reference r
* or r->pool, because r->pool may have been destroyed
@@ -273,7 +284,7 @@ AP_DECLARE(void) ap_process_request_after_handler(request_rec *r)
if (c->cs)
c->cs->state = CONN_STATE_WRITE_COMPLETION;
- check_pipeline(c);
+ check_pipeline(c, bb);
AP_PROCESS_REQUEST_RETURN((uintptr_t)r, r->uri, r->status);
if (ap_extended_status) {
ap_time_process_request(c->sbh, STOP_PREQUEST);
@@ -363,7 +374,8 @@ void ap_process_request(request_rec *r)
ap_process_async_request(r);
if (!c->data_in_input_filters) {
- bb = apr_brigade_create(c->pool, c->bucket_alloc);
+ RETRIEVE_BRIGADE_FROM_POOL(bb, "ap_process_request_after_handler_brigade",
+ c->pool, c->bucket_alloc);
b = apr_bucket_flush_create(c->bucket_alloc);
APR_BRIGADE_INSERT_HEAD(bb, b);
rv = ap_pass_brigade(c->output_filters, bb);
@@ -380,6 +392,7 @@ void ap_process_request(request_rec *r)
"Timeout while writing data for URI %s to the"
" client", r->unparsed_uri);
}
+ apr_brigade_cleanup(bb);
}
if (ap_extended_status) {
ap_time_process_request(c->sbh, STOP_PREQUEST);

35
SPECS/httpd.spec

@ -15,9 +15,10 @@ @@ -15,9 +15,10 @@
Summary: Apache HTTP Server
Name: httpd
Version: 2.4.6
Release: 80%{?dist}
Release: 90%{?dist}
URL: http://httpd.apache.org/
Source0: http://archive.apache.org/dist/httpd/httpd-%{version}.tar.bz2
Source0: http://www.apache.org/dist/httpd/httpd-%{version}.tar.bz2
### TODO: we need to create a powerel version
#Source1: centos-noindex.tar.gz
Source2: httpd.logrotate
Source3: httpd.sysconf
@ -135,6 +136,7 @@ Patch111: httpd-2.4.6-r1348019.patch @@ -135,6 +136,7 @@ Patch111: httpd-2.4.6-r1348019.patch
# https://bugzilla.redhat.com/show_bug.cgi?id=1396197
Patch112: httpd-2.4.6-r1587053.patch
# https://bugzilla.redhat.com/show_bug.cgi?id=1376835
# https://bugzilla.redhat.com/show_bug.cgi?id=1527295
Patch113: httpd-2.4.6-mpm-segfault.patch
# https://bugzilla.redhat.com/show_bug.cgi?id=1372692
Patch114: httpd-2.4.6-r1681114.patch
@ -174,6 +176,22 @@ Patch130: httpd-2.4.6-r1811976.patch @@ -174,6 +176,22 @@ Patch130: httpd-2.4.6-r1811976.patch
Patch131: httpd-2.4.6-r1650310.patch
# https://bugzilla.redhat.com/show_bug.cgi?id=1557785
Patch132: httpd-2.4.6-r1530999.patch
# https://bugzilla.redhat.com/show_bug.cgi?id=1533793
Patch133: httpd-2.4.6-r1555539.patch
# https://bugzilla.redhat.com/show_bug.cgi?id=1523536
Patch134: httpd-2.4.6-r1737363.patch
# https://bugzilla.redhat.com/show_bug.cgi?id=1548501
Patch135: httpd-2.4.6-r1826995.patch
# https://bugzilla.redhat.com/show_bug.cgi?id=1556761
Patch136: httpd-2.4.6-default-port-worker.patch
# https://bugzilla.redhat.com/show_bug.cgi?id=1493181
Patch137: httpd-2.4.6-r1825120.patch
# https://bugzilla.redhat.com/show_bug.cgi?id=1458364
Patch138: httpd-2.4.6-r1515372.patch
# https://bugzilla.redhat.com/show_bug.cgi?id=1458364
Patch139: httpd-2.4.6-r1824872.patch
# https://bugzilla.redhat.com/show_bug.cgi?id=1583218
Patch140: httpd-2.4.6-r1833014.patch

# Security fixes
Patch200: httpd-2.4.6-CVE-2013-6438.patch
@ -197,6 +215,9 @@ Patch217: httpd-2.4.6-CVE-2017-7668.patch @@ -197,6 +215,9 @@ Patch217: httpd-2.4.6-CVE-2017-7668.patch
Patch218: httpd-2.4.6-CVE-2017-7679.patch
Patch219: httpd-2.4.6-CVE-2017-9788.patch
Patch220: httpd-2.4.6-CVE-2017-9798.patch
Patch221: httpd-2.4.6-CVE-2018-1312.patch
Patch222: httpd-2.4.6-CVE-2019-0217.patch
Patch223: httpd-2.4.6-CVE-2019-0220.patch

License: ASL 2.0
Group: System Environment/Daemons
@ -504,6 +525,8 @@ export LYNX_PATH=/usr/bin/links @@ -504,6 +525,8 @@ export LYNX_PATH=/usr/bin/links
--enable-cgid --enable-cgi \
--enable-authn-anon --enable-authn-alias \
--disable-imagemap \
--disable-lua \
--disable-luajit \
$*
make %{?_smp_mflags}

@ -609,8 +632,8 @@ rm -v $RPM_BUILD_ROOT%{docroot}/html/*.html \ @@ -609,8 +632,8 @@ 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 \
$RPM_BUILD_ROOT%{contentdir}/icons/poweredby.png
#ln -s ../noindex/images/poweredby.png \
# $RPM_BUILD_ROOT%{contentdir}/icons/poweredby.png

# symlinks for /etc/httpd
ln -s ../..%{_localstatedir}/log/httpd $RPM_BUILD_ROOT/etc/httpd/logs
@ -790,12 +813,12 @@ rm -rf $RPM_BUILD_ROOT @@ -790,12 +813,12 @@ rm -rf $RPM_BUILD_ROOT
%dir %{contentdir}/icons
%dir %{contentdir}/error
%dir %{contentdir}/error/include
%dir %{contentdir}/noindex
#%dir %{contentdir}/noindex
%{contentdir}/icons/*
%{contentdir}/error/README
%{contentdir}/error/*.var
%{contentdir}/error/include/*.html
%{contentdir}/noindex/*
#%{contentdir}/noindex/*

%dir %{docroot}
%dir %{docroot}/cgi-bin

Loading…
Cancel
Save