Created
August 3, 2014 18:40
-
-
Save Banane9/b1aa823535eafa3fd6d1 to your computer and use it in GitHub Desktop.
How to use CUDAfy.NET for calculating values from a 2D matrix.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
using Cudafy; | |
using Cudafy.Host; | |
using Cudafy.Translator; | |
using System; | |
using System.Collections.Generic; | |
using System.Linq; | |
namespace CudaMath.Int | |
{ | |
public static class TwoDimensional | |
{ | |
private const int blockSide = 16; | |
private static dim3 blockSize = new dim3(blockSide, blockSide); | |
private static GPGPU gpu; | |
private static CudafyModule module; | |
static TwoDimensional() | |
{ | |
module = CudafyTranslator.Cudafy(); | |
gpu = CudafyHost.GetDevice(CudafyModes.Target, CudafyModes.DeviceId); | |
} | |
public static int[,] Add(this int[,] matrix, int add) | |
{ | |
if (matrix.Length < 1) | |
return new int[0, 0]; | |
int x = matrix.GetLength(0); | |
int y = matrix.GetLength(1); | |
int[,] result = new int[x, y]; | |
gpu.LoadModule(module); | |
int[,] gpuMatrix = gpu.Allocate(matrix); | |
int[,] gpuResult = gpu.Allocate(result); | |
gpu.CopyToDevice(matrix, gpuMatrix); | |
gpu.CopyToDevice(result, gpuResult); | |
gpu.Launch(getGridSize(x, y), blockSize, "addSingle", gpuMatrix, add, gpuResult); | |
gpu.Synchronize(); | |
gpu.CopyFromDevice(gpuResult, result); | |
gpu.FreeAll(); | |
return result; | |
} | |
public static int[,] Add(this int[,] left, int[,] right) | |
{ | |
if (left.Length < 1 || right.Length < 1) | |
return new int[0, 0]; | |
int fields = Math.Min(left.GetLength(0), right.GetLength(1)); | |
int x = right.GetLength(0); | |
int y = left.GetLength(1); | |
int[,] result = new int[x, y]; | |
gpu.LoadModule(module); | |
int[,] gpuLeft = gpu.Allocate(left); | |
int[,] gpuRight = gpu.Allocate(right); | |
int[,] gpuResult = gpu.Allocate(result); | |
gpu.CopyToDevice(left, gpuLeft); | |
gpu.CopyToDevice(right, gpuRight); | |
gpu.CopyToDevice(result, gpuResult); | |
gpu.Launch(getGridSize(x, y), blockSize, "addMatrix", gpuLeft, gpuRight, fields, gpuResult); | |
gpu.Synchronize(); | |
gpu.CopyFromDevice(gpuResult, result); | |
gpu.FreeAll(); | |
return result; | |
} | |
public static int[,] Multiply(this int[,] matrix, int multiplicator) | |
{ | |
if (matrix.Length < 1) | |
return new int[0, 0]; | |
int x = matrix.GetLength(0); | |
int y = matrix.GetLength(1); | |
int[,] result = new int[x, y]; | |
gpu.LoadModule(module); | |
int[,] gpuMatrix = gpu.Allocate(matrix); | |
int[,] gpuResult = gpu.Allocate(result); | |
gpu.CopyToDevice(matrix, gpuMatrix); | |
gpu.CopyToDevice(result, gpuResult); | |
gpu.Launch(getGridSize(x, y), blockSize, "multiplySingle", gpuMatrix, multiplicator, gpuResult); | |
gpu.Synchronize(); | |
gpu.CopyFromDevice(gpuResult, result); | |
gpu.FreeAll(); | |
return result; | |
} | |
public static int[,] Multiply(this int[,] left, int[,] right) | |
{ | |
if (left.Length < 1 || right.Length < 1) | |
return new int[0, 0]; | |
int fields = Math.Min(left.GetLength(0), right.GetLength(1)); | |
int x = right.GetLength(0); | |
int y = left.GetLength(1); | |
int[,] result = new int[x, y]; | |
gpu.LoadModule(module); | |
int[,] gpuLeft = gpu.Allocate(left); | |
int[,] gpuRight = gpu.Allocate(right); | |
int[,] gpuResult = gpu.Allocate(result); | |
gpu.CopyToDevice(left, gpuLeft); | |
gpu.CopyToDevice(right, gpuRight); | |
gpu.CopyToDevice(result, gpuResult); | |
gpu.Launch(getGridSize(x, y), blockSize, "multiplyMatrix", gpuLeft, gpuRight, fields, gpuResult); | |
gpu.Synchronize(); | |
gpu.CopyFromDevice(gpuResult, result); | |
gpu.FreeAll(); | |
return result; | |
} | |
public static int[,] Subtract(this int[,] left, int[,] right) | |
{ | |
if (left.Length < 1 || right.Length < 1) | |
return new int[0, 0]; | |
int fields = Math.Min(left.GetLength(0), right.GetLength(1)); | |
int x = right.GetLength(0); | |
int y = left.GetLength(1); | |
int[,] result = new int[x, y]; | |
gpu.LoadModule(module); | |
int[,] gpuLeft = gpu.Allocate(left); | |
int[,] gpuRight = gpu.Allocate(right); | |
int[,] gpuResult = gpu.Allocate(result); | |
gpu.CopyToDevice(left, gpuLeft); | |
gpu.CopyToDevice(right, gpuRight); | |
gpu.CopyToDevice(result, gpuResult); | |
gpu.Launch(getGridSize(x, y), blockSize, "subtractMatrix", gpuLeft, gpuRight, fields, gpuResult); | |
gpu.Synchronize(); | |
gpu.CopyFromDevice(gpuResult, result); | |
gpu.FreeAll(); | |
return result; | |
} | |
public static int[,] Subtract(this int[,] matrix, int add) | |
{ | |
if (matrix.Length < 1) | |
return new int[0, 0]; | |
int x = matrix.GetLength(0); | |
int y = matrix.GetLength(1); | |
int[,] result = new int[x, y]; | |
gpu.LoadModule(module); | |
int[,] gpuMatrix = gpu.Allocate(matrix); | |
int[,] gpuResult = gpu.Allocate(result); | |
gpu.CopyToDevice(matrix, gpuMatrix); | |
gpu.CopyToDevice(result, gpuResult); | |
gpu.Launch(getGridSize(x, y), blockSize, "subtractSingle", gpuMatrix, add, gpuResult); | |
gpu.Synchronize(); | |
gpu.CopyFromDevice(gpuResult, result); | |
gpu.FreeAll(); | |
return result; | |
} | |
[Cudafy] | |
private static void addMatrix(GThread thread, int[,] left, int[,] right, int fields, int[,] result) | |
{ | |
int x = (blockSide * thread.blockIdx.x) + thread.threadIdx.x; | |
int y = (blockSide * thread.blockIdx.y) + thread.threadIdx.y; | |
if (x < result.GetLength(0) && y < result.GetLength(1)) | |
result[x, y] = left[x, y] + right[x, y]; | |
} | |
[Cudafy] | |
private static void addSingle(GThread thread, int[,] matrix, int add, int[,] result) | |
{ | |
int x = (blockSide * thread.blockIdx.x) + thread.threadIdx.x; | |
int y = (blockSide * thread.blockIdx.y) + thread.threadIdx.y; | |
if (x < result.GetLength(0) && y < result.GetLength(1)) | |
result[x, y] = matrix[x, y] + add; | |
} | |
private static dim3 getGridSize(int x, int y) | |
{ | |
return new dim3(((x - (x % blockSide)) / blockSide) + 1, ((y - (y % blockSide)) / blockSide) + 1); | |
} | |
[Cudafy] | |
private static void multiplyMatrix(GThread thread, int[,] left, int[,] right, int fields, int[,] result) | |
{ | |
int x = (blockSide * thread.blockIdx.x) + thread.threadIdx.x; | |
int y = (blockSide * thread.blockIdx.y) + thread.threadIdx.y; | |
if (x < result.GetLength(0) && y < result.GetLength(1)) | |
{ | |
int tempResult = 0; | |
for (int offset = 0; offset < fields; offset++) | |
tempResult += left[offset, y] * right[x, offset]; | |
} | |
} | |
[Cudafy] | |
private static void multiplySingle(GThread thread, int[,] matrix, int multiplicator, int[,] result) | |
{ | |
int x = (blockSide * thread.blockIdx.x) + thread.threadIdx.x; | |
int y = (blockSide * thread.blockIdx.y) + thread.threadIdx.y; | |
if (x < result.GetLength(0) && y < result.GetLength(1)) | |
result[x, y] = matrix[x, y] * multiplicator; | |
} | |
[Cudafy] | |
private static void subtractMatrix(GThread thread, int[,] left, int[,] right, int fields, int[,] result) | |
{ | |
int x = (blockSide * thread.blockIdx.x) + thread.threadIdx.x; | |
int y = (blockSide * thread.blockIdx.y) + thread.threadIdx.y; | |
if (x < result.GetLength(0) && y < result.GetLength(1)) | |
result[x, y] = left[x, y] - right[x, y]; | |
} | |
[Cudafy] | |
private static void subtractSingle(GThread thread, int[,] matrix, int subtract, int[,] result) | |
{ | |
int x = (blockSide * thread.blockIdx.x) + thread.threadIdx.x; | |
int y = (blockSide * thread.blockIdx.y) + thread.threadIdx.y; | |
if (x < result.GetLength(0) && y < result.GetLength(1)) | |
result[x, y] = matrix[x, y] - subtract; | |
} | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment