Linux Kernel ne passe pas par des packages UDP multidiffusion

Récemment, j'ai mis en place un nouveau Serveur Ubuntu 10.04 et je remarque que mon server UDP ne peut plus voir de données de multidiffusion envoyées à l'interface, même après avoir rejoint le groupe de multidiffusion. J'ai exactement la même configuration sur deux autres machines Ubuntu 8.04.4 LTS et il n'y a pas de problème à recevoir des données après avoir adhéré au même groupe de multidiffusion.

La carte ethernet est un Broadcom netXtreme II BCM5709 et le pilote utilisé est:

b $ ethtool -i eth1 driver: bnx2 version: 2.0.2 firmware-version: 5.0.11 NCSI 2.0.5 bus-info: 0000:01:00.1 

J'utilise smcroute pour gérer mes loggings multidiffusion.

 b$ smcroute -d b$ smcroute -j eth1 233.37.54.71 

Après avoir rejoint le groupe ip maddr affiche l'logging nouvellement ajouté.

 b$ ip maddr 1: lo inet 224.0.0.1 inet6 ff02::1 2: eth0 link 33:33:ff:40:c6:ad link 01:00:5e:00:00:01 link 33:33:00:00:00:01 inet 224.0.0.1 inet6 ff02::1:ff40:c6ad inet6 ff02::1 3: eth1 link 01:00:5e:25:36:47 link 01:00:5e:25:36:3e link 01:00:5e:25:36:3d link 33:33:ff:40:c6:af link 01:00:5e:00:00:01 link 33:33:00:00:00:01 inet 233.37.54.71 <------- McastGroup. inet 224.0.0.1 inet6 ff02::1:ff40:c6af inet6 ff02::1 

Jusqu'à présent, bon, je peux voir que je reçois des données pour ce groupe de multidiffusion.

 b$ sudo tcpdump -i eth1 -s 65534 host 233.37.54.71 tcpdump: verbose output suppressed, use -v or -vv for full protocol decode listning on eth1, link-type EN10MB (Ethernet), capture size 65534 bytes 09:30:09.924337 IP 192.164.1.120.58848 > 233.37.54.71.15572: UDP, length 212 09:30:09.947547 IP 192.164.1.120.58848 > 233.37.54.71.15572: UDP, length 212 09:30:10.108378 IP 192.164.1.120.58866 > 233.37.54.71.15574: UDP, length 268 09:30:10.196841 IP 192.164.1.120.58848 > 233.37.54.71.15572: UDP, length 212 ... 

Je peux également confirmer que l'interface reçoit des packages mcast.

 b $ ethtool -S eth1 | grep mcast_pack rx_mcast_packets: 103998 tx_mcast_packets: 33 

Maintenant, voici le problème. Lorsque j'essaie de capturer le trafic à l'aide d'un simple server Ruby UDP, je reçois des données nulles! Voici un server simple qui lit l'envoi de données sur le port 15572 et imprime les deux premiers caractères. Cela fonctionne sur les deux 8.04.4 Ubuntu Servers, mais pas sur le server 10.04.

 require 'socket' s = UDPSocket.new s.bind("", 15572) 5.times do text, sender = s.recvfrom(2) puts text end 

Si j'envoie un package UDP conçu dans ruby ​​à localhost, le server le reçoit et imprime les deux premiers caractères. Je sais donc que le server ci-dessus fonctionne correctement.

 irb(main):001:0> require 'socket' => true irb(main):002:0> s = UDPSocket.new => #<UDPSocket:0x7f3ccd6615f0> irb(main):003:0> s.send("I2 XXX", 0, 'localhost', 15572) 

Lorsque je vérifie les statistics du protocole, je vois que InMcastPkts n'augmente pas. Alors que d'autres servers 8.04, sur le même réseau, ont reçu quelques milliers de packages en 10 secondes.

 b $ netstat -sgu ; sleep 10 ; netstat -sgu IcmpMsg: InType3: 11 OutType3: 11 Udp: 446 packets received 4 packets to unknown port received. 0 packet receive errors 461 packets sent UdpLite: IpExt: InMcastPkts: 4654 <--------- Same as below OutMcastPkts: 3426 InBcastPkts: 9854 InOctets: -1691733021 OutOctets: 51187936 InMcastOctets: 145207 OutMcastOctets: 109680 InBcastOctets: 1246341 IcmpMsg: InType3: 11 OutType3: 11 Udp: 446 packets received 4 packets to unknown port received. 0 packet receive errors 461 packets sent UdpLite: IpExt: InMcastPkts: 4656 <-------------- Same as above OutMcastPkts: 3427 InBcastPkts: 9854 InOctets: -1690886265 OutOctets: 51188788 InMcastOctets: 145267 OutMcastOctets: 109712 InBcastOctets: 1246341 

