001: //
002: // Copyright (C) 2005 United States Government as represented by the
003: // Administrator of the National Aeronautics and Space Administration
004: // (NASA). All Rights Reserved.
005: //
006: // This software is distributed under the NASA Open Source Agreement
007: // (NOSA), version 1.3. The NOSA has been approved by the Open Source
008: // Initiative. See the file NOSA-1.3-JPF at the top of the distribution
009: // directory tree for the complete NOSA document.
010: //
011: // THE SUBJECT SOFTWARE IS PROVIDED "AS IS" WITHOUT ANY WARRANTY OF ANY
012: // KIND, EITHER EXPRESSED, IMPLIED, OR STATUTORY, INCLUDING, BUT NOT
013: // LIMITED TO, ANY WARRANTY THAT THE SUBJECT SOFTWARE WILL CONFORM TO
014: // SPECIFICATIONS, ANY IMPLIED WARRANTIES OF MERCHANTABILITY, FITNESS FOR
015: // A PARTICULAR PURPOSE, OR FREEDOM FROM INFRINGEMENT, ANY WARRANTY THAT
016: // THE SUBJECT SOFTWARE WILL BE ERROR FREE, OR ANY WARRANTY THAT
017: // DOCUMENTATION, IF PROVIDED, WILL CONFORM TO THE SUBJECT SOFTWARE.
018: //
019: package gov.nasa.jpf;
020:
021: /**
022: * helper class to avoid indirection if there is just one observer
023: * (the usual case). Typical 'Container' pattern implementation
024: */
025: public class VMListenerMulticaster implements VMListener {
026: VMListener head;
027: VMListener tail;
028:
029: public static VMListener add(VMListener oldListener,
030: VMListener newListener) {
031: if (newListener == null) {
032: return oldListener;
033: }
034: if (oldListener == null) {
035: return newListener;
036: }
037:
038: // we store in the order of registration, multiple entries are allowed
039: // (but generally useless)
040: return new VMListenerMulticaster(oldListener, newListener);
041: }
042:
043: public static VMListener remove(VMListener oldListener,
044: VMListener removeListener) {
045: if (oldListener == removeListener) {
046: return null;
047: }
048: if (oldListener instanceof VMListenerMulticaster) {
049: return ((VMListenerMulticaster) oldListener)
050: .remove(removeListener);
051: }
052:
053: return oldListener;
054: }
055:
056: protected VMListener remove(VMListener listener) {
057: if (listener == head) {
058: return tail;
059: }
060: if (listener == tail) {
061: return head;
062: }
063:
064: VMListenerMulticaster h, t;
065: if (head instanceof VMListenerMulticaster) {
066: h = (VMListenerMulticaster) head;
067: if (tail instanceof VMListenerMulticaster) {
068: t = (VMListenerMulticaster) tail;
069: return new VMListenerMulticaster(h.remove(listener), t
070: .remove(listener));
071: } else {
072: return new VMListenerMulticaster(h.remove(listener),
073: tail);
074: }
075: } else if (tail instanceof VMListenerMulticaster) {
076: t = (VMListenerMulticaster) tail;
077: return new VMListenerMulticaster(head, t.remove(listener));
078: }
079:
080: return this ;
081: }
082:
083: public VMListenerMulticaster(VMListener h, VMListener t) {
084: head = h;
085: tail = t;
086: }
087:
088: public void instructionExecuted(VM vm) {
089: head.instructionExecuted(vm);
090: tail.instructionExecuted(vm);
091: }
092:
093: public void threadStarted(VM vm) {
094: head.threadStarted(vm);
095: tail.threadStarted(vm);
096: }
097:
098: public void threadTerminated(VM vm) {
099: head.threadTerminated(vm);
100: tail.threadTerminated(vm);
101: }
102:
103: public void classLoaded(VM vm) {
104: head.classLoaded(vm);
105: tail.classLoaded(vm);
106: }
107:
108: public void objectCreated(VM vm) {
109: head.objectCreated(vm);
110: tail.objectCreated(vm);
111: }
112:
113: public void objectReleased(VM vm) {
114: head.objectReleased(vm);
115: tail.objectReleased(vm);
116: }
117:
118: public void gcBegin(VM vm) {
119: head.gcBegin(vm);
120: tail.gcBegin(vm);
121: }
122:
123: public void gcEnd(VM vm) {
124: head.gcEnd(vm);
125: tail.gcEnd(vm);
126: }
127:
128: public void exceptionThrown(VM vm) {
129: head.exceptionThrown(vm);
130: tail.exceptionThrown(vm);
131: }
132:
133: }
|