ptolemy.domains.pn.kernel
Class PNDirector

java.lang.Object
  extended by ptolemy.kernel.util.NamedObj
      extended by ptolemy.kernel.util.Attribute
          extended by ptolemy.actor.Director
              extended by ptolemy.actor.process.ProcessDirector
                  extended by ptolemy.actor.process.CompositeProcessDirector
                      extended by ptolemy.domains.pn.kernel.PNDirector
All Implemented Interfaces:
java.io.Serializable, java.lang.Cloneable, Executable, Initializable, Changeable, Debuggable, DebugListener, Derivable, ModelErrorHandler, MoMLExportable, Moveable, Nameable
Direct Known Subclasses:
NondeterministicMerge.MergeDirector, TimedPNDirector

public class PNDirector
extends CompositeProcessDirector

A PNDirector governs the execution of a CompositeActor with extended Kahn-MacQueen process networks (PN) semantics. This model of computation has been extended to support mutations of graphs in a non-deterministic way.

The thread that calls the various execution methods (initialize, prefire, fire and postfire) on the director is referred to as the directing thread. This directing thread might be the main thread responsible for the execution of the entire simulation or might be the thread created by the executive director of the containing composite actor.

In the PN domain, the director creates a thread (an instance of ProcessThread), representing a Kahn process, for each actor in the model. The threads are created in initialize() and started in the prefire() method of the ProcessDirector. A process is considered active from its creation until its termination. An active process can block when trying to read from a channel (read-blocked), when trying to write to a channel (write-blocked) or when waiting for a queued topology change request to be processed (mutation-blocked).

A deadlock is when all the active processes are blocked. The director is responsible for handling deadlocks during execution. This director handles two different sorts of deadlocks, real deadlock and artificial deadlock.

A real deadlock is when all the processes are blocked on a read meaning that no process can proceed until it receives new data. The execution can be terminated, if desired, in such a situation. If the container of this director does not have any input ports (as is in the case of a top-level composite actor), then the executive director or manager terminates the execution. If the container has input ports, then it is up to the executive director of the container to decide on the termination of the execution. To terminate the execution after detection of a real deadlock, the manager or the executive director calls wrapup() on the director.

An artificial deadlock is when all processes are blocked and at least one process is blocked on a write. In this case the director increases the capacity of the receiver with the smallest capacity amongst all the receivers on which a process is blocked on a write. This breaks the deadlock and the execution can resume. If the increase results in a capacity that exceeds the value of maximumQueueCapacity, then instead of breaking the deadlock, an exception is thrown. This can be used to detect erroneous models that require unbounded queues.

There are at least three ways for a PN model to terminate itself:

  1. Have the model starve itself. Typically, a boolean switch is used. See the PN OrderedMerge demo at ptolemy/domains/pn/demo/OrderedMerge/OrderedMerge.xml
  2. Have the model call the Stop actor. See the PN RemoveNilTokens demo at ptolemy/domains/pn/demo/RemoveNilTokens/RemoveNilTokens.xmll
  3. Set the firingCountLimit (LimitedFiringSource._firingCountLimit) actor parameter to the number of iterations desired. Actors such as Ramp extend LimitedFiringSource and have the firingCountLimit parameter.

Since:
Ptolemy II 0.2
Version:
$Id: PNDirector.java 57040 2010-01-27 20:52:32Z cxh $
Author:
Mudit Goel, Edward A. Lee, Xiaowen Xin
See Also:
Serialized Form
Accepted Rating:
Green (davisj)
Proposed Rating:
Green (mudit)

Nested Class Summary
 
Nested classes/interfaces inherited from class ptolemy.kernel.util.NamedObj
NamedObj.ContainedObjectsIterator
 
Field Summary
private  java.util.LinkedList _processListeners
          List of process listeners.
protected  java.util.HashMap _readBlockedQueues
          The set of processes blocked on a read from a receiver.
