 	}
 
 	fwr.close();
-	// End loop and write out data.
-
+
+	//Free the memory and reset the device.
 	cudaFree(d_IC);
 	cudaFree(d_right);
 	cudaFree(d_left);

#define REAL       float
#define TH_DIFF    8.418e-5

__constant__ REAL fo;

__global__ void upTriangle(REAL *IC, REAL *right, REAL *left)
{

	__shared__ REAL temper[64];
	__shared__ REAL sR[32];
	__shared__ REAL sL[32];

	int gid = blockDim.x * blockIdx.x + threadIdx.x; //Global Thread ID
	int tid = threadIdx.x;
	int shft_wr;
	int shft_rd;

	temper[tid] = IC[gid];
	__syncthreads();
	int itr = -1;

	for (int k = 1; k<16; k++)
	{
		shft_wr = (k & 1);
		shft_rd = 32*((shft_wr+1) & 1);

		if (tid <= (31-k) && tid >= k)
		{
			temper[tid + (32*shft_wr)] = fo * (temper[tid+shft_rd-1] + temper[tid+shft_rd+1]) + (1-2.*fo) * temper[tid+shft_rd];
		}

		__syncthreads();

		if (shft_wr)
		{
			sL[k+itr] = temper[k-1];
			sL[k+itr+1] = temper[k];

	else
	{
		sL[tid] = right[blockDim.x*(gridDim.x-1) + tid];
	}

	__syncthreads();

	// Initialize temper. Kind of an unrolled for loop.  This is actually at
	// Timestep 0.
	temper[15] = sL[0];
	temper[16] = sL[1];
	temper[17] = sR[0];
	temper[18] = sR[1];

	//Now we need two counters since we need to use sL and sR EVERY iteration
	//instead of every other iteration and instead of growing smaller with every
	//iteration this grows larger.
	int itr = 2;
	int itr2 = 18;
	//k needs to insert the relevant left right values around the computed values
	//every timestep.  Since it grows larger the loop is reversed.
	for (int k = 17; k>1; k--)
	{
		// This tells you if the current row is the first or second.
