Rewrote the entire thing using my new OpenCL template. Makes small one offs like these reallly simple

master
MitchellHansen 8 years ago
parent 08fd8b2398
commit 7743321465

63
.gitattributes vendored

@ -1,63 +0,0 @@
###############################################################################
# Set default behavior to automatically normalize line endings.
###############################################################################
* text=auto
###############################################################################
# Set default behavior for command prompt diff.
#
# This is need for earlier builds of msysgit that does not have it on by
# default for csharp files.
# Note: This is only used by command line
###############################################################################
#*.cs diff=csharp
###############################################################################
# Set the merge driver for project and solution files
#
# Merging from the command prompt will add diff markers to the files if there
# are conflicts (Merging from VS is not affected by the settings below, in VS
# the diff markers are never inserted). Diff markers may cause the following
# file extensions to fail to load in VS. An alternative would be to treat
# these files as binary and thus will always conflict and require user
# intervention with every merge. To do so, just uncomment the entries below
###############################################################################
#*.sln merge=binary
#*.csproj merge=binary
#*.vbproj merge=binary
#*.vcxproj merge=binary
#*.vcproj merge=binary
#*.dbproj merge=binary
#*.fsproj merge=binary
#*.lsproj merge=binary
#*.wixproj merge=binary
#*.modelproj merge=binary
#*.sqlproj merge=binary
#*.wwaproj merge=binary
###############################################################################
# behavior for image files
#
# image files are treated as binary by default.
###############################################################################
#*.jpg binary
#*.png binary
#*.gif binary
###############################################################################
# diff behavior for common document formats
#
# Convert binary document formats to text before diffing them. This feature
# is only available from the command line. Turn it on by uncommenting the
# entries below.
###############################################################################
#*.doc diff=astextplain
#*.DOC diff=astextplain
#*.docx diff=astextplain
#*.DOCX diff=astextplain
#*.dot diff=astextplain
#*.DOT diff=astextplain
#*.pdf diff=astextplain
#*.PDF diff=astextplain
#*.rtf diff=astextplain
#*.RTF diff=astextplain

257
.gitignore vendored

@ -1,212 +1,47 @@
## Ignore Visual Studio temporary files, build results, and # Compiled source #
## files generated by popular Visual Studio add-ons. ###################
*.com
# User-specific files *.class
*.suo *.dll
*.user *.exe
*.userosscache *.o
*.sln.docstates *.so
# User-specific files (MonoDevelop/Xamarin Studio) # Packages #
*.userprefs ############
# it's better to unpack these files and commit the raw source
# Build results # git has its own built in compression methods
[Dd]ebug/ *.7z
[Dd]ebugPublic/ *.dmg
[Rr]elease/ *.gz
[Rr]eleases/ *.iso
x64/ *.jar
x86/ *.rar
build/ *.tar
bld/ *.zip
[Bb]in/
[Oo]bj/ # Logs and databases #
######################
# Visual Studio 2015 cache/options directory
.vs/
# MSTest test Results
[Tt]est[Rr]esult*/
[Bb]uild[Ll]og.*
# NUNIT
*.VisualState.xml
TestResult.xml
# Build Results of an ATL Project
[Dd]ebugPS/
[Rr]eleasePS/
dlldata.c
# DNX
project.lock.json
artifacts/
*_i.c
*_p.c
*_i.h
*.ilk
*.meta
*.obj
*.pch
*.pdb
*.pgc
*.pgd
*.rsp
*.sbr
*.tlb
*.tli
*.tlh
*.tmp
*.tmp_proj
*.log *.log
*.vspscc *.sql
*.vssscc *.sqlite
.builds
*.pidb # OS generated files #
*.svclog ######################
*.scc .DS_Store
.DS_Store?
# Chutzpah Test files ._*
_Chutzpah* .Spotlight-V100
.Trashes
# Visual C++ cache files ehthumbs.db
ipch/ Thumbs.db
*.aps
*.ncb # CMake Generated Files #
*.opensdf #########################
*.sdf CMakeCache.txt
*.cachefile CMakeFiles
CMakeScripts
# Visual Studio profiler Makefile
*.psess cmake_install.cmake
*.vsp install_manifest.txt
*.vspx CTestTestfile.cmake
# TFS 2012 Local Workspace
$tf/
# Guidance Automation Toolkit
*.gpState
# ReSharper is a .NET coding add-in
_ReSharper*/
*.[Rr]e[Ss]harper
*.DotSettings.user
# JustCode is a .NET coding add-in
.JustCode
# TeamCity is a build add-in
_TeamCity*
# DotCover is a Code Coverage Tool
*.dotCover
# NCrunch
_NCrunch_*
.*crunch*.local.xml
# MightyMoose
*.mm.*
AutoTest.Net/
# Web workbench (sass)
.sass-cache/
# Installshield output folder
[Ee]xpress/
# DocProject is a documentation generator add-in
DocProject/buildhelp/
DocProject/Help/*.HxT
DocProject/Help/*.HxC
DocProject/Help/*.hhc
DocProject/Help/*.hhk
DocProject/Help/*.hhp
DocProject/Help/Html2
DocProject/Help/html
# Click-Once directory
publish/
# Publish Web Output
*.[Pp]ublish.xml
*.azurePubxml
## TODO: Comment the next line if you want to checkin your
## web deploy settings but do note that will include unencrypted
## passwords
#*.pubxml
*.publishproj
# NuGet Packages
*.nupkg
# The packages folder can be ignored because of Package Restore
**/packages/*
# except build/, which is used as an MSBuild target.
!**/packages/build/
# Uncomment if necessary however generally it will be regenerated when needed
#!**/packages/repositories.config
# Windows Azure Build Output
csx/
*.build.csdef
# Windows Store app package directory
AppPackages/
# Visual Studio cache files
# files ending in .cache can be ignored
*.[Cc]ache
# but keep track of directories ending in .cache
!*.[Cc]ache/
# Others
ClientBin/
[Ss]tyle[Cc]op.*
~$*
*~
*.dbmdl
*.dbproj.schemaview
*.pfx
*.publishsettings
node_modules/
orleans.codegen.cs
# RIA/Silverlight projects
Generated_Code/
# Backup & report files from converting an old project file
# to a newer Visual Studio version. Backup files are not needed,
# because we have git ;-)
_UpgradeReport_Files/
Backup*/
UpgradeLog*.XML
UpgradeLog*.htm
# SQL Server files
*.mdf
*.ldf
# Business Intelligence projects
*.rdl.data
*.bim.layout
*.bim_*.settings
# Microsoft Fakes
FakesAssemblies/
# Node.js Tools for Visual Studio
.ntvs_analysis.dat
# Visual Studio 6 build log
*.plg
# Visual Studio 6 workspace options file
*.opt
# LightSwitch generated files
GeneratedArtifacts/
_Pvt_Extensions/
ModelManifest.xml

@ -0,0 +1,101 @@
# Check versions
message(STATUS "CMake version: ${CMAKE_VERSION}")
cmake_minimum_required(VERSION 3.1)
set_property(GLOBAL PROPERTY USE_FOLDERS ON)
# Set the project name
set(PNAME Conways)
project(${PNAME})
# Set up variables, and find SFML
if (WIN32)
set(SFML_ROOT root CACHE STRING "User specified path")
set(SFML_INCLUDE_DIR ${SFML_ROOT}/include)
endif()
set(SFML_COMPONENTS graphics window system network audio)
set(CMAKE_MODULE_PATH ${CMAKE_CURRENT_SOURCE_DIR})
find_package(SFML 2.1 COMPONENTS ${SFML_COMPONENTS} REQUIRED)
message(STATUS "SFML found: ${SFML_FOUND}")
# Find OpenCL
find_package( OpenCL REQUIRED )
message(STATUS "OpenCL found: ${OPENCL_FOUND}")
# Find OpenGL
find_package( OpenGL REQUIRED)
message(STATUS "OpenGL found: ${OPENGL_FOUND}")
# Include the directories for the main program, GL, CL and SFML's headers
include_directories(${SFML_INCLUDE_DIR})
include_directories(${OpenCL_INCLUDE_DIRS})
include_directories(include)
# Glob all thr sources into their values
file(GLOB_RECURSE SOURCES "src/*.cpp")
file(GLOB_RECURSE HEADERS "include/*.h" "include/*.hpp")
file(GLOB_RECURSE KERNELS "kernels/*.cl")
add_executable(${PNAME} ${SOURCES} ${HEADERS} ${KERNELS})
# Follow the sub directory structure to add sub-filters in VS
# Gotta do it one by one unfortunately
foreach (source IN ITEMS ${SOURCES})
if (IS_ABSOLUTE "${source}")
get_filename_component(filename ${source} DIRECTORY)
STRING(REGEX REPLACE "/" "\\\\" filename ${filename})
string(REGEX MATCHALL "src(.*)" substrings ${filename})
list(GET substrings 0 substring)
SOURCE_GROUP(${substring} FILES ${source})
endif()
endforeach()
foreach (source IN ITEMS ${HEADERS})
if (IS_ABSOLUTE "${source}")
get_filename_component(filename ${source} DIRECTORY)
STRING(REGEX REPLACE "/" "\\\\" filename ${filename})
string(REGEX MATCHALL "include(.*)" substrings ${filename})
list(GET substrings 0 substring)
SOURCE_GROUP(${substring} FILES ${source})
endif()
endforeach()
foreach (source IN ITEMS ${KERNELS})
if (IS_ABSOLUTE "${source}")
get_filename_component(filename ${source} DIRECTORY)
STRING(REGEX REPLACE "/" "\\\\" filename ${filename})
string(REGEX MATCHALL "kernels(.*)" substrings ${filename})
list(GET substrings 0 substring)
SOURCE_GROUP(${substring} FILES ${source})
endif()
endforeach()
# Link CL, GL, and SFML
target_link_libraries (${PNAME} ${SFML_LIBRARIES} ${SFML_DEPENDENCIES})
target_link_libraries (${PNAME} ${OpenCL_LIBRARY})
target_link_libraries (${PNAME} ${OPENGL_LIBRARIES})
if (NOT WIN32)
target_link_libraries (${PNAME} -lpthread)
endif()
# Setup to use C++14
set_property(TARGET ${PNAME} PROPERTY CXX_STANDARD 14)

@ -1,28 +0,0 @@

Microsoft Visual Studio Solution File, Format Version 12.00
# Visual Studio 14
VisualStudioVersion = 14.0.23107.0
MinimumVisualStudioVersion = 10.0.40219.1
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "Conway_OpenCL", "Conway_OpenCL\Conway_OpenCL.vcxproj", "{000000DA-0000-0000-0000-000000000000}"
EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|x64 = Debug|x64
Debug|x86 = Debug|x86
Release|x64 = Release|x64
Release|x86 = Release|x86
EndGlobalSection
GlobalSection(ProjectConfigurationPlatforms) = postSolution
{000000DA-0000-0000-0000-000000000000}.Debug|x64.ActiveCfg = Debug|x64
{000000DA-0000-0000-0000-000000000000}.Debug|x64.Build.0 = Debug|x64
{000000DA-0000-0000-0000-000000000000}.Debug|x86.ActiveCfg = Debug|Win32
{000000DA-0000-0000-0000-000000000000}.Debug|x86.Build.0 = Debug|Win32
{000000DA-0000-0000-0000-000000000000}.Release|x64.ActiveCfg = Release|x64
{000000DA-0000-0000-0000-000000000000}.Release|x64.Build.0 = Release|x64
{000000DA-0000-0000-0000-000000000000}.Release|x86.ActiveCfg = Release|Win32
{000000DA-0000-0000-0000-000000000000}.Release|x86.Build.0 = Release|Win32
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE
EndGlobalSection
EndGlobal