private  java.util.LinkedList _receivers
          The list of all receivers that this director has created.
protected  java.util.HashMap _writeBlockedQueues
          The set of receivers blocked on a write to a receiver.
 Parameter initialQueueCapacity
          The initial size of the queues for each communication channel.
 Parameter maximumQueueCapacity
          The maximum size of the queues for each communication channel.
static boolean READ_BLOCKED
          Indicator that a thread is read blocked.
static boolean WRITE_BLOCKED
          Indicator that a thread is write blocked.
 
Fields inherited from class ptolemy.actor.process.ProcessDirector
_notDone, _stopFireRequested
 
Fields inherited from class ptolemy.actor.Director
_actorsFinishedExecution, _currentTime, _finishRequested, _initializables, _stopRequested, timeResolution
 
Fields inherited from class ptolemy.kernel.util.NamedObj
_changeListeners, _changeLock, _changeRequests, _debugging, _debugListeners, _elementName, _isPersistent, _verbose, _workspace, ATTRIBUTES, CLASSNAME, COMPLETE, CONTENTS, DEEP, FULLNAME, LINKS
 
Fields inherited from interface ptolemy.actor.Executable
COMPLETED, NOT_READY, STOP_ITERATING
 
Constructor Summary
PNDirector()
          Construct a director in the default workspace with an empty string as its name.
PNDirector(CompositeEntity container, java.lang.String name)
          Construct a director in the given container with the given name.
PNDirector(Workspace workspace)
          Construct a director in the workspace with an empty name.
 
Method Summary
protected  void _incrementLowestWriteCapacityPort()
          Double the capacity of one of the queues with the smallest capacity belonging to a receiver on which a process is blocked while attempting to write.
private  void _init()
           
protected  boolean _resolveInternalDeadlock()
          Resolve an artificial deadlock and return true.
 void addProcessListener(PNProcessListener listener)
          Add a process state change listener to this director.
 java.lang.Object clone(Workspace workspace)
          Clone the director into the specified workspace.
 void initialize()
          Invoke the initialize() method of ProcessDirector.
 Receiver newReceiver()
          Return a new receiver compatible with this director.
 boolean postfire()
          Return true if the containing composite actor contains active processes and the composite actor has input ports and if stop() has not been called.
 void preinitialize()
          Override the base class to reset the capacities of all the receivers.
 void removeProcessListener(PNProcessListener listener)
          Remove a process listener from this director.
 java.lang.String[] suggestedModalModelDirectors()
          Return an array of suggested ModalModel directors to use with PNDirector.
 boolean supportMultirateFiring()
          Return true to indicate that a ModalModel under control of this director supports multirate firing.
 void threadBlocked(java.lang.Thread thread, ProcessReceiver receiver, boolean readOrWrite)
          Notify the director that the specified thread is blocked on an I/O operation.
 void threadUnblocked(java.lang.Thread thread, ProcessReceiver receiver, boolean readOrWrite)
          Notify the director that the specified thread is unblocked on an I/O operation.
 
Methods inherited from class ptolemy.actor.process.CompositeProcessDirector
_areActorsExternallyBlocked, _areThreadsDeadlocked, _controllerBlocked, _controllerUnBlocked, _isInputControllerBlocked, _isOutputControllerBlocked, _resolveDeadlock, createBranchController, getInputController, getOutputController, prefire, setModelTime, stopInputBranchController, stopOutputBranchController, threadBlocked, threadUnblocked, wrapup
 
Methods inherited from class ptolemy.actor.process.ProcessDirector
_areAllThreadsStopped, _getActiveThreadsCount, _getBlockedThreadsCount, _getStoppedThreadsCount, _newProcessThread, addThread, finish, fire, initialize, isStopFireRequested, isStopRequested, isThreadActive, removeThread, stop, stopFire, terminate, threadHasPaused, threadHasResumed, transferInputs, transferOutputs
 
