Skip to content

Instantly share code, notes, and snippets.

@haileys
Created April 19, 2016 20:01
Show Gist options
  • Save haileys/db63c008ef87b5f57823c8b210cbc0c9 to your computer and use it in GitHub Desktop.
Save haileys/db63c008ef87b5f57823c8b210cbc0c9 to your computer and use it in GitHub Desktop.
#include <stdio.h>
#include <stdlib.h>
#include <pthread.h>
#include <errno.h>
struct worker_ctx {
pthread_t thr;
size_t n;
size_t stride;
size_t offset;
size_t result;
};
static size_t
calc_part(size_t n, size_t stride, size_t offset)
{
size_t x, y, c = 0, r = n * n;
for (y = offset; y < n; y += stride) {
for (x = 0; x < n; x++) {
if (x * x + y * y < r) {
c++;
}
}
}
return c;
}
static void*
thread_main(void* ptr)
{
struct worker_ctx* ctx = ptr;
ctx->result = calc_part(ctx->n, ctx->stride, ctx->offset);
return NULL;
}
int
main(int argc, const char** argv)
{
size_t n = 0, w = 0, c = 0, i;
if (argc < 3) {
fprintf(stderr, "usage: sqpi n worker_count\n");
return 1;
}
sscanf(argv[1], "%zu", &n);
if (n == 0) {
fprintf(stderr, "n must > 0\n");
return 1;
}
sscanf(argv[2], "%zu", &w);
if (w == 0) {
fprintf(stderr, "worker_count must > 0\n");
return 1;
}
struct worker_ctx* workers = calloc(n, sizeof(*workers));
if (!workers) {
perror("could not allocate workers");
return 1;
}
for (i = 0; i < w; i++) {
workers[i].n = n;
workers[i].stride = w;
workers[i].offset = i;
if (pthread_create(&workers[i].thr, NULL, thread_main, &workers[i])) {
perror("could not spawn worker thread");
return 1;
}
}
for (i = 0; i < w; i++) {
if (pthread_join(workers[i].thr, NULL)) {
perror("could not join worker thread");
return 1;
}
}
for (i = 0; i < n; i++) {
c += workers[i].result;
}
double result = ((double)c / (double)(n * n)) * 4.0;
printf("%lf\n", result);
return 0;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment