ether: Add a field for the driver_name
[akaros.git] / tests / pthread_barrier_test.c
index ce7e806..dd2d303 100644 (file)
@@ -1,44 +1,78 @@
-#include <rstdio.h>
+#include <parlib/stdio.h>
 #include <pthread.h>
 #include <stdlib.h>
-#include <parlib.h>
+#include <parlib/parlib.h>
 #include <unistd.h>
+#include <sys/time.h>
 
-pthread_mutex_t lock = PTHREAD_MUTEX_INITIALIZER;
-//#define printf_safe(...) {}
-#define printf_safe(...) \
-       pthread_mutex_lock(&lock); \
-       printf(__VA_ARGS__); \
-       pthread_mutex_unlock(&lock);
-
-#define NUM_TEST_THREADS 32
-pthread_t my_threads[NUM_TEST_THREADS];
-void *my_retvals[NUM_TEST_THREADS];
 pthread_barrier_t barrier;
 
-void *thread(void* arg)
+#define MAX_NR_TEST_THREADS 100000
+int nr_threads = 100;
+int nr_loops = 10000;
+int nr_vcores = 0;
+
+pthread_t *my_threads;
+void **my_retvals;
+bool run_barriertest = FALSE;
+
+void *thread(void *arg)
 {      
-       for(int i=0; i<NUM_TEST_THREADS; i++) {
-               //printf_safe("[A] pthread %d on vcore %d\n", pthread_self()->id, vcore_id());
+       while (!run_barriertest)
+               cpu_relax();
+       for(int i = 0; i < nr_loops; i++) {
                pthread_barrier_wait(&barrier);
        }
-       return (void*)(pthread_self()->id);
+       return (void*)(long)pthread_self()->id;
 }
 
 int main(int argc, char** argv) 
 {
-       pthread_barrier_init(&barrier, NULL, NUM_TEST_THREADS);
-       #define NUM_ITERATIONS 5000
-       for(int j=0; j<NUM_ITERATIONS; j++) {
-//     while (1) {
-               for (int i = 1; i <= NUM_TEST_THREADS; i++) {
-                       pthread_create(&my_threads[i-1], NULL, &thread, NULL);
-               }
-               for (int i = 1; i <= NUM_TEST_THREADS; i++) {
-                       pthread_join(my_threads[i-1], &my_retvals[i-1]);
+       struct timeval start_tv = {0};
+       struct timeval end_tv = {0};
+       long usec_diff;
+       if (argc > 1)
+               nr_threads = strtol(argv[1], 0, 10);
+       if (argc > 2)
+               nr_loops = strtol(argv[2], 0, 10);
+       if (argc > 3)
+               nr_vcores = strtol(argv[3], 0, 10);
+       printf("Running %d threads for %d iterations on %d vcores\n",
+              nr_threads, nr_loops, nr_vcores);
+       nr_threads = MIN(nr_threads, MAX_NR_TEST_THREADS);
+       my_threads = malloc(sizeof(pthread_t) * nr_threads);
+       my_retvals = malloc(sizeof(void*) * nr_threads);
+       if (!(my_retvals && my_threads))
+               perror("Init threads/malloc");
+       if (nr_vcores) {
+               /* Only do the vcore trickery if requested */
+               parlib_never_yield = TRUE;
+               pthread_mcp_init();                                     /* gives us one vcore */
+               vcore_request_total(nr_vcores);
+               parlib_never_vc_request = TRUE;
+               for (int i = 0; i < nr_vcores; i++) {
+                       printd("Vcore %d mapped to pcore %d\n", i,
+                                  __procinfo.vcoremap[i].pcoreid);
                }
-               printf("Iteration %d of %d\n", j, NUM_ITERATIONS);
        }
+       pthread_barrier_init(&barrier, NULL, nr_threads);
+       for (int i = 0; i < nr_threads; i++) {
+               pthread_create(&my_threads[i], NULL, &thread, NULL);
+       }
+       if (gettimeofday(&start_tv, 0))
+               perror("Start time error...");
+       run_barriertest = TRUE;
+       for (int i = 0; i < nr_threads; i++) {
+               pthread_join(my_threads[i], &my_retvals[i]);
+       }
+       if (gettimeofday(&end_tv, 0))
+               perror("End time error...");
+       pthread_barrier_destroy(&barrier);
+       usec_diff = (end_tv.tv_sec - start_tv.tv_sec) * 1000000 +
+                   (end_tv.tv_usec - start_tv.tv_usec);
+       printf("Done: %d threads, %d loops, %d vcores\n",
+              nr_threads, nr_loops, nr_vcores);
+       printf("Time to run: %d usec, %f usec per barrier\n", usec_diff,
+              (float)usec_diff / nr_loops);
        pthread_barrier_destroy(&barrier);
-       sys_proc_destroy(getpid(), 0);
 }