You are viewing a plain text version of this content. The canonical link for it is here.
Posted to java-dev@axis.apache.org by "Stein S (JIRA)" <ji...@apache.org> on 2008/01/30 14:32:40 UTC

[jira] Created: (AXIS2-3484) The ConfigurationContext in Axis2-Kernal causes ConcurrentModificationException in Session-Scope and thus is not multithreading-able

The ConfigurationContext in Axis2-Kernal causes ConcurrentModificationException in Session-Scope and thus is not multithreading-able
------------------------------------------------------------------------------------------------------------------------------------

                 Key: AXIS2-3484
                 URL: https://issues.apache.org/jira/browse/AXIS2-3484
             Project: Axis 2.0 (Axis2)
          Issue Type: Bug
          Components: kernel
    Affects Versions: 1.3
         Environment: WinXP, Eclipse 3.3.1.1, Tomcat 5.5.23
            Reporter: Stein S
            Priority: Critical
             Fix For: 1.3


Hello,

I have found a problem with a ConcurrentModificationException in the class 'org.apache.axis2.context.ConfigurationContext' of the Axis2-kernel. In my test-case, I work with a stateful webservice in session-scope and the addressing-module included.

My service-xml looks like this:

<serviceGroup>
    <service
            name="Beratungsservice"
            class="de.is2.web.beratungsservice.service.BeratungsserviceLifeCycle"
			scope="soapsession"
    >
        <description>Beratungsservice</description>
		<module ref="addressing"/>
        <messageReceivers>
            <messageReceiver
                mep="http://www.w3.org/2004/08/wsdl/in-out"
                class="de.is2.web.gen.beratungsservice.service.BeratungsserviceMessageReceiverInOut"
            />
        </messageReceivers>
        <schema schemaNamespace="http://is2.de/prototype/Beratungsservice"/>

        <parameter name="ServiceClass">de.is2.web.beratungsservice.service.Beratungsservice</parameter>
        <parameter name="modifyUserWSDLPortAddress">true</parameter>        
		<parameter name="Traeger_RootConfig">/rootconfig.xml</parameter>
    </service>
</serviceGroup>		

The session-timeout in axis2.xml is set to 30 seconds (default).

To test the service, I am using 30 client-threads, which send parallel calls to the service. 

private static void testMultiCall() {
        for(int index = 0; index < 30; index++) {
            try {
                Thread.sleep(100);
            }
            catch (InterruptedException oEx) {
                oEx.printStackTrace();
            }
            try {
                new Thread(new TestRunner(index), "T" + index).start();
            }
            catch (Throwable e) {
                e.printStackTrace();
            }
        }
    }

Sometimes, I get ConcurrentModificationException  on server-side as shown below: 

java.util.ConcurrentModificationException
	at java.util.Hashtable$Enumerator.next(Hashtable.java:1020)
	at java.util.Hashtable$Enumerator.next(Hashtable.java:1020)
	at org.apache.axis2.context.ConfigurationContext.cleanupServiceGroupContexts(ConfigurationContext.java:591)
	at org.apache.axis2.context.ConfigurationContext.fillServiceContextAndServiceGroupContext(ConfigurationContext.java:232)
	at org.apache.axis2.engine.DispatchPhase.loadContexts(DispatchPhase.java:183)
	at org.apache.axis2.engine.DispatchPhase.checkPostConditions(DispatchPhase.java:95)
	at org.apache.axis2.engine.Phase.invoke(Phase.java:308)
	at org.apache.axis2.engine.AxisEngine.invoke(AxisEngine.java:212)
	at org.apache.axis2.engine.AxisEngine.receive(AxisEngine.java:132)
	at org.apache.axis2.transport.http.HTTPTransportUtils.processHTTPPostRequest(HTTPTransportUtils.java:275)
	at org.apache.axis2.transport.http.AxisServlet.doPost(AxisServlet.java:120)
	at javax.servlet.http.HttpServlet.service(HttpServlet.java:710)
	at javax.servlet.http.HttpServlet.service(HttpServlet.java:803)
	at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:269)
	at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:188)
	at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:210)
	at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:174)
	at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:127)
	at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:117)
	at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:108)
	at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:151)
	at org.apache.coyote.http11.Http11Processor.process(Http11Processor.java:870)
	at org.apache.coyote.http11.Http11BaseProtocol$Http11ConnectionHandler.processConnection(Http11BaseProtocol.java:665)
	at org.apache.tomcat.util.net.PoolTcpEndpoint.processSocket(PoolTcpEndpoint.java:528)
	at org.apache.tomcat.util.net.LeaderFollowerWorkerThread.runIt(LeaderFollowerWorkerThread.java:81)
	at org.apache.tomcat.util.threads.ThreadPool$ControlRunnable.run(ThreadPool.java:685)
	at java.lang.Thread.run(Thread.java:595)

