summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--src/com/jogamp/opencl/util/concurrent/CLCommandQueuePool.java49
-rw-r--r--src/com/jogamp/opencl/util/concurrent/CLQueueContext.java2
-rw-r--r--test/com/jogamp/opencl/util/concurrent/CLMultiContextTest.java12
3 files changed, 46 insertions, 17 deletions
diff --git a/src/com/jogamp/opencl/util/concurrent/CLCommandQueuePool.java b/src/com/jogamp/opencl/util/concurrent/CLCommandQueuePool.java
index ee6dc86b..b80f09e6 100644
--- a/src/com/jogamp/opencl/util/concurrent/CLCommandQueuePool.java
+++ b/src/com/jogamp/opencl/util/concurrent/CLCommandQueuePool.java
@@ -9,7 +9,6 @@ import com.jogamp.opencl.CLResource;
import com.jogamp.opencl.util.CLMultiContext;
import java.util.ArrayList;
import java.util.Collection;
-import java.util.Collections;
import java.util.List;
import java.util.concurrent.Callable;
import java.util.concurrent.ExecutorService;
@@ -26,15 +25,32 @@ import java.util.concurrent.ThreadFactory;
*/
public class CLCommandQueuePool implements CLResource {
- private final List<CLQueueContext> contexts;
+ private List<CLQueueContext> contexts;
private ExecutorService excecutor;
private FinishAction finishAction = FinishAction.DO_NOTHING;
- private CLCommandQueuePool(Collection<CLQueueContext> contexts) {
- this.contexts = Collections.unmodifiableList(new ArrayList<CLQueueContext>(contexts));
+ private CLCommandQueuePool(CLQueueContextFactory factory, Collection<CLCommandQueue> queues) {
+ this.contexts = initContexts(queues, factory);
initExecutor();
}
+ private List<CLQueueContext> initContexts(Collection<CLCommandQueue> queues, CLQueueContextFactory factory) {
+ List<CLQueueContext> newContexts = new ArrayList<CLQueueContext>(queues.size());
+
+ int index = 0;
+ for (CLCommandQueue queue : queues) {
+
+ CLQueueContext old = null;
+ if(this.contexts != null && !this.contexts.isEmpty()) {
+ old = this.contexts.get(index++);
+ old.release();
+ }
+
+ newContexts.add(factory.setup(queue, old));
+ }
+ return newContexts;
+ }
+
private void initExecutor() {
this.excecutor = Executors.newFixedThreadPool(contexts.size(), new QueueThreadFactory(contexts));
}
@@ -52,11 +68,7 @@ public class CLCommandQueuePool implements CLResource {
}
public static CLCommandQueuePool create(CLQueueContextFactory factory, Collection<CLCommandQueue> queues) {
- List<CLQueueContext> contexts = new ArrayList<CLQueueContext>(queues.size());
- for (CLCommandQueue queue : queues) {
- contexts.add(factory.setup(queue, null));
- }
- return new CLCommandQueuePool(contexts);
+ return new CLCommandQueuePool(factory, queues);
}
public <R> Future<R> submit(CLTask<R> task) {
@@ -70,6 +82,20 @@ public class CLCommandQueuePool implements CLResource {
}
return excecutor.invokeAll(wrapper);
}
+
+ /**
+ * Switches the context of all queues - this operation can be expensive.
+ * Blocks until all tasks finish and sets up a new context for all queues.
+ */
+ public <C extends CLQueueContext> CLCommandQueuePool switchContext(CLQueueContextFactory<C> factory) {
+
+ excecutor.shutdown();
+ finishQueues(); // just to be sure
+
+ contexts = initContexts(getQueues(), factory);
+ initExecutor();
+ return this;
+ }
/**
* Calls {@link CLCommandQueue#flush()} on all queues.
@@ -96,6 +122,7 @@ public class CLCommandQueuePool implements CLResource {
excecutor.shutdown();
for (CLQueueContext context : contexts) {
context.queue.finish().release();
+ context.release();
}
}
@@ -121,6 +148,10 @@ public class CLCommandQueuePool implements CLResource {
return finishAction;
}
+ /**
+ * Sets the action which is run after every completed task.
+ * This is mainly intended for debugging, default value is {@link FinishAction#DO_NOTHING}.
+ */
public void setFinishAction(FinishAction action) {
this.finishAction = action;
}
diff --git a/src/com/jogamp/opencl/util/concurrent/CLQueueContext.java b/src/com/jogamp/opencl/util/concurrent/CLQueueContext.java
index fef0047d..3956f93d 100644
--- a/src/com/jogamp/opencl/util/concurrent/CLQueueContext.java
+++ b/src/com/jogamp/opencl/util/concurrent/CLQueueContext.java
@@ -44,7 +44,7 @@ public abstract class CLQueueContext implements CLResource {
}
public void release() {
- throw new UnsupportedOperationException("Not supported yet.");
+ program.release();
}
}
diff --git a/test/com/jogamp/opencl/util/concurrent/CLMultiContextTest.java b/test/com/jogamp/opencl/util/concurrent/CLMultiContextTest.java
index f076324a..7a1ed7aa 100644
--- a/test/com/jogamp/opencl/util/concurrent/CLMultiContextTest.java
+++ b/test/com/jogamp/opencl/util/concurrent/CLMultiContextTest.java
@@ -23,8 +23,8 @@ import static java.lang.System.*;
*/
public class CLMultiContextTest {
-// @Rule
-// public MethodRule methodTimeout= new Timeout(10000);
+ @Rule
+ public MethodRule methodTimeout= new Timeout(10000);
@Test
public void createMultiContextTest() {
@@ -52,15 +52,11 @@ public class CLMultiContextTest {
}
private final static String programSource =
- " // OpenCL Kernel Function for element by element vector addition \n"
- + "kernel void vectorAdd(global const int* a, global const int* b, global int* c, int iNumElements) { \n"
- + " // get index in global data array \n"
+ "kernel void vectorAdd(global const int* a, global const int* b, global int* c, int iNumElements) { \n"
+ " int iGID = get_global_id(0); \n"
- + " // bound check (equivalent to the limit on a 'for' loop for standard/serial C code \n"
+ " if (iGID >= iNumElements) { \n"
+ " return; \n"
+ " } \n"
- + " // add the vector elements \n"
+ " c[iGID] = a[iGID] + b[iGID]; \n"
+ "} \n";
@@ -75,6 +71,8 @@ public class CLMultiContextTest {
CLCommandQueuePool pool = CLCommandQueuePool.create(factory, mc);
assertTrue(pool.getSize() > 0);
+
+ pool.switchContext(factory);
pool.release();
}finally{