Methods inherited from class ptolemy.actor.Director
_description, _fireContainerAt, _isEmbedded, _isTopLevel, _transferInputs, _transferOutputs, addInitializable, attributeChanged, createSchedule, defaultDependency, fireAt, fireAt, fireAtCurrentTime, getCausalityInterface, getCurrentTime, getErrorTolerance, getGlobalTime, getModelNextIterationTime, getModelStartTime, getModelStopTime, getModelTime, getNextIterationTime, getStartTime, getStopTime, getTimeResolution, implementsStrictActorSemantics, invalidateResolvedTypes, invalidateSchedule, isFireFunctional, isStrict, iterate, preinitialize, removeInitializable, requestInitialization, setContainer, setCurrentTime
 
Methods inherited from class ptolemy.kernel.util.Attribute
_checkContainer, _getContainedObject, _propagateExistence, getContainer, moveDown, moveToFirst, moveToIndex, moveToLast, moveUp, setName, updateContent
 
Methods inherited from class ptolemy.kernel.util.NamedObj
_addAttribute, _adjustOverride, _attachText, _cloneFixAttributeFields, _debug, _debug, _debug, _debug, _debug, _exportMoMLContents, _getIndentPrefix, _isMoMLSuppressed, _markContentsDerived, _propagateValue, _recordDecoratedAttributes, _removeAttribute, _splitName, _stripNumericSuffix, _validateSettables, addChangeListener, addDebugListener, attributeList, attributeList, attributeTypeChanged, clone, containedObjectsIterator, deepContains, depthInHierarchy, description, description, event, executeChangeRequests, exportMoML, exportMoML, exportMoML, exportMoML, exportMoML, exportMoMLPlain, getAttribute, getAttribute, getAttributes, getChangeListeners, getClassName, getDecoratorAttribute, getDecoratorAttributes, getDerivedLevel, getDerivedList, getDisplayName, getElementName, getFullName, getModelErrorHandler, getName, getName, getPrototypeList, getSource, handleModelError, isDeferringChangeRequests, isOverridden, isPersistent, lazyContainedObjectsIterator, message, propagateExistence, propagateValue, propagateValues, removeChangeListener, removeDebugListener, requestChange, setClassName, setDeferringChangeRequests, setDerivedLevel, setDisplayName, setModelErrorHandler, setPersistent, setSource, sortContainedObjects, toplevel, toString, uniqueName, validateSettables, workspace
 
Methods inherited from class java.lang.Object
equals, finalize, getClass, hashCode, notify, notifyAll, wait, wait, wait
 

Field Detail

initialQueueCapacity

public Parameter initialQueueCapacity
The initial size of the queues for each communication channel. This is an integer that defaults to 1.


maximumQueueCapacity

public Parameter maximumQueueCapacity
The maximum size of the queues for each communication channel. This is an integer that defaults to 65536. To specify unbounded queues, set this to 0.


READ_BLOCKED

public static final boolean READ_BLOCKED
Indicator that a thread is read blocked.

See Also:
Constant Field Values

WRITE_BLOCKED

public static final boolean WRITE_BLOCKED
Indicator that a thread is write blocked.

See Also:
Constant Field Values

_readBlockedQueues

protected java.util.HashMap _readBlockedQueues
The set of processes blocked on a read from a receiver.


_writeBlockedQueues

protected java.util.HashMap _writeBlockedQueues
The set of receivers blocked on a write to a receiver.


_processListeners

private java.util.LinkedList _processListeners
List of process listeners.


_receivers

private java.util.LinkedList _receivers
The list of all receivers that this director has created.

Constructor Detail

PNDirector

public PNDirector()
           throws IllegalActionException,
                  NameDuplicationException
Construct a director in the default workspace with an empty string as its name. The director is added to the list of objects in the workspace. Increment the version number of the workspace. Create a director parameter "initialQueueCapacity" with the default value 1. This sets the initial capacities of the queues in all the receivers created in the PN domain.

