Significant performance hit after spawning dummy thread unrelated to task, in C

Viewed 133

I am working on a C program to generate graphs to do with Ramsey Theory, and I'm currently refining my multithreading performance. At some point I decided to just do a sanity check and make sure that my multi-threaded implementation, when told to run with only 1 thread, is at least not slower than my original implementation.

It turns out it was running about 50% slower. A lot of trial and error later I managed to get it to the following state:

void * blah(){
   printf("Hello, this is thread\n");
}

void clean(){
   //Set up function

   pthread_t tid;
   pthread_create(&tid, NULL, blah, NULL);

   //Do computationally expensive stuff in the current thread
}

As shown above, the program takes 42 seconds with the first data set, and 767 with the other. If I comment out the pthread_create call, the same exact program processes the first data set in 30 seconds and the second in 528 seconds.

I've tried looking for solutions and found a lot of great answers to do with false sharing and cache thrashing etc. When running the multithreaded version with 2, 3, or 4 threads I do see that each further thread runs a little slower, but what I cannot understand is why spawning even a single unrelated thread kills performance so much.

Even spawning a dozen copies of the same blah thread in this reduced case results in the exact same performance penalty. I even tried again without the -O3 compile flag and the same proportional slowdown was there, albeit a little less extreme. The only thing that might have to do with it that I haven't tried yet is to compile and run on a different system.

Any clues would be greatly appreciated.

Edit:

After taking into account the suggestions from the comments, it appears I have found the problem. @ninjalj suggested that it might be to do with malloc locks, so I wrote the following test code that runs in 19 seconds without the call to pthread_create, and 32 seconds with it, at least on my machine.

#include <stdlib.h>
#include <stdio.h>
#include <time.h>
#include <pthread.h>

#define CALLS 10000

void * dummy(void * args){
  printf("Hello, this is thread\n");
}

int main(int argc, char ** argv){
  pthread_t tid;
  pthread_create(&tid, NULL, dummy, NULL);

  time_t start, end;
  start = time(NULL);

  int * memory;
  for(int i = 0; i < CALLS*10; i ++){
    for(int j = 0; j < CALLS; j++){
      memory = malloc(10);
      free(memory);
    }
  }

  end = time(NULL);
  printf("That took %d s\n", end - start);
}
0 Answers
Related