Applied patch (FELIX-289) to add support for having "glue code" components
inside composites.


git-svn-id: https://svn.apache.org/repos/asf/felix/trunk@539496 13f79535-47bb-0310-9956-ffa450edef68
diff --git a/ipojo/pom.xml b/ipojo/pom.xml
index 9cc366f..d562295 100644
--- a/ipojo/pom.xml
+++ b/ipojo/pom.xml
@@ -17,6 +17,12 @@
       <scope>provided</scope>
     </dependency>
     <dependency>
+      <groupId>${pom.groupId}</groupId>
+      <artifactId>org.osgi.compendium</artifactId>
+      <version>0.9.0-incubator-SNAPSHOT</version>
+      <scope>provided</scope>
+    </dependency>
+    <dependency>
       <groupId>asm</groupId>
       <artifactId>asm</artifactId>
       <version>2.2.1</version>
@@ -39,13 +45,14 @@
             <Bundle-Vendor>Clement ESCOFFIER</Bundle-Vendor>
             <Bundle-Description> iPOJO </Bundle-Description>
             <Import-Package>
-              org.osgi.framework; version="1.3", 
-              org.osgi.service.cm; version="1.2",
-              org.osgi.service.log; version="1.3"
+              org.osgi.framework, 
+              org.osgi.service.cm,
+              org.osgi.service.log
             </Import-Package>
             <Private-Package>
     			org.apache.felix.ipojo.composite.architecture,
     			org.apache.felix.ipojo.composite.service*,
+    			org.apache.felix.ipojo.composite.instance,
     			org.apache.felix.ipojo.handlers.architecture,
     			org.apache.felix.ipojo.handlers.configuration,
     			org.apache.felix.ipojo.handlers.dependency.nullable,
@@ -61,8 +68,8 @@
               org.apache.felix.ipojo.handlers.dependency; version="0.7.1",
               org.apache.felix.ipojo.handlers.providedservice; version="0.7.1", 
               org.apache.felix.ipojo.composite; version="0.7.1",
-              org.osgi.service.cm; version="1.2",
-              org.osgi.service.log; version="1.3"
+              org.osgi.service.cm,
+              org.osgi.service.log
             </Export-Package>
           </instructions>
         </configuration>
diff --git a/ipojo/src/main/java/org/apache/felix/ipojo/ComponentFactory.java b/ipojo/src/main/java/org/apache/felix/ipojo/ComponentFactory.java
index 8fa9012..50db0fa 100644
--- a/ipojo/src/main/java/org/apache/felix/ipojo/ComponentFactory.java
+++ b/ipojo/src/main/java/org/apache/felix/ipojo/ComponentFactory.java
@@ -109,11 +109,6 @@
      * Logger for the factory (and all component instance).
      */
     private Logger m_logger;
-
-    /**
-     * True when the factory is active (non stopping and non starting).
-     */
-    private boolean m_active = false;
     
     /**
      * Index used to generate instance name if not set.
@@ -289,34 +284,36 @@
      * Stop all the instance managers.
      */
     public synchronized void stop() {
-        m_active = false;
         Collection col = m_componentInstances.values();
         Iterator it = col.iterator();
         while (it.hasNext()) {
             ComponentInstance ci = (ComponentInstance) it.next();
             if (ci.isStarted()) {
-                ci.dispose();
+                if (ci instanceof CompositeManager) { 
+                    ((CompositeManager) ci).kill();
+                } else { 
+                    ((InstanceManager) ci).kill(); 
+                } 
             }
         }
 
         m_logger.stop();
-
+        
         m_componentInstances.clear();
         if (m_sr != null) {
             m_sr.unregister();
         }
         m_sr = null;
-
+        m_componentDesc = null;
     }
 
     /**
      * Start all the instance managers.
      */
     public synchronized void start() {
-        if (m_active) {
+        if (m_componentDesc != null) { // Already started.
             return;
-        } // Already started
-
+        }
         Properties props = new Properties();
 
         // create a ghost component
@@ -354,19 +351,16 @@
         props.put(Constants.SERVICE_PID, m_factoryName);
 
         // Exposition of the factory service
-        m_active = true;
         m_sr = m_context.registerService(new String[] { Factory.class.getName(), ManagedServiceFactory.class.getName() }, this, props);
     }
 
     /**
-     * Callback called by instance when stopped.
+     * Callback called by instance when disposed.
      * 
-     * @param ci : the instance stopping
+     * @param ci : the destroyed instance
      */
-    protected synchronized void stopped(ComponentInstance ci) {
-        if (m_active) {
-            m_componentInstances.remove(ci.getInstanceName());
-        }
+    protected synchronized void disposed(ComponentInstance ci) {
+        m_componentInstances.remove(ci.getInstanceName());
     }
 
     /**
diff --git a/ipojo/src/main/java/org/apache/felix/ipojo/ComponentInstance.java b/ipojo/src/main/java/org/apache/felix/ipojo/ComponentInstance.java
index 3dd5abe..4883c06 100644
--- a/ipojo/src/main/java/org/apache/felix/ipojo/ComponentInstance.java
+++ b/ipojo/src/main/java/org/apache/felix/ipojo/ComponentInstance.java
@@ -32,6 +32,11 @@
 public interface ComponentInstance {
 
     /**
+     * Component Instance State : DISPOSED. The instance was destroyed.
+     */
+    int DISPOSED = -1;
+    
+    /**
      * Component Instance State : STOPPED. The component instance is not
      * started.
      */
@@ -116,5 +121,17 @@
      * @param configuration : the new configuration.
      */
     void reconfigure(Dictionary configuration);
+    
+    /**
+     * Add an instance state listener on the current instance.
+     * @param listener : the listener to add.
+     */
+    void addInstanceStateListener(InstanceStateListener listener);
+    
+    /**
+     * Remove an instance state listener on the current instance.
+     * @param listener : the listener to remove.
+     */
+    void removeInstanceStateListener(InstanceStateListener listener);
 
 }
diff --git a/ipojo/src/main/java/org/apache/felix/ipojo/CompositeManager.java b/ipojo/src/main/java/org/apache/felix/ipojo/CompositeManager.java
index 19b461a..3d8f438 100644
--- a/ipojo/src/main/java/org/apache/felix/ipojo/CompositeManager.java
+++ b/ipojo/src/main/java/org/apache/felix/ipojo/CompositeManager.java
@@ -63,6 +63,12 @@
      * Component state (STOPPED at the beginning).
      */
     private int m_state = STOPPED;
+    
+    /**
+     * Instance State Listener List.
+     */
+    private InstanceStateListener[] m_instanceListeners = new InstanceStateListener[0];
+
 
     /**
      * Component type information.
@@ -252,6 +258,10 @@
 
         m_internalContext.stop(); // Turn off the factory tracking
         m_state = STOPPED;
+        
+        for (int i = 0; i < m_instanceListeners.length; i++) {
+            m_instanceListeners[i].stateChanged(this, STOPPED);
+        }
     }
     
     /** 
@@ -259,18 +269,39 @@
      * @see org.apache.felix.ipojo.ComponentInstance#dispose()
      */
     public void dispose() {
-        if (m_state != STOPPED) {
+        if (m_state > STOPPED) {
             stop();
         }
         
-        m_factory.stopped(this);
+        for (int i = 0; i < m_instanceListeners.length; i++) {
+            m_instanceListeners[i].stateChanged(this, DISPOSED);
+        }
+        
+        m_factory.disposed(this);
 
         // Cleaning
-        m_factory = null;
-        m_name = null;
-        m_context = null;
-        m_handlers = null;
-        m_componentDesc = null;
+        m_state = DISPOSED;
+        m_handlers = new CompositeHandler[0];
+        m_instanceListeners = new InstanceStateListener[0];
+    }
+    
+    /**
+     * Kill the current instance.
+     * Only the factory of this instance can call this method.
+     */
+    protected void kill() {
+        if (m_state > STOPPED) {
+            stop();
+        }
+        
+        for (int i = 0; i < m_instanceListeners.length; i++) {
+            m_instanceListeners[i].stateChanged(this, DISPOSED);
+        }
+
+        // Cleaning
+        m_state = DISPOSED;
+        m_handlers = new CompositeHandler[0];
+        m_instanceListeners = new InstanceStateListener[0];
     }
 
     /**
@@ -294,6 +325,10 @@
             for (int i = m_handlers.length - 1; i > -1; i--) {
                 m_handlers[i].stateChanged(state);
             }
+            
+            for (int i = 0; i < m_instanceListeners.length; i++) {
+                m_instanceListeners[i].stateChanged(this, state);
+            }
         }
     }
 
@@ -314,6 +349,56 @@
     public boolean isStarted() {
         return m_state != STOPPED;
     }
+    
+    /**
+     * Add an instance to the created instance list.
+     * @param listener : the instance state listener to add.
+     * @see org.apache.felix.ipojo.ComponentInstance#addInstanceStateListener(org.apache.felix.ipojo.InstanceStateListener)
+     */
+    public void addInstanceStateListener(InstanceStateListener listener) {
+        for (int i = 0; (m_instanceListeners != null) && (i < m_instanceListeners.length); i++) {
+            if (m_instanceListeners[i] == listener) {
+                return;
+            }
+        }
+
+        if (m_instanceListeners.length > 0) {
+            InstanceStateListener[] newInstances = new InstanceStateListener[m_instanceListeners.length + 1];
+            System.arraycopy(m_instanceListeners, 0, newInstances, 0, m_instanceListeners.length);
+            newInstances[m_instanceListeners.length] = listener;
+            m_instanceListeners = newInstances;
+        } else {
+            m_instanceListeners = new InstanceStateListener[] { listener };
+        }
+    }
+    
+    /**
+     * Remove an instance state listener.
+     * @param listener : the listener to remove
+     * @see org.apache.felix.ipojo.ComponentInstance#removeInstanceStateListener(org.apache.felix.ipojo.InstanceStateListener)
+     */
+    public void removeInstanceStateListener(InstanceStateListener listener) {
+        int idx = -1;
+        for (int i = 0; i < m_instanceListeners.length; i++) {
+            if (m_instanceListeners[i] == listener) {
+                idx = i;
+                break;
+            }
+        }
+        
+        if (idx >= 0) {
+            if ((m_instanceListeners.length - 1) == 0) {
+                m_instanceListeners = new InstanceStateListener[0];
+            } else {
+                InstanceStateListener[] newInstances = new InstanceStateListener[m_instanceListeners.length - 1];
+                System.arraycopy(m_instanceListeners, 0, newInstances, 0, idx);
+                if (idx < newInstances.length) {
+                    System.arraycopy(m_instanceListeners, idx + 1, newInstances, idx, newInstances.length - idx);
+                }
+                m_instanceListeners = newInstances;
+            }
+        }
+    }
 
     // ===================== end Lifecycle management =====================
 
diff --git a/ipojo/src/main/java/org/apache/felix/ipojo/IPojoConfiguration.java b/ipojo/src/main/java/org/apache/felix/ipojo/IPojoConfiguration.java
index 706a767..ec6f56f 100644
--- a/ipojo/src/main/java/org/apache/felix/ipojo/IPojoConfiguration.java
+++ b/ipojo/src/main/java/org/apache/felix/ipojo/IPojoConfiguration.java
@@ -18,6 +18,7 @@
  */
 package org.apache.felix.ipojo;
 
+import org.apache.felix.ipojo.composite.instance.InstanceHandler;
 import org.apache.felix.ipojo.composite.service.importer.ImportExportHandler;
 import org.apache.felix.ipojo.composite.service.instantiator.ServiceInstantiatorHandler;
 import org.apache.felix.ipojo.handlers.architecture.ArchitectureHandler;
@@ -56,6 +57,7 @@
     public static final Class[] INTERNAL_COMPOSITE_HANDLERS = new Class[] { 
         ServiceInstantiatorHandler.class, 
         ImportExportHandler.class,
+        InstanceHandler.class,
         org.apache.felix.ipojo.composite.service.provides.ProvidedServiceHandler.class,
         org.apache.felix.ipojo.composite.architecture.ArchitectureHandler.class
     };
diff --git a/ipojo/src/main/java/org/apache/felix/ipojo/InstanceManager.java b/ipojo/src/main/java/org/apache/felix/ipojo/InstanceManager.java
index 772c556..75f36a2 100644
--- a/ipojo/src/main/java/org/apache/felix/ipojo/InstanceManager.java
+++ b/ipojo/src/main/java/org/apache/felix/ipojo/InstanceManager.java
@@ -81,6 +81,11 @@
      * Instances of the components.
      */
     private Object[] m_pojoObjects = new Object[0];
+    
+    /**
+     * Instance State Listener List.
+     */
+    private InstanceStateListener[] m_instanceListeners = new InstanceStateListener[0];
 
     /**
      * Component type information.
@@ -127,7 +132,7 @@
 
         // Add the name
         m_name = (String) configuration.get("name");
-
+        
         // Create the standard handlers and add these handlers to the list
         for (int i = 0; i < IPojoConfiguration.INTERNAL_HANDLERS.length; i++) {
             // Create a new instance
@@ -260,6 +265,9 @@
         m_pojoObjects = new Object[0];
 
         m_state = STOPPED;
+        for (int i = 0; i < m_instanceListeners.length; i++) {
+            m_instanceListeners[i].stateChanged(this, STOPPED);
+        }
     }
     
     /** 
@@ -267,22 +275,44 @@
      * @see org.apache.felix.ipojo.ComponentInstance#dispose()
      */
     public void dispose() {
-        if (m_state != STOPPED) {
+        if (m_state > STOPPED) { // Valid or invalid
             stop();
         }
         
-        m_factory.stopped(this);
+        for (int i = 0; i < m_instanceListeners.length; i++) {
+            m_instanceListeners[i].stateChanged(this, DISPOSED);
+        }
+        
+        m_factory.disposed(this);
 
         // Cleaning
-        m_factory = null;
-        m_name = null;
-        m_className = null;
-        m_context = null;
-        m_handlers = null;
-        m_fieldRegistration = null;
+        m_handlers = new Handler[0];
+        m_fieldRegistration = new HashMap();
         m_clazz = null;
-        m_pojoObjects = null;
-        m_componentDesc = null;
+        m_pojoObjects = new Object[0];
+        m_instanceListeners = new InstanceStateListener[0];
+    }
+    
+    /**
+     * Kill the current instance.
+     * Only the factory of this instance can call this method.
+     */
+    protected void kill() {
+        if (m_state > STOPPED) {
+            stop();
+        }
+        
+        for (int i = 0; i < m_instanceListeners.length; i++) {
+            m_instanceListeners[i].stateChanged(this, DISPOSED);
+        }
+
+        // Cleaning
+        m_state = DISPOSED;
+        m_handlers = new Handler[0];
+        m_fieldRegistration = new HashMap();
+        m_clazz = null;
+        m_pojoObjects = new Object[0];
+        m_instanceListeners = new InstanceStateListener[0];
     }
 
     /**
@@ -306,6 +336,10 @@
             for (int i = m_handlers.length - 1; i > -1; i--) {
                 m_handlers[i].stateChanged(state);
             }
+            
+            for (int i = 0; i < m_instanceListeners.length; i++) {
+                m_instanceListeners[i].stateChanged(this, state);
+            }
         }
     }
 
@@ -324,7 +358,57 @@
      * @see org.apache.felix.ipojo.ComponentInstance#isStarted()
      */
     public boolean isStarted() {
-        return m_state != STOPPED;
+        return m_state > STOPPED;
+    }
+    
+    /**
+     * Add an instance to the created instance list.
+     * @param listener : the instance state listener to add.
+     * @see org.apache.felix.ipojo.ComponentInstance#addInstanceStateListener(org.apache.felix.ipojo.InstanceStateListener)
+     */
+    public void addInstanceStateListener(InstanceStateListener listener) {
+        for (int i = 0; (m_instanceListeners != null) && (i < m_instanceListeners.length); i++) {
+            if (m_instanceListeners[i] == listener) {
+                return;
+            }
+        }
+
+        if (m_instanceListeners.length > 0) {
+            InstanceStateListener[] newInstances = new InstanceStateListener[m_instanceListeners.length + 1];
+            System.arraycopy(m_instanceListeners, 0, newInstances, 0, m_instanceListeners.length);
+            newInstances[m_instanceListeners.length] = listener;
+            m_instanceListeners = newInstances;
+        } else {
+            m_instanceListeners = new InstanceStateListener[] { listener };
+        }
+    }
+    
+    /**
+     * Remove an instance state listener.
+     * @param listener : the listener to remove
+     * @see org.apache.felix.ipojo.ComponentInstance#removeInstanceStateListener(org.apache.felix.ipojo.InstanceStateListener)
+     */
+    public void removeInstanceStateListener(InstanceStateListener listener) {
+        int idx = -1;
+        for (int i = 0; i < m_instanceListeners.length; i++) {
+            if (m_instanceListeners[i] == listener) {
+                idx = i;
+                break;
+            }
+        }
+        
+        if (idx >= 0) {
+            if ((m_instanceListeners.length - 1) == 0) {
+                m_instanceListeners = new InstanceStateListener[0];
+            } else {
+                InstanceStateListener[] newInstances = new InstanceStateListener[m_instanceListeners.length - 1];
+                System.arraycopy(m_instanceListeners, 0, newInstances, 0, idx);
+                if (idx < newInstances.length) {
+                    System.arraycopy(m_instanceListeners, idx + 1, newInstances, idx, newInstances.length - idx);
+                }
+                m_instanceListeners = newInstances;
+            }
+        }
     }
 
     // ===================== end Lifecycle management =====================
@@ -398,7 +482,7 @@
 
         if (idx >= 0) {
             if ((m_pojoObjects.length - 1) == 0) {
-                m_pojoObjects = new Element[0];
+                m_pojoObjects = new Object[0];
             } else {
                 Object[] newInstances = new Object[m_pojoObjects.length - 1];
                 System.arraycopy(m_pojoObjects, 0, newInstances, 0, idx);
@@ -479,8 +563,6 @@
             e.printStackTrace();
         }
 
-        m_factory.getLogger().log(Logger.INFO, "[" + m_name + "] createInstance -> Return the instance " + instance);
-
         // Register the new instance
         addInstance(instance);
         // Call createInstance on Handlers :
@@ -689,13 +771,14 @@
      * Check the state of all handlers.
      */
     public void checkInstanceState() {
-        m_factory.getLogger().log(Logger.INFO, "[" + m_name + "] Check the instance state");
+        if (!isStarted()) { return; }
+        
         boolean isValid = true;
         for (int i = 0; i < m_handlers.length; i++) {
             boolean b = m_handlers[i].isValid();
             isValid = isValid && b;
         }
-
+     
         // Update the component state if necessary
         if (!isValid && m_state == VALID) {
             // Need to update the state to UNRESOLVED
diff --git a/ipojo/src/main/java/org/apache/felix/ipojo/InstanceStateListener.java b/ipojo/src/main/java/org/apache/felix/ipojo/InstanceStateListener.java
new file mode 100644
index 0000000..ca2659f
--- /dev/null
+++ b/ipojo/src/main/java/org/apache/felix/ipojo/InstanceStateListener.java
@@ -0,0 +1,35 @@
+/* 
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.felix.ipojo;
+
+/**
+ * Instance state listener.
+ * This listener allows anyone to be notified when the listened instance state changes. 
+ * @author <a href="mailto:felix-dev@incubator.apache.org">Felix Project Team</a>
+ */
+public interface InstanceStateListener {
+    
+    /**
+     * State change listener.
+     * Each time an instance state change, this method is called.
+     * @param instance : changing instance
+     * @param newState : new instance state
+     */
+    void stateChanged(ComponentInstance instance, int newState);
+}
diff --git a/ipojo/src/main/java/org/apache/felix/ipojo/architecture/InstanceDescription.java b/ipojo/src/main/java/org/apache/felix/ipojo/architecture/InstanceDescription.java
index 2e6c55d..eef38a1 100644
--- a/ipojo/src/main/java/org/apache/felix/ipojo/architecture/InstanceDescription.java
+++ b/ipojo/src/main/java/org/apache/felix/ipojo/architecture/InstanceDescription.java
@@ -212,6 +212,9 @@
         if (m_state == ComponentInstance.INVALID) {
             instance.addAttribute(new Attribute("state", "invalid"));
         }
+        if (m_state == ComponentInstance.DISPOSED) {
+            instance.addAttribute(new Attribute("state", "disposed"));
+        }
         // Bundle
         instance.addAttribute(new Attribute("bundle", "" + m_bundleId));
 
diff --git a/ipojo/src/main/java/org/apache/felix/ipojo/composite/ServiceRegistry.java b/ipojo/src/main/java/org/apache/felix/ipojo/composite/ServiceRegistry.java
index 857e123..0c2df57 100644
--- a/ipojo/src/main/java/org/apache/felix/ipojo/composite/ServiceRegistry.java
+++ b/ipojo/src/main/java/org/apache/felix/ipojo/composite/ServiceRegistry.java
@@ -242,8 +242,7 @@
                 ServiceReference[] refs = getServiceReferences(clazz, null);
                 if (refs != null) {
                     return refs[0];
-                } // If the refs != null we are sure that it exist one
-                // references or more.
+                } // If the refs != null we are sure that it exists one reference or more.
             } catch (InvalidSyntaxException ex) {
                 System.err.println("Scope Service Registry : Problem when look for service reference" + ex.getMessage());
             }
diff --git a/ipojo/src/main/java/org/apache/felix/ipojo/composite/instance/InstanceHandler.java b/ipojo/src/main/java/org/apache/felix/ipojo/composite/instance/InstanceHandler.java
new file mode 100644
index 0000000..568c985
--- /dev/null
+++ b/ipojo/src/main/java/org/apache/felix/ipojo/composite/instance/InstanceHandler.java
@@ -0,0 +1,414 @@
+/* 
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.felix.ipojo.composite.instance;
+
+import java.util.Dictionary;
+import java.util.Properties;
+
+import org.apache.felix.ipojo.ComponentInstance;
+import org.apache.felix.ipojo.CompositeHandler;
+import org.apache.felix.ipojo.CompositeManager;
+import org.apache.felix.ipojo.Factory;
+import org.apache.felix.ipojo.InstanceManager;
+import org.apache.felix.ipojo.InstanceStateListener;
+import org.apache.felix.ipojo.ServiceContext;
+import org.apache.felix.ipojo.UnacceptableConfiguration;
+import org.apache.felix.ipojo.architecture.HandlerDescription;
+import org.apache.felix.ipojo.metadata.Element;
+import org.apache.felix.ipojo.parser.ParseException;
+import org.apache.felix.ipojo.util.Logger;
+import org.osgi.framework.BundleContext;
+import org.osgi.framework.InvalidSyntaxException;
+import org.osgi.framework.ServiceEvent;
+import org.osgi.framework.ServiceListener;
+import org.osgi.framework.ServiceReference;
+
+/**
+ * Composite Instance Handler.
+ * This handler allo to create an instance inside a composite.
+ * This instance is determine by its type and a configuration.
+ * @author <a href="mailto:felix-dev@incubator.apache.org">Felix Project Team</a>
+ */
+public class InstanceHandler extends CompositeHandler implements ServiceListener, InstanceStateListener {
+
+    /**
+     * Bundle context.
+     */
+    private BundleContext m_context;
+    
+    /**
+     * Internal context.
+     */
+    private ServiceContext m_scope;
+    
+    /**
+     * Instance logger.
+     */
+    private Logger m_logger;
+    
+    /**
+     * Composite Manager.
+     */
+    private CompositeManager m_manager;
+    
+    /**
+     * IS the handler valid ?
+     */
+    private boolean m_validity = false;
+    
+    /**
+     * This structure aims to manage a configuration. It stores all necessary
+     * information to create an instance and to track the factory.
+     */
+    private class ManagedConfiguration {
+        /**
+         * Configuration of the instance to create.
+         */
+        private Dictionary m_configuration;
+
+        /**
+         * Factory name.
+         */
+        private String m_factoryName;
+
+        /**
+         * Created instance.
+         */
+        private ComponentInstance m_instance;
+
+        /**
+         * Constructor.
+         * 
+         * @param conf : the configuration to create.
+         */
+        ManagedConfiguration(Dictionary conf) {
+            m_configuration = conf;
+        }
+
+        /**
+         * Return the managed configuration.
+         * @return the configuration.
+         */
+        Dictionary getConfiguration() {
+            return m_configuration;
+        }
+
+        /**
+         * Return the used factory name.
+         * @return the factory
+         */
+        String getFactory() {
+            return m_factoryName;
+        }
+
+        /**
+         * Return the created instance.
+         * @return the instance (or null if no instance are created).
+         */
+        ComponentInstance getInstance() {
+            return m_instance;
+        }
+
+        /**
+         * Set the factory name.
+         * 
+         * @param name : the factory name.
+         */
+        void setFactory(String name) {
+            m_factoryName = name;
+        }
+
+        /**
+         * Set the instance object.
+         * 
+         * @param instance : the instance
+         */
+        void setInstance(ComponentInstance instance) {
+            m_instance = instance;
+        }
+    }
+
+    /**
+     * Configurations to create and maintains.
+     */
+    private ManagedConfiguration[] m_configurations = new ManagedConfiguration[0];
+
+    /**
+     * Create an instance using the given factory and the given configuration.
+     * 
+     * @param fact : the facotry name to used.
+     * @param config : the configuration.
+     */
+    private void createInstance(Factory fact, ManagedConfiguration config) {
+        Dictionary conf = config.getConfiguration();
+        try {
+            config.setInstance(fact.createComponentInstance(conf, m_scope));
+            config.setFactory(fact.getName());
+            config.getInstance().addInstanceStateListener(this);
+        } catch (UnacceptableConfiguration e) {
+            m_logger.log(Logger.ERROR, "A factory is available for the configuration but the configuration is not acceptable", e);
+        }
+    }
+
+    /**
+     * Service Listener implementation.
+     * @param ev : the service event
+     * @see org.osgi.framework.ServiceListener#serviceChanged(org.osgi.framework.ServiceEvent)
+     */
+    public void serviceChanged(ServiceEvent ev) {
+        ServiceReference ref = ev.getServiceReference();
+        String factoryName = (String) ref.getProperty(org.osgi.framework.Constants.SERVICE_PID);
+        String componentClass = (String) ref.getProperty("component.class");
+        boolean implicated = false;
+        if (ev.getType() == ServiceEvent.REGISTERED) {
+            for (int i = 0; i < m_configurations.length; i++) {
+                if (m_configurations[i].getInstance() == null
+                        && (m_configurations[i].getConfiguration().get("component").equals(factoryName)
+                        || m_configurations[i].getConfiguration().get("component").equals(componentClass))) {
+                    Factory fact = (Factory) m_context.getService(ref);
+                    createInstance(fact, m_configurations[i]);
+                    implicated = true;
+                }
+            }
+            if (implicated && !m_validity && checkValidity()) {
+                m_manager.checkInstanceState();
+            }
+            return;
+        }
+
+        if (ev.getType() == ServiceEvent.UNREGISTERING) {
+            for (int i = 0; i < m_configurations.length; i++) {
+                if (m_configurations[i].getInstance() != null && m_configurations[i].getFactory().equals(factoryName)) {
+                    m_configurations[i].setInstance(null);
+                    m_configurations[i].setFactory(null);
+                    m_context.ungetService(ref);
+                    implicated = true;
+                }
+            }
+            if (implicated && m_validity && !checkValidity()) {
+                m_manager.checkInstanceState();
+            }
+            return;
+        }
+    }
+
+    /**
+     * Stop all created instances.
+     */
+    public synchronized void stop() {
+        m_context.removeServiceListener(this);
+        for (int i = 0; i < m_configurations.length; i++) {
+            if (m_configurations[i].getInstance() != null) {
+                m_configurations[i].getInstance().removeInstanceStateListener(this);
+                m_configurations[i].getInstance().dispose();
+            }
+            m_configurations[i].setInstance(null);
+            m_configurations[i].setFactory(null);
+        }
+        m_configurations = null;
+    }
+    
+    
+    /**
+     * Configrue method.
+     * @param im : instance manager.
+     * @param metadata : component type metadata.
+     * @param configuration : instance configuration.
+     * @see org.apache.felix.ipojo.CompositeHandler#configure(org.apache.felix.ipojo.CompositeManager, org.apache.felix.ipojo.metadata.Element, java.util.Dictionary)
+     */
+    public void configure(CompositeManager im, Element metadata, Dictionary configuration) {
+        m_manager = im;
+        m_context = im.getContext();
+        m_logger = im.getFactory().getLogger();
+        m_scope = im.getServiceContext();
+        Element[] instances = metadata.getElements("instance");
+        m_configurations = new ManagedConfiguration[instances.length];
+        for (int i = 0; i < instances.length; i++) {
+            Dictionary conf = null;
+            try {
+                conf = parseInstance(instances[i]);
+            } catch (ParseException e) {
+                m_logger.log(Logger.ERROR, "An instance cannot be parsed correctly", e);
+                return;
+            }
+            m_configurations[i] = new ManagedConfiguration(conf);
+        }
+
+        if (m_configurations.length > 0) {
+            im.register(this);
+        }
+    }
+    
+    /**
+     * Parse an Element to get a dictionary.
+     * 
+     * @param instance : the Element describing an instance.
+     * @return : the resulting dictionary
+     * @throws ParseException : occurs when a configuration cannot be parse correctly.
+     */
+    private Dictionary parseInstance(Element instance) throws ParseException {
+        Dictionary dict = new Properties();
+        if (instance.containsAttribute("name")) {
+            dict.put("name", instance.getAttribute("name"));
+        }
+        if (!instance.containsAttribute("component")) {
+            throw new ParseException("An instance does not have the 'component' attribute");
+        }
+        
+        dict.put("component", instance.getAttribute("component"));
+
+        for (int i = 0; i < instance.getElements("property").length; i++) {
+            parseProperty(instance.getElements("property")[i], dict);
+        }
+
+        return dict;
+    }
+    
+    /**
+     * Parse a property.
+     * @param prop : the current element to parse
+     * @param dict : the dictionary to populate
+     * @throws ParseException : occurs if the proeprty cannot be parsed correctly
+     */
+    private void parseProperty(Element prop, Dictionary dict) throws ParseException {
+        // Check that the property has a name
+        if (!prop.containsAttribute("name")) {
+            throw new ParseException("A property does not have the 'name' attribute");
+        }
+        // Final case : the property element has a 'value' attribute
+        if (prop.containsAttribute("value")) {
+            dict.put(prop.getAttribute("name"), prop.getAttribute("value"));
+        } else {
+            // Recursive case
+            // Check if there is 'property' element
+            Element[] subProps = prop.getElements("property");
+            if (subProps.length == 0) {
+                throw new ParseException("A complex property must have at least one 'property' sub-element");
+            }
+            Dictionary dict2 = new Properties();
+            for (int i = 0; i < subProps.length; i++) {
+                parseProperty(subProps[i], dict2);
+                dict.put(prop.getAttribute("name"), dict2);
+            }
+        }
+    }
+
+    /**
+     * Start method.
+     * @see org.apache.felix.ipojo.CompositeHandler#start()
+     */
+    public void start() {
+        for (int i = 0; i < m_configurations.length; i++) {
+
+            // Get the component type name :
+            String componentType = (String) m_configurations[i].getConfiguration().get("component");
+            Factory fact = null;
+
+            try {
+                String fil = "(|(" + org.osgi.framework.Constants.SERVICE_PID + "=" + componentType + ")(component.class=" + componentType + "))";
+                ServiceReference[] refs = m_context.getServiceReferences(org.apache.felix.ipojo.Factory.class.getName(), fil);
+                if (refs != null) {
+                    fact = (Factory) m_context.getService(refs[0]);
+                    createInstance(fact, m_configurations[i]);
+                }
+            } catch (InvalidSyntaxException e) {
+                m_logger.log(Logger.ERROR, "Invalid syntax filter for the type : " + componentType, e);
+            }
+        }
+
+        // Register a service listenner on Factory Service
+        try {
+            m_context.addServiceListener(this, "(objectClass=" + Factory.class.getName() + ")");
+        } catch (InvalidSyntaxException e) {
+            m_logger.log(Logger.ERROR, "Invalid syntax filter when registering a listener on Factory Service", e);
+        }
+        
+        //Compute validity 
+        checkValidity();
+    }
+    
+    /**
+     * The handler is valid if all managed instances are created and are valid.
+     * @return true if all managed configuration have been instanciated and are valid.
+     * @see org.apache.felix.ipojo.CompositeHandler#isValid()
+     */
+    public boolean isValid() {
+        return m_validity;
+    }
+    
+    /**
+     * Check handler validity.
+     * The method update the m_validity field.
+     * @return the new validity.
+     */
+    private boolean checkValidity() {
+        for (int i = 0; i < m_configurations.length; i++) {
+            if (m_configurations[i].getInstance() == null || m_configurations[i].getInstance().getState() != ComponentInstance.VALID) {
+                m_validity = false;
+                return false;
+            }
+        }
+        m_validity = true;
+        return true;
+    }
+
+    /** Instance state listener.
+     *  This method listens when managed instance states change.
+     *  @param instance : instance
+     *  @param newState : the now state of the given instance
+     *  @see org.apache.felix.ipojo.InstanceStateListener#stateChanged(org.apache.felix.ipojo.ComponentInstance, int)
+     */
+    public void stateChanged(ComponentInstance instance, int newState) {
+        switch(newState) {
+            case ComponentInstance.DISPOSED : 
+            case ComponentInstance.STOPPED :
+                break; // Should not happen
+            case ComponentInstance.VALID :
+                if (! m_validity && checkValidity()) { 
+                    m_manager.checkInstanceState();
+                }
+                break;
+            case ComponentInstance.INVALID :
+                if (m_validity && ! checkValidity()) {
+                    m_manager.checkInstanceState();
+                }
+        }
+    }
+    
+    /**
+     * Method returning an instance object of the given componenet type.
+     * This method must be coalled only on 'primitive' type.
+     * @param type : type.
+     * @return an instance object or null if not found.
+     */
+    public Object getObjectFromInstance(String type)  {
+        for (int i = 0; i < m_configurations.length; i++) {
+            if (m_configurations[i].getInstance() != null && type.equals(m_configurations[i].getFactory()) && m_configurations[i].getInstance().getState() == ComponentInstance.VALID) {
+                return ((InstanceManager) m_configurations[i].getInstance()).getPojoObject();
+            }
+        }
+        return null;
+    }
+    
+    public HandlerDescription getDescription() {
+        //TODO
+        return null;
+    }
+
+}
diff --git a/ipojo/src/main/java/org/apache/felix/ipojo/composite/instance/InstanceHandlerDescription.java b/ipojo/src/main/java/org/apache/felix/ipojo/composite/instance/InstanceHandlerDescription.java
new file mode 100644
index 0000000..4e84b82
--- /dev/null
+++ b/ipojo/src/main/java/org/apache/felix/ipojo/composite/instance/InstanceHandlerDescription.java
@@ -0,0 +1,81 @@
+/* 
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.felix.ipojo.composite.instance;
+
+import java.util.List;
+
+import org.apache.felix.ipojo.ComponentInstance;
+import org.apache.felix.ipojo.architecture.HandlerDescription;
+import org.apache.felix.ipojo.metadata.Attribute;
+import org.apache.felix.ipojo.metadata.Element;
+
+/**
+ * Description of the Instance Handler.
+ * 
+ * @author <a href="mailto:felix-dev@incubator.apache.org">Felix Project Team</a>
+ */
+public class InstanceHandlerDescription extends HandlerDescription {
+
+    /**
+     * List of managed instances.
+     */
+    private List m_instances;
+
+    /**
+     * Constructor.
+     * 
+     * @param arg0 : name of the handler
+     * @param arg1 : validity of the handler
+     * @param insts : list of component instances
+     */
+    public InstanceHandlerDescription(String arg0, boolean arg1, List insts) {
+        super(arg0, arg1);
+        m_instances = insts;
+    }
+
+    /**
+     * Build service instantiator handler description.
+     * @return the handler description
+     * @see org.apache.felix.ipojo.architecture.HandlerDescription#getHandlerInfo()
+     */
+    public Element getHandlerInfo() {
+        Element instances = super.getHandlerInfo();
+        for (int i = 0; i < m_instances.size(); i++) {
+            ComponentInstance inst = (ComponentInstance) m_instances.get(i);
+            Element instance = new Element("Instance", "");
+            instance.addAttribute(new Attribute("Name", inst.getInstanceName()));
+            String state = null;
+            switch(inst.getState()) {
+                case ComponentInstance.DISPOSED : 
+                    state = "disposed"; break;
+                case ComponentInstance.STOPPED : 
+                    state = "stopped"; break;
+                case ComponentInstance.VALID : 
+                    state = "valid"; break;
+                case ComponentInstance.INVALID : 
+                    state = "invalid"; break;
+            }
+            instance.addAttribute(new Attribute("State", state));
+            instance.addElement(inst.getInstanceDescription().getDescription());
+            instances.addElement(instances);
+        }
+        return instances;
+    }
+
+}
diff --git a/ipojo/src/main/java/org/apache/felix/ipojo/composite/service/instantiator/ServiceInstantiatorHandler.java b/ipojo/src/main/java/org/apache/felix/ipojo/composite/service/instantiator/ServiceInstantiatorHandler.java
index d641cb0..b005b20 100644
--- a/ipojo/src/main/java/org/apache/felix/ipojo/composite/service/instantiator/ServiceInstantiatorHandler.java
+++ b/ipojo/src/main/java/org/apache/felix/ipojo/composite/service/instantiator/ServiceInstantiatorHandler.java
@@ -148,8 +148,8 @@
         if (!m_isValid) {
             if (isValid()) {
                 m_manager.checkInstanceState();
+                m_isValid = true;
             }
-            m_isValid = true;
         }
     }
 
@@ -160,8 +160,8 @@
         if (m_isValid) {
             if (!isValid()) {
                 m_manager.checkInstanceState();
+                m_isValid = false;
             }
-            m_isValid = false;
         }
     }
 
diff --git a/ipojo/src/main/java/org/apache/felix/ipojo/composite/service/instantiator/SvcInstance.java b/ipojo/src/main/java/org/apache/felix/ipojo/composite/service/instantiator/SvcInstance.java
index 84f0221..57afd00 100644
--- a/ipojo/src/main/java/org/apache/felix/ipojo/composite/service/instantiator/SvcInstance.java
+++ b/ipojo/src/main/java/org/apache/felix/ipojo/composite/service/instantiator/SvcInstance.java
@@ -185,11 +185,10 @@
                 String k = (String) kk.nextElement();
                 p.put(k, m_configuration.get(k));
             }