The exception is thrown in the method 'cleanupServiceGroupContexts()' at the line 'String sgCtxtId = (String) sgCtxtMapKeyIter.next();'

  private void cleanupServiceGroupContexts() {
        if (serviceGroupContextMap == null) {
            return;
        }
        long currentTime = new Date().getTime();
        for (Iterator sgCtxtMapKeyIter = serviceGroupContextMap.keySet().iterator();
             sgCtxtMapKeyIter.hasNext();) {
            String sgCtxtId = (String) sgCtxtMapKeyIter.next();
            ServiceGroupContext serviceGroupContext =
                    (ServiceGroupContext) serviceGroupContextMap.get(sgCtxtId);
            if ((currentTime - serviceGroupContext.getLastTouchedTime()) >
                getServiceGroupContextTimoutInterval()) {
                sgCtxtMapKeyIter.remove();
                cleanupServiceContexts(serviceGroupContext);
                contextRemoved(serviceGroupContext);
            }
        }
    }

When ever a new session is established, the axis-kernel checks the context for timed-out sessions an perform a clean-up. 
It seems, that the reason for the problem is the iterator of the keyset, which is not synchronised and thus, not prepared for multiple modification in different threads.

In my tests, I have temporary modified the method 'cleanupServiceGroupContexts()' and synchronized  the member 'serviceGroupContextMap'  as following:

private void cleanupServiceGroupContexts() {
        if (serviceGroupContextMap == null) {
            return;
        }
        long currentTime = new Date().getTime();
        
        synchronized (serviceGroupContextMap) {
            
            for (Iterator sgCtxtMapKeyIter = serviceGroupContextMap.keySet().iterator();
                 sgCtxtMapKeyIter.hasNext();) {
                String sgCtxtId = (String) sgCtxtMapKeyIter.next();
                ServiceGroupContext serviceGroupContext =
                        (ServiceGroupContext) serviceGroupContextMap.get(sgCtxtId);
                if ((currentTime - serviceGroupContext.getLastTouchedTime()) >
                    getServiceGroupContextTimoutInterval()) {
                    sgCtxtMapKeyIter.remove();
                    cleanupServiceContexts(serviceGroupContext);
                    contextRemoved(serviceGroupContext);
                }
            }            
        }        
    }

That synchronisation seems to solve the problem and no more ConcurrentModificationException are thrown.

Is this problem known so far? 
Have I done the proper modification to fix the bug?
Is there a bug-fix in the next release possible?

Thanks
S. Stein

-- 
This message is automatically generated by JIRA.
-
You can reply to this email to add a comment to the issue online.


---------------------------------------------------------------------
To unsubscribe, e-mail: axis-dev-unsubscribe@ws.apache.org
For additional commands, e-mail: axis-dev-help@ws.apache.org


[jira] Resolved: (AXIS2-3484) The ConfigurationContext in Axis2-Kernal causes ConcurrentModificationException in Session-Scope and thus is not multithreading-able

