Skip to content

《记录一次内存泄漏》 #31

Description

@bingtaoli

代码如下所示,session_init_active_id函数每500ms执行一次,就泄漏一个sessionid_st大小的内存。

根因就是创建hash表的时候没有传析构函数。struct中没有指针就不用释放自己了?

/* 登陆会话结构 */
typedef struct _session_id_st {
    sfe_uint32_t session_id;    /* session id */
    sfe_uint32_t uid;
    char seat[64];              /* session SEAT */
    char display[64];           /* DISPLAY变量 */
    char type[64];              /* Type变量 */
    char service[64];           /* Service变量 */
} session_id_st;

static int get_sessions(sfe_hash_st **p) 
{
     // 获取新的hash表
    sfe_hash_st *session_map = eaio_xhash_create(NULL, NULL);
    // 往hash表中存数据 
    session_id_st *item = (session_id_st *)malloc(sizeof(session_id_st));
    xhash_insert(session_map, &item->session_id, sizeof(item->session_id), item);
    *p = session_map;
}

/**
 * 获取登陆会话列表
*/
void session_init_active_id()
{
    sfe_hash_st *session_map = NULL;
    int ret = get_sessions(&session_map);
    if (ret) {
        warn("get sessions failed ret:%d\n", ret);
        return;
    }
    // 更新全局hash表
    sfe_hash_st *p = s_session_hash;
    s_session_hash = session_map;
    eaio_xhash_destroy(p);
}

修改:

sfe_hash_st *session_map = eaio_xhash_create(free, NULL);

教训一

这个函数每500ms执行一次,每次泄漏大概8+8+4x64=272个字节,一个小时就是3600x2x272=1958400bytes,也就是1.9M的内存,一天就是1.9Mx24=46M的内存。

这个为啥跑稳定性测试没有跑出来?

因为没有关注这个进程的内存,主观觉得这个进程肯定没问题。

教训二

对于这种高频执行的流程,一定要做性能测试,它外网500ms每执行一次。你性能测试就需要10ms执行一次,看是否会有内存泄漏。

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions