Fixed a bug in ConfigurationDependency which did not correctly detect the state transition from an available configuration to a no longer available one (for example, if you deleted the configuration). Furthermore, some whitespace cleanups and some synchronization inconsistencies solved.
Updated the pom.xml to use current dependencies and versions.

git-svn-id: https://svn.apache.org/repos/asf/felix/trunk@616718 13f79535-47bb-0310-9956-ffa450edef68
diff --git a/dependencymanager/pom.xml b/dependencymanager/pom.xml
index ce8b44c..7fb85fc 100644
--- a/dependencymanager/pom.xml
+++ b/dependencymanager/pom.xml
@@ -27,13 +27,13 @@
   <modelVersion>4.0.0</modelVersion>
   <packaging>bundle</packaging>
   <name>Apache Felix Dependency Manager</name>
-  <version>0.9.0-SNAPSHOT</version>
+  <version>1.1.0-SNAPSHOT</version>
   <artifactId>org.apache.felix.dependencymanager</artifactId>
   <dependencies>
     <dependency>
       <groupId>${pom.groupId}</groupId>
       <artifactId>org.osgi.core</artifactId>
-      <version>1.1.0-SNAPSHOT</version>
+      <version>1.0.0</version>
       <scope>provided</scope>
     </dependency>
     <dependency>
diff --git a/dependencymanager/src/main/java/org/apache/felix/dependencymanager/ConfigurationDependency.java b/dependencymanager/src/main/java/org/apache/felix/dependencymanager/ConfigurationDependency.java
index 31410e4..83b3364 100644
--- a/dependencymanager/src/main/java/org/apache/felix/dependencymanager/ConfigurationDependency.java
+++ b/dependencymanager/src/main/java/org/apache/felix/dependencymanager/ConfigurationDependency.java
@@ -120,7 +120,7 @@
 		if ((oldSettings == null) && (settings != null)) {
 			m_service.dependencyAvailable(this);
 		}
-		if ((oldSettings == null) && (settings == null)) {
+		if ((oldSettings != null) && (settings == null)) {
 			m_service.dependencyUnavailable(this);
 		}
 		if ((oldSettings != null) && (settings != null)) {
diff --git a/dependencymanager/src/main/java/org/apache/felix/dependencymanager/Service.java b/dependencymanager/src/main/java/org/apache/felix/dependencymanager/Service.java
index a72174a..cbd98b5 100644
--- a/dependencymanager/src/main/java/org/apache/felix/dependencymanager/Service.java
+++ b/dependencymanager/src/main/java/org/apache/felix/dependencymanager/Service.java
@@ -197,4 +197,51 @@
      * for this service.
      */
     public void stop();
+    
+    /**
+     * Sets the factory to use to create the implementation. You can specify
+     * both the factory class and method to invoke. The method should return
+     * the implementation, and can use any method to create it. Actually, this
+     * can be used together with <code>setComposition</code> to create a
+     * composition of instances that work together to implement a service. The
+     * factory itself can also be instantiated lazily by not specifying an
+     * instance, but a <code>Class</code>.
+     * 
+     * @param factory the factory instance or class
+     * @param createMethod the name of the create method
+     */
+	public Service setFactory(Object factory, String createMethod);
+	
+	/**
+	 * Sets the factory to use to create the implementation. You specify the
+	 * method to invoke. The method should return the implementation, and can
+	 * use any method to create it. Actually, this can be used together with
+	 * <code>setComposition</code> to create a composition of instances that
+	 * work together to implement a service. The factory method is called on
+	 * ??? TODO ???
+	 * 
+	 * @param createMethod the name of the create method
+	 */
+	public Service setFactory(String createMethod);
+	
+	/**
+	 * Sets the instance and method to invoke to get back all instances that
+	 * are part of a composition and need dependencies injected. All of them
+	 * will be searched for any of the dependencies. The method that is
+	 * invoked must return an <code>Object[]</code>.
+	 * 
+	 * @param instance the instance that has the method
+	 * @param getMethod the method to invoke
+	 */
+	public Service setComposition(Object instance, String getMethod);
+	
+	/**
+	 * Sets the method to invoke on the service implementation to get back all
+	 * instances that are part of a composition and need dependencies injected.
+	 * All of them will be searched for any of the dependencies. The method that
+	 * is invoked must return an <code>Object[]</code>.
+	 * 
+	 * @param getMethod the method to invoke
+	 */
+	public Service setComposition(String getMethod);
 }
diff --git a/dependencymanager/src/main/java/org/apache/felix/dependencymanager/ServiceDependency.java b/dependencymanager/src/main/java/org/apache/felix/dependencymanager/ServiceDependency.java
index b661810..206f6a9 100644
--- a/dependencymanager/src/main/java/org/apache/felix/dependencymanager/ServiceDependency.java
+++ b/dependencymanager/src/main/java/org/apache/felix/dependencymanager/ServiceDependency.java
@@ -61,15 +61,15 @@
         m_autoConfig = true;
     }
 
