I accidentally left tethereal running on my home dsl firewall all day. When I noticed the rest of the network was behaving really slowly, I investigated, and found this in top output.. Mem: 105596k total, 103804k used, 1792k free, 116k buffers Swap: 1277944k total, 621384k used, 656560k free, 6252k cached PID USER PR NI VIRT RES SHR S %CPU %MEM TIME+ COMMAND 12984 root 16 0 621m 75m 1268 D 0.3 73.5 22:38.68 tethereal before starting tethereal , there was no swap used at all (it's normal state on this box) (01:46:01:davej@firewall:~)$ free total used free shared buffers cached Mem: 105596 103468 2128 0 100 7572 -/+ buffers/cache: 95796 9800 Swap: 1277944 621040 656904 (01:48:53:davej@firewall:~)$ sudo kill -9 12984 (01:49:34:davej@firewall:~)$ free total used free shared buffers cached Mem: 105596 33332 72264 0 296 10004 -/+ buffers/cache: 23032 82564 Swap: 1277944 11476 1266468
running this under valgrind for a few minutes is.. enlightening. valgrind --leak-check=yes --show-reachable=yes tethereal -V -i eth0 among lots of smaller allocations reported are.. ==24353== 586,560 bytes in 2,264 blocks are possibly lost in loss record 44 of 46 ==24353== at 0x48044B3: memalign (vg_replace_malloc.c:332) ==24353== by 0x4804509: posix_memalign (vg_replace_malloc.c:384) ==24353== by 0xBE0488: (within /usr/lib/libglib-2.0.so.0.902.4) ==24353== by 0xBE1717: g_slice_alloc (in /usr/lib/libglib-2.0.so.0.902.4) ==24353== by 0xBD18A2: g_mem_chunk_alloc (in /usr/lib/libglib-2.0.so.0.902.4)==24353== by 0x509191D: proto_register_protocol (in /usr/lib/libethereal.so.0.0.1) ==24353== by 0x50C7483: proto_register_3com_xns (in /usr/lib/libethereal.so.0.0.1) ==24353== by 0x564D346: register_all_protocols (in /usr/lib/libethereal.so.0.0.1) ==24353== by 0x509691A: proto_init (in /usr/lib/libethereal.so.0.0.1) ==24353== by 0x5082B4D: epan_init (in /usr/lib/libethereal.so.0.0.1) ==24353== by 0x1BF46: main (in /usr/sbin/tethereal) ==24353== ==24353== ==24353== 1,504,512 bytes in 6,048 blocks are still reachable in loss record 45 of 46 ==24353== at 0x48044B3: memalign (vg_replace_malloc.c:332) ==24353== by 0x4804509: posix_memalign (vg_replace_malloc.c:384) ==24353== by 0xBE0488: (within /usr/lib/libglib-2.0.so.0.902.4) ==24353== by 0xBE1717: g_slice_alloc (in /usr/lib/libglib-2.0.so.0.902.4) ==24353== by 0xBD18F9: g_mem_chunk_new (in /usr/lib/libglib-2.0.so.0.902.4) ==24353== by 0x50AD0C5: tvbuff_init (in /usr/lib/libethereal.so.0.0.1) ==24353== by 0x5082B26: epan_init (in /usr/lib/libethereal.so.0.0.1) ==24353== by 0x1BF46: main (in /usr/sbin/tethereal) ==24353== ==24353== ==24353== 21,612,761 bytes in 29,858 blocks are still reachable in loss record 46 of 46 ==24353== at 0x48051F9: malloc (vg_replace_malloc.c:149) ==24353== by 0xBD1715: g_malloc (in /usr/lib/libglib-2.0.so.0.902.4) ==24353== by 0xBD2F8E: g_log_set_handler (in /usr/lib/libglib-2.0.so.0.902.4)==24353== by 0x1BEA6: main (in /usr/sbin/tethereal) ==24353== ==24353== LEAK SUMMARY: ==24353== definitely lost: 22,187 bytes in 2,830 blocks. ==24353== possibly lost: 586,560 bytes in 2,264 blocks. ==24353== still reachable: 23,878,820 bytes in 46,086 blocks. ==24353== suppressed: 0 bytes in 0 blocks.
It really looks bad. I've asked ethereal developers and here is what they suggest to try first -------- From gharris Are you running Tethereal either 1) without the "-w" option, so it dissects packets in order to display them or 2) with the "-R" option, so it dissects packets in order to do read filtering? If so, don't - the dissection produces a lot of state information, as well as packet reassembly information, and, by design, that information doesn't get freed until Tethereal exits. *Some* of it might be freeable while the capture is being done, but some of it is information that could conceivably be needed at some arbitrary later point in the dissection of the packet stream, so it can't be freed. -------- It's true that with -R option I see lower mem consuption but still some small leaks are present.
as shown in the comment above, I was using -V -i eth0 if it's designed this way, it's arguably horribly broken by design.
Yep, it's a design issue keeping the persistent data to produce sequences. ------- From gharris So it was, as I suspected, run without "-w", so it was dissecting. We might be able to avoid *persistently* saving reassembled packet data, although to make that work in Ethereal we need to make random access, including random access to compressed files, efficient (so that when you click on a packet whose contents are reassembled, we can re-read the packets from which it was reassembled and reconstruct the reassembled data). We might also be able to have a global "don't do any reassembly" flag. That would probably get rid of the biggest consumers of memory from dissection. There's other state information that would persist; an option to disable *that* would mean that, for a lot of protocols, replies won't be dissectable (as you need information from the request to dissect the reply; it might, or might not, be possible to get rid of that information once the reply's dissected, as some of it might need to be kept around for retransmissions and the like). (Note, BTW, that tcpdump, when run without the "-S" option, also keeps persistent state information around to produce relative sequence numbers.) --
Oh nice, there's also a Wiki page about memory consumption http://wiki.ethereal.com/KnownBugs/OutOfMemory