How to get the real listener PID in AIX 7.1? Shouldn't rmsock
work as widely described on the internet?
https://www-01.ibm.com/support/docview.wss?uid=isg3T1019570
The case:
There is a program that implements both server and client protocols which is chosen by arguments at runtime. Like as:
$ myprogram -switcher-mode:port
$ myprogram -provider-mode:port
As soon as the listener is launched we can get its PID using rmsock
. Let's assume an arbitrary port number of 40000:
$ netstat -Aan | grep '\.40000.*LISTEN$' | awk '{ print $1 }' | xargs -n1 -i rmsock {} tcpcb
The socket 0xf1000e000334b808 is being held by proccess 10683226 (serviceprg)
$ ps -fp 10683226
UID PID PPID C STIME TTY TIME CMD
test 10683226 1 0 08:17:43 - 2 serviceprg -switcher-mode:40000
We can see that it's the correct process, the switcher that listen to the port: serviceprg -switcher-mode:40000.
When the problem begins:
As soon as we start new processes (in background) in provider mode, the rmsock
might return their PID as if they were the listener (it's randomly). However those processes may be launched from two ways, manually and automatically (both ways cause the issue) by the switcher when it "feels" that it needs more providers to perform the burst of requests, so it launches more providers using the libc.a
function system()
like this:
system("serviceprg -provider-mode:40000 1>/dev/null 2>/dev/null &");
So, when we check the lister PID using rmsock
it might returns the wrong PID, like as:
$ netstat -Aan | grep '\.40000.*LISTEN$' | awk '{ print $1 }' | xargs -n1 -i rmsock {} tcpcb
The socket 0xf1000e000334b808 is being held by proccess 10690461 (serviceprg)
$ ps -fp 10690461
UID PID PPID C STIME TTY TIME CMD
test 10690461 1 0 08:20:04 - 1:10 serviceprg -provider-mode:40000
Check that the program being run for that PID is a process launched after the real listener, and it doesn't listen to the port but connects to it as a client program: serviceprg -provider-mode:40000
When we kill that process, let's say the above PID 10690461, rmsock
shifts and might answer another process as the listener wrongly (or the real one, this behaviour seems to be random), when you kill every client connected to that port, then rmsock
will always return the correct PID of the real listener.
Just in case you want to know a bit more about its architecture: Other programs connect to that port asking for services, the listener is a switcher that delivers each client request to a instance of the program that provides the service, but it's in that case the same program and it connects to the same port, look at the following diagram:
netstat
output for: port + the "LISTEN" word at the end of the line ("LISTEN$"). That's why we get only one, but thermsock
points the listener socket to the wrong process (sometimes). The fullnetstat
output grepping only the port number is huge with all sort of statuses (ESTABLISHED, TIME_WAIT and the desired one: LISTEN)