View | Details | Raw Unified | Return to bug 65419
Collapse All | Expand All

(-)modules/proxy/proxy_util.c (-24 / +75 lines)
Lines 19-24 Link Here
19
#include "ap_mpm.h"
19
#include "ap_mpm.h"
20
#include "scoreboard.h"
20
#include "scoreboard.h"
21
#include "apr_version.h"
21
#include "apr_version.h"
22
#include "apr_strings.h"
22
#include "apr_hash.h"
23
#include "apr_hash.h"
23
#include "proxy_util.h"
24
#include "proxy_util.h"
24
#include "ajp.h"
25
#include "ajp.h"
Lines 1820-1836 PROXY_DECLARE(proxy_worker *) ap_proxy_get_worker( Link Here
1820
 * shared. This allows for dynamic addition during
1821
 * shared. This allows for dynamic addition during
1821
 * config and runtime.
1822
 * config and runtime.
1822
 */
1823
 */
1823
PROXY_DECLARE(char *) ap_proxy_define_worker(apr_pool_t *p,
1824
static char *proxy_define_worker(apr_pool_t *p,
1824
                                             proxy_worker **worker,
1825
                                 proxy_worker **worker,
1825
                                             proxy_balancer *balancer,
1826
                                 proxy_balancer *balancer,
1826
                                             proxy_server_conf *conf,
1827
                                 proxy_server_conf *conf, const char *url,
1827
                                             const char *url,
1828
                                 int do_malloc, int matchable)
1828
                                             int do_malloc)
1829
{
1829
{
1830
    int rv;
1830
    apr_status_t rv;
1831
    apr_uri_t uri, urisock;
1832
    proxy_worker_shared *wshared;
1831
    proxy_worker_shared *wshared;
1833
    char *ptr, *sockpath = NULL;
1832
    const char *ptr = NULL, *sockpath = NULL, *pdollars = NULL;
1833
    apr_uri_t uri;
1834
1834
1835
    /*
1835
    /*
1836
     * Look to see if we are using UDS:
1836
     * Look to see if we are using UDS:
Lines 1837-1856 PROXY_DECLARE(proxy_worker *) ap_proxy_get_worker( Link Here
1837
     * require format: unix:/path/foo/bar.sock|http://ignored/path2/
1837
     * require format: unix:/path/foo/bar.sock|http://ignored/path2/
1838
     * This results in talking http to the socket at /path/foo/bar.sock
1838
     * This results in talking http to the socket at /path/foo/bar.sock
1839
     */
1839
     */
1840
    ptr = ap_strchr((char *)url, '|');
1840
    if (!ap_cstr_casecmp(url, "unix:") && (ptr = ap_strchr_c(url + 5, '|'))) {
1841
    if (ptr) {
1841
        rv = apr_uri_parse(p, apr_pstrmemdup(p, url, ptr - url), &uri);
1842
        *ptr = '\0';
1842
        if (rv == APR_SUCCESS) {
1843
        rv = apr_uri_parse(p, url, &urisock);
1843
            sockpath = ap_runtime_dir_relative(p, uri.path);;
1844
        if (rv == APR_SUCCESS && !ap_cstr_casecmp(urisock.scheme, "unix")) {
1844
            ptr++;    /* so we get the scheme for the uds */
1845
            sockpath = ap_runtime_dir_relative(p, urisock.path);;
1846
            url = ptr+1;    /* so we get the scheme for the uds */
1847
        }
1845
        }
1848
        else {
1846
        else {
1849
            *ptr = '|';
1847
            ptr = url;
1850
        }
1848
        }
1851
    }
1849
    }
1852
    rv = apr_uri_parse(p, url, &uri);
1850
    else {
1851
        ptr = url;
1852
    }
1853
1853
1854
    if (matchable) {
1855
        /* apr_uri_parse() will accept the '$' sign anywhere in the URL but
1856
         * in the :port part, and we don't want scheme://host:port$1$2/path
1857
         * to fail (e.g. "ProxyPassMatch ^/(a|b)(/.*)? http://host:port$2").
1858
         * So we trim all the $n from the :port and prepend them in uri.path
1859
         * afterward for apr_uri_unparse() to restore the original URL below.
1860
         */
1861
#define IS_REF(x) (x[0] == '$' && apr_isdigit(x[1]))
1862
        const char *pos = ap_strstr_c(ptr, "://");
1863
        if (pos) {
1864
            pos += 3;
1865
            while (*pos && *pos != ':' && *pos != '/') {
1866
                pos++;
1867
            }
1868
            if (*pos == ':') {
1869
                pos++;
1870
                while (*pos && !IS_REF(pos) && *pos != '/') {
1871
                    pos++;
1872
                }
1873
                if (IS_REF(pos)) {
1874
                    struct iovec vec[2];
1875
                    const char *path = pos + 2;
1876
                    while (*path && *path != '/') {
1877
                        path++;
1878
                    }
1879
                    pdollars = apr_pstrmemdup(p, pos, path - pos);
1880
                    vec[0].iov_base = (void *)ptr;
1881
                    vec[0].iov_len = pos - ptr;
1882
                    vec[1].iov_base = (void *)path;
1883
                    vec[1].iov_len = strlen(path);
1884
                    ptr = apr_pstrcatv(p, vec, 2, NULL);
1885
                }
1886
            }
1887
        }
1888
#undef IS_REF
1889
    }
1890
1891
    rv = apr_uri_parse(p, ptr, &uri);
1854
    if (rv != APR_SUCCESS) {
1892
    if (rv != APR_SUCCESS) {
1855
        return apr_pstrcat(p, "Unable to parse URL: ", url, NULL);
1893
        return apr_pstrcat(p, "Unable to parse URL: ", url, NULL);
1856
    }
1894
    }
Lines 1870-1875 PROXY_DECLARE(proxy_worker *) ap_proxy_get_worker( Link Here
1870
        ap_str_tolower(uri.hostname);
1908
        ap_str_tolower(uri.hostname);
1871
    }
1909
    }
1872
    ap_str_tolower(uri.scheme);
1910
    ap_str_tolower(uri.scheme);
1911
1912
    /* Restore/prepend pdollars (if any). */
1913
    if (pdollars) {
1914
        uri.path = apr_pstrcat(p, pdollars, uri.path, NULL);
1915
    }
1916
1873
    /*
1917
    /*
1874
     * Workers can be associated w/ balancers or on their
1918
     * Workers can be associated w/ balancers or on their
1875
     * own; ie: the generic reverse-proxy or a worker
1919
     * own; ie: the generic reverse-proxy or a worker
Lines 1910-1915 PROXY_DECLARE(proxy_worker *) ap_proxy_get_worker( Link Here
1910
        uri.port = 0;
1954
        uri.port = 0;
1911
    }
1955
    }
1912
    ptr = apr_uri_unparse(p, &uri, APR_URI_UNP_REVEALPASSWORD);
1956
    ptr = apr_uri_unparse(p, &uri, APR_URI_UNP_REVEALPASSWORD);
1957
1913
    if (PROXY_STRNCPY(wshared->name, ptr) != APR_SUCCESS) {
1958
    if (PROXY_STRNCPY(wshared->name, ptr) != APR_SUCCESS) {
1914
        ap_log_error(APLOG_MARK, APLOG_ERR, 0, ap_server_conf, APLOGNO(02808)
1959
        ap_log_error(APLOG_MARK, APLOG_ERR, 0, ap_server_conf, APLOGNO(02808)
1915
        "Alert! worker name (%s) too long; truncated to: %s", ptr, wshared->name);
1960
        "Alert! worker name (%s) too long; truncated to: %s", ptr, wshared->name);
Lines 1960-1965 PROXY_DECLARE(proxy_worker *) ap_proxy_get_worker( Link Here
1960
    return NULL;
2005
    return NULL;
1961
}
2006
}
1962
2007
2008
PROXY_DECLARE(char *) ap_proxy_define_worker(apr_pool_t *p,
2009
                                             proxy_worker **worker,
2010
                                             proxy_balancer *balancer,
2011
                                             proxy_server_conf *conf,
2012
                                             const char *url,
2013
                                             int do_malloc)
2014
{
2015
    return proxy_define_worker(p, worker, balancer, conf, url, do_malloc, 0);
2016
}
2017
1963
PROXY_DECLARE(char *) ap_proxy_define_match_worker(apr_pool_t *p,
2018
PROXY_DECLARE(char *) ap_proxy_define_match_worker(apr_pool_t *p,
1964
                                             proxy_worker **worker,
2019
                                             proxy_worker **worker,
1965
                                             proxy_balancer *balancer,
2020
                                             proxy_balancer *balancer,
Lines 1968-1985 PROXY_DECLARE(char *) ap_proxy_define_match_worker Link Here
1968
                                             int do_malloc)
2023
                                             int do_malloc)
1969
{
2024
{
1970
    char *err;
2025
    char *err;
1971
    const char *pdollar = ap_strchr_c(url, '$');
1972
2026
1973
    if (pdollar != NULL) {
2027
    err = proxy_define_worker(p, worker, balancer, conf, url, do_malloc, 1);
1974
        url = apr_pstrmemdup(p, url, pdollar - url);
1975
    }
1976
    err = ap_proxy_define_worker(p, worker, balancer, conf, url, do_malloc);
1977
    if (err) {
2028
    if (err) {
1978
        return err;
2029
        return err;
1979
    }
2030
    }
1980
2031
1981
    (*worker)->s->is_name_matchable = 1;
2032
    (*worker)->s->is_name_matchable = 1;
1982
    if (pdollar) {
2033
    if (ap_strchr_c(url, '$')) {
1983
        /* Before ap_proxy_define_match_worker() existed, a regex worker
2034
        /* Before ap_proxy_define_match_worker() existed, a regex worker
1984
         * with dollar substitution was never matched against the actual
2035
         * with dollar substitution was never matched against the actual
1985
         * URL thus the request fell through the generic worker. To avoid
2036
         * URL thus the request fell through the generic worker. To avoid

Return to bug 65419