Beefy Boxes and Bandwidth Generously Provided by pair Networks
Clear questions and runnable code
get the best and fastest answer
 
PerlMonks  

Same multicast packet received by multiple NICs

by sophate (Beadle)
on Jun 01, 2012 at 17:08 UTC ( [id://973818]=perlquestion: print w/replies, xml ) Need Help??

sophate has asked for the wisdom of the Perl Monks concerning the following question:

Hi Monks,

I have a server that has two NICs, eth1(192.168.0.1) and eth2(192.168.1.1). Each NIC can receive the same multicast packets to 224.10.10.10:12345. The multicast traffic to the two NICs are via two ISOLATED routing paths to provide resiliency. I'm writing a Perl program to monitor the multicast traffic via each NIC. The idea is that if I don't get any multicast packets from a NIC, I can suspect there is something wrong with that multicast path. A sample program with IO::Socket::Multicast is shown below.

The problem is that if NIC1 receives packet A and NIC2 receives packet A', the recv() call of both threads gets both A and A'! This defeat the purpose that if one mcast path is down, recv() returns nothing for the socket associated with the NIC connected to the mcast path with problem coz recv() can still get data from the NIC without issue. Any one can shred some light on why the sockets gets the data from all the NICs?

#!/usr/bin/perl -w use warnings; use strict; use IO::Socket::Multicast; use threads; use threads::shared; my $thread1 = threads->create(\&MulticastListen, '192.168.0.1'); $thread1->detach(); my $thread2 = threads->create(\&MulticastListen, '192.168.1.1'); $thread2->detach(); while (1) { # Some codes here } ################# ## Subroutines ## ################# sub MulticastListen { my $interfaceIP = shift; my $Socket = IO::Socket::Multicast->new( LocalPort => '12345', LocalAddr => '224.10.10.10', ReuseAddr => 1 ); $Socket->mcast_add('224.10.10.10', $interfaceIP ); while (1) { $Socket->recv( $Data, 1024 ); print "[$Data]\n"; } }

Replies are listed 'Best First'.
Re: Same multicast packet received by multiple NICs
by BrowserUk (Patriarch) on Jun 01, 2012 at 20:22 UTC

    I've no experience of using IO::Socket::Multicast, but all the examples supply Proto => 'udp' on the constructor -- you do not.

    Looking at the source, it does add that parameter on the consructor, but only if *no parameters* are supplied.

    It also adds it to the parameter list in the configure method before passing through to the SUPER->configure method, but only if the Proto attribute does not already exist; and as you do not call that method directly, it is unclear to me whether it will get added if you supply some parameters to new() but not that one.

    Soemthing to consider.

    Also, you appear to be using the server address as the LocalAddr parameter of the constructor rather than the PeerAddr, which looks wrong to me; but (again), I've never used the module.


    With the rise and rise of 'Social' network sites: 'Computers are making people easier to use everyday'
    Examine what is said, not who speaks -- Silence betokens consent -- Love the truth but pardon error.
    "Science is about questioning the status quo. Questioning authority".
    In the absence of evidence, opinion is indistinguishable from prejudice.

    The start of some sanity?

      thanks for the reply. The socket is associated with the right NIC. From the results of "netstat -g", if can see the sockets bind to the correct NICs. I don't think "Proto => 'udp'" matters here as it is udp by default for the IO::Socket::Multicast constructor. By using tcpdump, I can see the traffic I expected, i.e. if one path is having issue, no results from tcpdump. But the recv call stills get the data from another NIC that is getting mcast packets!

      I suspect this is an issue with "sockets" as I have another multicast client "mdump"(written in C, https://community.informatica.com/solutions/1470) behaves the same way!

Re: Same multicast packet received by multiple NICs
by Illuminatus (Curate) on Jun 01, 2012 at 22:51 UTC
    I also caveat that I've never used this module before. You could try specifying the interface device rather than the IP assigned to it, but since mcast_add just uses that to lookup the device IP, I can't see that it would make any difference.

    If I want to see what's appearing on the NIC, I lean towards going to the source. You can use Net::Pcap with a compiled filter to get what you're looking for -- no pesky network stack mucking things up :)

    fnord

      Thanks but I don't think the interface device name or IP matters here. Actually I'm using the workaround to use Perl sockets to listen to the mcast from the NICs then create additional threads to monitor the traffic with tcpdump. It looks clumsy but it works. However, I still have no clue why recv() of a socket mapped to a particular NIC can receives data from ALL NICs listening to the same mcast address:port.

        It may depend on your OS. This module creates a socket of type SOCK_DGRAM. These route at the IP/UDP level. I know the module says it can limit you to what's on one NIC, but I'm pretty sure on Linux there's no way to enforce this. The point of multicast is to deliver to every endpoint using that destination address. Maybe the Windows stack has hooks to limit this. I am curious as to why you need to listen for the mcast traffic on a socket if you're using tcpdump to see them as well. You can pass a filter to tcpdump to only see what you're looking for.

        fnord

Log In?
Username:
Password:

What's my password?
Create A New User
Domain Nodelet?
Node Status?
node history
Node Type: perlquestion [id://973818]
Approved by MidLifeXis
Front-paged by MidLifeXis
help
Chatterbox?
and the web crawler heard nothing...

How do I use this?Last hourOther CB clients
Other Users?
Others cooling their heels in the Monastery: (3)
As of 2024-03-28 15:20 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    No recent polls found