欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

nginx之從main函數(shù)開(kāi)始了解配置文件處理及配置信息的讀入過(guò)程

 更新時(shí)間:2025年07月02日 09:15:05   作者:dai1396734  
這篇文章主要介紹了nginx之從main函數(shù)開(kāi)始了解配置文件處理及配置信息的讀入過(guò)程,具有很好的參考價(jià)值,希望對(duì)大家有所幫助,如有錯(cuò)誤或未考慮完全的地方,望不吝賜教

nginx配置文件相關(guān)的參數(shù)保存在以下幾個(gè)成員中,從main函數(shù)(nginx.c中)開(kāi)始,一步一步查看ngx_cycle_s 中與配置相關(guān)的成員是如何賦值的:

struct ngx_cycle_s {
    void                  ****conf_ctx;
	...
    ngx_str_t                 conf_file;
    ngx_str_t                 conf_param;
    ngx_str_t                 conf_prefix;
    ngx_str_t                 prefix;
	...
};

一:ngx_process_options 函數(shù),忽略其他不相干部分

static ngx_int_t
ngx_process_options(ngx_cycle_t *cycle)
{
    u_char  *p;
    size_t   len;

    if (ngx_prefix) {
    	//如果執(zhí)行命令時(shí)指定路徑,就會(huì)進(jìn)入這個(gè)條件,所以省略了
		//例如 ./nginx -p /home/dmj
       ....
    } else {
		...
		//NGX_CONF_PREFIX  = "/conf"
        ngx_str_set(&cycle->conf_prefix, NGX_CONF_PREFIX);
        //NGX_PREFIX = "usr/local/nginx"
        ngx_str_set(&cycle->prefix, NGX_PREFIX);
    }
	
    if (ngx_conf_file) {
        cycle->conf_file.len = ngx_strlen(ngx_conf_file);
        cycle->conf_file.data = ngx_conf_file;
    } else {
    	//NGX_CONF_PATH= "conf/nginx.conf"
        ngx_str_set(&cycle->conf_file, NGX_CONF_PATH);
    }
	 //合并前綴路徑與文件名得到此時(shí)cycle->conf_file = "/usr/local/nginx//conf/nginx.conf"
    if (ngx_conf_full_name(cycle, &cycle->conf_file, 0) != NGX_OK) {
        return NGX_ERROR;
    }
	//cycle->conf_prefix 指向 cycle->conf_file 也為"/usr/local/nginx//conf/nginx.conf"
	//但是該指針長(zhǎng)度只取了前綴路徑部分"/usr/local/nginx//conf/"
    for (p = cycle->conf_file.data + cycle->conf_file.len - 1;
         p > cycle->conf_file.data;
         p--)
    {
        if (ngx_path_separator(*p)) {
            cycle->conf_prefix.len = p - cycle->conf_file.data + 1;
            cycle->conf_prefix.data = cycle->conf_file.data;
            break;
        }
    }

	....
    return NGX_OK;
}

經(jīng)過(guò)上訴代碼,至此將ngx_cycle_s 中配置文件路徑相關(guān)的成員賦值了,此時(shí)conf_param及 conf_ctx未賦值

struct ngx_cycle_s {
    void                  ****conf_ctx;
	...
    ngx_str_t                 conf_file;	//“usr/local/nginx//conf/nginx.conf”
    ngx_str_t                 conf_param;	
    ngx_str_t                 conf_prefix;	//“usr/local/nginx//conf/
    ngx_str_t                 prefix;		//"usr/local/nginx"
	...
};

二:先不管conf_param,著重看下conf_ctx成員

他是一個(gè)4級(jí)指針,里面包含了所有配置文件的配置信息,也就是說(shuō)nginx.conf 文件中的內(nèi)容,經(jīng)過(guò)解析后都會(huì)保存到conf_ctx 指針

2.1 ngx_preinit_modules函數(shù)