-    public boolean isRequired() {
+    public synchronized boolean isRequired() {
         return m_isRequired;
     }
 
-    public boolean isAvailable() {
+    public synchronized boolean isAvailable() {
         return m_isAvailable;
     }
     
-    public boolean isAutoConfig() {
+    public synchronized boolean isAutoConfig() {
         return m_autoConfig;
     }
 
@@ -86,12 +86,16 @@
 
     private Object getNullObject() {
         if (m_nullObject == null) {
-            m_nullObject = Proxy.newProxyInstance(m_trackedServiceName.getClassLoader(), new Class[] {m_trackedServiceName}, new DefaultNullObject()); 
+            Class trackedServiceName;
+            synchronized (this) {
+                trackedServiceName = m_trackedServiceName;
+            }
+            m_nullObject = Proxy.newProxyInstance(trackedServiceName.getClassLoader(), new Class[] {trackedServiceName}, new DefaultNullObject()); 
         }
         return m_nullObject;
     }
     
-    public Class getInterface() {
+    public synchronized Class getInterface() {
         return m_trackedServiceName;
     }
 
@@ -203,6 +207,8 @@
         if (!isRequired()) {
             invokeRemoved(ref, service);
         }
+        
+        // unget what we got in addingService (see ServiceTracker 701.4.1)
         m_context.ungetService(ref);
     }
 
@@ -241,7 +247,7 @@
         return false;
     }
     
-    private Object getCallbackInstance() {
+    private synchronized Object getCallbackInstance() {
         Object callbackInstance = m_callbackInstance;
         if (callbackInstance == null) {
             callbackInstance = m_service.getService();
@@ -253,8 +259,12 @@
         Class currentClazz = instance.getClass();
         boolean done = false;
         while (!done && currentClazz != null) {
+            Class trackedServiceName;
+            synchronized (this) {
+                trackedServiceName = m_trackedServiceName;
+            }
             done = invokeMethod(instance, currentClazz, methodName,
-                new Class[][] {{ServiceReference.class, m_trackedServiceName}, {ServiceReference.class, Object.class}, {ServiceReference.class}, {m_trackedServiceName}, {Object.class}, {}},
+                new Class[][] {{ServiceReference.class, trackedServiceName}, {ServiceReference.class, Object.class}, {ServiceReference.class}, {trackedServiceName}, {Object.class}, {}},
                 new Object[][] {{reference, service}, {reference, service}, {reference}, {service}, {service}, {}},
                 false);
             if (!done) {
@@ -419,7 +429,7 @@
         }
     }
     
-    public String toString() {
+    public synchronized String toString() {
         return "ServiceDependency[" + m_trackedServiceName + " " + m_trackedServiceFilter + "]";
     }
 }
diff --git a/dependencymanager/src/main/java/org/apache/felix/dependencymanager/ServiceImpl.java b/dependencymanager/src/main/java/org/apache/felix/dependencymanager/ServiceImpl.java
index 6794d5a..a63f4b8 100644
--- a/dependencymanager/src/main/java/org/apache/felix/dependencymanager/ServiceImpl.java
+++ b/dependencymanager/src/main/java/org/apache/felix/dependencymanager/ServiceImpl.java
@@ -18,8 +18,17 @@
  */
 package org.apache.felix.dependencymanager;
 
-import java.lang.reflect.*;
-import java.util.*;
+import java.lang.reflect.Constructor;
+import java.lang.reflect.Field;
+import java.lang.reflect.Method;
+import java.lang.reflect.Proxy;
+import java.util.ArrayList;
+import java.util.Dictionary;
+import java.util.Enumeration;
+import java.util.Hashtable;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Properties;
 
 import org.osgi.framework.BundleContext;
 import org.osgi.framework.ServiceRegistration;
@@ -692,7 +701,7 @@
 	    		try {
 					Method m = m_compositionManagerInstance.getClass().getDeclaredMethod(m_compositionManagerGetMethod, null);
             		m.setAccessible(true);
-					instances = (Object[]) m.invoke(m_compositionManager, null);
+					instances = (Object[]) m.invoke(m_compositionManagerInstance, null);
 				}
 	    		catch (Exception e) {
 					// TODO Auto-generated catch block