|
What this is
Other links
The source code/* * Sun Public License Notice * * The contents of this file are subject to the Sun Public License * Version 1.0 (the "License"). You may not use this file except in * compliance with the License. A copy of the License is available at * http://www.sun.com/ * * The Original Code is NetBeans. The Initial Developer of the Original * Code is Sun Microsystems, Inc. Portions Copyright 1997-2001 Sun * Microsystems, Inc. All Rights Reserved. */ package org.netbeans.modules.javacore.jmiimpl.javamodel; import java.lang.reflect.Array; import java.util.Collection; import java.util.ConcurrentModificationException; import java.util.Iterator; import javax.jmi.reflect.RefObject; import org.netbeans.api.mdr.events.AssociationEvent; import org.netbeans.mdr.handlers.AssociationHandler; import org.netbeans.mdr.storagemodel.MdrStorage; import org.netbeans.mdr.util.EventNotifier; /** This collection wrapper is intended to assotiations persistent outside of MDR * repository, in this case in inner collection. So this wrapper simulates MDR event * system and asks MDR for lock/unlock support. * Wrapper can also verify check type for add/remove operations. * * @author Vladimir Hudec */ public class ReferenceColWrapper implements Collection { protected final MdrStorage storage; protected final AssociationHandler source; protected final EventNotifier.Association notifier; protected final RefObject fixed; protected final String endName; private Collection inner; private int modCount = 0; protected final MetadataElement parent; protected final int changeMask; private TypeVerifier typeVerifier; /***********************************************************************************/ /** Creates new CollectionWrapper */ public ReferenceColWrapper(MdrStorage storage, AssociationHandler source, RefObject fixed, String endName, MetadataElement parent, int changeMask, Collection inner) { this(storage, source, fixed, endName, parent, changeMask); setInnerList(inner); } protected ReferenceColWrapper(MdrStorage storage, AssociationHandler source, RefObject fixed, String endName, MetadataElement parent, int changeMask) { this.storage = storage; this.source = source; this.notifier = storage == null ? null : storage.getEventNotifier().ASSOCIATION; this.fixed = fixed; this.endName = endName; this.parent = parent; this.changeMask = changeMask; } public void setInnerList(Collection inner) { modCount++; this.inner = inner; if (inner instanceof TypeVerifier) { typeVerifier = (TypeVerifier) inner; } } public Collection getInnerCollection() { return inner; } protected int getModCount() { return modCount; } protected void objectChanged(Object obj) { if (parent == null) { if (obj instanceof MetadataElement) { ((MetadataElement) obj).objectChanged(changeMask); } } else { parent.objectChanged(changeMask); } } public void setTypeVerifier(TypeVerifier newTypeVerifier) { this.typeVerifier = newTypeVerifier; } /** lock/unlock support */ protected void lock(boolean writeAccess) { storage.getRepository().beginTrans(writeAccess); } protected void unlock() { storage.getRepository().endTrans(); } protected void unlock(boolean fail) { storage.getRepository().endTrans(fail); } protected void checkType(Object obj) throws javax.jmi.reflect.TypeMismatchException { if (typeVerifier != null) typeVerifier.checkType(obj); } protected void checkWrite() { if (source == null) { throw new UnsupportedOperationException(); } } /** Collection read operations */ public boolean contains(Object obj) { lock(false); try { return inner.contains(obj); } finally { unlock(); } } public Iterator iterator() { lock(false); try { return new ReferenceIteratorWrapper(inner.iterator()); } finally { unlock(); } } public int size() { lock(false); try { return inner.size(); } finally { unlock(); } } public boolean isEmpty() { lock(false); try { return inner.isEmpty(); } finally { unlock(); } } public boolean containsAll(Collection collection) { lock(false); try { return inner.containsAll(collection); } finally { unlock(); } } public Object[] toArray(Object[] obj) { lock(false); try { // System.out.println("toArray: obj="+obj+", obj.length="+obj.length+", inner="+inner+", inner.size="+inner.size()); // if (obj.length>0&&obj[0]!=null) // System.out.println("toArray: obj[0].getClass="+obj[0].getClass()); Object[] value = inner.toArray(); // if (value.length>0) // System.out.println("toArray: value[0].getClass="+value[0].getClass()); Object[] result = obj; if (value.length > result.length) { result = (Object[]) Array.newInstance(obj.getClass().getComponentType(), value.length); } else if (value.length < result.length) { result[value.length] = null; } System.arraycopy(value, 0, result, 0, value.length); return result; } finally { unlock(); } } public Object[] toArray() { return toArray(new Object[size()]); } public boolean equals(Object object) { if (object == this) return true; if (!(object instanceof Collection)) return false; lock(false); try { Iterator it1 = iterator(); Iterator it2 = ((Collection) object).iterator(); while(it1.hasNext() && it2.hasNext()) { Object o1 = it1.next(); Object o2 = it2.next(); if (!(o1==null ? o2==null : o1.equals(o2))) return false; } return !(it1.hasNext() || it2.hasNext()); } finally { unlock(); } } public int hashCode() { lock(false); try { int hashCode = 1; for (Iterator it = iterator(); it.hasNext();) { Object obj = it.next(); hashCode = 31*hashCode + (obj==null ? 0 : obj.hashCode()); } return hashCode; } finally { unlock(); } } /** Collection add/remove operations */ public void clear() { checkWrite(); boolean fail = true; lock(true); try { Object elements[] = inner.toArray(); for (int i = 0; i < elements.length; i++) { remove(elements[i]); } fail = false; } finally { unlock(fail); } } public boolean addAll(Collection collection) { checkWrite(); boolean fail = true; lock(true); try { boolean result = false; for (Iterator it = collection.iterator(); it.hasNext();) { result |= add(it.next()); } fail = false; return result; } finally { unlock(fail); } } public boolean retainAll(Collection collection) { checkWrite(); boolean fail = true; lock(true); try { boolean result = false; Object elements[] = inner.toArray(); for (int i = 0; i < elements.length; i++) { Object o = elements[i]; if (!collection.contains(o)) { remove(o); result = true; } } fail = false; return result; } finally { unlock(fail); } } public boolean removeAll(Collection collection) { checkWrite(); boolean fail = true; lock(true); try { boolean result = false; for (Iterator it = collection.iterator(); it.hasNext();) { result |= remove(it.next()); } fail = false; return result; } finally { unlock(fail); } } public boolean remove(Object obj) { checkWrite(); checkType(obj); boolean fail = true; lock(true); try { if (storage.eventsEnabled()) { AssociationEvent event = new AssociationEvent( source, AssociationEvent.EVENT_ASSOCIATION_REMOVE, fixed, endName, (RefObject) obj, null, AssociationEvent.POSITION_NONE); notifier.firePlannedChange(source, event); } boolean result = inner.remove(obj); objectChanged(obj); fail = false; return result; } finally { unlock(fail); } } public boolean add(Object obj) { checkWrite(); checkType(obj); boolean fail = true; lock(true); try { if (storage.eventsEnabled()) { AssociationEvent event = new AssociationEvent( source, AssociationEvent.EVENT_ASSOCIATION_ADD, fixed, endName, null, (RefObject) obj, AssociationEvent.POSITION_NONE); notifier.firePlannedChange(source, event); } boolean result = inner.add(obj); objectChanged(obj); fail = false; return result; } finally { unlock(fail); } } /** Iterator implementation */ protected class ReferenceIteratorWrapper implements Iterator { protected Iterator innerIterator; protected Object lastRead = null; protected final int modCount; public ReferenceIteratorWrapper(Iterator innerIterator) { this.innerIterator = innerIterator; this.modCount = getParentModCount(); } protected int getParentModCount() { return ReferenceColWrapper.this.getModCount(); } protected void testModCount() throws ConcurrentModificationException { if (modCount != getParentModCount()) throw new ConcurrentModificationException(); } public boolean hasNext() { testModCount(); lock(false); try { return innerIterator.hasNext(); } finally { unlock(); } } public Object next() { testModCount(); lock(false); try { return (lastRead = innerIterator.next()); } finally { unlock(); } } public void remove() { checkWrite(); testModCount(); //checkType(lastRead); boolean fail = true; lock(true); try { if (storage.eventsEnabled()) { AssociationEvent event = new AssociationEvent( source, AssociationEvent.EVENT_ASSOCIATION_REMOVE, fixed, endName, (RefObject) lastRead, null, AssociationEvent.POSITION_NONE); notifier.firePlannedChange(source, event); } innerIterator.remove(); objectChanged(lastRead); fail = false; } finally { unlock(fail); } } } } |
... this post is sponsored by my books ... | |
#1 New Release! |
FP Best Seller |
Copyright 1998-2021 Alvin Alexander, alvinalexander.com
All Rights Reserved.
A percentage of advertising revenue from
pages under the /java/jwarehouse
URI on this website is
paid back to open source projects.