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

📄 util.c

📁 Apache HTTP Server 是一个功能强大的灵活的与HTTP/1.1相兼容的web服务器.这里给出的是Apache HTTP服务器的源码。
💻 C
📖 第 1 页 / 共 4 页
字号:
/* * copy at most n leading directories of s into d * d should be at least as large as s plus 1 extra byte * assumes n > 0 * the return value is the ever useful pointer to the trailing \0 of d * * MODIFIED FOR HAVE_DRIVE_LETTERS and NETWARE environments,  * so that if n == 0, "/" is returned in d with n == 1  * and s == "e:/test.html", "e:/" is returned in d * *** See also directory_walk in modules/http/http_request.c * examples: *    /a/b, 0  ==> /  (true for all platforms) *    /a/b, 1  ==> / *    /a/b, 2  ==> /a/ *    /a/b, 3  ==> /a/b/ *    /a/b, 4  ==> /a/b/ * *    c:/a/b 0 ==> / *    c:/a/b 1 ==> c:/ *    c:/a/b 2 ==> c:/a/ *    c:/a/b 3 ==> c:/a/b *    c:/a/b 4 ==> c:/a/b */AP_DECLARE(char *) ap_make_dirstr_prefix(char *d, const char *s, int n){    if (n < 1) {        *d = '/';        *++d = '\0';        return (d);    }    for (;;) {        if (*s == '\0' || (*s == '/' && (--n) == 0)) {            *d = '/';            break;        }        *d++ = *s++;    }    *++d = 0;    return (d);}/* * return the parent directory name including trailing / of the file s */AP_DECLARE(char *) ap_make_dirstr_parent(apr_pool_t *p, const char *s){    const char *last_slash = ap_strrchr_c(s, '/');    char *d;    int l;    if (last_slash == NULL) {        return apr_pstrdup(p, "");    }    l = (last_slash - s) + 1;    d = apr_palloc(p, l + 1);    memcpy(d, s, l);    d[l] = 0;    return (d);}AP_DECLARE(int) ap_count_dirs(const char *path){    register int x, n;    for (x = 0, n = 0; path[x]; x++)        if (path[x] == '/')            n++;    return n;}AP_DECLARE(char *) ap_getword_nc(apr_pool_t *atrans, char **line, char stop){    return ap_getword(atrans, (const char **) line, stop);}AP_DECLARE(char *) ap_getword(apr_pool_t *atrans, const char **line, char stop){    const char *pos = *line;    int len;    char *res;    while ((*pos != stop) && *pos) {        ++pos;    }    len = pos - *line;    res = (char *)apr_palloc(atrans, len + 1);    memcpy(res, *line, len);    res[len] = 0;    if (stop) {        while (*pos == stop) {            ++pos;        }    }    *line = pos;    return res;}AP_DECLARE(char *) ap_getword_white_nc(apr_pool_t *atrans, char **line){    return ap_getword_white(atrans, (const char **) line);}AP_DECLARE(char *) ap_getword_white(apr_pool_t *atrans, const char **line){    const char *pos = *line;    int len;    char *res;    while (!apr_isspace(*pos) && *pos) {        ++pos;    }    len = pos - *line;    res = (char *)apr_palloc(atrans, len + 1);    memcpy(res, *line, len);    res[len] = 0;    while (apr_isspace(*pos)) {        ++pos;    }    *line = pos;    return res;}AP_DECLARE(char *) ap_getword_nulls_nc(apr_pool_t *atrans, char **line,                                       char stop){    return ap_getword_nulls(atrans, (const char **) line, stop);}AP_DECLARE(char *) ap_getword_nulls(apr_pool_t *atrans, const char **line,                                    char stop){    const char *pos = ap_strchr_c(*line, stop);    char *res;    if (!pos) {        res = apr_pstrdup(atrans, *line);        *line += strlen(*line);        return res;    }    res = apr_pstrndup(atrans, *line, pos - *line);    ++pos;    *line = pos;    return res;}/* Get a word, (new) config-file style --- quoted strings and backslashes * all honored */static char *substring_conf(apr_pool_t *p, const char *start, int len,                            char quote){    char *result = apr_palloc(p, len + 2);    char *resp = result;    int i;    for (i = 0; i < len; ++i) {        if (start[i] == '\\' && (start[i + 1] == '\\'                                 || (quote && start[i + 1] == quote)))            *resp++ = start[++i];        else            *resp++ = start[i];    }    *resp++ = '\0';#if RESOLVE_ENV_PER_TOKEN    return (char *)ap_resolve_env(p,result);#else    return result;#endif}AP_DECLARE(char *) ap_getword_conf_nc(apr_pool_t *p, char **line){    return ap_getword_conf(p, (const char **) line);}AP_DECLARE(char *) ap_getword_conf(apr_pool_t *p, const char **line){    const char *str = *line, *strend;    char *res;    char quote;    while (*str && apr_isspace(*str))        ++str;    if (!*str) {        *line = str;        return "";    }    if ((quote = *str) == '"' || quote == '\'') {        strend = str + 1;        while (*strend && *strend != quote) {            if (*strend == '\\' && strend[1] && strend[1] == quote)                strend += 2;            else                ++strend;        }        res = substring_conf(p, str + 1, strend - str - 1, quote);        if (*strend == quote)            ++strend;    }    else {        strend = str;        while (*strend && !apr_isspace(*strend))            ++strend;        res = substring_conf(p, str, strend - str, 0);    }    while (*strend && apr_isspace(*strend))        ++strend;    *line = strend;    return res;}/* Check a string for any ${ENV} environment variable * construct and replace each them by the value of * that environment variable, if it exists. If the * environment value does not exist, leave the ${ENV} * construct alone; it means something else. */AP_DECLARE(const char *) ap_resolve_env(apr_pool_t *p, const char * word){# define SMALL_EXPANSION 5    struct sll {        struct sll *next;        const char *string;        apr_size_t len;    } *result, *current, sresult[SMALL_EXPANSION];    char *res_buf, *cp;    const char *s, *e, *ep;    unsigned spc;    apr_size_t outlen;    s = ap_strchr_c(word, '$');    if (!s) {        return word;    }    /* well, actually something to do */    ep = word + strlen(word);    spc = 0;    result = current = &(sresult[spc++]);    current->next = NULL;    current->string = word;    current->len = s - word;    outlen = current->len;    do {        /* prepare next entry */        if (current->len) {            current->next = (spc < SMALL_EXPANSION)                            ? &(sresult[spc++])                            : (struct sll *)apr_palloc(p,                                                       sizeof(*current->next));            current = current->next;            current->next = NULL;            current->len = 0;        }        if (*s == '$') {            if (s[1] == '{' && (e = ap_strchr_c(s, '}'))) {                word = getenv(apr_pstrndup(p, s+2, e-s-2));                if (word) {                    current->string = word;                    current->len = strlen(word);                    outlen += current->len;                }                else {                    current->string = s;                    current->len = e - s + 1;                    outlen += current->len;                }                s = e + 1;            }            else {                current->string = s++;                current->len = 1;                ++outlen;            }        }        else {            word = s;            s = ap_strchr_c(s, '$');            current->string = word;            current->len = s ? s - word : ep - word;            outlen += current->len;        }    } while (s && *s);    /* assemble result */    res_buf = cp = apr_palloc(p, outlen + 1);    do {        if (result->len) {            memcpy(cp, result->string, result->len);            cp += result->len;        }        result = result->next;    } while (result);    res_buf[outlen] = '\0';    return res_buf;}AP_DECLARE(int) ap_cfg_closefile(ap_configfile_t *cfp){#ifdef DEBUG    ap_log_error(APLOG_MARK, APLOG_DEBUG, 0, NULL,         "Done with config file %s", cfp->name);#endif    return (cfp->close == NULL) ? 0 : cfp->close(cfp->param);}static apr_status_t cfg_close(void *param){    apr_file_t *cfp = (apr_file_t *) param;    return (apr_file_close(cfp));}static int cfg_getch(void *param){    char ch;    apr_file_t *cfp = (apr_file_t *) param;    if (apr_file_getc(&ch, cfp) == APR_SUCCESS)        return ch;    return (int)EOF;}static void *cfg_getstr(void *buf, size_t bufsiz, void *param){    apr_file_t *cfp = (apr_file_t *) param;    apr_status_t rv;    rv = apr_file_gets(buf, bufsiz, cfp);    if (rv == APR_SUCCESS || (APR_STATUS_IS_EOF(rv) && strcmp(buf, "")))        return buf;    return NULL;}/* Open a ap_configfile_t as FILE, return open ap_configfile_t struct pointer */AP_DECLARE(apr_status_t) ap_pcfg_openfile(ap_configfile_t **ret_cfg,                                          apr_pool_t *p, const char *name){    ap_configfile_t *new_cfg;    apr_file_t *file = NULL;    apr_finfo_t finfo;    apr_status_t status;#ifdef DEBUG    char buf[120];#endif    if (name == NULL) {        ap_log_error(APLOG_MARK, APLOG_ERR, 0, NULL,               "Internal error: pcfg_openfile() called with NULL filename");        return APR_EBADF;    }    status = apr_file_open(&file, name, APR_READ | APR_BUFFERED,                           APR_OS_DEFAULT, p);#ifdef DEBUG    ap_log_error(APLOG_MARK, APLOG_DEBUG, 0, NULL,                "Opening config file %s (%s)",                name, (status != APR_SUCCESS) ?                 apr_strerror(status, buf, sizeof(buf)) : "successful");#endif    if (status != APR_SUCCESS)        return status;    status = apr_file_info_get(&finfo, APR_FINFO_TYPE, file);    if (status != APR_SUCCESS)        return status;    if (finfo.filetype != APR_REG &&#if defined(WIN32) || defined(OS2) || defined(NETWARE)        strcasecmp(apr_filename_of_pathname(name), "nul") != 0) {#else        strcmp(name, "/dev/null") != 0) {#endif /* WIN32 || OS2 */        ap_log_error(APLOG_MARK, APLOG_ERR, 0, NULL,                     "Access to file %s denied by server: not a regular file",                     name);        apr_file_close(file);        return APR_EBADF;    }#ifdef WIN32    /* Some twisted character [no pun intended] at MS decided that a     * zero width joiner as the lead wide character would be ideal for     * describing Unicode text files.  This was further convoluted to     * another MSism that the same character mapped into utf-8, EF BB BF     * would signify utf-8 text files.     *     * Since MS configuration files are all protecting utf-8 encoded     * Unicode path, file and resource names, we already have the correct      * WinNT encoding.  But at least eat the stupid three bytes up front.     */    {        unsigned char buf[4];        apr_size_t len = 3;        status = apr_file_read(file, buf, &len);        if ((status != APR_SUCCESS) || (len < 3)               || memcmp(buf, "\xEF\xBB\xBF", 3) != 0) {            apr_off_t zero = 0;            apr_file_seek(file, APR_SET, &zero);        }    }#endif    new_cfg = apr_palloc(p, sizeof(*new_cfg));    new_cfg->param = file;    new_cfg->name = apr_pstrdup(p, name);    new_cfg->getch = (int (*)(void *)) cfg_getch;    new_cfg->getstr = (void *(*)(void *, size_t, void *)) cfg_getstr;    new_cfg->close = (int (*)(void *)) cfg_close;    new_cfg->line_number = 0;    *ret_cfg = new_cfg;    return APR_SUCCESS;}/* Allocate a ap_configfile_t handle with user defined functions and params */AP_DECLARE(ap_configfile_t *) ap_pcfg_open_custom(apr_pool_t *p,                       const char *descr,                       void *param,                       int(*getch)(void *param),                       void *(*getstr) (void *buf, size_t bufsiz, void *param),                       int(*close_func)(void *param)){    ap_configfile_t *new_cfg = apr_palloc(p, sizeof(*new_cfg));#ifdef DEBUG    ap_log_error(APLOG_MARK, APLOG_DEBUG, 0, NULL,                 "Opening config handler %s", descr);#endif    new_cfg->param = param;    new_cfg->name = descr;    new_cfg->getch = getch;    new_cfg->getstr = getstr;    new_cfg->close = close_func;    new_cfg->line_number = 0;    return new_cfg;}   /* Read one character from a configfile_t */AP_DECLARE(int) ap_cfg_getc(ap_configfile_t *cfp){    register int ch = cfp->getch(cfp->param);    if (ch == LF)         ++cfp->line_number;    return ch;}  /* Read one line from open ap_configfile_t, strip LF, increase line number *//* If custom handler does not define a getstr() function, read char by char */AP_DECLARE(int) ap_cfg_getline(char *buf, size_t bufsize, ap_configfile_t *cfp){    /* If a "get string" function is defined, use it */    if (cfp->getstr != NULL) {        char *src, *dst;        char *cp;        char *cbuf = buf;        size_t cbufsize = bufsize;        while (1) {            ++cfp->line_number;            if (cfp->getstr(cbuf, cbufsize, cfp->param) == NULL)                return 1;            /*             *  check for line continuation,             *  i.e. match [^\\]\\[\r]\n only             */            cp = cbuf;            while (cp < cbuf+cbufsize && *cp != '\0')                cp++;            if (cp > cbuf && cp[-1] == LF) {                cp--;                if (cp > cbuf && cp[-1] == CR)                    cp--;                if (cp > cbuf && cp[-1] == '\\') {                    cp--;                    if (!(cp > cbuf && cp[-1] == '\\')) {                        /*                         * line continuation requested -                         * then remove backslash and continue                         */                        cbufsize -= (cp-cbuf);                        cbuf = cp;                        continue;                    }                    else {                        /*                          * no real continuation because escaped -                         * then just remove escape character                         */                        for ( ; cp < cbuf+cbufsize && *cp != '\0'; cp++)                            cp[0] = cp[1];                    }                   }            }            break;        }        /*         * Leading and trailing white space is eliminated completely         */        src = buf;        while (apr_isspace(*src))            ++src;        /* blast trailing whitespace */        dst = &src[strlen(src)];        while (--dst >= src && apr_isspace(*dst))            *dst = '\0';        /* Zap leading whitespace by shifting */        if (src != buf)            for (dst = buf; (*dst++ = *src++) != '\0'; )                ;#ifdef DEBUG_CFG_LINES        ap_log_error(APLOG_MARK, APLOG_DEBUG, 0, NULL, "Read config: %s", buf);#endif        return 0;    } else {        /* No "get string" function defined; read character by character */

⌨️ 快捷键说明

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