From e80327a02e9c5372db8691f592596c94f232f9f2 Mon Sep 17 00:00:00 2001 From: Cliff Woolley Date: Mon, 6 May 2002 03:10:24 +0000 Subject: [PATCH] Added an optional function (ap_register_rewrite_mapfunc) which allows third-party modules to extend mod_rewrite's "int:" internal RewriteMap functionality. Concept by: Tahiry Ramanamampanoharana git-svn-id: https://svn.apache.org/repos/asf/httpd/httpd/trunk@94939 13f79535-47bb-0310-9956-ffa450edef68 --- CHANGES | 4 +++ modules/mappers/mod_rewrite.c | 62 ++++++++++++++++++++--------------- modules/mappers/mod_rewrite.h | 22 +++++++++---- 3 files changed, 54 insertions(+), 34 deletions(-) diff --git a/CHANGES b/CHANGES index 57a4c47002..9d80ea135b 100644 --- a/CHANGES +++ b/CHANGES @@ -1,5 +1,9 @@ Changes with Apache 2.0.37 + *) Allow mod_rewrite's set of "int:" internal RewriteMap functions + to be extended by third-party modules via an optional function. + [Tahiry Ramanamampanoharana , Cliff Woolley] + *) Fix mod_include expression parser's handling of unquoted strings followed immediately by a closing paren. PR 8462. [Brian Pane] diff --git a/modules/mappers/mod_rewrite.c b/modules/mappers/mod_rewrite.c index 6ad33aa812..0acb04ef14 100644 --- a/modules/mappers/mod_rewrite.c +++ b/modules/mappers/mod_rewrite.c @@ -90,6 +90,7 @@ #include "apr.h" #include "apr_strings.h" +#include "apr_hash.h" #include "apr_user.h" #include "apr_lib.h" #include "apr_signal.h" @@ -180,6 +181,9 @@ /* the module (predeclaration) */ module AP_MODULE_DECLARE_DATA rewrite_module; + /* rewritemap int: handler function registry */ +static apr_hash_t *mapfunc_hash; + /* the cache */ static cache *cachep; @@ -458,19 +462,8 @@ static const char *cmd_rewritemap(cmd_parms *cmd, void *dconf, const char *a1, newmap->type = MAPTYPE_INT; newmap->datafile = NULL; newmap->checkfile = NULL; - if (strcmp(a2+4, "tolower") == 0) { - newmap->func = rewrite_mapfunc_tolower; - } - else if (strcmp(a2+4, "toupper") == 0) { - newmap->func = rewrite_mapfunc_toupper; - } - else if (strcmp(a2+4, "escape") == 0) { - newmap->func = rewrite_mapfunc_escape; - } - else if (strcmp(a2+4, "unescape") == 0) { - newmap->func = rewrite_mapfunc_unescape; - } - else if (sconf->state == ENGINE_ENABLED) { + newmap->func = apr_hash_get(mapfunc_hash, a2+4, strlen(a2+4)); + if ((sconf->state == ENGINE_ENABLED) && (newmap->func == NULL)) { return apr_pstrcat(cmd->pool, "RewriteMap: internal map not found:", a2+4, NULL); } @@ -921,15 +914,31 @@ static const char *cmd_rewriterule_setflag(apr_pool_t *p, rewriterule_entry *cfg /* ** ** Global Module Initialization -** [called from read_config() after all -** config commands were already called] ** */ -static int init_module(apr_pool_t *p, - apr_pool_t *plog, - apr_pool_t *ptemp, - server_rec *s) +static int pre_config(apr_pool_t *pconf, + apr_pool_t *plog, + apr_pool_t *ptemp) +{ + APR_OPTIONAL_FN_TYPE(ap_register_rewrite_mapfunc) *map_pfn_register; + + /* register int: rewritemap handlers */ + mapfunc_hash = apr_hash_make(pconf); + map_pfn_register = APR_RETRIEVE_OPTIONAL_FN(ap_register_rewrite_mapfunc); + if (map_pfn_register) { + map_pfn_register("tolower", rewrite_mapfunc_tolower); + map_pfn_register("toupper", rewrite_mapfunc_toupper); + map_pfn_register("escape", rewrite_mapfunc_escape); + map_pfn_register("unescape", rewrite_mapfunc_unescape); + } + return OK; +} + +static int post_config(apr_pool_t *p, + apr_pool_t *plog, + apr_pool_t *ptemp, + server_rec *s) { apr_status_t rv; void *data; @@ -2781,7 +2790,7 @@ static char *lookup_map(request_rec *r, char *name, char *key) } } else if (s->type == MAPTYPE_INT) { - if ((value = lookup_map_internal(r, s->func, key)) != NULL) { + if ((value = s->func(r, key)) != NULL) { rewritelog(r, 5, "map lookup OK: map=%s key=%s -> val=%s", s->name, key, value); return value; @@ -2982,13 +2991,9 @@ static char *lookup_map_program(request_rec *r, apr_file_t *fpin, } } -static char *lookup_map_internal(request_rec *r, - char *(*func)(request_rec *, char *), - char *key) +static void ap_register_rewrite_mapfunc(char *name, rewrite_mapfunc_t *func) { - /* currently we just let the function convert - the key to a corresponding value */ - return func(r, key); + apr_hash_set(mapfunc_hash, name, strlen(name), (const void *)func); } static char *rewrite_mapfunc_toupper(request_rec *r, char *key) @@ -4187,8 +4192,11 @@ static const command_rec command_table[] = { static void register_hooks(apr_pool_t *p) { + APR_REGISTER_OPTIONAL_FN(ap_register_rewrite_mapfunc); + ap_hook_handler(handler_redirect, NULL, NULL, APR_HOOK_MIDDLE); - ap_hook_post_config(init_module, NULL, NULL, APR_HOOK_MIDDLE); + ap_hook_pre_config(pre_config, NULL, NULL, APR_HOOK_MIDDLE); + ap_hook_post_config(post_config, NULL, NULL, APR_HOOK_MIDDLE); ap_hook_child_init(init_child, NULL, NULL, APR_HOOK_MIDDLE); ap_hook_fixups(hook_fixup, NULL, NULL, APR_HOOK_FIRST); diff --git a/modules/mappers/mod_rewrite.h b/modules/mappers/mod_rewrite.h index e31bd80d68..f325dd8f0e 100644 --- a/modules/mappers/mod_rewrite.h +++ b/modules/mappers/mod_rewrite.h @@ -115,6 +115,7 @@ #if APR_HAS_THREADS #include "apr_thread_mutex.h" #endif +#include "apr_optional.h" #include "ap_config.h" /* Include from the Apache server ... */ @@ -384,10 +385,13 @@ static const char *cmd_rewriterule_setflag(apr_pool_t *p, rewriterule_entry *cfg char *key, char *val); /* initialisation */ -static int init_module(apr_pool_t *p, - apr_pool_t *plog, - apr_pool_t *ptemp, - server_rec *s); +static int pre_config(apr_pool_t *pconf, + apr_pool_t *plog, + apr_pool_t *ptemp); +static int post_config(apr_pool_t *pconf, + apr_pool_t *plog, + apr_pool_t *ptemp, + server_rec *s); static void init_child(apr_pool_t *p, server_rec *s); /* runtime hooks */ @@ -425,13 +429,17 @@ static char *lookup_map_dbmfile(request_rec *r, const char *file, char *key); #endif static char *lookup_map_program(request_rec *r, apr_file_t *fpin, apr_file_t *fpout, char *key); -static char *lookup_map_internal(request_rec *r, - char *(*func)(request_rec *r, char *key), - char *key); + +typedef char *(rewrite_mapfunc_t)(request_rec *r, char *key); +static void ap_register_rewrite_mapfunc(char *name, rewrite_mapfunc_t *func); +APR_DECLARE_OPTIONAL_FN(void, ap_register_rewrite_mapfunc, + (char *name, rewrite_mapfunc_t *func)); + static char *rewrite_mapfunc_toupper(request_rec *r, char *key); static char *rewrite_mapfunc_tolower(request_rec *r, char *key); static char *rewrite_mapfunc_escape(request_rec *r, char *key); static char *rewrite_mapfunc_unescape(request_rec *r, char *key); + static char *select_random_value_part(request_rec *r, char *value); static void rewrite_rand_init(void); static int rewrite_rand(int l, int h); -- 2.40.0