内容简介:http://stackoverflow.com/questions/7121212/how-to-make-pthread-cond-timedwait-robust-against-system-clock-manipulations
考虑以下源代码,它完全符合POSIX标准:
#include <stdio.h> #include <limits.h> #include <stdint.h> #include <stdlib.h> #include <pthread.h> #include <sys/time.h> int main (int argc, char ** argv) { pthread_cond_t c; pthread_mutex_t m; char printTime[UCHAR_MAX]; pthread_mutex_init(&m, NULL); pthread_cond_init(&c, NULL); for (;;) { struct tm * tm; struct timeval tv; struct timespec ts; gettimeofday(&tv, NULL); printf("sleep (%ld)\n", (long)tv.tv_sec); sleep(3); tm = gmtime(&tv.tv_sec); strftime(printTime, UCHAR_MAX, "%Y-%m-%d %H:%M:%S", tm); printf("%s (%ld)\n", printTime, (long)tv.tv_sec); ts.tv_sec = tv.tv_sec + 5; ts.tv_nsec = tv.tv_usec * 1000; pthread_mutex_lock(&m); pthread_cond_timedwait(&c, &m, &ts); pthread_mutex_unlock(&m); } return 0; }
每5秒打印一次当前的系统日期,但是在获取当前系统时间(gettimeofday)和条件wait(pthread_cond_timedwait)之间休眠3秒钟.
在打印“睡眠(…)”之后,尝试将系统时钟设置为过去两天.怎么了?那么,pthread_cond_timedwait现在等待两天2秒,而不是像通常那样等待2秒的时间.
我该如何解决?
如何编写符合POSIX标准的代码,当用户操作系统时钟时,代码不会中断?
请记住,即使没有用户交互,系统时钟也可能会改变(例如,NTP客户端可能每天自动更新一次时钟).将时钟摆在未来没有问题,只会让睡眠早起来,这通常没有问题,你可以轻松地“检测”并相应处理,但将时钟设置为过去(例如因为是运行在未来,NTP检测到并修复它)可能会造成很大的问题.
PS:
我的系统上不存在pthread_condattr_setclock()和CLOCK_MONOTONIC.对于POSIX 2008规范(“Base”)的一部分,这些规范是强制性的,但大多数系统仍然遵循POSIX 2004规范,而在POSIX 2004规范中,这两个规范都是可选的(高级实时扩展).
有趣的是,我以前没有遇到过这样的行为,但是再一次,我并不习惯我的系统时间这么多:-)
假设你是为了有效的原因,一个可能(虽然kludgy)解决方案是有另一个线程,唯一的目的是定期踢条件变量来唤醒任何如此受影响的线程.
换句话说,就像:
while (1) { sleep (10); pthread_cond_signal (&condVar); }
等待条件变量被踢脚本的代码应该是检查它的谓词(要照顾虚假的唤醒),所以这不应该对功能产生真正的不利影响.
这是一个轻微的性能打击,但每十秒钟一次不应该是太多的问题.这只是为了照顾那些(无论什么原因)你的等待时间等待很长时间的情况.
另一种可能性是重新设计您的应用程序,以便您根本不需要定时等待.
在线程需要被某些原因唤醒的情况下,它总是由另一个线程完成,该线程完全有能力踢出一个条件变量来唤醒一个(或广播唤醒它们).
这与我上面提到的踢脚线非常相似,但是作为你的架构的一个组成部分,而不是一个螺栓.
http://stackoverflow.com/questions/7121212/how-to-make-pthread-cond-timedwait-robust-against-system-clock-manipulations
以上所述就是小编给大家介绍的《如何使pthread_cond_timedwait()对系统时钟操作有效?》,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对 码农网 的支持!
猜你喜欢:本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们。