功能如下:

  • 給ngx_modules 中的模塊的 name , index賦值
  • 同時(shí)統(tǒng)計(jì)模塊總數(shù) 靜態(tài)全局 ngx_modules數(shù)組大小+NGX_MAX_DYNAMIC_MODULES(定義為128)

ngx_modules大小與conf_ctx指向的數(shù)組大小一致,后面會(huì)有提到,因此先簡(jiǎn)單說(shuō)明下其初始化的時(shí)候

ngx_int_t
ngx_preinit_modules(void)
{
    ngx_uint_t  i;

    for (i = 0; ngx_modules[i]; i++) {
        ngx_modules[i]->index = i;
        ngx_modules[i]->name = ngx_module_names[i];
    }

    ngx_modules_n = i;
    ngx_max_module = ngx_modules_n + NGX_MAX_DYNAMIC_MODULES;

    return NGX_OK;
}

2.2 ngx_init_cycle函數(shù)

在這里做了很多初始化的操作,函數(shù)太長(zhǎng),這里只截取函數(shù)內(nèi)與配置相關(guān)的代碼

2.2.1 conf_ctx 分配內(nèi)存,大小與模塊個(gè)數(shù)相同的,ngx_max_module 就是模塊的總數(shù)(靜態(tài) 數(shù)組 + 動(dòng)態(tài)大小128)

   cycle->conf_ctx = ngx_pcalloc(pool, ngx_max_module * sizeof(void *));
    if (cycle->conf_ctx == NULL) {
        ngx_destroy_pool(pool);
        return NULL;
    }

2.2.2 將靜態(tài)數(shù)組ngx_modules 拷貝進(jìn)cycle->modules,此時(shí)還有動(dòng)態(tài)的128個(gè)沒(méi)有模塊數(shù)據(jù)

ngx_int_t
ngx_cycle_modules(ngx_cycle_t *cycle)
{
    /*
     * create a list of modules to be used for this cycle,
     * copy static modules to it
     */

    cycle->modules = ngx_pcalloc(cycle->pool, (ngx_max_module + 1)
                                              * sizeof(ngx_module_t *));
    if (cycle->modules == NULL) {
        return NGX_ERROR;
    }

    ngx_memcpy(cycle->modules, ngx_modules,
               ngx_modules_n * sizeof(ngx_module_t *));

    cycle->modules_n = ngx_modules_n;

    return NGX_OK;
}

2.2.3 調(diào)用create_conf 函數(shù)為核心模塊創(chuàng)建配置結(jié)構(gòu)體,那非核心模塊呢?

 for (i = 0; cycle->modules[i]; i++) {
 		//非核心模塊,查找下一個(gè)模塊
        if (cycle->modules[i]->type != NGX_CORE_MODULE) {
            continue;
        }

        module = cycle->modules[i]->ctx;

        if (module->create_conf) {
            rv = module->create_conf(cycle);//創(chuàng)建一個(gè)默認(rèn)值的ngx_core_conf_t
            if (rv == NULL) {
                ngx_destroy_pool(pool);
                return NULL;
            }
            cycle->conf_ctx[cycle->modules[i]->index] = rv;//將配置結(jié)構(gòu)體放入配置項(xiàng)列表
        }
    }

下表為nginx定義模塊類(lèi)型為NGX_CORE_MODULE的模塊,此時(shí)因?yàn)閏ycle->modules只有靜態(tài)數(shù)組中的模塊,而下面表格所列只有ngx_core_module和ngx_regex_module在靜態(tài)數(shù)組中,因此

核心模塊創(chuàng)建配置結(jié)構(gòu)體接口實(shí)現(xiàn)配置結(jié)構(gòu)體類(lèi)型
ngx_core_modulengx_core_module_create_confngx_core_conf_t
ngx_errlog_module無(wú)無(wú)
ngx_regex_modulengx_regex_create_confngx_regex_conf_t
ngx_openssl_modulengx_openssl_create_confngx_openssl_conf_t
ngx_events_module無(wú)無(wú)
ngx_http_module無(wú)無(wú)
ngx_mail_module無(wú)無(wú)
ngx_google_perftools_modulengx_google_perftools_create_confngx_google_perftools_conf_t
ngx_stream_module無(wú)無(wú)