Throws:
IllegalActionException - If the name has a period in it, or the director is not compatible with the specified container.
NameDuplicationException - If the container already contains an entity with the specified name.

PNDirector

public PNDirector(Workspace workspace)
           throws IllegalActionException,
                  NameDuplicationException
Construct a director in the workspace with an empty name. The director is added to the list of objects in the workspace. Increment the version number of the workspace. Create a director parameter "initialQueueCapacity" with the default value 1. This sets the initial capacities of the queues in all the receivers created in the PN domain.

Parameters:
workspace - The workspace of this object.
Throws:
IllegalActionException - If the name has a period in it, or the director is not compatible with the specified container.
NameDuplicationException - If the container already contains an entity with the specified name.

PNDirector

public PNDirector(CompositeEntity container,
                  java.lang.String name)
           throws IllegalActionException,
                  NameDuplicationException
Construct a director in the given container with the given name. If the container argument must not be null, or a NullPointerException will be thrown. If the name argument is null, then the name is set to the empty string. Increment the version number of the workspace. Create a director parameter "initialQueueCapacity" with the default value 1. This sets the initial capacities of the queues in all the receivers created in the PN domain.

Parameters:
container - Container of the director.
name - Name of this director.
Throws:
IllegalActionException - If the director is not compatible with the specified container. Thrown in derived classes.
NameDuplicationException - If the container not a CompositeActor and the name collides with an entity in the container.
Method Detail

addProcessListener

public void addProcessListener(PNProcessListener listener)
Add a process state change listener to this director. The listener will be notified of each change to the state of a process.

Parameters:
listener - The PNProcessListener to add.
See Also:
removeProcessListener(PNProcessListener)

clone

public java.lang.Object clone(Workspace workspace)
                       throws java.lang.CloneNotSupportedException
Clone the director into the specified workspace. The new object is not added to the directory of that workspace (It must be added by the user if he wants it to be there). The result is a new director with no container, no pending mutations, and no topology listeners. The count of active processes is zero.

Overrides:
clone in class CompositeProcessDirector
Parameters:
workspace - The workspace for the cloned object.
Returns:
The new PNDirector.
Throws:
java.lang.CloneNotSupportedException - If one of the attributes cannot be cloned.
See Also:
NamedObj.exportMoML(Writer, int, String), NamedObj.setDeferringChangeRequests(boolean)

initialize

public void initialize()
                throws IllegalActionException
Invoke the initialize() method of ProcessDirector. Also set all the state variables to the their initial values. The list of process listeners is not reset as the developer might want to reuse the list of listeners.

Specified by:
initialize in interface Initializable
Overrides:
initialize in class CompositeProcessDirector
Throws:
IllegalActionException - If the initialize() method of one of the deeply contained actors throws it.

newReceiver

public Receiver newReceiver()
Return a new receiver compatible with this director. The receiver is an instance of PNQueueReceiver. Set the initial capacity of the FIFO queue in the receiver to the value specified by the director parameter "initialQueueCapacity". The default value of the parameter is 1.

Overrides:
newReceiver in class CompositeProcessDirector
Returns:
A new PNQueueReceiver.

postfire

public boolean postfire()
                 throws IllegalActionException
Return true if the containing composite actor contains active processes and the composite actor has input ports and if stop() has not been called. Return false otherwise. This method is normally called only after detecting a real deadlock, or if stopFire() is called. True is returned to indicate that the composite actor can start its execution again if it receives data on any of its input ports.

Specified by:
postfire in interface Executable
Overrides:
postfire in class ProcessDirector
Returns:
true to indicate that the composite actor can continue executing on receiving additional input on its input ports.
Throws:
IllegalActionException - Not thrown in this base class. May be thrown by derived classes.

preinitialize

public void preinitialize()
                   throws IllegalActionException
Override the base class to reset the capacities of all the receivers.

