Mam dziwny problem. Mam następujący kod:pthread_cond_timedwait wraca natychmiast
dbg("condwait: timeout = %d, %d\n",
abs_timeout->tv_sec, abs_timeout->tv_nsec);
ret = pthread_cond_timedwait(&q->q_cond, &q->q_mtx, abs_timeout);
if (ret == ETIMEDOUT)
{
dbg("cond timed out\n");
return -ETIMEDOUT;
}
dbg
połączeń gettimeofday
przed każdym wierszu i poprzedza wiersz z czasem. Wynika to w następujący wynik:
7.991151: condwait: timeout = 5, 705032704
7.991158: cond timed out
Jak widać, tylko 7 mikrosekund przekazywane pomiędzy dwoma liniami debugowania, jeszcze pthread_cond_timedwait
powrócił ETIMEDOUT
. Jak to się może stać? Próbowałem nawet ustawić zegar na coś innego podczas inicjowania zmiennej cond:
int ret;
ret = pthread_condattr_init(&attributes);
if (ret != 0) printf("CONDATTR INIT FAILED: %d\n", ret);
ret = pthread_condattr_setclock(&attributes, CLOCK_REALTIME);
if (ret != 0) printf("SETCLOCK FAILED: %d\n", ret);
ret = pthread_cond_init(&q->q_cond, &attributes);
if (ret != 0) printf("COND INIT FAILED: %d\n", ret);
(żaden z komunikatów o błędach nie został wydrukowany). Próbowałem zarówno CLOCK_REALTIME
i CLOCK_MONOTONIC
.
Ten kod jest częścią kolejki blokującej. Potrzebuję funkcjonalności takiej, że jeśli nic nie zostanie umieszczone w tej kolejce w ciągu 5 sekund, dzieje się coś innego. Muteks i cond są inicjowane, ponieważ kolejka blokująca działa dobrze, jeśli nie używam pthread_cond_timedwait
.
Och, mam. Możesz użyć pthread_get_expiration_np(), aby dowiedzieć się, jaki jest czas abs. – Claudiu
@ Claudiu pthread_get_expiration_np() nie jest dostępny na moim GNU/Linux. Zamiast tego musiałem: 'timeval now; gettimeofday (i teraz, NULL); long int abstime_ns_large = now.tv_usec * 1000 + delay_ns; timespec abstime = {teraz.tv_sec + (abstime_ns_large/1000000000), abstime_ns_large% 1000000000}; 'gdzie delay_ns jest żądanym opóźnieniem w nanosekundach.Następnie użyj abstime w swoim wywołaniu pthread_cond_timedwait. –