0

OpenCL カーネルを実行するマルチスレッド Java アプリケーションを実行しようとしています。カーネルが終了したときにスレッドの 1 つに通知したかったので、clSetEventCallback メソッドを使用しようとしました。

そのためにメソッドを用意しました

void runKernel(
    cl_program program, 
    String functionName, 
    Object... params, 
    long[] globalWorkSize, 
    long[] localWorkSize
){
    System.out.println(System.currentTimeMillis() +": Preparing Kernel "+kernel+);
    int[] errCode = new int[1];
    int errno;
    cl_kernel kernel = CL.clCreateKernel(program, functionName, errCode);

    /******INSERT ALL THE PARAMS******/

    System.out.println(System.currentTimeMillis() +": Enqueueing Kernel "+kernel+);


    cl_event event = new cl_event();
    CL.clEnqueueNDRangeKernel(this.queue, kernel, 1, null, globalWorkSize, localWorkSize, 0, null, event);
    CL.clSetEventCallback(event, CL_COMPLETE, new EventCallbackFunction() {
        @Override
        public void function(cl_event event, int command_exec_callback_type, Object user_data) {
            System.out.println(System.currentTimeMillis() +": Finished kernel " + user_data);
        }
    }, kernel);
}

この関数を呼び出して、5 秒間隔で 3 つの異なるカーネルを実行します。コードは正常に実行され、期待される結果が得られます。ただし、アプリケーションの出力を見ると、コールバック メソッドは実際のカーネルの完了時に実行されず、プログラムが run メソッドを再度呼び出すと実行されます。最後に実行されたカーネルのコールバックは実行されません (得られた結果が正しいため、カーネルは実行されます)。

1475085785924: Prepared Kernel cl_kernel[0x7f8b28098c90]
1475085785924: Enqueueing Kernel cl_kernel[0x7f8b28098c90]
1475085790925: Prepared Kernel cl_kernel[0x7f8b284fbd50]
1475085790925: Enqueueing Kernel cl_kernel[0x7f8b284fbd50]
1475085790925: Finished kernel cl_kernel[0x7f8b28098c90]
1475085795926: Prepared Kernel cl_kernel[0x7f8b2851abd0] 
1475085795926: Enqueueing Kernel cl_kernel[0x7f8b2851abd0]
1475085795926: Finished kernel cl_kernel[0x7f8b284fbd50]

次のカーネルがエンキューされるまでコールバックが実行されないように、コードに問題はありますか? 私は何か見落としてますか?または、JOCL/OpenCL ライブラリがカーネルの終了を正しく通知していませんか?

4

1 に答える 1