Apache模块开发指南-APR池

转:原文: http://blog.csdn.net/zmxiangde_88/article/details/8038150

-------------------------------------------------------------------------------

博文主要内容来自APR_POOL的帮助文档

APR的意思是Apache可移植运行库,是Apache portable Run-time Libraries的缩写,主要是为编写上层的应用程序提供一个跨平台使用的接口,在早期的时候,为了应用程序在多个操作系统和平台上能够运行,应用本身需要处理各种具体的细节,针对不同的平台调用不同的处理函数等等,到了今天,这些操作平台之间不同的调用以及细节处理都有一个通用的处理方式,这就是APR库。

在实际的应用程序开发过程中,经常有内存操作,在Apache模块开发时,内存的操作可以通过这个池来完成。就是在需要内存的时候,从这个池上分配,当不再需要使用任何内存时,可以将这个池释放,这样就可以释放这个池上所有的内存(那些被多次分配的,可以一次被释放了,但我们需要为内存注册一个释放内存的操作)。事实上,每个HTTP request结构都有一个apr_pool_t结构实例,后者表示内存池的管理实例,也是Apache中资源管理的核心。

一,三个基本的API

[cpp]view plaincopy

  1. APR_DECLARE(apr_status_t) apr_pool_create(apr_pool_t **newpool,
  2. apr_pool_t *parent);
  3. APR_DECLARE(void *) apr_palloc(apr_pool_t *p, apr_size_t size);
  4. APR_DECLARE(void) apr_pool_destroy(apr_pool_t *p);

上面三个API分别表示创建一个APR池,从池中分配内存,释放APR池,是一个内存池的最基本的三个操作。

二,一个例子

[cpp]view plaincopy

  1. #include <stdio.h>
  2. #include <stdlib.h>
  3. #include <assert.h>
  4. #include <apr_general.h>
  5. #include <apr_pools.h>
  6. #define MEM_ALLOC_SIZE 1024
  7. /**
  8. * memory pool sample code
  9. * @remark Error checks omitted
  10. */
  11. int main(int argc, const char *argv[])
  12. {
  13. apr_status_t rv;
  14. apr_pool_t *mp;
  15. char *buf1;
  16. char *buf2;
  17. /* per-process initialization */
  18. rv = apr_initialize();
  19. if (rv != APR_SUCCESS) {
  20. assert(0);
  21. return -1;
  22. }
  23. /* create a memory pool. */
  24. apr_pool_create(&mp, NULL);
  25. /* allocate memory chunks from the memory pool */
  26. buf1 = apr_palloc(mp, MEM_ALLOC_SIZE);
  27. buf2 = apr_palloc(mp, MEM_ALLOC_SIZE);
  28. /* destroy the memory pool. These chunks above are freed by this */
  29. apr_pool_destroy(mp);
  30. apr_terminate();
  31. return 0;
  32. }

上面例子中的,要注意的是rv=apr_initialize()和apr_terminate(),这两个方法相当于初始化APR内部数据结构和结束APR库的使用,apr_initialize()函数必须是第一个被调用的APR库函数。

三,关于apr_pool_clear函数

这个函数和apr_pool_destory函数类似,但它在调用之后,内存池仍然可以使用。

[cpp]view plaincopy

  1. apr_pool_t *mp;
  2. apr_pool_create(&mp, NULL);
  3. for (i = 0; i < n; ++i) {
  4. do_operation(..., mp);
  5. apr_pool_clear(mp);
  6. }
  7. apr_pool_destroy(mp);

四,apr_pool_cleanup_register

一般的从池中分配的内存之后,当内存池被释放时,这块内存也会被自动的回收,也可以调用apr_pool_cleanup_register以显式的指定一个回调函数,当指定的内存被释放时。

如:

[cpp]view plaincopy

  1. int *value=(int*)malloc(sizeof(int));
  2. apr_pool_cleanup_register(pool,value,free,apr_pool_cleanup_null);

在这个注册之后,我们不用关心内存是否被释放以及什么时候释放的。当apr_pool_destory(pool)释放内存池时,上面的value指向的内存就会被自动的释放,并且调用free来释放。