I would like to keep track of the processes that initiate outbound connections on a Linux desktop. The best I can come up with is this:
iptables -A OUTPUT -m state --state NEW -j LOG --log-uid
This logs the uid/gid that initiates the connection, but not the process/command name or even the pid. If I could just get the pid, I could probably whip up a script that pulls the process name when the log is written, but it seems like that is not even possible.
Ideally I'd also like to log the processes that accept incoming connections too.
Any ideas how this might be possible with iptables [or anything else] on a Linux box?
Best Answer
You could write a program to monitor /proc/net/tcp, whose output looks like this:
You can then relate opened ports to inodes, which can be related back to processes and file descriptors by doing readlink on the file descriptors listed for each process:
See here that inode 4847458 corresponds to the first tcp socket in the list above. The output of netstat -tapn verifies this for me (and recall that 0x50 == 80):
When the monitor program notices a change in /proc/net/tcp, parse the data and determine if the change is a newly opened socket. Then you could just enumerate all the file descriptors for each process listed in /proc, doing readlink on each on to find the matching inode. Once you find that, you have the owning pid, from which you can get anything else you might want, particularly if you have process accounting on.
If you don't need your notification to be instantaneous, then your monitor program could use a slow poll (perhaps a period of 50ms or 100ms, or even 1000ms).