此時(shí)內(nèi)存大概是這樣分布,其余的都還只是指針,未指向特定結(jié)構(gòu)體

在這里插入圖片描述

2.2.4 調(diào)用ngx_conf_parse函數(shù),解析配置文件

    conf.ctx = cycle->conf_ctx; //配置結(jié)構(gòu)體列表
    conf.cycle = cycle;
    conf.pool = pool;
    conf.log = log;
    conf.module_type = NGX_CORE_MODULE;
    conf.cmd_type = NGX_MAIN_CONF;
    
if (ngx_conf_parse(&conf, &cycle->conf_file) != NGX_CONF_OK) {
        environ = senv;
        ngx_destroy_cycle_pools(&conf);
        return NULL;
    }

三:這個(gè)函數(shù)很重要,單獨(dú)拎出來(lái)說(shuō)明

ngx_conf_parse全部?jī)?nèi)容就不貼了,貼幾個(gè)關(guān)鍵代碼:

char *
ngx_conf_parse(ngx_conf_t *cf, ngx_str_t *filename)
{
    
    ....
	//打開(kāi)文件,并將文件信息放入cf
    if (filename) {

        /* open configuration file */
        fd = ngx_open_file(filename->data, NGX_FILE_RDONLY, NGX_FILE_OPEN, 0);
        ...
        cf->conf_file->file.fd = fd;
        cf->conf_file->file.name.len = filename->len;
        cf->conf_file->file.name.data = filename->data;
        cf->conf_file->file.offset = 0;
        cf->conf_file->file.log = cf->log;
        cf->conf_file->line = 1;

        type = parse_file;
	...
	//循環(huán)讀取文件內(nèi)容
    for ( ;; ) {

        /******************************************
        1.讀取文件內(nèi)容,每次讀取一個(gè)buf大小(4K),如果文件內(nèi)容不足4K則全部讀取到buf中.
        2.掃描buf中的內(nèi)容,每次掃描一個(gè)token就會(huì)存入cf->args中,然后返回.
        3.返回后調(diào)用ngx_conf_parse函數(shù)會(huì)調(diào)用*cf->handler和ngx_conf_handler(cf, rc)函數(shù)處理.
        3.如果是復(fù)雜配置項(xiàng),會(huì)調(diào)用上次執(zhí)行的狀態(tài)繼續(xù)解析配置文件.
        *****************************************/
        rc = ngx_conf_read_token(cf);

        /*
         * ngx_conf_read_token() may return
         *
         *    NGX_ERROR             there is error
         *    NGX_OK                the token terminated by ";" was found
         *    NGX_CONF_BLOCK_START  the token terminated by "{" was found
         *    NGX_CONF_BLOCK_DONE   the "}" was found
         *    NGX_CONF_FILE_DONE    the configuration file is done
         */

        if (rc == NGX_ERROR) {
            goto done;
        }
		//循環(huán)結(jié)束
        if (rc == NGX_CONF_BLOCK_DONE) {
            goto done;
        }
        //循環(huán)結(jié)束
        if (rc == NGX_CONF_FILE_DONE) {
            goto done;
        }


        /* rc == NGX_OK || rc == NGX_CONF_BLOCK_START */
        //cf->handler初始為空,需要在ngx_conf_handler配置
        if (cf->handler) {
            /*
             * the custom handler, i.e., that is used in the http's
             * "types { ... }" directive
             */
            rv = (*cf->handler)(cf, NULL, cf->handler_conf);
            if (rv == NGX_CONF_OK) {
                continue;
            }
       		...
        }

		//常規(guī)內(nèi)容處理
        rc = ngx_conf_handler(cf, rc);

        if (rc == NGX_ERROR) {
            goto failed;
        }
    }

	...
}

代碼包含2部分:

  • 上半部分,文件信息讀入
  • 下半部分,循環(huán)遍歷文件內(nèi)容

前面部分已經(jīng)描述了,配置文件路徑是如何得到的,在這里重新將文件信息賦值進(jìn)ngx_conf_t 結(jié)構(gòu)體 cf中,以便傳入后面的函數(shù)去讀取文件內(nèi)容,不多描述,講下第2點(diǎn)循環(huán)遍歷文件內(nèi)容,這里有幾個(gè)關(guān)鍵點(diǎn)

  • 循環(huán)何時(shí)退出?
  • 內(nèi)容如何讀???
  • 內(nèi)容如何放入全局的conf_ctx中

3.1 循環(huán)何時(shí)退出?

從for ( ;; ) 代碼開(kāi)始看,正常的情況下是在塊結(jié)束(rc == NGX_CONF_BLOCK_DONE也就是 字符"}")和文件結(jié)束(rc == NGX_CONF_FILE_DONE)時(shí)退出,文件讀取結(jié)束退出理解,但是塊結(jié)束怎么就退出了?

塊中不還有塊嗎?類(lèi)似下圖這種,道理也很簡(jiǎn)單,塊里面讀取過(guò)程都一樣,是一種遞歸的調(diào)用,塊里面遇到塊會(huì)繼續(xù)調(diào)用ngx_conf_parse函數(shù),只是nginx把這些過(guò)程都放到模塊的接口去了

在這里插入圖片描述

3.2 內(nèi)容如何讀取

ngx_conf_read_token就是對(duì)文件內(nèi)容的讀取,上面代碼也有注釋?zhuān)?/p>

