0

I am developing a simple gossip udp system for a college project where end users should first initialize their own peer network configuration (ip:port) and also set up the network configuration for two neighbours. Only afterwards they are able to search for a specific file present within the system.

There are two kinds of messages exchanged between these peers: SEARCH messages which represent a forwarded request from the original peer to another until the requested file is found or all peers are reached. RESPONSE messages which represent when a file from a specific request is found and should be forwarded directly to the original requestor.

There are two threads to handle the exchange of messages between each peer. One should constantly be on the lookout for any incoming SEARCH messages and runs right after the user initializes their own peer and their neighbours' network configuration, while the other should lookout only once for an incoming RESPONSE message and runs right after the user enters the name of the requested file to be searched for. This latter should also includes a timeout feature if there is no response for ten seconds.

Even though both are similar, to fulfill the timeout behavior I have tried to create two isolated threads, one to continuously receive any incoming SEARCH messages and the other to run just once to receive only one incoming RESPONSE message.

The issue happens when the timeout feature comes into play. I have tried using peerSocket.setSoTimeout(10000) into the RESPONSE thread and it gets stuck there and doesn't move on to the next line.

However, strange enough, when I move this exact method within the SEARCH thread, it works fine. I really don't know if this has to do with the fact that both are using the same socket.

I would really appreciate some advice into this.

SEARCH THREAD:

public static class receiveSearchMessage extends Thread {
        public void run() {
            // Repeats the operation...
            while (true) {

                //Packet generation
                Gson gson = new Gson();

                byte[] recBuffer = new byte[1024];

                DatagramPacket recPkt = new DatagramPacket(recBuffer, recBuffer.length);

                //Awaiting for any incoming search messages from other peers
                try {
                    peerSocket.receive(recPkt);
                } catch (IOException e) {
                    // TODO Auto-generated catch block
                    e.printStackTrace();
                }

                String msg = new String(recPkt.getData(), recPkt.getOffset(), recPkt.getLength());

                receivedMessage = gson.fromJson(msg, Message.class);
            }
        }
    }

RESPONSE THREAD:

public static class receiveResponseMessage extends Thread {
        public void run() {
            Gson gson = new Gson();

            byte[] recBuffer = new byte[1024];

            DatagramPacket recPkt = new DatagramPacket(recBuffer, recBuffer.length);

            //Awaiting for an incoming response message from other peer
            try {
                peerSocket.setSoTimeout(10000);
                peerSocket.receive(recPkt);
                peerSocket.setSoTimeout(0);
            } catch (SocketTimeoutException e) {
                System.out.println("No one in the system has the file [" + fileName + "]");
                return;
            } catch (IOException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            } 

            String msg = new String(recPkt.getData(), recPkt.getOffset(), recPkt.getLength());

            receivedMessage = gson.fromJson(msg, Message.class);

        }
    }
JOC
  • 73
  • 5

1 Answers1

0

Your code is not complete, but my guess is that peerSocket is the same DatagranSocket in both threads?

If so, the receiveSearchMessage thread is liable to be consuming messages that you are wanting receiveResponseMessage to consume.

Some possible ways to handle this are:

  • have two distinct sockets listening on different ports, OR
  • have a single thread that receives all messages, works out what that they are and hands them off to other threads to process, OR
  • have a single thread that receives and processes all message.

Unfortunately, your problem description is rather unclear and it is therefore difficult to work out which (if any) of the above is a correct solution.

However, if you have two threads receiving from the same socket with no kind of coordination, you can never be sure that the right threads will get the right messages. So what you are currently doing is wrong ... assuming they are both using the same port.

Stephen C
  • 698,415
  • 94
  • 811
  • 1,216