package org.kne.opencl64.concurrent;

import java.io.IOException;
import java.nio.charset.Charset;
import java.util.HashMap;
import java.util.List;

import org.kne.opencl64.OpenCLCommandQueue;
import org.kne.opencl64.OpenCLContext;
import org.kne.opencl64.OpenCLDevice;
import org.kne.opencl64.OpenCLProgram;

public class OpenCLContextThread extends Thread {
	private OpenCLDevice device;
	private OpenCLContext context;
	private OpenCLCommandQueue queue;
	public OpenCLContextThread(OpenCLDevice device) {
		super();
		this.device=device;
		context=new OpenCLContext(device.getPlatform(), device);
		queue=new OpenCLCommandQueue(context, device);
	}

	public OpenCLContextThread(OpenCLDevice device,Runnable task) {
		super(task);
		this.device=device;
		context=new OpenCLContext(device.getPlatform(), device);
		queue=new OpenCLCommandQueue(context, device);
	}


	public OpenCLContextThread(OpenCLDevice device,OpenCLContext context) {
		super();
		this.device=device;
		this.context=context;
		queue=new OpenCLCommandQueue(context, device);
	}

	public OpenCLContextThread(OpenCLDevice device,OpenCLContext context,Runnable task) {
		super(task);
		this.device=device;
		this.context=context;
		queue=new OpenCLCommandQueue(context, device);
	}

	private HashMap<String, OpenCLProgram>cache=new HashMap<>();
	public OpenCLProgram getProgram(String resourcepath)  {
		OpenCLProgram opg=cache.computeIfAbsent(resourcepath, (k)->{
			try {
		String programSource = new String( OpenCLContextThread.class.getResourceAsStream(resourcepath).readAllBytes(),Charset.forName("utf8"));
		OpenCLProgram prog= new OpenCLProgram(context, programSource); 
		prog.buildProgram(List.of(device));
		String log=prog.getBuildLog(device);
		if(!log.isBlank()) {
		System.out.print("编译日志："+log );
		}
		return prog;
		} catch (IOException e) {
			e.printStackTrace();
		}
			return null;
		});
		return opg;
	}

	public OpenCLContext getOpenCLContext() {
		return context;
	}
	public OpenCLCommandQueue getOpenCLCommandQueue() {
		return queue;
	}

	public OpenCLDevice getDevice() {
		return device;
	}
	
}