Posted by "Davanum Srinivas (JIRA)" <ji...@apache.org>.
     [ https://issues.apache.org/jira/browse/AXIS2-3484?page=com.atlassian.jira.plugin.system.issuetabpanels:all-tabpanel ]

Davanum Srinivas resolved AXIS2-3484.
-------------------------------------

       Resolution: Fixed
    Fix Version/s:     (was: 1.3)
                   nightly

Looks like a good fix to me. Checked into svn revision 616761.

thanks,
dims

> The ConfigurationContext in Axis2-Kernal causes ConcurrentModificationException in Session-Scope and thus is not multithreading-able
> ------------------------------------------------------------------------------------------------------------------------------------
>
>                 Key: AXIS2-3484
>                 URL: https://issues.apache.org/jira/browse/AXIS2-3484
>             Project: Axis 2.0 (Axis2)
>          Issue Type: Bug
>          Components: kernel
>    Affects Versions: 1.3
>         Environment: WinXP, Eclipse 3.3.1.1, Tomcat 5.5.23
>            Reporter: Stein S
>            Priority: Critical
>             Fix For: nightly
>
>   Original Estimate: 1h
>  Remaining Estimate: 1h
>
> Hello,
> I have found a problem with a ConcurrentModificationException in the class 'org.apache.axis2.context.ConfigurationContext' of the Axis2-kernel. In my test-case, I work with a stateful webservice in session-scope and the addressing-module included.
> My service-xml looks like this:
> <serviceGroup>
>     <service
>             name="Beratungsservice"
>             class="de.is2.web.beratungsservice.service.BeratungsserviceLifeCycle"
> 			scope="soapsession"
>     >
>         <description>Beratungsservice</description>
> 		<module ref="addressing"/>
>         <messageReceivers>
>             <messageReceiver
>                 mep="http://www.w3.org/2004/08/wsdl/in-out"
>                 class="de.is2.web.gen.beratungsservice.service.BeratungsserviceMessageReceiverInOut"
>             />
>         </messageReceivers>
>         <schema schemaNamespace="http://is2.de/prototype/Beratungsservice"/>
>         <parameter name="ServiceClass">de.is2.web.beratungsservice.service.Beratungsservice</parameter>
>         <parameter name="modifyUserWSDLPortAddress">true</parameter>        
> 		<parameter name="Traeger_RootConfig">/rootconfig.xml</parameter>
>     </service>
> </serviceGroup>		
> The session-timeout in axis2.xml is set to 30 seconds (default).
> To test the service, I am using 30 client-threads, which send parallel calls to the service. 
> private static void testMultiCall() {
>         for(int index = 0; index < 30; index++) {
>             try {
>                 Thread.sleep(100);
>             }
>             catch (InterruptedException oEx) {
>                 oEx.printStackTrace();
>             }
>             try {
>                 new Thread(new TestRunner(index), "T" + index).start();
>             }
>             catch (Throwable e) {
>                 e.printStackTrace();
>             }
>         }
>     }
> Sometimes, I get ConcurrentModificationException  on server-side as shown below: 
> java.util.ConcurrentModificationException
> 	at java.util.Hashtable$Enumerator.next(Hashtable.java:1020)
> 	at java.util.Hashtable$Enumerator.next(Hashtable.java:1020)
> 	at org.apache.axis2.context.ConfigurationContext.cleanupServiceGroupContexts(ConfigurationContext.java:591)
> 	at org.apache.axis2.context.ConfigurationContext.fillServiceContextAndServiceGroupContext(ConfigurationContext.java:232)
> 	at org.apache.axis2.engine.DispatchPhase.loadContexts(DispatchPhase.java:183)
> 	at org.apache.axis2.engine.DispatchPhase.checkPostConditions(DispatchPhase.java:95)
> 	at org.apache.axis2.engine.Phase.invoke(Phase.java:308)
> 	at org.apache.axis2.engine.AxisEngine.invoke(AxisEngine.java:212)
> 	at org.apache.axis2.engine.AxisEngine.receive(AxisEngine.java:132)
> 	at org.apache.axis2.transport.http.HTTPTransportUtils.processHTTPPostRequest(HTTPTransportUtils.java:275)
> 	at org.apache.axis2.transport.http.AxisServlet.doPost(AxisServlet.java:120)
> 	at javax.servlet.http.HttpServlet.service(HttpServlet.java:710)
> 	at javax.servlet.http.HttpServlet.service(HttpServlet.java:803)
> 	at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:269)
> 	at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:188)
> 	at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:210)
> 	at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:174)
> 	at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:127)
> 	at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:117)
> 	at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:108)
> 	at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:151)
> 	at org.apache.coyote.http11.Http11Processor.process(Http11Processor.java:870)
> 	at org.apache.coyote.http11.Http11BaseProtocol$Http11ConnectionHandler.processConnection(Http11BaseProtocol.java:665)
> 	at org.apache.tomcat.util.net.PoolTcpEndpoint.processSocket(PoolTcpEndpoint.java:528)
> 	at org.apache.tomcat.util.net.LeaderFollowerWorkerThread.runIt(LeaderFollowerWorkerThread.java:81)
> 	at org.apache.tomcat.util.threads.ThreadPool$ControlRunnable.run(ThreadPool.java:685)
> 	at java.lang.Thread.run(Thread.java:595)
> The exception is thrown in the method 'cleanupServiceGroupContexts()' at the line 'String sgCtxtId = (String) sgCtxtMapKeyIter.next();'
>   private void cleanupServiceGroupContexts() {
>         if (serviceGroupContextMap == null) {
>             return;
>         }
>         long currentTime = new Date().getTime();
>         for (Iterator sgCtxtMapKeyIter = serviceGroupContextMap.keySet().iterator();
>              sgCtxtMapKeyIter.hasNext();) {
>             String sgCtxtId = (String) sgCtxtMapKeyIter.next();
>             ServiceGroupContext serviceGroupContext =
>                     (ServiceGroupContext) serviceGroupContextMap.get(sgCtxtId);
>             if ((currentTime - serviceGroupContext.getLastTouchedTime()) >
>                 getServiceGroupContextTimoutInterval()) {
>                 sgCtxtMapKeyIter.remove();
>                 cleanupServiceContexts(serviceGroupContext);
>                 contextRemoved(serviceGroupContext);
>             }
>         }
>     }
> When ever a new session is established, the axis-kernel checks the context for timed-out sessions an perform a clean-up. 
> It seems, that the reason for the problem is the iterator of the keyset, which is not synchronised and thus, not prepared for multiple modification in different threads.
> In my tests, I have temporary modified the method 'cleanupServiceGroupContexts()' and synchronized  the member 'serviceGroupContextMap'  as following:
> private void cleanupServiceGroupContexts() {
>         if (serviceGroupContextMap == null) {
>             return;
>         }
>         long currentTime = new Date().getTime();
>         
>         synchronized (serviceGroupContextMap) {
>             
>             for (Iterator sgCtxtMapKeyIter = serviceGroupContextMap.keySet().iterator();
>                  sgCtxtMapKeyIter.hasNext();) {
>                 String sgCtxtId = (String) sgCtxtMapKeyIter.next();
>                 ServiceGroupContext serviceGroupContext =
>                         (ServiceGroupContext) serviceGroupContextMap.get(sgCtxtId);
>                 if ((currentTime - serviceGroupContext.getLastTouchedTime()) >
>                     getServiceGroupContextTimoutInterval()) {
>                     sgCtxtMapKeyIter.remove();
>                     cleanupServiceContexts(serviceGroupContext);
>                     contextRemoved(serviceGroupContext);
>                 }
>             }            
>         }        
>     }
> That synchronisation seems to solve the problem and no more ConcurrentModificationException are thrown.
> Is this problem known so far? 
> Have I done the proper modification to fix the bug?
> Is there a bug-fix in the next release possible?
> Thanks
> S. Stein

-- 
This message is automatically generated by JIRA.
-
You can reply to this email to add a comment to the issue online.


---------------------------------------------------------------------
To unsubscribe, e-mail: axis-dev-unsubscribe@ws.apache.org
For additional commands, e-mail: axis-dev-help@ws.apache.org