Annotation of parser3/src/targets/apache/mod_parser3.c, revision 1.5

1.1       moko        1: /** @file
1.2       moko        2:        Parser: apache 1.3 and 2.2 module
1.1       moko        3: 
1.2       moko        4:        Copyright (c) 2001-2010 ArtLebedev Group (http://www.artlebedev.com)
1.1       moko        5:        Author: Alexandr Petrosian <paf@design.ru> (http://paf.design.ru)
                      6: */
                      7: 
1.5     ! moko        8: static const char * const IDENT_MOD_PARSER3_C="$Date: 2010-11-14 22:49:57 $";
1.1       moko        9: 
                     10: #ifdef WIN32
                     11: #include <winsock2.h>
                     12: #endif
                     13: 
                     14: #include "httpd.h"
                     15: #include "http_config.h"
                     16: #include "http_core.h"
                     17: #include "http_log.h"
                     18: #include "http_main.h"
                     19: #include "http_protocol.h"
                     20: #include "util_script.h"
1.2       moko       21: 
                     22: #include "pa_httpd.h"
                     23: 
1.3       moko       24: #define PARSER3_HANDLER "parser3-handler"
                     25: 
1.2       moko       26: /*
                     27: * To Ease Compatibility
                     28: */
                     29: #ifdef STANDARD20_MODULE_STUFF
                     30: 
                     31: #include "apr_strings.h"
                     32: 
                     33: #define ap_pcalloc     apr_pcalloc
                     34: #define ap_pstrdup     apr_pstrdup
                     35: 
                     36: #define ap_table_get   apr_table_get
                     37: #define ap_table_elts  apr_table_elts
                     38: #define ap_table_addn  apr_table_addn
                     39: #define ap_table_do    apr_table_do
                     40: 
                     41: #else
                     42: 
1.1       moko       43: #include "ap_alloc.h"
                     44: 
1.2       moko       45: #define apr_pool_t pool
                     46: #define apr_table_t table
                     47: 
                     48: #define ap_add_version_component(p, v) ap_add_version_component(v) 
                     49: 
                     50: #endif /* STANDARD20_MODULE_STUFF */
1.1       moko       51: 
                     52: /*
                     53: * Declare ourselves so the configuration routines can find and know us.
                     54: * We'll fill it in at the end of the module.
                     55: */
1.2       moko       56: 
                     57: #ifdef STANDARD20_MODULE_STUFF
                     58: module AP_MODULE_DECLARE_DATA parser3_module;
                     59: #else
                     60: module MODULE_VAR_EXPORT parser3_module;
                     61: #endif
1.1       moko       62: 
                     63: /*
                     64: * Locate our directory configuration record for the current request.
                     65: */
                     66: static Parser_module_config *our_dconfig(request_rec *r) {
1.5     ! moko       67:        return (Parser_module_config *) ap_get_module_config(r->per_dir_config, &parser3_module);
1.1       moko       68: }
                     69: 
                     70: static const char* cmd_parser_config(cmd_parms *cmd, void *mconfig, char *file_spec) {
                     71:        Parser_module_config *cfg = (Parser_module_config *) mconfig;
                     72:        
                     73:        // remember assigned filespec into cfg
                     74:        cfg->parser_config_filespec=file_spec;
                     75:        
                     76:        return NULL;
                     77: }
1.2       moko       78: 
1.1       moko       79: static const char* cmd_parser_status_allowed(cmd_parms *cmd, void *mconfig, char *file_spec) {
                     80:        Parser_module_config *cfg = (Parser_module_config *) mconfig;
                     81:        
                     82:        cfg->parser_status_allowed=1;
                     83:        
                     84:        return NULL;
                     85: }
                     86: 
                     87: /* 
1.2       moko       88: * Now let's declare routines for each of the callback phase in order.
1.1       moko       89: */
                     90: 