@ -1,395 +0,0 @@
#include <CL/cl.h>
#include <CL/opencl.h>
#include <string.h>
#include <stdio.h>
#include <stdlib.h>
#include <iostream>
#include <string>
#include <fstream>
#include <random>
#include <ctime>
#include <SFML/Graphics.hpp>
#include <windows.h>
#include <GL/glew.h>
#include <GLFW/glfw3.h>
#include "Shader.hpp"
#define SUCCESS 0
#define FAILURE 1
float elap_time() {
static __int64 start = 0;
static __int64 frequency = 0;
if (start == 0) {
QueryPerformanceCounter((LARGE_INTEGER*)&start);
QueryPerformanceFrequency((LARGE_INTEGER*)&frequency);
return 0.0f;
}
__int64 counter = 0;
QueryPerformanceCounter((LARGE_INTEGER*)&counter);
return (float)((counter - start) / double(frequency));
}
// convert the kernel file into a string
int convertToString(const char *filename, std::string& s)
{
size_t size;
char* str;
std::fstream f(filename, (std::fstream::in | std::fstream::binary));
if(f.is_open())
{
size_t fileSize;
f.seekg(0, std::fstream::end);
size = fileSize = (size_t)f.tellg();
f.seekg(0, std::fstream::beg);
str = new char[size+1];
if(!str)
{
f.close();
return 0;
}
f.read(str, fileSize);
f.close();
str[size] = '\0';
s = str;
delete[] str;
return 0;
}
std::cout << "Error: failed to open file\n:" << filename << std::endl;
return FAILURE;
}
void key_callback(GLFWwindow* window, int key, int scancode, int action, int mode) {
if (key == GLFW_KEY_ESCAPE && action == GLFW_PRESS)
glfwSetWindowShouldClose(window, GL_TRUE);
}
int main(int argc, char* argv[])
{
int WINDOW_X = 1000;
int WINDOW_Y = 1000;
int GRID_WIDTH = WINDOW_X;
int GRID_HEIGHT = WINDOW_Y;
int WORKER_SIZE = 1000;
// ======================================= Setup OpenGL =======================================================
glfwInit();
glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3);
glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 3);
glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE);
glfwWindowHint(GLFW_RESIZABLE, GL_FALSE);
GLFWwindow* gl_window = glfwCreateWindow(GRID_WIDTH, GRID_HEIGHT, "GPU accelerated life", nullptr, nullptr);
glfwMakeContextCurrent(gl_window);
glfwSetKeyCallback(gl_window, key_callback);
glewExperimental = GL_TRUE;
glewInit();
glViewport(0, 0, GRID_WIDTH, GRID_HEIGHT);
glClearColor(0.2f, 0.3f, 0.3f, 1.0f);
// Stolen from LearnOpenGL, aint got no time for that
Shader vert_frag_shaders("Z:\\VS_Projects\\Conway_OpenCL\\Conway_OpenCL\\vertex_shader.sh", "Z:\\VS_Projects\\Conway_OpenCL\\Conway_OpenCL\\fragment_shader.sh");
GLfloat vertices[] = {
// Positions // Colors // Texture Coords
1.0f, 1.0f, 0.0f, 1.0f, 0.0f, 0.0f, 1.0f, 1.0f, // Top Right
1.0f, -1.0f, 0.0f, 0.0f, 1.0f, 0.0f, 1.0f, 0.0f, // Bottom Right
-1.0f, -1.0f, 0.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, // Bottom Left
-1.0f, 1.0f, 0.0f, 1.0f, 1.0f, 0.0f, 0.0f, 1.0f // Top Left
};
GLuint indices[] = {
0, 1, 3, // First Triangle
1, 2, 3 // Second Triangle
};
GLuint VBO, VAO, EBO;
glGenVertexArrays(1, &VAO);
glGenBuffers(1, &VBO);
glGenBuffers(1, &EBO);
// Bind the Vertex Array Object first, then bind and set vertex buffer(s) and attribute pointer(s).
glBindVertexArray(VAO);
glBindBuffer(GL_ARRAY_BUFFER, VBO);
glBufferData(GL_ARRAY_BUFFER, sizeof(vertices), vertices, GL_STATIC_DRAW);
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, EBO);
glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(indices), indices, GL_STATIC_DRAW);
// Position attribute
glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 8 * sizeof(GLfloat), (GLvoid*)0);
glEnableVertexAttribArray(0);
// Color attribute
glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, 8 * sizeof(GLfloat), (GLvoid*)(3 * sizeof(GLfloat)));
glEnableVertexAttribArray(1);
// TexCoord attribute
glVertexAttribPointer(2, 2, GL_FLOAT, GL_FALSE, 8 * sizeof(GLfloat), (GLvoid*)(6 * sizeof(GLfloat)));
glEnableVertexAttribArray(2);
glBindVertexArray(0); // Unbind VAO
// ============================== OpenCL Setup ==================================================================
// Get the platforms
cl_uint numPlatforms;
cl_platform_id platform = NULL;
cl_int status = clGetPlatformIDs(0, NULL, &numPlatforms); // Retrieve the number of platforms
if (status != CL_SUCCESS) {
std::cout << "Error: Getting platforms!" << std::endl;
return FAILURE;
}
// Choose the first available platform
if(numPlatforms > 0) {
cl_platform_id* platforms = new cl_platform_id[numPlatforms];
status = clGetPlatformIDs(numPlatforms, platforms, NULL); // Now populate the array with the platforms
platform = platforms[0];
delete platforms;
}
cl_uint numDevices = 0;
cl_device_id *devices;
status = clGetDeviceIDs(platform, CL_DEVICE_TYPE_GPU, 0, NULL, &numDevices);
if (numDevices == 0) { //no GPU available.
std::cout << "No GPU device available." << std::endl;
std::cout << "Choose CPU as default device." << std::endl;
status = clGetDeviceIDs(platform, CL_DEVICE_TYPE_CPU, 0, NULL, &numDevices);
devices = new cl_device_id[numDevices];
status = clGetDeviceIDs(platform, CL_DEVICE_TYPE_CPU, numDevices, devices, NULL);
}
else {
devices = new cl_device_id[numDevices];
status = clGetDeviceIDs(platform, CL_DEVICE_TYPE_GPU, numDevices, devices, NULL);
}
HGLRC hGLRC = wglGetCurrentContext();
HDC hDC = wglGetCurrentDC();
cl_context_properties cps[] ={CL_CONTEXT_PLATFORM, (cl_context_properties)platform, CL_GL_CONTEXT_KHR, (cl_context_properties)hGLRC, CL_WGL_HDC_KHR, (cl_context_properties)hDC, 0 };
cl_context context = clCreateContext(cps, 1, devices,NULL,NULL,NULL);
cl_command_queue commandQueue = clCreateCommandQueue(context, devices[0], 0, NULL);
// ============================== Kernel Compilation, Setup ====================================================
// Read the kernel from the file to a string
const char *compute_kernel_filename = "Z:\\VS_Projects\\Conway_OpenCL\\Conway_OpenCL\\conway_compute.cl";
const char *align_kernel_filename = "Z:\\VS_Projects\\Conway_OpenCL\\Conway_OpenCL\\conway_align.cl";
std::string compute_kernel_string;
std::string align_kernel_string;
convertToString(compute_kernel_filename, compute_kernel_string);
convertToString(align_kernel_filename, align_kernel_string);
// Create a program with the source
const char *compute_source = compute_kernel_string.c_str();
const char *align_source = align_kernel_string.c_str();
size_t compute_source_size[] = {strlen(compute_source)};
size_t align_source_size[] = { strlen(align_source) };
cl_program compute_program = clCreateProgramWithSource(context, 1, &compute_source, compute_source_size, NULL);
cl_program align_program = clCreateProgramWithSource(context, 1, &align_source, align_source_size, NULL);
// Build the compute program
status = clBuildProgram(compute_program, 1, devices, NULL, NULL, NULL);
if (status == CL_BUILD_PROGRAM_FAILURE) {
size_t log_size;
clGetProgramBuildInfo(compute_program, devices[0], CL_PROGRAM_BUILD_LOG, 0, NULL, &log_size);
char *log = new char[log_size];
clGetProgramBuildInfo(compute_program, devices[0], CL_PROGRAM_BUILD_LOG, log_size, log, NULL);
std::cout << log << std::endl;
}
// Build the align program
status = clBuildProgram(align_program, 1, devices, NULL, NULL, NULL);
if (status == CL_BUILD_PROGRAM_FAILURE) {
size_t log_size;
clGetProgramBuildInfo(align_program, devices[0], CL_PROGRAM_BUILD_LOG, 0, NULL, &log_size);
char *log = new char[log_size];
clGetProgramBuildInfo(align_program, devices[0], CL_PROGRAM_BUILD_LOG, log_size, log, NULL);
std::cout << log << std::endl;
}
// Now create the kernels
cl_kernel compute_kernel = clCreateKernel(compute_program, "conway_compute", NULL);
cl_kernel align_kernel = clCreateKernel(align_program, "conway_align", NULL);
// ======================================= Setup grid =========================================================
// Setup the rng
std::mt19937 rng(time(NULL));
std::uniform_int_distribution<int> rgen(0, 4); // 25% chance
// Init the grids
unsigned char* node_grid = new unsigned char[GRID_WIDTH * GRID_HEIGHT];
for (int i = 0; i < GRID_WIDTH * GRID_HEIGHT; i++) {
if (rgen(rng) == 1) {
node_grid[i] = 1;
}
else {
node_grid[i] = 0;
}
}
// ====================================== Setup Rendering ==========================================================
unsigned char* pixel_array = new sf::Uint8[WINDOW_X * WINDOW_Y * 4];
for (int i = 0; i < GRID_WIDTH * GRID_HEIGHT * 4; i += 4) {
pixel_array[i] = i % 255; // R?
pixel_array[i + 1] = 70; // G?
pixel_array[i + 2] = 100; // B?
pixel_array[i + 3] = 100; // A?
}
GLuint texture;
glGenTextures(1, &texture);
glBindTexture(GL_TEXTURE_2D, texture);
//////////////////////////
glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_DECAL);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_DECAL);
// when texture area is small, bilinear filter the closest mipmap
glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_NEAREST);
// when texture area is large, bilinear filter the first mipmap
glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
// texture should tile
glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, GRID_WIDTH, GRID_HEIGHT, 0, GL_RGBA, GL_UNSIGNED_BYTE, pixel_array);
glGenerateMipmap(GL_TEXTURE_2D);
delete pixel_array;
// ========================================= Setup the buffers ==================================================
int err = 0;
cl_mem frontWriteBuffer = clCreateFromGLTexture(context , CL_MEM_WRITE_ONLY, GL_TEXTURE_2D, 0, texture, &err);
cl_mem frontReadBuffer = clCreateFromGLTexture(context, CL_MEM_READ_ONLY, GL_TEXTURE_2D, 0, texture, &err);
cl_mem backBuffer = clCreateBuffer(context, CL_MEM_READ_WRITE | CL_MEM_COPY_HOST_PTR, sizeof(int), (void*)node_grid, &err);
cl_mem workerCountBuffer = clCreateBuffer(context, CL_MEM_READ_ONLY | CL_MEM_COPY_HOST_PTR, sizeof(int), &WORKER_SIZE, &err);
cl_mem gridWidthBuffer = clCreateBuffer(context, CL_MEM_READ_ONLY | CL_MEM_COPY_HOST_PTR, sizeof(int), &GRID_WIDTH, &err);
cl_mem gridHeightBuffer = clCreateBuffer(context, CL_MEM_READ_ONLY | CL_MEM_COPY_HOST_PTR, sizeof(int), &GRID_HEIGHT, &err);
// Compute kernel args
status = clSetKernelArg(compute_kernel, 0, sizeof(cl_mem), (void *)&frontWriteBuffer);
status = clSetKernelArg(compute_kernel, 1, sizeof(cl_mem), (void *)&backBuffer);
status = clSetKernelArg(compute_kernel, 2, sizeof(cl_mem), (void *)&workerCountBuffer);
status = clSetKernelArg(compute_kernel, 3, sizeof(cl_mem), (void *)&gridWidthBuffer);
status = clSetKernelArg(compute_kernel, 4, sizeof(cl_mem), (void *)&gridHeightBuffer);
status = clSetKernelArg(align_kernel, 0, sizeof(cl_mem), (void *)&frontReadBuffer);
status = clSetKernelArg(align_kernel, 1, sizeof(cl_mem), (void *)&backBuffer);
status = clSetKernelArg(align_kernel, 2, sizeof(cl_mem), (void *)&workerCountBuffer);
status = clSetKernelArg(align_kernel, 3, sizeof(cl_mem), (void *)&gridWidthBuffer);
status = clSetKernelArg(align_kernel, 4, sizeof(cl_mem), (void *)&gridHeightBuffer);
// ===================================== Loop ==================================================================
while (!glfwWindowShouldClose(gl_window)) {
glClearColor(0.2f, 0.3f, 0.3f, 1.0f);
glClear(GL_COLOR_BUFFER_BIT);
// ======================================= OpenCL Shtuff ===================================================
// Work size, for each y line
size_t global_work_size[1] = { WORKER_SIZE };
status = clEnqueueAcquireGLObjects(commandQueue, 1, &frontReadBuffer, 0, 0, 0);
status = clEnqueueAcquireGLObjects(commandQueue, 1, &frontWriteBuffer, 0, 0, 0);
status = clEnqueueNDRangeKernel(commandQueue, compute_kernel, 1, NULL, global_work_size, NULL, 0, NULL, NULL);
status = clEnqueueNDRangeKernel(commandQueue, align_kernel, 1, NULL, global_work_size, NULL, 0, NULL, NULL);
status = clEnqueueReleaseGLObjects(commandQueue, 1, &frontReadBuffer, 0, NULL, NULL);
status = clEnqueueReleaseGLObjects(commandQueue, 1, &frontWriteBuffer, 0, NULL, NULL);
clFinish(commandQueue);
// ======================================= Rendering Shtuff =================================================
glfwPollEvents();
glActiveTexture(GL_TEXTURE0);
glBindTexture(GL_TEXTURE_2D, texture);
glUniform1i(glGetUniformLocation(vert_frag_shaders.Program, "pixel_texture"), 0);
// Draw the triangle
vert_frag_shaders.Use();
glBindVertexArray(VAO);
glDrawElements(GL_TRIANGLES, 6, GL_UNSIGNED_INT, 0);
glBindVertexArray(0);
glFinish();
// Render
glfwSwapBuffers(gl_window);
}
glfwTerminate();
// Release the buffers
status = clReleaseMemObject(frontReadBuffer);
status = clReleaseMemObject(workerCountBuffer);
status = clReleaseMemObject(gridWidthBuffer);
status = clReleaseMemObject(gridHeightBuffer);
// And the program stuff
status = clReleaseKernel(compute_kernel);
status = clReleaseProgram(compute_program);
status = clReleaseProgram(align_program);
status = clReleaseCommandQueue(commandQueue);
status = clReleaseContext(context);
if (devices != NULL)
{
delete devices;
devices = NULL;
}
return SUCCESS;
}

