We have been having some really wierd errors on our mud, so we want to valgrind to try to find some data corruption. To make the output close to usable, I have been using code to clean all memory that has been allocated, then booting and shutting down right away. I have been able to fix most issues with it, except for some error about conditional jumps in deflate and get_hostbyname, but I have a few that I can't figure out:
USA
#1
USA
#2
bool RACE_DATA::load_race_file(char *racefile)
{
char filename[256];
RACE_DATA *race;
FILE *fp;
snprintf(filename, 256, "%s%s", RACES_DIR, racefile);
if ((fp = fopen(filename, "r")) != NULL)
{
for (;;)
{
char letter;
char *word;
letter = fread_letter(fp);
if (letter == '*')
{
fread_to_eol(fp);
continue;
}
if (letter != '#')
{
bug("Load_race_file: # not found.", 0);
break;
}
word = fread_word(fp);
if (!str_cmp(word, "RACE"))
{
race = new RACE_DATA;
race->load(fp);
races.push_back(race); /* Line 309 */
break;
}
else if (!str_cmp(word, "END"))
break;
else
{
bug("Load_race_file: bad section: %s.", word);
break;
}
}
FCLOSE(fp);
return TRUE;
}
return FALSE;
}
And I am getting this error:
==22665== 20 bytes in 5 blocks are still reachable in loss record 2 of 10
==22665== at 0x1B904727: operator new(unsigned) (vg_replace_malloc.c:132)
==22665== by 0x1B9A0EC1: __gnu_cxx::__pool<true>::_M_initialize(void (*)(void*)) (in /usr/lib/libstdc++.so.6.0.5)
==22665== by 0x80757E8: __gnu_cxx::__common_pool_policy<__gnu_cxx::__pool, true>::_S_initialize() (mt_allocator.h:472)
==22665== by 0x8073E28: __gnu_cxx::__pool<true>::_M_initialize_once(void (*)()) (mt_allocator.h:332)
==22665== by 0x807510E: __gnu_cxx::__common_pool_policy<__gnu_cxx::__pool, true>::_S_initialize_once() (mt_allocator.h:460)
==22665== by 0x81B8FC6: __gnu_cxx::__mt_alloc<std::_List_node<RACE_DATA*>, __gnu_cxx::__common_pool_policy<__gnu_cxx::__pool, true> >::allocate(unsigned, void const*) (mt_allocator.h:693)
==22665== by 0x81B90F1: std::_List_base<RACE_DATA*, std::allocator<RACE_DATA*> >::_M_get_node() (stl_list.h:312)
==22665== by 0x81B910A: std::list<RACE_DATA*, std::allocator<RACE_DATA*> >::_M_create_node(RACE_DATA* const&) (stl_list.h:437)
==22665== by 0x81B9167: std::list<RACE_DATA*, std::allocator<RACE_DATA*> >::_M_insert(std::_List_iterator<RACE_DATA*>, RACE_DATA* const&) (stl_list.h:1151)
==22665== by 0x81B91B2: std::list<RACE_DATA*, std::allocator<RACE_DATA*> >::push_back(RACE_DATA* const&) (stl_list.h:773)
==22665== by 0x81B87D1: RACE_DATA::load_race_file(char*) (races.c:309)
==22665== by 0x81B89A1: RACE_DATA::load_races() (races.c:367)
==22665== by 0x81230C1: boot_db(bool) (db.c:942)
==22665== by 0x810AEA9: main (comm.c:344)
==22665== 120 bytes in 1 blocks are still reachable in loss record 7 of 10
==22665== at 0x1B904727: operator new(unsigned) (vg_replace_malloc.c:132)
==22665== by 0x81B878B: RACE_DATA::load_race_file(char*) (races.c:307)
==22665== by 0x81B89A1: RACE_DATA::load_races() (races.c:367)
==22665== by 0x81230C1: boot_db(bool) (db.c:942)
==22665== by 0x810AEA9: main (comm.c:344)
Now, does this mean that I am putting bad data into the list, or that maybe I'm not traversing the whole list to free it? Any insight would be great.
Tossed my code into the grinder again now that you brought this up, and decided to play a baseless hunch. Here's some of what I got on a clean shutdown:
==19215== 334560 bytes in 82 blocks are still reachable in loss record 5 of 5
==19215== at 0x1B904C1E: operator new(unsigned) (vg_replace_malloc.c:164)
==19215== by 0x1B9BC02E: __gnu_cxx::__pool<true>::_M_reserve_block(unsigned, unsigned) (in /usr/lib/libstdc++.so.6.0.5)
==19215== by 0x1B9BC9A0: (within /usr/lib/libstdc++.so.6.0.5)
==19215== by 0x1BA0738C: std::string::_Rep::_S_create(unsigned, unsigned, std::allocator<char> const&) (in /usr/lib/libstdc++.so.6.0.5)
==19215== by 0x1BA0B41E: (within /usr/lib/libstdc++.so.6.0.5)
==19215== by 0x1BA0C03B: std::string::string(char const*, std::allocator<char> const&) (in /usr/lib/libstdc++.so.6.0.5)
==19215== by 0x814B810: main (comm.c:1265)
comm.c:1265 =
if( !is_number( argv[1] ) )
Now in this particular case I had is_number accepting only a std::string for an argument. It hit me that I might want to put back the const char* version to see how it reacted.
The leak report disappeared as soon as I put back the second version of is_number. So this leads me to beleive Valgrind considers the char->string promotion to be some form of memory leak. It's probably right since it would convert it on the fly into a std::string which would have to involve some sort of memory thing. I reground the code and came back with a different error, causes in a similar manner due to there only being one version of the function with std::string parameters being accepted.
Perhaps you are running into a similar situation here? No idea what your race->load() function looks like but you might check it for weirdness like this.
==19215== 334560 bytes in 82 blocks are still reachable in loss record 5 of 5
==19215== at 0x1B904C1E: operator new(unsigned) (vg_replace_malloc.c:164)
==19215== by 0x1B9BC02E: __gnu_cxx::__pool<true>::_M_reserve_block(unsigned, unsigned) (in /usr/lib/libstdc++.so.6.0.5)
==19215== by 0x1B9BC9A0: (within /usr/lib/libstdc++.so.6.0.5)
==19215== by 0x1BA0738C: std::string::_Rep::_S_create(unsigned, unsigned, std::allocator<char> const&) (in /usr/lib/libstdc++.so.6.0.5)
==19215== by 0x1BA0B41E: (within /usr/lib/libstdc++.so.6.0.5)
==19215== by 0x1BA0C03B: std::string::string(char const*, std::allocator<char> const&) (in /usr/lib/libstdc++.so.6.0.5)
==19215== by 0x814B810: main (comm.c:1265)
comm.c:1265 =
if( !is_number( argv[1] ) )
Now in this particular case I had is_number accepting only a std::string for an argument. It hit me that I might want to put back the const char* version to see how it reacted.
The leak report disappeared as soon as I put back the second version of is_number. So this leads me to beleive Valgrind considers the char->string promotion to be some form of memory leak. It's probably right since it would convert it on the fly into a std::string which would have to involve some sort of memory thing. I reground the code and came back with a different error, causes in a similar manner due to there only being one version of the function with std::string parameters being accepted.
Perhaps you are running into a similar situation here? No idea what your race->load() function looks like but you might check it for weirdness like this.
I see what you're getting at now:
==20274== 338640 bytes in 83 blocks are still reachable in loss record 4 of 4
==20274== at 0x1B904C1E: operator new(unsigned) (vg_replace_malloc.c:164)
==20274== by 0x1B9BC02E: __gnu_cxx::__pool<true>::_M_reserve_block(unsigned, unsigned) (in /usr/lib/libstdc++.so.6.0.5)
==20274== by 0x80B278C: std::_List_base<shell_cmd*, std::allocator<shell_cmd*> >::_M_get_node() (stl_list.h:312)
==20274== by 0x80B27A2: std::list<shell_cmd*, std::allocator<shell_cmd*> >::_M_create_node(shell_cmd* const&) (stl_list.h:437)
==20274== by 0x80B2809: std::list<shell_cmd*, std::allocator<shell_cmd*> >::_M_insert(std::_List_iterator<shell_cmd*>, shell_cmd* const&) (stl_list.h:1151)
==20274== by 0x80B283A: std::list<shell_cmd*, std::allocator<shell_cmd*> >::push_back(shell_cmd* const&) (stl_list.h:773)
==20274== by 0x80B1650: add_shellcommand(shell_cmd*) (shell.c:925)
==20274== by 0x80B1E5F: fread_shellcommand(_IO_FILE*, int) (shell.c:1006)
==20274== by 0x80B219A: load_shellcommands() (shell.c:1135)
==20274== by 0x81592BB: boot_db(bool) (db.c:1908)
Line 925:
shellcmdlist.push_back( command );
I've poured over the code in my case and can't really figure on why this should get reported.
BTW - About the uninitialized stuff for deflate, there's not much you can do about that. Best bet would be to set a suppression file to stop it from reporting on zlib stuff.
==20274== 338640 bytes in 83 blocks are still reachable in loss record 4 of 4
==20274== at 0x1B904C1E: operator new(unsigned) (vg_replace_malloc.c:164)
==20274== by 0x1B9BC02E: __gnu_cxx::__pool<true>::_M_reserve_block(unsigned, unsigned) (in /usr/lib/libstdc++.so.6.0.5)
==20274== by 0x80B278C: std::_List_base<shell_cmd*, std::allocator<shell_cmd*> >::_M_get_node() (stl_list.h:312)
==20274== by 0x80B27A2: std::list<shell_cmd*, std::allocator<shell_cmd*> >::_M_create_node(shell_cmd* const&) (stl_list.h:437)
==20274== by 0x80B2809: std::list<shell_cmd*, std::allocator<shell_cmd*> >::_M_insert(std::_List_iterator<shell_cmd*>, shell_cmd* const&) (stl_list.h:1151)
==20274== by 0x80B283A: std::list<shell_cmd*, std::allocator<shell_cmd*> >::push_back(shell_cmd* const&) (stl_list.h:773)
==20274== by 0x80B1650: add_shellcommand(shell_cmd*) (shell.c:925)
==20274== by 0x80B1E5F: fread_shellcommand(_IO_FILE*, int) (shell.c:1006)
==20274== by 0x80B219A: load_shellcommands() (shell.c:1135)
==20274== by 0x81592BB: boot_db(bool) (db.c:1908)
Line 925:
shellcmdlist.push_back( command );
I've poured over the code in my case and can't really figure on why this should get reported.
BTW - About the uninitialized stuff for deflate, there's not much you can do about that. Best bet would be to set a suppression file to stop it from reporting on zlib stuff.