讀取文件內(nèi)容,每次讀取一個(gè)buf大小(4K),如果文件內(nèi)容不足4K則全部讀取到buf中.掃描buf中的內(nèi)容,每次掃描一個(gè)token就會(huì)存入cf->args中,然后返回.

掃描buf中的內(nèi)容,每次掃描一個(gè)token就會(huì)存入cf->args中,然后返回.

什么情況下回返回呢?

  • - 讀到了一個(gè)配置項(xiàng),比如(模塊內(nèi)也一樣): “worker_processes 1;” 、 “index index.html index.htm;”
  • - 讀到了一個(gè)模塊名,比如:“http { "
  • - 塊結(jié)束,比如:”}"

返回后調(diào)用ngx_conf_parse函數(shù)會(huì)調(diào)用*cf->handler和ngx_conf_handler(cf, rc)函數(shù)處理.

如果是復(fù)雜配置項(xiàng),會(huì)調(diào)用上次執(zhí)行的狀態(tài)繼續(xù)解析配置文件.

所以一次讀一個(gè)token出來(lái),也就是一個(gè)配置項(xiàng),放入cf->args

3.3 內(nèi)容如何放入全局的conf_ctx中?

我們來(lái)看ngx_conf_handler函數(shù),也只貼重要部分

static ngx_int_t
ngx_conf_handler(ngx_conf_t *cf, ngx_int_t last)
{
    char           *rv;
    void           *conf, **confp;
    ngx_uint_t      i, found;
    ngx_str_t      *name;
    ngx_command_t  *cmd;
    //cf->args->elts 不是包含了配置項(xiàng)的名字和值嗎?為什么可以取到名字?
    //因?yàn)閏f->args->elts是一個(gè)鏈表,首節(jié)點(diǎn)就是配置項(xiàng)名字,并且每個(gè)元素都以'\0'結(jié)尾了
    name = cf->args->elts;

    found = 0;
    //遍歷模塊
    for (i = 0; cf->cycle->modules[i]; i++) {

        cmd = cf->cycle->modules[i]->commands;
        if (cmd == NULL) {
            continue;
        }
        //遍歷模塊的配置項(xiàng)
        for ( /* void */ ; cmd->name.len; cmd++) {

            if (name->len != cmd->name.len) {
                continue;
            }
            //匹配配置項(xiàng)的名字
            if (ngx_strcmp(name->data, cmd->name.data) != 0) {
                continue;
            }

            found = 1;

            if (cf->cycle->modules[i]->type != NGX_CONF_MODULE
                && cf->cycle->modules[i]->type != cf->module_type)
            {
                continue;
            }

            /* is the directive's location right ? */
            //匹配配置項(xiàng)的類(lèi)型
            if (!(cmd->type & cf->cmd_type)) {
                continue;
            }
         	...

            /* set up the directive's configuration context */

            conf = NULL;
            
            if (cmd->type & NGX_DIRECT_CONF) {
                conf = ((void **) cf->ctx)[cf->cycle->modules[i]->index];

            } else if (cmd->type & NGX_MAIN_CONF) {
                conf = &(((void **) cf->ctx)[cf->cycle->modules[i]->index]);

            } else if (cf->ctx) {
                
                confp = *(void **) ((char *) cf->ctx + cmd->conf);

                if (confp) {
                    conf = confp[cf->cycle->modules[i]->ctx_index];
                }

            }

            rv = cmd->set(cf, cmd, conf);

      		...
        }
    }
	...
}