@ -1,241 +0,0 @@
<?xml version="1.0" encoding="utf-8"?>
<Project DefaultTargets="Build" ToolsVersion="14.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<ItemGroup Label="ProjectConfigurations">
<ProjectConfiguration Include="Debug|Win32">
<Configuration>Debug</Configuration>
<Platform>Win32</Platform>
</ProjectConfiguration>
<ProjectConfiguration Include="Debug|x64">
<Configuration>Debug</Configuration>
<Platform>x64</Platform>
</ProjectConfiguration>
<ProjectConfiguration Include="Release|Win32">
<Configuration>Release</Configuration>
<Platform>Win32</Platform>
</ProjectConfiguration>
<ProjectConfiguration Include="Release|x64">
<Configuration>Release</Configuration>
<Platform>x64</Platform>
</ProjectConfiguration>
</ItemGroup>
<PropertyGroup Label="Globals">
<ProjectGuid>{000000DA-0000-0000-0000-000000000000}</ProjectGuid>
<RootNamespace>Conway_OpenCL</RootNamespace>
<ProjectName>Conway_OpenCL</ProjectName>
</PropertyGroup>
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
<ConfigurationType>Application</ConfigurationType>
<UseDebugLibraries>true</UseDebugLibraries>
<PlatformToolset>v140</PlatformToolset>
<CharacterSet>MultiByte</CharacterSet>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
<ConfigurationType>Application</ConfigurationType>
<UseDebugLibraries>true</UseDebugLibraries>
<PlatformToolset>v140</PlatformToolset>
<CharacterSet>MultiByte</CharacterSet>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
<ConfigurationType>Application</ConfigurationType>
<UseDebugLibraries>false</UseDebugLibraries>
<PlatformToolset>v140</PlatformToolset>
<WholeProgramOptimization>false</WholeProgramOptimization>
<CharacterSet>MultiByte</CharacterSet>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
<ConfigurationType>Application</ConfigurationType>
<UseDebugLibraries>false</UseDebugLibraries>
<PlatformToolset>v140</PlatformToolset>
<WholeProgramOptimization>true</WholeProgramOptimization>
<CharacterSet>MultiByte</CharacterSet>
</PropertyGroup>
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
<ImportGroup Label="ExtensionSettings">
</ImportGroup>
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
</ImportGroup>
<ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
</ImportGroup>
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
</ImportGroup>
<ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
</ImportGroup>
<PropertyGroup Label="UserMacros" />
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
<LinkIncremental>false</LinkIncremental>
<OutDir>$(SolutionDir)bin\x86\$(Configuration)\</OutDir>
<IntDir>temp\x86\$(Configuration)\</IntDir>
<IncludePath>Z:\Cpp_Libs\SFML-Visual_Studio2015RCx32\include;Z:\Cpp_Libs\glew-1.13.0\include;Z:\Cpp_Libs\glfw-3.1.2.bin.WIN32\include;$(IncludePath)</IncludePath>
<LibraryPath>Z:\Cpp_Libs\SFML-Visual_Studio2015RCx32\lib;Z:\Cpp_Libs\glew-1.13.0\lib\Release\Win32;Z:\Cpp_Libs\glfw-3.1.2.bin.WIN32\lib-vc2015;$(LibraryPath)</LibraryPath>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
<OutDir>$(SolutionDir)bin\x86\$(Configuration)\</OutDir>
<IntDir>temp\x86\$(Configuration)\</IntDir>
<IncludePath>Z:\Cpp_Libs\SFML-Visual_Studio2015RCx32\include;Z:\Cpp_Libs\glew-1.13.0\include;Z:\Cpp_Libs\glfw-3.1.2.bin.WIN32\include;$(IncludePath)</IncludePath>
<LibraryPath>Z:\Cpp_Libs\SFML-Visual_Studio2015RCx32\lib;Z:\Cpp_Libs\glew-1.13.0\lib\Release\Win32;Z:\Cpp_Libs\glfw-3.1.2.bin.WIN32\lib-vc2015;$(LibraryPath)</LibraryPath>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
<OutDir>$(SolutionDir)bin\x86_64\$(Configuration)\</OutDir>
<IntDir>temp\x86_64\$(Configuration)\</IntDir>
<IncludePath>Z:\Cpp_Libs\SFML-Visual_Studio2015RCx64\include;Z:\Cpp_Libs\glew-1.13.0\include;Z:\Cpp_Libs\glfw-3.1.2.bin.WIN64\include;$(IncludePath)</IncludePath>
<LibraryPath>Z:\Cpp_Libs\SFML-Visual_Studio2015RCx64\lib;Z:\Cpp_Libs\glew-1.13.0\lib\Release\x64;Z:\Cpp_Libs\glfw-3.1.2.bin.WIN64\lib-vc2015;$(LibraryPath)</LibraryPath>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
<OutDir>$(SolutionDir)bin\x86_64\$(Configuration)\</OutDir>
<IntDir>temp\x86_64\$(Configuration)\</IntDir>
<LinkIncremental>false</LinkIncremental>
<IncludePath>Z:\Cpp_Libs\SFML-Visual_Studio2015RCx64\include;Z:\Cpp_Libs\glew-1.13.0\include;Z:\Cpp_Libs\glfw-3.1.2.bin.WIN64\include;$(IncludePath)</IncludePath>
<LibraryPath>Z:\Cpp_Libs\SFML-Visual_Studio2015RCx64\lib;Z:\Cpp_Libs\glew-1.13.0\lib\Release\x64;Z:\Cpp_Libs\glfw-3.1.2.bin.WIN64\lib-vc2015;$(LibraryPath)</LibraryPath>
</PropertyGroup>
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
<ClCompile>
<WarningLevel>Level3</WarningLevel>
<Optimization>Disabled</Optimization>
<AdditionalIncludeDirectories>../../../../include;../../../../include/SDKUtil;$(AMDAPPSDKROOT)/include;Z:\Cpp_Libs\SFML-Visual_Studio2015RCx32\include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
<InlineFunctionExpansion>Disabled</InlineFunctionExpansion>
<PreprocessorDefinitions>WIN32;_WINDOWS;_DEBUG;_CRT_SECURE_NO_WARNINGS;CMAKE_INTDIR="Debug";%(PreprocessorDefinitions)</PreprocessorDefinitions>
<MinimalRebuild>false</MinimalRebuild>
<RuntimeTypeInfo>true</RuntimeTypeInfo>
<CompileAs>CompileAsCpp</CompileAs>
<DisableSpecificWarnings>4005;4996</DisableSpecificWarnings>
<DebugInformationFormat>ProgramDatabase</DebugInformationFormat>
<ProgramDataBaseFileName>$(SolutionDir)bin/x86/Debug/HelloWorld.pdb</ProgramDataBaseFileName>
<AssemblerListingLocation>Debug</AssemblerListingLocation>
</ClCompile>
<Link>
<GenerateDebugInformation>true</GenerateDebugInformation>
<AdditionalLibraryDirectories>..\..\..\..\lib\win32\;$(AMDAPPSDKROOT)\lib\x86\;%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
<AdditionalDependencies>kernel32.lib;user32.lib;gdi32.lib;winspool.lib;shell32.lib;ole32.lib;oleaut32.lib;uuid.lib;comdlg32.lib;advapi32.lib;OpenCL.lib;opengl32.lib;glew32.lib;glfw3.lib;sfml-graphics-d.lib;sfml-audio-d.lib;sfml-network-d.lib;sfml-system-d.lib;sfml-window-d.lib;%(AdditionalDependencies)</AdditionalDependencies>
<SubSystem>Console</SubSystem>
<ImageHasSafeExceptionHandlers>false</ImageHasSafeExceptionHandlers>
<AdditionalOptions> /machine:X86 /debug %(AdditionalOptions)</AdditionalOptions>
<ImportLibrary>$(SolutionDir)bin/x86/Debug/HelloWorld.lib</ImportLibrary>
</Link>
<PostBuildEvent>
<Command>copy conway_compute.cl "$(OutDir)conway_kernel.cl" /Y
copy conway_align.cl "$(OutDir)conway_kernel.cl" /Y</Command>
</PostBuildEvent>
</ItemDefinitionGroup>
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
<ClCompile>
<WarningLevel>Level3</WarningLevel>
<Optimization>Disabled</Optimization>
<AdditionalIncludeDirectories>../../../../include;../../../../include/SDKUtil;$(AMDAPPSDKROOT)/include;Z:\Cpp_Libs\SFML-Visual_Studio2015RCx64\include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
<InlineFunctionExpansion>Disabled</InlineFunctionExpansion>
<PreprocessorDefinitions>WIN32;_WINDOWS;_DEBUG;_CRT_SECURE_NO_WARNINGS;CMAKE_INTDIR="Debug";%(PreprocessorDefinitions)</PreprocessorDefinitions>
<RuntimeTypeInfo>true</RuntimeTypeInfo>
<ProgramDataBaseFileName>$(SolutionDir)bin/x86_64/Debug/HelloWorld.pdb</ProgramDataBaseFileName>
<AssemblerListingLocation>Debug</AssemblerListingLocation>
<CompileAs>CompileAsCpp</CompileAs>
<DisableSpecificWarnings>4005;4996</DisableSpecificWarnings>
</ClCompile>
<Link>
<GenerateDebugInformation>true</GenerateDebugInformation>
<AdditionalLibraryDirectories>..\..\..\..\lib\win64\;$(AMDAPPSDKROOT)\lib\x86_64\;%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
<AdditionalDependencies>kernel32.lib;user32.lib;gdi32.lib;winspool.lib;shell32.lib;ole32.lib;oleaut32.lib;uuid.lib;comdlg32.lib;advapi32.lib;OpenCL.lib;opengl32.lib;glfw3.lib;glew32.lib;sfml-graphics-d.lib;sfml-audio-d.lib;sfml-network-d.lib;sfml-system-d.lib;sfml-window-d.lib;%(AdditionalDependencies)</AdditionalDependencies>
<SubSystem>Console</SubSystem>
<ImportLibrary>$(SolutionDir)bin/x86_64/Debug/HelloWorld.lib</ImportLibrary>
<ImageHasSafeExceptionHandlers>false</ImageHasSafeExceptionHandlers>
<AdditionalOptions> /machine:x64 /debug %(AdditionalOptions)</AdditionalOptions>
</Link>
<PostBuildEvent>
<Command>copy conway_compute.cl "$(OutDir)conway_kernel.cl" /Y
copy conway_align.cl "$(OutDir)conway_kernel.cl" /Y</Command>
</PostBuildEvent>
</ItemDefinitionGroup>
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
<ClCompile>
<WarningLevel>Level3</WarningLevel>
<Optimization>MaxSpeed</Optimization>
<FunctionLevelLinking>
</FunctionLevelLinking>
<IntrinsicFunctions>false</IntrinsicFunctions>
<AdditionalIncludeDirectories>../../../../include;../../../../include/SDKUtil;$(AMDAPPSDKROOT)/include;Z:\Cpp_Libs\SFML-Visual_Studio2015RCx32\include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
<DebugInformationFormat />
<InlineFunctionExpansion>AnySuitable</InlineFunctionExpansion>
<PreprocessorDefinitions>WIN32;_WINDOWS;NDEBUG;_CRT_SECURE_NO_WARNINGS;CMAKE_INTDIR="Release";%(PreprocessorDefinitions)</PreprocessorDefinitions>
<RuntimeTypeInfo>true</RuntimeTypeInfo>
<ProgramDataBaseFileName>$(SolutionDir)bin/x86/Release/HelloWorld.pdb</ProgramDataBaseFileName>
<CompileAs>CompileAsCpp</CompileAs>
<DisableSpecificWarnings>4005;4996</DisableSpecificWarnings>
<AssemblerListingLocation>Release</AssemblerListingLocation>
</ClCompile>
<Link>
<GenerateDebugInformation>false</GenerateDebugInformation>
<EnableCOMDATFolding>
</EnableCOMDATFolding>
<OptimizeReferences>
</OptimizeReferences>
<AdditionalDependencies>kernel32.lib;user32.lib;gdi32.lib;winspool.lib;shell32.lib;ole32.lib;oleaut32.lib;uuid.lib;comdlg32.lib;advapi32.lib;OpenCL.lib;opengl32.lib;glew32.lib;glfw3.lib;sfml-graphics.lib;sfml-audio.lib;sfml-network.lib;sfml-system.lib;sfml-window.lib;%(AdditionalDependencies)</AdditionalDependencies>
<AdditionalLibraryDirectories>..\..\..\..\lib\win32\;$(AMDAPPSDKROOT)\lib\x86\;%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
<SubSystem>Console</SubSystem>
<ImportLibrary>$(SolutionDir)bin/x86/Release/HelloWorld.lib</ImportLibrary>
<ImageHasSafeExceptionHandlers>false</ImageHasSafeExceptionHandlers>
<AdditionalOptions> /machine:X86 %(AdditionalOptions)</AdditionalOptions>
</Link>
<ProjectReference>
<LinkLibraryDependencies>false</LinkLibraryDependencies>
</ProjectReference>
<PostBuildEvent>
<Command>copy conway_compute.cl "$(OutDir)conway_kernel.cl" /Y
copy conway_align.cl "$(OutDir)conway_kernel.cl" /Y</Command>
</PostBuildEvent>
</ItemDefinitionGroup>
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
<ClCompile>
<WarningLevel>Level3</WarningLevel>
<Optimization>MaxSpeed</Optimization>
<FunctionLevelLinking>
</FunctionLevelLinking>
<IntrinsicFunctions>false</IntrinsicFunctions>
<AdditionalIncludeDirectories>../../../../include;../../../../include/SDKUtil;$(AMDAPPSDKROOT)/include;Z:\Cpp_Libs\SFML-Visual_Studio2015RCx64\include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
<InlineFunctionExpansion>AnySuitable</InlineFunctionExpansion>
<DebugInformationFormat />
<PreprocessorDefinitions>WIN32;_WINDOWS;NDEBUG;_CRT_SECURE_NO_WARNINGS;CMAKE_INTDIR="Release";%(PreprocessorDefinitions)</PreprocessorDefinitions>
<RuntimeTypeInfo>true</RuntimeTypeInfo>
<AssemblerListingLocation>Release</AssemblerListingLocation>
<CompileAs>CompileAsCpp</CompileAs>
<DisableSpecificWarnings>4005;4996</DisableSpecificWarnings>
<ProgramDataBaseFileName>$(SolutionDir)bin/x86_64/Release/HelloWorld.pdb</ProgramDataBaseFileName>
<WholeProgramOptimization>false</WholeProgramOptimization>
</ClCompile>
<Link>
<GenerateDebugInformation>false</GenerateDebugInformation>
<EnableCOMDATFolding>
</EnableCOMDATFolding>
<OptimizeReferences>
</OptimizeReferences>
<AdditionalLibraryDirectories>..\..\..\..\lib\win64\;$(AMDAPPSDKROOT)\lib\x86_64\;%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
<AdditionalDependencies>kernel32.lib;user32.lib;gdi32.lib;winspool.lib;shell32.lib;ole32.lib;oleaut32.lib;uuid.lib;comdlg32.lib;advapi32.lib;OpenCL.lib;opengl32.lib;glfw3.lib;glew32.lib;sfml-graphics.lib;sfml-audio.lib;sfml-network.lib;sfml-system.lib;sfml-window.lib;%(AdditionalDependencies)</AdditionalDependencies>
<SubSystem>Console</SubSystem>
<LinkTimeCodeGeneration />
<ImportLibrary>$(SolutionDir)bin/x86_64/Release/HelloWorld.lib</ImportLibrary>
<ImageHasSafeExceptionHandlers>false</ImageHasSafeExceptionHandlers>
<AdditionalOptions> /machine:x64 %(AdditionalOptions)</AdditionalOptions>
</Link>
<PostBuildEvent>
<Command>copy conway_compute.cl "$(OutDir)conway_kernel.cl" /Y
copy conway_align.cl "$(OutDir)conway_kernel.cl" /Y</Command>
</PostBuildEvent>
</ItemDefinitionGroup>
<ItemGroup>
<ClCompile Include="Conway.hpp" />
</ItemGroup>
<ItemGroup>
<None Include="conway_compute.cl" />
<None Include="conway_align.cl" />
<None Include="fragment_shader.sh" />
<None Include="vertex_shader.sh" />
</ItemGroup>
<ItemGroup>
<ClInclude Include="Shader.hpp" />
</ItemGroup>
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
<ImportGroup Label="ExtensionTargets">
</ImportGroup>
</Project>

@ -1,90 +0,0 @@
#ifndef SHADER_H
#define SHADER_H
#include <string>
#include <fstream>
#include <sstream>
#include <iostream>
#include <GL/glew.h>
class Shader {
public:
GLuint Program;
// Constructor generates the shader on the fly
Shader(const GLchar* vertexPath, const GLchar* fragmentPath) {
// 1. Retrieve the vertex/fragment source code from filePath
std::string vertexCode;
std::string fragmentCode;
std::ifstream vShaderFile;
std::ifstream fShaderFile;
// ensures ifstream objects can throw exceptions:
vShaderFile.exceptions(std::ifstream::badbit);
fShaderFile.exceptions(std::ifstream::badbit);
try {
// Open files
vShaderFile.open(vertexPath);
fShaderFile.open(fragmentPath);
std::stringstream vShaderStream, fShaderStream;
// Read file's buffer contents into streams
vShaderStream << vShaderFile.rdbuf();
fShaderStream << fShaderFile.rdbuf();
// close file handlers
vShaderFile.close();
fShaderFile.close();
// Convert stream into string
vertexCode = vShaderStream.str();
fragmentCode = fShaderStream.str();
}
catch (std::ifstream::failure e) {
std::cout << "ERROR::SHADER::FILE_NOT_SUCCESFULLY_READ" << std::endl;
}
const GLchar* vShaderCode = vertexCode.c_str();
const GLchar * fShaderCode = fragmentCode.c_str();
GLint success = 0;
GLchar infoLog[512];
// Vertex Shader
GLuint vertex = glCreateShader(GL_VERTEX_SHADER);
glShaderSource(vertex, 1, &vShaderCode, NULL);
glCompileShader(vertex);
// Print compile errors if any
glGetShaderiv(vertex, GL_COMPILE_STATUS, &success);
if (!success) {
glGetShaderInfoLog(vertex, 512, NULL, infoLog);
std::cout << "ERROR::SHADER::VERTEX::COMPILATION_FAILED\n" << infoLog << std::endl;
}
// Fragment Shader
GLuint fragment = glCreateShader(GL_FRAGMENT_SHADER);
glShaderSource(fragment, 1, &fShaderCode, NULL);
glCompileShader(fragment);
// Print compile errors if any
glGetShaderiv(fragment, GL_COMPILE_STATUS, &success);
if (!success) {
glGetShaderInfoLog(fragment, 512, NULL, infoLog);
std::cout << "ERROR::SHADER::FRAGMENT::COMPILATION_FAILED\n" << infoLog << std::endl;
}
// Shader Program
this->Program = glCreateProgram();
glAttachShader(this->Program, vertex);
glAttachShader(this->Program, fragment);
glLinkProgram(this->Program);
// Print linking errors if any
glGetProgramiv(this->Program, GL_LINK_STATUS, &success);
if (!success) {
glGetProgramInfoLog(this->Program, 512, NULL, infoLog);
std::cout << "ERROR::SHADER::PROGRAM::LINKING_FAILED\n" << infoLog << std::endl;
}
// Delete the shaders as they're linked into our program now and no longer necessery
glDeleteShader(vertex);
glDeleteShader(fragment);
}
// Uses the current shader
void Use() {
glUseProgram(this->Program);
}
};
#endif

@ -1,20 +0,0 @@
__kernel void conway_align(__read_only image2d_t front_image, __global char* back_image, __global int* num_workers, __global int* grid_width, __global int *grid_height)
{
const sampler_t sampler=CLK_NORMALIZED_COORDS_FALSE | CLK_ADDRESS_CLAMP | CLK_FILTER_NEAREST;
// Caclulate the start and end range that this worker will be calculating
int data_length = *grid_width * *grid_height;
int start_range = (data_length / *num_workers) * get_global_id(0);
int end_range = (data_length / *num_workers) * (get_global_id(0) + 1);
for (int i = start_range; i < end_range; i++){
uint4 pixel;
pixel = read_imageui(front_image, sampler, (int2)(i,get_global_id(0)));
back_image[i] = pixel.w / 255;
}
}

@ -1,59 +0,0 @@
__kernel void conway_compute(__write_only image2d_t front_image, __global char* back_image, __global int* num_workers, __global int* grid_width, __global int *grid_height)
{
float4 black = (float4)(.49, .68, .81, 1);
float4 white = (float4)(.49, .68, .71, .3);
// Caclulate the start and end range that this worker will be calculating
int data_length = *grid_width * *grid_height;
int start_range = (data_length / *num_workers) * get_global_id(0);
int end_range = (data_length / *num_workers) * (get_global_id(0) + 1);
// x, y + 1
int neighbors = 0;
for (int i = start_range; i < end_range; i++){
int2 pixelcoord = (int2) (i % *grid_width, i / *grid_height);
// add all 8 blocks to neghbors
neighbors = 0;
// Top
neighbors += back_image[i - *grid_width];
// Top right
neighbors += back_image[i - *grid_width + 1];
// Right
neighbors += back_image[i + 1];
// Bottom Right
neighbors += back_image[i + *grid_width + 1];
// Bottom
neighbors += back_image[i + *grid_width];
// Bottom Left
neighbors += back_image[i + *grid_width - 1];
// Left
neighbors += back_image[i - 1];
// Top left
neighbors += back_image[i - *grid_width - 1];
// push living status to the padded second char
write_imagef(front_image, pixelcoord, black);
if (neighbors == 3 || (neighbors == 2 && back_image[i])){
write_imagef(front_image, pixelcoord, white);
}
//else
//write_imagei(front_image, pixelcoord, white);
}
}

@ -1,15 +0,0 @@
#version 330 core
in vec3 ourColor;
in vec2 TexCoord;
out vec4 color;
// Texture samplers
uniform sampler2D pixel_texture;
void main()
{
// Linearly interpolate between both textures (second texture is only slightly combined)
//color = vec4(1.0f, 0.5f, 0.2f, 1.0f);
color = texture(pixel_texture, TexCoord);
}

@ -1,16 +0,0 @@
#version 330 core
layout (location = 0) in vec3 position;
layout (location = 1) in vec3 color;
layout (location = 2) in vec2 texCoord;
out vec3 ourColor;
out vec2 TexCoord;
void main()
{
gl_Position = vec4(position, 1.0f);
ourColor = color;
// We swap the y-axis by substracing our coordinates from 1. This is done because most images have the top y-axis inversed with OpenGL's top y-axis.
// TexCoord = texCoord;
TexCoord = vec2(texCoord.x, 1.0 - texCoord.y);
}

