[ 
https://issues.apache.org/jira/browse/FELIX-3761?page=com.atlassian.jira.plugin.system.issuetabpanels:comment-tabpanel&focusedCommentId=13498685#comment-13498685
 ] 

Guillaume Nodet commented on FELIX-3761:
----------------------------------------

I'm proposing the following patch, which is only about removing the bundle lock 
access in the Felix#registerService method
{code}
diff --git a/framework/src/main/java/org/apache/felix/framework/Felix.java 
b/framework/src/main/java/org/apache/felix/framework/Felix.java
index 8ffec89..08b6d90 100644
--- a/framework/src/main/java/org/apache/felix/framework/Felix.java
+++ b/framework/src/main/java/org/apache/felix/framework/Felix.java
@@ -3446,51 +3446,32 @@ public class Felix extends BundleImpl implements 
Framework
             throw new IllegalArgumentException("Service object cannot be 
null.");
         }
 
-        // Acquire bundle lock.
-        try
-        {
-            acquireBundleLock(bundle, Bundle.STARTING | Bundle.ACTIVE | 
Bundle.STOPPING);
-        }
-        catch (IllegalStateException ex)
-        {
-            throw new IllegalStateException(
-                "Can only register services while bundle is active or 
activating.");
-        }
-
         ServiceRegistration reg = null;
 
-        try
+        // Check to make sure that the service object is
+        // an instance of all service classes; ignore if
+        // service object is a service factory.
+        if (!(svcObj instanceof ServiceFactory))
         {
-            // Check to make sure that the service object is
-            // an instance of all service classes; ignore if
-            // service object is a service factory.
-            if (!(svcObj instanceof ServiceFactory))
+            for (int i = 0; i < classNames.length; i++)
             {
-                for (int i = 0; i < classNames.length; i++)
+                Class clazz = Util.loadClassUsingClass(svcObj.getClass(), 
classNames[i], m_secureAction);
+                if (clazz == null)
                 {
-                    Class clazz = Util.loadClassUsingClass(svcObj.getClass(), 
classNames[i], m_secureAction);
-                    if (clazz == null)
-                    {
-                        throw new IllegalArgumentException(
-                            "Cannot cast service: " + classNames[i]);
-                    }
-                    else if (!clazz.isAssignableFrom(svcObj.getClass()))
-                    {
-                        throw new IllegalArgumentException(
-                            "Service object is not an instance of \""
-                            + classNames[i] + "\".");
-                    }
+                    throw new IllegalArgumentException(
+                        "Cannot cast service: " + classNames[i]);
+                }
+                else if (!clazz.isAssignableFrom(svcObj.getClass()))
+                {
+                    throw new IllegalArgumentException(
+                        "Service object is not an instance of \""
+                        + classNames[i] + "\".");
                 }
             }
-
-            reg = m_registry.registerService(bundle, classNames, svcObj, dict);
-        }
-        finally
-        {
-            // Always release bundle lock.
-            releaseBundleLock(bundle);
         }
 
+        reg = m_registry.registerService(bundle, classNames, svcObj, dict);
+
         // Check to see if this a listener hook; if so, then we need
         // to invoke the callback with all existing service listeners.
         if (ServiceRegistry.isHook(
{code}

                
> When a bundle registers a service, the bundle lock is obtained without any 
> real purpose
> ---------------------------------------------------------------------------------------
>
>                 Key: FELIX-3761
>                 URL: https://issues.apache.org/jira/browse/FELIX-3761
>             Project: Felix
>          Issue Type: Bug
>    Affects Versions: framework-4.0.2
>            Reporter: Guillaume Nodet
>
> It leads to the following kind of deadlocks:
> {code}
> "Felix WebConsole worker" Id=170 in WAITING on 
> lock=[Ljava.lang.Object;@108a93d9
>     at java.lang.Object.wait(Native Method)
>     at java.lang.Object.wait(Object.java:485)
>     at org.apache.felix.framework.Felix.acquireBundleLock(Felix.java:5203)
>     at org.apache.felix.framework.Felix.registerService(Felix.java:3452)
>     at 
> org.apache.felix.framework.BundleContextImpl.registerService(BundleContextImpl.java:346)
>     at 
> org.apache.felix.framework.BundleContextImpl.registerService(BundleContextImpl.java:320)
>     at 
> org.apache.felix.webconsole.internal.core.BundlesServlet.activate(BundlesServlet.java:132)
>     at 
> org.apache.felix.webconsole.internal.servlet.PluginHolder$InternalPlugin.doGetConsolePlugin(PluginHolder.java:752)
>     at 
> org.apache.felix.webconsole.internal.servlet.PluginHolder$Plugin.getConsolePlugin(PluginHolder.java:535)
>     at 
> org.apache.felix.webconsole.internal.servlet.PluginHolder.getPlugin(PluginHolder.java:205)
>     at 
> org.apache.felix.webconsole.internal.servlet.OsgiManager.initInternalPlugins(OsgiManager.java:1016)
>     at 
> org.apache.felix.webconsole.internal.servlet.OsgiManager.doUpdateConfiguration(OsgiManager.java:981)
>     at 
> org.apache.felix.webconsole.internal.servlet.OsgiManager$6.run(OsgiManager.java:930)
>     at 
> org.apache.felix.webconsole.internal.servlet.Executor$Worker.run(Executor.java:67)
> "FelixFrameworkWiring" Id=168 in WAITING on lock=java.lang.Object@3d6bca49
>     at java.lang.Object.wait(Native Method)
>     at java.lang.Object.wait(Object.java:485)
>     at 
> org.apache.felix.webconsole.internal.servlet.Executor.shutdown(Executor.java:45)
>       - locked org.apache.felix.webconsole.internal.servlet.Executor@21875b11
>     at 
> org.apache.felix.webconsole.internal.servlet.OsgiManager.dispose(OsgiManager.java:407)
>     at 
> org.apache.felix.webconsole.internal.KarafOsgiManagerActivator.stop(KarafOsgiManagerActivator.java:52)
>     at 
> org.apache.felix.framework.util.SecureAction.stopActivator(SecureAction.java:667)
>     at org.apache.felix.framework.Felix.stopBundle(Felix.java:2604)
>     at org.apache.felix.framework.Felix$RefreshHelper.stop(Felix.java:4961)
>     at org.apache.felix.framework.Felix.refreshPackages(Felix.java:4203)
>     at 
> org.apache.felix.framework.FrameworkWiringImpl.run(FrameworkWiringImpl.java:172)
>     at java.lang.Thread.run(Thread.java:680)
> {code}
> There's really no need to grab the bundle lock because the bundle is 
> necessarily starting / active / stopping, else an exception would have been 
> thrown when calling the registerService because the BundleContext object 
> would have been invalidated, and the registry itself is synchronized.  

--
This message is automatically generated by JIRA.
If you think it was sent incorrectly, please contact your JIRA administrators
For more information on JIRA, see: http://www.atlassian.com/software/jira

Reply via email to