Si j'essaie de forcer l'interface dans le mode promisc, rien ne change.

À ce stade, je suis bloqué. J'ai confirmé que la configuration du kernel a la multidiffusion activée. Peut-être y-a-t-il d'autres options de configuration que je devrais vérifier?

 b $ grep CONFIG_IP_MULTICAST /boot/config-2.6.32-23-server CONFIG_IP_MULTICAST=y 

Des idées sur l'endroit où aller?

5 Solutions collect form web for “Linux Kernel ne passe pas par des packages UDP multidiffusion”

Dans notre cas, notre problème a été résolu par les parameters sysctl, un autre que Maciej.

Veuillez noter que je ne parle pas pour l'OP (buecking), je suis venu sur cette publication en raison du problème lié par les détails de base (pas de trafic de multidiffusion dans userland).

Nous avons une application qui lit datatables envoyées à quatre adresses de multidiffusion et un port unique par adresse de multidiffusion, à partir d'un appareil qui est (généralement) connecté directement à une interface sur le server de réception.

Nous essayions de déployer ce logiciel sur un site client lorsqu'il a échoué mystérieusement sans raison connue. Les tentatives de debugging de ce logiciel ont abouti à l'inspection de chaque appel système, finalement, ils nous ont tous dit la même chose:

Notre logiciel request des données, et l'OS n'en fournit jamais.

Le countur de packages multicast a augmenté, tcpdump a montré que le trafic atteignait la boîte / interface spécifique, mais nous ne pouvions rien faire avec. SELinux était désactivé, iptables fonctionnait mais n'avait aucune règle dans aucune des tables.

Étonné, nous l'étions.

Au fur et à mesure, nous avons commencé à penser aux parameters du kernel que sysctl gère, mais aucune des fonctionnalités documentées n'était particulièrement pertinente, ou si elles concernaient le trafic de multidiffusion, elles étaient activées. Oh, et ifconfig a énuméré "MULTICAST" dans la ligne de fonction (haut, diffusion, exécution, multidiffusion). Par curiosité, nous avons regardé /etc/sysctl.conf . 'et voici, l'image de base de ce client a ajouté quelques lignes supplémentaires en bas.

Dans notre cas, le client avait défini net.ipv4.all.rp_filter = 1 . rp_filter est le filter Route Path, qui (comme je le comprends bien) rejette tout le trafic qui n'aurait pas pu atteindre cette case. Le réseau de sauts de sous-réseau, pensant que l'IP source est faussée.

Eh bien, ce server était sur un sous-réseau 192.168.1 / 24 et l'adresse IP source de l'appliance pour le trafic multicast était quelque part dans le réseau 10. *. Ainsi, le filter empêchait le server de faire quelque chose de significatif avec le trafic.

Quelques réglages approuvés par le client; net.ipv4.eth0.rp_filter = 1 et net.ipv4.eth1.rp_filter = 0 et nous étions en train de fonctionner heureusement.

TL / DR Assurez-vous également que votre multicast ne provient pas d'un vlan. tcpdump -e aiderait à déterminer s'ils le faisaient.

En toute équité, quelqu'un devrait build une page avec une list de contrôle de choses qui peuvent empêcher la multidiffusion d'atteindre l'user. Je me suis heurté à cela pendant quelques jours, et naturellement, rien que je n'ai pu find sur le Web m'a aidé.

Non seulement je pouvais voir les packages dans le tcpdump , mais je pouvais recevoir d'autres packages de multidiffusion, pour d'autres producteurs, juste sur une autre interface. La command que j'ai fini par utiliser pour tester si je peux recevoir une diffusion multiplex était:

 $ GRP=224.xxx # set me to the group $ PORT=yyyy # set me to the receiving port $ IFACE=mmmm # set me to the name or IP address of the interface $ strace -f socat - UDP4-DATAGRAM:$GRP:$PORT,ip-add-membership=$GRP:$IFACE,bind=0.0.0.0:$PORT,multicast-loop=0 

