improve performance
This commit is contained in:
parent
1f4c04541a
commit
7fabe51b4e
1 changed files with 24 additions and 43 deletions
|
@ -7,17 +7,21 @@
|
||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
#include <time.h>
|
#include <time.h>
|
||||||
|
|
||||||
|
#define WIDTH 3840
|
||||||
|
#define HEIGHT 2160
|
||||||
#define ITERATIONS 1000
|
#define ITERATIONS 1000
|
||||||
|
|
||||||
|
#define SCALE (WIDTH / 4.0)
|
||||||
|
#define DX (WIDTH / 2)
|
||||||
|
#define DY (HEIGHT / 2)
|
||||||
|
|
||||||
struct mandelbrot_args {
|
struct mandelbrot_args {
|
||||||
unsigned int *image;
|
unsigned int *image;
|
||||||
double scale;
|
int x, y;
|
||||||
int x, y, dx, dy, width, height;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
struct mandelbrot_args *
|
struct mandelbrot_args *
|
||||||
new_mandelbrot_args(unsigned int *image, double scale, int x, int y, int dx,
|
new_mandelbrot_args(unsigned int *image, int x, int y)
|
||||||
int dy, int width, int height)
|
|
||||||
{
|
{
|
||||||
struct mandelbrot_args *args;
|
struct mandelbrot_args *args;
|
||||||
|
|
||||||
|
@ -27,18 +31,13 @@ new_mandelbrot_args(unsigned int *image, double scale, int x, int y, int dx,
|
||||||
}
|
}
|
||||||
|
|
||||||
args->image = image;
|
args->image = image;
|
||||||
args->scale = scale;
|
|
||||||
args->x = x;
|
args->x = x;
|
||||||
args->y = y;
|
args->y = y;
|
||||||
args->dx = dx;
|
|
||||||
args->dy = dy;
|
|
||||||
args->width = width;
|
|
||||||
args->height = height;
|
|
||||||
|
|
||||||
return args;
|
return args;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int
|
int
|
||||||
mandel(double complex c)
|
mandel(double complex c)
|
||||||
{
|
{
|
||||||
double complex z = 0.0;
|
double complex z = 0.0;
|
||||||
|
@ -50,13 +49,13 @@ mandel(double complex c)
|
||||||
return i;
|
return i;
|
||||||
}
|
}
|
||||||
|
|
||||||
static double complex
|
double complex
|
||||||
toc(int x, int y, int dx, int dy, double scale)
|
toc(int x, int y, int dx, int dy, double scale)
|
||||||
{
|
{
|
||||||
return ((x - dx) + I * (y - dy)) / scale;
|
return ((x - dx) + I * (y - dy)) / scale;
|
||||||
}
|
}
|
||||||
|
|
||||||
static unsigned int
|
unsigned int
|
||||||
torgb(int n)
|
torgb(int n)
|
||||||
{
|
{
|
||||||
unsigned char r, g, b;
|
unsigned char r, g, b;
|
||||||
|
@ -100,18 +99,14 @@ draw_pixel(void *closure, struct scheduler *s)
|
||||||
{
|
{
|
||||||
struct mandelbrot_args *args = (struct mandelbrot_args *)closure;
|
struct mandelbrot_args *args = (struct mandelbrot_args *)closure;
|
||||||
unsigned int *image = args->image;
|
unsigned int *image = args->image;
|
||||||
double scale = args->scale;
|
|
||||||
int x = args->x;
|
int x = args->x;
|
||||||
int y = args->y;
|
int y = args->y;
|
||||||
int dx = args->dx;
|
|
||||||
int dy = args->dy;
|
|
||||||
int width = args->width;
|
|
||||||
|
|
||||||
(void)s; // pas de nouvelle tâche dans le scheduler
|
(void)s; // pas de nouvelle tâche dans le scheduler
|
||||||
|
|
||||||
free(closure);
|
free(closure);
|
||||||
|
|
||||||
pixel(image, scale, x, y, dx, dy, width);
|
pixel(image, SCALE, x, y, DX, DY, WIDTH);
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
|
@ -119,32 +114,24 @@ draw(void *closure, struct scheduler *s)
|
||||||
{
|
{
|
||||||
struct mandelbrot_args *args = (struct mandelbrot_args *)closure;
|
struct mandelbrot_args *args = (struct mandelbrot_args *)closure;
|
||||||
unsigned int *image = args->image;
|
unsigned int *image = args->image;
|
||||||
double scale = args->scale;
|
|
||||||
int dx = args->dx;
|
|
||||||
int dy = args->dy;
|
|
||||||
int width = args->width;
|
|
||||||
int height = args->height;
|
|
||||||
|
|
||||||
free(closure);
|
free(closure);
|
||||||
|
|
||||||
for(int y = 0; y < height; y++) {
|
for(int y = args->y; y < HEIGHT; y++) {
|
||||||
for(int x = 0; x < width; x++) {
|
for(int x = args->x; x < WIDTH; x++) {
|
||||||
int rc = sched_spawn(
|
int rc =
|
||||||
draw_pixel,
|
sched_spawn(draw_pixel, new_mandelbrot_args(image, x, y), s);
|
||||||
new_mandelbrot_args(image, scale, x, y, dx, dy, width, height),
|
|
||||||
s);
|
|
||||||
assert(rc >= 0);
|
assert(rc >= 0);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
draw_serial(unsigned int *image, double scale, int dx, int dy, int width,
|
draw_serial(unsigned int *image)
|
||||||
int height)
|
|
||||||
{
|
{
|
||||||
for(int y = 0; y < height; y++) {
|
for(int y = 0; y < HEIGHT; y++) {
|
||||||
for(int x = 0; x < width; x++) {
|
for(int x = 0; x < WIDTH; x++) {
|
||||||
pixel(image, scale, x, y, dx, dy, width);
|
pixel(image, SCALE, x, y, DX, DY, WIDTH);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -156,13 +143,9 @@ benchmark_mandelbrot(int serial, int nthreads)
|
||||||
struct timespec begin, end;
|
struct timespec begin, end;
|
||||||
double delay;
|
double delay;
|
||||||
int rc;
|
int rc;
|
||||||
int width = 3840;
|
int size = WIDTH * HEIGHT;
|
||||||
int height = 2160;
|
|
||||||
double scale = width / 4.0;
|
|
||||||
int dx = width / 2;
|
|
||||||
int dy = height / 2;
|
|
||||||
|
|
||||||
if(!(image = malloc(width * height * sizeof(unsigned int)))) {
|
if(!(image = malloc(size * sizeof(unsigned int)))) {
|
||||||
perror("Image allocation");
|
perror("Image allocation");
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
@ -170,11 +153,9 @@ benchmark_mandelbrot(int serial, int nthreads)
|
||||||
clock_gettime(CLOCK_MONOTONIC, &begin);
|
clock_gettime(CLOCK_MONOTONIC, &begin);
|
||||||
|
|
||||||
if(serial) {
|
if(serial) {
|
||||||
draw_serial(image, scale, dx, dy, width, height);
|
draw_serial(image);
|
||||||
} else {
|
} else {
|
||||||
rc = sched_init(
|
rc = sched_init(nthreads, size, draw, new_mandelbrot_args(image, 0, 0));
|
||||||
nthreads, width * height, draw,
|
|
||||||
new_mandelbrot_args(image, scale, 0, 0, dx, dy, width, height));
|
|
||||||
assert(rc >= 0);
|
assert(rc >= 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Reference in a new issue