使用Memory Allocation API检测用户自定义的内存泄漏

我们知道,Intel® Inspector XE 2011 有一套接口函数库,比如支持在用户程序中Pause/Resume 性能分析,自定义的同步变量的识别, 帧(Frame)级别的性能分析,等。本篇要介绍的是另外一种功能,如何侦测自定义的内存泄露。即用户从自己的内存池里申请内存,而又没有释放。

一般工作流程:找到相关的INCLUDE文件和库文件。

    1. Include ittnotify.h, located at <install_dir>/include, in your code.

    1. Insert __itt_* notifications in appropriate places in your code.

    1. Link to the libittnotify.lib file located at <install_dir>/lib.



 相关的Memory Allocation APIs

typedef void* __itt_heap_function;
__itt_heap_function __itt_heap_function_create( const __itt_char* name, const __itt_char* domain )
void __itt_heap_allocate_begin( __itt_heap_function h, size_t size, int initialized );

void __itt_heap_allocate_end( __itt_heap_function h, void** addr, size_t size, int initialized );
void __itt_heap_free_begin( __itt_heap_function h, void* addr );

void __itt_heap_free_end( __itt_heap_function h, void* addr );
void __itt_heap_reallocate_begin( __itt_heap_function h, void* addr, size_t new_size, int initialized );

void __itt_heap_reallocate_end( __itt_heap_function h, void* addr, void** new_addr, size_t new_size, int initialized );
void __itt_heap_internal_access_begin( void );

void __itt_heap_internal_access_end( void );


 

以下用一个简单的例子(final_test_heap_api.cpp),介绍如何使用以上的APIs

#include<stdio.h>
#include<stdlib.h>

#include "ittnotify.h"

__itt_heap_function my_heap_malloc_h;
__itt_heap_function my_heap_free_h;

#define SIZE_HEAP  1024  /*1KB*/

const char *mName="my_malloc";
const char *fName="my_free";
const char *domain="my heap";

struct heap_struct
{
   void *start_addr;
   char *cur_addr;
   int size_heap;
};

// struct heap_struct my_heap;

void initialization(struct heap_struct *heap)
{
    __itt_heap_internal_access_begin();
   heap->start_addr = (int *)malloc(SIZE_HEAP);
    __itt_heap_internal_access_end();
   printf ("my heap start addr = 0x%lx\n", heap->start_addr);
   heap->cur_addr = (char*)heap->start_addr;

}

void *my_malloc(struct heap_struct *heap, int size)
{
    void *addr;
    __itt_heap_allocate_begin(my_heap_malloc_h, size, 1);
    addr = heap->cur_addr;
    heap->cur_addr += size; /* for next time */
    __itt_heap_allocate_end(my_heap_malloc_h, &addr, size, 1);

    return (addr);

}

void my_free(void* addr)
{
    __itt_heap_free_begin(my_heap_free_h, addr);
    /* do something here*/
    ;
    __itt_heap_free_end(my_heap_free_h, addr);

}

int main()
{
    int *int_p, *int_q;
    char *s;
    char *t;

    struct heap_struct my_heap;

    my_heap_malloc_h = __itt_heap_function_create(mName, domain);
    printf ("my_malloc_heap_h is %lx\n", my_heap_malloc_h);
    my_heap_free_h = __itt_heap_function_create(fName, domain);
    printf ("my_free_heap_h is %lx\n", my_heap_free_h);

    initialization(&my_heap);

    int_p=(int *)my_malloc(&my_heap, sizeof(int));
    printf ("allocating of int_p at 0x%lx\n", int_p);

    int_q=(int *)my_malloc(&my_heap, sizeof(int));
    printf ("allocating of int_q at 0x%lx\n", int_q);

    s=(char *)my_malloc(&my_heap, sizeof(char)*16);
    printf ("allocating of string at 0x%lx\n", s);

    t=(char *)my_malloc(&my_heap, sizeof(char)*32);
    printf ("allocating of string at 0x%lx\n", t);

/*
 * mi3 should report out of boundary issue
    __itt_heap_internal_access_begin();
    s[17] = 'a';
    __itt_heap_internal_access_end();
 */
    my_free(t);
    my_free(s);
    /* int_q is not free, will be reported */
    /* int_p is not free */
    /*   NOTE: because it is reachable from global memory (my_heap.start_addr)
     *   it won't be reported
     *   Peter: now move my_heap from global to local
     */

    printf("This is the test program \n");
    return(0);
}


1.  编译源代码 (使用Intel® C/C++ Compiler 12.0)

[root@kentsfield-01 peter]# source /opt/intel/compilerpro-12.0/bin/compilervars.sh intel64

[root@kentsfield-01 peter]# icpc -g final_test_heap_api.cpp libittnotify.a -o final_test_heap_api –lpthread

2.  使用Inspector XE 检测内存

[root@kentsfield-01 peter]# source /opt/intel/inspector_xe_2011/inspxe-vars.sh

Copyright (C) 2009-2011 Intel Corporation. All rights reserved.

Intel® Inspector XE 2011 (build 148563)

[root@kentsfield-01 peter]# inspxe-cl -collect mi3 -- ./final_test_heap_api

Used suppression file(s): []

my_malloc_heap_h is 0

my_free_heap_h is 1

my heap start addr = 0x19dd0f10

allocating of int_p at 0x19dd0f10

allocating of int_q at 0x19dd0f14

allocating of string at 0x19dd0f18

allocating of string at 0x19dd0f28

This is the test program

2 new problem(s) found

    2 Memory leak problem(s) detected

 


3.  可以使用Inspector XE 图形界面,在源代码级浏览结果(Call Stack:Caller/Callee)

Categories:
For more complete information about compiler optimizations, see our Optimization Notice.