La raison de strace ici est que je ne pouvais pas faire socat imprimer les packages à la stdout, mais dans la sortie strace vous pouvez clairement voir si socat reçoit des données réelles de la prise liée (il sera muet sinon après un couple des appels select initiaux)

  • rp_filter sysctl – ne s'applique pas, les systèmes sont sur le même réseau IP (je les ai mis à 0 tout de même, semble que 1 est un paramètre par défaut maintenant, au less pour Ubuntu).
  • firewalls / etc – le système de réception est sans pare-feu (je ne pense pas que les packages apparaîtront dans tcpdump s'ils étaient par path de fer, mais je suppose que c'est possible si le pare-feu est drôle)
  • Routage IP / Multicast et plusieurs interfaces – J'ai joint explicitement le groupe sur l'interface correcte
  • Wacky réseau de matériel – c'était mon dernier recours, mais changer d'ordinateur portable à un Intel NUC n'a pas aidé. C'est à propos de l'endroit où j'ai commencé à mâcher mes coudes et à me faire passer à SE.
  • Le problème dans mon cas était l'utilisation de VLAN par le matériel spécialisé qui produisait ces packages de multidiffusion. Pour voir si c'est votre problème, assurez-vous d'inclure le -e sur tcpdump et vérifiez les tags vlan. Il faudra configurer une interface dans le vlan correct avant que l'user puisse récupérer ces packages. Le cadeau pour moi en fait était que les producteurs de multidiffusion ne font pas de ping, mais ne vont même pas entrer dans le cache ARP, bien que je puisse clairement voir les réponses ARP.

Pour l'exécuter avec VLAN, ce lien pourrait être utile pour configurer le routing multicast. (Malheureusement, je suis nouveau sur cela, alors la réputation ne me permet pas d'append une réponse. D'où cette édition.)

Voici ce que j'ai fait (utiliser sudo si nécessaire):

 ip link add link eth0 name eth0_100 type vlan id 100 ip addr add 192.168.100.2/24 brd 192.168.100.255 dev eth0_100 ip link set dev eth0_100 up ip maddr add 01:00:5e:01:01:01 dev eth0_100 route -n add -net 224.0.0.0 netmask 240.0.0.0 dev eth0_100 

De cette façon, une interface supplémentaire si créée pour le trafic vlan avec vlan id 100. L'ip vlan pourrait être inutile. Ensuite, une adresse de multidiffusion est configurée pour la nouvelle interface (01: 00: 5e: 01: 01: 01 est l'adresse de la couche de binding pour 239.1.1.1) et tout le trafic de multidiffusion entrant est lié à eth0_100. J'ai également fait toutes les étapes possibles dans les réponses ci-dessus (vérifier iptables, rp_filter etc.).

Vous pouvez essayer d'examiner ces parameters:

proc

 echo "0" > /proc/sys/net/ipv4/icmp_echo_ignore_broadcasts 

sysctl.conf

 sed -i -e 's|^net.ipv4.icmp_echo_ignore_broadcasts =.*|net.ipv4.icmp_echo_ignore_broadcasts = 0|g' /etc/sysctl.conf 

Ceux-ci ont été utilisés pour permettre la multidiffusion dans RHEL.

Vous voudrez peut-être vous assurer que votre pare-feu autorise le trafic mutlicast; à nouveau avec RHEL j'ai activé ce qui suit:

 # allow anything in on multicast addresses -A INPUT -s 224.0.0.0/4 -j ACCEPT -A INPUT -p igmp -d 224.0.0.0/4 -j ACCEPT # needed for multicast ping responses -A INPUT -p icmp --icmp-type 0 -j ACCEPT 

Utilisez-vous un switch managé? Certains ont des options pour empêcher les «tempêtes de diffusion» ou d'autres problèmes de multidiffusion, ce qui pourrait les empêcher d'éviter certains types de packages. Je suggérerais d'examiner la documentation de votre switch.

 s.bind("", 15572) 

Sûr de ""? Pourquoi ne pas utiliser l'adresse IP de multidiffusion à laquelle vous souhaitez vous lier?

  • Demande de réception de Boradcast à partir de différents sous-réseaux
  • Proxy UDP avec des packages clonés
  • Le multidiffusion fonctionne uniquement en mode promiscuous
  • udp à travers nat
  • UDP inondant plusieurs servers
  • Comment puis-je déterminer si mon VPN traverse le trafic UDP?
  • rsyslog udp forwarding tronque à 2048 caractères
  • udp diffusé sur le port 25860
  • Quelles applications basées sur UDP?
  • Dépannage de la multidiffusion UDP sur Windows
  • Renvoi de port pour accéder aux services sur les servers derrière NAT
  • Les astuces du serveur de linux et windows, tels que ubuntu, centos, apache, nginx, debian et des sujets de rĂ©seau.