@ -1,241 +0,0 @@
<?xml version="1.0" encoding="utf-8"?>
<Project DefaultTargets="Build" ToolsVersion="14.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<ItemGroup Label="ProjectConfigurations">
<ProjectConfiguration Include="Debug|Win32">
<Configuration>Debug</Configuration>
<Platform>Win32</Platform>
</ProjectConfiguration>
<ProjectConfiguration Include="Debug|x64">
<Configuration>Debug</Configuration>
<Platform>x64</Platform>
</ProjectConfiguration>
<ProjectConfiguration Include="Release|Win32">
<Configuration>Release</Configuration>
<Platform>Win32</Platform>
</ProjectConfiguration>
<ProjectConfiguration Include="Release|x64">
<Configuration>Release</Configuration>
<Platform>x64</Platform>
</ProjectConfiguration>
</ItemGroup>
<PropertyGroup Label="Globals">
<ProjectGuid>{000000DA-0000-0000-0000-000000000000}</ProjectGuid>
<RootNamespace>Conway_OpenCL</RootNamespace>
<ProjectName>Conway_OpenCL</ProjectName>
</PropertyGroup>
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
<ConfigurationType>Application</ConfigurationType>
<UseDebugLibraries>true</UseDebugLibraries>
<PlatformToolset>v140</PlatformToolset>
<CharacterSet>MultiByte</CharacterSet>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
<ConfigurationType>Application</ConfigurationType>
<UseDebugLibraries>true</UseDebugLibraries>
<PlatformToolset>v140</PlatformToolset>
<CharacterSet>MultiByte</CharacterSet>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
<ConfigurationType>Application</ConfigurationType>
<UseDebugLibraries>false</UseDebugLibraries>
<PlatformToolset>v140</PlatformToolset>
<WholeProgramOptimization>false</WholeProgramOptimization>
<CharacterSet>MultiByte</CharacterSet>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
<ConfigurationType>Application</ConfigurationType>
<UseDebugLibraries>false</UseDebugLibraries>
<PlatformToolset>v140</PlatformToolset>
<WholeProgramOptimization>true</WholeProgramOptimization>
<CharacterSet>MultiByte</CharacterSet>
</PropertyGroup>
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
<ImportGroup Label="ExtensionSettings">
</ImportGroup>
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
</ImportGroup>
<ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
</ImportGroup>
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
</ImportGroup>
<ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
</ImportGroup>
<PropertyGroup Label="UserMacros" />
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
<LinkIncremental>false</LinkIncremental>
<OutDir>$(SolutionDir)bin\x86\$(Configuration)\</OutDir>
<IntDir>temp\x86\$(Configuration)\</IntDir>
<IncludePath>Z:\Cpp_Libs\SFML-Visual_Studio2015RCx32\include;Z:\Cpp_Libs\glew-1.13.0\include;Z:\Cpp_Libs\glfw-3.1.2.bin.WIN32\include;$(IncludePath)</IncludePath>
<LibraryPath>Z:\Cpp_Libs\SFML-Visual_Studio2015RCx32\lib;Z:\Cpp_Libs\glew-1.13.0\lib\Release\Win32;Z:\Cpp_Libs\glfw-3.1.2.bin.WIN32\lib-vc2015;$(LibraryPath)</LibraryPath>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
<OutDir>$(SolutionDir)bin\x86\$(Configuration)\</OutDir>
<IntDir>temp\x86\$(Configuration)\</IntDir>
<IncludePath>Z:\Cpp_Libs\SFML-Visual_Studio2015RCx32\include;Z:\Cpp_Libs\glew-1.13.0\include;Z:\Cpp_Libs\glfw-3.1.2.bin.WIN32\include;$(IncludePath)</IncludePath>
<LibraryPath>Z:\Cpp_Libs\SFML-Visual_Studio2015RCx32\lib;Z:\Cpp_Libs\glew-1.13.0\lib\Release\Win32;Z:\Cpp_Libs\glfw-3.1.2.bin.WIN32\lib-vc2015;$(LibraryPath)</LibraryPath>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
<OutDir>$(SolutionDir)bin\x86_64\$(Configuration)\</OutDir>
<IntDir>temp\x86_64\$(Configuration)\</IntDir>
<IncludePath>Z:\Cpp_Libs\SFML-Visual_Studio2015RCx64\include;Z:\Cpp_Libs\glew-1.13.0\include;Z:\Cpp_Libs\glfw-3.1.2.bin.WIN64\include;$(IncludePath)</IncludePath>
<LibraryPath>Z:\Cpp_Libs\SFML-Visual_Studio2015RCx64\lib;Z:\Cpp_Libs\glew-1.13.0\lib\Release\x64;Z:\Cpp_Libs\glfw-3.1.2.bin.WIN64\lib-vc2015;$(LibraryPath)</LibraryPath>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
<OutDir>$(SolutionDir)bin\x86_64\$(Configuration)\</OutDir>
<IntDir>temp\x86_64\$(Configuration)\</IntDir>
<LinkIncremental>false</LinkIncremental>
<IncludePath>Z:\Cpp_Libs\SFML-Visual_Studio2015RCx64\include;Z:\Cpp_Libs\glew-1.13.0\include;Z:\Cpp_Libs\glfw-3.1.2.bin.WIN64\include;$(IncludePath)</IncludePath>
<LibraryPath>Z:\Cpp_Libs\SFML-Visual_Studio2015RCx64\lib;Z:\Cpp_Libs\glew-1.13.0\lib\Release\x64;Z:\Cpp_Libs\glfw-3.1.2.bin.WIN64\lib-vc2015;$(LibraryPath)</LibraryPath>
</PropertyGroup>
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
<ClCompile>
<WarningLevel>Level3</WarningLevel>
<Optimization>Disabled</Optimization>
<AdditionalIncludeDirectories>../../../../include;../../../../include/SDKUtil;$(AMDAPPSDKROOT)/include;Z:\Cpp_Libs\SFML-Visual_Studio2015RCx32\include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
<InlineFunctionExpansion>Disabled</InlineFunctionExpansion>
<PreprocessorDefinitions>WIN32;_WINDOWS;_DEBUG;_CRT_SECURE_NO_WARNINGS;CMAKE_INTDIR="Debug";%(PreprocessorDefinitions)</PreprocessorDefinitions>
<MinimalRebuild>false</MinimalRebuild>
<RuntimeTypeInfo>true</RuntimeTypeInfo>
<CompileAs>CompileAsCpp</CompileAs>
<DisableSpecificWarnings>4005;4996</DisableSpecificWarnings>
<DebugInformationFormat>ProgramDatabase</DebugInformationFormat>
<ProgramDataBaseFileName>$(SolutionDir)bin/x86/Debug/HelloWorld.pdb</ProgramDataBaseFileName>
<AssemblerListingLocation>Debug</AssemblerListingLocation>
</ClCompile>
<Link>
<GenerateDebugInformation>true</GenerateDebugInformation>
<AdditionalLibraryDirectories>..\..\..\..\lib\win32\;$(AMDAPPSDKROOT)\lib\x86\;%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
<AdditionalDependencies>kernel32.lib;user32.lib;gdi32.lib;winspool.lib;shell32.lib;ole32.lib;oleaut32.lib;uuid.lib;comdlg32.lib;advapi32.lib;OpenCL.lib;opengl32.lib;glew32.lib;glfw3.lib;sfml-graphics-d.lib;sfml-audio-d.lib;sfml-network-d.lib;sfml-system-d.lib;sfml-window-d.lib;%(AdditionalDependencies)</AdditionalDependencies>
<SubSystem>Console</SubSystem>
<ImageHasSafeExceptionHandlers>false</ImageHasSafeExceptionHandlers>
<AdditionalOptions> /machine:X86 /debug %(AdditionalOptions)</AdditionalOptions>
<ImportLibrary>$(SolutionDir)bin/x86/Debug/HelloWorld.lib</ImportLibrary>
</Link>
<PostBuildEvent>
<Command>copy conway_compute.cl "$(OutDir)conway_kernel.cl" /Y
copy conway_align.cl "$(OutDir)conway_kernel.cl" /Y</Command>
</PostBuildEvent>
</ItemDefinitionGroup>
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
<ClCompile>
<WarningLevel>Level3</WarningLevel>
<Optimization>Disabled</Optimization>
<AdditionalIncludeDirectories>../../../../include;../../../../include/SDKUtil;$(AMDAPPSDKROOT)/include;Z:\Cpp_Libs\SFML-Visual_Studio2015RCx64\include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
<InlineFunctionExpansion>Disabled</InlineFunctionExpansion>
<PreprocessorDefinitions>WIN32;_WINDOWS;_DEBUG;_CRT_SECURE_NO_WARNINGS;CMAKE_INTDIR="Debug";%(PreprocessorDefinitions)</PreprocessorDefinitions>
<RuntimeTypeInfo>true</RuntimeTypeInfo>
<ProgramDataBaseFileName>$(SolutionDir)bin/x86_64/Debug/HelloWorld.pdb</ProgramDataBaseFileName>
<AssemblerListingLocation>Debug</AssemblerListingLocation>
<CompileAs>CompileAsCpp</CompileAs>
<DisableSpecificWarnings>4005;4996</DisableSpecificWarnings>
</ClCompile>
<Link>
<GenerateDebugInformation>true</GenerateDebugInformation>
<AdditionalLibraryDirectories>..\..\..\..\lib\win64\;$(AMDAPPSDKROOT)\lib\x86_64\;%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
<AdditionalDependencies>kernel32.lib;user32.lib;gdi32.lib;winspool.lib;shell32.lib;ole32.lib;oleaut32.lib;uuid.lib;comdlg32.lib;advapi32.lib;OpenCL.lib;opengl32.lib;glfw3.lib;glew32.lib;sfml-graphics-d.lib;sfml-audio-d.lib;sfml-network-d.lib;sfml-system-d.lib;sfml-window-d.lib;%(AdditionalDependencies)</AdditionalDependencies>
<SubSystem>Console</SubSystem>
<ImportLibrary>$(SolutionDir)bin/x86_64/Debug/HelloWorld.lib</ImportLibrary>
<ImageHasSafeExceptionHandlers>false</ImageHasSafeExceptionHandlers>
<AdditionalOptions> /machine:x64 /debug %(AdditionalOptions)</AdditionalOptions>
</Link>
<PostBuildEvent>
<Command>copy conway_compute.cl "$(OutDir)conway_kernel.cl" /Y
copy conway_align.cl "$(OutDir)conway_kernel.cl" /Y</Command>
</PostBuildEvent>
</ItemDefinitionGroup>
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
<ClCompile>
<WarningLevel>Level3</WarningLevel>
<Optimization>MaxSpeed</Optimization>
<FunctionLevelLinking>
</FunctionLevelLinking>
<IntrinsicFunctions>false</IntrinsicFunctions>
<AdditionalIncludeDirectories>../../../../include;../../../../include/SDKUtil;$(AMDAPPSDKROOT)/include;Z:\Cpp_Libs\SFML-Visual_Studio2015RCx32\include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
<DebugInformationFormat />
<InlineFunctionExpansion>AnySuitable</InlineFunctionExpansion>
<PreprocessorDefinitions>WIN32;_WINDOWS;NDEBUG;_CRT_SECURE_NO_WARNINGS;CMAKE_INTDIR="Release";%(PreprocessorDefinitions)</PreprocessorDefinitions>
<RuntimeTypeInfo>true</RuntimeTypeInfo>
<ProgramDataBaseFileName>$(SolutionDir)bin/x86/Release/HelloWorld.pdb</ProgramDataBaseFileName>
<CompileAs>CompileAsCpp</CompileAs>
<DisableSpecificWarnings>4005;4996</DisableSpecificWarnings>
<AssemblerListingLocation>Release</AssemblerListingLocation>
</ClCompile>
<Link>
<GenerateDebugInformation>false</GenerateDebugInformation>
<EnableCOMDATFolding>
</EnableCOMDATFolding>
<OptimizeReferences>
</OptimizeReferences>
<AdditionalDependencies>kernel32.lib;user32.lib;gdi32.lib;winspool.lib;shell32.lib;ole32.lib;oleaut32.lib;uuid.lib;comdlg32.lib;advapi32.lib;OpenCL.lib;opengl32.lib;glew32.lib;glfw3.lib;sfml-graphics.lib;sfml-audio.lib;sfml-network.lib;sfml-system.lib;sfml-window.lib;%(AdditionalDependencies)</AdditionalDependencies>
<AdditionalLibraryDirectories>..\..\..\..\lib\win32\;$(AMDAPPSDKROOT)\lib\x86\;%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
<SubSystem>Console</SubSystem>
<ImportLibrary>$(SolutionDir)bin/x86/Release/HelloWorld.lib</ImportLibrary>
<ImageHasSafeExceptionHandlers>false</ImageHasSafeExceptionHandlers>
<AdditionalOptions> /machine:X86 %(AdditionalOptions)</AdditionalOptions>
</Link>
<ProjectReference>
<LinkLibraryDependencies>false</LinkLibraryDependencies>
</ProjectReference>
<PostBuildEvent>
<Command>copy conway_compute.cl "$(OutDir)conway_kernel.cl" /Y
copy conway_align.cl "$(OutDir)conway_kernel.cl" /Y</Command>
</PostBuildEvent>
</ItemDefinitionGroup>
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
<ClCompile>
<WarningLevel>Level3</WarningLevel>
<Optimization>MaxSpeed</Optimization>
<FunctionLevelLinking>
</FunctionLevelLinking>
<IntrinsicFunctions>false</IntrinsicFunctions>
<AdditionalIncludeDirectories>../../../../include;../../../../include/SDKUtil;$(AMDAPPSDKROOT)/include;Z:\Cpp_Libs\SFML-Visual_Studio2015RCx64\include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
<InlineFunctionExpansion>AnySuitable</InlineFunctionExpansion>
<DebugInformationFormat />
<PreprocessorDefinitions>WIN32;_WINDOWS;NDEBUG;_CRT_SECURE_NO_WARNINGS;CMAKE_INTDIR="Release";%(PreprocessorDefinitions)</PreprocessorDefinitions>
<RuntimeTypeInfo>true</RuntimeTypeInfo>
<AssemblerListingLocation>Release</AssemblerListingLocation>
<CompileAs>CompileAsCpp</CompileAs>
<DisableSpecificWarnings>4005;4996</DisableSpecificWarnings>
<ProgramDataBaseFileName>$(SolutionDir)bin/x86_64/Release/HelloWorld.pdb</ProgramDataBaseFileName>
<WholeProgramOptimization>false</WholeProgramOptimization>
</ClCompile>
<Link>
<GenerateDebugInformation>false</GenerateDebugInformation>
<EnableCOMDATFolding>
</EnableCOMDATFolding>
<OptimizeReferences>
</OptimizeReferences>
<AdditionalLibraryDirectories>..\..\..\..\lib\win64\;$(AMDAPPSDKROOT)\lib\x86_64\;%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
<AdditionalDependencies>kernel32.lib;user32.lib;gdi32.lib;winspool.lib;shell32.lib;ole32.lib;oleaut32.lib;uuid.lib;comdlg32.lib;advapi32.lib;OpenCL.lib;opengl32.lib;glfw3.lib;glew32.lib;sfml-graphics.lib;sfml-audio.lib;sfml-network.lib;sfml-system.lib;sfml-window.lib;%(AdditionalDependencies)</AdditionalDependencies>
<SubSystem>Console</SubSystem>
<LinkTimeCodeGeneration />
<ImportLibrary>$(SolutionDir)bin/x86_64/Release/HelloWorld.lib</ImportLibrary>
<ImageHasSafeExceptionHandlers>false</ImageHasSafeExceptionHandlers>
<AdditionalOptions> /machine:x64 %(AdditionalOptions)</AdditionalOptions>
</Link>
<PostBuildEvent>
<Command>copy conway_compute.cl "$(OutDir)conway_kernel.cl" /Y
copy conway_align.cl "$(OutDir)conway_kernel.cl" /Y</Command>
</PostBuildEvent>
</ItemDefinitionGroup>
<ItemGroup>
<ClCompile Include="Conway.hpp" />
</ItemGroup>
<ItemGroup>
<None Include="conway_compute.cl" />
<None Include="conway_align.cl" />
<None Include="fragment_shader.sh" />
<None Include="vertex_shader.sh" />
</ItemGroup>
<ItemGroup>
<ClInclude Include="Shader.hpp" />
</ItemGroup>
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
<ImportGroup Label="ExtensionTargets">
</ImportGroup>
</Project>

