* Therefore we limit the resulting length of the line.
* This is the default value.
*/
-#define AP_SUBST_MAX_LINE_LENGTH (128*MAX_STRING_LEN)
+#define AP_SUBST_MAX_LINE_LENGTH (1024*1024)
static const char substitute_filter_name[] = "SUBSTITUTE";
apr_array_header_t *patterns;
apr_size_t max_line_length;
int max_line_length_set;
+ int inherit_before;
} subst_dir_conf;
typedef struct {
static void *create_substitute_dcfg(apr_pool_t *p, char *d)
{
subst_dir_conf *dcfg =
- (subst_dir_conf *) apr_pcalloc(p, sizeof(subst_dir_conf));
+ (subst_dir_conf *) apr_palloc(p, sizeof(subst_dir_conf));
dcfg->patterns = apr_array_make(p, 10, sizeof(subst_pattern_t));
dcfg->max_line_length = AP_SUBST_MAX_LINE_LENGTH;
+ dcfg->max_line_length_set = 0;
+ dcfg->inherit_before = -1;
return dcfg;
}
static void *merge_substitute_dcfg(apr_pool_t *p, void *basev, void *overv)
{
subst_dir_conf *a =
- (subst_dir_conf *) apr_pcalloc(p, sizeof(subst_dir_conf));
+ (subst_dir_conf *) apr_palloc(p, sizeof(subst_dir_conf));
subst_dir_conf *base = (subst_dir_conf *) basev;
subst_dir_conf *over = (subst_dir_conf *) overv;
- a->patterns = apr_array_append(p, over->patterns,
- base->patterns);
+ a->inherit_before = (over->inherit_before != -1)
+ ? over->inherit_before
+ : base->inherit_before;
+ /* SubstituteInheritBefore wasn't the default behavior until 2.5.x,
+ * and may be re-disabled as desired; the original default behavior
+ * was to apply inherited subst patterns after locally scoped patterns.
+ * In later 2.2 and 2.4 versions, SubstituteInheritBefore may be toggled
+ * 'on' to follow the corrected/expected behavior, without violating POLS.
+ */
+ if (a->inherit_before == 1) {
+ a->patterns = apr_array_append(p, base->patterns,
+ over->patterns);
+ }
+ else {
+ a->patterns = apr_array_append(p, over->patterns,
+ base->patterns);
+ }
a->max_line_length = over->max_line_length_set ?
- over->max_line_length : base->max_line_length;
- a->max_line_length_set = over->max_line_length_set ?
- over->max_line_length_set : base->max_line_length_set;
+ over->max_line_length : base->max_line_length;
+ a->max_line_length_set = over->max_line_length_set
+ | base->max_line_length_set;
return a;
}
apr_status_t rv;
have_match = 1;
if (script->flatten && !force_quick) {
- /* copy bytes before the match */
+ /* check remaining buffer size */
+ /* Note that the last param in ap_varbuf_regsub below
+ * must stay positive. If it gets 0, it would mean
+ * unlimited space available. */
if (vb.strlen + regm[0].rm_so >= cfg->max_line_length)
return APR_ENOMEM;
+ /* copy bytes before the match */
if (regm[0].rm_so > 0)
ap_varbuf_strmemcat(&vb, pos, regm[0].rm_so);
/* add replacement string, last argument is unsigned! */
if (rv != APR_SUCCESS)
goto err;
APR_BRIGADE_CONCAT(ctx->passbb, ctx->pattbb);
+ apr_brigade_cleanup(ctx->linebb);
}
- apr_brigade_cleanup(ctx->linebb);
APR_BUCKET_REMOVE(b);
APR_BRIGADE_INSERT_TAIL(ctx->passbb, b);
}
if (rv != APR_SUCCESS || max < 0)
{
return "SubstituteMaxLineLength must be a non-negative integer optionally "
- "suffixed with 'k', 'm' or 'g'.";
+ "suffixed with 'b', 'k', 'm' or 'g'.";
}
dcfg->max_line_length = (apr_size_t)max;
dcfg->max_line_length_set = 1;
}
static const command_rec substitute_cmds[] = {
- AP_INIT_TAKE1("Substitute", set_pattern, NULL, OR_ALL,
+ AP_INIT_TAKE1("Substitute", set_pattern, NULL, OR_FILEINFO,
"Pattern to filter the response content (s/foo/bar/[inf])"),
- AP_INIT_TAKE1("SubstituteMaxLineLength", set_max_line_length, NULL, OR_ALL,
+ AP_INIT_TAKE1("SubstituteMaxLineLength", set_max_line_length, NULL, OR_FILEINFO,
"Maximum line length"),
+ AP_INIT_FLAG("SubstituteInheritBefore", ap_set_flag_slot,
+ (void *)APR_OFFSETOF(subst_dir_conf, inherit_before), OR_FILEINFO,
+ "Apply inherited patterns before those of the current context"),
{NULL}
};