函數(shù)邏輯也很簡(jiǎn)單,遍歷所有模塊的所有配置項(xiàng),比如配置文件讀取到deamon off;時(shí),或 讀取master_process時(shí)

在這里插入圖片描述

就會(huì)找到ngx_core_module模塊及其配置項(xiàng)ngx_core_commands

在這里插入圖片描述

找到后,根據(jù)配置項(xiàng)類(lèi)型從全局conf_ctx中取出指針,該指針指向包含存儲(chǔ)該配置項(xiàng)信息的結(jié)構(gòu)體,然后調(diào)用模塊配置項(xiàng)的接口set函數(shù),處理該信息,set接口會(huì)如何處理?繼續(xù)往下看

四 以http塊信息讀取來(lái)說(shuō)明set的作用

一般來(lái)說(shuō)信息會(huì)存儲(chǔ)到指定的配置結(jié)構(gòu)體中,比如deamon,master_process,會(huì)將其信息存入ngx_core_conf_t

在這里插入圖片描述

經(jīng)過(guò)之前的代碼引入和說(shuō)明,我們可以簡(jiǎn)潔的將ngx_conf_parse函數(shù)調(diào)用過(guò)程貼出來(lái)

1、ngx_conf_parse

	 for ( ;; ) {
	    rc = ngx_conf_read_token(cf);
	    //常規(guī)內(nèi)容處理
	    rc = ngx_conf_handler(cf, rc);
	 }

2、ngx_conf_handler,conf的取值可能不同,第一次看有點(diǎn)繞,但是沒(méi)關(guān)系,你只要明白這玩意的目的是為了取出對(duì)應(yīng)的配置結(jié)構(gòu)體就行,然后set的目的就是設(shè)置該結(jié)構(gòu)體的信息

	...
    if (cmd->type & NGX_DIRECT_CONF)
    {
        conf = ((void **)cf->ctx)[cf->cycle->modules[i]->index];
    }
    else if (cmd->type & NGX_MAIN_CONF)
    {
        conf = &(((void **)cf->ctx)[cf->cycle->modules[i]->index]);
    }
    else if (cf->ctx)
    {

        confp = *(void **)((char *)cf->ctx + cmd->conf);

        if (confp)
        {
            conf = confp[cf->cycle->modules[i]->ctx_index];
        }
    }

    rv = cmd->set(cf, cmd, conf);
	...

4.1 當(dāng)讀取到http時(shí),遍歷模塊及其配置項(xiàng),調(diào)用其set接口

在這里插入圖片描述

依上圖及源碼,會(huì)調(diào)用ngx_http_block函數(shù)來(lái)處理http這個(gè)配置信息,其函數(shù)如下:

static char *
ngx_http_block(ngx_conf_t *cf, ngx_command_t *cmd, void *conf)

