Handlungsüberblick Im vorherigen Artikel haben wir den Analyseprozess der Standortanweisung analysiert. Lassen Sie uns diesen Inhalt kurz überprüfen: Jeder Standort entspricht einer ngx_http_core_loc_conf_t-Struktur, und alle Standorte sind über eine bidirektionale Warteschlange miteinander verbunden. Die Datenstruktur ist relativ komplex. Die Listen-Direktive Als leistungsstarker HTTP-Server ist die Netzwerkverarbeitung der Kern von nginx. Wenn Sie die Netzwerkinitialisierung verstehen, können Sie Ihr Verständnis der Netzwerkverarbeitung von nginx vertiefen. Es gibt zwei wichtige netzwerkbezogene Konfigurationsbefehle: „listen“ und „server_name“. Der Listen-Befehl legt die Nginx-Abhöradresse fest. Beim IP-Protokoll ist diese Adresse Adresse und Port. Beim UNIX-Domain-Socket-Protokoll ist diese Adresse Pfad. Ein Listen-Befehl kann nur eine Adresse oder einen Port angeben. Die Adresse kann auch ein Hostname sein. Ausgehend von diesem Artikel analysieren wir den Analyseprozess der Listen-Direktive. Die Konfiguration der Listen-Direktive ist wie folgt: Aus dem Handbuch von nginx.org können wir die Verwendung von Listen entnehmen: Abhöradresse[:Port] [Standardserver] [setfib=Nummer] [Backlog=Nummer] [rcvbuf=Größe] [sndbuf=Größe] [accept_filter=Filter] [verschoben] [binden] [ipv6only=an|aus] [ssl] [so_keepalive=an|aus|[keepidle]:[keepintvl]:[keepcnt]]; Die von einer Listen-Anweisung übertragenen Parameter sind sehr komplex. Allerdings schenken wir diesen weniger häufig verwendeten Parametern im Allgemeinen wenig Beachtung. Im Folgenden sind einige gängige Konfigurationsmethoden aufgeführt: hören Sie 127.0.0.1:8000; Hören Sie 127.0.0.1, ohne den Port hinzuzufügen, der Standard-Abhörport ist 80; hören 8000 hören *:8000 listen localhost:8000 Analysieren Sie die URI und den Port in der Listen-Direktive Aus dem obigen Inhalt wissen wir, dass Listen mehrere Verwendungszwecke hat. Beim Parsen müssen wir die Portnummer und den URI-Teil der Listen-Direktive abrufen. Nginx bietet die Methode ngx_parse_url() zum Parsen von URI und Port. Diese Funktion wird beim Parsen der Listen-Direktive aufgerufen. ngx_int_t ngx_parse_url(ngx_pool_t *Pool, ngx_url_t *u) { u_char *p; Größe_t Länge; p = u->url.data; Länge = u->url.länge; // Hier ist das Protokoll zum Parsen der Unix-Domäne if (len >= 5 && ngx_strncasecmp(p, (u_char *) "unix:", 5) == 0) { gibt ngx_parse_unix_domain_url(Pool, u) zurück; } // IPV6-Protokoll analysieren if (len && p[0] == '[') { gibt ngx_parse_inet6_url(Pool, u) zurück; } // IPV4-Protokoll analysieren return ngx_parse_inet_url(pool, u); } Wir verwenden das IPV4-Protokoll, hier analysieren wir die Funktion ngx_parse_inet_url() // u.url = "80"; // u.listen = 1; // u.default_port = 80; statisches ngx_int_t ngx_parse_inet_url(ngx_pool_t *Pool, ngx_url_t *u) { u_char *p, *Host, *Port, *Letzter, *URI, *Argumente; Größe_t Länge; ngx_int_t n; Struktur sockaddr_in *sin; #wenn (NGX_HAVE_INET6) Struktur sockaddr_in6 *sin6; #endif u->socklen = sizeof(Struktur sockaddr_in); sin = (Struktur sockaddr_in *) &u->sockaddr; sin->sin_family = AF_INET; //IPV4-Typ u->family = AF_INET; Host = u->URL.Daten; // "80" last = host + u->url.len; // Die Position des letzten Zeichens des Hosts port = ngx_strlchr(host, last, ':'); // Port suchen, hier ist NULL uri = ngx_strlchr(host, last, '/'); // URI suchen, hier ist NULL args = ngx_strlchr(host, last, '?'); // Suche den Parameter args, der hier NULL ist wenn (Argumente) { wenn (uri == NULL || args < uri) { uri = Argumente; } } wenn (uri) { wenn (u->listen || !u->uri_part) { u->err = "ungültiger Host"; gib NGX_ERROR zurück; } u->uri.len = letzte - uri; u->uri.data = uri; letzte = uri; wenn (uri < port) { Port = NULL; } } wenn (Port) { Hafen++; Länge = letzter - Port; n = ngx_atoi(Port, Länge); wenn (n < 1 || n > 65535) { u->err = "ungültiger Port"; gib NGX_ERROR zurück; } u->port = (Eingangsport_t) n; sin->sin_port = htons((in_port_t) n); u->port_text.len = Länge; u->port_text.data = Port; letzte = Port - 1; } anders { wenn (uri == NULL) { wenn (u->listen) { /* Testwert nur als Port */ n = ngx_atoi(Host, letzter - Host); wenn (n != NGX_ERROR) { wenn (n < 1 || n > 65535) { u->err = "ungültiger Port"; gib NGX_ERROR zurück; } u->port = (Eingangsport_t) n; sin->sin_port = htons((in_port_t) n); u->port_text.len = letzter - Host; u->port_text.data = Host; u->Platzhalter = 1; gib NGX_OK zurück; } } } u->kein_port = 1; u->port = u->Standardport; sin->sin_port = htons(u->Standardport); } Länge = letzter - Host; wenn (Länge == 0) { u->err = "kein Host"; gib NGX_ERROR zurück; } u->host.len = Länge; u->host.data = Host; wenn (u->listen && len == 1 && *host == '*') { sin->sin_addr.s_addr = INADDR_ANY; u->Platzhalter = 1; gib NGX_OK zurück; } sin->sin_addr.s_addr = ngx_inet_addr(Host, Länge); wenn (sin->sin_addr.s_addr != INADDR_NONE) { wenn (sin->sin_addr.s_addr == INADDR_ANY) { u->Platzhalter = 1; } u->naddrs = 1; u->addrs = ngx_pcalloc(Pool, Größe von(ngx_addr_t)); wenn (u->addrs == NULL) { gib NGX_ERROR zurück; } sin = ngx_pcalloc(Pool, Größe von(Struktur sockaddr_in)); wenn (sin == NULL) { gib NGX_ERROR zurück; } ngx_memcpy(sin, &u->sockaddr, Größe von(Struktur sockaddr_in)); u->addrs[0].sockaddr = (Struktur sockaddr *) sin; u->addrs[0].socklen = sizeof(Struktur sockaddr_in); p = ngx_pnalloc(Pool, u->Host.Len + Sizeof(":65535") - 1); wenn (p == NULL) { gib NGX_ERROR zurück; } u->addrs[0].name.len = ngx_sprintf(p, "%V:%d", &u->Host, u->Port) – p; u->Adresse[0].name.data = p; gib NGX_OK zurück; } wenn (u->keine_Lösung) { gib NGX_OK zurück; } wenn (ngx_inet_resolve_host(pool, u) != NGX_OK) { gib NGX_ERROR zurück; } u->Familie = u->Adresse[0].sockaddr->sa_Familie; u->socklen = u->addrs[0].socklen; ngx_memcpy(&u->sockaddr, u->addrs[0].sockaddr, u->addrs[0].socklen); Schalter (u->Familie) { #wenn (NGX_HAVE_INET6) Fall AF_INET6: sin6 = (Struktur sockaddr_in6 *) &u->sockaddr; wenn (IN6_IS_ADDR_UNSPECIFIED(&sin6->sin6_addr)) { u->Platzhalter = 1; } brechen; #endif Standard: /* AF_INET */ sin = (Struktur sockaddr_in *) &u->sockaddr; wenn (sin->sin_addr.s_addr == INADDR_ANY) { u->Platzhalter = 1; } brechen; } gib NGX_OK zurück; } Diese Funktion analysiert die Adresse und Portnummer unseres Abhörgeräts. In unserer Konfigurationsdatei ist die Portnummer 80 und es ist keine Abhöradresse konfiguriert, daher ist u->wildcard = 1, was bedeutet, dass dies ein Platzhalter ist und wir diese Portnummer aller IP-Adressen des Servers abhören möchten. Analysieren der Listen-Direktive Werfen wir einen Blick auf die Listenkonfiguration aus dem Quellcode: { ngx_string("hören"), NGX_HTTP_SRV_CONF|NGX_CONF_1MEHR, ngx_http_core_listen, NGX_HTTP_SRV_CONF_OFFSET, 0, NULL } Aus der Konfigurationsdatei können wir erkennen, dass „listen“ nur im Servermodul erscheinen kann und mehrere Parameter haben kann. Die entsprechende Verarbeitungsfunktion ist ngx_http_core_listen. Lassen Sie uns diese Funktion analysieren. Wir haben einige Codes zur Fehlerbeurteilung gelöscht. statisches Zeichen * ngx_http_core_listen(ngx_conf_t *cf, ngx_command_t *cmd, void *conf) { ngx_http_core_srv_conf_t *cscf = conf; ngx_str_t *Wert, Größe; ngx_url_t u; ngx_uint_t n; ngx_http_listen_opt_t lsopt; cscf->listen = 1; Wert = cf->args->elts; ngx_memzero(&u, Größe von(ngx_url_t)); u.url = Wert[1]; u.listen = 1; u.Standardport = 80; wenn (ngx_parse_url(cf->pool, &u) != NGX_OK) { gib NGX_CONF_ERROR zurück; } ngx_memzero(&lsopt, Größe von(ngx_http_listen_opt_t)); ngx_memcpy(&lsopt.sockaddr.sockaddr, &u.sockaddr, u.socklen); lsopt.socklen = u.socklen; lsopt.backlog = NGX_LISTEN_BACKLOG; lsopt.rcvbuf = -1; lsopt.sndbuf = -1; #wenn (NGX_HAVE_SETFIB) lsopt.setfib = -1; #endif #wenn (NGX_HAVE_TCP_FASTOPEN) lsopt.fastopen = -1; #endif lsopt.wildcard = u.wildcard; #wenn (NGX_HAVE_INET6) lsopt.ipv6only = 1; #endif (leer) ngx_sock_ntop(&lsopt.sockaddr.sockaddr, lsopt.socklen, lsopt.addr, NGX_SOCKADDR_STRLEN, 1); für (n = 2; n < cf->args->nelts; n++) { wenn (ngx_strcmp(Wert[n].data, "Standardserver") == 0 || ngx_strcmp(Wert[n].data, "Standard") == 0) { lsopt.default_server = 1; weitermachen; } // Die anderen Codes hier dienen alle zur Verarbeitung verschiedener Parameter von listen, die für unsere Analyse hier nutzlos sind} wenn (ngx_http_add_listen(cf, cscf, &lsopt) == NGX_OK) { gib NGX_CONF_OK zurück; } gib NGX_CONF_ERROR zurück; } Der Gesamtprozess dieser Funktion besteht darin, die verschiedenen Parameter der Listenanweisung zu analysieren und ein ngx_http_listen_opt_t zu generieren. Wie der Name schon sagt, wird diese Struktur verwendet, um einige Listening-Port-Optionen (Listening-Port-Option) zu speichern. Hier wird eine Funktion ngx_parse_url() aufgerufen. Wir haben sie oben analysiert. Die Funktion dieser Funktion besteht darin, die Adresse und den Port in der URL zu analysieren. Dann kommt der wichtigste Teil. Die Funktion ngx_http_core_listen() ruft am Ende die Funktion ngx_http_add_listen() auf, die die Abhörportinformationen im dynamischen Port-Array der Struktur ngx_http_core_main_conf_t speichert. Funktion ngx_http_add_listen() // cf: Konfigurationsstruktur // cscf: Konfigurationsstruktur des Servers, auf dem sich die Listen-Direktive befindet // lsopt: Listen-Option, generiert durch ngx_http_core_listen() ngx_int_t ngx_http_add_listen(ngx_conf_t *cf, ngx_http_core_srv_conf_t *cscf, ngx_http_listen_opt_t *lsopt) { in_port_t p; ngx_uint_t ich; Struktur sockaddr *sa; ngx_http_conf_port_t *Port; ngx_http_core_main_conf_t *cmcf; // Holen Sie sich die main_conf-Struktur des Moduls ngx_http_core_module ngx_http_core_main_conf_t cmcf = ngx_http_conf_get_module_main_conf(cf, ngx_http_core_module); // Das Feld „Ports“ ist ein Array, wenn (cmcf->ports == NULL) { cmcf->ports = ngx_array_create(cf->temp_pool, 2, Größe von (ngx_http_conf_port_t)); wenn (cmcf->ports == NULL) { gib NGX_ERROR zurück; } } sa = &lsopt->sockaddr.sockaddr; p = ngx_inet_get_port(sa); Port = cmcf->Ports->elts; für (i = 0; i < cmcf->ports->nelts; i++) { wenn (p != port[i].port || sa->sa_family != port[i].family) { weitermachen; } /* ein Port ist bereits in der Portliste */ gibt ngx_http_add_addresses zurück (cf, cscf, &port[i], lsopt); } /* einen Port zur Portliste hinzufügen */ Port = ngx_array_push(cmcf->ports); wenn (Port == NULL) { gib NGX_ERROR zurück; } port->Familie = sa->sa_familie; Port->Port = p; port->adressen.elts = NULL; gibt ngx_http_add_address(cf, cscf, port, lsopt) zurück; } Diese Funktion speichert die Portnummerninformationen im Portfeld der Struktur ngx_http_core_main_conf_t. Zusammenfassen Das Obige ist der vollständige Inhalt dieses Artikels. Ich hoffe, dass der Inhalt dieses Artikels einen gewissen Lernwert für Ihr Studium oder Ihre Arbeit hat. Wenn Sie Fragen haben, können Sie eine Nachricht hinterlassen. Vielen Dank für Ihre Unterstützung von 123WORDPRESS.COM. Das könnte Sie auch interessieren:
|
<<: Mysql, einige komplexe SQL-Anweisungen (Abfragen und Löschen doppelter Zeilen)
>>: Ausführliche Erläuterung des globalen Status des WeChat-Applets
Ich möchte kürzlich einen Docker für Cron-geplant...
In diesem Artikelbeispiel wird der spezifische Co...
Docker-Version 1.13.1 Problemprozess Ein MySQL-Co...
<br />Vorheriger Artikel: Webdesign-Tutorial...
Inhaltsverzeichnis 1. MySQL herunterladen 1.1 Her...
MySQL-Fehler: Parameterindex außerhalb des gültig...
Als ersten Artikel dieser Studiennotiz beginnen w...
Ich habe mir kürzlich die Pressekonferenz von App...
Der spezifische Code lautet wie folgt: <!DOCTY...
Beim Kompilieren und Installieren von Nginx werde...
Cursor Die von der Auswahlabfrage zurückgegebenen...
Inhaltsverzeichnis Wirkung Beginnen Sie mit der T...
In einem Artikel vor langer Zeit habe ich über di...
Inhaltsverzeichnis Überblick 0. Grundlagen von Ja...
Inhaltsverzeichnis brauchen: Funktionspunkte Rend...