Nginx 源碼分析-- 內存池(pool)的分析 一


  Nginx內存池(pool)的管理的實現主要寫在ngx_palloc.c這個文件中,為了明晰的看該文件中的函數之間的關系,我們描繪出以下一張簡單的示意圖:

 Nginx內存池(pool)管理功能函數關系圖

圖1  Nginx內存池(pool)管理功能函數關系圖

  由以上圖我們可以清晰的看出 Nginx內存池(pool)管理函數可分為兩部分,一部分底層支持函數主要為ngx_alloc、ngx_free、ngx_align_ptr(內存對齊的宏)、ngx_memalign、ngx_memzero,這部分函數比較簡單多為對C語言標准庫的一些封裝,另一部分內存池管理功能函數如ngx_creat_pool、ngx_destroy_pool、ngx_reset_pool、ngx_palloc等,內存分配功能以ngx_palloc為核心進行

1、底層支持函數

  其實從Nginx整個軟件的構建來看都存在這類函數,並非只存在於內存池(pool)管理中。這類函數有這樣一些特點,函數的內部結構一般比較簡單,多是簡單的對C標准庫中的函數進行一些簡單必要的封裝,很大一部分是以宏定義的方式給出,有些是直接將C標准庫中的函數名進行重命名而已,具體來說以下典型示例:

#define ngx_free free

即直接將C中的free 函數重命名為 ngx_free。

#define ngx_memzero(buf, n) (void) memset(buf, 0, n)

用宏來定義函數,運用memset函數將buf初始化為0。

void * ngx_alloc(size_t size, ngx_log_t *log)
{       
    void  *p;
    p = malloc(size);
    if (p == NULL) {
        ngx_log_error(NGX_LOG_EMERG, log, ngx_errno,"malloc(%uz) failed", size);
    }
    ngx_log_debug2(NGX_LOG_DEBUG_ALLOC, log, 0, "malloc: %p:%uz", p, size);
    return p;
}

對C語言標准庫中的malloc內存分配函數進行封裝同時,如果分配失敗,將失敗信息寫入日志和調試信息中。以上三類函數示例在Nginx源碼中非常典型,出現很多。

2、內存池管理主要數據結構

  在具體介紹內存池功能管理函數前,我們不得不對Nginx中內存管理的主要數據結構進行了解。

typedef struct {
    u_char               *last;
    u_char               *end;
    ngx_pool_t           *next;
    ngx_uint_t            failed;
} ngx_pool_data_t;

參數說明:last為當前當前可用空間的尾部邊界地址,end為已使用空間的尾部地址,next為下一個pool的地址,failed用來記錄內存分配失敗。由此可以看出Nginx的內存pool是由鏈表結構構成。

struct ngx_pool_s {
    ngx_pool_data_t       d;
    size_t                max;
    ngx_pool_t           *current;
    ngx_chain_t          *chain;
    ngx_pool_large_t     *large;
    ngx_pool_cleanup_t   *cleanup;
    ngx_log_t            *log;
};

參數說明:d可理解為當前pool中可以分配的內存地址(其中包含下一個pool的地址),max為內存池最大可分配地址,current當前內存池pool結點地址,chain一個ngx_chain_t結構指針 ,large接需求大內存時內存地址鏈表,cleanup回調函數指針,log日志指針。

struct ngx_pool_large_s {
    ngx_pool_large_t     *next;
    void                 *alloc;
};

參數說明:next指向ngx_pool_large_t鏈表下一個單元,alloc大塊內存的首地址,說明下Nginx數據結構中許多ngx_xxxxx_s 重命名為 ngx_xxxxx_t 此處ngx_pool_large_t 即為ngx_pool_large_s 結構

 

具體函數功能分析見二

 

  

 

  


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM