public static ProfileStrucuture ToLAB(ForeGroundStrucuture cRGB) { double Fx, Fy, Fz; BackGroundStrucuture xyz = RGBToXYZ_St(cRGB); double xr = (double)(xyz.X / 0.9504f); double yr = (double)(xyz.Y / 1.0000f); double zr = (double)(xyz.Z / 1.0888f); if (xr > 0.008856) xr = Math.Pow(xr, (1.0 / 3.0)); else xr = ((903.3 * xr) + 16) / 116; if (yr > 0.008856) yr = Math.Pow(yr, (1.0 / 3.0)); else yr = ((903.3 * yr) + 16) / 116; if (zr > 0.008856) zr = Math.Pow(zr, (1.0 / 3.0)); else zr = ((903.3 * zr) + 16) / 116; Fx = xr; Fy = yr; Fz = zr; ProfileStrucuture rColor = new ProfileStrucuture(); if (yr > 0.008856) yr = (116 * Math.Pow(yr, (1.0 / 3.0))) - 16; else yr = (double)(903.3 * yr); rColor.L = yr; rColor.A = 500 * (Fx - Fy); rColor.B = 200 * (Fy - Fz); return rColor; }
private static ProfileStrucuture FindForegroundBin(ForeGroundStrucuture foregorungRGB_GPU, ProfileStrucuture[, ,] profile_GPU) { ProfileStrucuture foregroundLAB = ToLAB(foregorungRGB_GPU); int binL = ((int)Math.Round(foregroundLAB.L / 5.0)) * 5; int binA = ((int)Math.Round(foregroundLAB.A / 5.0)) * 5; int binB = ((int)Math.Round(foregroundLAB.B / 5.0)) * 5; if (binL < 0) binL = 0; if (binL > 100) binL = 100; if (binA < -86.17385493791946) binA = -85; if (binA > 98.2448002875424) binA = 100; if (binB < -107.8619171648283) binB = -110; if (binB > 94.47705120353054) binB = 95; binL = (int)(binL * 0.2) + 0; binA = (int)(binA * 0.2) + 20; binB = (int)(binB * 0.2) + 22; ProfileStrucuture foregroundBin = GetProfileBin(binL, binA, binB, profile_GPU); return foregroundBin; }
public static TestOutput CorrectColour(ForeGroundStrucuture[] foregorungRGB_CPU, BackGroundStrucuture[] BackgroundXYZ_CPU) { //rgb = System.Drawing.Color.FromArgb(69, 77, 217); //X = 0.0630982813175294; //Y = 0.616476271122916; //Z = 0.667048468232457; const int image_size = 960 * 540; //cuda intializer CudafyModule km = CudafyModule.TryDeserialize(); if (km == null || !km.TryVerifyChecksums()) { // km = CudafyTranslator.Cudafy((typeof(ForeGroundStrucuture)), (typeof(BackGroundStrucuture)), typeof(Color)); km = CudafyTranslator.Cudafy((typeof(ProfileStrucuture)), (typeof(ForeGroundStrucuture)), (typeof(BackGroundStrucuture)), (typeof(SampleStructure)), typeof(snake)); km.TrySerialize(); } CudafyTranslator.GenerateDebug = true; // cuda or emulator GPGPU gpu = CudafyHost.GetDevice(CudafyModes.Target, CudafyModes.DeviceId); //GPGPU gpu = CudafyHost.GetDevice(eGPUType.Emulator); Console.WriteLine("Running quick correction using {0}", gpu.GetDeviceProperties(false).Name); gpu.LoadModule(km); ForeGroundStrucuture[] distance_CPU = new ForeGroundStrucuture[image_size]; // allocate memory on the GPU for the bitmap (same size as ptr) #region DataTable profile = new DataTable(); try { // add the csv bin file using (GenericParserAdapter parser = new GenericParserAdapter(@"C:\lev\STColorCorrection\Data\PROFILE\p3700.csv")) { System.Data.DataSet dsResult = parser.GetDataSet(); profile = dsResult.Tables[0]; } } catch (Exception ex) { Console.WriteLine(ex); } #endregion // allocate temp memory, initialize it, copy to constant memory on the GPU // L 0-21 A 0-41 B 0-45 ProfileStrucuture[, ,] profiles_CPU = new ProfileStrucuture[21, 41, 45]; SampleStructure[,] samples_CPU = new SampleStructure[image_size, 6]; //profile inicialization #region for (int indexL = 0; indexL < 21; indexL++) { for (int indexA = 0; indexA < 41; indexA++) { for (int indexB = 0; indexB < 45; indexB++) { profiles_CPU[indexL, indexA, indexB].L = indexL; profiles_CPU[indexL, indexA, indexB].A = indexA; profiles_CPU[indexL, indexA, indexB].B = indexB; profiles_CPU[indexL, indexA, indexB].Given_R = 0; profiles_CPU[indexL, indexA, indexB].Given_G = 0; profiles_CPU[indexL, indexA, indexB].Given_B = 0; profiles_CPU[indexL, indexA, indexB].ML = 0; profiles_CPU[indexL, indexA, indexB].MA = 0; profiles_CPU[indexL, indexA, indexB].MB = 0; profiles_CPU[indexL, indexA, indexB].MX = 0; profiles_CPU[indexL, indexA, indexB].MY = 0; profiles_CPU[indexL, indexA, indexB].MZ = 0; profiles_CPU[indexL, indexA, indexB].distance = -1.0; profiles_CPU[indexL, indexA, indexB].weight = -1.0; profiles_CPU[indexL, indexA, indexB].isempty = TRUE; profiles_CPU[indexL, indexA, indexB].isMoreAccurateThanOrigin = FALSE; } } } int lvalue, avalue, bvalue; try { for (int i = 1; i < profile.Rows.Count; i++) { lvalue = Convert.ToInt32(profile.Rows[i][0].ToString()); avalue = Convert.ToInt32(profile.Rows[i][1].ToString()); bvalue = Convert.ToInt32(profile.Rows[i][2].ToString()); lvalue = (int)(lvalue * 0.2); avalue = (int)(avalue * 0.2) + 20; bvalue = (int)(bvalue * 0.2) + 22; profiles_CPU[lvalue, avalue, bvalue].L = lvalue; profiles_CPU[lvalue, avalue, bvalue].A = avalue; profiles_CPU[lvalue, avalue, bvalue].B = bvalue; profiles_CPU[lvalue, avalue, bvalue].Given_R = (byte)Convert.ToByte(profile.Rows[i][9].ToString()); profiles_CPU[lvalue, avalue, bvalue].Given_G = (byte)Convert.ToByte(profile.Rows[i][10].ToString()); profiles_CPU[lvalue, avalue, bvalue].Given_B = (byte)Convert.ToByte(profile.Rows[i][11].ToString()); profiles_CPU[lvalue, avalue, bvalue].ML = (double)Convert.ToDouble(profile.Rows[i][3].ToString()); profiles_CPU[lvalue, avalue, bvalue].MA = (double)Convert.ToDouble(profile.Rows[i][4].ToString()); profiles_CPU[lvalue, avalue, bvalue].MB = (double)Convert.ToDouble(profile.Rows[i][5].ToString()); profiles_CPU[lvalue, avalue, bvalue].MX = (double)Convert.ToDouble(profile.Rows[i][6].ToString()); profiles_CPU[lvalue, avalue, bvalue].MY = (double)Convert.ToDouble(profile.Rows[i][7].ToString()); profiles_CPU[lvalue, avalue, bvalue].MZ = (double)Convert.ToDouble(profile.Rows[i][8].ToString()); profiles_CPU[lvalue, avalue, bvalue].isempty = FALSE; } } catch (Exception ex) { Console.WriteLine(ex); } #endregion //grab the colors ProfileStrucuture[, ,] profile_GPU = gpu.CopyToDevice(profiles_CPU); SampleStructure[,] samples_GPU = gpu.CopyToDevice(samples_CPU); //begin execution // capture the start time gpu.StartTimer(); ForeGroundStrucuture[] foregorungRGB_GPU = gpu.CopyToDevice(foregorungRGB_CPU); BackGroundStrucuture[] BackgroundXYZ_GPU = gpu.CopyToDevice(BackgroundXYZ_CPU); //out put ForeGroundStrucuture[] distance_GPU = gpu.Allocate(distance_CPU); // generate a bitmap from our sphere data //Image size: 1024 x 768 dim3 grids = new dim3(24, 675); dim3 threads = new dim3(8, 4); //dim3 grids = new dim3(1, 1); //dim3 threads = new dim3(1, 1); //quick_correct //gpu.Launch(grids, threads, ((Action<GThread, ProfileStrucuture[, ,], ForeGroundStrucuture[], BackGroundStrucuture[], ProfileStrucuture[], SampleStructure[,]>)QuickCorr), profile_GPU, foregorungRGB_GPU, BackgroundXYZ_GPU, distance_GPU, samples_GPU); //quick correct - testing gpu.Launch(grids, threads, ((Action<GThread, ProfileStrucuture[, ,], ForeGroundStrucuture[], BackGroundStrucuture[], ForeGroundStrucuture[], SampleStructure[,]>)Snake), profile_GPU, foregorungRGB_GPU, BackgroundXYZ_GPU, distance_GPU, samples_GPU); // copy our bitmap back from the GPU for display gpu.CopyFromDevice(distance_GPU, distance_CPU); // get stop time, and display the timing results double elapsedTime = gpu.StopTimer(); TestOutput to_return = new TestOutput(); to_return.output_image = distance_CPU; to_return.timeTaken = elapsedTime; Console.WriteLine("Time to generate: {0} ms", elapsedTime); gpu.Free(foregorungRGB_GPU); gpu.Free(BackgroundXYZ_GPU); gpu.Free(distance_GPU); gpu.FreeAll(); return to_return; }
public static void Snake(GThread thread, ProfileStrucuture[, ,] profile_GPU, ForeGroundStrucuture[] foregorungRGB_GPU, BackGroundStrucuture[] BackgroundXYZ_GPU, ForeGroundStrucuture[] ptr, SampleStructure[,] samples) { // map from threadIdx/BlockIdx to pixel position int x = thread.threadIdx.x + thread.blockIdx.x * thread.blockDim.x; int y = thread.threadIdx.y + thread.blockIdx.y * thread.blockDim.y; int offset = x + y * thread.blockDim.x * thread.gridDim.x; double ox = (x - 1.0 / 2.0); double oy = (y - 1.0 / 2.0); // double closestColor = double.MaxValue; double diffL = 0.0; double diffA = 0.0; double diffB = 0.0; //int BestL = 0; //int BestA = 0; //int BestB = 0; //1 - Converts the foreground to how the display shows it ProfileStrucuture foregroundColorToShow = new ProfileStrucuture(); ProfileStrucuture foregroundLAB = ToLAB(foregorungRGB_GPU[offset]); int binL = ((int)Math.Round(foregroundLAB.L / 5.0)) * 5; int binA = ((int)Math.Round(foregroundLAB.A / 5.0)) * 5; int binB = ((int)Math.Round(foregroundLAB.B / 5.0)) * 5; if (binL > 100) binL = 100; if (binA < -86.17385493791946) binA = -85; if (binA > 98.2448002875424) binA = 100; if (binB < -107.8619171648283) binB = -110; if (binB > 94.47705120353054) binB = 95; binL = (int)(binL * 0.2) + 0; binA = (int)(binA * 0.2) + 20; binB = (int)(binB * 0.2) + 22; foregroundColorToShow.ML = profile_GPU[binL, binA, binB].ML; foregroundColorToShow.MA = profile_GPU[binL, binA, binB].MA; foregroundColorToShow.MB = profile_GPU[binL, binA, binB].MB; //1.1 - Extra step for Quick Correction Point3D origin = new Point3D(10.0, 20.0, 22.0); Point3D step = new Point3D(10, 20, 22); //2 - Get the accuracy ProfileStrucuture actualBin = GetProfileBin(origin.X, origin.Y, origin.Z, profile_GPU); if (actualBin.isempty == TRUE) return; BackGroundStrucuture PredictionXYZ = addXYZ_st(actualBin.MX, actualBin.MY, actualBin.MZ, BackgroundXYZ_GPU[offset]); ProfileStrucuture PredictionLAB = XYZtoLAB_st(PredictionXYZ); //diffL = foregroundColorToShow.ML - PredictionLAB.L; //diffA = foregroundColorToShow.MA - PredictionLAB.A; //diffB = foregroundColorToShow.MB - PredictionLAB.B; diffL = PredictionLAB.L - foregroundColorToShow.ML; diffA = PredictionLAB.A - foregroundColorToShow.MA; diffB = PredictionLAB.B - foregroundColorToShow.MB; //diffL = PredictionXYZ.X - foregroundColorToShow.MX; //diffA = PredictionXYZ.Y - foregroundColorToShow.MY; //diffB = PredictionXYZ.Z - foregroundColorToShow.MZ; diffL = diffL * diffL; diffA = diffA * diffA; diffB = diffB * diffB; //originBin.distanceLAB actualBin.distance = Math.Sqrt(diffL + diffA + diffB); //declaring 6 separate samples - CUDA does not support array declaration in kernel device code Point3D top = new Point3D(); Point3D bottom = new Point3D(); Point3D left = new Point3D(); Point3D right = new Point3D(); Point3D forward = new Point3D(); Point3D backward = new Point3D(); int countSamplesClosestThanOrigin = 0; do { //sample 6 bins top.X = origin.X + 1; top.Y = origin.Y; top.Z = origin.Z; bottom.X = origin.X - 1; bottom.Y = origin.Y; bottom.Z = origin.Z; left.X = origin.X; left.Y = origin.Y - 1; left.Z = origin.Z; right.X = origin.X; right.Y = origin.Y + 1; right.Z = origin.Z; forward.X = origin.X; forward.Y = origin.Y; forward.Z = origin.Z - 1; backward.X = origin.X; backward.Y = origin.Y; backward.Z = origin.Z + 1; samples[offset, 0] = GetProfileBinForSample(top.X, top.Y, top.Z, profile_GPU); samples[offset, 1] = GetProfileBinForSample(bottom.X, bottom.Y, bottom.Z, profile_GPU); samples[offset, 2] = GetProfileBinForSample(left.X, left.Y, left.Z, profile_GPU); samples[offset, 3] = GetProfileBinForSample(right.X, right.Y, right.Z, profile_GPU); samples[offset, 4] = GetProfileBinForSample(forward.X, forward.Y, forward.Z, profile_GPU); samples[offset, 5] = GetProfileBinForSample(backward.X, backward.Y, backward.Z, profile_GPU); countSamplesClosestThanOrigin = 0; //calculate color correction for all samples #region for (int index = 0; index < 6; index++) { if (samples[offset, index].isempty == TRUE || samples[offset, index].isempty == 0.0) continue; BackGroundStrucuture temp_XYZ = addXYZ_st(samples[offset, index].MX, samples[offset, index].MY, samples[offset, index].MZ, BackgroundXYZ_GPU[offset]); ProfileStrucuture PredictionlAB = XYZtoLAB_st(temp_XYZ); diffL = PredictionlAB.L - foregroundColorToShow.ML; diffA = PredictionlAB.A - foregroundColorToShow.MA; diffB = PredictionlAB.B - foregroundColorToShow.MB; diffL = diffL * diffL; diffA = diffA * diffA; diffB = diffB * diffB; //curr_distanceLAB samples[offset, index].distance = Math.Sqrt(diffL + diffA + diffB); if (samples[offset, index].distance >= actualBin.distance) { continue; } else { samples[offset, index].isMoreAccurateThanOrigin = (int)TRUE; countSamplesClosestThanOrigin++; } } #endregion if (countSamplesClosestThanOrigin > 0) { //6.1 calculates weights double totalimprovements = 0; for (int index = 0; index < 6; index++) { if (!(samples[offset, index].isMoreAccurateThanOrigin == TRUE)) { continue; } totalimprovements += (actualBin.distance - samples[offset, index].distance); } for (int index = 0; index < 6; index++) { if (!(samples[offset, index].isMoreAccurateThanOrigin == 1)) { continue; } samples[offset, index].weight = ((actualBin.distance - samples[offset, index].distance) / totalimprovements); } //6.2 calculates displacement Point3D displacement = new Point3D(0, 0, 0); for (int index = 0; index < 6; index++) { if (!(samples[offset, index].isMoreAccurateThanOrigin == 1)) { continue; } displacement.X = displacement.X + (samples[offset, index].L - origin.X) * samples[offset, index].weight; displacement.Y = displacement.Y + (samples[offset, index].A - origin.Y) * samples[offset, index].weight; displacement.Z = displacement.Z + (samples[offset, index].B - origin.Z) * samples[offset, index].weight; } if (displacement.X > 0) displacement.X = Math.Ceiling(displacement.X); else displacement.X = Math.Floor(displacement.X); if (displacement.Y > 0) displacement.Y = Math.Ceiling(displacement.Y); else displacement.Y = Math.Floor(displacement.Y); if (displacement.Z > 0) displacement.Z = Math.Ceiling(displacement.Z); else displacement.Z = Math.Floor(displacement.Z); //6.3 pokes new origin Point3D newOriginLoc = new Point3D(); newOriginLoc.X = origin.X + displacement.X; newOriginLoc.Y = origin.Y + displacement.Y; newOriginLoc.Z = origin.Z + displacement.Z; ProfileStrucuture newOriginBin = GetProfileBin(newOriginLoc.X, newOriginLoc.Y, newOriginLoc.Z, profile_GPU); while (newOriginBin.isempty == TRUE) { /////////////////////// round to even missing /////////////////// //6.4 moves half the magnitude in the given direction displacement.X = Math.Round(displacement.X / 2); displacement.Y = Math.Round(displacement.Y / 2); displacement.Z = Math.Round(displacement.Z / 2); newOriginLoc.X = origin.X + displacement.X; newOriginLoc.Y = origin.Y + displacement.Y; newOriginLoc.Z = origin.Z + displacement.Z; newOriginBin = GetProfileBin(newOriginLoc.X, newOriginLoc.Y, newOriginLoc.Z, profile_GPU); } //calclates the accuracy of the posible new origin if (newOriginBin.isempty == TRUE) return; PredictionXYZ = addXYZ_st(newOriginBin.MX, newOriginBin.MY, newOriginBin.MZ, BackgroundXYZ_GPU[offset]); ProfileStrucuture PredictionlAB = XYZtoLAB_st(PredictionXYZ); diffL = PredictionlAB.L - foregroundColorToShow.ML; diffA = PredictionlAB.A - foregroundColorToShow.MA; diffB = PredictionlAB.B - foregroundColorToShow.MB; //diffL = PredictionXYZ.X - foregroundColorToShow.MX; //diffA = PredictionXYZ.Y - foregroundColorToShow.MY; //diffB = PredictionXYZ.Z - foregroundColorToShow.MZ; diffL = diffL * diffL; diffA = diffA * diffA; diffB = diffB * diffB; //originBin.distanceLAB newOriginBin.distance = Math.Sqrt(diffL + diffA + diffB); if ((origin.X == newOriginLoc.X && origin.Y == newOriginLoc.Y && origin.Z == newOriginLoc.Z) || actualBin.distance <= newOriginBin.distance) // it's the same location then just reduces the step countSamplesClosestThanOrigin = 0; else { origin = newOriginLoc; actualBin = newOriginBin; } } } while (countSamplesClosestThanOrigin > 0); ForeGroundStrucuture ValueToReturn = new ForeGroundStrucuture(); ValueToReturn.R = actualBin.Given_R; ValueToReturn.G = actualBin.Given_G; ValueToReturn.B = actualBin.Given_B; ptr[offset] = ValueToReturn; }
public static BackGroundStrucuture RGBToXYZ_St(ForeGroundStrucuture RGB) { // by the formula given the the web page http://www.brucelindbloom.com/index.html [XYZ]=[M][RGB] //In order to properly use this matrix, the RGB values must be linear and in the nominal range [0.0, 1.0]. // RGB values may first need conversion (for example, dividing by 255 and then raising them to a power) // Where M for D65: 0.4124564 0.3575761 0.1804375 //0.2126729 0.7151522 0.0721750 //0.0193339 0.1191920 0.9503041 //// to make rgb values linear red, green, blue values BackGroundStrucuture XYZ = new BackGroundStrucuture(); double rLinear = (double)(RGB.R / 255.0); double gLinear = (double)(RGB.G / 255.0); double bLinear = (double)(RGB.B / 255.0); // convert to a sRGB form //double r = Math.pow((rLinear ), 2.2) ; //double g = Math.pow((gLinear ), 2.2) ; //double b = Math.pow((bLinear ), 2.2) ; double r, g, b; if (rLinear > 0.04045) { r = (double)((double)(rLinear + 0.055) / 1.055); r = Math.Pow(r, (double)2.200000); } else r = (double)(rLinear / 12.92); if (gLinear > 0.04045) { g = (double)((double)(gLinear + 0.055) / 1.055); g = Math.Pow((double)g, (double)2.2); } else g = (double)(gLinear / 12.92); if (bLinear > 0.04045) { b = (double)((double)(bLinear + 0.055) / 1.055); b = Math.Pow((double)b, (double)2.2); } else b = (double)(bLinear / 12.92); XYZ.X = (double)(r * 0.4124564 + g * 0.3575761 + b * 0.1804375); XYZ.Y = (double)(r * 0.2126729 + g * 0.7151522 + b * 0.0721750); XYZ.Z = (double)(r * 0.0193339 + g * 0.1191920 + b * 0.9503041); //if (XYZ.X > 0.9504) // XYZ.X = 0.9504F; //else if (XYZ.X < 0) // XYZ.X = 0; //else // XYZ.X = XYZ.X; //if (XYZ.Y > 1) // XYZ.Y = 1; //else if (XYZ.Y < 0) // XYZ.Y = 0; //else // XYZ.Y = XYZ.Y; //if (XYZ.Z > 1.0888) // XYZ.Z = 1.0888F; //else if (XYZ.Z < 0) // XYZ.Z = 0; //else // XYZ.Z = XYZ.Z; return XYZ; }
public static void Bruteforce(GThread thread, ProfileStrucuture[, ,] profile_GPU, ForeGroundStrucuture[] foregorungRGB_GPU, BackGroundStrucuture[] BackgroundXYZ_GPU, ForeGroundStrucuture[] ptr) { // map from threadIdx/BlockIdx to pixel position int x = thread.threadIdx.x + thread.blockIdx.x * thread.blockDim.x; int y = thread.threadIdx.y + thread.blockIdx.y * thread.blockDim.y; int offset = x + y * thread.blockDim.x * thread.gridDim.x; double ox = (x - 1.0 / 2.0); double oy = (y - 1.0 / 2.0); double closestColor = double.MaxValue; double diffL = 0.0; double diffA = 0.0; double diffB = 0.0; int BestL = 0; int BestA = 0; int BestB = 0; ProfileStrucuture returnBin = new ProfileStrucuture(); ProfileStrucuture foregroundLAB = ToLAB(foregorungRGB_GPU[offset]); int binL = ((int)Math.Round(foregroundLAB.L / 5.0)) * 5; int binA = ((int)Math.Round(foregroundLAB.A / 5.0)) * 5; int binB = ((int)Math.Round(foregroundLAB.B / 5.0)) * 5; if (binL > 100) binL = 100; if (binA < -86.17385493791946) binA = -85; if (binA > 98.2448002875424) binA = 100; if (binB < -107.8619171648283) binB = -110; if (binB > 94.47705120353054) binB = 95; binL = (int)(binL * 0.2) + 0; binA = (int)(binA * 0.2) + 20; binB = (int)(binB * 0.2) + 22; returnBin.ML = profile_GPU[binL, binA, binB].ML; returnBin.MA = profile_GPU[binL, binA, binB].MA; returnBin.MB = profile_GPU[binL, binA, binB].MB; double closestBinDistance; for (int indexL = 0; indexL < 21; indexL++) { for (int indexA = 0; indexA < 41; indexA++) { for (int indexB = 0; indexB < 45; indexB++) { ProfileStrucuture actualBin = profile_GPU[indexL, indexA, indexB]; if (actualBin.isempty == TRUE) continue; BackGroundStrucuture PredictionXYZ = addXYZ_st(actualBin.MX, actualBin.MY, actualBin.MZ, BackgroundXYZ_GPU[offset]); ProfileStrucuture PredictionlAB = XYZtoLAB_st(PredictionXYZ); diffL = PredictionlAB.L - returnBin.ML; diffA = PredictionlAB.A - returnBin.MA; diffB = PredictionlAB.B - returnBin.MB; //diffL = PredictionXYZ.X - returnBin.MX; //diffA = PredictionXYZ.Y - returnBin.MY; //diffB = PredictionXYZ.Z - returnBin.MZ; diffL = diffL * diffL; diffA = diffA * diffA; diffB = diffB * diffB; closestBinDistance = Math.Sqrt(diffL + diffA + diffB); if (closestBinDistance >= closestColor) continue; else { closestColor = closestBinDistance; BestL = indexL; BestA = indexA; BestB = indexB; } } } } ProfileStrucuture return_bin = profile_GPU[BestL, BestA, BestB]; ForeGroundStrucuture ValueToReturn = new ForeGroundStrucuture(); ValueToReturn.R = return_bin.Given_R; ValueToReturn.G = return_bin.Given_G; ValueToReturn.B = return_bin.Given_B; ptr[offset] = ValueToReturn; }
public static TestOutput CorrectColour(ForeGroundStrucuture[] foregorungRGB_CPU, BackGroundStrucuture[] BackgroundXYZ_CPU) { //set these to constant if you want testing //rgb = System.Drawing.Color.FromArgb(65, 108, 20); //X = 0.613829950099918; //Y = 0.938638756488747; //Z = 1.08019833591292; const int image_size = 960 * 540; //cuda intializer CudafyModule km = CudafyModule.TryDeserialize(); if (km == null || !km.TryVerifyChecksums()) { // km = CudafyTranslator.Cudafy((typeof(ForeGroundStrucuture)), (typeof(BackGroundStrucuture)), typeof(Color)); km = CudafyTranslator.Cudafy(typeof(ProfileStrucuture),typeof(ForeGroundStrucuture), typeof(BackGroundStrucuture), typeof(bf)); km.TrySerialize(); } CudafyTranslator.GenerateDebug = true; // cuda or emulator GPGPU gpu = CudafyHost.GetDevice(CudafyModes.Target, CudafyModes.DeviceId); //sGPGPU gpu = CudafyHost.GetDevice(eGPUType.Emulator); gpu.LoadModule(km); Console.WriteLine("Running brute force correction using {0}", gpu.GetDeviceProperties(false).Name); ForeGroundStrucuture[] output_image_CPU = new ForeGroundStrucuture[image_size]; // allocate memory on the GPU for the bitmap (same size as ptr) DataTable profile = new DataTable(); try { // add the csv bin file using (GenericParserAdapter parser = new GenericParserAdapter(@"C:\lev\STColorCorrection\Data\PROFILE\p3700.csv")) { System.Data.DataSet dsResult = parser.GetDataSet(); profile = dsResult.Tables[0]; } } catch(Exception ex) {Console.WriteLine(ex); } // allocate temp memory, initialize it, copy to constant memory on the GPU // L 0-21 A 0-41 B 0-45 ProfileStrucuture[ , , ] profiles_CPU = new ProfileStrucuture[21,41,45]; //ForeGroundStrucuture[] foregorungRGB_CPU = new ForeGroundStrucuture[image_size]; //BackGroundStrucuture[] BackgroundXYZ_CPU = new BackGroundStrucuture[image_size]; for (int indexL = 0; indexL < 21; indexL++) { for (int indexA = 0; indexA < 41; indexA++) { for (int indexB = 0; indexB < 45; indexB++) { profiles_CPU[indexL, indexA, indexB].L = indexL; profiles_CPU[indexL, indexA, indexB].A = indexA; profiles_CPU[indexL, indexA, indexB].B = indexB; profiles_CPU[indexL, indexA, indexB].Given_R = 0; profiles_CPU[indexL, indexA, indexB].Given_G = 0; profiles_CPU[indexL, indexA, indexB].Given_B = 0; profiles_CPU[indexL, indexA, indexB].ML = 0; profiles_CPU[indexL, indexA, indexB].MA = 0; profiles_CPU[indexL, indexA, indexB].MB = 0; profiles_CPU[indexL, indexA, indexB].MX = 0; profiles_CPU[indexL, indexA, indexB].MY = 0; profiles_CPU[indexL, indexA, indexB].MZ = 0; profiles_CPU[indexL, indexA, indexB].isempty = TRUE; profiles_CPU[indexL, indexA, indexB].isMoreAccurateThanOrigin = -1; } } } int lvalue, avalue, bvalue; try { for (int i = 1; i < profile.Rows.Count; i++) { lvalue=Convert.ToInt32 (profile.Rows[i][0].ToString()); avalue = Convert.ToInt32(profile.Rows[i][1].ToString()); bvalue= Convert.ToInt32(profile.Rows[i][2].ToString()); lvalue=(int)(lvalue*0.2); avalue=(int)(avalue*0.2)+20; bvalue=(int)(bvalue*0.2)+22; profiles_CPU[lvalue, avalue, bvalue].L = lvalue; profiles_CPU[lvalue, avalue, bvalue].A = avalue; profiles_CPU[lvalue, avalue, bvalue].B = bvalue; profiles_CPU[lvalue, avalue, bvalue].Given_R = (byte)Convert.ToByte(profile.Rows[i][9].ToString()); profiles_CPU[lvalue, avalue, bvalue].Given_G = (byte)Convert.ToByte(profile.Rows[i][10].ToString()); profiles_CPU[lvalue, avalue, bvalue].Given_B = (byte)Convert.ToByte(profile.Rows[i][11].ToString()); profiles_CPU[lvalue, avalue, bvalue].ML = (double)Convert.ToDouble(profile.Rows[i][3].ToString()); profiles_CPU[lvalue, avalue, bvalue].MA = (double)Convert.ToDouble(profile.Rows[i][4].ToString()); profiles_CPU[lvalue, avalue, bvalue].MB = (double)Convert.ToDouble(profile.Rows[i][5].ToString()); profiles_CPU[lvalue, avalue, bvalue].MX = (double)Convert.ToDouble(profile.Rows[i][6].ToString()); profiles_CPU[lvalue, avalue, bvalue].MY = (double)Convert.ToDouble(profile.Rows[i][7].ToString()); profiles_CPU[lvalue, avalue, bvalue].MZ = (double)Convert.ToDouble(profile.Rows[i][8].ToString()); profiles_CPU[lvalue, avalue, bvalue].isempty = FALSE; } } catch (Exception ex) { Console.WriteLine(ex); } //foreground and background image inicialization #region //try //{ // for (int i = 0; i < 1; i++) // { // foregorungRGB_CPU[i].R = rgb.R; // foregorungRGB_CPU[i].G = rgb.G; // foregorungRGB_CPU[i].B = rgb.B; // BackgroundXYZ_CPU[i].X = X; // BackgroundXYZ_CPU[i].Y = Y; // BackgroundXYZ_CPU[i].Z = Z; // } //} //catch (Exception ex) //{ Console.WriteLine(ex); } #endregion ProfileStrucuture[, ,] profile_GPU = gpu.CopyToDevice(profiles_CPU); // capture the start time gpu.StartTimer(); ForeGroundStrucuture[] foregorungRGB_GPU = gpu.CopyToDevice(foregorungRGB_CPU); BackGroundStrucuture[] BackgroundXYZ_GPU = gpu.CopyToDevice(BackgroundXYZ_CPU); //out put ForeGroundStrucuture[] distance_GPU = gpu.Allocate(output_image_CPU); // generate a bitmap from our sphere data //Image size: 1024 x 768 //dim3 grids = new dim3(1, 1); //dim3 threads = new dim3(1,1); dim3 grids = new dim3(24, 675); dim3 threads = new dim3(8, 4); gpu.Launch(grids, threads, ((Action<GThread, ProfileStrucuture[, ,], ForeGroundStrucuture[], BackGroundStrucuture[], ForeGroundStrucuture[]>)Bruteforce), profile_GPU, foregorungRGB_GPU, BackgroundXYZ_GPU, distance_GPU); //gpu.Launch(grids, threads, ((Action<GThread, ForeGroundStrucuture[], BackGroundStrucuture[], double[]>)Bruteforce), foregorungRGB_GPU, BackgroundXYZ_GPU, distance_GPU); // copy our bitmap back from the GPU for display gpu.CopyFromDevice(distance_GPU, output_image_CPU); // get stop time, and display the timing results double elapsedTime = gpu.StopTimer(); TestOutput to_return = new TestOutput(); to_return.output_image = output_image_CPU; to_return.timeTaken = elapsedTime; //encapsulte the output image into a class //output_image_CPU[0].execution_time = elapsedTime; Console.WriteLine("Time to generate: {0} ms", elapsedTime); gpu.Free(foregorungRGB_GPU); gpu.Free(BackgroundXYZ_GPU); gpu.Free(distance_GPU); gpu.FreeAll(); return to_return; }