implemented multithreading, but with mutex. will mit atomic operations optimieren
This commit is contained in:
+7
-1
@@ -9,6 +9,8 @@
|
|||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
#include "interface.h"
|
#include "interface.h"
|
||||||
#include "helper.h"
|
#include "helper.h"
|
||||||
|
#include <time.h>
|
||||||
|
#include <stdio.h>
|
||||||
|
|
||||||
void example_color(int width, int height, int channels, unsigned char **image) {
|
void example_color(int width, int height, int channels, unsigned char **image) {
|
||||||
for (int i = 0; i < height * width; i++) {
|
for (int i = 0; i < height * width; i++) {
|
||||||
@@ -113,7 +115,11 @@ void exampleCornell( int width, int height, int channels, unsigned char **image)
|
|||||||
objectList[18] = (object){1, &(makroObj3.quad6), 0};
|
objectList[18] = (object){1, &(makroObj3.quad6), 0};
|
||||||
|
|
||||||
|
|
||||||
|
clock_t startTime = clock();
|
||||||
displaySzene(objectList, objectCount, cam1, width, height, channels, image);
|
displaySzene(objectList, objectCount, cam1, width, height, channels, image);
|
||||||
|
clock_t endTime = clock();
|
||||||
|
double elapsedTime = (endTime - startTime)/(double)CLOCKS_PER_SEC;
|
||||||
|
printf("%.3lf\n", elapsedTime);
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
+67
-24
@@ -9,6 +9,57 @@
|
|||||||
#include "raytrace.h"
|
#include "raytrace.h"
|
||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
#include "helper.h"
|
#include "helper.h"
|
||||||
|
#include <pthread.h>
|
||||||
|
#define WORKTHREADSIZE 32
|
||||||
|
|
||||||
|
void* renderPixel(RenderArgs *arg, int pixelId) {
|
||||||
|
RenderArgs *args = (RenderArgs*)arg;
|
||||||
|
int step = pixelId * args->channels;
|
||||||
|
int x = pixelId % args->width;
|
||||||
|
int y = pixelId / args->width;
|
||||||
|
RGBA pixelColor;
|
||||||
|
|
||||||
|
vec3 *pixelOrigin = (vec3 *)malloc(sizeof(vec3));
|
||||||
|
*pixelOrigin = vec3Add(*args->screenTopLeft,
|
||||||
|
vec3Add(
|
||||||
|
vec3Scale(*args->vecPixelStepX, x),
|
||||||
|
vec3Scale(*args->vecPixelStepY, y)
|
||||||
|
)
|
||||||
|
);
|
||||||
|
|
||||||
|
ray *lightRay = (ray *)malloc(sizeof(ray));;
|
||||||
|
lightRay->origin = args->cam1->origin;
|
||||||
|
|
||||||
|
lightRay->direction = vec3Normalize(vec3Subtract(*pixelOrigin, args->cam1->origin));
|
||||||
|
|
||||||
|
pixelColor = getPixelColor(args->objectList,args->objectCount, lightRay);
|
||||||
|
free(pixelOrigin);
|
||||||
|
free(lightRay);
|
||||||
|
|
||||||
|
(*args->image)[step] = (int)(pixelColor.r * 255.0);
|
||||||
|
(*args->image)[step+1] = (int)(pixelColor.g * 255.0);
|
||||||
|
(*args->image)[step+2] = (int)(pixelColor.b * 255.0);
|
||||||
|
if (args->channels == 4) {
|
||||||
|
(*args->image)[step+3] = 255;
|
||||||
|
}
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
void *workerLoop(void *arg) {
|
||||||
|
RenderArgs *args = (RenderArgs*)arg;
|
||||||
|
|
||||||
|
while (1) {
|
||||||
|
pthread_mutex_lock(&args->mutexKey);
|
||||||
|
int pixelId = args->nextPixelId;
|
||||||
|
args->nextPixelId++;
|
||||||
|
pthread_mutex_unlock(&args->mutexKey);
|
||||||
|
|
||||||
|
if (pixelId >= args->pixelCount) break;
|
||||||
|
|
||||||
|
renderPixel(args, pixelId);
|
||||||
|
}
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
void displaySzene(object objectList[], int objectCount, camera cam1, int width, int height, int channels, unsigned char **image) {
|
void displaySzene(object objectList[], int objectCount, camera cam1, int width, int height, int channels, unsigned char **image) {
|
||||||
const vec3 worldUp = (vec3){0, 1, 0};
|
const vec3 worldUp = (vec3){0, 1, 0};
|
||||||
@@ -24,34 +75,26 @@ void displaySzene(object objectList[], int objectCount, camera cam1, int width,
|
|||||||
double pixelStepY = cam1.height / cam1.resolutionY;
|
double pixelStepY = cam1.height / cam1.resolutionY;
|
||||||
vec3 vecPixelStepX = vec3Scale(screenX, pixelStepX);
|
vec3 vecPixelStepX = vec3Scale(screenX, pixelStepX);
|
||||||
vec3 vecPixelStepY = vec3Scale(screenY, pixelStepY);
|
vec3 vecPixelStepY = vec3Scale(screenY, pixelStepY);
|
||||||
for (int i = 0; i < height * width; i++) {
|
|
||||||
int step = i *channels;
|
|
||||||
int x = i % width;
|
|
||||||
int y = i / width;
|
|
||||||
RGBA pixelColor;
|
|
||||||
|
|
||||||
vec3 *pixelOrigin = (vec3 *)malloc(sizeof(vec3));
|
pthread_t *threadIdList = (pthread_t *)malloc(sizeof(pthread_t) * WORKTHREADSIZE);
|
||||||
*pixelOrigin = vec3Add(screenTopLeft,
|
|
||||||
vec3Add(
|
|
||||||
vec3Scale(vecPixelStepX, x),
|
|
||||||
vec3Scale(vecPixelStepY, y)
|
|
||||||
)
|
|
||||||
);
|
|
||||||
|
|
||||||
ray *lightRay = (ray *)malloc(sizeof(ray));;
|
|
||||||
lightRay->origin = cam1.origin;
|
|
||||||
|
|
||||||
lightRay->direction = vec3Normalize(vec3Subtract(*pixelOrigin, cam1.origin));
|
|
||||||
|
|
||||||
pixelColor = getPixelColor(objectList,objectCount, lightRay);
|
RenderArgs *args = (RenderArgs*)malloc(sizeof(RenderArgs));
|
||||||
free(pixelOrigin);
|
*args = (RenderArgs){objectList, objectCount, width, channels, &screenTopLeft, &vecPixelStepX, &vecPixelStepY, &cam1, image, 0, 0,width * height};
|
||||||
free(lightRay);
|
pthread_mutex_init(&args->mutexKey, NULL);
|
||||||
|
//pthread_t threadId;
|
||||||
(*image)[step] = (int)(pixelColor.r * 255.0);
|
for (int i = 0; i < WORKTHREADSIZE; i++) {
|
||||||
(*image)[step+1] = (int)(pixelColor.g * 255.0);
|
pthread_create(&(threadIdList[i]), NULL, workerLoop, args);
|
||||||
(*image)[step+2] = (int)(pixelColor.b * 255.0);
|
|
||||||
if (channels == 4) {
|
|
||||||
(*image)[step+3] = 255;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//renderPixel(i, objectList, objectCount, width, channels, &screenTopLeft, &vecPixelStepX, &vecPixelStepY, &cam1, image);
|
||||||
|
|
||||||
|
for (int i = 0; i < WORKTHREADSIZE; i++) {
|
||||||
|
pthread_join(threadIdList[i], NULL);
|
||||||
}
|
}
|
||||||
|
pthread_mutex_destroy(&args->mutexKey);
|
||||||
|
free(threadIdList);
|
||||||
|
free(args);
|
||||||
}
|
}
|
||||||
+1
-1
@@ -8,7 +8,7 @@
|
|||||||
#include <math.h>
|
#include <math.h>
|
||||||
#define epsilon 1e-8
|
#define epsilon 1e-8
|
||||||
#define RAYSPERPIXEL 100
|
#define RAYSPERPIXEL 100
|
||||||
#define lightBounces 5
|
#define lightBounces 6
|
||||||
#define GLOBALILLUMINATION 0.3
|
#define GLOBALILLUMINATION 0.3
|
||||||
enum objectType {
|
enum objectType {
|
||||||
SPHERETYPE,
|
SPHERETYPE,
|
||||||
|
|||||||
@@ -1,4 +1,5 @@
|
|||||||
#pragma once
|
#pragma once
|
||||||
|
#include <pthread.h>
|
||||||
struct vec3 {
|
struct vec3 {
|
||||||
double x, y, z;
|
double x, y, z;
|
||||||
};
|
};
|
||||||
@@ -56,3 +57,19 @@ struct object {
|
|||||||
struct cube {
|
struct cube {
|
||||||
quad quad1,quad2,quad3,quad4,quad5,quad6;
|
quad quad1,quad2,quad3,quad4,quad5,quad6;
|
||||||
}; typedef struct cube cube;
|
}; typedef struct cube cube;
|
||||||
|
|
||||||
|
typedef struct {
|
||||||
|
//int pixelId;
|
||||||
|
object *objectList;
|
||||||
|
int objectCount;
|
||||||
|
int width;
|
||||||
|
int channels;
|
||||||
|
vec3 *screenTopLeft;
|
||||||
|
vec3 *vecPixelStepX;
|
||||||
|
vec3 *vecPixelStepY;
|
||||||
|
camera *cam1;
|
||||||
|
unsigned char **image;
|
||||||
|
int nextPixelId;
|
||||||
|
pthread_mutex_t mutexKey;
|
||||||
|
int pixelCount;
|
||||||
|
} RenderArgs;
|
||||||
Reference in New Issue
Block a user