1.3       moko       91: static int parser_handler(request_rec *r) {
                     92: 
                     93: //     ap_log_rerror(APLOG_MARK, APLOG_EMERG, 0, r, "handler, r->handler=%s", r->handler);
                     94: 
                     95: #ifdef STANDARD20_MODULE_STUFF
                     96:        if(strcmp(r->handler, PARSER3_HANDLER))
                     97:                return DECLINED;
                     98: #endif
                     99:        // converting to parser version
                    100:        pa_request_rec pr={
                    101:                r,
                    102:                r->pool,
                    103:                r->header_only,
                    104:                &r->status,
                    105:                r->method,
                    106:                r->headers_out,
                    107:                r->subprocess_env,
                    108:                &r->content_type,
                    109:                r->uri,
                    110:                r->filename,
                    111:                r->path_info,
                    112:                r->args,
                    113: #ifdef STANDARD20_MODULE_STUFF
                    114:                r->finfo.filetype == 0
                    115: #else          
                    116:                r->finfo.st_mode == 0
                    117: #endif
1.1       moko      118:        };
                    119: 
                    120:        // config
1.3       moko      121:        Parser_module_config *dcfg=our_dconfig(r);
                    122: 
                    123:        return pa_parser_handler(&pr, dcfg);
1.1       moko      124: }
                    125: 
                    126: /* 
1.4       moko      127: * This function is called during process initialisation.
1.1       moko      128: */
                    129: 
