Commit 9ecd8f4c authored by Stefan Fritsch's avatar Stefan Fritsch
Browse files

properly merge directory configs in mod_include


git-svn-id: https://svn.apache.org/repos/asf/httpd/httpd/trunk@1128430 13f79535-47bb-0310-9956-ffa450edef68
parent 64e0b5db
Loading
Loading
Loading
Loading
+4 −0
Changes for CHANGES: 4 added lines, 0 removed lines.
Original line number Diff line number Diff line
@@ -2,6 +2,10 @@

Changes with Apache 2.3.13

  *) mod_include: Merge directory configs instead of one SSI* config directive
     causing all other per-directory SSI* config directives to be reset.
     [Stefan Fritsch]

  *) mod_charset_lite: Remove DebugLevel option in favour of per-module
     loglevel. [Stefan Fritsch]

+6 −1
Changes for docs/manual/upgrading.xml: 6 added lines, 1 removed line.
Original line number Diff line number Diff line
@@ -225,6 +225,11 @@
        module="filter">FilterProvider</directive> syntax has changed and
        now uses a boolean expression to determine if a filter is applied.
        </li>

        <li><module>mod_include</module>: An SSI* config directive in directory
        scope no longer causes all other per-directory SSI* directives to be
        reset to their default values.
        </li>
      </ul>
    </section>
  </section>
@@ -233,7 +238,7 @@
    <title>Misc Changes</title>

    <ul>
      <li><module>mod_auto_index</module>: will now extract titles and
      <li><module>mod_autoindex</module>: will now extract titles and
      display descriptions for .xhtml files, which were previously
      ignored.</li>

