@@ -10,7 +10,8 @@ Introduction
|
||||
|
||||
NetHogs is a small 'net top' tool. Instead of breaking the traffic down per protocol or per subnet, like most tools do, it groups bandwidth by process. NetHogs does not rely on a special kernel module to be loaded. If there's suddenly a lot of network traffic, you can fire up NetHogs and immediately see which PID is causing this. This makes it easy to indentify programs that have gone wild and are suddenly taking up your bandwidth.
|
||||
|
||||
Since NetHogs heavily relies on /proc, it currently runs on Linux only.
|
||||
Since NetHogs heavily relies on /proc, some functionalities are only available on Linux.
|
||||
NetHogs can be built on Mac OS X, but it will only show connections, not processes.
|
||||
|
||||
Status
|
||||
------
|
||||
|
||||
@@ -22,7 +22,11 @@
|
||||
|
||||
#include <iostream>
|
||||
#include <cassert>
|
||||
#include <malloc.h>
|
||||
#ifdef __APPLE__
|
||||
#include <sys/malloc.h>
|
||||
#else
|
||||
#include <malloc.h>
|
||||
#endif
|
||||
#include "nethogs.h"
|
||||
#include "connection.h"
|
||||
#include "process.h"
|
||||
|
||||
@@ -28,11 +28,17 @@
|
||||
#include "nethogs.h"
|
||||
#include "conninode.h"
|
||||
|
||||
#if defined __APPLE__
|
||||
#ifndef s6_addr32
|
||||
#define s6_addr32 __u6_addr.__u6_addr32
|
||||
#endif
|
||||
#endif
|
||||
|
||||
extern local_addr * local_addrs;
|
||||
|
||||
/*
|
||||
/*
|
||||
* connection-inode table. takes information from /proc/net/tcp.
|
||||
* key contains source ip, source port, destination ip, destination
|
||||
* key contains source ip, source port, destination ip, destination
|
||||
* port in format: '1.2.3.4:5-1.2.3.4:5'
|
||||
*/
|
||||
std::map <std::string, unsigned long> conninode;
|
||||
@@ -179,12 +185,16 @@ void refreshconninode ()
|
||||
//delete conninode;
|
||||
//conninode = new HashTable (256);
|
||||
|
||||
if (! addprocinfo ("/proc/net/tcp"))
|
||||
{
|
||||
std::cout << "Error: couldn't open /proc/net/tcp\n";
|
||||
exit(0);
|
||||
}
|
||||
addprocinfo ("/proc/net/tcp6");
|
||||
#if defined(__APPLE__)
|
||||
addprocinfo("net.inet.tcp.pcblist");
|
||||
#else
|
||||
if (! addprocinfo ("/proc/net/tcp"))
|
||||
{
|
||||
std::cout << "Error: couldn't open /proc/net/tcp\n";
|
||||
exit(0);
|
||||
}
|
||||
addprocinfo ("/proc/net/tcp6");
|
||||
#endif
|
||||
|
||||
//if (DEBUG)
|
||||
// reviewUnknown();
|
||||
|
||||
@@ -225,7 +225,9 @@ struct prg_node * findPID (unsigned long inode)
|
||||
return node;
|
||||
}
|
||||
|
||||
reread_mapping();
|
||||
#ifndef __APPLE__
|
||||
reread_mapping();
|
||||
#endif
|
||||
|
||||
struct prg_node * retval = inodeproc[inode];
|
||||
if (bughuntmode)
|
||||
|
||||
24
nethogs.cpp
24
nethogs.cpp
@@ -128,10 +128,18 @@ int process_tcp (u_char * userdata, const dp_header * header, const u_char * m_p
|
||||
switch (args->sa_family)
|
||||
{
|
||||
case (AF_INET):
|
||||
packet = new Packet (args->ip_src, ntohs(tcp->source), args->ip_dst, ntohs(tcp->dest), header->len, header->ts);
|
||||
#ifdef __APPLE__
|
||||
packet = new Packet (args->ip_src, ntohs(tcp->th_sport), args->ip_dst, ntohs(tcp->th_dport), header->len, header->ts);
|
||||
#else
|
||||
packet = new Packet (args->ip_src, ntohs(tcp->source), args->ip_dst, ntohs(tcp->dest), header->len, header->ts);
|
||||
#endif
|
||||
break;
|
||||
case (AF_INET6):
|
||||
packet = new Packet (args->ip6_src, ntohs(tcp->source), args->ip6_dst, ntohs(tcp->dest), header->len, header->ts);
|
||||
#ifdef __APPLE__
|
||||
packet = new Packet (args->ip6_src, ntohs(tcp->th_sport), args->ip6_dst, ntohs(tcp->th_dport), header->len, header->ts);
|
||||
#else
|
||||
packet = new Packet (args->ip6_src, ntohs(tcp->source), args->ip6_dst, ntohs(tcp->dest), header->len, header->ts);
|
||||
#endif
|
||||
break;
|
||||
}
|
||||
|
||||
@@ -162,10 +170,18 @@ int process_udp (u_char * userdata, const dp_header * header, const u_char * m_p
|
||||
switch (args->sa_family)
|
||||
{
|
||||
case (AF_INET):
|
||||
packet = new Packet (args->ip_src, ntohs(udp->source), args->ip_dst, ntohs(udp->dest), header->len, header->ts);
|
||||
#ifdef __APPLE__
|
||||
packet = new Packet (args->ip_src, ntohs(udp->uh_sport), args->ip_dst, ntohs(udp->uh_dport), header->len, header->ts);
|
||||
#else
|
||||
packet = new Packet (args->ip_src, ntohs(udp->source), args->ip_dst, ntohs(udp->dest), header->len, header->ts);
|
||||
#endif
|
||||
break;
|
||||
case (AF_INET6):
|
||||
packet = new Packet (args->ip6_src, ntohs(udp->source), args->ip6_dst, ntohs(udp->dest), header->len, header->ts);
|
||||
#ifdef __APPLE__
|
||||
packet = new Packet (args->ip6_src, ntohs(udp->uh_sport), args->ip6_dst, ntohs(udp->uh_dport), header->len, header->ts);
|
||||
#else
|
||||
packet = new Packet (args->ip6_src, ntohs(udp->source), args->ip6_dst, ntohs(udp->dest), header->len, header->ts);
|
||||
#endif
|
||||
break;
|
||||
}
|
||||
|
||||
|
||||
@@ -29,7 +29,11 @@
|
||||
#include <arpa/inet.h>
|
||||
#include <cassert>
|
||||
#include <cstring>
|
||||
#include <malloc.h>
|
||||
#ifdef __APPLE__
|
||||
#include <sys/malloc.h>
|
||||
#else
|
||||
#include <malloc.h>
|
||||
#endif
|
||||
#include <iostream>
|
||||
|
||||
#define _BSD_SOURCE 1
|
||||
|
||||
@@ -25,7 +25,11 @@
|
||||
#include "packet.h"
|
||||
#include <netinet/tcp.h>
|
||||
#include <netinet/in.h>
|
||||
#include <malloc.h>
|
||||
#ifdef __APPLE__
|
||||
#include <sys/malloc.h>
|
||||
#else
|
||||
#include <malloc.h>
|
||||
#endif
|
||||
#include <cassert>
|
||||
#include <net/if.h>
|
||||
#include <net/ethernet.h>
|
||||
|
||||
24
process.cpp
24
process.cpp
@@ -24,7 +24,9 @@
|
||||
#include <strings.h>
|
||||
#include <string>
|
||||
#include <ncurses.h>
|
||||
#include <asm/types.h>
|
||||
#ifndef __APPLE__
|
||||
#include <asm/types.h>
|
||||
#endif
|
||||
#include <sys/types.h>
|
||||
#include <sys/stat.h>
|
||||
#include <unistd.h>
|
||||
@@ -215,34 +217,36 @@ Process * getProcess (Connection * connection, const char * devicename)
|
||||
// no? refresh and check conn/inode table
|
||||
if (bughuntmode)
|
||||
{
|
||||
std::cout << "? new connection not in connection-to-inode table before refresh.\n";
|
||||
std::cout << "? new connection not in connection-to-inode table before refresh.\n";
|
||||
}
|
||||
// refresh the inode->pid table first. Presumably processing the renewed connection->inode table
|
||||
// refresh the inode->pid table first. Presumably processing the renewed connection->inode table
|
||||
// is slow, making this worthwhile.
|
||||
// We take the fact for granted that we might already know the inode->pid (unlikely anyway if we
|
||||
// We take the fact for granted that we might already know the inode->pid (unlikely anyway if we
|
||||
// haven't seen the connection->inode yet though).
|
||||
reread_mapping();
|
||||
#ifndef __APPLE__
|
||||
reread_mapping();
|
||||
#endif
|
||||
refreshconninode();
|
||||
inode = conninode[connection->refpacket->gethashstring()];
|
||||
if (bughuntmode)
|
||||
{
|
||||
if (inode == 0)
|
||||
{
|
||||
std::cout << ":( inode for connection not found after refresh.\n";
|
||||
std::cout << ":( inode for connection not found after refresh.\n";
|
||||
}
|
||||
else
|
||||
{
|
||||
std::cout << ":) inode for connection found after refresh.\n";
|
||||
std::cout << ":) inode for connection found after refresh.\n";
|
||||
}
|
||||
}
|
||||
#if REVERSEHACK
|
||||
if (inode == 0)
|
||||
{
|
||||
/* HACK: the following is a hack for cases where the
|
||||
* 'local' addresses aren't properly recognised, as is
|
||||
/* HACK: the following is a hack for cases where the
|
||||
* 'local' addresses aren't properly recognised, as is
|
||||
* currently the case for IPv6 */
|
||||
|
||||
/* we reverse the direction of the stream if
|
||||
/* we reverse the direction of the stream if
|
||||
* successful. */
|
||||
Packet * reversepacket = connection->refpacket->newInverted();
|
||||
inode = conninode[reversepacket->gethashstring()];
|
||||
|
||||
Reference in New Issue
Block a user