-            
             ComponentInstance instance = factory.createComponentInstance(p);
             m_usedRef.put(ref, instance);
             m_context.ungetService(ref);
-        } catch (UnacceptableConfiguration e) {
+        } catch (Throwable e) {
             m_handler.getManager().getFactory().getLogger().log(Logger.ERROR,
                     "A matching factory (" + ref.getProperty("service.pid") + ") seems to refuse the given configuration : " + e.getMessage());
         }
diff --git a/ipojo/src/main/java/org/apache/felix/ipojo/composite/service/provides/CompositionMetadata.java b/ipojo/src/main/java/org/apache/felix/ipojo/composite/service/provides/CompositionMetadata.java
index a2ae734..420190d 100644
--- a/ipojo/src/main/java/org/apache/felix/ipojo/composite/service/provides/CompositionMetadata.java
+++ b/ipojo/src/main/java/org/apache/felix/ipojo/composite/service/provides/CompositionMetadata.java
@@ -27,12 +27,16 @@
 import java.util.Map;
 import java.util.Set;
 
+import org.apache.felix.ipojo.Factory;
 import org.apache.felix.ipojo.composite.service.provides.manipulation.Manipulator;
 import org.apache.felix.ipojo.composite.service.provides.manipulation.POJOWriter;
 import org.apache.felix.ipojo.metadata.Attribute;
 import org.apache.felix.ipojo.metadata.Element;
 import org.apache.felix.ipojo.util.Logger;
 import org.osgi.framework.BundleContext;
