alarm.c 1.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124
  1. #include "u.h"
  2. #include "../port/lib.h"
  3. #include "mem.h"
  4. #include "dat.h"
  5. #include "fns.h"
  6. Alarms alarms;
  7. Rendez alarmr;
  8. Talarm talarm;
  9. void
  10. alarmkproc(void*)
  11. {
  12. Proc *rp;
  13. ulong now;
  14. for(;;){
  15. now = MACHP(0)->ticks;
  16. qlock(&alarms);
  17. while((rp = alarms.head) && rp->alarm <= now){
  18. if(rp->alarm != 0L){
  19. if(canqlock(&rp->debug)){
  20. if(!waserror()){
  21. postnote(rp, 0, "alarm", NUser);
  22. poperror();
  23. }
  24. qunlock(&rp->debug);
  25. rp->alarm = 0L;
  26. }else
  27. break;
  28. }
  29. alarms.head = rp->palarm;
  30. }
  31. qunlock(&alarms);
  32. sleep(&alarmr, return0, 0);
  33. }
  34. }
  35. /*
  36. * called every clock tick
  37. */
  38. void
  39. checkalarms(void)
  40. {
  41. Proc *p;
  42. ulong now;
  43. p = alarms.head;
  44. now = MACHP(0)->ticks;
  45. if(p && p->alarm <= now)
  46. wakeup(&alarmr);
  47. if(talarm.list == 0 || !canlock(&talarm))
  48. return;
  49. for(;;) {
  50. p = talarm.list;
  51. if(p == 0)
  52. break;
  53. if(p->twhen == 0) {
  54. talarm.list = p->tlink;
  55. p->trend = 0;
  56. continue;
  57. }
  58. if(now < p->twhen)
  59. break;
  60. wakeup(p->trend);
  61. talarm.list = p->tlink;
  62. p->trend = 0;
  63. }
  64. unlock(&talarm);
  65. }
  66. ulong
  67. procalarm(ulong time)
  68. {
  69. Proc **l, *f;
  70. ulong when, old;
  71. if(up->alarm)
  72. old = tk2ms(up->alarm - MACHP(0)->ticks);
  73. else
  74. old = 0;
  75. if(time == 0) {
  76. up->alarm = 0;
  77. return old;
  78. }
  79. when = ms2tk(time)+MACHP(0)->ticks;
  80. qlock(&alarms);
  81. l = &alarms.head;
  82. for(f = *l; f; f = f->palarm) {
  83. if(up == f){
  84. *l = f->palarm;
  85. break;
  86. }
  87. l = &f->palarm;
  88. }
  89. up->palarm = 0;
  90. if(alarms.head) {
  91. l = &alarms.head;
  92. for(f = *l; f; f = f->palarm) {
  93. if(f->alarm > when) {
  94. up->palarm = f;
  95. *l = up;
  96. goto done;
  97. }
  98. l = &f->palarm;
  99. }
  100. *l = up;
  101. }
  102. else
  103. alarms.head = up;
  104. done:
  105. up->alarm = when;
  106. qunlock(&alarms);
  107. return old;
  108. }