1.3       moko      130: #ifdef STANDARD20_MODULE_STUFF
                    131: static void parser_module_init(apr_pool_t *p, server_rec *s) {
                    132: #else
1.2       moko      133: static void parser_module_init(server_rec *s, apr_pool_t *p) {
                    134:        ap_add_version_component(p, pa_version());
1.1       moko      135: #endif 
1.3       moko      136:        ap_log_perror(APLOG_MARK, APLOG_EMERG, 0, p, "parser inited %d", getpid());
1.1       moko      137:        pa_setup_module_cells();
                    138: }
                    139: 
                    140: /* 
1.2       moko      141: * All our process-death routine does is add its trace to the log.
                    142: */
                    143: static void parser_module_done(server_rec *s, apr_pool_t *p) {
1.1       moko      144:        pa_destroy_module_cells();
                    145: }
                    146: 
                    147: /*
1.2       moko      148: * This function gets called to create a per-directory configuration record.
1.1       moko      149: */
1.2       moko      150: static void *parser_create_dir_config(apr_pool_t *p, char *dirspec) {
1.1       moko      151:        /*
1.2       moko      152:        * Allocate the space for our record from the apr_pool_t supplied.
1.1       moko      153:        */
1.5     ! moko      154:        Parser_module_config *cfg= (Parser_module_config *) ap_pcalloc(p, sizeof(Parser_module_config));
1.1       moko      155:        return (void *) cfg;
                    156: }
                    157: 
                    158: /*
1.2       moko      159: * This function gets called to merge two per-directory configuration records.
1.1       moko      160: *
1.2       moko      161: * 20011126 paf: noticed, that this is called even on virtual root merge with something "parent",
                    162: * while thought that that is part of merge_server...
1.1       moko      163: *
1.2       moko      164: */
                    165: static void *parser_merge_dir_config(apr_pool_t *p, void *parent_conf, void *newloc_conf) {
                    166:        Parser_module_config *merged_config = (Parser_module_config *) ap_pcalloc(p, sizeof(Parser_module_config));
1.1       moko      167:        Parser_module_config *pconf = (Parser_module_config *) parent_conf;
                    168:        Parser_module_config *nconf = (Parser_module_config *) newloc_conf;
                    169:        
                    170:        merged_config->parser_config_filespec = ap_pstrdup(p, nconf->parser_config_filespec?
                    171:                nconf->parser_config_filespec:pconf->parser_config_filespec);
1.5     ! moko      172:        merged_config->parser_status_allowed= pconf->parser_status_allowed || nconf->parser_status_allowed;
1.1       moko      173:        
                    174:        return (void *) merged_config;
                    175: }
                    176: 
                    177: /*
1.2       moko      178: * This function gets called to create a per-server configuration record.
1.1       moko      179: */
1.2       moko      180: static void *parser_create_server_config(apr_pool_t *p, server_rec *s) {
1.1       moko      181:        /*
                    182:        * As with the parser_create_dir_config() routine, we allocate and fill
                    183:        * in an empty record.
                    184:        */
1.5     ! moko      185:        Parser_module_config *cfg= (Parser_module_config *) ap_pcalloc(p, sizeof(Parser_module_config));
1.1       moko      186:        
                    187:        return (void *) cfg;
                    188: }
                    189: 
                    190: /*
1.2       moko      191: * This function gets called to merge two per-server configuration records.
1.1       moko      192: */
1.2       moko      193: static void *parser_merge_server_config(apr_pool_t *p, void *server1_conf, void *server2_conf)
1.1       moko      194: {
1.2       moko      195:        Parser_module_config *merged_config = (Parser_module_config *) ap_pcalloc(p, sizeof(Parser_module_config));
1.1       moko      196:        Parser_module_config *s1conf = (Parser_module_config *) server1_conf;
                    197:        Parser_module_config *s2conf = (Parser_module_config *) server2_conf;
                    198:        
                    199:        /*
                    200:        * Our inheritance rules are our own, and part of our module's semantics.
                    201:        * Basically, just note whence we came.
                    202:        */
                    203:        merged_config->parser_config_filespec = ap_pstrdup(p, s2conf->parser_config_filespec?
                    204:                s2conf->parser_config_filespec:s1conf->parser_config_filespec);
1.5     ! moko      205:        merged_config->parser_status_allowed= s1conf->parser_status_allowed || s2conf->parser_status_allowed;
1.1       moko      206:        
                    207:        return (void *) merged_config;
                    208: }
                    209: 
                    210: /* 
                    211: * List of directives specific to our module.
                    212: */
                    213: static const command_rec parser_cmds[] =
                    214: {
                    215:        {
1.5     ! moko      216:                "ParserConfig",                         /* directive name */
1.1       moko      217:                        (const char* (*)(void))((void *)cmd_parser_config), // config action routine
1.5     ! moko      218:                        (void*)0,                       /* argument to include in call */
        !           219:                        (int)(OR_OPTIONS),              /* where available */
        !           220:                        TAKE1,                          /* arguments */
        !           221:                        "Parser config filespec"        // directive description
1.1       moko      222:        },
                    223:        {
1.5     ! moko      224:                "ParserStatusAllowed",                  /* directive name */
1.1       moko      225:                        (const char* (*)(void))((void *)cmd_parser_status_allowed), // config action routine
1.5     ! moko      226:                        (void*)0,                       /* argument to include in call */
        !           227:                        (int)(ACCESS_CONF),             /* where available */
        !           228:                        NO_ARGS,                        /* arguments */
1.1       moko      229:                        "Parser status class can be used" // directive description
                    230:        },
                    231:        {NULL}
                    232: };
                    233: 
                    234: /*--------------------------------------------------------------------------*/
                    235: /* Now the list of content handlers available from this module.             */
                    236: /*--------------------------------------------------------------------------*/
1.2       moko      237: 
                    238: #ifndef STANDARD20_MODULE_STUFF
1.1       moko      239: static const handler_rec parser_handlers[] =
                    240: {
1.3       moko      241:        {PARSER3_HANDLER, parser_handler},
1.1       moko      242:        {NULL}
                    243: };
1.2       moko      244: #endif
1.1       moko      245: 
                    246: /*--------------------------------------------------------------------------*/
                    247: /* Finally, the list of callback routines and data structures that          */
                    248: /* provide the hooks into our module from the other parts of the server.    */
                    249: /*--------------------------------------------------------------------------*/
1.2       moko      250: 
                    251: #ifdef STANDARD20_MODULE_STUFF
                    252: 
1.1       moko      253: /* 
1.2       moko      254: * register hooks.
1.1       moko      255: */
1.2       moko      256: static void parser_register_hooks(apr_pool_t* pool)
                    257: {
1.3       moko      258: //     ap_add_version_component(pool, pa_version());
1.2       moko      259: //     ap_hook_post_config(parser_server_init, NULL, NULL, APR_HOOK_MIDDLE);
                    260:        ap_hook_handler(parser_handler, NULL, NULL, APR_HOOK_MIDDLE);
1.3       moko      261:        ap_hook_child_init(parser_module_init, NULL, NULL, APR_HOOK_MIDDLE);
1.2       moko      262: };
                    263: 
                    264: module AP_MODULE_DECLARE_DATA parser3_module =
                    265: {
                    266:        STANDARD20_MODULE_STUFF,
                    267: #else
1.1       moko      268: module MODULE_VAR_EXPORT parser3_module =
                    269: {
                    270:        STANDARD_MODULE_STUFF,
1.5     ! moko      271:        parser_module_init,             /* module initializer */
1.2       moko      272: #endif
1.5     ! moko      273:        parser_create_dir_config,       /* per-directory config creator */
        !           274:        parser_merge_dir_config,        /* dir config merger */
        !           275:        parser_create_server_config,    /* server config creator */
        !           276:        parser_merge_server_config,     /* server config merger */
        !           277:        parser_cmds,                    /* command apr_table_t */
1.2       moko      278: #ifdef STANDARD20_MODULE_STUFF
1.5     ! moko      279:        parser_register_hooks           /* register hooks */
1.2       moko      280: #else
1.5     ! moko      281:        parser_handlers,                /* [9] list of handlers */
        !           282:        0,                              /* [2] filename-to-URI translation */
        !           283:        0,                              /* [5] check/validate user_id */
        !           284:        0,                              /* [6] check user_id is valid *here* */
        !           285:        0,                              /* [4] check access by host address */
        !           286:        0,                              /* [7] MIME type checker/setter */
        !           287:        0,                              /* [8] fixups */
        !           288:        0,                              /* [10] logger */
        !           289:        0,                              /* [3] header parser */
        !           290:        0,                              /* process initializer */
        !           291:        parser_module_done              /* process exit/cleanup */
1.2       moko      292: #endif // STANDARD20_MODULE_STUFF
1.1       moko      293: };
                    294: 
                    295: #if defined(_MSC_VER)
                    296: #      define APACHE_WIN32_SRC "../../../../win32/apache13/src"
                    297: #      ifdef _DEBUG
                    298: #              pragma comment(lib, APACHE_WIN32_SRC "/CoreD/ApacheCore.lib")
                    299: #      else
                    300: #              pragma comment(lib, APACHE_WIN32_SRC "/CoreR/ApacheCore.lib")
                    301: #      endif
                    302: #endif
                    303: 
                    304: 
                    305: // interface to C++
                    306: 
1.4       moko      307: #define        PA_APLOG_EMERG          0       /* system is unusable */
                    308: #define        PA_APLOG_ALERT          1       /* action must be taken immediately */
                    309: #define        PA_APLOG_CRIT           2       /* critical conditions */
                    310: #define        PA_APLOG_ERR            3       /* error conditions */
1.1       moko      311: #define        PA_APLOG_WARNING        4       /* warning conditions */
1.4       moko      312: #define        PA_APLOG_NOTICE         5       /* normal but significant condition */
                    313: #define        PA_APLOG_INFO           6       /* informational */
                    314: #define        PA_APLOG_DEBUG          7       /* debug-level messages */
1.1       moko      315: 
                    316: #define        PA_APLOG_LEVELMASK      7       /* mask off the level value */
                    317: 
1.4       moko      318: #define PA_APLOG_NOERRNO       (PA_APLOG_LEVELMASK + 1)
1.1       moko      319: 
                    320: #define PA_APLOG_MARK  __FILE__,__LINE__
                    321: 
1.2       moko      322: void pa_ap_log_rerror(const char *file, int line, int level, const pa_request_rec *s, const char *fmt, ...) {
1.1       moko      323:        const char* str;
                    324:        va_list l;
                    325:        va_start(l, fmt); 
                    326:        str=va_arg(l, const char*);
                    327:        va_end(l); 
                    328: 
                    329:        ap_log_rerror(file, line, level,
1.2       moko      330: #ifdef STANDARD20_MODULE_STUFF
                    331:                                0,
                    332: #endif
1.1       moko      333:                      (request_rec*)s->real_request_rec, "%s", str);
                    334: }
                    335: 
                    336: 
1.2       moko      337: void pa_ap_log_error(const char *file, int line, int level, const pa_server_rec *s, const char *fmt, ...) {
1.1       moko      338:        const char* str;
                    339:        va_list l;
                    340:        va_start(l, fmt); 
                    341:        str=va_arg(l, const char*);
                    342:        va_end(l); 
                    343: 
                    344:        ap_log_error(file, line, level,
1.2       moko      345: #ifdef STANDARD20_MODULE_STUFF
                    346:                                0,
                    347: #endif
1.1       moko      348:                      (server_rec*)s, "%s", str);
                    349: }
                    350: 
                    351: // ap_alloc.h
                    352: 
                    353: const char* pa_ap_table_get(const pa_table *t, const char *name) {
1.2       moko      354:        return ap_table_get((const apr_table_t*)t, name);
1.1       moko      355: }
                    356: void pa_ap_table_addn(pa_table *t, const char *name, const char *val) {
1.2       moko      357:        ap_table_addn((apr_table_t*)t, name, val);
1.1       moko      358: }
                    359: 
                    360: int pa_ap_table_size(const pa_table *t) {
1.2       moko      361:        return ap_table_elts((const apr_table_t*)t)->nelts;
1.1       moko      362: }
                    363: 
1.2       moko      364: void pa_ap_table_do(int (*comp) (void *, const char *, const char *), void *rec, const pa_table *t, ...) {
                    365:        ap_table_do(comp, rec, (apr_table_t*)t, 0);
1.1       moko      366: }
                    367: 
                    368: char * pa_ap_pstrdup(pa_pool *p, const char *s) {
1.2       moko      369:        return ap_pstrdup((apr_pool_t*)p, s);
1.1       moko      370: }
                    371: 
                    372: // http_protocol.h
                    373: 
                    374: int pa_ap_setup_client_block(pa_request_rec *r, int read_policy) {
                    375:        return ap_setup_client_block((request_rec*)r->real_request_rec,
                    376:                read_policy);
                    377: }
                    378: int pa_ap_should_client_block(pa_request_rec *r) {
                    379:        return ap_should_client_block((request_rec*)r->real_request_rec);
                    380: }
                    381: long pa_ap_get_client_block(pa_request_rec *r, char *buffer, int bufsiz) {
                    382:        return ap_get_client_block((request_rec*)r->real_request_rec,
                    383:                buffer, bufsiz);
                    384: }
                    385: void pa_ap_send_http_header(pa_request_rec *r) {
1.2       moko      386: // Apache2 send headers before body automatically
                    387: #ifndef STANDARD20_MODULE_STUFF
1.1       moko      388:        ap_send_http_header((request_rec*)r->real_request_rec);
1.2       moko      389: #endif
1.1       moko      390: }
                    391: int pa_ap_rwrite(const void *buf, int nbyte, pa_request_rec *r) {
                    392:        return ap_rwrite(buf, nbyte, (request_rec*)r->real_request_rec);
                    393: }
                    394: 
                    395: // http_main.h
                    396: 
                    397: void pa_ap_hard_timeout(char *s, pa_request_rec *r) {
1.2       moko      398: // Apache 2 uses non-blocking I/O
                    399: #ifndef STANDARD20_MODULE_STUFF
1.1       moko      400:        ap_hard_timeout(s, (request_rec*)r->real_request_rec);
1.2       moko      401: #endif
1.1       moko      402: }
                    403: void pa_ap_reset_timeout(pa_request_rec *r) {
1.2       moko      404: #ifndef STANDARD20_MODULE_STUFF
1.1       moko      405:        ap_reset_timeout((request_rec*)r->real_request_rec);
1.2       moko      406: #endif
1.1       moko      407: }
                    408: void pa_ap_kill_timeout(pa_request_rec *r) {
1.2       moko      409: #ifndef STANDARD20_MODULE_STUFF
1.1       moko      410:        ap_kill_timeout((request_rec*)r->real_request_rec);
1.2       moko      411: #endif
1.1       moko      412: }
                    413: 
                    414: // util_script.h
                    415: 
                    416: void pa_ap_add_cgi_vars(pa_request_rec *r) {
                    417:        ap_add_cgi_vars((request_rec*)r->real_request_rec);
                    418: }
                    419: void pa_ap_add_common_vars(pa_request_rec *r) {
                    420:        ap_add_common_vars((request_rec*)r->real_request_rec);
                    421: }
                    422: 
1.2       moko      423: #ifndef WIN32
1.1       moko      424: // signal.h
                    425: 
                    426: void (*pa_signal (int sig, void (*disp)(int)))(int) {
                    427:        if(sig==PA_SIGPIPE && disp==PA_SIG_IGN)
                    428:                return signal(SIGPIPE, SIG_IGN);
                    429: 
                    430:        return 0;
                    431: }
1.5     ! moko      432: #endif

E-mail: