pthread_cond_signal耗时分析
【问题描述】
平均调用要3us
【内部耗时】
主要是futex_wait系统调用
【ftrace】
参考https://blog.csdn.net/weixin_44410537/article/details/103587609
sudo trace-cmd record -p function_graph -P 25314
sudo trace-cmd report
【测试代码】
#include<stdio.h> #include<unistd.h> #include<stdlib.h> #include<string.h> #include "sys/time.h" #include <stdio.h> #include <pthread.h> //#define TOTAL_COUNT (1000 * 1000 * 10) #define TOTAL_COUNT (1000 * 1000 * 10 ) #define NUM_Threads 10 #define COUNT (TOTAL_COUNT/NUM_Threads) #define PRODUCE_COUNT 18000 #define AVERAGE_PRODUCE_COUNT (PRODUCE_COUNT/NUM_Threads) #define je_malloc malloc #define je_free free //#include <jemalloc/jemalloc.h> pthread_cond_t cond; pthread_mutex_t qlock; static int producer_index=0; static int consumer_index=0; typedef unsigned long long uint64; #define MIN(A, B) ((B) < (A) ? (B) : (A)) #define MAX(A, B) ((B) > (A) ? (B) : (A)) uint64 us_clock_now(){ struct timeval st; gettimeofday(&st, NULL); return st.tv_sec * 1000 * 1000 + st.tv_usec; } #define TIME_BEGIN(name) uint64 __##name##begin = us_clock_now(); #define TIME_END(name, print_interval_us) \ do { \ static __thread uint64 __##name##total = 0; \ static __thread uint64 __##name##count = 0; \ static __thread uint64 __##name##min = 1000000000000; \ static __thread uint64 __##name##max = 0; \ static __thread uint64 __##name##pre_total = 0; \ static __thread uint64 __##name##pre_count = 0; \ static __thread uint64 __##name##log_time = 0; \ uint64 current = (us_clock_now() - __##name##begin);\ __##name##min = MIN(current, __##name##min); \ __##name##max = MAX(current, __##name##max); \ __##name##total += current; \ __##name##count++; \ if (us_clock_now() - __##name##log_time > print_interval_us) \ { \ __##name##log_time = us_clock_now(); \ uint64 __##name##this_total = __##name##total - __##name##pre_total; \ uint64 __##name##this_count = __##name##count - __##name##pre_count; \ __##name##pre_total = __##name##total; \ __##name##pre_count = __##name##count; \ if (__##name##this_count > 1) { \ printf("[TIME=%llu][%ld]%-30s,count:%10llu,avg:%10llu(us), min:%llu,max:%llu, total:%10llu(us)\n", \ us_clock_now()/1000000,pthread_self(), \ #name, __##name##this_count, \ __##name##this_count == 0 ? 0 :__##name##this_total / __##name##this_count, __##name##min, __##name##max, __##name##this_total); \ } \ __##name##min=1000000000000; \ __##name##max = 0;\ } \ } while (0); void *PrintHello(void *arg) { printf("producer_begin\n"); while(1){ TIME_BEGIN(pthread_cond_signal); pthread_cond_signal(&cond); TIME_END(pthread_cond_signal, 1000 *1000); usleep(1); } return 0; } void *Consumer(void *arg) { printf("Consumer_begin\n"); while(1){ // TIME_BEGIN(test_consumer); pthread_cond_wait(&cond, &qlock); // usleep(10); // TIME_END(test_consumer, 1000 *1000); } return 0; } int main(){ pthread_t producer; int i=0; int ret = pthread_create(&producer, NULL, PrintHello, (void *)i); pthread_t consumer; ret = pthread_create(&consumer, NULL, Consumer, (void *)i); void *a1; pthread_join(producer,&a1); return 0; }