@ -0,0 +1,369 @@
# This script locates the SFML library
# ------------------------------------
#
# Usage
# -----
#
# When you try to locate the SFML libraries, you must specify which modules you want to use (system, window, graphics, network, audio, main).
# If none is given, the SFML_LIBRARIES variable will be empty and you'll end up linking to nothing.
# example:
# find_package(SFML COMPONENTS graphics window system) # find the graphics, window and system modules
#
# You can enforce a specific version, either MAJOR.MINOR or only MAJOR.
# If nothing is specified, the version won't be checked (i.e. any version will be accepted).
# example:
# find_package(SFML COMPONENTS ...) # no specific version required
# find_package(SFML 2 COMPONENTS ...) # any 2.x version
# find_package(SFML 2.4 COMPONENTS ...) # version 2.4 or greater
#
# By default, the dynamic libraries of SFML will be found. To find the static ones instead,
# you must set the SFML_STATIC_LIBRARIES variable to TRUE before calling find_package(SFML ...).
# Since you have to link yourself all the SFML dependencies when you link it statically, the following
# additional variables are defined: SFML_XXX_DEPENDENCIES and SFML_DEPENDENCIES (see their detailed
# description below).
# In case of static linking, the SFML_STATIC macro will also be defined by this script.
# example:
# set(SFML_STATIC_LIBRARIES TRUE)
# find_package(SFML 2 COMPONENTS network system)
#
# On Mac OS X if SFML_STATIC_LIBRARIES is not set to TRUE then by default CMake will search for frameworks unless
# CMAKE_FIND_FRAMEWORK is set to "NEVER" for example. Please refer to CMake documentation for more details.
# Moreover, keep in mind that SFML frameworks are only available as release libraries unlike dylibs which
# are available for both release and debug modes.
#
# If SFML is not installed in a standard path, you can use the SFML_ROOT CMake (or environment) variable
# to tell CMake where SFML is.
#
# Output
# ------
#
# This script defines the following variables:
# - For each specified module XXX (system, window, graphics, network, audio, main):
# - SFML_XXX_LIBRARY_DEBUG: the name of the debug library of the xxx module (set to SFML_XXX_LIBRARY_RELEASE is no debug version is found)
# - SFML_XXX_LIBRARY_RELEASE: the name of the release library of the xxx module (set to SFML_XXX_LIBRARY_DEBUG is no release version is found)
# - SFML_XXX_LIBRARY: the name of the library to link to for the xxx module (includes both debug and optimized names if necessary)
# - SFML_XXX_FOUND: true if either the debug or release library of the xxx module is found
# - SFML_XXX_DEPENDENCIES: the list of libraries the module depends on, in case of static linking
# - SFML_LIBRARIES: the list of all libraries corresponding to the required modules
# - SFML_FOUND: true if all the required modules are found
# - SFML_INCLUDE_DIR: the path where SFML headers are located (the directory containing the SFML/Config.hpp file)
# - SFML_DEPENDENCIES: the list of libraries SFML depends on, in case of static linking
#
# example:
# find_package(SFML 2 COMPONENTS system window graphics audio REQUIRED)
# include_directories(${SFML_INCLUDE_DIR})
# add_executable(myapp ...)
# target_link_libraries(myapp ${SFML_LIBRARIES})
# define the SFML_STATIC macro if static build was chosen
if(SFML_STATIC_LIBRARIES)
add_definitions(-DSFML_STATIC)
endif()
# define the list of search paths for headers and libraries
set(FIND_SFML_PATHS
${SFML_ROOT}
$ENV{SFML_ROOT}
~/Library/Frameworks
/Library/Frameworks
/usr/local
/usr
/sw
/opt/local
/opt/csw
/opt)
# find the SFML include directory
find_path(SFML_INCLUDE_DIR SFML/Config.hpp
PATH_SUFFIXES include
PATHS ${FIND_SFML_PATHS})
# check the version number
set(SFML_VERSION_OK TRUE)
if(SFML_FIND_VERSION AND SFML_INCLUDE_DIR)
# extract the major and minor version numbers from SFML/Config.hpp
# we have to handle framework a little bit differently:
if("${SFML_INCLUDE_DIR}" MATCHES "SFML.framework")
set(SFML_CONFIG_HPP_INPUT "${SFML_INCLUDE_DIR}/Headers/Config.hpp")
else()
set(SFML_CONFIG_HPP_INPUT "${SFML_INCLUDE_DIR}/SFML/Config.hpp")
endif()
FILE(READ "${SFML_CONFIG_HPP_INPUT}" SFML_CONFIG_HPP_CONTENTS)
STRING(REGEX REPLACE ".*#define SFML_VERSION_MAJOR ([0-9]+).*" "\\1" SFML_VERSION_MAJOR "${SFML_CONFIG_HPP_CONTENTS}")
STRING(REGEX REPLACE ".*#define SFML_VERSION_MINOR ([0-9]+).*" "\\1" SFML_VERSION_MINOR "${SFML_CONFIG_HPP_CONTENTS}")
STRING(REGEX REPLACE ".*#define SFML_VERSION_PATCH ([0-9]+).*" "\\1" SFML_VERSION_PATCH "${SFML_CONFIG_HPP_CONTENTS}")
if (NOT "${SFML_VERSION_PATCH}" MATCHES "^[0-9]+$")
set(SFML_VERSION_PATCH 0)
endif()
math(EXPR SFML_REQUESTED_VERSION "${SFML_FIND_VERSION_MAJOR} * 10000 + ${SFML_FIND_VERSION_MINOR} * 100 + ${SFML_FIND_VERSION_PATCH}")
# if we could extract them, compare with the requested version number
if (SFML_VERSION_MAJOR)
# transform version numbers to an integer
math(EXPR SFML_VERSION "${SFML_VERSION_MAJOR} * 10000 + ${SFML_VERSION_MINOR} * 100 + ${SFML_VERSION_PATCH}")
# compare them
if(SFML_VERSION LESS SFML_REQUESTED_VERSION)
set(SFML_VERSION_OK FALSE)
endif()
else()
# SFML version is < 2.0
if (SFML_REQUESTED_VERSION GREATER 10900)
set(SFML_VERSION_OK FALSE)
set(SFML_VERSION_MAJOR 1)
set(SFML_VERSION_MINOR x)
set(SFML_VERSION_PATCH x)
endif()
endif()
endif()
# find the requested modules
set(SFML_FOUND TRUE) # will be set to false if one of the required modules is not found
foreach(FIND_SFML_COMPONENT ${SFML_FIND_COMPONENTS})
string(TOLOWER ${FIND_SFML_COMPONENT} FIND_SFML_COMPONENT_LOWER)
string(TOUPPER ${FIND_SFML_COMPONENT} FIND_SFML_COMPONENT_UPPER)
set(FIND_SFML_COMPONENT_NAME sfml-${FIND_SFML_COMPONENT_LOWER})
# no suffix for sfml-main, it is always a static library
if(FIND_SFML_COMPONENT_LOWER STREQUAL "main")
# release library
find_library(SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_RELEASE
NAMES ${FIND_SFML_COMPONENT_NAME}
PATH_SUFFIXES lib64 lib
PATHS ${FIND_SFML_PATHS})
# debug library
find_library(SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_DEBUG
NAMES ${FIND_SFML_COMPONENT_NAME}-d
PATH_SUFFIXES lib64 lib
PATHS ${FIND_SFML_PATHS})
else()
# static release library
find_library(SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_STATIC_RELEASE
NAMES ${FIND_SFML_COMPONENT_NAME}-s
PATH_SUFFIXES lib64 lib
PATHS ${FIND_SFML_PATHS})
# static debug library
find_library(SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_STATIC_DEBUG
NAMES ${FIND_SFML_COMPONENT_NAME}-s-d
PATH_SUFFIXES lib64 lib
PATHS ${FIND_SFML_PATHS})
# dynamic release library
find_library(SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_DYNAMIC_RELEASE
NAMES ${FIND_SFML_COMPONENT_NAME}
PATH_SUFFIXES lib64 lib
PATHS ${FIND_SFML_PATHS})
# dynamic debug library
find_library(SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_DYNAMIC_DEBUG
NAMES ${FIND_SFML_COMPONENT_NAME}-d
PATH_SUFFIXES lib64 lib
PATHS ${FIND_SFML_PATHS})
# choose the entries that fit the requested link type
if(SFML_STATIC_LIBRARIES)
if(SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_STATIC_RELEASE)
set(SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_RELEASE ${SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_STATIC_RELEASE})
endif()
if(SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_STATIC_DEBUG)
set(SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_DEBUG ${SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_STATIC_DEBUG})
endif()
else()
if(SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_DYNAMIC_RELEASE)
set(SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_RELEASE ${SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_DYNAMIC_RELEASE})
endif()
if(SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_DYNAMIC_DEBUG)
set(SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_DEBUG ${SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_DYNAMIC_DEBUG})
endif()
endif()
endif()
if (SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_DEBUG OR SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_RELEASE)
# library found
set(SFML_${FIND_SFML_COMPONENT_UPPER}_FOUND TRUE)
# if both are found, set SFML_XXX_LIBRARY to contain both
if (SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_DEBUG AND SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_RELEASE)
set(SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY debug ${SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_DEBUG}
optimized ${SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_RELEASE})
endif()
# if only one debug/release variant is found, set the other to be equal to the found one
if (SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_DEBUG AND NOT SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_RELEASE)
# debug and not release
set(SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_RELEASE ${SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_DEBUG})
set(SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY ${SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_DEBUG})
endif()
if (SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_RELEASE AND NOT SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_DEBUG)
# release and not debug
set(SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_DEBUG ${SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_RELEASE})
set(SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY ${SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_RELEASE})
endif()
else()
# library not found
set(SFML_FOUND FALSE)
set(SFML_${FIND_SFML_COMPONENT_UPPER}_FOUND FALSE)
set(SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY "")
set(FIND_SFML_MISSING "${FIND_SFML_MISSING} SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY")
endif()
# mark as advanced
MARK_AS_ADVANCED(SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY
SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_RELEASE
SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_DEBUG
SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_STATIC_RELEASE
SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_STATIC_DEBUG
SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_DYNAMIC_RELEASE
SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY_DYNAMIC_DEBUG)
# add to the global list of libraries
set(SFML_LIBRARIES ${SFML_LIBRARIES} "${SFML_${FIND_SFML_COMPONENT_UPPER}_LIBRARY}")
endforeach()
# in case of static linking, we must also define the list of all the dependencies of SFML libraries
if(SFML_STATIC_LIBRARIES)
# detect the OS
if(${CMAKE_SYSTEM_NAME} MATCHES "Windows")
set(FIND_SFML_OS_WINDOWS 1)
elseif(${CMAKE_SYSTEM_NAME} MATCHES "Linux")
set(FIND_SFML_OS_LINUX 1)
elseif(${CMAKE_SYSTEM_NAME} MATCHES "FreeBSD")
set(FIND_SFML_OS_FREEBSD 1)
elseif(${CMAKE_SYSTEM_NAME} MATCHES "Darwin")
set(FIND_SFML_OS_MACOSX 1)
endif()
# start with an empty list
set(SFML_DEPENDENCIES)
set(FIND_SFML_DEPENDENCIES_NOTFOUND)
# macro that searches for a 3rd-party library
macro(find_sfml_dependency output friendlyname)
# No lookup in environment variables (PATH on Windows), as they may contain wrong library versions
find_library(${output} NAMES ${ARGN} PATHS ${FIND_SFML_PATHS} PATH_SUFFIXES lib NO_SYSTEM_ENVIRONMENT_PATH)
if(${${output}} STREQUAL "${output}-NOTFOUND")
unset(output)
set(FIND_SFML_DEPENDENCIES_NOTFOUND "${FIND_SFML_DEPENDENCIES_NOTFOUND} ${friendlyname}")
endif()
endmacro()
# sfml-system
list(FIND SFML_FIND_COMPONENTS "system" FIND_SFML_SYSTEM_COMPONENT)
if(NOT ${FIND_SFML_SYSTEM_COMPONENT} EQUAL -1)
# update the list -- these are only system libraries, no need to find them
if(FIND_SFML_OS_LINUX OR FIND_SFML_OS_FREEBSD OR FIND_SFML_OS_MACOSX)
set(SFML_SYSTEM_DEPENDENCIES "pthread")
endif()
if(FIND_SFML_OS_LINUX)
set(SFML_SYSTEM_DEPENDENCIES ${SFML_SYSTEM_DEPENDENCIES} "rt")
endif()
if(FIND_SFML_OS_WINDOWS)
set(SFML_SYSTEM_DEPENDENCIES "winmm")
endif()
set(SFML_DEPENDENCIES ${SFML_SYSTEM_DEPENDENCIES} ${SFML_DEPENDENCIES})
endif()
# sfml-network
list(FIND SFML_FIND_COMPONENTS "network" FIND_SFML_NETWORK_COMPONENT)
if(NOT ${FIND_SFML_NETWORK_COMPONENT} EQUAL -1)
# update the list -- these are only system libraries, no need to find them
if(FIND_SFML_OS_WINDOWS)
set(SFML_NETWORK_DEPENDENCIES "ws2_32")
endif()
set(SFML_DEPENDENCIES ${SFML_NETWORK_DEPENDENCIES} ${SFML_DEPENDENCIES})
endif()
# sfml-window
list(FIND SFML_FIND_COMPONENTS "window" FIND_SFML_WINDOW_COMPONENT)
if(NOT ${FIND_SFML_WINDOW_COMPONENT} EQUAL -1)
# find libraries
if(FIND_SFML_OS_LINUX OR FIND_SFML_OS_FREEBSD)
find_sfml_dependency(X11_LIBRARY "X11" X11)
find_sfml_dependency(LIBXCB_LIBRARIES "XCB" xcb libxcb)
find_sfml_dependency(X11_XCB_LIBRARY "X11-xcb" X11-xcb libX11-xcb)
find_sfml_dependency(XCB_RANDR_LIBRARY "xcb-randr" xcb-randr libxcb-randr)
find_sfml_dependency(XCB_IMAGE_LIBRARY "xcb-image" xcb-image libxcb-image)
endif()
if(FIND_SFML_OS_LINUX)
find_sfml_dependency(UDEV_LIBRARIES "UDev" udev libudev)
endif()
# update the list
if(FIND_SFML_OS_WINDOWS)
set(SFML_WINDOW_DEPENDENCIES ${SFML_WINDOW_DEPENDENCIES} "opengl32" "winmm" "gdi32")
elseif(FIND_SFML_OS_LINUX)
set(SFML_WINDOW_DEPENDENCIES ${SFML_WINDOW_DEPENDENCIES} "GL" ${X11_LIBRARY} ${LIBXCB_LIBRARIES} ${X11_XCB_LIBRARY} ${XCB_RANDR_LIBRARY} ${XCB_IMAGE_LIBRARY} ${UDEV_LIBRARIES})
elseif(FIND_SFML_OS_FREEBSD)
set(SFML_WINDOW_DEPENDENCIES ${SFML_WINDOW_DEPENDENCIES} "GL" ${X11_LIBRARY} ${LIBXCB_LIBRARIES} ${X11_XCB_LIBRARY} ${XCB_RANDR_LIBRARY} ${XCB_IMAGE_LIBRARY} "usbhid")
elseif(FIND_SFML_OS_MACOSX)
set(SFML_WINDOW_DEPENDENCIES ${SFML_WINDOW_DEPENDENCIES} "-framework OpenGL -framework Foundation -framework AppKit -framework IOKit -framework Carbon")
endif()
set(SFML_DEPENDENCIES ${SFML_WINDOW_DEPENDENCIES} ${SFML_DEPENDENCIES})
endif()
# sfml-graphics
list(FIND SFML_FIND_COMPONENTS "graphics" FIND_SFML_GRAPHICS_COMPONENT)
if(NOT ${FIND_SFML_GRAPHICS_COMPONENT} EQUAL -1)
# find libraries
find_sfml_dependency(FREETYPE_LIBRARY "FreeType" freetype)
find_sfml_dependency(JPEG_LIBRARY "libjpeg" jpeg)
# update the list
set(SFML_GRAPHICS_DEPENDENCIES ${FREETYPE_LIBRARY} ${JPEG_LIBRARY})
set(SFML_DEPENDENCIES ${SFML_GRAPHICS_DEPENDENCIES} ${SFML_DEPENDENCIES})
endif()
# sfml-audio
list(FIND SFML_FIND_COMPONENTS "audio" FIND_SFML_AUDIO_COMPONENT)
if(NOT ${FIND_SFML_AUDIO_COMPONENT} EQUAL -1)
# find libraries
find_sfml_dependency(OPENAL_LIBRARY "OpenAL" openal openal32)
find_sfml_dependency(OGG_LIBRARY "Ogg" ogg)
find_sfml_dependency(VORBIS_LIBRARY "Vorbis" vorbis)
find_sfml_dependency(VORBISFILE_LIBRARY "VorbisFile" vorbisfile)
find_sfml_dependency(VORBISENC_LIBRARY "VorbisEnc" vorbisenc)
find_sfml_dependency(FLAC_LIBRARY "FLAC" FLAC)
# update the list
set(SFML_AUDIO_DEPENDENCIES ${OPENAL_LIBRARY} ${FLAC_LIBRARY} ${VORBISENC_LIBRARY} ${VORBISFILE_LIBRARY} ${VORBIS_LIBRARY} ${OGG_LIBRARY})
set(SFML_DEPENDENCIES ${SFML_DEPENDENCIES} ${SFML_AUDIO_DEPENDENCIES})
endif()
endif()
# handle errors
if(NOT SFML_VERSION_OK)
# SFML version not ok
set(FIND_SFML_ERROR "SFML found but version too low (requested: ${SFML_FIND_VERSION}, found: ${SFML_VERSION_MAJOR}.${SFML_VERSION_MINOR}.${SFML_VERSION_PATCH})")
set(SFML_FOUND FALSE)
elseif(SFML_STATIC_LIBRARIES AND FIND_SFML_DEPENDENCIES_NOTFOUND)
set(FIND_SFML_ERROR "SFML found but some of its dependencies are missing (${FIND_SFML_DEPENDENCIES_NOTFOUND})")
set(SFML_FOUND FALSE)
elseif(NOT SFML_FOUND)
# include directory or library not found
set(FIND_SFML_ERROR "Could NOT find SFML (missing: ${FIND_SFML_MISSING})")
endif()
if (NOT SFML_FOUND)
if(SFML_FIND_REQUIRED)
# fatal error
message(FATAL_ERROR ${FIND_SFML_ERROR})
elseif(NOT SFML_FIND_QUIETLY)
# error but continue
message("${FIND_SFML_ERROR}")
endif()
endif()
# handle success
if(SFML_FOUND AND NOT SFML_FIND_QUIETLY)
message(STATUS "Found SFML ${SFML_VERSION_MAJOR}.${SFML_VERSION_MINOR}.${SFML_VERSION_PATCH} in ${SFML_INCLUDE_DIR}")
endif()

@ -0,0 +1,4 @@
##About
A simple rework of the CPU based Conway's game of life simulation on the GPU

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

After

Width:  |  Height:  |  Size: 322 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 21 KiB

