]> gerrit.simantics Code Review - simantics/platform.git/blobdiff - bundles/org.simantics.modeling/src/org/simantics/modeling/scl/SCLRealm.java
Some fixes for resource cleaning spreadsheets in simupedia
[simantics/platform.git] / bundles / org.simantics.modeling / src / org / simantics / modeling / scl / SCLRealm.java
index ea82e7e4ccdbcb97b27d456dc7f5da5df8ea0045..9870ad785b4dabfa6cbc737eaf18bbe58c19aaaa 100644 (file)
@@ -1,8 +1,8 @@
 package org.simantics.modeling.scl;
 
 import java.io.IOException;
+import java.util.List;
 import java.util.Map;
-import java.util.concurrent.ExecutorService;
 import java.util.concurrent.LinkedBlockingQueue;
 import java.util.concurrent.Semaphore;
 import java.util.concurrent.ThreadFactory;
@@ -19,7 +19,6 @@ import org.simantics.scl.compiler.types.Type;
 import org.simantics.scl.runtime.SCLContext;
 import org.simantics.scl.runtime.function.Function;
 import org.simantics.scl.runtime.tuple.Tuple0;
-import org.simantics.simulator.variable.NodeManager;
 import org.simantics.simulator.variable.Realm;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
@@ -31,26 +30,21 @@ public class SCLRealm implements Realm {
 
     public static final String SCL = "scl";
     
-    THashMap<String,Type> contextTypes = new THashMap<String,Type>();
+    private THashMap<String,Type> contextTypes = new THashMap<String,Type>();
     
-    CommandSession connection;
-    String id;
-    Thread executorThread;
-    ExecutorService executor = new ThreadPoolExecutor(0, 1, 60, TimeUnit.SECONDS,
-            new LinkedBlockingQueue<Runnable>(), new ThreadFactory() {
-        @Override
-        public Thread newThread(Runnable r) {
-            executorThread = new Thread(r);
-            return executorThread;
-        }
-    });
+    private CommandSession connection;
+    private String id;
+    private Thread executorThread;
+    private SCLRealmThreadFactory factory = new SCLRealmThreadFactory(this);
+    private ThreadPoolExecutor executor = new ThreadPoolExecutor(0, 1, 60, TimeUnit.SECONDS,
+            new LinkedBlockingQueue<Runnable>(), factory);
     
-    Semaphore beginSyncExec = new Semaphore(0);
-    Semaphore endSyncExec = new Semaphore(0);
+    private Semaphore beginSyncExec = new Semaphore(0);
+    private Semaphore endSyncExec = new Semaphore(0);
     
-    SCLNodeManager nodeManager;
+    private SCLNodeManager nodeManager;
     
-    Runnable scheduleSyncExec = new Runnable() {
+    private Runnable scheduleSyncExec = new Runnable() {
         @Override
         public void run() {
             beginSyncExec.release();
@@ -170,13 +164,30 @@ public class SCLRealm implements Realm {
         SCLSessionManager.CONNECTIONS.remove(id);
         executor.shutdown();
         try {
-            executor.awaitTermination(500L, TimeUnit.MILLISECONDS);
+            if (!executor.awaitTermination(500L, TimeUnit.MILLISECONDS)) {
+                List<Runnable> runnables = executor.shutdownNow();
+                if (!runnables.isEmpty()) {
+                    LOGGER.info("Some runnables left to execute in realm " + this + ": " + runnables);
+                }
+            }
         } catch (InterruptedException e) {
+            LOGGER.info("Could not shutdown executor " + executor + " in realm " + this, e);
         }
         //connection.close();
+        
+        factory.clear();
+        factory = null;
+        // Should not happen
+        if (executorThread.isAlive())
+            executorThread.interrupt();
+        executorThread = null;
+        executor = null;
+        
+        // clear nodeManager
+        nodeManager.clear();
     }
 
-    public NodeManager<String> getNodeManager() {
+    public SCLNodeManager getNodeManager() {
         return nodeManager;
     }
     
@@ -221,4 +232,27 @@ public class SCLRealm implements Realm {
                }
     }
     
+    private static class SCLRealmThreadFactory implements ThreadFactory {
+
+        private SCLRealm realm;
+
+        public SCLRealmThreadFactory(SCLRealm realm) {
+             this.realm = realm;
+         }
+        
+        @Override
+        public Thread newThread(Runnable r) {
+            Thread t = new Thread(r);
+            realm.setThread(t);
+            return t;
+        }
+        
+        void clear() {
+            realm = null;
+        }
+    }
+
+    private void setThread(Thread t) {
+        this.executorThread = t;
+    }
 }