comparison src/http/ngx_http_core_module.c @ 322:56675f002600 NGINX_0_5_31

nginx 0.5.31 *) Feature: named locations. *) Feature: the "proxy_store" and "fastcgi_store" directives. *) Feature: the "proxy_store_access" and "fastcgi_store_access" directives.
author Igor Sysoev <http://sysoev.ru>
date Wed, 15 Aug 2007 00:00:00 +0400
parents 95d92ec39071
children 7cf404023f50
comparison
equal deleted inserted replaced
321:6762c33c7da8 322:56675f002600
931 static ngx_int_t 931 static ngx_int_t
932 ngx_http_core_find_location(ngx_http_request_t *r, 932 ngx_http_core_find_location(ngx_http_request_t *r,
933 ngx_array_t *locations, ngx_uint_t regex_start, size_t len) 933 ngx_array_t *locations, ngx_uint_t regex_start, size_t len)
934 { 934 {
935 ngx_int_t n, rc; 935 ngx_int_t n, rc;
936 ngx_uint_t i, found, noregex; 936 ngx_uint_t i, found;
937 ngx_http_core_loc_conf_t *clcf, **clcfp; 937 ngx_http_core_loc_conf_t *clcf, **clcfp;
938 #if (NGX_PCRE)
939 ngx_uint_t noregex;
940 #endif
938 941
939 ngx_log_debug1(NGX_LOG_DEBUG_HTTP, r->connection->log, 0, 942 ngx_log_debug1(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
940 "find location for \"%V\"", &r->uri); 943 "find location for \"%V\"", &r->uri);
941 944
942 found = 0; 945 found = 0;
946 #if (NGX_PCRE)
943 noregex = 0; 947 noregex = 0;
948 #endif
944 949
945 clcfp = locations->elts; 950 clcfp = locations->elts;
946 for (i = 0; i < locations->nelts; i++) { 951 for (i = 0; i < locations->nelts; i++) {
947 952
953 if (clcfp[i]->noname
948 #if (NGX_PCRE) 954 #if (NGX_PCRE)
949 if (clcfp[i]->regex) { 955 || clcfp[i]->regex
950 break;
951 }
952 #endif 956 #endif
953 957 || clcfp[i]->named)
954 if (clcfp[i]->noname) { 958 {
955 break; 959 break;
956 } 960 }
957 961
958 ngx_log_debug2(NGX_LOG_DEBUG_HTTP, r->connection->log, 0, 962 ngx_log_debug2(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
959 "find location: %s\"%V\"", 963 "find location: %s\"%V\"",
997 if (len > clcfp[i]->name.len) { 1001 if (len > clcfp[i]->name.len) {
998 /* the previous match is longer */ 1002 /* the previous match is longer */
999 break; 1003 break;
1000 } 1004 }
1001 1005
1006 found = 1;
1007
1002 r->loc_conf = clcfp[i]->loc_conf; 1008 r->loc_conf = clcfp[i]->loc_conf;
1009 #if (NGX_PCRE)
1003 noregex = clcfp[i]->noregex; 1010 noregex = clcfp[i]->noregex;
1004 found = 1; 1011 #endif
1005 } 1012 }
1006 } 1013 }
1007 1014
1008 if (found) { 1015 if (found) {
1009 clcf = ngx_http_get_module_loc_conf(r, ngx_http_core_module); 1016 clcf = ngx_http_get_module_loc_conf(r, ngx_http_core_module);
1026 1033
1027 /* regex matches */ 1034 /* regex matches */
1028 1035
1029 for (i = regex_start; i < locations->nelts; i++) { 1036 for (i = regex_start; i < locations->nelts; i++) {
1030 1037
1031 if (clcfp[i]->noname) { 1038 if (!clcfp[i]->regex) {
1032 break; 1039 break;
1033 } 1040 }
1034 1041
1035 ngx_log_debug1(NGX_LOG_DEBUG_HTTP, r->connection->log, 0, 1042 ngx_log_debug1(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
1036 "find location: ~ \"%V\"", &clcfp[i]->name); 1043 "find location: ~ \"%V\"", &clcfp[i]->name);
1511 1518
1512 return NGX_DONE; 1519 return NGX_DONE;
1513 } 1520 }
1514 1521
1515 1522
1523 ngx_int_t
1524 ngx_http_named_location(ngx_http_request_t *r, ngx_str_t *name)
1525 {
1526 ngx_uint_t i;
1527 ngx_http_core_srv_conf_t *cscf;
1528 ngx_http_core_loc_conf_t **clcfp;
1529 ngx_http_core_main_conf_t *cmcf;
1530
1531 cscf = ngx_http_get_module_srv_conf(r, ngx_http_core_module);
1532
1533 clcfp = cscf->locations.elts;
1534
1535 for (i = cscf->named_start; i < cscf->locations.nelts; i++) {
1536
1537 if (name->len != clcfp[i]->name.len
1538 || ngx_strncmp(name->data, clcfp[i]->name.data, name->len) != 0)
1539 {
1540 continue;
1541 }
1542
1543 ngx_log_debug3(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
1544 "named location: %V \"%V?%V\"", name, &r->uri, &r->args);
1545
1546 r->internal = 1;
1547
1548 r->loc_conf = clcfp[i]->loc_conf;
1549
1550 ngx_http_update_location_config(r);
1551
1552 cmcf = ngx_http_get_module_main_conf(r, ngx_http_core_module);
1553
1554 r->phase_handler = cmcf->phase_engine.location_rewrite_index;
1555 ngx_http_core_run_phases(r);
1556
1557 return NGX_DONE;
1558 }
1559
1560 ngx_log_error(NGX_LOG_ERR, r->connection->log, 0,
1561 "could not find name location \"%V\"", name);
1562
1563 ngx_http_finalize_request(r, NGX_HTTP_INTERNAL_SERVER_ERROR);
1564 return NGX_DONE;
1565 }
1566
1567
1516 ngx_http_cleanup_t * 1568 ngx_http_cleanup_t *
1517 ngx_http_cleanup_add(ngx_http_request_t *r, size_t size) 1569 ngx_http_cleanup_add(ngx_http_request_t *r, size_t size)
1518 { 1570 {
1519 ngx_http_cleanup_t *cln; 1571 ngx_http_cleanup_t *cln;
1520 1572
1555 ngx_uint_t i; 1607 ngx_uint_t i;
1556 ngx_conf_t pcf; 1608 ngx_conf_t pcf;
1557 ngx_http_module_t *module; 1609 ngx_http_module_t *module;
1558 ngx_http_conf_ctx_t *ctx, *http_ctx; 1610 ngx_http_conf_ctx_t *ctx, *http_ctx;
1559 ngx_http_core_srv_conf_t *cscf, **cscfp; 1611 ngx_http_core_srv_conf_t *cscf, **cscfp;
1612 ngx_http_core_loc_conf_t **clcfp;
1560 ngx_http_core_main_conf_t *cmcf; 1613 ngx_http_core_main_conf_t *cmcf;
1561 #if (NGX_PCRE)
1562 ngx_http_core_loc_conf_t **clcfp;
1563 #endif
1564 1614
1565 ctx = ngx_pcalloc(cf->pool, sizeof(ngx_http_conf_ctx_t)); 1615 ctx = ngx_pcalloc(cf->pool, sizeof(ngx_http_conf_ctx_t));
1566 if (ctx == NULL) { 1616 if (ctx == NULL) {
1567 return NGX_CONF_ERROR; 1617 return NGX_CONF_ERROR;
1568 } 1618 }
1642 } 1692 }
1643 1693
1644 ngx_sort(cscf->locations.elts, (size_t) cscf->locations.nelts, 1694 ngx_sort(cscf->locations.elts, (size_t) cscf->locations.nelts,
1645 sizeof(ngx_http_core_loc_conf_t *), ngx_http_core_cmp_locations); 1695 sizeof(ngx_http_core_loc_conf_t *), ngx_http_core_cmp_locations);
1646 1696
1697 clcfp = cscf->locations.elts;
1698
1647 #if (NGX_PCRE) 1699 #if (NGX_PCRE)
1648 1700
1649 cscf->regex_start = cscf->locations.nelts; 1701 cscf->regex_start = cscf->locations.nelts;
1650 clcfp = cscf->locations.elts;
1651 1702
1652 for (i = 0; i < cscf->locations.nelts; i++) { 1703 for (i = 0; i < cscf->locations.nelts; i++) {
1653 if (clcfp[i]->regex) { 1704 if (clcfp[i]->regex) {
1654 cscf->regex_start = i; 1705 cscf->regex_start = i;
1655 break; 1706 break;
1656 } 1707 }
1657 } 1708 }
1658 1709
1659 #endif 1710 #endif
1711
1712 cscf->named_start = cscf->locations.nelts;
1713
1714 for (i = 0; i < cscf->locations.nelts; i++) {
1715 if (clcfp[i]->named) {
1716 cscf->named_start = i;
1717 break;
1718 }
1719 }
1660 1720
1661 return rv; 1721 return rv;
1662 } 1722 }
1663 1723
1664 1724
1756 "invalid location modifier \"%V\"", &value[1]); 1816 "invalid location modifier \"%V\"", &value[1]);
1757 return NGX_CONF_ERROR; 1817 return NGX_CONF_ERROR;
1758 } 1818 }
1759 1819
1760 } else { 1820 } else {
1821
1761 clcf->name = value[1]; 1822 clcf->name = value[1];
1823
1824 if (value[1].data[0] == '@') {
1825 clcf->named = 1;
1826 }
1762 } 1827 }
1763 1828
1764 pclcf = pctx->loc_conf[ngx_http_core_module.ctx_index]; 1829 pclcf = pctx->loc_conf[ngx_http_core_module.ctx_index];
1765 1830
1766 if (pclcf->name.len == 0) { 1831 if (pclcf->name.len == 0) {
1778 1843
1779 if (pclcf->exact_match) { 1844 if (pclcf->exact_match) {
1780 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0, 1845 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0,
1781 "location \"%V\" could not be inside " 1846 "location \"%V\" could not be inside "
1782 "the exact location \"%V\"", 1847 "the exact location \"%V\"",
1848 &clcf->name, &pclcf->name);
1849 return NGX_CONF_ERROR;
1850 }
1851
1852 if (pclcf->named) {
1853 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0,
1854 "location \"%V\" could not be inside "
1855 "the named location \"%V\"",
1783 &clcf->name, &pclcf->name); 1856 &clcf->name, &pclcf->name);
1784 return NGX_CONF_ERROR; 1857 return NGX_CONF_ERROR;
1785 } 1858 }
1786 1859
1787 #if (NGX_PCRE) 1860 #if (NGX_PCRE)
1858 ngx_int_t rc; 1931 ngx_int_t rc;
1859 ngx_http_core_loc_conf_t *first, *second; 1932 ngx_http_core_loc_conf_t *first, *second;
1860 1933
1861 first = *(ngx_http_core_loc_conf_t **) one; 1934 first = *(ngx_http_core_loc_conf_t **) one;
1862 second = *(ngx_http_core_loc_conf_t **) two; 1935 second = *(ngx_http_core_loc_conf_t **) two;
1936
1937 if (first->named && !second->named) {
1938 /* shift named locations to the end */
1939 return 1;
1940 }
1941
1942 if (!first->named && second->named) {
1943 /* shift named locations to the end */
1944 return -1;
1945 }
1946
1947 if (first->named && second->named) {
1948 return ngx_strcmp(first->name.data, second->name.data);
1949 }
1863 1950
1864 if (first->noname && !second->noname) { 1951 if (first->noname && !second->noname) {
1865 /* shift no named locations to the end */ 1952 /* shift no named locations to the end */
1866 return 1; 1953 return 1;
1867 } 1954 }
2704 } 2791 }
2705 2792
2706 return NGX_CONF_ERROR; 2793 return NGX_CONF_ERROR;
2707 } 2794 }
2708 2795
2796 if (lcf->named && alias) {
2797 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0,
2798 "the \"alias\" directive may not be used "
2799 "inside named location");
2800
2801 return NGX_CONF_ERROR;
2802 }
2803
2709 #if (NGX_PCRE) 2804 #if (NGX_PCRE)
2710 2805
2711 if (lcf->regex && alias) { 2806 if (lcf->regex && alias) {
2712 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0, 2807 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0,
2713 "the \"alias\" directive may not be used " 2808 "the \"alias\" directive may not be used "