Con la transmisión, el cliente envía un mensaje a todos en la red y todos los servidores responden. Con la multidifusión, usted define una dirección de grupo de multidifusión y todos los servidores se suscriben a ella. El cliente luego envía un mensaje al grupo, los servidores que se han suscrito lo reciben y responden.
La multidifusión es cuando un remitente desea enviar a un grupo de receptores, como cuando un cliente del juego quiere enviar a un grupo (potencial) de servidores. Las direcciones de multidifusión son direcciones especiales donde el sistema sabe tratarlas de manera diferente. El receptor le dice al sistema que desea recibir mensajes enviados a un grupo en particular, y el remitente envía un mensaje a la dirección del grupo. En una LAN esto simplemente funciona. En las LAN necesita un enrutamiento de multidifusión que no se implementa en la mayoría de las redes. Pero la transmisión tampoco funcionaría en las LAN.
El uso de multidifusión asegura que solo los sistemas en la red que se preocupan por recibir el mensaje lo reciban.
La forma de implementar esto depende del lenguaje de programación, etc.
La estructura de una dirección de multidifusión IPv6 es la siguiente:
- Siempre comienza con los primeros 8 bits de la dirección establecida en 1, lo que significa que los dos primeros caracteres de la dirección serán
ff
;
- El tercer carácter (bits 9 a 12) en la dirección especifica banderas. En su caso, probablemente desee una dirección de multidifusión fija para su aplicación. En ese caso, el tercer carácter será un
0
que indica una dirección de multidifusión asignada permanentemente;
- El cuarto carácter (bits 13 a 16) determina el alcance de la dirección. Probablemente usará el valor
2
para el ámbito de enlace local (LAN).
Juntos, esto significa que usará una dirección que comience con ff02:
.
Las direcciones de multidifusión son asignadas por IANA. RFC3307 define cómo hacerlo (el criterio es Expert Review, por lo que no es necesario escribir un RFC sobre lo que está haciendo ni nada de eso). En esta respuesta, usaré la dirección de multidifusión ff02::db8:aa:bb
, que se encuentra en el bloque reservado para la documentación.
No tiene que tener acceso de root para usar la multidifusión. Los siguientes ejemplos de Python3.3 se pueden ejecutar con una cuenta de usuario normal:
El servidor (escuchando en la dirección de multidifusión):
#!/usr/bin/env python3.3
import socket
import struct
if_idx = socket.if_nametoindex('en0')
addr = 'ff02::db8:aa:bb'
port = 42424
group = socket.inet_pton(socket.AF_INET6, addr) + struct.pack("I", if_idx)
sock = socket.socket(socket.AF_INET6, socket.SOCK_DGRAM)
sock.setsockopt(socket.IPPROTO_IPV6, socket.IPV6_JOIN_GROUP, group)
sock.bind(('::', port))
while True:
msg, sender = sock.recvfrom(1024)
print('Received "%s" from "%s"' % (str(msg, 'UTF-8'), sender))
sock.sendto(bytes('Received %d bytes from you' % len(msg), 'UTF-8'), sender)
Y el cliente (enviando al grupo de multidifusión y escuchando las respuestas):
#!/usr/bin/env python3.3
import socket
if_idx = socket.if_nametoindex('en0')
addr = 'ff02::db8:aa:bb'
port = 42424
sock = socket.socket(socket.AF_INET6, socket.SOCK_DGRAM)
sock.setsockopt(socket.IPPROTO_IPV6, socket.IPV6_MULTICAST_IF, if_idx)
sock.sendto(bytes('Hello there!', 'UTF-8'), (addr, port))
while True:
# You probably wait a certain time for replies, not indefinitely like this example
msg, sender = sock.recvfrom(1024)
print('Received "%s" from "%s"' % (str(msg, 'UTF-8'), sender))
Usé Python 3.3 porque las versiones anteriores no tienen socket.if_nametoindex
, pero todo lo demás también debería funcionar en Python 2.
PD: usar una biblioteca o marco existente para el descubrimiento de servicios como se sugiere en otra respuesta es una buena idea. Utilizará multidifusión bajo el capó, pero le ahorrará tener que diseñar e implementar su propio protocolo.