調(diào)用函數(shù)前,先搞清楚其傳參,如下圖,前2個(gè)參數(shù)好理解,后一個(gè)參數(shù)是什么意思?前面也說(shuō)了是找出其配置結(jié)構(gòu)體的位置指針

在這里插入圖片描述

可以這樣理解,conf指向conf_ctx的第7個(gè)元素

在這里插入圖片描述

繼續(xù)了解ngx_http_block函數(shù),從源碼可以看出該函數(shù)做了以下幾件事

4.1.1 ngx_http_conf_ctx_t結(jié)構(gòu)體的分配,如下圖代碼所示,注意此時(shí)的conf就是上圖紅框標(biāo)識(shí)的conf

在這里插入圖片描述

此時(shí)conf_ctx 內(nèi)存如下圖,此時(shí) http配置項(xiàng)的結(jié)構(gòu)體已經(jīng)掛到全局conf_ctx上來(lái)了

在這里插入圖片描述

4.1.2 統(tǒng)計(jì)http模塊個(gè)數(shù),并為每個(gè)http模塊ctx_index賦值

在這里插入圖片描述

4.1.3 為ngx_http_conf_ctx_t結(jié)構(gòu)體的3個(gè)成員的分配內(nèi)存,有多少個(gè)http模塊就分配多少個(gè)指針給其成員,為什么要這么分配?

typedef struct {
    void        **main_conf;
    void        **srv_conf;
    void        **loc_conf;
} ngx_http_conf_ctx_t;

4.1.4 為每個(gè)http模塊創(chuàng)建其配置結(jié)構(gòu)體,與為全局conf_ctx分配內(nèi)存,創(chuàng)建配置結(jié)構(gòu)體一樣,都是其數(shù)組內(nèi)部指針指向不同的結(jié)構(gòu)體,而這些結(jié)構(gòu)體就是為了保持配置文件中的信息,內(nèi)存分配如下圖,篇幅有限只顯示了前幾個(gè)http模塊,注意:這里的索引就是第2步中模塊的ctx_index

在這里插入圖片描述

4.1.5 繼續(xù)解析http塊內(nèi)的配置信息,調(diào)用ngx_conf_parse函數(shù)

過(guò)程大致與“第三”大節(jié)一樣,此時(shí)有幾個(gè)變量要注意,其中ctx 就是上圖的ngx_http_conf_ctx_t,模塊類(lèi)型和配置類(lèi)型都變了,如下代碼:

	cf->ctx = ctx;
	cf->module_type = NGX_HTTP_MODULE;
    cf->cmd_type = NGX_HTTP_MAIN_CONF;
    rv = ngx_conf_parse(cf, NULL);

最后調(diào)用ngx_conf_handler函數(shù)時(shí),

在這里插入圖片描述

看起來(lái)沒(méi)變化,其實(shí)上圖中

  • cf->ctx為ngx_http_conf_ctx_t
  • cf->cmd_type = NGX_HTTP_MAIN_CONF

因此最終conf=confp[cf->cycle->modules[i]->ctx_index]?為什么這么取?可以先看下cmd->conf如何定義的

struct ngx_command_s {
    ngx_str_t             name;
    ngx_uint_t            type;
    char               *(*set)(ngx_conf_t *cf, ngx_command_t *cmd, void *conf);
    ngx_uint_t            conf;
    ngx_uint_t            offset;
    void                 *post;
};

取值如下圖

在這里插入圖片描述

該宏定義如下,是找到成員變量在結(jié)構(gòu)體中的偏移,也就可以根據(jù)cmd.conf找到是配置結(jié)構(gòu)體在ngx_http_conf_ctx_t結(jié)構(gòu)體中的哪個(gè)數(shù)組(main_conf、ser_conf、loc_conf),然后再根據(jù)模塊的ctx_index找到其對(duì)應(yīng)的配置結(jié)構(gòu)體

