1 #ifndef __PROFILE_H_ 2 #define __PROFILE_H_ 3 4 #include <sys/time.h> 5 6 #ifndef PROFILE_MAX_VAR 7 #define PROFILE_MAX_VAR 20 8 #endif 9 10 #ifdef PROFILE_STATIC 11 #define STATIC static 12 #else 13 #define STATIC 14 #endif 15 16 #ifdef PROFILE_ON 17 18 #define PROFILE_LOCK() \ 19 __lock = __sync_lock_test_and_set(&__st_lock, 1) 20 21 #define PROFILE_UNLOCK() \ 22 if (__lock == 0) __sync_lock_release(&__st_lock) 23 24 #define PROFILE_INIT() \ 25 STATIC struct timeval __tv_total_from, __tv_total_to; \ 26 STATIC long __c_total_us = 0, __c_etc_us = 0; \ 27 STATIC long *__var_list[PROFILE_MAX_VAR] = {NULL}; \ 28 STATIC char *__name_list[PROFILE_MAX_VAR] = {NULL}; \ 29 char __lock = 0; \ 30 static char __st_lock = 0 31 32 #define PROFILE_START() \ 33 do { \ 34 if (__lock == 0) gettimeofday(&__tv_total_from, NULL); \ 35 } while (0) 36 37 #define PROFILE_END() \ 38 do {\ 39 if (__lock == 0) { \ 40 gettimeofday(&__tv_total_to, NULL); \ 41 __c_total_us \ 42 += (__tv_total_to.tv_sec - __tv_total_from.tv_sec) * 1000000 \ 43 + (__tv_total_to.tv_usec - __tv_total_from.tv_usec); \ 44 } \ 45 } while (0) 46 47 #define PROFILE_VAR(var) \ 48 STATIC struct timeval __##var##_tv_from, __##var##_tv_to; \ 49 STATIC long __##var##_us = 0; \ 50 STATIC int __iter_##var = -1; \ 51 {if (__lock == 0 && __iter_##var == -1) \ 52 for (__iter_##var = 0; __iter_##var < PROFILE_MAX_VAR; __iter_##var++) \ 53 if (__var_list[__iter_##var] == NULL) { \ 54 __var_list[__iter_##var] = &__##var##_us; \ 55 __name_list[__iter_##var] = (char *)#var; break;}} 56 57 #define PROFILE_FROM(var) \ 58 do { \ 59 if (__lock == 0) \ 60 gettimeofday(&__##var##_tv_from, NULL); \ 61 } while (0) 62 63 #define PROFILE_TO(var) \ 64 do { \ 65 if (__lock == 0) { \ 66 gettimeofday(&__##var##_tv_to, NULL); \ 67 __##var##_us \ 68 += (__##var##_tv_to.tv_sec - __##var##_tv_from.tv_sec) * 1000000 \ 69 + (__##var##_tv_to.tv_usec - __##var##_tv_from.tv_usec); \ 70 } \ 71 } while (0) 72 73 #define PROFILE_PRINT(fp) \ 74 do { int i; \ 75 if (__lock == 0) { \ 76 __c_etc_us = __c_total_us; \ 77 for (i = 0; i < PROFILE_MAX_VAR; i++) \ 78 if (__var_list[i]) __c_etc_us -= *__var_list[i]; \ 79 fprintf(fp, "[PROFILE %s]\n", __func__); \ 80 for (i = 0; i < PROFILE_MAX_VAR; i++) \ 81 if (__var_list[i] != NULL) { \ 82 printf(" : %11.3lf ms (%5.2lf %%)", \ 83 (double)*__var_list[i] / 1000.0, \ 84 100 * (double)*__var_list[i] / (double)__c_total_us); \ 85 printf("\r%s\n", __name_list[i]); \ 86 } \ 87 fprintf(fp, "etc. (includes the overhead) : %11.3lf ms (%5.2lf %%)\n", \ 88 (double)__c_etc_us / 1000.0, \ 89 100 * (double)__c_etc_us / (double)__c_total_us); \ 90 fprintf(fp, "total : %11.3lf ms\n", \ 91 (double)__c_total_us / 1000.0); \ 92 fflush(fp); \ 93 } \ 94 } while (0) 95 96 #else /* PROFILE_ON */ 97 #define PROFILE_LOCK() 98 #define PROFILE_UNLOCK() 99 #define PROFILE_INIT() 100 #define PROFILE_START() 101 #define PROFILE_END() 102 #define PROFILE_VAR(args...) 103 #define PROFILE_FROM(args...) 104 #define PROFILE_TO(args...) 105 #define PROFILE_PRINT(args...) 106 #endif /* PROFILE_ON */ 107 108 #endif /* __PROFILE_H_ */ 109