more raytrace_worker optimization and cleaning pyrit
authorRadek Brich <radek.brich@devl.cz>
Sat, 29 Mar 2008 10:56:56 +0100
branchpyrit
changeset 54 dbe3c7a4e0f0
parent 53 228cb8bfdd54
child 55 f6d75ae82c88
more raytrace_worker optimization and cleaning
include/raytracer.h
src/raytracer.cc
--- a/include/raytracer.h	Sat Mar 29 02:17:22 2008 +0100
+++ b/include/raytracer.h	Sat Mar 29 10:56:56 2008 +0100
@@ -63,8 +63,8 @@
 	Vector3 SphereDistribute(int i, int n, Float extent, Vector3 &normal);
 
 	Sample *sample_queue;
-	int sample_queue_max, sample_queue_pos, sample_queue_count;
-	bool sample_queue_end;
+	int sample_queue_pos, sample_queue_size, sample_queue_count;
+	bool end_of_samples;
 	pthread_mutex_t sample_queue_mutex, sampler_mutex;
 	pthread_cond_t sample_queue_cond, worker_ready_cond;
 
--- a/src/raytracer.cc	Sat Mar 29 02:17:22 2008 +0100
+++ b/src/raytracer.cc	Sat Mar 29 10:56:56 2008 +0100
@@ -395,9 +395,10 @@
 
 void *Raytracer::raytrace_worker(void *d)
 {
+	static const int my_queue_size = 32;
 	Raytracer *rt = (Raytracer*)d;
-	Sample my_queue[80];
-	Colour my_colours[80];
+	Sample my_queue[my_queue_size];
+	Colour my_colours[my_queue_size];
 	int my_count;
 	Ray ray;
 	for (;;)
@@ -407,7 +408,7 @@
 
 		while (rt->sample_queue_count == 0)
 		{
-			if (rt->sample_queue_end)
+			if (rt->end_of_samples)
 			{
 				dbgmsg(4, "T thread [%d] exiting\n", pthread_self());
 				pthread_mutex_unlock(&rt->sample_queue_mutex);
@@ -416,18 +417,22 @@
 			pthread_cond_wait(&rt->sample_queue_cond, &rt->sample_queue_mutex);
 		}
 
-		if (rt->sample_queue_count >= 80)
-			my_count = 80;
+		if (rt->sample_queue_count >= my_queue_size)
+			my_count = my_queue_size;
 		else
 			my_count = rt->sample_queue_count;
 		rt->sample_queue_count -= my_count;
 
-		for (int i = 0; i < my_count; i++)
+		// copy samples to local queue
+		if (rt->sample_queue_pos+my_count >= rt->sample_queue_size)
 		{
-			my_queue[i] = rt->sample_queue[rt->sample_queue_pos++];
-			if (rt->sample_queue_pos > rt->sample_queue_max)
-				rt->sample_queue_pos = 0;
+			memcpy(my_queue, rt->sample_queue+rt->sample_queue_pos,
+				(rt->sample_queue_size - rt->sample_queue_pos)*sizeof(Sample));
+			my_count -= rt->sample_queue_size - rt->sample_queue_pos;
+			rt->sample_queue_pos = 0;
 		}
+		memcpy(my_queue, rt->sample_queue+rt->sample_queue_pos,
+			my_count*sizeof(Sample));
 
 		pthread_mutex_unlock(&rt->sample_queue_mutex);
 
@@ -451,11 +456,15 @@
 	if (!sampler || !camera || !top)
 		return;
 
-	sample_queue_end = false;
-	sample_queue_max = 2000;
-	sample_queue = new Sample [sample_queue_max+1];
+	static const int sample_queue_size = 2000;
+	sample_queue = new Sample [sample_queue_size+1];
 	sample_queue_pos = 0;
 	sample_queue_count = 0;
+	end_of_samples = false;
+	static const int my_count_max = 512;
+	int  my_count, my_pos = 0;
+	int sampnum = 0, sampdone;
+	bool more_samples;
 
 	// create workers
 	dbgmsg(1, "* running %d threads\n", num_threads);
@@ -472,12 +481,8 @@
 	dbgmsg(1, "* raytracing...\n");
 	dbgmsg(2, "-  0%% done");
 
+	pthread_mutex_lock(&sampler_mutex);
 	sampler->init();
-	int sampnum = 0, sampdone;
-	int my_pos = 0, my_count;
-	bool more_samples;
-
-	pthread_mutex_lock(&sampler_mutex);
 	while ( (sampnum = sampler->initSampleSet()) > 0 )
 	{
 		sampdone = 0;
@@ -487,9 +492,9 @@
 			while ( more_samples = sampler->nextSample(&sample_queue[my_pos++]) )
 			{
 				my_count++;
-				if (my_count >= 1000)
+				if (my_count >= my_count_max)
 					break;
-				if (my_pos > sample_queue_max)
+				if (my_pos >= sample_queue_size)
 					my_pos = 0;
 			}
 			if (!more_samples)
@@ -500,7 +505,7 @@
 			sample_queue_count += my_count;
 
 			// wait for workers if there is enough samples ready on queue
-			while (sample_queue_count > 1000)
+			while (sample_queue_count > my_count_max)
 			{
 				pthread_cond_signal(&sample_queue_cond);
 				pthread_cond_wait(&worker_ready_cond, &sample_queue_mutex);
@@ -521,7 +526,7 @@
 	dbgmsg(2, "- waiting for threads to finish\n");
 
 	pthread_mutex_lock(&sample_queue_mutex);
-	sample_queue_end = true;
+	end_of_samples = true;
 	while (sample_queue_count)
 	{
 		pthread_cond_broadcast(&sample_queue_cond);