Locate nginx request server and location Configuration

Source: Internet
Author: User
First, let's look at a figure:

It is the nginx listen port configuration to form a structure diagram. Please note the following points:


1. Each port has a ngx_http_port_t structure. The ngx_http_conf_addr_t structure is stored in the addrs variable in the same port configuration.


2. not all the same ports need to create ngx_http_conf_addr_t. If the listen ADDR: port configuration is the same as the previous port configuration, this structure is not created, only put the server conf of the port, that is, cscf, into the servers array in the ngx_http_conf_addr_t structure. If the ADDR part is different, a new ngx_http_conf_addr_t is created.


After all the configurations are parsed, ngx_http_optimize_servers will perform some sorting and optimization work. The most important thing is to prepare for enabling port listening later.

For each port, ngx_http_init_listening is called:

Static Export (ngx_conf_t * Cf, expose * port) {ngx_uint_t I, last, bind_wildcard; ngx_listening_t * ls; ngx_http_port_t * hport; Export * ADDR; ADDR = port-> addrs. ELTs; last = port-> addrs. nelts; // the configuration of the same port, that is, ngx_http_conf_addr_t will be used for sorting. The following annotations introduce the configuration of // listen. For details, refer to the official wiki: http: nginx.org/httpcoremodulepoliclisten/** if there is a binding to an "*: P Ort "then we need to bind () to * The" *: Port "only and ignore other implicit bindings. the bindings * have been already sorted: explicit bindings are on the start, then * Implicit bindings go, and wildcard binding is in the end. * /// check that the configuration of this port contains an IF (ADDR [last-1]) with wildcard configuration. OPT. wildcard) {// only set the last wildcard to bind, so that the previous wildcard does not have the BIND tag // For BIND, the typical situation (sorted) is: binded, nobind, wildcard (nobind), wildcard (Binde D) ADDR [last-1]. OPT. bind = 1; bind_wildcard = 1;} else {bind_wildcard = 0;} I = 0; while (I <last) {// except for configuration with wildcard, there is also a configuration that explicitly specifies the need for bind, and the need to handle this configuration // when it is clearly indicated that the BIND is required, refer to the function ngx_http_core_listen if (bind_wildcard &&! ADDR [I]. OPT. BIND) {I ++; continue;} // port to be listened to. assign a ngx_listening_t structure ls = ngx_http_add_listening (CF, & ADDR [I]); if (LS = NULL) {return ngx_error;} hport = ngx_pcalloc (CF-> pool, sizeof (ngx_http_port_t); If (hport = NULL) {return ngx_error ;} ls-> servers = hport; if (I = last-1) {// This is the end of processing, when last> 1 indicates that the nobind and // wildcard types exist in the configuration, that is, the port is regarded as multiple addresses. For more information about how to handle this situation, see ngx_http_init_reques. T hport-> naddrs = last;} else {// The current port explicitly requires bind, the meaning of naddrs 1 is that the port is explicitly bind to an address hport-> naddrs = 1; // The following ADDR ++ will continue processing from the next port, that is, compared with ADDR, the bottom of the array is naturally from 0 I = 0;} switch (LS-> sockaddr-> sa_family) {default: /* af_inet */If (ngx_http_add_addrs (CF, hport, ADDR )! = Ngx_ OK) {return ngx_error;} break;} // once a port marked as bind is processed, ADDR starts from the next one; // The number of ports from the next ADDR to the end last --;} return ngx_ OK ;}

Then let's look at the ngx_http_init_request function: 
  
If (Port-> naddrs> 1) {// naddrs> 1 has been analyzed before, and the address to be used is processed by ngx_connection_local_sockaddr. /** There are several addresses on this port and one of them * is an "*: Port" wildcard so getsockname () in ngx_http_server_addr () * is required to determine a server address * // This function actually calls getsockname to obtain the Server IP address of the connection if (ngx_connection_local_sockaddr (C, null, 0 )! = Ngx_ OK) {ngx_http_close_connection (c); return;} switch (c-> local_sockaddr-> sa_family) {default:/* af_inet */sin = (struct sockaddr_in *) c-> local_sockaddr; ADDR = port-> addrs;/* the last address is "*" * // if it is a configuration other than binded on the port, if the IP address has the same IP address, use its configuration. Otherwise, use the final configuration for (I = 0; I <port-> naddrs-1; I ++) {If (ADDR [I]. ADDR = sin-> sin_addr.s_addr) {break ;}} addr_conf = & ADDR [I]. conf; break ;}} Else {// naddrs = 1 switch (c-> local_sockaddr-> sa_family) {default:/* af_inet */ADDR = port-> addrs; addr_conf = & ADDR [0]. conf; break ;}/// the main role of the above operation is to obtain cscf, that is, the core server Conf, ngx_http_core_srv_conf_t structure. // For default_server, in ngx_http_add_address processing, the first added port sets default_server // as the current cscf of the port, and in ngx_http_add_addresses, it targets the same ADDR: port, modify the // default_server point. For details, refer to this function. Cscf = addr_conf-> default_server; // get cscf. The rest is easy to say. In this way, the configuration of the request sent to this port is obtained, R-> main_conf = cscf-> CTX-> main_conf; r-> srv_conf = cscf-> CTX-> srv_conf; r-> loc_conf = cscf-> CTX-> loc_conf;

 
When processing requests, the configuration of related modules is usually obtained through some macros:
# Define ngx_http_get_module_main_conf (R, module) (R)-> main_conf [module. ctx_index]
# Define ngx_http_get_module_srv_conf (R, module) (R)-> srv_conf [module. ctx_index]
# Define ngx_http_get_module_loc_conf (R, module) (R)-> loc_conf [module. ctx_index]
It should be noted that the configuration obtained here is HTTP core, especially for location configuration, different modules may have their own needs, so the emergence of ngx_http_find_config_phase in the HTTP processing phase occurs, the main function of this phase is to find the corresponding location configuration in static_locations and regex_locations in the core location configuration based on the specific URL. For more information, see ngx_http_core_find_location. Before reading this, you need to understand nginx
Location. The common location, generally non-regular, is placed in the Three-tree managed by static_locations, and the regular configuration is placed in the regex_locations linked list. After these concepts are clarified, the logic of the function is very simple.

  • Previous Article: nginx HTTP processing process analysis details
  • Next article: nginx keepalive connection recovery mechanism
  • Contact Us

    The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

    If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

    A Free Trial That Lets You Build Big!

    Start building with 50+ products and up to 12 months usage for Elastic Compute Service

    • Sales Support

      1 on 1 presale consultation

    • After-Sales Support

      24/7 Technical Support 6 Free Tickets per Quarter Faster Response

    • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.