/** * Replaces place holders in the form of %%placeholder_name%% with valid values. E.g. * %%shared_mem_size%%. These are used in the CUDA templates provided by Rootbeer * * @see rootbeer/generate/opencl/CudaKernel.c * <p>It also replaces %%java_lang_*_TypeNumber%% with their respective type numbers as * returned by the Soot RoobteerClassLoader fork. * @see rootbeer/generate/opencl/GarbageCollector.c */ private String setupEntryPoint(StringBuilder builder) { String cuda_code = builder.toString(); String replacement = getRuntimeBasicBlockClassName() + "_gpuMethod" + NameMangling.v().mangle(VoidType.v()); // class names can have $ in them, make them regex safe replacement = replacement.replace("$", "\\$"); cuda_code = cuda_code.replaceAll("%%invoke_run%%", replacement); assert (m_configuration != null); int size = m_configuration.getSharedMemSize(); String size_str = "" + size; cuda_code = cuda_code.replaceAll("%%shared_mem_size%%", size_str); cuda_code = cuda_code.replaceAll("%%MallocAlignZeroBits%%", "" + Constants.MallocAlignZeroBits); cuda_code = cuda_code.replaceAll("%%MallocAlignBytes%%", "" + Constants.MallocAlignBytes); boolean exceptions = m_configuration.getExceptions(); String exceptions_str; if (exceptions) exceptions_str = "" + 1; else exceptions_str = "" + 0; cuda_code = cuda_code.replaceAll("%%using_exceptions%%", exceptions_str); for (String typeString : Arrays.asList( "StringBuilder", "NullPointerException", "OutOfMemoryError", "String", "Integer", "Long", "Float", "Double", "Boolean")) { cuda_code = cuda_code.replaceAll( "%%java_lang_" + typeString + "_TypeNumber%%", "" + RootbeerClassLoader.v().getClassNumber("java.lang." + typeString)); } return cuda_code; }
/** * For manually provided CUDA code it returns the file as a string. If not it converts the java * code to CUDA using Jimple as intermediary * * @return List of Strings. 1st is CUDA code for Linux, 2nd is for Windows */ private String[] makeSourceCode() throws Exception { assert (m_configuration != null); if (m_configuration.isManualCuda()) { final String cuda_code = readCode(m_configuration.getManualCudaFilename()); final String[] ret = new String[2]; ret[0] = cuda_code; ret[1] = cuda_code; return ret; } /* this gets switched to true again, if a new statement is found in * MethodJimpleValueSwitch e.g. when parsed in OpenCLMethod's or * OpenCLArrayType's Value.apply */ m_usesGarbageCollector = false; List<NumberedType> types = RootbeerClassLoader.v().getDfsInfo().getNumberedTypes(); writeTypesToFile(types); final StringBuilder unix_code = new StringBuilder(); final StringBuilder windows_code = new StringBuilder(); final String method_protos = methodPrototypesString(); final String gc_string = garbageCollectorString(); final String bodies_string = methodBodiesString(); /* true/false arguments are used to differ between unix and windows */ unix_code.append(headerString(true)); unix_code.append(method_protos); unix_code.append(gc_string); unix_code.append(bodies_string); unix_code.append(kernelString(true)); windows_code.append(headerString(false)); windows_code.append(method_protos); windows_code.append(gc_string); windows_code.append(bodies_string); windows_code.append(kernelString(false)); final String cuda_unix = setupEntryPoint(unix_code); final String cuda_windows = setupEntryPoint(windows_code); // print out code for debugging PrintWriter writer = new PrintWriter(new FileWriter(RootbeerPaths.v().getRootbeerHome() + "generated_unix.cu")); writer.println(cuda_unix); writer.flush(); writer.close(); // print out code for debugging writer = new PrintWriter( new FileWriter(RootbeerPaths.v().getRootbeerHome() + "generated_windows.cu")); writer.println(cuda_windows); writer.flush(); writer.close(); NameMangling.v().writeTypesToFile(); String[] ret = new String[2]; ret[0] = cuda_unix; ret[1] = cuda_windows; return ret; }