WIP: xcb_wait_for_special_event_with_timeout()
This surely has portability problems and is ugly since it works with three different representations (timeout in milliseconds, deadline as timeval, deadline as timespec).
Also, this is completely untested. But at least its a start.
Related to #38
Anyone who wants is free to pick this up and do it properly.
For the public API, I was thinking on whether this should be a timeout
(as it is now) or a deadline (struct timeval / timespec
). I only picked
the timeout so that no structs from sys/time.h
appear in the public
API. No idea if that was a good choice.
Merge request reports
Activity
mentioned in issue #38
477 489 pthread_mutex_unlock(&c->iolock); 478 490 do { 479 491 #if USE_POLL 480 ret = poll(&fd, 1, -1); 492 int timeout = -1; 493 if(deadline && now) { 494 struct timeval diff; 495 timersub(deadline, now, &diff); 496 timeout = now->tv_sec * 1000 + now->tv_usec / 1000; 445 451 /* If the thing I should be doing is already being done, wait for it. */ 446 452 if(count ? c->out.writing : c->in.reading) 447 453 { 448 pthread_cond_wait(cond, &c->iolock); 454 if(deadline) { 455 struct timespec spec; 456 spec.tv_sec = deadline->tv_sec; 457 spec.tv_nsec = deadline->tv_usec * 100; 793 timeout.tv_sec = millisecs_timeout / 1000; 794 timeout.tv_usec = (millisecs_timeout % 1000) * 1000; 795 gettimeofday(&now, NULL); // TODO: Check for errors? 796 timeradd(&now, &timeout, &deadline); 797 798 pthread_mutex_lock(&c->iolock); 799 800 insert_special(&c->in.special_waiters, &special, se); 801 802 /* get_special_event returns 0 on empty list. */ 803 while(!(event = get_special_event(c, se))) { 804 if(timercmp(&deadline, &now, <)) 805 break; 806 if(!_xcb_conn_timedwait(c, &se->special_event_cond, 0, 0, &now, &deadline)) 807 break; 808 gettimeofday(&now, NULL); // TODO: Check for errors? 486 504 break; 487 505 } 488 506 #else 489 ret = select(c->fd + 1, &rfds, &wfds, 0, 0); 507 struct timeval diff; 508 struct timeval *timeout = NULL; 509 if(deadline && now) { 510 timersub(deadline, now, &diff); 511 timeout = &diff; 512 } 513 ret = select(c->fd + 1, &rfds, &wfds, 0, timeout); 490 514 #endif 491 515 } while (ret == -1 && errno == EINTR); mentioned in issue mesa/mesa#3344 (closed)
mentioned in commit tguillem/mesa@ea93da11
Hello,
Thanks Michel and Uli for your work.
VLC developer here. I tried to fix the comments addressed by Michel.
Here is my fixup patch: tguillem/libxcb@d78820c7
I could test it, using the following patch on mesa: tguillem/mesa@ea93da11
It fixes VLC deadlocks with Qt when closing the window.
Cool, though FWIW Mesa needs to check if the window still exists and try again if it does, like mesa/mesa!5368 (d7d76878) did. Otherwise it may spuriously bail after e.g. the thread was stopped for >= 1s for any reason.
mentioned in issue mesa/mesa#116 (closed)
mentioned in merge request mesa/mesa!13564 (merged)
mentioned in issue mesa/mesa#6537 (closed)
mentioned in merge request mesa/mesa!17742 (closed)
mentioned in merge request mesa/mesa!19279 (merged)
unassigned @daenzer