Specified by:
preinitialize in interface Initializable
Overrides:
preinitialize in class ProcessDirector
Throws:
IllegalActionException - If the superclass throws it.

removeProcessListener

public void removeProcessListener(PNProcessListener listener)
Remove a process listener from this director. If the listener is not attached to this director, do nothing.

Parameters:
listener - The PNProcessListener to be removed.
See Also:
addProcessListener(PNProcessListener)

suggestedModalModelDirectors

public java.lang.String[] suggestedModalModelDirectors()
Return an array of suggested ModalModel directors to use with PNDirector. The default director is MultirateFSMDirector, the alternative director is FSMDirector.

Overrides:
suggestedModalModelDirectors in class Director
Returns:
An array of suggested directors to be used with ModalModel.
See Also:
Director.suggestedModalModelDirectors()

supportMultirateFiring

public boolean supportMultirateFiring()
Return true to indicate that a ModalModel under control of this director supports multirate firing.

Overrides:
supportMultirateFiring in class Director
Returns:
True indicating a ModalModel under control of this director supports multirate firing.

threadBlocked

public void threadBlocked(java.lang.Thread thread,
                          ProcessReceiver receiver,
                          boolean readOrWrite)
Notify the director that the specified thread is blocked on an I/O operation.

Parameters:
thread - The thread.
receiver - The receiver handling the I/O operation, or null if it is not a specific receiver.
readOrWrite - Either READ_BLOCKED or WRITE_BLOCKED to indicate whether the thread is blocked on read or write.
See Also:
CompositeProcessDirector.threadBlocked(Thread, ProcessReceiver)

threadUnblocked

public void threadUnblocked(java.lang.Thread thread,
                            ProcessReceiver receiver,
                            boolean readOrWrite)
Notify the director that the specified thread is unblocked on an I/O operation. If the thread has not been registered with threadBlocked(), then this call is ignored.

Parameters:
thread - The thread.
receiver - The receiver handling the I/O operation, or null if it is not a specific receiver.
readOrWrite - Either READ_BLOCKED or WRITE_BLOCKED to indicate whether the thread is blocked on read or write.
See Also:
CompositeProcessDirector.threadUnblocked(Thread, ProcessReceiver)

_incrementLowestWriteCapacityPort

protected void _incrementLowestWriteCapacityPort()
                                          throws IllegalActionException
Double the capacity of one of the queues with the smallest capacity belonging to a receiver on which a process is blocked while attempting to write.

Traverse through the list of receivers on which a process is blocked on a write and choose the one containing the queue with the smallest capacity. Double the capacity if the capacity is non-negative. In case the capacity is negative, set the capacity to 1. Unblock the process blocked on a write to the receiver containing this queue. Notify the thread corresponding to the blocked process to resume its execution and return.

Throws:
IllegalActionException - If the resulting capacity would exceed the value of maximumQueueCapacity.

_resolveInternalDeadlock

protected boolean _resolveInternalDeadlock()
                                    throws IllegalActionException
Resolve an artificial deadlock and return true. If the deadlock is not an artificial deadlock (it is a real deadlock), then return false. If it is an artificial deadlock, select the receiver with the smallest queue capacity on which any process is blocked on a write and increment the capacity of the contained queue. If the capacity is non-negative, then increment the capacity by 1. Otherwise set the capacity to 1. Unblock the process blocked on this receiver. Notify the thread corresponding to the blocked process and return true.

If derived classes introduce new forms of deadlocks, they should override this method to introduce mechanisms of handling those deadlocks. This method is called from the fire() method of the director alone.

Overrides:
_resolveInternalDeadlock in class CompositeProcessDirector
Returns:
True after handling an artificial deadlock. Otherwise return false.
Throws:
IllegalActionException - If the maximum queue capacity is exceeded. This might be thrown by derived classes.

_init

private void _init()
            throws IllegalActionException,
                   NameDuplicationException
Throws:
IllegalActionException
NameDuplicationException