⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 mod_example.c

📁 Apache HTTP Server 是一个功能强大的灵活的与HTTP/1.1相兼容的web服务器.这里给出的是Apache HTTP服务器的源码。
💻 C
📖 第 1 页 / 共 4 页
字号:
    const char *sofar;    char *addon;    char *where;    apr_pool_t *p;    const char *trace_copy;    /*     * Make sure our pools and tables are set up - we need 'em.     */    setup_module_cells();    /*     * Now, if we're in request-context, we use the request pool.     */    if (r != NULL) {        p = r->pool;        if ((trace_copy = apr_table_get(r->notes, TRACE_NOTE)) == NULL) {            trace_copy = "";        }    }    else {        /*         * We're not in request context, so the trace gets attached to our         * module-wide pool.  We do the create/destroy every time we're called         * in non-request context; this avoids leaking memory in some of         * the subsequent calls that allocate memory only once (such as the         * key formation below).         *         * Make a new sub-pool and copy any existing trace to it.  Point the         * trace cell at the copied value.         */        apr_pool_create(&p, x_pool);        if (trace != NULL) {            trace = apr_pstrdup(p, trace);        }        /*         * Now, if we have a sub-pool from before, nuke it and replace with         * the one we just allocated.         */        if (x_subpool != NULL) {            apr_pool_destroy(x_subpool);        }        x_subpool = p;        trace_copy = trace;    }    /*     * If we weren't passed a configuration record, we can't figure out to     * what location this call applies.  This only happens for co-routines     * that don't operate in a particular directory or server context.  If we     * got a valid record, extract the location (directory or server) to which     * it applies.     */    where = (mconfig != NULL) ? mconfig->loc : "nowhere";    where = (where != NULL) ? where : "";    /*     * Now, if we're not in request context, see if we've been called with     * this particular combination before.  The apr_table_t is allocated in the     * module's private pool, which doesn't get destroyed.     */    if (r == NULL) {        char *key;        key = apr_pstrcat(p, note, ":", where, NULL);        if (apr_table_get(static_calls_made, key) != NULL) {            /*             * Been here, done this.             */            return;        }        else {            /*             * First time for this combination of routine and environment -             * log it so we don't do it again.             */            apr_table_set(static_calls_made, key, "been here");        }    }    addon = apr_pstrcat(p,                        "   <li>\n"                        "    <dl>\n"                        "     <dt><samp>", note, "</samp></dt>\n"                        "     <dd><samp>[", where, "]</samp></dd>\n"                        "    </dl>\n"                        "   </li>\n",                        NULL);    sofar = (trace_copy == NULL) ? "" : trace_copy;    trace_copy = apr_pstrcat(p, sofar, addon, NULL);    if (r != NULL) {        apr_table_set(r->notes, TRACE_NOTE, trace_copy);    }    else {        trace = trace_copy;    }    /*     * You *could* change the following if you wanted to see the calling     * sequence reported in the server's error_log, but beware - almost all of     * these co-routines are called for every single request, and the impact     * on the size (and readability) of the error_log is considerable.     */#define EXAMPLE_LOG_EACH 0    if (EXAMPLE_LOG_EACH && (s != NULL)) {        ap_log_error(APLOG_MARK, APLOG_DEBUG, 0, s, "mod_example: %s", note);    }}/*--------------------------------------------------------------------------*//* We prototyped the various syntax for command handlers (routines that     *//* are called when the configuration parser detects a directive declared    *//* by our module) earlier.  Now we actually declare a "real" routine that   *//* will be invoked by the parser when our "real" directive is               *//* encountered.                                                             *//*                                                                          *//* If a command handler encounters a problem processing the directive, it   *//* signals this fact by returning a non-NULL pointer to a string            *//* describing the problem.                                                  *//*                                                                          *//* The magic return value DECLINE_CMD is used to deal with directives       *//* that might be declared by multiple modules.  If the command handler      *//* returns NULL, the directive was processed; if it returns DECLINE_CMD,    *//* the next module (if any) that declares the directive is given a chance   *//* at it.  If it returns any other value, it's treated as the text of an    *//* error message.                                                           *//*--------------------------------------------------------------------------*//*  * Command handler for the NO_ARGS "Example" directive.  All we do is mark the * call in the trace log, and flag the applicability of the directive to the * current location in that location's configuration record. */static const char *cmd_example(cmd_parms *cmd, void *mconfig){    x_cfg *cfg = (x_cfg *) mconfig;    /*     * "Example Wuz Here"     */    cfg->local = 1;    trace_add(cmd->server, NULL, cfg, "cmd_example()");    return NULL;}/*--------------------------------------------------------------------------*//*                                                                          *//* Now we declare our content handlers, which are invoked when the server   *//* encounters a document which our module is supposed to have a chance to   *//* see.  (See mod_mime's SetHandler and AddHandler directives, and the      *//* mod_info and mod_status examples, for more details.)                     *//*                                                                          *//* Since content handlers are dumping data directly into the connection     *//* (using the r*() routines, such as rputs() and rprintf()) without         *//* intervention by other parts of the server, they need to make             *//* sure any accumulated HTTP headers are sent first.  This is done by       *//* calling send_http_header().  Otherwise, no header will be sent at all,   *//* and the output sent to the client will actually be HTTP-uncompliant.     *//*--------------------------------------------------------------------------*//*  * Sample content handler.  All this does is display the call list that has * been built up so far. * * The return value instructs the caller concerning what happened and what to * do next: *  OK ("we did our thing") *  DECLINED ("this isn't something with which we want to get involved") *  HTTP_mumble ("an error status should be reported") */static int x_handler(request_rec *r){    x_cfg *dcfg;    if (strcmp(r->handler, "example-handler")) {        return DECLINED;    }    dcfg = our_dconfig(r);    trace_add(r->server, r, dcfg, "x_handler()");    /*     * We're about to start sending content, so we need to force the HTTP     * headers to be sent at this point.  Otherwise, no headers will be sent     * at all.  We can set any we like first, of course.  **NOTE** Here's     * where you set the "Content-type" header, and you do so by putting it in     * r->content_type, *not* r->headers_out("Content-type").  If you don't     * set it, it will be filled in with the server's default type (typically     * "text/plain").  You *must* also ensure that r->content_type is lower     * case.     *     * We also need to start a timer so the server can know if the connexion     * is broken.     */    ap_set_content_type(r, "text/html");    /*     * If we're only supposed to send header information (HEAD request), we're     * already there.     */    if (r->header_only) {        return OK;    }    /*     * Now send our actual output.  Since we tagged this as being     * "text/html", we need to embed any HTML.     */    ap_rputs(DOCTYPE_HTML_3_2, r);    ap_rputs("<HTML>\n", r);    ap_rputs(" <HEAD>\n", r);    ap_rputs("  <TITLE>mod_example Module Content-Handler Output\n", r);    ap_rputs("  </TITLE>\n", r);    ap_rputs(" </HEAD>\n", r);    ap_rputs(" <BODY>\n", r);    ap_rputs("  <H1><SAMP>mod_example</SAMP> Module Content-Handler Output\n", r);    ap_rputs("  </H1>\n", r);    ap_rputs("  <P>\n", r);    ap_rprintf(r, "  Apache HTTP Server version: \"%s\"\n",	    ap_get_server_version());    ap_rputs("  <BR>\n", r);    ap_rprintf(r, "  Server built: \"%s\"\n", ap_get_server_built());    ap_rputs("  </P>\n", r);;    ap_rputs("  <P>\n", r);    ap_rputs("  The format for the callback trace is:\n", r);    ap_rputs("  </P>\n", r);    ap_rputs("  <DL>\n", r);    ap_rputs("   <DT><EM>n</EM>.<SAMP>&lt;routine-name&gt;", r);    ap_rputs("(&lt;routine-data&gt;)</SAMP>\n", r);    ap_rputs("   </DT>\n", r);    ap_rputs("   <DD><SAMP>[&lt;applies-to&gt;]</SAMP>\n", r);    ap_rputs("   </DD>\n", r);    ap_rputs("  </DL>\n", r);    ap_rputs("  <P>\n", r);    ap_rputs("  The <SAMP>&lt;routine-data&gt;</SAMP> is supplied by\n", r);    ap_rputs("  the routine when it requests the trace,\n", r);    ap_rputs("  and the <SAMP>&lt;applies-to&gt;</SAMP> is extracted\n", r);    ap_rputs("  from the configuration record at the time of the trace.\n", r);    ap_rputs("  <STRONG>SVR()</STRONG> indicates a server environment\n", r);    ap_rputs("  (blank means the main or default server, otherwise it's\n", r);    ap_rputs("  the name of the VirtualHost); <STRONG>DIR()</STRONG>\n", r);    ap_rputs("  indicates a location in the URL or filesystem\n", r);    ap_rputs("  namespace.\n", r);    ap_rputs("  </P>\n", r);    ap_rprintf(r, "  <H2>Static callbacks so far:</H2>\n  <OL>\n%s  </OL>\n",            trace);    ap_rputs("  <H2>Request-specific callbacks so far:</H2>\n", r);    ap_rprintf(r, "  <OL>\n%s  </OL>\n", apr_table_get(r->notes, TRACE_NOTE));    ap_rputs("  <H2>Environment for <EM>this</EM> call:</H2>\n", r);    ap_rputs("  <UL>\n", r);    ap_rprintf(r, "   <LI>Applies-to: <SAMP>%s</SAMP>\n   </LI>\n", dcfg->loc);    ap_rprintf(r, "   <LI>\"Example\" directive declared here: %s\n   </LI>\n",            (dcfg->local ? "YES" : "NO"));    ap_rprintf(r, "   <LI>\"Example\" inherited: %s\n   </LI>\n",            (dcfg->congenital ? "YES" : "NO"));    ap_rputs("  </UL>\n", r);    ap_rputs(" </BODY>\n", r);    ap_rputs("</HTML>\n", r);    /*     * We're all done, so cancel the timeout we set.  Since this is probably     * the end of the request we *could* assume this would be done during     * post-processing - but it's possible that another handler might be     * called and inherit our outstanding timer.  Not good; to each its own.     */    /*     * We did what we wanted to do, so tell the rest of the server we     * succeeded.     */    return OK;}/*--------------------------------------------------------------------------*//*                                                                          *//* Now let's declare routines for each of the callback phase in order.      *//* (That's the order in which they're listed in the callback list, *not     *//* the order in which the server calls them!  See the command_rec           *//* declaration near the bottom of this file.)  Note that these may be       *//* called for situations that don't relate primarily to our function - in   *//* other words, the fixup handler shouldn't assume that the request has     *//* to do with "example" stuff.                                              *//*                                                                          *//* With the exception of the content handler, all of our routines will be   *//* called for each request, unless an earlier handler from another module   *//* aborted the sequence.                                                    *//*                                                                          *//* Handlers that are declared as "int" can return the following:            *//*                                                                          *//*  OK          Handler accepted the request and did its thing with it.     *//*  DECLINED    Handler took no action.                                     *//*  HTTP_mumble Handler looked at request and found it wanting.             *//*                                                                          *//* What the server does after calling a module handler depends upon the     *//* handler's return value.  In all cases, if the handler returns            *//* DECLINED, the server will continue to the next module with an handler    *//* for the current phase.  However, if the handler return a non-OK,         *//* non-DECLINED status, the server aborts the request right there.  If      *//* the handler returns OK, the server's next action is phase-specific;      *//* see the individual handler comments below for details.                   *//*                                                                          *//*--------------------------------------------------------------------------*//*  * This function is called during server initialisation.  Any information * that needs to be recorded must be in static cells, since there's no * configuration record. * * There is no return value. *//*  * This function is called when an heavy-weight process (such as a child) is * being run down or destroyed.  As with the child initialisation function, * any information that needs to be recorded must be in static cells, since * there's no configuration record. * * There is no return value. *//*  * This function is called during server initialisation when an heavy-weight * process (such as a child) is being initialised.  As with the * module initialisation function, any information that needs to be recorded * must be in static cells, since there's no configuration record. * * There is no return value. *//* * This function gets called to create a per-directory configuration * record.  This will be called for the "default" server environment, and for * each directory for which the parser finds any of our directives applicable. * If a directory doesn't have any of our directives involved (i.e., they * aren't in the .htaccess file, or a <Location>, <Directory>, or related * block), this routine will *not* be called - the configuration for the * closest ancestor is used. * * The return value is a pointer to the created module-specific * structure. */

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -