mod_authz_core.c revision 21da42a6b8f551ef603bd06356d3bf71d6d0c21d
5beae861ede7eba138c7140f195ae77ba3106cbffielding/* Licensed to the Apache Software Foundation (ASF) under one or more
5beae861ede7eba138c7140f195ae77ba3106cbffielding * contributor license agreements. See the NOTICE file distributed with
5beae861ede7eba138c7140f195ae77ba3106cbffielding * this work for additional information regarding copyright ownership.
fd2db14d870ff9aa9795841360f6e3d562ad69a2jerenkrantz * The ASF licenses this file to You under the Apache License, Version 2.0
5beae861ede7eba138c7140f195ae77ba3106cbffielding * (the "License"); you may not use this file except in compliance with
5beae861ede7eba138c7140f195ae77ba3106cbffielding * the License. You may obtain a copy of the License at
5beae861ede7eba138c7140f195ae77ba3106cbffielding * Unless required by applicable law or agreed to in writing, software
5beae861ede7eba138c7140f195ae77ba3106cbffielding * distributed under the License is distributed on an "AS IS" BASIS,
5beae861ede7eba138c7140f195ae77ba3106cbffielding * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
5beae861ede7eba138c7140f195ae77ba3106cbffielding * See the License for the specific language governing permissions and
5beae861ede7eba138c7140f195ae77ba3106cbffielding * limitations under the License.
5beae861ede7eba138c7140f195ae77ba3106cbffielding * Security options etc.
5beae861ede7eba138c7140f195ae77ba3106cbffielding * Module derived from code originally written by Rob McCool
5beae861ede7eba138c7140f195ae77ba3106cbffieldingtypedef struct provider_alias_rec {
5beae861ede7eba138c7140f195ae77ba3106cbffieldingtypedef enum {
5beae861ede7eba138c7140f195ae77ba3106cbffieldingtypedef struct authz_section_conf authz_section_conf;
e38f3ccb1d1368339739ba98be433ec16b1967e4aaron /** true if this is not a real container but produced by AuthMerging;
5beae861ede7eba138c7140f195ae77ba3106cbffielding * only used for logging */
7b3ca63bf6e5fe39125b04327d321d61da0afe89jerenkrantztypedef struct authz_core_dir_conf authz_core_dir_conf;
5beae861ede7eba138c7140f195ae77ba3106cbffieldingtypedef struct authz_core_srv_conf {
5beae861ede7eba138c7140f195ae77ba3106cbffieldingstatic authz_core_dir_conf *authz_core_first_dir_conf;
5beae861ede7eba138c7140f195ae77ba3106cbffieldingstatic void *create_authz_core_dir_config(apr_pool_t *p, char *dummy)
5beae861ede7eba138c7140f195ae77ba3106cbffielding authz_core_dir_conf *conf = apr_pcalloc(p, sizeof(*conf));
acf47691e4f2e788ea89e30f27015402f4bf9075trawick return (void *)conf;
5beae861ede7eba138c7140f195ae77ba3106cbffieldingstatic void *merge_authz_core_dir_config(apr_pool_t *p,
5beae861ede7eba138c7140f195ae77ba3106cbffielding authz_core_dir_conf *base = (authz_core_dir_conf *)basev;
5beae861ede7eba138c7140f195ae77ba3106cbffielding authz_core_dir_conf *new = (authz_core_dir_conf *)newv;
5beae861ede7eba138c7140f195ae77ba3106cbffielding if (new->op == AUTHZ_LOGIC_UNSET && !new->section && base->section ) {
5beae861ede7eba138c7140f195ae77ba3106cbffielding /* Only authz_forbidden_on_fail has been set in new. Don't treat
5beae861ede7eba138c7140f195ae77ba3106cbffielding * it as a new auth config w.r.t. AuthMerging */
5beae861ede7eba138c7140f195ae77ba3106cbffielding else if (new->op == AUTHZ_LOGIC_OFF || new->op == AUTHZ_LOGIC_UNSET ||
5beae861ede7eba138c7140f195ae77ba3106cbffielding section->first->next = apr_pmemdup(p, new->section,
fd2db14d870ff9aa9795841360f6e3d562ad69a2jerenkrantz section = apr_pmemdup(p, new->section, sizeof(*new->section));
5beae861ede7eba138c7140f195ae77ba3106cbffielding conf->authz_forbidden_on_fail = base->authz_forbidden_on_fail;
5beae861ede7eba138c7140f195ae77ba3106cbffielding conf->authz_forbidden_on_fail = new->authz_forbidden_on_fail;
5beae861ede7eba138c7140f195ae77ba3106cbffielding return (void*)conf;
fd2db14d870ff9aa9795841360f6e3d562ad69a2jerenkrantzstatic void *create_authz_core_svr_config(apr_pool_t *p, server_rec *s)
5beae861ede7eba138c7140f195ae77ba3106cbffielding return (void *)authcfg;
5beae861ede7eba138c7140f195ae77ba3106cbffielding/* This is a fake authz provider that really merges various authz alias
5beae861ede7eba138c7140f195ae77ba3106cbffielding * configurations and then invokes them.
5beae861ede7eba138c7140f195ae77ba3106cbffieldingstatic authz_status authz_alias_check_authorization(request_rec *r,
5beae861ede7eba138c7140f195ae77ba3106cbffielding /* Look up the provider alias in the alias list.
5beae861ede7eba138c7140f195ae77ba3106cbffielding * Get the the dir_config and call ap_Merge_per_dir_configs()
5beae861ede7eba138c7140f195ae77ba3106cbffielding * Call the real provider->check_authorization() function
5beae861ede7eba138c7140f195ae77ba3106cbffielding * return the result of the above function call
5beae861ede7eba138c7140f195ae77ba3106cbffielding provider_name = apr_table_get(r->notes, AUTHZ_PROVIDER_NAME_NOTE);
5beae861ede7eba138c7140f195ae77ba3106cbffielding authcfg = ap_get_module_config(r->server->module_config,
5beae861ede7eba138c7140f195ae77ba3106cbffielding prvdraliasrec = apr_hash_get(authcfg->alias_rec, provider_name,
5beae861ede7eba138c7140f195ae77ba3106cbffielding /* If we found the alias provider in the list, then merge the directory
5beae861ede7eba138c7140f195ae77ba3106cbffielding configurations and call the real provider */
5beae861ede7eba138c7140f195ae77ba3106cbffielding ap_conf_vector_t *orig_dir_config = r->per_dir_config;
5beae861ede7eba138c7140f195ae77ba3106cbffielding check_authorization(r, prvdraliasrec->provider_args,
5beae861ede7eba138c7140f195ae77ba3106cbffielding ap_log_rerror(APLOG_MARK, APLOG_ERR, 0, r, APLOGNO(02305)
5beae861ede7eba138c7140f195ae77ba3106cbffielding "no alias provider found for '%s' (BUG?)",
5beae861ede7eba138c7140f195ae77ba3106cbffieldingstatic const char *authz_require_alias_section(cmd_parms *cmd, void *mconfig,
5beae861ede7eba138c7140f195ae77ba3106cbffielding const char *args)
5beae861ede7eba138c7140f195ae77ba3106cbffielding const char *errmsg;
5beae861ede7eba138c7140f195ae77ba3106cbffielding const char *err = ap_check_cmd_context(cmd, GLOBAL_ONLY);
5beae861ede7eba138c7140f195ae77ba3106cbffielding args = apr_pstrndup(cmd->temp_pool, args, endp - args);
5beae861ede7eba138c7140f195ae77ba3106cbffielding "> directive requires additional arguments", NULL);
5beae861ede7eba138c7140f195ae77ba3106cbffielding /* Pull the real provider name and the alias name from the block header */
5beae861ede7eba138c7140f195ae77ba3106cbffielding provider_alias = ap_getword_conf(cmd->pool, &args);
if (!errmsg) {
if (err)
return errmsg;
return section;
const char *args)
if (err)
return err;
if (child) {
return NULL;
const char *args)
const char *errmsg;
if (args[0]) {
NULL);
if (errmsg) {
return errmsg;
if (!old_section) {
if (child) {
NULL);
return NULL;
const char *arg)
return NULL;
while (child) {
return !OK;
if (prev) {
while (child) {
return ret;
return OK;
while (conf) {
return !OK;
return OK;
#ifdef AUTHZ_EXTRA_CONFIGS
{NULL}
return auth_result;
while (child) {
return AUTHZ_GENERAL_ERROR;
* Handling of AUTHZ_DENIED/AUTHZ_DENIED_NO_USER: Return
return auth_result;
if (ap_auth_type(r)) {
return HTTP_INTERNAL_SERVER_ERROR;
return OK;
return OK;
if (after_authn) {
r->uri);
if (r->user)
return HTTP_UNAUTHORIZED;
return DECLINED;
return HTTP_FORBIDDEN;
return HTTP_FORBIDDEN;
if (r->user)
return HTTP_UNAUTHORIZED;
return HTTP_INTERNAL_SERVER_ERROR;
return authorize_user_core(r, 0);
const char *require_line,
const void *parsed_require_line)
t = require_line;
return AUTHZ_GRANTED;
return AUTHZ_DENIED;
NULL,
const char *require_line,
const void *parsed_require_line)
if (parsed_require_line) {
return AUTHZ_GRANTED;
return AUTHZ_DENIED;
const void **parsed_require_line)
return NULL;
return NULL;
const char *require_line,
const void *parsed_require_line)
return AUTHZ_GRANTED;
return AUTHZ_DENIED;
const void **parsed_require_line)
t = require_line;
int m = ap_method_number_of(w);
if (m == M_INVALID) {
return NULL;
const char *require_line,
const void *parsed_require_line)
if (rc <= 0)
return AUTHZ_DENIED;
return AUTHZ_GRANTED;
const void **parsed_require_line)
NULL);
if (expr_err)
return NULL;