#define NGX_HTTP_MAIN_CONF_OFFSET  offsetof(ngx_http_conf_ctx_t, main_conf)
#define NGX_HTTP_SRV_CONF_OFFSET   offsetof(ngx_http_conf_ctx_t, srv_conf)
#define NGX_HTTP_LOC_CONF_OFFSET   offsetof(ngx_http_conf_ctx_t, loc_conf)

4.2 遇到server塊怎么處理?

函數(shù)就不展開(kāi)了,是ngx_http_core_module模塊的ngx_http_core_server,讀者可以自己去讀源碼

在這里插入圖片描述

過(guò)程與遇到http塊差不多

  • 創(chuàng)建一個(gè)ngx_http_conf_ctx_t結(jié)構(gòu)體變量ctx
  • 將其main_conf指向http塊的main_conf位置,如圖綠色線部分,為srv_conf 和loc_conf重新分配內(nèi)存,
  • 獲取srv_conf 數(shù)組中索引ngx_http_core_module.ctx_index的結(jié)構(gòu)體,就是索引為0的結(jié)構(gòu)體,也是ngx_http_core_srv_conf_t結(jié)構(gòu)體,將其結(jié)構(gòu)體成員ctx指向一開(kāi)始創(chuàng)建的ctx,下圖右邊部分的圖示
  • 將獲取到的ngx_http_core_srv_conf_t結(jié)構(gòu)體放入ngx_http_core_main_conf_t結(jié)構(gòu)體,如圖坐標(biāo)紅色箭頭的圖示,這樣不管遇到多少個(gè)server塊都能將其信息保存,同時(shí)也能反向查找到
  • 繼續(xù)解析文件,調(diào)用ngx_conf_parse
   /* parse inside server{} */
   pcf = *cf;
   cf->ctx = ctx;
   cf->cmd_type = NGX_HTTP_SRV_CONF;
   rv = ngx_conf_parse(cf, NULL);

在這里插入圖片描述

4.3 遇到location塊怎么處理?

同樣會(huì)遇到塊location,和上面一樣,直接查看ngx_http_core_location函數(shù),此時(shí)的cf->ctx 為 解析server塊時(shí)創(chuàng)建的ngx_http_conf_ctx_t

在這里插入圖片描述

過(guò)程與上面的處理差不多,

  • 依然會(huì)創(chuàng)建ngx_http_conf_ctx_t結(jié)構(gòu)體變量ctx
  • 其main_conf與server_conf指向上一級(jí),也就是處理server塊時(shí)創(chuàng)建的ngx_http_conf_ctx_t的結(jié)構(gòu)體main_conf與server_conf,而location則新分配內(nèi)存

這里有個(gè)不同,就是多個(gè)location塊怎么處理?

看下面代碼,注意ctx代碼為處理當(dāng)前l(fā)ocation生成的ngx_http_conf_ctx_t,而pctx為上一級(jí)也就是server塊生成的ngx_http_conf_ctx_t

	ngx_http_core_loc_conf_t  *clcf, *pclcf;
	clcf = ctx->loc_conf[ngx_http_core_module.ctx_index];
    clcf->loc_conf = ctx->loc_conf;
    
	pclcf = pctx->loc_conf[ngx_http_core_module.ctx_index];
 	if (ngx_http_add_location(cf, &pclcf->locations, clcf) != NGX_OK) {
        return NGX_CONF_ERROR;
    }

在看ngx_http_add_location,這就不展開(kāi)了,目的是將當(dāng)前l(fā)ocation的配置結(jié)構(gòu)體ngx_http_core_loc_conf_t 放入上一級(jí)的locations中取,如下圖:

在這里插入圖片描述

結(jié)構(gòu)體分配完成后會(huì)繼續(xù)ngx_conf_parse,此時(shí)不會(huì)在遇到塊了,所以會(huì)將配置信息放入特殊的結(jié)構(gòu)體中,然后再一一退出遞歸(因?yàn)榇藭r(shí)ngx_conf_parse還是在遞歸中)。

總結(jié)

