]>
git.saurik.com Git - apple/xnu.git/blob - tools/tests/kqueue_tests/kqueue_timer_tests.c
10 int kq
, passed
, failed
;
13 * Wait for given kevent, which should return in 'expected' usecs.
16 do_simple_kevent(struct kevent64_s
*kev
, uint64_t expected
)
19 uint64_t elapsed_usecs
, delta_usecs
;
20 struct timespec timeout
;
21 struct timeval before
, after
;
23 /* time out after 1 sec extra delay */
24 timeout
.tv_sec
= (expected
/ (1000 * 1000)) + 1;
25 timeout
.tv_nsec
= (expected
% (1000 * 1000)) * 1000;
27 /* measure time for the kevent */
28 gettimeofday(&before
, NULL
);
29 ret
= kevent64(kq
, kev
, 1, kev
, 1, 0, &timeout
);
30 gettimeofday(&after
, NULL
);
32 if (ret
< 1 || (kev
->flags
& EV_ERROR
)) {
33 printf("\tfailure: kevent returned %d, error %d\n", ret
,
34 (ret
== -1 ? errno
: (int) kev
->data
));
39 elapsed_usecs
= (after
.tv_sec
- before
.tv_sec
) * (1000 * 1000) +
40 (after
.tv_usec
- before
.tv_usec
);
41 delta_usecs
= abs(elapsed_usecs
- (expected
));
43 /* failure if we're 30% off, or 50 mics late */
44 if (delta_usecs
> (30 * expected
/ 100.0) && delta_usecs
> 50) {
45 printf("\tfailure: expected %lld usec, measured %lld usec.\n",
46 expected
, elapsed_usecs
);
49 printf("\tsuccess.\n");
55 test_absolute_kevent(int time
, int scale
)
58 struct kevent64_s kev
;
59 uint64_t nowus
, expected
, deadline
;
63 gettimeofday(&tv
, NULL
);
64 nowus
= tv
.tv_sec
* (1000 * 1000LL) + tv
.tv_usec
;
68 printf("Testing %d sec absolute timer...\n", time
);
69 timescale
= 1000 * 1000;
72 printf("Testing %d usec absolute timer...\n", time
);
76 printf("Testing %d msec absolute timer...\n", time
);
80 printf("Failure: scale 0x%x not recognized.\n", scale
);
84 expected
= time
* timescale
;
85 deadline
= nowus
/ timescale
+ time
;
87 /* deadlines in the past should fire immediately */
91 EV_SET64(&kev
, 1, EVFILT_TIMER
, EV_ADD
,
92 NOTE_ABSOLUTE
| scale
, deadline
, 0,0,0);
93 ret
= do_simple_kevent(&kev
, expected
);
102 test_oneshot_kevent(int time
, int scale
)
105 uint64_t expected
= 0;
106 struct kevent64_s kev
;
110 printf("Testing %d sec interval timer...\n", time
);
111 expected
= time
* (1000 * 1000);
114 printf("Testing %d usec interval timer...\n", time
);
118 printf("Testing %d nsec interval timer...\n", time
);
119 expected
= time
/ 1000;
122 printf("Testing %d msec interval timer...\n", time
);
123 expected
= time
* 1000;
126 printf("Failure: scale 0x%x not recognized.\n", scale
);
130 /* deadlines in the past should fire immediately */
134 EV_SET64(&kev
, 2, EVFILT_TIMER
, EV_ADD
| EV_ONESHOT
, scale
, time
,
136 ret
= do_simple_kevent(&kev
, expected
);
146 test_repeating_kevent(int usec
)
148 struct kevent64_s kev
;
149 int expected_pops
, ret
;
151 expected_pops
= 1000 * 1000 / usec
;
152 printf("Testing repeating kevent for %d pops in a second...\n",
155 EV_SET64(&kev
, 3, EVFILT_TIMER
, EV_ADD
, NOTE_USECONDS
, usec
, 0, 0, 0);
156 ret
= kevent64(kq
, &kev
, 1, NULL
, 0, 0, NULL
);
158 printf("\tfailure: kevent64 returned %d\n", ret
);
165 ret
= kevent64(kq
, NULL
, 0, &kev
, 1, 0, NULL
);
166 if (ret
!= 1 || (kev
.flags
& EV_ERROR
)) {
167 printf("\tfailure: kevent64 returned %d\n", ret
);
172 /* check how many times the timer fired: within 5%? */
173 if (kev
.data
> expected_pops
+ (expected_pops
/ 20) ||
174 kev
.data
< expected_pops
- (expected_pops
/ 20)) {
175 printf("\tfailure: saw %lld pops.\n", kev
.data
);
178 printf("\tsuccess: saw %lld pops.\n", kev
.data
);
182 EV_SET64(&kev
, 3, EVFILT_TIMER
, EV_DELETE
, 0, 0, 0, 0, 0);
183 ret
= kevent64(kq
, &kev
, 1, NULL
, 0, 0, NULL
);
185 printf("\tfailed to stop repeating timer: %d\n", ret
);
190 test_updated_kevent(int first
, int second
)
192 struct kevent64_s kev
;
195 printf("Testing update from %d to %d msecs...\n", first
, second
);
197 EV_SET64(&kev
, 4, EVFILT_TIMER
, EV_ADD
|EV_ONESHOT
, 0, first
, 0, 0, 0);
198 ret
= kevent64(kq
, &kev
, 1, NULL
, 0, 0, NULL
);
200 printf("\tfailure: initial kevent returned %d\n", ret
);
205 EV_SET64(&kev
, 4, EVFILT_TIMER
, EV_ONESHOT
, 0, second
, 0, 0, 0);
208 ret
= do_simple_kevent(&kev
, second
* 1000);
219 struct kevent64_s kev
;
220 uint64_t nowms
, deadline
;
227 test_absolute_kevent(100, 0);
228 test_absolute_kevent(200, 0);
229 test_absolute_kevent(300, 0);
230 test_absolute_kevent(1000, 0);
231 test_absolute_kevent(500, NOTE_USECONDS
);
232 test_absolute_kevent(100, NOTE_USECONDS
);
233 test_absolute_kevent(5, NOTE_SECONDS
);
234 test_absolute_kevent(-1000, 0);
236 test_oneshot_kevent(1, NOTE_SECONDS
);
237 test_oneshot_kevent(10, 0);
238 test_oneshot_kevent(200, NOTE_USECONDS
);
239 test_oneshot_kevent(300000, NOTE_NSECONDS
);
240 test_oneshot_kevent(-1, NOTE_SECONDS
);
242 test_repeating_kevent(100 * 1000);
243 test_repeating_kevent(5 * 1000);
244 test_repeating_kevent(200);
245 test_repeating_kevent(50);
246 test_repeating_kevent(10);
248 test_updated_kevent(1000, 2000);
249 test_updated_kevent(2000, 1000);
250 test_updated_kevent(1000, -1);
252 printf("\nFinished: %d tests passed, %d failed.\n", passed
, failed
);