[armedbear-cvs] r11553 - trunk/abcl/src/org/armedbear/lisp

Erik Huelsmann ehuelsmann at common-lisp.net
Sun Jan 11 08:29:21 UTC 2009


Author: ehuelsmann
Date: Sun Jan 11 08:29:20 2009
New Revision: 11553

Log:
Increase performance of LispThread.currentThread() by more than 50% (uncontended case).
MAPCAR-THREADS correctness: use a concurrent hashmap.

- Increases function initialization of most lisp functions (which call currentThread())
- Simplifies LispThread code (eliminating synchronized blocks and caching variables)

Modified:
   trunk/abcl/src/org/armedbear/lisp/LispThread.java

Modified: trunk/abcl/src/org/armedbear/lisp/LispThread.java
==============================================================================
--- trunk/abcl/src/org/armedbear/lisp/LispThread.java	(original)
+++ trunk/abcl/src/org/armedbear/lisp/LispThread.java	Sun Jan 11 08:29:20 2009
@@ -33,59 +33,34 @@
 
 package org.armedbear.lisp;
 
-import java.util.WeakHashMap;
 import java.util.Iterator;
+import java.util.concurrent.ConcurrentHashMap;
 
 public final class LispThread extends LispObject
 {
     private static boolean use_fast_calls = false;
 
-    private static final Object lock = new Object();
+    // use a concurrent hashmap: we may want to add threads
+    // while at the same time iterating the hash
+    final private static ConcurrentHashMap<Thread,LispThread> map =
+       new ConcurrentHashMap<Thread,LispThread>();
 
-    private static WeakHashMap<Thread,LispThread> map =
-       new WeakHashMap<Thread,LispThread>();
-
-    private static Thread currentJavaThread;
-    private static LispThread currentLispThread;
-
-    public static final LispThread currentThread()
-    {
-        Thread javaThread = Thread.currentThread();
-        synchronized (lock) {
-            if (javaThread == currentJavaThread)
-                return currentLispThread;
-        }
-        LispThread lispThread = (LispThread) map.get(javaThread);
-        if (lispThread == null) {
-            lispThread = new LispThread(javaThread);
-            put(javaThread, lispThread);
-        }
-        synchronized (lock) {
-            currentJavaThread = javaThread;
-            currentLispThread = lispThread;
-        }
-        return lispThread;
-    }
-
-    private static void put(Thread javaThread, LispThread lispThread)
-    {
-        synchronized (lock) {
-            WeakHashMap<Thread,LispThread> m = new WeakHashMap<Thread,LispThread>(map);
-            m.put(javaThread, lispThread);
-            map = m;
+    private static ThreadLocal<LispThread> threads = new ThreadLocal<LispThread>(){
+        @Override
+        public LispThread initialValue() {
+            Thread thisThread = Thread.currentThread();
+            LispThread newThread = new LispThread(thisThread);
+            LispThread.map.put(thisThread,newThread);
+            return newThread;
         }
-    }
+    };
 
-    public static void remove(Thread javaThread)
+    public static final LispThread currentThread()
     {
-        synchronized (lock) {
-            WeakHashMap<Thread,LispThread> m = new WeakHashMap<Thread,LispThread>(map);
-            m.remove(javaThread);
-            map = m;
-        }
+        return threads.get();
     }
 
-    private final Thread javaThread;
+   private final Thread javaThread;
     private boolean destroyed;
     private final LispObject name;
     public SpecialBinding lastSpecialBinding;
@@ -121,12 +96,12 @@
                     }
                 }
                 finally {
-                    remove(javaThread);
+                    // make sure the thread is *always* removed from the hash again
+                    map.remove(Thread.currentThread());
                 }
             }
         };
         javaThread = new Thread(r);
-        put(javaThread, this);
         this.name = name;
         javaThread.setDaemon(true);
         javaThread.start();




More information about the armedbear-cvs mailing list