以上為個(gè)人經(jīng)驗(yàn),希望能給大家一個(gè)參考,也希望大家多多支持腳本之家。

相關(guān)文章

  • Nginx網(wǎng)站服務(wù)詳解

    Nginx網(wǎng)站服務(wù)詳解

    這篇文章主要介紹了Nginx網(wǎng)站服務(wù),具有很好的參考價(jià)值,希望對(duì)大家有所幫助,如有錯(cuò)誤或未考慮完全的地方,望不吝賜教
    2025-06-06
  • Nginx七層及四層反向代理配置的全過(guò)程

    Nginx七層及四層反向代理配置的全過(guò)程

    反向代理是以代理服務(wù)器來(lái)接受internet連接請(qǐng)求,然后再把請(qǐng)求轉(zhuǎn)發(fā)給另外的服務(wù)器,下面這篇文章主要給大家介紹了關(guān)于Nginx七層及四層反向代理配置的相關(guān)資料,需要的朋友可以參考下
    2022-03-03
  • Nginx通過(guò)header中的標(biāo)識(shí)進(jìn)行分發(fā)

    Nginx通過(guò)header中的標(biāo)識(shí)進(jìn)行分發(fā)

    本文主要介紹了Nginx通過(guò)header中的標(biāo)識(shí)進(jìn)行分發(fā),文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧
    2023-03-03
  • Nginx中的網(wǎng)站服務(wù)詳解

    Nginx中的網(wǎng)站服務(wù)詳解

    這篇文章主要介紹了Nginx中的網(wǎng)站服務(wù),具有很好的參考價(jià)值,希望對(duì)大家有所幫助,如有錯(cuò)誤或未考慮完全的地方,望不吝賜教
    2025-05-05
  • Linux安裝Nginx步驟詳解

    Linux安裝Nginx步驟詳解

    這篇文章主要介紹了Linux安裝Nginx步驟,本文給大家介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下
    2020-11-11
  • CentOS如何用nginx搭建文件下載服務(wù)器

    CentOS如何用nginx搭建文件下載服務(wù)器

    Nginx 是開(kāi)源、高性能、高可靠的 Web 和反向代理服務(wù)器,而且支持熱部署,幾乎可以做到 7 * 24 小時(shí)不間斷運(yùn)行,即使運(yùn)行幾個(gè)月也不需要重新啟動(dòng),這篇文章主要介紹了CentOS用nginx搭建文件下載服務(wù)器,需要的朋友可以參考下
    2023-11-11
  • Nginx之QPS限制模塊的具體使用

    Nginx之QPS限制模塊的具體使用

    本文主要介紹了Nginx之QPS限制模塊的具體使用,主要介紹Nginx QPS限制模塊的原理、安裝和使用方法,具有一定的參考價(jià)值,感興趣的可以了解一下
    2023-09-09
  • nginx中g(shù)zip壓縮提升網(wǎng)站速度的實(shí)現(xiàn)方法

    nginx中g(shù)zip壓縮提升網(wǎng)站速度的實(shí)現(xiàn)方法

    這篇文章主要介紹了nginx中g(shù)zip壓縮提升網(wǎng)站速度的實(shí)現(xiàn)方法,非常不錯(cuò),具有一定的參考借鑒價(jià)值,需要的朋友可以參考下
    2019-08-08
  • Nginx?Proxy?Manager的具體實(shí)現(xiàn)

    Nginx?Proxy?Manager的具體實(shí)現(xiàn)

    Nginx?Proxy?Manager?就是一個(gè)?Nginx?的代理管理器,本文主要介紹了Nginx?Proxy?Manager的具體實(shí)現(xiàn),具有一定的參考價(jià)值,感興趣的可以了解一下
    2024-05-05
  • nginx配置文件詳解中文版

    nginx配置文件詳解中文版

    這篇文章主要介紹了nginx配置文件nginx.conf的配置參數(shù)詳解,并增加了中文版注釋,需要的朋友可以參考下
    2014-03-03

最新評(píng)論