+import org.osgi.framework.Constants;
+import org.osgi.framework.InvalidSyntaxException;
+import org.osgi.framework.ServiceReference;
 
 /**
  * Check and build a compostion, i.e. a pojo containing the composition.
@@ -121,9 +125,34 @@
 
     /**
      * Build Available Mappings.
+     * @throws CompositionException : a factory is not available, the composition cannot be checked.
      */
-    private void buildAvailableMappingList() {
+    private void buildAvailableMappingList() throws CompositionException {
         int index = 0;
+        
+        for (int i = 0; i < m_handler.getInstanceType().size(); i++) {
+            String type = (String) m_handler.getInstanceType().get(i);
+            try {
+                ServiceReference[] refs = m_context.getServiceReferences(Factory.class.getName(), "(" + Constants.SERVICE_PID + "=" + type + ")");
+                if (refs == null) {
+                    m_handler.getManager().getFactory().getLogger().log(Logger.ERROR, "The factory " + type + " is not available, cannot check the composition");
+                    throw new CompositionException("The factory " + type + " needs to be available to check the composition");
+                } else {
+                    String className = (String) refs[0].getProperty("component.class");
+                    Class impl = m_context.getBundle().loadClass(className);
+                    SpecificationMetadata spec = new SpecificationMetadata(impl, type, m_handler);
+                    FieldMetadata field = new FieldMetadata(spec);
+                    field.setName("_field" + index);
+                    Mapping map = new Mapping(spec, field);
+                    m_mappings.add(map);
+                    index++;
+                }
+            } catch (InvalidSyntaxException e) {
+                m_handler.getManager().getFactory().getLogger().log(Logger.ERROR, "A LDAP filter is not valid : " + e.getMessage());
+            } catch (ClassNotFoundException e) {
+                m_handler.getManager().getFactory().getLogger().log(Logger.ERROR, "The implementation class of a component cannot be loaded : " + e.getMessage());
+            }
+        }
 
         for (int i = 0; i < m_handler.getSpecifications().size(); i++) {
             SpecificationMetadata spec = (SpecificationMetadata) m_handler.getSpecifications().get(i);
@@ -140,6 +169,7 @@
             index++;
         }
     }
+    
 
     /**
      * Build the delegation mapping.
@@ -149,38 +179,56 @@
         buildAvailableMappingList();
 
         // Dependency closure is OK, now look for method delegation
-        Map/* <MethodMetadata, Mapping> */availableMethods = new HashMap();
+        Map/* <MethodMetadata, Mapping> */availableSvcMethods = new HashMap();
+        Map/* <MethodMetadata, Mapping> */availableInstMethods = new HashMap();
 
         for (int i = 0; i < m_mappings.size(); i++) {
             Mapping map = (Mapping) m_mappings.get(i);
             SpecificationMetadata spec = map.getSpecification();
             for (int j = 0; j < spec.getMethods().size(); j++) {
                 MethodMetadata method = (MethodMetadata) spec.getMethods().get(j);
-                availableMethods.put(method, map);
+                if (spec.isInterface()) { 
+                    availableSvcMethods.put(method, map);
+                } else {
+                    availableInstMethods.put(method, map);
+                }
             }
         }
 
-        // For each needed method search if available and store the mapping
+        // For each needed method, search if available and store the mapping
         for (int j = 0; j < m_specification.getMethods().size(); j++) {
             MethodMetadata method = (MethodMetadata) m_specification.getMethods().get(j);
-            Set keys = availableMethods.keySet();
+            Set keys = availableInstMethods.keySet(); // Look first in methods contained in the glue code.
             Iterator it = keys.iterator();
             boolean found = false;
             while (it.hasNext() & !found) {
                 MethodMetadata met = (MethodMetadata) it.next();
                 if (met.equals(method)) {
                     found = true;
-                    FieldMetadata field = ((Mapping) availableMethods.get(met)).getField();
+                    FieldMetadata field = ((Mapping) availableInstMethods.get(met)).getField();
                     field.setUseful(true);
                     method.setDelegation(field);
-                    // Test optionality
-                    if (field.isOptional() && !method.getExceptions().contains("java/lang/UnsupportedOperationException")) {
-                        m_handler.getManager().getFactory().getLogger().log(Logger.WARNING, "The method " + method.getMethodName() + " could not be provided correctly : the specification " + field.getSpecification().getName() + " is optional");
+                }
+            }
+            if (!found) { // If not found looks inside method contained in services.
+                keys = availableSvcMethods.keySet(); // Look first in methods contained in the glue code
+                it = keys.iterator();
+                while (it.hasNext() & !found) {
+                    MethodMetadata met = (MethodMetadata) it.next();
+                    if (met.equals(method)) {
+                        found = true;
+                        FieldMetadata field = ((Mapping) availableSvcMethods.get(met)).getField();
+                        field.setUseful(true);
+                        method.setDelegation(field);
+                        // Test optionality
+                        if (field.isOptional() && !method.getExceptions().contains("java/lang/UnsupportedOperationException")) {
+                            m_handler.getManager().getFactory().getLogger().log(Logger.WARNING, "The method " + method.getMethodName() + " could not be provided correctly : the specification " + field.getSpecification().getName() + " is optional");
+                        }
                     }
                 }
             }
             if (!found) {
-                throw new CompositionException("Composition non consistent : " + method.getMethodName() + " could not be delegated");
+                throw new CompositionException("Unconsistent composition - the method " + method.getMethodName() + " could not be delegated");
             }
         }
     }
@@ -226,7 +274,7 @@
         List fields = getFieldList();
         for (int i = 0; i < fields.size(); i++) {
             FieldMetadata field = (FieldMetadata) fields.get(i);
-            if (field.isUseful()) {
+            if (field.isUseful() && field.getSpecification().isInterface()) {
                 Element dep = new Element("Dependency", "");
                 dep.addAttribute(new Attribute("field", field.getName()));
                 if (field.getSpecification().isOptional()) {
@@ -236,6 +284,19 @@
                 elem.addElement(dep);
             }
         }
+        
+        Element properties = new Element("properties", "");
+        for (int i = 0; i < fields.size(); i++) {
+            FieldMetadata field = (FieldMetadata) fields.get(i);
+            if (field.isUseful() &&  ! field.getSpecification().isInterface()) {
+                Element prop = new Element("Property", "");
+                prop.addAttribute(new Attribute("field", field.getName()));
+                properties.addElement(prop);
+            }
+        }
+        if (properties.getElements().length != 0) {
+            elem.addElement(properties);
+        }
 
         // Insert information to metadata
         Element manip = new Element("Manipulation", "");
@@ -268,7 +329,7 @@
      * Get the field list to use for the delegation.
      * @return the field list.
      */
-    private List getFieldList() {
+    public List getFieldList() {
         List list = new ArrayList();
         for (int i = 0; i < m_mappings.size(); i++) {
             Mapping map = (Mapping) m_mappings.get(i);
diff --git a/ipojo/src/main/java/org/apache/felix/ipojo/composite/service/provides/ProvidedService.java b/ipojo/src/main/java/org/apache/felix/ipojo/composite/service/provides/ProvidedService.java
index 633bf24..be77541 100644
--- a/ipojo/src/main/java/org/apache/felix/ipojo/composite/service/provides/ProvidedService.java
+++ b/ipojo/src/main/java/org/apache/felix/ipojo/composite/service/provides/ProvidedService.java
@@ -18,6 +18,7 @@
  */
 package org.apache.felix.ipojo.composite.service.provides;
 
+import java.util.List;
 import java.util.Properties;
 
 import org.apache.felix.ipojo.ComponentFactory;
@@ -25,7 +26,9 @@
 import org.apache.felix.ipojo.CompositeManager;
 import org.apache.felix.ipojo.ServiceContext;
 import org.apache.felix.ipojo.UnacceptableConfiguration;
+import org.apache.felix.ipojo.composite.instance.InstanceHandler;
 import org.apache.felix.ipojo.metadata.Element;
+import org.apache.felix.ipojo.util.Logger;
 import org.osgi.framework.BundleContext;
 import org.osgi.framework.Constants;
 
@@ -79,6 +82,11 @@
      * Exporter.
      */
     private ServiceExporter m_exports;
+    
+    /**
+     * Created instance name.
+     */
+    private String m_instanceName;
 
     /**
      * Constructor.
@@ -92,36 +100,28 @@
         m_scope = m_manager.getServiceContext();
         m_context = m_manager.getContext();
         m_composition = new CompositionMetadata(m_manager.getContext(), element, handler, name);
-        try {
-            m_composition.buildMapping();
-        } catch (CompositionException e) {
-            return;
-        }
     }
 
     /**
      * Start method.
      * Build service implementation type, factory and instance.
+     * @throws CompositionException if a consistent mapping cannot be discovered.
      */
-    public void start() {
-        String name = m_composition.getSpecificationMetadata().getName() + "Provider";
+    public void start() throws CompositionException {
+        m_composition.buildMapping();
+        
+        m_instanceName = m_composition.getSpecificationMetadata().getName() + "Provider";
         m_clazz = m_composition.buildPOJO();
-        m_metadata = m_composition.buildMetadata(name);
+        m_metadata = m_composition.buildMetadata(m_instanceName);
 
         // Create the factory
         m_factory = new ComponentFactory(m_context, m_clazz, m_metadata);
         m_factory.start();
 
-        Properties p = new Properties();
-        p.put("name", name);
-        try {
-            m_instance = m_factory.createComponentInstance(p, m_scope);
-        } catch (UnacceptableConfiguration e) {
-            return;
-        }
         // Create the exports
-        m_exports = new ServiceExporter(m_composition.getSpecificationMetadata().getName(), "(" + Constants.SERVICE_PID + "=" + name + ")", false, false,
+        m_exports = new ServiceExporter(m_composition.getSpecificationMetadata().getName(), "(" + Constants.SERVICE_PID + "=" + m_instanceName + ")", false, false,
                 m_scope, m_context, this);
+        m_exports.start();
     }
 
     /**
@@ -165,9 +165,9 @@
      * Unregister published service.
      */
     protected void unregister() {
-        if (m_exports != null) {
-            m_instance.stop();
-            m_exports.stop();
+        if (m_instance != null) {
+            m_instance.dispose();
+            m_instance = null;
         }
     }
 
@@ -176,11 +176,42 @@
      */
     protected void register() {
         if (m_exports != null) {
-            m_instance.start();
-            m_exports.start();
+            if (m_instance != null) { m_instance.dispose(); }
+            Properties p = new Properties();
+            p.put("name", m_instanceName);
+            List fields = m_composition.getFieldList();
+            for (int i = 0; i < fields.size(); i++) {
+                FieldMetadata fm = (FieldMetadata) fields.get(i);
+                if (fm.isUseful() && !fm.getSpecification().isInterface()) {
+                    String type = fm.getSpecification().getComponentType();
+                    Object o = getObjectByType(type);
+                    p.put(fm.getName(), o); 
+                }
+            }
+            try {
+                m_instance = m_factory.createComponentInstance(p, m_scope);
+            } catch (UnacceptableConfiguration e) {
+                e.printStackTrace();
+                return;
+            }
         }
     }
 
+    /**
+     * Get an object from the given type.
+     * @param type : type
+     * @return an object from an instance of this type or null
+     */
+    private Object getObjectByType(String type) {
+        InstanceHandler h = (InstanceHandler) m_manager.getCompositeHandler("org.apache.felix.ipojo.composite.instance.InstanceHandler");
+        Object o = h.getObjectFromInstance(type);
+        if (o == null) {
+            m_manager.getFactory().getLogger().log(Logger.ERROR, "An instance object cannot be found for the type : " + type);
+        }
+        return o;
+        
+    }
+
     public String getSpecification() {
         return m_composition.getSpecificationMetadata().getName();
     }
diff --git a/ipojo/src/main/java/org/apache/felix/ipojo/composite/service/provides/ProvidedServiceHandler.java b/ipojo/src/main/java/org/apache/felix/ipojo/composite/service/provides/ProvidedServiceHandler.java
index 9175f3a..e937b17 100644
--- a/ipojo/src/main/java/org/apache/felix/ipojo/composite/service/provides/ProvidedServiceHandler.java
+++ b/ipojo/src/main/java/org/apache/felix/ipojo/composite/service/provides/ProvidedServiceHandler.java
@@ -27,6 +27,7 @@
 import org.apache.felix.ipojo.CompositeManager;
 import org.apache.felix.ipojo.architecture.HandlerDescription;
 import org.apache.felix.ipojo.metadata.Element;
+import org.apache.felix.ipojo.util.Logger;
 import org.osgi.framework.BundleContext;
 
 /**
@@ -56,6 +57,16 @@
     private ArrayList m_managedServices = new ArrayList();
 
     /**
+     * Handler validity. False if
+     */
+    private boolean m_valid = false;
+
+    /**
+     * List of component type.
+     */
+    private ArrayList m_types;
+
+    /**
      * Configure the handler.
      * 
      * @param im : the instance manager
@@ -76,6 +87,7 @@
 
         // Compute imports and instances
         computeAvailableServices(metadata);
+        computeAvailableTypes(metadata);
 
         for (int i = 0; i < provides.length; i++) {
             ProvidedService ps = new ProvidedService(this, provides[i], "" + i);
@@ -94,9 +106,24 @@
     public void start() {
         for (int i = 0; i < m_managedServices.size(); i++) {
             ProvidedService ps = (ProvidedService) m_managedServices.get(i);
-            ps.start();
+            try {
+                ps.start();
+            } catch (CompositionException e) {
+                m_manager.getFactory().getLogger().log(Logger.ERROR, "Cannot start the provided service handler", e);
+                m_valid = false;
+                return;
+            }
         }
-
+        m_valid  = true;
+    }
+    
+    /**
+     * Check the handler validity.
+     * @return true if the handler is valid.
+     * @see org.apache.felix.ipojo.CompositeHandler#isValid()
+     */
+    public boolean isValid() {
+        return m_valid;
     }
 
     /**
@@ -188,5 +215,23 @@
     public HandlerDescription getDescription() {
         return new ProvidedServiceHandlerDescription(true, m_managedServices);
     }
+    
+    /**
+     * Build available instance type.
+     * 
+     * @param metadata : composite metadata
+     */
+    private void computeAvailableTypes(Element metadata) {
+        m_types = new ArrayList();
+        Element[] instances = metadata.getElements("instance", "");
+        for (int i = 0; i < instances.length; i++) {
+            String itf = instances[i].getAttribute("component");
+            m_types.add(itf);
+        }
+    }
+
+    public List getInstanceType() {
+        return m_types;
+    }
 
 }
diff --git a/ipojo/src/main/java/org/apache/felix/ipojo/composite/service/provides/SpecificationMetadata.java b/ipojo/src/main/java/org/apache/felix/ipojo/composite/service/provides/SpecificationMetadata.java
index b007a87..d45c862 100644
--- a/ipojo/src/main/java/org/apache/felix/ipojo/composite/service/provides/SpecificationMetadata.java
+++ b/ipojo/src/main/java/org/apache/felix/ipojo/composite/service/provides/SpecificationMetadata.java
@@ -20,6 +20,7 @@
 
 import java.io.IOException;
 import java.io.InputStream;
+import java.lang.reflect.Method;
 import java.net.URL;
 import java.util.ArrayList;
 
@@ -55,6 +56,16 @@
      * Is the specification optional?
      */
     private boolean m_isOptional = false;
+    
+    /**
+     * Is the specification an interface?
+     */
+    private boolean m_isInterface = true;
+    
+    /**
+     * Componenet Type.
+     */
+    private String m_componentType = null;
 
     /**
      * Reference on the handler.
@@ -141,6 +152,36 @@
         m_isAggregate = isAggregate;
         m_isOptional = isOptional;
     }
+    
+    /**
+     * Constructor.
+     * @param c : class
+     * @param type : componenet type
+     * @param psd : the parent handler
+     */
+    public SpecificationMetadata(Class c, String type, ProvidedServiceHandler psd) {
+        m_handler = psd;
+        m_isAggregate = false;
+        m_isOptional = false;
+        m_componentType = type;
+        m_name = c.getName();
+        Method[] methods = c.getMethods();
+        for (int i = 0; i < methods.length; i++) {
+            String desc = Type.getMethodDescriptor(methods[i]);
+            MethodMetadata method = new MethodMetadata(methods[i].getName(), desc);
+            Type[] args = Type.getArgumentTypes(desc);
+            Class[] exceptionClasses = methods[i].getExceptionTypes();
+            for (int j = 0; j < args.length; j++) {
+                method.addArgument(args[j].getClassName());
+            }
+            for (int j = 0; j < exceptionClasses.length; j++) {
+                method.addException(exceptionClasses[j].getName());
+            }
+
+            addMethod(method);
+        }
+        m_isInterface = false;
+    }
 
     public boolean isAggregate() {
         return m_isAggregate;
@@ -149,9 +190,17 @@
     public boolean isOptional() {
         return m_isOptional;
     }
+    
+    public boolean isInterface() {
+        return m_isInterface;
+    }
 
     public void setIsOptional(boolean optional) {
         m_isOptional = optional;
     }
+    
+    public String getComponentType() {
+        return m_componentType;
+    }
 
 }
diff --git a/ipojo/src/main/java/org/apache/felix/ipojo/composite/service/provides/manipulation/POJOWriter.java b/ipojo/src/main/java/org/apache/felix/ipojo/composite/service/provides/manipulation/POJOWriter.java
index 2dc57e1..36ae9bc 100644
--- a/ipojo/src/main/java/org/apache/felix/ipojo/composite/service/provides/manipulation/POJOWriter.java
+++ b/ipojo/src/main/java/org/apache/felix/ipojo/composite/service/provides/manipulation/POJOWriter.java
@@ -196,7 +196,11 @@
             }
 
             // Invoke
-            mv.visitMethodInsn(INVOKEINTERFACE, delegator.getSpecification().getName().replace('.', '/'), name, desc);
+            if (delegator.getSpecification().isInterface()) {
+                mv.visitMethodInsn(INVOKEINTERFACE, delegator.getSpecification().getName().replace('.', '/'), name, desc);
+            } else {
+                mv.visitMethodInsn(INVOKEVIRTUAL, delegator.getSpecification().getName().replace('.', '/'), name, desc);
+            }
 
             // Return
             writeReturn(Type.getReturnType(desc), mv);
diff --git a/ipojo/src/main/java/org/apache/felix/ipojo/handlers/dependency/Dependency.java b/ipojo/src/main/java/org/apache/felix/ipojo/handlers/dependency/Dependency.java
index 4e0b298..b98131b 100644
--- a/ipojo/src/main/java/org/apache/felix/ipojo/handlers/dependency/Dependency.java
+++ b/ipojo/src/main/java/org/apache/felix/ipojo/handlers/dependency/Dependency.java
@@ -613,8 +613,10 @@
      * Stop the dependency.
      */
     public void stop() {
+        m_handler.getInstanceManager().getContext().removeServiceListener(this);
+        
         m_handler.getInstanceManager().getFactory().getLogger().log(Logger.INFO,
-                "[" + m_handler.getInstanceManager().getClassName() + "] Stop a dependency on : " + m_specification + " with " + m_strFilter);
+                "[" + m_handler.getInstanceManager().getInstanceName() + "] Stop a dependency on : " + m_specification + " with " + m_strFilter + " (" + m_handler.getInstanceManager() + ")");
         m_state = UNRESOLVED;
 
         // Unget all services references
@@ -623,7 +625,6 @@
         }
 
         m_ref = new ServiceReference[0];
-        m_handler.getInstanceManager().getContext().removeServiceListener(this);
         m_clazz = null;
         m_services = new Object[0];
     }
diff --git a/ipojo/src/main/java/org/apache/felix/ipojo/handlers/dependency/DependencyHandler.java b/ipojo/src/main/java/org/apache/felix/ipojo/handlers/dependency/DependencyHandler.java
index 9a4c05d..b850a72 100644
--- a/ipojo/src/main/java/org/apache/felix/ipojo/handlers/dependency/DependencyHandler.java
+++ b/ipojo/src/main/java/org/apache/felix/ipojo/handlers/dependency/DependencyHandler.java
@@ -123,11 +123,7 @@
      * Check the validity of the dependencies.
      */
     protected void checkContext() {
-
         synchronized (this) {
-
-            m_manager.getFactory().getLogger().log(Logger.INFO, "[DependencyHandler on " + m_manager.getClassName() + "] Check Context ...");
-
             // Store the initial state
             int initialState = m_state;
 
@@ -451,12 +447,9 @@
             Dependency dep = m_dependencies[i];
             valide = valide & dep.isSatisfied();
             if (!valide) {
-                m_manager.getFactory().getLogger().log(Logger.INFO,
-                        "[DependencyHandler on " + m_manager.getClassName() + "] Component Dependencies are not valid : " + dep.getSpecification());
                 return false;
             }
         }
-        m_manager.getFactory().getLogger().log(Logger.INFO, "[DependencyHandler on " + m_manager.getClassName() + "] Component Dependencies are valid");
         return valide;
     }
 
diff --git a/ipojo/src/main/java/org/apache/felix/ipojo/util/Logger.java b/ipojo/src/main/java/org/apache/felix/ipojo/util/Logger.java
index a04a59c..364212a 100644
--- a/ipojo/src/main/java/org/apache/felix/ipojo/util/Logger.java
+++ b/ipojo/src/main/java/org/apache/felix/ipojo/util/Logger.java
@@ -32,8 +32,6 @@
  */
 public class Logger implements ServiceListener {
 
-    // TODO how to stop the logging (remove listener ...)
-
     /**
      * Log Level ERROR.
      */