/* * (C) Copyright 2005 Arnaud Bailly (arnaud.oqube@gmail.com), * Yves Roos (yroos@lifl.fr) and others. * * Licensed under the Apache License, Version 2.0 (the License); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an AS IS BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package rationals.ioautomata.testing; import rationals.ioautomata.IOAutomaton; import rationals.ioautomata.IOAutomatonSMAdapter; import rationals.ioautomata.IOTransition; import rationals.ioautomata.IOTransitionBuilder; import java.util.concurrent.BlockingQueue; /** * An asynchronous implementation of StateMachine backed up by an IOAutomaton. * <p> * This implementation is asynchronous in the sense that input and output * methods are non blocking. * * @author nono * @version $Id: AsynchIOAutomatonSMAdapter.java 14 2007-06-04 20:47:25Z oqube $ */ public class AsynchIOAutomatonSMAdapter extends IOAutomatonSMAdapter { private BlockingQueue inQueue; private BlockingQueue outQueue; private boolean stop; private boolean error; public AsynchIOAutomatonSMAdapter(IOAutomaton<IOTransition,IOTransitionBuilder> auto) { super(auto); setInputEnabled(true); } public AsynchIOAutomatonSMAdapter(IOAutomaton<IOTransition,IOTransitionBuilder> a, BlockingQueue queue, BlockingQueue queue2) { this(a); this.inQueue = queue; this.outQueue = queue2; } /* * (non-Javadoc) * * @see rationals.ioautomata.IOStateMachine#input(java.lang.Object) */ public void input(Object o) { inQueue.add(o); synchronized (this) { notifyAll(); } } /* * (non-Javadoc) * * @see rationals.ioautomata.IOStateMachine#output() */ public Object output() { Object out = outQueue.poll(); return out; } /* * (non-Javadoc) * * @see rationals.ioautomata.IOStateMachine#output(java.lang.Object[], int, * int) */ public int output(Object[] out, int start, int len) { int i; for (i = start; i < len && i < out.length; i++) { Object o = outQueue.poll(); if (o == null) break; out[i] = o; } return i - start; } /* * (non-Javadoc) * * @see rationals.ioautomata.IOStateMachine#availableOutput() */ public int availableOutput() { return outQueue.size(); } /* * (non-Javadoc) * * @see rationals.ioautomata.IOStateMachine#stop() */ public void stop() { this.stop = true; } /* * (non-Javadoc) * * @see java.lang.Runnable#run() */ public void run() { _run: while (!stop) { Object in = inQueue.poll(); /* find a transition with this label */ super.input(in); Object out = super.output(); if (out == null) // nothing to do synchronized (this) { do { try { wait(200); } catch (InterruptedException e) { e.printStackTrace(); } out = super.output(); } while (inQueue.isEmpty() && out == null); } if (out != null) { try { outQueue.put(out); } catch (InterruptedException e) { e.printStackTrace(); } } } } public boolean isError() { return error; } public BlockingQueue getInQueue() { return inQueue; } public void setInQueue(BlockingQueue inQueue) { this.inQueue = inQueue; } public BlockingQueue getOutQueue() { return outQueue; } public void setOutQueue(BlockingQueue outQueue) { this.outQueue = outQueue; } }