You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@tapestry.apache.org by hl...@apache.org on 2011/09/14 19:02:02 UTC
svn commit: r1170712 - in
/tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal:
PerThreadOperationTracker.java services/PerthreadManagerImpl.java
util/JDKUtils.java
Author: hlship
Date: Wed Sep 14 17:02:02 2011
New Revision: 1170712
URL: http://svn.apache.org/viewvc?rev=1170712&view=rev
Log:
TAP5-1647: PerThreadOperationTracker uses a synchronized block with high thread contention
Modified:
tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/PerThreadOperationTracker.java
tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/services/PerthreadManagerImpl.java
tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/util/JDKUtils.java
Modified: tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/PerThreadOperationTracker.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/PerThreadOperationTracker.java?rev=1170712&r1=1170711&r2=1170712&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/PerThreadOperationTracker.java (original)
+++ tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/PerThreadOperationTracker.java Wed Sep 14 17:02:02 2011
@@ -1,4 +1,4 @@
-// Copyright 2008, 2009 The Apache Software Foundation
+// Copyright 2008, 2009, 2011 The Apache Software Foundation
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
@@ -16,8 +16,11 @@ package org.apache.tapestry5.ioc.interna
import org.apache.tapestry5.ioc.Invokable;
import org.apache.tapestry5.ioc.OperationTracker;
+import org.apache.tapestry5.ioc.internal.util.JDKUtils;
import org.slf4j.Logger;
+import java.util.concurrent.locks.Lock;
+
/**
* Manages a per-thread OperationTracker using a ThreadLocal.
*/
@@ -25,6 +28,8 @@ public class PerThreadOperationTracker i
{
private final Logger logger;
+ private final Lock lock = JDKUtils.createLockForThreadLocalCreation();
+
private final ThreadLocal<OperationTrackerImpl> perThread = new ThreadLocal<OperationTrackerImpl>()
{
@Override
@@ -39,14 +44,29 @@ public class PerThreadOperationTracker i
this.logger = logger;
}
- synchronized OperationTracker get()
+ OperationTracker get()
{
- return perThread.get();
+ try
+ {
+ lock.lock();
+
+ return perThread.get();
+ } finally
+ {
+ lock.unlock();
+ }
}
- synchronized void cleanup()
+ void cleanup()
{
- if (perThread.get().isEmpty()) perThread.remove();
+ try
+ {
+ lock.lock();
+ if (perThread.get().isEmpty()) perThread.remove();
+ } finally
+ {
+ lock.unlock();
+ }
}
public void run(String description, Runnable operation)
@@ -54,8 +74,7 @@ public class PerThreadOperationTracker i
try
{
get().run(description, operation);
- }
- finally
+ } finally
{
cleanup();
}
@@ -66,8 +85,7 @@ public class PerThreadOperationTracker i
try
{
return get().invoke(description, operation);
- }
- finally
+ } finally
{
cleanup();
}
Modified: tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/services/PerthreadManagerImpl.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/services/PerthreadManagerImpl.java?rev=1170712&r1=1170711&r2=1170712&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/services/PerthreadManagerImpl.java (original)
+++ tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/services/PerthreadManagerImpl.java Wed Sep 14 17:02:02 2011
@@ -14,26 +14,23 @@
package org.apache.tapestry5.ioc.internal.services;
-import java.util.List;
-import java.util.Map;
-import java.util.concurrent.atomic.AtomicInteger;
-import java.util.concurrent.locks.Lock;
-import java.util.concurrent.locks.ReentrantLock;
-
import org.apache.tapestry5.ioc.Invokable;
import org.apache.tapestry5.ioc.internal.util.CollectionFactory;
-import org.apache.tapestry5.ioc.internal.util.DummyLock;
-import org.apache.tapestry5.ioc.internal.util.InternalUtils;
import org.apache.tapestry5.ioc.internal.util.JDKUtils;
import org.apache.tapestry5.ioc.services.PerThreadValue;
import org.apache.tapestry5.ioc.services.PerthreadManager;
import org.apache.tapestry5.ioc.services.ThreadCleanupListener;
import org.slf4j.Logger;
+import java.util.List;
+import java.util.Map;
+import java.util.concurrent.atomic.AtomicInteger;
+import java.util.concurrent.locks.Lock;
+
@SuppressWarnings("all")
public class PerthreadManagerImpl implements PerthreadManager
{
- private final Lock lock;
+ private final Lock lock = JDKUtils.createLockForThreadLocalCreation();
private final PerThreadValue<List<ThreadCleanupListener>> listenersValue;
@@ -54,15 +51,8 @@ public class PerthreadManagerImpl implem
public PerthreadManagerImpl(Logger logger)
{
- this(logger, JDKUtils.JDK_1_5);
- }
-
- PerthreadManagerImpl(Logger logger, boolean useSynchronization)
- {
this.logger = logger;
- lock = useSynchronization ? new ReentrantLock() : new DummyLock();
-
listenersValue = createValue();
}
@@ -73,8 +63,7 @@ public class PerthreadManagerImpl implem
lock.lock();
return holder.get();
- }
- finally
+ } finally
{
lock.unlock();
}
@@ -113,8 +102,7 @@ public class PerthreadManagerImpl implem
try
{
listener.threadDidCleanup();
- }
- catch (Exception ex)
+ } catch (Exception ex)
{
logger.warn(ServiceMessages.threadCleanupError(listener, ex), ex);
}
@@ -133,8 +121,7 @@ public class PerthreadManagerImpl implem
// released to the GC.
holder.remove();
- }
- finally
+ } finally
{
lock.unlock();
}
@@ -194,8 +181,7 @@ public class PerthreadManagerImpl implem
try
{
runnable.run();
- }
- finally
+ } finally
{
cleanup();
}
@@ -206,8 +192,7 @@ public class PerthreadManagerImpl implem
try
{
return invokable.invoke();
- }
- finally
+ } finally
{
cleanup();
}
Modified: tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/util/JDKUtils.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/util/JDKUtils.java?rev=1170712&r1=1170711&r2=1170712&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/util/JDKUtils.java (original)
+++ tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/util/JDKUtils.java Wed Sep 14 17:02:02 2011
@@ -1,4 +1,4 @@
-// Copyright 2009 The Apache Software Foundation
+// Copyright 2009, 2011 The Apache Software Foundation
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
@@ -14,6 +14,9 @@
package org.apache.tapestry5.ioc.internal.util;
+import java.util.concurrent.locks.Lock;
+import java.util.concurrent.locks.ReentrantLock;
+
/**
* Internal utilities for identifying the JDK version, used in the rare cases
* that we are patching around JDK bugs.
@@ -29,4 +32,16 @@ public class JDKUtils
{
return System.getProperty("java.specification.version").equals(versionId);
}
+
+ /**
+ * Returns a {@link ReentrantLock} used to serialize access to the construction of a thread local; this is only needed under JDK 1.5 (due to a bug in the JDK);
+ * for other JDKs, a {@link DummyLock} is returned.
+ *
+ * @return lock to use when creating
+ * @since 5.3
+ */
+ public static Lock createLockForThreadLocalCreation()
+ {
+ return JDK_1_5 ? new ReentrantLock() : new DummyLock();
+ }
}