I will start by saying that I'm not absolutely a network expert. I'm trying to create a UDP multicast socket system with four RaspBerry Pi model B. Into each Rpi is running a listening script (I will call it "listen.py") socket client.
Case 1 - I'm perfectly able to send datagram if I run the socket server (I will call it "server.py") directly inside of the Rpi (by SSH, with my laptop as well).
I have: -listen.py on boot of the Rpi (here I create a socket client); -I run the server.py (the server.py is obviously into the Rpi) In this case I receive answer from all 4 Rpi that joined the multicast group (224.1.1.1)
Case 2 - I created a socket server java and a socket client python in my laptop and everything works perfectly (same code, same multicast group, same multicast port).I tried also without multicast using just 'localhost' and everything works as well. With netstat I can see multicast group and port.
netstat -lu
Active Internet connections (only servers)
Proto Recv-Q Send-Q Local Address Foreign Address State
udp 0 0 224.1.1.1:21581 *:* //MulticastGroupIp:Port
udp 0 0 192.168.1.103:ntp *:* //Static ip of one Rpi
udp 0 0 *:ntp *:*
My problem is that if I run the server.py from my laptop (no SSH) I have no answer from the listen.py, socket client, which is running into the Rpi. I absolutely need to send datagram from my laptop (I want a java class) to the 4 Rpi.
I have excluded the possibilities of bad code, wrong multicast ip group, wrong multicast port group. Firewall is off in my laptop and in the router as well. The parameter net.ipv4.ip_forward on the Rpi is 1. I know that UDP is unreliable but here I'm speaking about 100% of the datagram lost. IGMP is enabled on my D-Link router. I have the same problem with Ethernet and WiFi configuration.
I really need other ideas.....So I tried to write here. Sorry, this is my first post and I'm newbie a bit of everything. I will appreciate any suggestion. Probably it's something stupid that I can't understand.
Maybe some problems with the routing table???? This is mine:
route
Kernel IP routing table
Destination Gateway Genmask Flags Metric Ref Use Iface
default D-Link.Home 0.0.0.0 UG 0 0 0 wlan0
192.168.1.0 * 255.255.255.0 U 0 0 0 wlan0
Thanks in advance
For me the code works well and the problem is not there but if can be useful to understand better the situation.....
Code of server.py (useless to say that I have python installed in my machine with Windows 7):
import socket
import sys
# import time
print 'message:'
n = sys.stdin.readline()
n = n.strip('\n')
MCAST_GRP = '224.1.1.1'
MCAST_PORT = 21581
sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM, socket.IPPROTO_UDP)
sock.setsockopt(socket.IPPROTO_IP, socket.IP_MULTICAST_TTL, 2)
sock.sendto(n, (MCAST_GRP, MCAST_PORT))
or with java (It's exactly what I want...a server socket java but at the moment it's not the priority):
public class PythonScriptScan {
private static int portMulticasting = 21581;
// private boolean broadcast = true;
private DatagramSocket socket;
private String groupMulticast = "224.1.1.1"; // group address
private int delay = 3000;
public PythonScriptScan() {
try {
socket = new DatagramSocket();
} catch (SocketException e) {
e.printStackTrace();
System.exit(1);
}
}
public void start(String agentName) {
try {
InetAddress group = InetAddress.getByName(groupMulticast);
@SuppressWarnings("resource")
MulticastSocket s = new MulticastSocket(portMulticasting);
s.joinGroup(group);
// while (broadcast) {
byte[] buf = new byte[10240];
buf = agentName.getBytes();
DatagramPacket packet = new DatagramPacket(buf, buf.length, group, portMulticasting);
System.out.println(packet);
socket.send(packet);
// OK, I'm done talking - leave the group...
s.leaveGroup(group);
try {
Thread.sleep(delay);
} catch (InterruptedException e) {
System.exit(0);
}
// }
socket.close();
} catch (IOException e) {
e.printStackTrace();
}
}
public static void main(String[] args) throws IOException {
System.out.println("Insert Message");
@SuppressWarnings("resource")
Scanner sc = new Scanner(System.in);
String agentName = sc.nextLine();
PythonScriptScan agent = new PythonScriptScan();
agent.start(agentName);
}
and listen.py (It's running on boot in each Rpis, the configuration that I want is with Ethernet, each Rpis has a static ip and they are connected properly with my D-link router):
#!/usr/bin/python
import socket
import struct
import fcntl
import subprocess
import sys
import errno
import time
import os
# Create the socket
MCAST_GRP = "224.1.1.1"
MCAST_PORT = 21581
try:
sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM, socket.IPPROTO_UDP)
except socket.error, msg:
print 'Could not create socket. Error code: ' + str(msg[0]) + ' , Error message : ' + msg[1]
sock.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
# Bind to the server address
# sock.bind(('', MCAST_PORT))
sock.bind((MCAST_GRP, MCAST_PORT))
# Tell the operating system to add the socket to the multicast group on all interfaces
mreq = struct.pack('4sl', socket.inet_aton(MCAST_GRP), socket.INADDR_ANY)
sock.setsockopt(socket.IPPROTO_IP, socket.IP_ADD_MEMBERSHIP, mreq)
# Receive loop
try:
while True:
print >>sys.stderr, '\nWAITING TO RECEIVE MESSAGE'
d = sock.recvfrom(10240)
data = d[0]
addr = d[1]
print data.strip(), addr
finally:
print >>sys.stderr, 'closing socket'
sock.close()