How to make a queue for a notification for a specific time and run the code depending on whether it receives a notice or not?

advertisements

I'm trying to implement something which is a bit of a variation of UDP.

The server thread receives datagram packets, parses them, and passes them to the appropriate thread. If it receives a message, it replies with an acknowledgement and passes it to the ReceiveMessage Thread which prints it onscreen.

I have a SendMessage Thread and a ReceiveMessage thread.

I want the SendMessage thread to send a packet, and wait for an acknowledgement for a specific timeout period. I want to send a notify() to SendMessage, if the server receives an acknowledgement, and if it doesn't, I want the SendMessage thread to timeout and execute different code in both cases. How can I achieve this?

public class ListenThread extends Thread{

protected DatagramSocket socket = null;
protected Boolean on = true;
protected String id;
protected HashMap <String,Contact> people = null;
protected String user;

public ListenThread(String macadd, String user, HashMap <String, Contact> people) throws SocketException
{
    super("ListenThread");
    this.socket = new DatagramSocket(3333);
    this.id=macadd;
    this.people = people;
    this.user = user;
}

@Override
public void run()
{

    while (on)
            {

                byte[] buf = new byte[256];
                try{
                        // receive request
                        DatagramPacket packet = new DatagramPacket(buf, buf.length);
                        socket.receive(packet);

                        String packdetails[] = new String(packet.getData(), 0, packet.getLength()).split(":");//Important part of receiving request. Tool used to parse the request
                        InetAddress address = packet.getAddress();

                        if(packdetails[0].equals("D"))  // if it's a Detection Packet
                        {/* Handle what to do with Detection packets */
                            }// end of small if
                        }//end of big if
                        else if(packdetails[0].equals("M"))// implies, Message type packet
                        {
                            Timestamp t =new Timestamp(new Date().getTime());
                            //Send Acknowledgement
                            String PString = new String("A:"+id);
                            buf = PString.getBytes();
                            packet = new DatagramPacket(buf, buf.length, address, 3333);

                            new ReceiveMessage(packdetails, address, people, t).start();
                        }
                        else// if it's an acknowledgemnt
                        {
                            //notify the sendmessage thread
                        }
                    }//end of try
                    catch (UnknownHostException e)
                    {
                        System.err.print("Unable to find IP of current machine");
                    }
                    catch (IOException except)
                    {
                        System.err.print("Network Problem : Unable to send packets!");
                    }
            }//end of while
    }//end of run

}//end of class

public class SendMessage extends Thread{
protected Contact person = null;
protected String Message = null;

public SendMessage(Contact person, String Message)
{
    this.person=person;
    this.Message= Message;
}
@Override
public void run()
{
    System.out.println(person.getusername()+": "+Message);
    try
    {
        person.SendMessage(Message);
        Thread.currentThread().wait(500);// If i get notify => received acknowledgement
    }
    catch(IOException e)
    {
        System.err.println("Unable to send message!");
    }
    catch (InterruptedException e)
    {
        System.err.print("Woken before receiving notify");
    }
}


There are many to achieve this, You could opt for CountDownLatch or CyclicBarrier where the Sender thread would wait for the receiver to act on the barrier. Another alternative would be for the receiver thread to put the ack message in a blockingQueue and the sender could consume the ack from the queue while waiting on it.