+46 −25
Changes for modules/filters/mod_include.c: 46 added lines, 25 removed lines.
Original line number Diff line number Diff line
@@ -107,7 +107,8 @@ typedef struct parse_node {
typedef enum {
    XBITHACK_OFF,
    XBITHACK_ON,
    XBITHACK_FULL
    XBITHACK_FULL,
    XBITHACK_UNSET
} xbithack_t;

typedef struct {
@@ -115,9 +116,9 @@ typedef struct {
    const char *default_time_fmt;
    const char *undefined_echo;
    xbithack_t  xbithack;
    int accessenable;
    int lastmodified;
    int etag;
    signed char accessenable;
    signed char lastmodified;
    signed char etag;
} include_dir_config;

typedef struct {
@@ -462,9 +463,8 @@ static const char lazy_eval_sentinel;
#define DEFAULT_ERROR_MSG "[an error occurred while processing this directive]"
#define DEFAULT_TIME_FORMAT "%A, %d-%b-%Y %H:%M:%S %Z"
#define DEFAULT_UNDEFINED_ECHO "(none)"
#define DEFAULT_ACCESSENABLE 0
#define DEFAULT_LASTMODIFIED 0
#define DEFAULT_ETAG 0

#define UNSET -1

#ifdef XBITHACK
#define DEFAULT_XBITHACK XBITHACK_FULL
@@ -3686,7 +3686,7 @@ static int includes_setup(ap_filter_t *f)
     * We don't know if we are going to be including a file or executing
     * a program - in either case a strong ETag header will likely be invalid.
     */
    if (!conf->etag) {
    if (conf->etag <= 0) {
        apr_table_setn(f->r->notes, "no-etag", "");
    }

@@ -3730,20 +3730,23 @@ static apr_status_t includes_filter(ap_filter_t *f, apr_bucket_brigade *b)
        if ((ap_allow_options(r) & OPT_INC_WITH_EXEC) == 0) {
            ctx->flags |= SSI_FLAG_NO_EXEC;
        }
        intern->accessenable = conf->accessenable;
        intern->accessenable = (conf->accessenable > 0);

        ctx->if_nesting_level = 0;
        intern->re = NULL;

        ctx->error_str = conf->default_error_msg;
        ctx->time_str = conf->default_time_fmt;
        ctx->error_str = conf->default_error_msg ? conf->default_error_msg :
                         DEFAULT_ERROR_MSG;
        ctx->time_str = conf->default_time_fmt ? conf->default_time_fmt :
                        DEFAULT_TIME_FORMAT;
        intern->start_seq  = sconf->default_start_tag;
        intern->start_seq_pat = bndm_compile(ctx->pool, intern->start_seq,
                                             strlen(intern->start_seq));
        intern->end_seq = sconf->default_end_tag;
        intern->end_seq_len = strlen(intern->end_seq);
        intern->undefined_echo = conf->undefined_echo;
        intern->undefined_echo_len = strlen(conf->undefined_echo);
        intern->undefined_echo = conf->undefined_echo ? conf->undefined_echo :
                                 DEFAULT_UNDEFINED_ECHO;
        intern->undefined_echo_len = strlen(intern->undefined_echo);
    }

    if ((parent = ap_get_module_config(r->request_config, &include_module))) {
@@ -3787,7 +3790,7 @@ static apr_status_t includes_filter(ap_filter_t *f, apr_bucket_brigade *b)
     */

    /* Must we respect the last modified header? By default, no */
    if (conf->lastmodified) {
    if (conf->lastmodified > 0) {

        /* update the last modified if we have a valid time, and only if
         * we don't already have a valid last modified.
@@ -3801,7 +3804,9 @@ static apr_status_t includes_filter(ap_filter_t *f, apr_bucket_brigade *b)
    }

    /* Assure the platform supports Group protections */
    else if (((conf->xbithack == XBITHACK_FULL)
    else if (((conf->xbithack == XBITHACK_FULL ||
               (conf->xbithack == XBITHACK_UNSET &&
                DEFAULT_XBITHACK == XBITHACK_FULL))
        && (r->finfo.valid & APR_FINFO_GPROT)
        && (r->finfo.protection & APR_GEXECUTE))) {
        ap_update_mtime(r, r->finfo.mtime);
@@ -3844,7 +3849,10 @@ static int include_fixup(request_rec *r)
        include_dir_config *conf = ap_get_module_config(r->per_dir_config,
                                                        &include_module);

        if (conf->xbithack == XBITHACK_OFF) {
        if (conf->xbithack == XBITHACK_OFF ||
            (DEFAULT_XBITHACK == XBITHACK_OFF &&
             conf->xbithack == XBITHACK_UNSET))
        {
            return DECLINED;
        }

@@ -3876,19 +3884,32 @@ static int include_fixup(request_rec *r)

static void *create_includes_dir_config(apr_pool_t *p, char *dummy)
{
    include_dir_config *result = apr_palloc(p, sizeof(include_dir_config));
    include_dir_config *result = apr_pcalloc(p, sizeof(include_dir_config));

    result->default_error_msg = DEFAULT_ERROR_MSG;
    result->default_time_fmt  = DEFAULT_TIME_FORMAT;
    result->undefined_echo    = DEFAULT_UNDEFINED_ECHO;
    result->xbithack          = DEFAULT_XBITHACK;
    result->accessenable      = DEFAULT_ACCESSENABLE;
    result->lastmodified      = DEFAULT_LASTMODIFIED;
    result->etag              = DEFAULT_ETAG;
    result->xbithack          = XBITHACK_UNSET;
    result->accessenable      = UNSET;
    result->lastmodified      = UNSET;
    result->etag              = UNSET;

    return result;
}

#define MERGE(b,o,n,val,unset) n->val = o->val != unset  ? o->val : b->val
static void *merge_includes_dir_config(apr_pool_t *p, void *basev, void *overridesv)
{
    include_dir_config *base = (include_dir_config *)basev,
                       *over = (include_dir_config *)overridesv,
                       *new  = apr_palloc(p, sizeof(include_dir_config));
    MERGE(base, over, new, default_error_msg, NULL);
    MERGE(base, over, new, default_time_fmt,  NULL);
    MERGE(base, over, new, undefined_echo,    NULL);
    MERGE(base, over, new, xbithack,          XBITHACK_UNSET);
    MERGE(base, over, new, accessenable,      UNSET);
    MERGE(base, over, new, lastmodified,      UNSET);
    MERGE(base, over, new, etag,              UNSET);
    return new;
}

static void *create_includes_server_config(apr_pool_t *p, server_rec *server)
{
    include_server_config *result;
@@ -4068,7 +4089,7 @@ AP_DECLARE_MODULE(include) =
{
    STANDARD20_MODULE_STUFF,
    create_includes_dir_config,   /* dir config creater */
    NULL,                         /* dir merger --- default is to override */
    merge_includes_dir_config,    /* dir config merger */
    create_includes_server_config,/* server config */
    NULL,                         /* merge server config */
    includes_cmds,                /* command apr_table_t */