@ -0,0 +1,149 @@
#pragma once
#include <string>
#include <SFML/Graphics.hpp>
#include <unordered_map>
#include <iostream>
#include "Vector4.hpp"
#include <string.h>
#include <memory>
#ifdef linux
#include <CL/cl.h>
#include <CL/opencl.h>
#include <GL/glx.h>
#elif defined _WIN32
#define CL_USE_DEPRECATED_OPENCL_1_2_APIS
#include <CL/cl_gl.h>
#include <CL/cl.h>
#include <CL/opencl.h>
// Note: windows.h must be included before Gl/GL.h
#include <windows.h>
#include <GL/GL.h>
#elif defined TARGET_OS_MAC
#include <OpenCL/opencl.h>
#endif
class OpenCL {
public:
OpenCL();
~OpenCL();
// command queues are associated with a device and context, so for multi-gpu applications you would need
// multiple command queues
// CONTEXTS
// - An OpenCL context is created with one or more devices. Contexts are used by the OpenCL runtime
// for managing objects such as command - queues, memory, program and kernel objects and for executing
// kernels on one or more devices specified in the context.
// - Contexts cannot be created using more than one platform!
bool init();
bool compile_kernel(std::string kernel_path, std::string kernel_name);
// Create an image buffer from an SF texture. Access Type is the read/write specifier required by OpenCL
bool create_image_buffer_from_texture(std::string buffer_name, sf::Texture* texture, cl_int access_type);
// Have CL create and manage the texture for the image buffer. Access Type is the read/write specifier required by OpenCL
bool create_image_buffer(std::string buffer_name, sf::Vector2i size, sf::Vector2f position, cl_int access_type);
// Create a buffer with CL_MEM_READ_ONLY and CL_MEM_COPY_HOST_PTR
int create_buffer(std::string buffer_name, cl_uint size, void* data);
// Create a buffer with user defined data access flags
int create_buffer(std::string buffer_name, cl_uint size, void* data, cl_mem_flags flags);
int set_kernel_arg(std::string kernel_name, int index, std::string buffer_name);
void run_kernel(std::string kernel_name, sf::Vector2i work_size);
void draw(sf::RenderWindow *window);
class device {
public:
#pragma pack(push, 1)
struct packed_data {
cl_device_type device_type;
cl_uint clock_frequency;
char opencl_version[64];
cl_uint compute_units;
char device_extensions[1024];
char device_name[256];
char platform_name[128];
};
#pragma pack(pop)
device(cl_device_id device_id, cl_platform_id platform_id);
device(const device& d);
void print(std::ostream& stream) const;
void print_packed_data(std::ostream& stream);
cl_device_id getDeviceId() const { return device_id; };
cl_platform_id getPlatformId() const { return platform_id; };
private:
packed_data data;
cl_device_id device_id;
cl_platform_id platform_id;
cl_bool is_little_endian = false;
bool cl_gl_sharing = false;
};
private:
int error = 0;
// The device which we have selected according to certain criteria
cl_platform_id platform_id;
cl_device_id device_id;
// The GL shared context and its subsiquently generated command queue
cl_context context;
cl_command_queue command_queue;
// Maps which contain a mapping from "name" to the host side CL memory object
std::unordered_map<std::string, cl_kernel> kernel_map;
std::unordered_map<std::string, cl_mem> buffer_map;
std::unordered_map<std::string, std::pair<sf::Sprite, std::unique_ptr<sf::Texture>>> image_map;
std::vector<device> device_list;
// Query the hardware on this machine and store the devices
bool aquire_hardware();
// After aquiring hardware, create a shared context using platform specific CL commands
bool create_shared_context();
// Command queues must be created with a valid context
bool create_command_queue();
// Store a cl_mem object in the buffer map <string:name, cl_mem:buffer>
bool store_buffer(cl_mem buffer, std::string buffer_name);
// Using CL release the memory object and remove the KVP associated with the buffer name
bool release_buffer(std::string buffer_name);
bool load_config();
void save_config();
static bool vr_assert(int error_code, std::string function_name);
};

@ -0,0 +1,479 @@
////////////////////////////////////////////////////////////
//
// This is a small addition to the SFML sf::Vector templates which
// adds a sf::Vector4(f, i, u)
//
////////////////////////////////////////////////////////////
//
// SFML - Simple and Fast Multimedia Library
// Copyright (C) 2007-2016 Laurent Gomila (laurent@sfml-dev.org)
//
// This software is provided 'as-is', without any express or implied warranty.
// In no event will the authors be held liable for any damages arising from the use of this software.
//
// Permission is granted to anyone to use this software for any purpose,
// including commercial applications, and to alter it and redistribute it freely,
// subject to the following restrictions:
//
// 1. The origin of this software must not be misrepresented;
// you must not claim that you wrote the original software.
// If you use this software in a product, an acknowledgment
// in the product documentation would be appreciated but is not required.
//
// 2. Altered source versions must be plainly marked as such,
// and must not be misrepresented as being the original software.
//
// 3. This notice may not be removed or altered from any source distribution.
//
////////////////////////////////////////////////////////////
#ifndef SFML_VECTOR4_H
#define SFML_VECTOR4_H
namespace sf {
////////////////////////////////////////////////////////////
/// \brief Utility template class for manipulating
/// 2-dimensional vectors
///
////////////////////////////////////////////////////////////
template <typename T>
class Vector4 {
public:
////////////////////////////////////////////////////////////
/// \brief Default constructor
///
/// Creates a Vector4(0, 0).
///
////////////////////////////////////////////////////////////
Vector4();
////////////////////////////////////////////////////////////
/// \brief Construct the vector from its coordinates
///
/// \param X X coordinate
/// \param Y Y coordinate
///
////////////////////////////////////////////////////////////
Vector4(T X, T Y, T Z, T W);
////////////////////////////////////////////////////////////
/// \brief Construct the vector from another type of vector
///
/// This constructor doesn't replace the copy constructor,
/// it's called only when U != T.
/// A call to this constructor will fail to compile if U
/// is not convertible to T.
///
/// \param vector Vector to convert
///
////////////////////////////////////////////////////////////
template <typename U>
explicit Vector4(const Vector4<U>& vector);
////////////////////////////////////////////////////////////
// Member data
////////////////////////////////////////////////////////////
T x; ///< X coordinate of the vector
T y; ///< Y coordinate of the vector
T z; ///< Z coordinate of the vector
T w; ///< W coordinate of the vector
};
////////////////////////////////////////////////////////////
/// \relates Vector4
/// \brief Overload of unary operator -
///
/// \param right Vector to negate
///
/// \return Memberwise opposite of the vector
///
////////////////////////////////////////////////////////////
template <typename T>
Vector4<T> operator -(const Vector4<T>& right);
////////////////////////////////////////////////////////////
/// \relates Vector4
/// \brief Overload of binary operator +=
///
/// This operator performs a memberwise addition of both vectors,
/// and assigns the result to \a left.
///
/// \param left Left operand (a vector)
/// \param right Right operand (a vector)
///
/// \return Reference to \a left
///
////////////////////////////////////////////////////////////
template <typename T>
Vector4<T>& operator +=(Vector4<T>& left, const Vector4<T>& right);
////////////////////////////////////////////////////////////
/// \relates Vector4
/// \brief Overload of binary operator -=
///
/// This operator performs a memberwise subtraction of both vectors,
/// and assigns the result to \a left.
///
/// \param left Left operand (a vector)
/// \param right Right operand (a vector)
///
/// \return Reference to \a left
///
////////////////////////////////////////////////////////////
template <typename T>
Vector4<T>& operator -=(Vector4<T>& left, const Vector4<T>& right);
////////////////////////////////////////////////////////////
/// \relates Vector4
/// \brief Overload of binary operator +
///
/// \param left Left operand (a vector)
/// \param right Right operand (a vector)
///
/// \return Memberwise addition of both vectors
///
////////////////////////////////////////////////////////////
template <typename T>
Vector4<T> operator +(const Vector4<T>& left, const Vector4<T>& right);
////////////////////////////////////////////////////////////
/// \relates Vector4
/// \brief Overload of binary operator -
///
/// \param left Left operand (a vector)
/// \param right Right operand (a vector)
///
/// \return Memberwise subtraction of both vectors
///
////////////////////////////////////////////////////////////
template <typename T>
Vector4<T> operator -(const Vector4<T>& left, const Vector4<T>& right);
////////////////////////////////////////////////////////////
/// \relates Vector4
/// \brief Overload of binary operator *
///
/// \param left Left operand (a vector)
/// \param right Right operand (a scalar value)
///
/// \return Memberwise multiplication by \a right
///
////////////////////////////////////////////////////////////
template <typename T>
Vector4<T> operator *(const Vector4<T>& left, T right);
////////////////////////////////////////////////////////////
/// \relates Vector4
/// \brief Overload of binary operator *
///
/// \param left Left operand (a scalar value)
/// \param right Right operand (a vector)
///
/// \return Memberwise multiplication by \a left
///
////////////////////////////////////////////////////////////
template <typename T>
Vector4<T> operator *(T left, const Vector4<T>& right);
////////////////////////////////////////////////////////////
/// \relates Vector4
/// \brief Overload of binary operator *=
///
/// This operator performs a memberwise multiplication by \a right,
/// and assigns the result to \a left.
///
/// \param left Left operand (a vector)
/// \param right Right operand (a scalar value)
///
/// \return Reference to \a left
///
////////////////////////////////////////////////////////////
template <typename T>
Vector4<T>& operator *=(Vector4<T>& left, T right);
////////////////////////////////////////////////////////////
/// \relates Vector4
/// \brief Overload of binary operator /
///
/// \param left Left operand (a vector)
/// \param right Right operand (a scalar value)
///
/// \return Memberwise division by \a right
///
////////////////////////////////////////////////////////////
template <typename T>
Vector4<T> operator /(const Vector4<T>& left, T right);
////////////////////////////////////////////////////////////
/// \relates Vector4
/// \brief Overload of binary operator /=
///
/// This operator performs a memberwise division by \a right,
/// and assigns the result to \a left.
///
/// \param left Left operand (a vector)
/// \param right Right operand (a scalar value)
///
/// \return Reference to \a left
///
////////////////////////////////////////////////////////////
template <typename T>
Vector4<T>& operator /=(Vector4<T>& left, T right);
////////////////////////////////////////////////////////////
/// \relates Vector4
/// \brief Overload of binary operator ==
///
/// This operator compares strict equality between two vectors.
///
/// \param left Left operand (a vector)
/// \param right Right operand (a vector)
///
/// \return True if \a left is equal to \a right
///
////////////////////////////////////////////////////////////
template <typename T>
bool operator ==(const Vector4<T>& left, const Vector4<T>& right);
////////////////////////////////////////////////////////////
/// \relates Vector4
/// \brief Overload of binary operator !=
///
/// This operator compares strict difference between two vectors.
///
/// \param left Left operand (a vector)
/// \param right Right operand (a vector)
///
/// \return True if \a left is not equal to \a right
///
////////////////////////////////////////////////////////////
template <typename T>
bool operator !=(const Vector4<T>& left, const Vector4<T>& right);
////////////////////////////////////////////////////////////
template <typename T>
inline Vector4<T>::Vector4() :
x(0),
y(0),
z(0),
w(0){
}
////////////////////////////////////////////////////////////
template <typename T>
inline Vector4<T>::Vector4(T X, T Y, T Z, T W) :
x(X),
y(Y),
z(Z),
w(W) {
}
////////////////////////////////////////////////////////////
template <typename T>
template <typename U>
inline Vector4<T>::Vector4(const Vector4<U>& vector) :
x(static_cast<T>(vector.x)),
y(static_cast<T>(vector.y)),
z(static_cast<T>(vector.z)),
w(static_cast<T>(vector.w)) {
}
////////////////////////////////////////////////////////////
template <typename T>
inline Vector4<T> operator -(const Vector4<T>& right) {
return Vector4<T>(
-right.x,
-right.y,
-right.z,
-right.w
);
}
////////////////////////////////////////////////////////////
template <typename T>
inline Vector4<T>& operator +=(Vector4<T>& left, const Vector4<T>& right) {
left.x += right.x;
left.y += right.y;
left.z += right.z;
left.w += right.w;
return left;
}
////////////////////////////////////////////////////////////
template <typename T>
inline Vector4<T>& operator -=(Vector4<T>& left, const Vector4<T>& right) {
left.x -= right.x;
left.y -= right.y;
left.z -= right.z;
left.w -= right.w;
return left;
}
////////////////////////////////////////////////////////////
template <typename T>
inline Vector4<T> operator +(const Vector4<T>& left, const Vector4<T>& right) {
return Vector4<T>(
left.x + right.x,
left.y + right.y,
left.z + right.z,
left.w + right.w
);
}
////////////////////////////////////////////////////////////
template <typename T>
inline Vector4<T> operator -(const Vector4<T>& left, const Vector4<T>& right) {
return Vector4<T>(
left.x - right.x,
left.y - right.y,
left.z - right.z,
left.w - right.w
);
}
////////////////////////////////////////////////////////////
template <typename T>
inline Vector4<T> operator *(const Vector4<T>& left, T right) {
return Vector4<T>(
left.x * right,
left.y * right,
left.z * right,
left.w * right
);
}
////////////////////////////////////////////////////////////
template <typename T>
inline Vector4<T> operator *(T left, const Vector4<T>& right) {
return Vector4<T>(
right.x * left,
right.y * left,
right.z * left,
right.w * left
);
}
////////////////////////////////////////////////////////////
template <typename T>
inline Vector4<T>& operator *=(Vector4<T>& left, T right) {
left.x *= right;
left.y *= right;
left.z *= right;
left.w *= right;
return left;
}
////////////////////////////////////////////////////////////
template <typename T>
inline Vector4<T> operator /(const Vector4<T>& left, T right) {
return Vector4<T>(
left.x / right,
left.y / right,
left.z / right,
left.w / right
);
}
////////////////////////////////////////////////////////////
template <typename T>
inline Vector4<T>& operator /=(Vector4<T>& left, T right) {
left.x /= right;
left.y /= right;
left.z /= right;
left.w /= right;
return left;
}
////////////////////////////////////////////////////////////
template <typename T>
inline bool operator ==(const Vector4<T>& left, const Vector4<T>& right) {
return
(left.x == right.x) &&
(left.y == right.y) &&
(left.z == right.z) &&
(left.w == right.w);;
}
////////////////////////////////////////////////////////////
template <typename T>
inline bool operator !=(const Vector4<T>& left, const Vector4<T>& right) {
return
(left.x != right.x) ||
(left.y != right.y) ||
(left.z != right.z) ||
(left.w != right.w);
}
// Define the most common types
typedef Vector4<int> Vector4i;
typedef Vector4<unsigned int> Vector4u;
typedef Vector4<float> Vector4f;
} // namespace sf
#endif // SFML_Vector4_HPP
////////////////////////////////////////////////////////////
/// \class sf::Vector4
/// \ingroup system
///
/// sf::Vector4 is a simple class that defines a mathematical
/// vector with two coordinates (x and y). It can be used to
/// represent anything that has two dimensions: a size, a point,
/// a velocity, etc.
///
/// The template parameter T is the type of the coordinates. It
/// can be any type that supports arithmetic operations (+, -, /, *)
/// and comparisons (==, !=), for example int or float.
///
/// You generally don't have to care about the templated form (sf::Vector4<T>),
/// the most common specializations have special typedefs:
/// \li sf::Vector4<float> is sf::Vector4f
/// \li sf::Vector4<int> is sf::Vector4i
/// \li sf::Vector4<unsigned int> is sf::Vector4u
///
/// The sf::Vector4 class has a small and simple interface, its x and y members
/// can be accessed directly (there are no accessors like setX(), getX()) and it
/// contains no mathematical function like dot product, cross product, length, etc.
///
/// Usage example:
/// \code
/// sf::Vector4f v1(16.5f, 24.f);
/// v1.x = 18.2f;
/// float y = v1.y;
///
/// sf::Vector4f v2 = v1 * 5.f;
/// sf::Vector4
/// v3 = v1 + v2;
///
/// bool different = (v2 != v3);
/// \endcode
///
/// Note: for 3-dimensional vectors, see sf::Vector3.
///
////////////////////////////////////////////////////////////

