Changes with Apache 2.0.25-dev
+ *) Introduce the map_to_storage hook, which allows modules to bypass
+ the directory_walk and file_walk for non-file requests. TRACE
+ shortcut moved to http_protocol.c as APR_HOOK_MIDDLE, and the
+ directory_walk/file_walk happen as APR_HOOK_VERY_LAST in core.c.
+ [William Rowe]
+
*) Add the ability for mod_include to add the INCLUDES filter
if the file is configured for the server-parsed handler.
This makes the configuration for .shtml files much easier
*/
AP_DECLARE_HOOK(int,translate_name,(request_rec *r))
+/**
+ * This hook allow modules to set the per_dir_config based on their own
+ * context (such as <Proxy > sections) and responds to contextless requests
+ * such as TRACE that need no security or filesystem mapping.
+ * based on the filesystem.
+ * @param r The current request
+ * @return DONE (or HTTP_) if this contextless request was just fulfilled
+ * (such as TRACE), OK if this is not a file, and DECLINED if this is a file.
+ * The core map_to_storage (HOOK_RUN_LAST) will directory_walk and file_walk
+ * the r->filename.
+ *
+ * @ingroup hooks
+ */
+AP_DECLARE_HOOK(int,map_to_storage,(request_rec *r))
+
/**
* This hook allows modules to check the authentication information sent with
* the request.
*/
AP_DECLARE_HOOK(void,insert_filter,(request_rec *r))
-AP_DECLARE(int) directory_walk(request_rec *r);
-AP_DECLARE(int) location_walk(request_rec *r);
-AP_DECLARE(int) file_walk(request_rec *r);
+AP_DECLARE(int) ap_location_walk(request_rec *r);
+AP_DECLARE(int) ap_directory_walk(request_rec *r);
+AP_DECLARE(int) ap_file_walk(request_rec *r);
#ifdef __cplusplus
}
APR_HOOK_REALLY_LAST);
ap_hook_process_connection(ap_process_http_connection,NULL,NULL,
APR_HOOK_REALLY_LAST);
+ ap_hook_map_to_storage(ap_send_http_trace,NULL,NULL,APR_HOOK_MIDDLE);
ap_hook_http_method(http_method,NULL,NULL,APR_HOOK_REALLY_LAST);
ap_hook_default_port(http_port,NULL,NULL,APR_HOOK_REALLY_LAST);
return list + 2;
}
-AP_DECLARE(int) ap_send_http_trace(request_rec *r)
+AP_DECLARE_NONSTD(int) ap_send_http_trace(request_rec *r)
{
int rv;
apr_bucket_brigade *b;
header_struct h;
+ if (r->method_number != M_TRACE)
+ return DECLINED;
+
/* Get the original request */
while (r->prev)
r = r->prev;
apr_brigade_puts(b, NULL, NULL, CRLF);
ap_pass_brigade(r->output_filters, b);
- return OK;
+ return DONE;
}
AP_DECLARE(int) ap_send_http_options(request_rec *r)
ap_getparents(r->uri); /* OK --- shrinking transformations... */
- if ((access_status = location_walk(r))) {
+ if ((access_status = ap_location_walk(r))) {
ap_die(access_status, r);
return;
}
return;
}
- if (r->proto_num > HTTP_VERSION(1,0) && apr_table_get(r->subprocess_env, "downgrade-1.0")) {
- r->proto_num = HTTP_VERSION(1,0);
- }
-
- if (!r->proxyreq) {
- /*
- * We don't want TRACE to run through the normal handler set, we
- * handle it specially.
- */
- if (r->method_number == M_TRACE) {
- if ((access_status = ap_send_http_trace(r)))
- ap_die(access_status, r);
- else
- ap_finalize_request_protocol(r);
- return;
- }
- }
-
- /*
- * NB: directory_walk() clears the per_dir_config, so we don't inherit
- * from location_walk() above
- */
-
- if ((access_status = directory_walk(r))) {
- ap_die(access_status, r);
- return;
- }
-
- if ((access_status = file_walk(r))) {
- ap_die(access_status, r);
+ if ((access_status = ap_run_map_to_storage(r))) {
+ /* This request wasn't in storage (e.g. TRACE) */
+ if (access_status == DONE)
+ ap_finalize_request_protocol(r);
+ else
+ ap_die(access_status, r);
return;
}
- if ((access_status = location_walk(r))) {
+ if ((access_status = ap_location_walk(r))) {
ap_die(access_status, r);
return;
}
AP_DECLARE(void) ap_basic_http_header(request_rec *r, apr_bucket_brigade *bb);
/**
- * XXX NEED DOC
+ * Send an appropriate response to an http TRACE request.
* @param r The current request
+ * @tip returns DONE or the HTTP status error if it handles the TRACE,
+ * or DECLINED if the request was not for TRACE.
+ * request method was not TRACE.
*/
-AP_DECLARE(int) ap_send_http_trace(request_rec *r);
+AP_DECLARE_NONSTD(int) ap_send_http_trace(request_rec *r);
/**
- * XXX NEED DOC
+ * Send an appropriate response to an http OPTIONS request.
* @param r The current request
*/
AP_DECLARE(int) ap_send_http_options(request_rec *r);
return OK;
}
+/*****************************************************************
+ *
+ * Test the filesystem name through directory_walk and file_walk
+ */
+static int core_map_to_storage(request_rec *r)
+{
+ int access_status;
+
+ if ((access_status = ap_directory_walk(r))) {
+ return access_status;
+ }
+
+ if ((access_status = ap_file_walk(r))) {
+ return access_status;
+ }
+
+ return OK;
+}
+
+
static int do_nothing(request_rec *r) { return OK; }
static int default_handler(request_rec *r)
{
ap_hook_post_config(core_post_config,NULL,NULL,APR_HOOK_REALLY_FIRST);
ap_hook_translate_name(ap_core_translate,NULL,NULL,APR_HOOK_REALLY_LAST);
+ ap_hook_map_to_storage(core_map_to_storage,NULL,NULL,APR_HOOK_REALLY_LAST);
ap_hook_open_logs(core_open_logs,NULL,NULL,APR_HOOK_MIDDLE);
ap_hook_handler(default_handler,NULL,NULL,APR_HOOK_REALLY_LAST);
/* FIXME: I suspect we can eliminate the need for these - Ben */
APR_HOOK_STRUCT(
APR_HOOK_LINK(translate_name)
+ APR_HOOK_LINK(map_to_storage)
APR_HOOK_LINK(check_user_id)
APR_HOOK_LINK(fixups)
APR_HOOK_LINK(type_checker)
AP_IMPLEMENT_HOOK_RUN_FIRST(int,translate_name,
(request_rec *r),(r),DECLINED)
+AP_IMPLEMENT_HOOK_RUN_FIRST(int,map_to_storage,
+ (request_rec *r),(r),DECLINED)
AP_IMPLEMENT_HOOK_RUN_FIRST(int,check_user_id,
(request_rec *r),(r),DECLINED)
AP_IMPLEMENT_HOOK_RUN_ALL(int,fixups,
return OK;
}
-AP_DECLARE(int) directory_walk(request_rec *r)
+AP_DECLARE(int) ap_directory_walk(request_rec *r)
{
core_server_config *sconf = ap_get_module_config(r->server->module_config,
&core_module);
return OK;
}
- /* The replacement code [above] for directory_walk eliminates this issue.
+ /* The replacement code [below] for directory_walk eliminates this issue.
*/
res = get_path_info(r);
if (res != OK) {
* they change, all the way down.
*/
-AP_DECLARE(int) directory_walk(request_rec *r)
+AP_DECLARE(int) ap_directory_walk(request_rec *r)
{
core_server_config *sconf = ap_get_module_config(r->server->module_config,
&core_module);
#endif /* defined REPLACE_PATH_INFO_METHOD */
-AP_DECLARE(int) location_walk(request_rec *r)
+
+AP_DECLARE(int) ap_location_walk(request_rec *r)
{
core_server_config *sconf = ap_get_module_config(r->server->module_config,
&core_module);
return OK;
}
-AP_DECLARE(int) file_walk(request_rec *r)
+AP_DECLARE(int) ap_file_walk(request_rec *r)
{
core_dir_config *conf = ap_get_module_config(r->per_dir_config,
&core_module);
return OK;
}
-
/*****************************************************************
*
* The sub_request mechanism.
ap_getparents(rnew->uri);
- if ((res = location_walk(rnew))) {
+ if ((res = ap_location_walk(rnew))) {
rnew->status = res;
return rnew;
}
* from location_walk() above
*/
- if ((res = directory_walk(rnew))
- || (res = file_walk(rnew))
- || (res = location_walk(rnew))
+ if ((res = ap_directory_walk(rnew))
+ || (res = ap_file_walk(rnew))
+ || (res = ap_location_walk(rnew))
|| (res = sub_req_common_validation(rnew))) {
rnew->status = res;
}
* directory_walk
*/
if (rnew->finfo.filetype == APR_DIR) {
- if (!(res = directory_walk(rnew)))
- if (!(res = file_walk(rnew)))
- res = location_walk(rnew);
+ if (!(res = ap_directory_walk(rnew)))
+ if (!(res = ap_file_walk(rnew)))
+ res = ap_location_walk(rnew);
}
else if (rnew->finfo.filetype == APR_REG || !rnew->finfo.filetype) {
/*
* do a file_walk, if it doesn't change the per_dir_config then
* we know that we don't have to redo all the access checks
*/
- if ( !(res = file_walk(rnew))
- && !(res = location_walk(rnew))
+ if ( !(res = ap_file_walk(rnew))
+ && !(res = ap_location_walk(rnew))
&& (rnew->per_dir_config == r->per_dir_config))
{
if ( (res = ap_run_type_checker(rnew))
* directory_walk
*/
if (rnew->finfo.filetype == APR_DIR) {
- if (!(res = directory_walk(rnew)))
- if (!(res = file_walk(rnew)))
- res = location_walk(rnew);
+ if (!(res = ap_directory_walk(rnew)))
+ if (!(res = ap_file_walk(rnew)))
+ res = ap_location_walk(rnew);
}
else if (rnew->finfo.filetype == APR_REG || !rnew->finfo.filetype) {
/*
* do a file_walk, if it doesn't change the per_dir_config then
* we know that we don't have to redo all the access checks
*/
- if ( !(res = file_walk(rnew))
- && !(res = location_walk(rnew))
+ if ( !(res = ap_file_walk(rnew))
+ && !(res = ap_location_walk(rnew))
&& (rnew->per_dir_config == r->per_dir_config))
{
if ( (res = ap_run_type_checker(rnew))
*/
rnew->uri = "INTERNALLY GENERATED file-relative req";
rnew->per_dir_config = r->server->lookup_defaults;
- res = directory_walk(rnew);
+ res = ap_directory_walk(rnew);
if (!res) {
- res = file_walk(rnew);
+ res = ap_file_walk(rnew);
}
}