/*
 *  ServantRequestPool.java v0.10 20-DEC-1999
 *  Copyright (c) TKK/TLM/Calypso
 *  Author: Alexey Mednonogov
 */

package codec.server;

import java.io.*;
import java.util.*;

import codec.*;
import codec.adapt.*;
import codec.convert.*;
import codec.debug.*;
import codec.dyntree.*;
import codec.export.*;
import codec.orb.*;
import codec.pco.*;
import codec.server.*;
import codec.client.*;
import codec.visit.*;
import codec.build.*;

/** Class responsible for managing the replies from Servers after performing
 *  asynchronous invocation requests. It is running in a separate thread,
 *  constantly checking responses from all registered requests. Once response
 *  is obtained, it delegates its further processing to ServerPool. */
final public class ServantRequestPool extends Thread {

    private Set requests;

    /** The field is for notifying the main class thread that new request is
     *  to be registered. Main class thread will then remove the lock from
     *  "requests" object and will try to obtain the lock again no earlier
     *  than this field is again set to 0. */
    private volatile Boolean requestUnlock = new Boolean(false);

    public ServantRequestPool() {
        requests = Collections.synchronizedSet(new HashSet());
    }

    /** Register the request object. Normally this shall be used after making
     *  asynchronous invocation. Since then class instance will be polling for
     *  operation response. */
    public void register(ServantRequest request) {

        synchronized (requestUnlock) { 
            requestUnlock = new Boolean(true);
            synchronized (requests) {
                requestUnlock = new Boolean(false);
                requests.add(request);
            }
        }
    }

    /** Class core checking for the operation responses from registered
     *  requests. */
    public void run() {

        while (true) {

            while (true) if (requestUnlock.booleanValue() == false) break;

            synchronized (requests) {
                Iterator iterator = requests.iterator();
                while (iterator.hasNext()) {

                    ServantRequest servantRequest =
                        (ServantRequest) iterator.next();
                    org.omg.CORBA.Request request =
                        servantRequest.getRequest();

					boolean isPollResponse = false;
					try {
						isPollResponse = request.poll_response();
					}
					catch (org.omg.CORBA.SystemException ex) {

						isPollResponse = true;
					}
                    if (isPollResponse) {

						System.out.println("ServantRequestPool::run(): " +
						   servantRequest.getPcoName() +
						   ": received response.");

                        ServerPool.operResponse(servantRequest);
                        iterator.remove();
                    }
                }
            }
        }
    }
}