@ -0,0 +1,159 @@
#pragma once
#include <SFML/Graphics.hpp>
#include <SFML/Graphics/VertexArray.hpp>
#include "Vector4.hpp"
#include <math.h>
#include <bitset>
#include <iostream>
#include <fstream>
#include <sstream>
#include <string>
#include <iterator>
#include <list>
#include <algorithm>
const double PI = 3.141592653589793238463;
const float PI_F = 3.14159265358979f;
inline sf::Vector3f SphereToCart(sf::Vector2f i) {
auto r = sf::Vector3f(
(1 * sin(i.y) * cos(i.x)),
(1 * sin(i.y) * sin(i.x)),
(1 * cos(i.y))
);
return r;
};
inline sf::Vector3f SphereToCart(sf::Vector3f i) {
auto r = sf::Vector3f(
(i.x * sin(i.z) * cos(i.y)),
(i.x * sin(i.z) * sin(i.y)),
(i.x * cos(i.z))
);
return r;
};
inline sf::Vector3f CartToSphere(sf::Vector3f in) {
auto r = sf::Vector3f(
sqrt(in.x * in.x + in.y * in.y + in.z * in.z),
atan(in.y / in.x),
atan(sqrt(in.x * in.x + in.y * in.y) / in.z)
);
return r;
};
inline sf::Vector2f CartToNormalizedSphere(sf::Vector3f in) {
auto r = sf::Vector2f(
atan2(sqrt(in.x * in.x + in.y * in.y), in.z),
atan2(in.y, in.x)
);
return r;
}
inline sf::Vector3f FixOrigin(sf::Vector3f base, sf::Vector3f head) {
return head - base;
}
inline sf::Vector3f Normalize(sf::Vector3f in) {
float multiplier = sqrt(in.x * in.x + in.y * in.y + in.z * in.z);
auto r = sf::Vector3f(
in.x / multiplier,
in.y / multiplier,
in.z / multiplier
);
return r;
}
inline float DotProduct(sf::Vector3f a, sf::Vector3f b){
return a.x * b.x + a.y * b.y + a.z * b.z;
}
inline float Magnitude(sf::Vector3f in){
return sqrt(in.x * in.x + in.y * in.y + in.z * in.z);
}
inline float AngleBetweenVectors(sf::Vector3f a, sf::Vector3f b){
return acos(DotProduct(a, b) / (Magnitude(a) * Magnitude(b)));
}
inline float DistanceBetweenPoints(sf::Vector3f a, sf::Vector3f b) {
return sqrt(DotProduct(a, b));
}
inline float DegreesToRadians(float in) {
return static_cast<float>(in * PI / 180.0f);
}
inline float RadiansToDegrees(float in) {
return static_cast<float>(in * 180.0f / PI);
}
inline std::string read_file(std::string file_name){
std::ifstream input_file(file_name);
if (!input_file.is_open()){
std::cout << file_name << " could not be opened" << std::endl;
return "";
}
std::stringstream buf;
buf << input_file.rdbuf();
input_file.close();
return buf.str();
}
inline void PrettyPrintUINT64(uint64_t i, std::stringstream* ss) {
*ss << "[" << std::bitset<15>(i) << "]";
*ss << "[" << std::bitset<1>(i >> 15) << "]";
*ss << "[" << std::bitset<8>(i >> 16) << "]";
*ss << "[" << std::bitset<8>(i >> 24) << "]";
*ss << "[" << std::bitset<32>(i >> 32) << "]";
}
inline void PrettyPrintUINT64(uint64_t i) {
std::cout << "[" << std::bitset<15>(i) << "]";
std::cout << "[" << std::bitset<1>(i >> 15) << "]";
std::cout << "[" << std::bitset<8>(i >> 16) << "]";
std::cout << "[" << std::bitset<8>(i >> 24) << "]";
std::cout << "[" << std::bitset<32>(i >> 32) << "]" << std::endl;
}
inline void DumpLog(std::stringstream* ss, std::string file_name) {
std::ofstream log_file;
log_file.open(file_name);
log_file << ss->str();
log_file.close();
}
#ifdef _MSC_VER
# include <intrin.h>
# define __builtin_popcount _mm_popcnt_u32
# define __builtin_popcountll _mm_popcnt_u64
#endif
inline int count_bits(int32_t v) {
return static_cast<int>(__builtin_popcount(v));
}
inline int count_bits(int64_t v) {
return static_cast<int>(__builtin_popcountll(v));
}

@ -0,0 +1,141 @@
int pixel_to_index(int2 dimensions, int2 pixel) {
if (pixel.x >= 0 && pixel.x <= dimensions.x &&
pixel.y >= 0 && pixel.x <= dimensions.y ){
return pixel.y * dimensions.x + pixel.x;
}
return -1;
}
__kernel void conways (
global int2* image_res,
__write_only image2d_t image,
global char* first_node_buffer,
global char* second_node_buffer,
global char* buffer_flip
){
size_t x_pixel = get_global_id(0);
size_t y_pixel = get_global_id(1);
//printf(": %i", y_pixel);
int2 pixel = (int2)(x_pixel, y_pixel);
//if (pixel.x > 1800)
// printf("%i, %i", pixel.x, pixel.y);
float4 dead = (float4)(.49, .68, .81, 1);
float4 alive = (float4)(.49, .68, .71, .3);
// add all 8 blocks to neghbors
int neighbors = 0;
int val = 0;
if (*buffer_flip == 0){
// Top
val = pixel_to_index(*image_res, (int2)(pixel.x, pixel.y+1));
if (val >= 0)
neighbors += first_node_buffer[val];
// Top Right
val = pixel_to_index(*image_res, (int2)(pixel.x+1, pixel.y+1));
if (val >= 0)
neighbors += first_node_buffer[val];
// Right
val = pixel_to_index(*image_res, (int2)(pixel.x+1, pixel.y));
if (val >= 0)
neighbors += first_node_buffer[val];
// Bottom Right
val = pixel_to_index(*image_res, (int2)(pixel.x+1, pixel.y-1));
if (val >= 0)
neighbors += first_node_buffer[val];
// Bottom
val = pixel_to_index(*image_res, (int2)(pixel.x, pixel.y-1));
if (val >= 0)
neighbors += first_node_buffer[val];
// Bottom Left
val = pixel_to_index(*image_res, (int2)(pixel.x-1, pixel.y-1));
if (val >= 0)
neighbors += first_node_buffer[val];
// Left
val = pixel_to_index(*image_res, (int2)(pixel.x-1, pixel.y));
if (val >= 0)
neighbors += first_node_buffer[val];
// Top Left
val = pixel_to_index(*image_res, (int2)(pixel.x-1, pixel.y+1));
if (val >= 0)
neighbors += first_node_buffer[val];
int base = pixel_to_index(*image_res, pixel);
if (neighbors == 3 || (neighbors == 2 && first_node_buffer[base])){
write_imagef(image, pixel, alive);
second_node_buffer[base] = 1;
} else {
write_imagef(image, pixel, dead);
second_node_buffer[base] = 0;
}
} else {
// Top
val = pixel_to_index(*image_res, (int2)(pixel.x, pixel.y+1));
if (val >= 0)
neighbors += second_node_buffer[val];
// Top Right
val = pixel_to_index(*image_res, (int2)(pixel.x+1, pixel.y+1));
if (val >= 0)
neighbors += second_node_buffer[val];
// Right
val = pixel_to_index(*image_res, (int2)(pixel.x+1, pixel.y));
if (val >= 0)
neighbors += second_node_buffer[val];
// Bottom Right
val = pixel_to_index(*image_res, (int2)(pixel.x+1, pixel.y-1));
if (val >= 0)
neighbors += second_node_buffer[val];
// Bottom
val = pixel_to_index(*image_res, (int2)(pixel.x, pixel.y-1));
if (val >= 0)
neighbors += second_node_buffer[val];
// Bottom Left
val = pixel_to_index(*image_res, (int2)(pixel.x-1, pixel.y-1));
if (val >= 0)
neighbors += second_node_buffer[val];
// Left
val = pixel_to_index(*image_res, (int2)(pixel.x-1, pixel.y));
if (val >= 0)
neighbors += second_node_buffer[val];
// Top Left
val = pixel_to_index(*image_res, (int2)(pixel.x-1, pixel.y+1));
if (val >= 0)
neighbors += second_node_buffer[val];
int base = pixel_to_index(*image_res, pixel);
if (neighbors == 3 || (neighbors == 2 && second_node_buffer[base])){
write_imagef(image, pixel, alive);
first_node_buffer[base] = 1;
} else {
write_imagef(image, pixel, dead);
first_node_buffer[base] = 0;
}
}
}

