methods</description>
<syntax><Limit <var>method</var> [<var>method</var>] ... > ...
</Limit></syntax>
-<contextlist><context>server config</context><context>virtual host</context>
-<context>directory</context><context>.htaccess</context>
+<contextlist><context>directory</context><context>.htaccess</context>
</contextlist>
-<override>All</override>
+<override>AuthConfig, Limit</override>
<usage>
<p>Access controls are normally effective for
<code>LOCK</code>, and <code>UNLOCK</code>. <strong>The method name is
case-sensitive.</strong> If <code>GET</code> is used it will also
restrict <code>HEAD</code> requests. The <code>TRACE</code> method
- cannot be limited (see <directive type="section" module="core"
+ cannot be limited (see <directive module="core"
>TraceEnable</directive>).</p>
<note type="warning">A <directive type="section"
module="core">LimitExcept</directive> section should always be
- used in preference to a <directive type="section"
- module="core">Limit</directive> section when restricting access,
- since a <directive type="section"
+ used in preference to a <directive type="section">Limit</directive>
+ section when restricting access, since a <directive type="section"
module="core">LimitExcept</directive> section provides protection
against arbitrary methods.</note>
+ <p>The <directive type="section">Limit</directive> and
+ <directive type="section" module="core">LimitExcept</directive>
+ directives may be nested. In this case, each successive level of
+ <directive type="section">Limit</directive> or <directive
+ type="section" module="core">LimitExcept</directive> directives must
+ further restrict the set of methods to which access controls apply.</p>
+
+ <note type="warning">When using
+ <directive type="section">Limit</directive> or
+ <directive type="section">LimitExcept</directive> directives with
+ the <directive module="mod_authz_core">Require</directive> directive,
+ note that the first <directive module="mod_authz_core">Require</directive>
+ to succeed authorizes the request, regardless of the presence of other
+ <directive module="mod_authz_core">Require</directive> directives.</note>
+
+ <p>For example, given the following configuration, all users will
+ be authorized for <code>POST</code> requests, and the
+ <code>Require group editors</code> directive will be ignored
+ in all cases:</p>
+
+ <example>
+ <LimitExcept GET>
+ <indent>
+ Require valid-user
+ </indent>
+ </LimitExcept><br />
+ <Limit POST>
+ <indent>
+ Require group editors
+ </indent>
+ </Limit>
+ </example>
</usage>
</directivesynopsis>
except the named ones</description>
<syntax><LimitExcept <var>method</var> [<var>method</var>] ... > ...
</LimitExcept></syntax>
-<contextlist><context>server config</context><context>virtual host</context>
-<context>directory</context><context>.htaccess</context>
+<contextlist><context>directory</context><context>.htaccess</context>
</contextlist>
-<override>All</override>
+<override>AuthConfig, Limit</override>
<usage>
<p><directive type="section">LimitExcept</directive> and
}
/*
- * Optional function coming from mod_authn_core, used for
+ * Optional function coming from mod_authn_core, used for
* retrieving the type of autorization
*/
static APR_OPTIONAL_FN_TYPE(authn_ap_auth_type) *authn_ap_auth_type;
}
/*
- * Optional function coming from mod_authn_core, used for
+ * Optional function coming from mod_authn_core, used for
* retrieving the authorization realm
*/
static APR_OPTIONAL_FN_TYPE(authn_ap_auth_name) *authn_ap_auth_name;
" cannot occur within <VirtualHost> section", NULL);
}
- if ((forbidden & NOT_IN_LIMIT) && cmd->limited != -1) {
+ if ((forbidden & (NOT_IN_LIMIT | NOT_IN_DIR_LOC_FILE))
+ && cmd->limited != -1) {
return apr_pstrcat(cmd->pool, cmd->cmd->name, gt,
- " cannot occur within <Limit> section", NULL);
+ " cannot occur within <Limit> or <LimitExcept> "
+ "section", NULL);
}
if ((forbidden & NOT_IN_DIR_LOC_FILE) == NOT_IN_DIR_LOC_FILE) {
const char *limited_methods;
void *tog = cmd->cmd->cmd_data;
apr_int64_t limited = 0;
+ apr_int64_t old_limited = cmd->limited;
const char *errmsg;
- const char *err = ap_check_cmd_context(cmd, NOT_IN_LIMIT);
- if (err != NULL) {
- return err;
- }
-
if (endp == NULL) {
return unclosed_directive(cmd);
}
/* Killing two features with one function,
* if (tog == NULL) <Limit>, else <LimitExcept>
*/
- cmd->limited = tog ? ~limited : limited;
+ limited = tog ? ~limited : limited;
+
+ if (!(old_limited & limited)) {
+ return apr_pstrcat(cmd->pool, cmd->cmd->name,
+ "> directive excludes all methods", NULL);
+ }
+ else if ((old_limited & limited) == old_limited) {
+ return apr_pstrcat(cmd->pool, cmd->cmd->name,
+ "> directive specifies methods already excluded",
+ NULL);
+ }
+
+ cmd->limited &= limited;
errmsg = ap_walk_config(cmd->directive->first_child, cmd, cmd->context);
- cmd->limited = -1;
+ cmd->limited = old_limited;
return errmsg;
}
const command_rec *thiscmd = cmd->cmd;
core_dir_config *c = mconfig;
ap_conf_vector_t *new_file_conf = ap_create_per_dir_config(cmd->pool);
- const char *err = ap_check_cmd_context(cmd, NOT_IN_LOCATION);
+ const char *err = ap_check_cmd_context(cmd,
+ NOT_IN_LOCATION | NOT_IN_LIMIT);
if (err != NULL) {
return err;
const command_rec *thiscmd = cmd->cmd;
core_dir_config *c = mconfig;
ap_conf_vector_t *new_file_conf = ap_create_per_dir_config(cmd->pool);
- const char *err = ap_check_cmd_context(cmd, NOT_IN_LOCATION);
+ const char *err = ap_check_cmd_context(cmd,
+ NOT_IN_LOCATION | NOT_IN_LIMIT);
const char *condition;
int expr_err = 0;
"more host addresses"),
AP_INIT_RAW_ARGS("<Files", filesection, NULL, OR_ALL,
"Container for directives affecting files matching specified patterns"),
-AP_INIT_RAW_ARGS("<Limit", ap_limit_section, NULL, OR_ALL,
+AP_INIT_RAW_ARGS("<Limit", ap_limit_section, NULL, OR_LIMIT | OR_AUTHCFG,
"Container for authentication directives when accessed using specified HTTP "
"methods"),
-AP_INIT_RAW_ARGS("<LimitExcept", ap_limit_section, (void*)1, OR_ALL,
+AP_INIT_RAW_ARGS("<LimitExcept", ap_limit_section, (void*)1,
+ OR_LIMIT | OR_AUTHCFG,
"Container for authentication directives to be applied when any HTTP "
"method other than those specified is used to access the resource"),
AP_INIT_TAKE1("<IfModule", start_ifmod, NULL, EXEC_ON_READ | OR_ALL,