On one of my systems at work good ol' netstat shows multicast group membership information, and ss is missing a couple. I wonder why. For example:
[root@myhost ~]# netstat -gn | egrep "Inter|239.192"
Interface RefCnt Group
em4.204 1 239.192.33.183
em1.16 2 239.192.35.1
em1.16 2 239.192.12.98
em1.16 1 239.192.32.1
[root@myhost ~]# ss -apu | egrep "State|239.192"
State Recv-Q Send-Q Local Address:Port Peer Address:Port
UNCONN 0 0 239.192.35.1:12965 *:*
UNCONN 0 0 239.192.12.98:12965 *:*
UNCONN 0 0 239.192.35.1:12965 *:*
UNCONN 0 0 239.192.12.98:12965 *:*
Notice that ss shows only those groups with a RefCnt of 2.
Technically, ip maddr show
is the replacement for netstat -gn
but it doesn't include the RefCnt, and its output is more cumbersome. Also, we're interested in the more detailed output of ss which can include the PID of the listening processes (not seen here because no processes are actually currently listening to the multicast, as show by netstat -ulpn
:
[root@myhost ~]# netstat -ulpn | egrep "Proto|239.192"
Proto Recv-Q Send-Q Local Address Foreign Address State PID/Program name
udp 0 0 239.192.35.1:12965 0.0.0.0:* -
udp 4480 0 239.192.12.98:12965 0.0.0.0:* -
udp 0 0 239.192.35.1:12965 0.0.0.0:* -
udp 0 0 239.192.12.98:12965 0.0.0.0:* -
(I encountered this question looking for an answer to a similar one, which is how to list processes that joined a particular multicast group...)
netstat -gn
and ip maddr
show multicast groups what are joined by the network interface, which roughly means that packets destined to the addresses will be accepted on the interface.
netstat -nau | grep (…)
and ss -au src 224.0.0.0/4
(notice the fancy filter in ss
) will display the sockets bound to multicast addresses.
These are two different and somewhat unrelated things.
Just binding a socket to a multicast address so that it shows up in ss
/ netstat
is fine, but it will not join the multicast group automatically.
Try: socat udp4-l:12345,bind=239.1.2.3 -
, which shows up in netstat as:
Proto Recv-Q Send-Q Local Address Foreign Address State PID/Program name
udp 0 0 239.1.2.3:12345 0.0.0.0:* 7604/socat
and such connection is completely useless until one joins the group – netstat -g
and ip maddr
do not mention this address.
To receive a multicast message, you do not need to bind to a multicast address.
Try this: socat udp4-listen:12345,ip-add-membership=239.1.2.3:br0 -
Until you get a message, you show up in netstat as:
Proto Recv-Q Send-Q Local Address Foreign Address State PID/Program name
udp 0 0 0.0.0.0:12345 0.0.0.0:* 6132/socat
Once you get a first message, you show up as:
Proto Recv-Q Send-Q Local Address Foreign Address State PID/Program name
udp 0 0 10.0.0.2:12345 10.0.0.3:52036 ESTABLISHED 6132/socat
Notice that there is no mention of the multicast group you joined in the socket description, despite the multicast is running just fine.
To see the multicast groups, you can use either netstat -g
IPv6/IPv4 Group Memberships
Interface RefCnt Group
--------------- ------ ---------------------
br0 1 239.1.2.3
or ip maddr
:
7: br0
link 01:00:5e:01:02:03
inet 239.1.2.3
(Only relevant lines are shown here.)
The API of joining a multicast group is actually setting a socket option 'IP_ADD_MEMBERSHIP'. To get a multicast message two things must batch: ① the port to which the socket is bound (as in bind(…)
function), and ② IP any of the joined groups on the specified interface.
(The socat above uses a pseudoconnection mode for UDP; you can also try a conectionless mode by e.g., socat UDP-DATAGRAM:10.0.0.4:3000,bind=10.0.0.2:2000,ip-add-membership=239.1.2.3:br0 -
which sends to 10.0.0.4:3000 and receives on both 10.0.0.2:2000 and 239.1.2.3:2000%br0, and always displays as the first netstat output)
As I tested today, if multiple programs join the same group, you'd see a use count in ip maddr
:
7: br0
link 01:00:5e:01:02:03 users 2
inet 239.1.2.3 users 2
which means it now displays the RefCnt provided it's greater than 1.
(You might need the reuseaddr option to test that with socat.)