@ -0,0 +1,737 @@
#include <OpenCL.h>
#include "util.hpp"
OpenCL::OpenCL() {
}
OpenCL::~OpenCL() {
}
void OpenCL::run_kernel(std::string kernel_name, sf::Vector2i work_size) {
size_t global_work_size[2] = { static_cast<size_t>(work_size.x), static_cast<size_t>(work_size.y) };
cl_kernel kernel = kernel_map.at(kernel_name);
error = clEnqueueAcquireGLObjects(command_queue, 1, &buffer_map.at("viewport_image"), 0, 0, 0);
if (vr_assert(error, "clEnqueueAcquireGLObjects"))
return;
//error = clEnqueueTask(command_queue, kernel, 0, NULL, NULL);
error = clEnqueueNDRangeKernel(
command_queue, kernel,
2, NULL, global_work_size,
NULL, 0, NULL, NULL);
if (vr_assert(error, "clEnqueueNDRangeKernel"))
return;
clFinish(command_queue);
// What if errors out and gl objects are never released?
error = clEnqueueReleaseGLObjects(command_queue, 1, &buffer_map.at("viewport_image"), 0, NULL, NULL);
if (vr_assert(error, "clEnqueueReleaseGLObjects"))
return;
}
void OpenCL::draw(sf::RenderWindow *window) {
for (auto &&i: image_map) {
window->draw(i.second.first);
}
}
bool OpenCL::aquire_hardware()
{
// Get the number of platforms
cl_uint platform_count = 0;
clGetPlatformIDs(0, nullptr, &platform_count);
if (platform_count == 0) {
std::cout << "There appears to be no OpenCL platforms on this machine" << std::endl;
return false;
}
// Get the ID's for those platforms
std::vector<cl_platform_id> plt_buf(platform_count);
clGetPlatformIDs(platform_count, plt_buf.data(), nullptr);
if (vr_assert(error, "clGetPlatformIDs"))
return false;
// Cycle through the platform ID's
for (unsigned int i = 0; i < platform_count; i++) {
// And get their device count
cl_uint deviceIdCount = 0;
error = clGetDeviceIDs(plt_buf[i], CL_DEVICE_TYPE_ALL, 0, nullptr, &deviceIdCount);
if (vr_assert(error, "clGetDeviceIDs"))
return false;
if (deviceIdCount == 0) {
std::cout << "There appears to be no devices associated with this platform" << std::endl;
} else {
// Get the device ids and place them in the device list
std::vector<cl_device_id> deviceIds(deviceIdCount);
error = clGetDeviceIDs(plt_buf[i], CL_DEVICE_TYPE_ALL, deviceIdCount, deviceIds.data(), NULL);
if (vr_assert(error, "clGetDeviceIDs"))
return false;
for (int d = 0; d < deviceIds.size(); d++) {
device_list.emplace_back(device(deviceIds[d], plt_buf.at(i)));
}
}
}
return true;
}
bool OpenCL::create_shared_context() {
// Hurray for standards!
// Setup the context properties to grab the current GL context
#ifdef linux
cl_context_properties context_properties[] = {
CL_GL_CONTEXT_KHR, (cl_context_properties)glXGetCurrentContext(),
CL_GLX_DISPLAY_KHR, (cl_context_properties)glXGetCurrentDisplay(),
CL_CONTEXT_PLATFORM, (cl_context_properties)platform_id,
0
};
#elif defined _WIN32
HGLRC hGLRC = wglGetCurrentContext();
HDC hDC = wglGetCurrentDC();
cl_context_properties context_properties[] = {
CL_CONTEXT_PLATFORM, (cl_context_properties)platform_id,
CL_GL_CONTEXT_KHR, (cl_context_properties)hGLRC,
CL_WGL_HDC_KHR, (cl_context_properties)hDC,
0
};
#elif defined TARGET_OS_MAC
CGLContextObj glContext = CGLGetCurrentContext();
CGLShareGroupObj shareGroup = CGLGetShareGroup(glContext);
cl_context_properties context_properties[] = {
CL_CONTEXT_PROPERTY_USE_CGL_SHAREGROUP_APPLE,
(cl_context_properties)shareGroup,
0
};
#elif
std::cout << "Target machine not supported for cl_khr_gl_sharing" << std::endl;
return false;
#endif
// Create our shared context
context = clCreateContext(
context_properties,
1,
&device_id,
nullptr, nullptr,
&error
);
if (vr_assert(error, "clCreateContext"))
return false;
return true;
}
bool OpenCL::create_command_queue() {
// Command queue requires a context and device id. It can also be a device ID list
// as long as the devices reside on the same platform
if (context && device_id) {
command_queue = clCreateCommandQueue(context, device_id, 0, &error);
if (vr_assert(error, "clCreateCommandQueue"))
return false;
} else {
std::cout << "Failed creating the command queue. Context or device_id not initialized" << std::endl;
return false;
}
return true;
}
bool OpenCL::compile_kernel(std::string kernel_path, std::string kernel_name) {
const char* source;
std::string tmp;
//Load in the kernel, and c stringify it
tmp = read_file(kernel_path);
source = tmp.c_str();
size_t kernel_source_size = strlen(source);
// Load the source into CL's data structure
cl_program program = clCreateProgramWithSource(
context, 1,
&source,
&kernel_source_size, &error
);
// This is not for compilation, it only loads the source
if (vr_assert(error, "clCreateProgramWithSource"))
return false;
// Try and build the program
// "-cl-finite-math-only -cl-fast-relaxed-math -cl-unsafe-math-optimizations"
error = clBuildProgram(program, 1, &device_id, "-cl-finite-math-only -cl-fast-relaxed-math -cl-unsafe-math-optimizations", NULL, NULL);
// Check to see if it errored out
if (vr_assert(error, "clBuildProgram")) {
// Get the size of the queued log
size_t log_size;
clGetProgramBuildInfo(program, device_id, CL_PROGRAM_BUILD_LOG, 0, NULL, &log_size);
char *log = new char[log_size];
// Grab the log
clGetProgramBuildInfo(program, device_id, CL_PROGRAM_BUILD_LOG, log_size, log, NULL);
std::cout << log;
return false;
}
// Done initializing the kernel
cl_kernel kernel = clCreateKernel(program, kernel_name.c_str(), &error);
if (vr_assert(error, "clCreateKernel"))
return false;
// Do I want these to overlap when repeated??
kernel_map[kernel_name] = kernel;
return true;
}
bool OpenCL::create_image_buffer_from_texture(std::string buffer_name, sf::Texture* texture, cl_int access_type) {
if (buffer_map.count(buffer_name) > 0) {
release_buffer(buffer_name);
// Need to check to see if we are taking care of the texture as well
if (image_map.count(buffer_name) > 0)
image_map.erase(buffer_name);
}
cl_mem buff = clCreateFromGLTexture(
context, access_type, GL_TEXTURE_2D,
0, texture->getNativeHandle(), &error);
if (vr_assert(error, "clCreateFromGLTexture"))
return false;
store_buffer(buff, buffer_name);
return true;
}
bool OpenCL::create_image_buffer(std::string buffer_name, sf::Vector2i size, sf::Vector2f position, cl_int access_type) {
if (buffer_map.count(buffer_name) > 0) {
release_buffer(buffer_name);
// Need to check to see if we are taking care of the texture as well
if (image_map.count(buffer_name) > 0)
image_map.erase(buffer_name);
}
std::unique_ptr<sf::Texture> texture(new sf::Texture);
texture->create(size.x, size.y);
cl_mem buff = clCreateFromGLTexture(
context, access_type, GL_TEXTURE_2D,
0, texture->getNativeHandle(), &error);
if (vr_assert(error, "clCreateFromGLTexture"))
return false;
sf::Sprite sprite(*texture);
sprite.setPosition(position);
image_map[buffer_name] = std::pair<sf::Sprite, std::unique_ptr<sf::Texture>>(sprite, std::move(texture));
store_buffer(buff, buffer_name);
return true;
}
int OpenCL::create_buffer(std::string buffer_name, cl_uint size, void* data) {
if (buffer_map.count(buffer_name) > 0) {
release_buffer(buffer_name);
}
cl_mem buff = clCreateBuffer(
context, CL_MEM_READ_ONLY | CL_MEM_COPY_HOST_PTR,
size, data, &error
);
if (vr_assert(error, "clCreateBuffer"))
return -1;
store_buffer(buff, buffer_name);
return 1;
}
int OpenCL::create_buffer(std::string buffer_name, cl_uint size, void* data, cl_mem_flags flags) {
if (buffer_map.count(buffer_name) > 0) {
release_buffer(buffer_name);
}
((char*)data)[10000];
cl_mem buff = clCreateBuffer(
context, flags,
size, data, &error
);
if (vr_assert(error, "clCreateBuffer"))
return -1;
store_buffer(buff, buffer_name);
return 1;
}
bool OpenCL::store_buffer(cl_mem buffer, std::string buffer_name) {
if (buffer_map.count(buffer_name) > 0) {
error = clReleaseMemObject(buffer_map.at(buffer_name));
if (vr_assert(error, "clReleaseMemObject")) {
std::cout << "Error releasing overlapping buffer : " << buffer_name;
std::cout << "Buffer not added";
return false;
}
}
buffer_map[buffer_name] = buffer;
return true;
}
bool OpenCL::release_buffer(std::string buffer_name) {
if (buffer_map.count(buffer_name) > 0) {
error = clReleaseMemObject(buffer_map.at(buffer_name));
if (vr_assert(error, "clReleaseMemObject")) {
std::cout << "Error releasing buffer : " << buffer_name;
std::cout << "Buffer not removed";
return false;
}
buffer_map.erase(buffer_name);
} else {
std::cout << "Error releasing buffer : " << buffer_name;
std::cout << "Buffer not found";
return false;
}
return true;
}
int OpenCL::set_kernel_arg(std::string kernel_name, int index, std::string buffer_name) {
error = clSetKernelArg(
kernel_map.at(kernel_name),
index,
sizeof(cl_mem),
(void *)&buffer_map.at(buffer_name));
if (vr_assert(error, "clSetKernelArg")) {
std::cout << buffer_name << std::endl;
std::cout << buffer_map.at(buffer_name) << std::endl;
return -1;
}
return 1;
}
bool OpenCL::load_config() {
std::ifstream input_file("device_config.bin", std::ios::binary | std::ios::in);
if (!input_file.is_open()) {
std::cout << "No config file..." << std::endl;
return false;
}
device::packed_data data;
input_file.read(reinterpret_cast<char*>(&data), sizeof(data));
std::cout << "config loaded, looking for device..." << std::endl;
for (auto d: device_list) {
if (memcmp(&d, &data, sizeof(device::packed_data)) == 0) {
std::cout << "Found saved device" << std::endl;
device_id = d.getDeviceId();
platform_id = d.getPlatformId();
break;
}
}
input_file.close();
return true;
}
void OpenCL::save_config() {
std::ofstream output_file;
output_file.open("device_config.bin", std::ofstream::binary | std::ofstream::out | std::ofstream::trunc);
device d(device_id, platform_id);
d.print_packed_data(output_file);
output_file.close();
}
bool OpenCL::init() {
if (!aquire_hardware())
return false;
if (!load_config()) {
std::cout << "Select a device number which you wish to use" << std::endl;
for (int i = 0; i < device_list.size(); i++) {
std::cout << "\n-----------------------------------------------------------------" << std::endl;
std::cout << "\tDevice Number : " << i << std::endl;
std::cout << "-----------------------------------------------------------------" << std::endl;
device_list.at(i).print(std::cout);
}
int selection = -1;
while (selection < 0 && selection >= device_list.size()) {
std::cout << "Device which you wish to use : ";
std::cin >> selection;
}
device_id = device_list.at(selection).getDeviceId();
platform_id = device_list.at(selection).getPlatformId();
save_config();
}
if (!create_shared_context())
return false;
if (!create_command_queue())
return false;
return true;
}
bool OpenCL::vr_assert(int error_code, std::string function_name) {
// Just gonna do a little jump table here, just error codes so who cares
std::string err_msg = "Error : ";
switch (error_code) {
case CL_SUCCESS:
return false;
case 1:
return false;
case CL_DEVICE_NOT_FOUND:
err_msg += "CL_DEVICE_NOT_FOUND";
break;
case CL_DEVICE_NOT_AVAILABLE:
err_msg = "CL_DEVICE_NOT_AVAILABLE";
break;
case CL_COMPILER_NOT_AVAILABLE:
err_msg = "CL_COMPILER_NOT_AVAILABLE";
break;
case CL_MEM_OBJECT_ALLOCATION_FAILURE:
err_msg = "CL_MEM_OBJECT_ALLOCATION_FAILURE";
break;
case CL_OUT_OF_RESOURCES:
err_msg = "CL_OUT_OF_RESOURCES";
break;
case CL_OUT_OF_HOST_MEMORY:
err_msg = "CL_OUT_OF_HOST_MEMORY";
break;
case CL_PROFILING_INFO_NOT_AVAILABLE:
err_msg = "CL_PROFILING_INFO_NOT_AVAILABLE";
break;
case CL_MEM_COPY_OVERLAP:
err_msg = "CL_MEM_COPY_OVERLAP";
break;
case CL_IMAGE_FORMAT_MISMATCH:
err_msg = "CL_IMAGE_FORMAT_MISMATCH";
break;
case CL_IMAGE_FORMAT_NOT_SUPPORTED:
err_msg = "CL_IMAGE_FORMAT_NOT_SUPPORTED";
break;
case CL_BUILD_PROGRAM_FAILURE:
err_msg = "CL_BUILD_PROGRAM_FAILURE";
break;
case CL_MAP_FAILURE:
err_msg = "CL_MAP_FAILURE";
break;
case CL_MISALIGNED_SUB_BUFFER_OFFSET:
err_msg = "CL_MISALIGNED_SUB_BUFFER_OFFSET";
break;
case CL_EXEC_STATUS_ERROR_FOR_EVENTS_IN_WAIT_LIST:
err_msg = "CL_EXEC_STATUS_ERROR_FOR_EVENTS_IN_WAIT_LIST";
break;
case CL_COMPILE_PROGRAM_FAILURE:
err_msg = "CL_COMPILE_PROGRAM_FAILURE";
break;
case CL_LINKER_NOT_AVAILABLE:
err_msg = "CL_LINKER_NOT_AVAILABLE";
break;
case CL_LINK_PROGRAM_FAILURE:
err_msg = "CL_LINK_PROGRAM_FAILURE";
break;
case CL_DEVICE_PARTITION_FAILED:
err_msg = "CL_DEVICE_PARTITION_FAILED";
break;
case CL_KERNEL_ARG_INFO_NOT_AVAILABLE:
err_msg = "CL_KERNEL_ARG_INFO_NOT_AVAILABLE";
break;
case CL_INVALID_VALUE:
err_msg = "CL_INVALID_VALUE";
break;
case CL_INVALID_DEVICE_TYPE:
err_msg = "CL_INVALID_DEVICE_TYPE";
break;
case CL_INVALID_PLATFORM:
err_msg = "CL_INVALID_PLATFORM";
break;
case CL_INVALID_DEVICE:
err_msg = "CL_INVALID_DEVICE";
break;
case CL_INVALID_CONTEXT:
err_msg = "CL_INVALID_CONTEXT";
break;
case CL_INVALID_QUEUE_PROPERTIES:
err_msg = "CL_INVALID_QUEUE_PROPERTIES";
break;
case CL_INVALID_COMMAND_QUEUE:
err_msg = "CL_INVALID_COMMAND_QUEUE";
break;
case CL_INVALID_HOST_PTR:
err_msg = "CL_INVALID_HOST_PTR";
break;
case CL_INVALID_MEM_OBJECT:
err_msg = "CL_INVALID_MEM_OBJECT";
break;
case CL_INVALID_IMAGE_FORMAT_DESCRIPTOR:
err_msg = "CL_INVALID_IMAGE_FORMAT_DESCRIPTOR";
break;
case CL_INVALID_IMAGE_SIZE:
err_msg = "CL_INVALID_IMAGE_SIZE";
break;
case CL_INVALID_SAMPLER:
err_msg = "CL_INVALID_SAMPLER";
break;
case CL_INVALID_BINARY:
err_msg = "CL_INVALID_BINARY";
break;
case CL_INVALID_BUILD_OPTIONS:
err_msg = "CL_INVALID_BUILD_OPTIONS";
break;
case CL_INVALID_PROGRAM:
err_msg = "CL_INVALID_PROGRAM";
break;
case CL_INVALID_PROGRAM_EXECUTABLE:
err_msg = "CL_INVALID_PROGRAM_EXECUTABLE";
break;
case CL_INVALID_KERNEL_NAME:
err_msg = "CL_INVALID_KERNEL_NAME";
break;
case CL_INVALID_KERNEL_DEFINITION:
err_msg = "CL_INVALID_KERNEL_DEFINITION";
break;
case CL_INVALID_KERNEL:
err_msg = "CL_INVALID_KERNEL";
break;
case CL_INVALID_ARG_INDEX:
err_msg = "CL_INVALID_ARG_INDEX";
break;
case CL_INVALID_ARG_VALUE:
err_msg = "CL_INVALID_ARG_VALUE";
break;
case CL_INVALID_ARG_SIZE:
err_msg = "CL_INVALID_ARG_SIZE";
break;
case CL_INVALID_KERNEL_ARGS:
err_msg = "CL_INVALID_KERNEL_ARGS";
break;
case CL_INVALID_WORK_DIMENSION:
err_msg = "CL_INVALID_WORK_DIMENSION";
break;
case CL_INVALID_WORK_GROUP_SIZE:
err_msg = "CL_INVALID_WORK_GROUP_SIZE";
break;
case CL_INVALID_WORK_ITEM_SIZE:
err_msg = "CL_INVALID_WORK_ITEM_SIZE";
break;
case CL_INVALID_GLOBAL_OFFSET:
err_msg = "CL_INVALID_GLOBAL_OFFSET";
break;
case CL_INVALID_EVENT_WAIT_LIST:
err_msg = "CL_INVALID_EVENT_WAIT_LIST";
break;
case CL_INVALID_EVENT:
err_msg = "CL_INVALID_EVENT";
break;
case CL_INVALID_OPERATION:
err_msg = "CL_INVALID_OPERATION";
break;
case CL_INVALID_GL_OBJECT:
err_msg = "CL_INVALID_GL_OBJECT";
break;
case CL_INVALID_BUFFER_SIZE:
err_msg = "CL_INVALID_BUFFER_SIZE";
break;
case CL_INVALID_MIP_LEVEL:
err_msg = "CL_INVALID_MIP_LEVEL";
break;
case CL_INVALID_GLOBAL_WORK_SIZE:
err_msg = "CL_INVALID_GLOBAL_WORK_SIZE";
break;
case CL_INVALID_PROPERTY:
err_msg = "CL_INVALID_PROPERTY";
break;
case CL_INVALID_IMAGE_DESCRIPTOR:
err_msg = "CL_INVALID_IMAGE_DESCRIPTOR";
break;
case CL_INVALID_COMPILER_OPTIONS:
err_msg = "CL_INVALID_COMPILER_OPTIONS";
break;
case CL_INVALID_LINKER_OPTIONS:
err_msg = "CL_INVALID_LINKER_OPTIONS";
break;
case CL_INVALID_DEVICE_PARTITION_COUNT:
err_msg = "CL_INVALID_DEVICE_PARTITION_COUNT";
break;
case CL_INVALID_GL_SHAREGROUP_REFERENCE_KHR:
err_msg = "CL_INVALID_GL_SHAREGROUP_REFERENCE_KHR";
break;
case CL_PLATFORM_NOT_FOUND_KHR:
err_msg = "CL_PLATFORM_NOT_FOUND_KHR";
break;
}
std::cout << err_msg << " =at= " << function_name << std::endl;
return true;
}
OpenCL::device::device(cl_device_id device_id, cl_platform_id platform_id) {
this->device_id = device_id;
this->platform_id = platform_id;
int error = 0;
error = clGetPlatformInfo(platform_id, CL_PLATFORM_NAME, 128, (void*)&data.platform_name, nullptr);
if (vr_assert(error, "clGetPlatformInfo"))
return;
error = clGetDeviceInfo(device_id, CL_DEVICE_VERSION, sizeof(char) * 128, &data.opencl_version, NULL);
error = clGetDeviceInfo(device_id, CL_DEVICE_TYPE, sizeof(cl_device_type), &data.device_type, NULL);
error = clGetDeviceInfo(device_id, CL_DEVICE_MAX_CLOCK_FREQUENCY, sizeof(cl_uint), &data.clock_frequency, NULL);
error = clGetDeviceInfo(device_id, CL_DEVICE_MAX_COMPUTE_UNITS, sizeof(cl_uint), &data.compute_units, NULL);
error = clGetDeviceInfo(device_id, CL_DEVICE_EXTENSIONS, 1024, &data.device_extensions, NULL);
error = clGetDeviceInfo(device_id, CL_DEVICE_NAME, 256, &data.device_name, NULL);
error = clGetDeviceInfo(device_id, CL_DEVICE_ENDIAN_LITTLE, sizeof(cl_bool), &is_little_endian, NULL);
// Check for the sharing extension
if (std::string(data.device_extensions).find("cl_khr_gl_sharing") != std::string::npos ||
std::string(data.device_extensions).find("cl_APPLE_gl_sharing") != std::string::npos) {
cl_gl_sharing = true;
}
}
OpenCL::device::device(const device& d) {
// member values, copy individually
device_id = d.device_id;
platform_id = d.platform_id;
is_little_endian = d.is_little_endian;
cl_gl_sharing = d.cl_gl_sharing;
// struct so it copies by value
data = d.data;
}
void OpenCL::device::print(std::ostream& stream) const {
stream << "\n\tDevice ID : " << device_id << std::endl;
stream << "\tDevice Name : " << data.device_name << std::endl;
stream << "\tPlatform ID : " << platform_id << std::endl;
stream << "\tPlatform Name : " << data.platform_name << std::endl;
stream << "\tOpenCL Version : " << data.opencl_version << std::endl;
stream << "\tSupports sharing : " << std::boolalpha << cl_gl_sharing << std::endl;
stream << "\tDevice Type : ";
if (data.device_type == CL_DEVICE_TYPE_CPU)
stream << "CPU" << std::endl;
else if (data.device_type == CL_DEVICE_TYPE_GPU)
stream << "GPU" << std::endl;
else if (data.device_type == CL_DEVICE_TYPE_ACCELERATOR)
stream << "Accelerator" << std::endl;
stream << "\tIs Little Endian : " << std::boolalpha << is_little_endian << std::endl;
stream << "\tClock Frequency : " << data.clock_frequency << std::endl;
stream << "\tCompute Units : " << data.compute_units << std::endl;
stream << "\n*Extensions*" << std::endl;
stream << data.device_extensions << std::endl;
stream << "\n";
}
void OpenCL::device::print_packed_data(std::ostream& stream) {
stream.write(reinterpret_cast<char*>(&data), sizeof(data));
}

@ -0,0 +1,133 @@
#include <iostream>
#include <SFML/Graphics.hpp>
#include <random>
#include <chrono>
#include "util.hpp"
#include <thread>
#include "OpenCL.h"
float elap_time() {
static std::chrono::time_point<std::chrono::system_clock> start;
static bool started = false;
if (!started) {
start = std::chrono::system_clock::now();
started = true;
}
std::chrono::time_point<std::chrono::system_clock> now = std::chrono::system_clock::now();
std::chrono::duration<double> elapsed_time = now - start;
return static_cast<float>(elapsed_time.count());
}
const int WINDOW_X = 1080;
const int WINDOW_Y = 1080;
void generate_nodes(sf::Uint8* nodes) {
for (int i = 0; i < WINDOW_X * WINDOW_Y; i += 1) {
if (rand() % 10 > 8)
nodes[i] = 1;
else
nodes[i] = 0;
}
}
int main() {
sf::RenderWindow window(sf::VideoMode(WINDOW_X, WINDOW_Y), "conways-game-of-life-opencl");
window.setFramerateLimit(60);
float physic_step = 0.166f;
float physic_time = 0.0f;
double frame_time = 0.0, elapsed_time = 0.0, delta_time = 0.0, accumulator_time = 0.0, current_time = 0.0;
OpenCL cl;
if (!cl.init())
return -1;
while (!cl.compile_kernel("../kernels/conways.cl", "conways")) {
std::cin.get();
}
sf::Vector2i image_resolution(WINDOW_X, WINDOW_Y);
cl.create_image_buffer("viewport_image", image_resolution, sf::Vector2f(0, 0), CL_MEM_WRITE_ONLY);
cl.create_buffer("image_res", sizeof(sf::Vector2i), &image_resolution);
sf::Uint8* nodes = new sf::Uint8[WINDOW_X * WINDOW_Y];
generate_nodes(nodes);
nodes[0] = 1;
cl.create_buffer("first_node_buffer", WINDOW_X * WINDOW_Y, (void*)nodes, CL_MEM_READ_WRITE | CL_MEM_COPY_HOST_PTR);
cl.create_buffer("second_node_buffer", WINDOW_X * WINDOW_Y, (void*)nodes, CL_MEM_READ_WRITE | CL_MEM_COPY_HOST_PTR);
char buffer_flip = 0;
cl.create_buffer("buffer_flip", sizeof(char), (void*)&buffer_flip, CL_MEM_READ_ONLY | CL_MEM_USE_HOST_PTR);
cl.set_kernel_arg("conways", 0, "image_res");
cl.set_kernel_arg("conways", 1, "viewport_image");
cl.set_kernel_arg("conways", 2, "first_node_buffer");
cl.set_kernel_arg("conways", 3, "second_node_buffer");
cl.set_kernel_arg("conways", 4, "buffer_flip");
while (window.isOpen())
{
sf::Event event; // Handle input
while (window.pollEvent(event)) {
if (event.type == sf::Event::Closed) {
window.close();
}
if (event.type == sf::Event::KeyPressed) {
if (event.key.code == sf::Keyboard::Down) {
}
if (event.key.code == sf::Keyboard::Up) {
}
if (event.key.code == sf::Keyboard::Right) {
}
if (event.key.code == sf::Keyboard::Left) {
}
if (event.key.code == sf::Keyboard::Equal) {
}
if (event.key.code == sf::Keyboard::Dash) {
}
}
}
elapsed_time = elap_time(); // Handle time
delta_time = elapsed_time - current_time;
current_time = elapsed_time;
if (delta_time > 0.02f)
delta_time = 0.02f;
accumulator_time += delta_time;
while (accumulator_time >= physic_step) { // While the frame has sim time, update
accumulator_time -= physic_step;
physic_time += physic_step;
}
window.clear(sf::Color::White);
cl.run_kernel("conways", image_resolution);
//cl.run_kernel("conways", sf::Vector2i(5, 5));
cl.draw(&window);
if (buffer_flip == 1)
buffer_flip = 0;
else
buffer_flip = 1;
window.display();
}
return 0;
}
Loading…
Cancel
Save