/** * Internal message delivery method. * * @pre threads > 0 */ private void sendUpdate( Address<? extends Receiver> receiver, Direction direction, Tuple updateElement) { ReteContainer affectedContainer = receiver.getContainer(); synchronized (globalTerminationCriteria) { long newCriterion = affectedContainer.sendUpdateToLocalAddress(receiver, direction, updateElement); terminationCriterion(affectedContainer, newCriterion); } }
/** * Internal message delivery method. * * @pre threads > 0 */ private void sendUpdates( Address<? extends Receiver> receiver, Direction direction, Collection<Tuple> updateElements) { if (updateElements.isEmpty()) return; ReteContainer affectedContainer = receiver.getContainer(); synchronized (globalTerminationCriteria) { long newCriterion = affectedContainer.sendUpdatesToLocalAddress(receiver, direction, updateElements); terminationCriterion(affectedContainer, newCriterion); } }
/** * Containers use this method to report whenever they run out of messages in their queue. * * <p>To be called from the thread of the reporting container. * * @pre threads > 0. * @param reportingContainer the container reporting the emptiness of its message queue. * @param clock the value of the container's clock when reporting. * @param localTerminationCriteria the latest clock values this container has received from other * containers since the last time it reported termination. */ void reportLocalUpdateTermination( ReteContainer reportingContainer, long clock, Map<ReteContainer, Long> localTerminationCriteria) { synchronized (globalTerminationCriteria) { for (Entry<ReteContainer, Long> criterion : localTerminationCriteria.entrySet()) { terminationCriterion(criterion.getKey(), criterion.getValue()); } reportedClocks.put(reportingContainer, clock); Long criterion = globalTerminationCriteria.get(reportingContainer); if (criterion != null && criterion < clock) globalTerminationCriteria.remove(reportingContainer); if (globalTerminationCriteria.isEmpty()) globalTerminationCriteria.notifyAll(); } }