Valgrind使用适当的free()和end()后,显示ncurses命令的内存泄漏 [英] Valgrind shows memory leaks from ncurses commands after using appropriate free() and end()

查看:83
本文介绍了Valgrind使用适当的free()和end()后,显示ncurses命令的内存泄漏的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个正在编写的程序可以更好地理解ncurses,当我将其推入 valgrind 时,它会输出许多与ncurses命令相关的泄漏.但是,我只使用 stdscr ,并在 main()的末尾调用 endwin().我通过使用menu.h设置了用户选项,并在最后使用了free_item和free_menu:

I have a program I'm writing to better understand ncurses, and when I push it through valgrind, it outputs many leaks associated with ncurses commands. However, I only use stdscr, and call endwin() at the end of main(). I have user options set by using menu.h, and use free_item and free_menu at the end:

menuChoice(WINDOW* scr, std::vector<std::string> *choices,
    std::string desc)
{
    //create the menu and the item pointer vector
    MENU* my_menu;
    std::vector<ITEM*> my_items;
    ITEM* cur = NULL;
    for (int x = 0; x < choices->size(); x++)
    {
        //populate the items vector with the string data in choices
        my_items.push_back(new_item(choices->at(x).c_str(), NULL));
    }
    //pushback a null item
    my_items.push_back((ITEM*)NULL);
    //create the menu and attach the items
    my_menu = new_menu((ITEM**)my_items.data());
    //print the desc and post the menu
    mvwprintw(scr, LINES - 3, 0, "%s\n", desc.c_str());
    post_menu(my_menu);
    wrefresh(scr);
    int c = 0;
    while((c = wgetch(scr)) != '\n')
    {   switch(c)
        {   case KEY_DOWN:
                menu_driver(my_menu, REQ_DOWN_ITEM);
                break;
            case KEY_UP:
                menu_driver(my_menu, REQ_UP_ITEM);
                break;
        }
    }
    cur = current_item(my_menu);
    int toReturn;
    toReturn = boost::lexical_cast<int>((char*) item_name(cur));
    unpost_menu(my_menu);
    for (int x = 0; x < my_items.size(); x++)
    {
        free_item(my_items[x]);
    }
    free_menu(my_menu);
    return toReturn;
}

但是, valgrind 仍然给了我很多这样的东西:

However, valgrind still gives me lots of this:

==25266==    at 0x402A17C: malloc (in /usr/lib/valgrind/vgpreload_memcheck-x86-linux.so)
==25266==    by 0x405F2F3: _nc_hash_map (in /lib/i386-linux-gnu/libncurses.so.5.9)
==25266==    by 0x405E606: _nc_scroll_optimize (in /lib/i386-linux-gnu/libncurses.so.5.9)
==25266==    by 0x4075FF1: doupdate (in /lib/i386-linux-gnu/libncurses.so.5.9)
==25266==    by 0x406B02E: wrefresh (in /lib/i386-linux-gnu/libncurses.so.5.9)
==25266==    by 0x4064AAF: ??? (in /lib/i386-linux-gnu/libncurses.so.5.9)
==25266==    by 0x4064C46: _nc_wgetch (in /lib/i386-linux-gnu/libncurses.so.5.9)
==25266==    by 0x40658B9: wgetch (in /lib/i386-linux-gnu/libncurses.so.5.9)
==25266==    by 0x804B309: blackjack::menuChoice(_win_st*, std::vector<std::string, std::allocator<std::string> >*, std::string) (blackjack.cpp:555)
==25266==    by 0x804AF66: blackjack::prefScreen(_win_st*) (blackjack.cpp:521)
==25266==    by 0x8049BFF: blackjack::blackjack(_win_st*) (blackjack.cpp:21)
==25266==    by 0x8050118: blackjack_routine(_win_st*) (main.cpp:50)
==25266== 
==25266== 1,900 bytes in 1 blocks are still reachable in loss record 44 of 49
==25266==    at 0x402C324: realloc (in /usr/lib/valgrind/vgpreload_memcheck-x86-linux.so)
==25266==    by 0x4088068: _nc_doalloc (in /lib/i386-linux-gnu/libtinfo.so.5.9)
==25266==    by 0x4090076: _nc_read_termtype (in /lib/i386-linux-gnu/libtinfo.so.5.9)
==25266==    by 0x40903EB: _nc_read_file_entry (in /lib/i386-linux-gnu/libtinfo.so.5.9)
==25266==    by 0x4090578: _nc_read_entry (in /lib/i386-linux-gnu/libtinfo.so.5.9)
==25266==    by 0x408A5E4: _nc_setup_tinfo (in /lib/i386-linux-gnu/libtinfo.so.5.9)
==25266==    by 0x408A95B: _nc_setupterm (in /lib/i386-linux-gnu/libtinfo.so.5.9)
==25266==    by 0x4069580: newterm (in /lib/i386-linux-gnu/libncurses.so.5.9)
==25266==    by 0x4066013: initscr (in /lib/i386-linux-gnu/libncurses.so.5.9)
==25266==    by 0x80500C2: main (main.cpp:36)
==25266== 
==25266== 2,836 bytes in 1 blocks are still reachable in loss record 45 of 49
==25266==    at 0x402A17C: malloc (in /usr/lib/valgrind/vgpreload_memcheck-x86-linux.so)
==25266==    by 0x408807F: _nc_doalloc (in /lib/i386-linux-gnu/libtinfo.so.5.9)
==25266==    by 0x406F026: _nc_printf_string (in /lib/i386-linux-gnu/libncurses.so.5.9)
==25266==    by 0x406AB22: vwprintw (in /lib/i386-linux-gnu/libncurses.so.5.9)
==25266==    by 0x406AC68: mvwprintw (in /lib/i386-linux-gnu/libncurses.so.5.9)
==25266==    by 0x804B2A3: blackjack::menuChoice(_win_st*, std::vector<std::string, std::allocator<std::string> >*, std::string) (blackjack.cpp:550)
==25266==    by 0x804AF66: blackjack::prefScreen(_win_st*) (blackjack.cpp:521)
==25266==    by 0x8049BFF: blackjack::blackjack(_win_st*) (blackjack.cpp:21)
==25266==    by 0x8050118: blackjack_routine(_win_st*) (main.cpp:50)
==25266==    by 0x80500F3: main (main.cpp:41)
==25266== 
==25266== 3,182 bytes in 1 blocks are still reachable in loss record 46 of 49
==25266==    at 0x402A17C: malloc (in /usr/lib/valgrind/vgpreload_memcheck-x86-linux.so)
==25266==    by 0x406C0CF: _nc_setupscreen (in /lib/i386-linux-gnu/libncurses.so.5.9)
==25266==    by 0x40695CE: newterm (in /lib/i386-linux-gnu/libncurses.so.5.9)
==25266==    by 0x4066013: initscr (in /lib/i386-linux-gnu/libncurses.so.5.9)
==25266==    by 0x80500C2: main (main.cpp:36)

虽然没有太多泄漏,但是当我觉得自己遵守规则时,仍然让我觉得做错了事.

While it doesn't show much leakage, it still makes me think I've done something wrong when I feel like I've followed the rules.

推荐答案

ncurses常见问题解答 ="a href =" http://invisible-island.net/ncurses/ncurses.faq.html#config_leaks"rel =" noreferrer>测试内存泄漏 :

That is discussed in the ncurses FAQ Testing for Memory Leaks:

也许您使用了dmalloc或valgrind之类的工具来检查内存泄漏.它通常会报告仍在使用大量内存.那是正常的.

Perhaps you used a tool such as dmalloc or valgrind to check for memory leaks. It will normally report a lot of memory still in use. That is normal.

ncurses配置脚本​​具有--disable-leaks选项,可用于继续分析.如果可能,它告诉ncurses释放内存.但是,大多数使用中的内存是永久"的.

The ncurses configure script has an option, --disable-leaks, which you can use to continue the analysis. It tells ncurses to free memory if possible. However, most of the in-use memory is "permanent".

任何curses的实现都不能释放与屏幕相关的内存,因为(即使在调用endwin()之后),它也必须可用于下一次对refresh()的调用.也出于性能原因保留了大块内存.这使得很难分析curses应用程序的内存泄漏.要解决此问题,请构建ncurses库的调试版本,该库将释放它们可以释放的那些块,并提供 _nc_free_and_exit()函数以在退出时释放其余部分.ncurses实用程序和测试程序使用此功能,例如通过 ExitProgram()宏.

Any implementation of curses must not free the memory associated with a screen, since (even after calling endwin()), it must be available for use in the next call to refresh(). There are also chunks of memory held for performance reasons. That makes it hard to analyze curses applications for memory leaks. To work around this, build a debugging version of the ncurses library which frees those chunks which it can, and provides the _nc_free_and_exit() function to free the remainder on exit. The ncurses utility and test programs use this feature, e.g., via the ExitProgram() macro.

这篇关于Valgrind使用适当的free()和end()后,显示ncurses命令的内存泄漏的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