]> Git Repo - qemu.git/blob - tests/ptimer-test.c
Merge remote-tracking branch 'remotes/pmaydell/tags/pull-target-arm-20191015' into...
[qemu.git] / tests / ptimer-test.c
1 /*
2  * QTest testcase for the ptimer
3  *
4  * Copyright (c) 2016 Dmitry Osipenko <[email protected]>
5  *
6  * This work is licensed under the terms of the GNU GPL, version 2 or later.
7  * See the COPYING file in the top-level directory.
8  *
9  */
10
11 #include "qemu/osdep.h"
12 #include <glib/gprintf.h>
13
14 #include "qemu/main-loop.h"
15 #include "hw/ptimer.h"
16
17 #include "libqtest.h"
18 #include "ptimer-test.h"
19
20 static bool triggered;
21
22 static void ptimer_trigger(void *opaque)
23 {
24     triggered = true;
25 }
26
27 static void ptimer_test_expire_qemu_timers(int64_t expire_time,
28                                            QEMUClockType type)
29 {
30     QEMUTimerList *timer_list = main_loop_tlg.tl[type];
31     QEMUTimer *t = timer_list->active_timers.next;
32
33     while (t != NULL) {
34         if (t->expire_time == expire_time) {
35             timer_del(t);
36
37             if (t->cb != NULL) {
38                 t->cb(t->opaque);
39             }
40         }
41
42         t = t->next;
43     }
44 }
45
46 static void ptimer_test_set_qemu_time_ns(int64_t ns)
47 {
48     ptimer_test_time_ns = ns;
49 }
50
51 static void qemu_clock_step(uint64_t ns)
52 {
53     int64_t deadline = qemu_clock_deadline_ns_all(QEMU_CLOCK_VIRTUAL,
54                                                   QEMU_TIMER_ATTR_ALL);
55     int64_t advanced_time = qemu_clock_get_ns(QEMU_CLOCK_VIRTUAL) + ns;
56
57     while (deadline != -1 && deadline <= advanced_time) {
58         ptimer_test_set_qemu_time_ns(deadline);
59         ptimer_test_expire_qemu_timers(deadline, QEMU_CLOCK_VIRTUAL);
60         deadline = qemu_clock_deadline_ns_all(QEMU_CLOCK_VIRTUAL,
61                                               QEMU_TIMER_ATTR_ALL);
62     }
63
64     ptimer_test_set_qemu_time_ns(advanced_time);
65 }
66
67 static void check_set_count(gconstpointer arg)
68 {
69     const uint8_t *policy = arg;
70     ptimer_state *ptimer = ptimer_init(ptimer_trigger, NULL, *policy);
71
72     triggered = false;
73
74     ptimer_transaction_begin(ptimer);
75     ptimer_set_count(ptimer, 1000);
76     ptimer_transaction_commit(ptimer);
77     g_assert_cmpuint(ptimer_get_count(ptimer), ==, 1000);
78     g_assert_false(triggered);
79     ptimer_free(ptimer);
80 }
81
82 static void check_set_limit(gconstpointer arg)
83 {
84     const uint8_t *policy = arg;
85     ptimer_state *ptimer = ptimer_init(ptimer_trigger, NULL, *policy);
86
87     triggered = false;
88
89     ptimer_transaction_begin(ptimer);
90     ptimer_set_limit(ptimer, 1000, 0);
91     ptimer_transaction_commit(ptimer);
92     g_assert_cmpuint(ptimer_get_count(ptimer), ==, 0);
93     g_assert_cmpuint(ptimer_get_limit(ptimer), ==, 1000);
94     g_assert_false(triggered);
95
96     ptimer_transaction_begin(ptimer);
97     ptimer_set_limit(ptimer, 2000, 1);
98     ptimer_transaction_commit(ptimer);
99     g_assert_cmpuint(ptimer_get_count(ptimer), ==, 2000);
100     g_assert_cmpuint(ptimer_get_limit(ptimer), ==, 2000);
101     g_assert_false(triggered);
102     ptimer_free(ptimer);
103 }
104
105 static void check_oneshot(gconstpointer arg)
106 {
107     const uint8_t *policy = arg;
108     ptimer_state *ptimer = ptimer_init(ptimer_trigger, NULL, *policy);
109     bool no_round_down = (*policy & PTIMER_POLICY_NO_COUNTER_ROUND_DOWN);
110
111     triggered = false;
112
113     ptimer_transaction_begin(ptimer);
114     ptimer_set_period(ptimer, 2000000);
115     ptimer_set_count(ptimer, 10);
116     ptimer_run(ptimer, 1);
117     ptimer_transaction_commit(ptimer);
118
119     qemu_clock_step(2000000 * 2 + 1);
120
121     g_assert_cmpuint(ptimer_get_count(ptimer), ==, no_round_down ? 8 : 7);
122     g_assert_false(triggered);
123
124     ptimer_transaction_begin(ptimer);
125     ptimer_stop(ptimer);
126     ptimer_transaction_commit(ptimer);
127
128     g_assert_cmpuint(ptimer_get_count(ptimer), ==, no_round_down ? 8 : 7);
129     g_assert_false(triggered);
130
131     qemu_clock_step(2000000 * 11);
132
133     g_assert_cmpuint(ptimer_get_count(ptimer), ==, no_round_down ? 8 : 7);
134     g_assert_false(triggered);
135
136     ptimer_transaction_begin(ptimer);
137     ptimer_run(ptimer, 1);
138     ptimer_transaction_commit(ptimer);
139
140     qemu_clock_step(2000000 * 7 + 1);
141
142     g_assert_cmpuint(ptimer_get_count(ptimer), ==, no_round_down ? 1 : 0);
143
144     if (no_round_down) {
145         g_assert_false(triggered);
146     } else {
147         g_assert_true(triggered);
148
149         triggered = false;
150     }
151
152     qemu_clock_step(2000000);
153
154     g_assert_cmpuint(ptimer_get_count(ptimer), ==, 0);
155
156     if (no_round_down) {
157         g_assert_true(triggered);
158
159         triggered = false;
160     } else {
161         g_assert_false(triggered);
162     }
163
164     qemu_clock_step(4000000);
165
166     g_assert_cmpuint(ptimer_get_count(ptimer), ==, 0);
167     g_assert_false(triggered);
168
169     ptimer_transaction_begin(ptimer);
170     ptimer_set_count(ptimer, 10);
171     ptimer_transaction_commit(ptimer);
172
173     qemu_clock_step(20000000 + 1);
174
175     g_assert_cmpuint(ptimer_get_count(ptimer), ==, 10);
176     g_assert_false(triggered);
177
178     ptimer_transaction_begin(ptimer);
179     ptimer_set_limit(ptimer, 9, 1);
180     ptimer_transaction_commit(ptimer);
181
182     qemu_clock_step(20000000 + 1);
183
184     g_assert_cmpuint(ptimer_get_count(ptimer), ==, 9);
185     g_assert_false(triggered);
186
187     ptimer_transaction_begin(ptimer);
188     ptimer_run(ptimer, 1);
189     ptimer_transaction_commit(ptimer);
190
191     qemu_clock_step(2000000 + 1);
192
193     g_assert_cmpuint(ptimer_get_count(ptimer), ==, no_round_down ? 8 : 7);
194     g_assert_false(triggered);
195
196     ptimer_transaction_begin(ptimer);
197     ptimer_set_count(ptimer, 20);
198     ptimer_transaction_commit(ptimer);
199
200     qemu_clock_step(2000000 * 19 + 1);
201
202     g_assert_cmpuint(ptimer_get_count(ptimer), ==, no_round_down ? 1 : 0);
203     g_assert_false(triggered);
204
205     qemu_clock_step(2000000);
206
207     g_assert_cmpuint(ptimer_get_count(ptimer), ==, 0);
208     g_assert_true(triggered);
209
210     ptimer_transaction_begin(ptimer);
211     ptimer_stop(ptimer);
212     ptimer_transaction_commit(ptimer);
213
214     triggered = false;
215
216     qemu_clock_step(2000000 * 12 + 1);
217
218     g_assert_cmpuint(ptimer_get_count(ptimer), ==, 0);
219     g_assert_false(triggered);
220     ptimer_free(ptimer);
221 }
222
223 static void check_periodic(gconstpointer arg)
224 {
225     const uint8_t *policy = arg;
226     ptimer_state *ptimer = ptimer_init(ptimer_trigger, NULL, *policy);
227     bool wrap_policy = (*policy & PTIMER_POLICY_WRAP_AFTER_ONE_PERIOD);
228     bool no_immediate_trigger = (*policy & PTIMER_POLICY_NO_IMMEDIATE_TRIGGER);
229     bool no_immediate_reload = (*policy & PTIMER_POLICY_NO_IMMEDIATE_RELOAD);
230     bool no_round_down = (*policy & PTIMER_POLICY_NO_COUNTER_ROUND_DOWN);
231     bool trig_only_on_dec = (*policy & PTIMER_POLICY_TRIGGER_ONLY_ON_DECREMENT);
232
233     triggered = false;
234
235     ptimer_transaction_begin(ptimer);
236     ptimer_set_period(ptimer, 2000000);
237     ptimer_set_limit(ptimer, 10, 1);
238     ptimer_run(ptimer, 0);
239     ptimer_transaction_commit(ptimer);
240
241     g_assert_cmpuint(ptimer_get_count(ptimer), ==, 10);
242     g_assert_false(triggered);
243
244     qemu_clock_step(1);
245
246     g_assert_cmpuint(ptimer_get_count(ptimer), ==, no_round_down ? 10 : 9);
247     g_assert_false(triggered);
248
249     qemu_clock_step(2000000 * 10 - 1);
250
251     g_assert_cmpuint(ptimer_get_count(ptimer), ==, wrap_policy ? 0 : 10);
252     g_assert_true(triggered);
253
254     qemu_clock_step(1);
255
256     g_assert_cmpuint(ptimer_get_count(ptimer), ==,
257                      wrap_policy ? 0 : (no_round_down ? 10 : 9));
258     g_assert_true(triggered);
259
260     triggered = false;
261
262     qemu_clock_step(2000000);
263
264     g_assert_cmpuint(ptimer_get_count(ptimer), ==,
265                     (no_round_down ? 9 : 8) + (wrap_policy ? 1 : 0));
266     g_assert_false(triggered);
267
268     ptimer_transaction_begin(ptimer);
269     ptimer_set_count(ptimer, 20);
270     ptimer_transaction_commit(ptimer);
271
272     g_assert_cmpuint(ptimer_get_count(ptimer), ==, 20);
273     g_assert_false(triggered);
274
275     qemu_clock_step(1);
276
277     g_assert_cmpuint(ptimer_get_count(ptimer), ==, no_round_down ? 20 : 19);
278     g_assert_false(triggered);
279
280     qemu_clock_step(2000000 * 11 + 1);
281
282     g_assert_cmpuint(ptimer_get_count(ptimer), ==, no_round_down ? 9 : 8);
283     g_assert_false(triggered);
284
285     qemu_clock_step(2000000 * 10);
286
287     g_assert_cmpuint(ptimer_get_count(ptimer), ==,
288                     (no_round_down ? 9 : 8) + (wrap_policy ? 1 : 0));
289     g_assert_true(triggered);
290
291     triggered = false;
292
293     ptimer_transaction_begin(ptimer);
294     ptimer_set_count(ptimer, 3);
295     ptimer_transaction_commit(ptimer);
296
297     g_assert_cmpuint(ptimer_get_count(ptimer), ==, 3);
298     g_assert_false(triggered);
299
300     qemu_clock_step(1);
301
302     g_assert_cmpuint(ptimer_get_count(ptimer), ==, no_round_down ? 3 : 2);
303     g_assert_false(triggered);
304
305     qemu_clock_step(2000000 * 4);
306
307     g_assert_cmpuint(ptimer_get_count(ptimer), ==,
308                     (no_round_down ? 9 : 8) + (wrap_policy ? 1 : 0));
309     g_assert_true(triggered);
310
311     ptimer_transaction_begin(ptimer);
312     ptimer_stop(ptimer);
313     ptimer_transaction_commit(ptimer);
314     triggered = false;
315
316     qemu_clock_step(2000000);
317
318     g_assert_cmpuint(ptimer_get_count(ptimer), ==,
319                     (no_round_down ? 9 : 8) + (wrap_policy ? 1 : 0));
320     g_assert_false(triggered);
321
322     ptimer_transaction_begin(ptimer);
323     ptimer_set_count(ptimer, 3);
324     ptimer_run(ptimer, 0);
325     ptimer_transaction_commit(ptimer);
326
327     qemu_clock_step(2000000 * 3 + 1);
328
329     g_assert_cmpuint(ptimer_get_count(ptimer), ==,
330                      wrap_policy ? 0 : (no_round_down ? 10 : 9));
331     g_assert_true(triggered);
332
333     triggered = false;
334
335     qemu_clock_step(2000000);
336
337     g_assert_cmpuint(ptimer_get_count(ptimer), ==,
338                     (no_round_down ? 9 : 8) + (wrap_policy ? 1 : 0));
339     g_assert_false(triggered);
340
341     ptimer_transaction_begin(ptimer);
342     ptimer_set_count(ptimer, 0);
343     ptimer_transaction_commit(ptimer);
344     g_assert_cmpuint(ptimer_get_count(ptimer), ==,
345                      no_immediate_reload ? 0 : 10);
346
347     if (no_immediate_trigger || trig_only_on_dec) {
348         g_assert_false(triggered);
349     } else {
350         g_assert_true(triggered);
351     }
352
353     triggered = false;
354
355     qemu_clock_step(1);
356
357     if (no_immediate_reload) {
358         g_assert_cmpuint(ptimer_get_count(ptimer), ==, 0);
359         g_assert_false(triggered);
360
361         qemu_clock_step(2000000);
362
363         if (no_immediate_trigger) {
364             g_assert_true(triggered);
365         } else {
366             g_assert_false(triggered);
367         }
368
369         triggered = false;
370     }
371
372     g_assert_cmpuint(ptimer_get_count(ptimer), ==, no_round_down ? 10 : 9);
373     g_assert_false(triggered);
374
375     qemu_clock_step(2000000 * 12);
376
377     g_assert_cmpuint(ptimer_get_count(ptimer), ==,
378                     (no_round_down ? 8 : 7) + (wrap_policy ? 1 : 0));
379     g_assert_true(triggered);
380
381     ptimer_transaction_begin(ptimer);
382     ptimer_stop(ptimer);
383     ptimer_transaction_commit(ptimer);
384
385     triggered = false;
386
387     qemu_clock_step(2000000 * 10);
388
389     g_assert_cmpuint(ptimer_get_count(ptimer), ==,
390                     (no_round_down ? 8 : 7) + (wrap_policy ? 1 : 0));
391     g_assert_false(triggered);
392
393     ptimer_transaction_begin(ptimer);
394     ptimer_run(ptimer, 0);
395     ptimer_transaction_commit(ptimer);
396
397     ptimer_transaction_begin(ptimer);
398     ptimer_set_period(ptimer, 0);
399     ptimer_transaction_commit(ptimer);
400
401     qemu_clock_step(2000000 + 1);
402
403     g_assert_cmpuint(ptimer_get_count(ptimer), ==,
404                     (no_round_down ? 8 : 7) + (wrap_policy ? 1 : 0));
405     g_assert_false(triggered);
406     ptimer_free(ptimer);
407 }
408
409 static void check_on_the_fly_mode_change(gconstpointer arg)
410 {
411     const uint8_t *policy = arg;
412     ptimer_state *ptimer = ptimer_init(ptimer_trigger, NULL, *policy);
413     bool wrap_policy = (*policy & PTIMER_POLICY_WRAP_AFTER_ONE_PERIOD);
414     bool no_round_down = (*policy & PTIMER_POLICY_NO_COUNTER_ROUND_DOWN);
415
416     triggered = false;
417
418     ptimer_transaction_begin(ptimer);
419     ptimer_set_period(ptimer, 2000000);
420     ptimer_set_limit(ptimer, 10, 1);
421     ptimer_run(ptimer, 1);
422     ptimer_transaction_commit(ptimer);
423
424     qemu_clock_step(2000000 * 9 + 1);
425
426     g_assert_cmpuint(ptimer_get_count(ptimer), ==, no_round_down ? 1 : 0);
427     g_assert_false(triggered);
428
429     ptimer_transaction_begin(ptimer);
430     ptimer_run(ptimer, 0);
431     ptimer_transaction_commit(ptimer);
432
433     g_assert_cmpuint(ptimer_get_count(ptimer), ==, no_round_down ? 1 : 0);
434     g_assert_false(triggered);
435
436     qemu_clock_step(2000000);
437
438     g_assert_cmpuint(ptimer_get_count(ptimer), ==,
439                     wrap_policy ? 0 : (no_round_down ? 10 : 9));
440     g_assert_true(triggered);
441
442     triggered = false;
443
444     qemu_clock_step(2000000 * 9);
445
446     ptimer_transaction_begin(ptimer);
447     ptimer_run(ptimer, 1);
448     ptimer_transaction_commit(ptimer);
449
450     g_assert_cmpuint(ptimer_get_count(ptimer), ==,
451                      (no_round_down ? 1 : 0) + (wrap_policy ? 1 : 0));
452     g_assert_false(triggered);
453
454     qemu_clock_step(2000000 * 3);
455
456     g_assert_cmpuint(ptimer_get_count(ptimer), ==, 0);
457     g_assert_true(triggered);
458     ptimer_free(ptimer);
459 }
460
461 static void check_on_the_fly_period_change(gconstpointer arg)
462 {
463     const uint8_t *policy = arg;
464     ptimer_state *ptimer = ptimer_init(ptimer_trigger, NULL, *policy);
465     bool no_round_down = (*policy & PTIMER_POLICY_NO_COUNTER_ROUND_DOWN);
466
467     triggered = false;
468
469     ptimer_transaction_begin(ptimer);
470     ptimer_set_period(ptimer, 2000000);
471     ptimer_set_limit(ptimer, 8, 1);
472     ptimer_run(ptimer, 1);
473     ptimer_transaction_commit(ptimer);
474
475     qemu_clock_step(2000000 * 4 + 1);
476
477     g_assert_cmpuint(ptimer_get_count(ptimer), ==, no_round_down ? 4 : 3);
478     g_assert_false(triggered);
479
480     ptimer_transaction_begin(ptimer);
481     ptimer_set_period(ptimer, 4000000);
482     ptimer_transaction_commit(ptimer);
483     g_assert_cmpuint(ptimer_get_count(ptimer), ==, no_round_down ? 4 : 3);
484
485     qemu_clock_step(4000000 * 2 + 1);
486
487     g_assert_cmpuint(ptimer_get_count(ptimer), ==, no_round_down ? 2 : 0);
488     g_assert_false(triggered);
489
490     qemu_clock_step(4000000 * 2);
491
492     g_assert_cmpuint(ptimer_get_count(ptimer), ==, 0);
493     g_assert_true(triggered);
494     ptimer_free(ptimer);
495 }
496
497 static void check_on_the_fly_freq_change(gconstpointer arg)
498 {
499     const uint8_t *policy = arg;
500     ptimer_state *ptimer = ptimer_init(ptimer_trigger, NULL, *policy);
501     bool no_round_down = (*policy & PTIMER_POLICY_NO_COUNTER_ROUND_DOWN);
502
503     triggered = false;
504
505     ptimer_transaction_begin(ptimer);
506     ptimer_set_freq(ptimer, 500);
507     ptimer_set_limit(ptimer, 8, 1);
508     ptimer_run(ptimer, 1);
509     ptimer_transaction_commit(ptimer);
510
511     qemu_clock_step(2000000 * 4 + 1);
512
513     g_assert_cmpuint(ptimer_get_count(ptimer), ==, no_round_down ? 4 : 3);
514     g_assert_false(triggered);
515
516     ptimer_transaction_begin(ptimer);
517     ptimer_set_freq(ptimer, 250);
518     ptimer_transaction_commit(ptimer);
519     g_assert_cmpuint(ptimer_get_count(ptimer), ==, no_round_down ? 4 : 3);
520
521     qemu_clock_step(2000000 * 4 + 1);
522
523     g_assert_cmpuint(ptimer_get_count(ptimer), ==, no_round_down ? 2 : 0);
524     g_assert_false(triggered);
525
526     qemu_clock_step(2000000 * 4);
527
528     g_assert_cmpuint(ptimer_get_count(ptimer), ==, 0);
529     g_assert_true(triggered);
530     ptimer_free(ptimer);
531 }
532
533 static void check_run_with_period_0(gconstpointer arg)
534 {
535     const uint8_t *policy = arg;
536     ptimer_state *ptimer = ptimer_init(ptimer_trigger, NULL, *policy);
537
538     triggered = false;
539
540     ptimer_transaction_begin(ptimer);
541     ptimer_set_count(ptimer, 99);
542     ptimer_run(ptimer, 1);
543     ptimer_transaction_commit(ptimer);
544
545     qemu_clock_step(10 * NANOSECONDS_PER_SECOND);
546
547     g_assert_cmpuint(ptimer_get_count(ptimer), ==, 99);
548     g_assert_false(triggered);
549     ptimer_free(ptimer);
550 }
551
552 static void check_run_with_delta_0(gconstpointer arg)
553 {
554     const uint8_t *policy = arg;
555     ptimer_state *ptimer = ptimer_init(ptimer_trigger, NULL, *policy);
556     bool wrap_policy = (*policy & PTIMER_POLICY_WRAP_AFTER_ONE_PERIOD);
557     bool no_immediate_trigger = (*policy & PTIMER_POLICY_NO_IMMEDIATE_TRIGGER);
558     bool no_immediate_reload = (*policy & PTIMER_POLICY_NO_IMMEDIATE_RELOAD);
559     bool no_round_down = (*policy & PTIMER_POLICY_NO_COUNTER_ROUND_DOWN);
560     bool trig_only_on_dec = (*policy & PTIMER_POLICY_TRIGGER_ONLY_ON_DECREMENT);
561
562     triggered = false;
563
564     ptimer_transaction_begin(ptimer);
565     ptimer_set_period(ptimer, 2000000);
566     ptimer_set_limit(ptimer, 99, 0);
567     ptimer_run(ptimer, 1);
568     ptimer_transaction_commit(ptimer);
569     g_assert_cmpuint(ptimer_get_count(ptimer), ==,
570                      no_immediate_reload ? 0 : 99);
571
572     if (no_immediate_trigger || trig_only_on_dec) {
573         g_assert_false(triggered);
574     } else {
575         g_assert_true(triggered);
576     }
577
578     triggered = false;
579
580     if (no_immediate_trigger || no_immediate_reload) {
581         qemu_clock_step(2000000 + 1);
582
583         g_assert_cmpuint(ptimer_get_count(ptimer), ==,
584                          no_immediate_reload ? 0 : (no_round_down ? 98 : 97));
585
586         if (no_immediate_trigger && no_immediate_reload) {
587             g_assert_true(triggered);
588
589             triggered = false;
590         } else {
591             g_assert_false(triggered);
592         }
593
594         ptimer_transaction_begin(ptimer);
595         ptimer_set_count(ptimer, 99);
596         ptimer_run(ptimer, 1);
597         ptimer_transaction_commit(ptimer);
598     }
599
600     qemu_clock_step(2000000 + 1);
601
602     g_assert_cmpuint(ptimer_get_count(ptimer), ==, no_round_down ? 98 : 97);
603     g_assert_false(triggered);
604
605     qemu_clock_step(2000000 * 97);
606
607     g_assert_cmpuint(ptimer_get_count(ptimer), ==, no_round_down ? 1 : 0);
608     g_assert_false(triggered);
609
610     qemu_clock_step(2000000 * 2);
611
612     g_assert_cmpuint(ptimer_get_count(ptimer), ==, 0);
613     g_assert_true(triggered);
614
615     triggered = false;
616
617     ptimer_transaction_begin(ptimer);
618     ptimer_set_count(ptimer, 0);
619     ptimer_run(ptimer, 0);
620     ptimer_transaction_commit(ptimer);
621     g_assert_cmpuint(ptimer_get_count(ptimer), ==,
622                      no_immediate_reload ? 0 : 99);
623
624     if (no_immediate_trigger || trig_only_on_dec) {
625         g_assert_false(triggered);
626     } else {
627         g_assert_true(triggered);
628     }
629
630     triggered = false;
631
632     qemu_clock_step(1);
633
634     if (no_immediate_reload) {
635         qemu_clock_step(2000000);
636     }
637
638     g_assert_cmpuint(ptimer_get_count(ptimer), ==, no_round_down ? 99 : 98);
639
640     if (no_immediate_reload && no_immediate_trigger) {
641         g_assert_true(triggered);
642     } else {
643         g_assert_false(triggered);
644     }
645
646     triggered = false;
647
648     qemu_clock_step(2000000);
649
650     g_assert_cmpuint(ptimer_get_count(ptimer), ==, no_round_down ? 98 : 97);
651     g_assert_false(triggered);
652
653     qemu_clock_step(2000000 * 98);
654
655     g_assert_cmpuint(ptimer_get_count(ptimer), ==,
656                     wrap_policy ? 0 : (no_round_down ? 99 : 98));
657     g_assert_true(triggered);
658
659     ptimer_transaction_begin(ptimer);
660     ptimer_stop(ptimer);
661     ptimer_transaction_commit(ptimer);
662     ptimer_free(ptimer);
663 }
664
665 static void check_periodic_with_load_0(gconstpointer arg)
666 {
667     const uint8_t *policy = arg;
668     ptimer_state *ptimer = ptimer_init(ptimer_trigger, NULL, *policy);
669     bool continuous_trigger = (*policy & PTIMER_POLICY_CONTINUOUS_TRIGGER);
670     bool no_immediate_trigger = (*policy & PTIMER_POLICY_NO_IMMEDIATE_TRIGGER);
671     bool trig_only_on_dec = (*policy & PTIMER_POLICY_TRIGGER_ONLY_ON_DECREMENT);
672
673     triggered = false;
674
675     ptimer_transaction_begin(ptimer);
676     ptimer_set_period(ptimer, 2000000);
677     ptimer_run(ptimer, 0);
678     ptimer_transaction_commit(ptimer);
679
680     g_assert_cmpuint(ptimer_get_count(ptimer), ==, 0);
681
682     if (no_immediate_trigger || trig_only_on_dec) {
683         g_assert_false(triggered);
684     } else {
685         g_assert_true(triggered);
686     }
687
688     triggered = false;
689
690     qemu_clock_step(2000000 + 1);
691
692     g_assert_cmpuint(ptimer_get_count(ptimer), ==, 0);
693
694     if (continuous_trigger || no_immediate_trigger) {
695         g_assert_true(triggered);
696     } else {
697         g_assert_false(triggered);
698     }
699
700     triggered = false;
701
702     ptimer_transaction_begin(ptimer);
703     ptimer_set_count(ptimer, 10);
704     ptimer_run(ptimer, 0);
705     ptimer_transaction_commit(ptimer);
706
707     qemu_clock_step(2000000 * 10 + 1);
708
709     g_assert_cmpuint(ptimer_get_count(ptimer), ==, 0);
710     g_assert_true(triggered);
711
712     triggered = false;
713
714     qemu_clock_step(2000000 + 1);
715
716     g_assert_cmpuint(ptimer_get_count(ptimer), ==, 0);
717
718     if (continuous_trigger) {
719         g_assert_true(triggered);
720     } else {
721         g_assert_false(triggered);
722     }
723
724     ptimer_transaction_begin(ptimer);
725     ptimer_stop(ptimer);
726     ptimer_transaction_commit(ptimer);
727     ptimer_free(ptimer);
728 }
729
730 static void check_oneshot_with_load_0(gconstpointer arg)
731 {
732     const uint8_t *policy = arg;
733     ptimer_state *ptimer = ptimer_init(ptimer_trigger, NULL, *policy);
734     bool no_immediate_trigger = (*policy & PTIMER_POLICY_NO_IMMEDIATE_TRIGGER);
735     bool trig_only_on_dec = (*policy & PTIMER_POLICY_TRIGGER_ONLY_ON_DECREMENT);
736
737     triggered = false;
738
739     ptimer_transaction_begin(ptimer);
740     ptimer_set_period(ptimer, 2000000);
741     ptimer_run(ptimer, 1);
742     ptimer_transaction_commit(ptimer);
743
744     g_assert_cmpuint(ptimer_get_count(ptimer), ==, 0);
745
746     if (no_immediate_trigger || trig_only_on_dec) {
747         g_assert_false(triggered);
748     } else {
749         g_assert_true(triggered);
750     }
751
752     triggered = false;
753
754     qemu_clock_step(2000000 + 1);
755
756     g_assert_cmpuint(ptimer_get_count(ptimer), ==, 0);
757
758     if (no_immediate_trigger) {
759         g_assert_true(triggered);
760     } else {
761         g_assert_false(triggered);
762     }
763
764     ptimer_free(ptimer);
765 }
766
767 static void add_ptimer_tests(uint8_t policy)
768 {
769     char policy_name[256] = "";
770     char *tmp;
771
772     if (policy == PTIMER_POLICY_DEFAULT) {
773         g_sprintf(policy_name, "default");
774     }
775
776     if (policy & PTIMER_POLICY_WRAP_AFTER_ONE_PERIOD) {
777         g_strlcat(policy_name, "wrap_after_one_period,", 256);
778     }
779
780     if (policy & PTIMER_POLICY_CONTINUOUS_TRIGGER) {
781         g_strlcat(policy_name, "continuous_trigger,", 256);
782     }
783
784     if (policy & PTIMER_POLICY_NO_IMMEDIATE_TRIGGER) {
785         g_strlcat(policy_name, "no_immediate_trigger,", 256);
786     }
787
788     if (policy & PTIMER_POLICY_NO_IMMEDIATE_RELOAD) {
789         g_strlcat(policy_name, "no_immediate_reload,", 256);
790     }
791
792     if (policy & PTIMER_POLICY_NO_COUNTER_ROUND_DOWN) {
793         g_strlcat(policy_name, "no_counter_rounddown,", 256);
794     }
795
796     if (policy & PTIMER_POLICY_TRIGGER_ONLY_ON_DECREMENT) {
797         g_strlcat(policy_name, "trigger_only_on_decrement,", 256);
798     }
799
800     g_test_add_data_func_full(
801         tmp = g_strdup_printf("/ptimer/set_count policy=%s", policy_name),
802         g_memdup(&policy, 1), check_set_count, g_free);
803     g_free(tmp);
804
805     g_test_add_data_func_full(
806         tmp = g_strdup_printf("/ptimer/set_limit policy=%s", policy_name),
807         g_memdup(&policy, 1), check_set_limit, g_free);
808     g_free(tmp);
809
810     g_test_add_data_func_full(
811         tmp = g_strdup_printf("/ptimer/oneshot policy=%s", policy_name),
812         g_memdup(&policy, 1), check_oneshot, g_free);
813     g_free(tmp);
814
815     g_test_add_data_func_full(
816         tmp = g_strdup_printf("/ptimer/periodic policy=%s", policy_name),
817         g_memdup(&policy, 1), check_periodic, g_free);
818     g_free(tmp);
819
820     g_test_add_data_func_full(
821         tmp = g_strdup_printf("/ptimer/on_the_fly_mode_change policy=%s",
822                               policy_name),
823         g_memdup(&policy, 1), check_on_the_fly_mode_change, g_free);
824     g_free(tmp);
825
826     g_test_add_data_func_full(
827         tmp = g_strdup_printf("/ptimer/on_the_fly_period_change policy=%s",
828                               policy_name),
829         g_memdup(&policy, 1), check_on_the_fly_period_change, g_free);
830     g_free(tmp);
831
832     g_test_add_data_func_full(
833         tmp = g_strdup_printf("/ptimer/on_the_fly_freq_change policy=%s",
834                               policy_name),
835         g_memdup(&policy, 1), check_on_the_fly_freq_change, g_free);
836     g_free(tmp);
837
838     g_test_add_data_func_full(
839         tmp = g_strdup_printf("/ptimer/run_with_period_0 policy=%s",
840                               policy_name),
841         g_memdup(&policy, 1), check_run_with_period_0, g_free);
842     g_free(tmp);
843
844     g_test_add_data_func_full(
845         tmp = g_strdup_printf("/ptimer/run_with_delta_0 policy=%s",
846                               policy_name),
847         g_memdup(&policy, 1), check_run_with_delta_0, g_free);
848     g_free(tmp);
849
850     g_test_add_data_func_full(
851         tmp = g_strdup_printf("/ptimer/periodic_with_load_0 policy=%s",
852                               policy_name),
853         g_memdup(&policy, 1), check_periodic_with_load_0, g_free);
854     g_free(tmp);
855
856     g_test_add_data_func_full(
857         tmp = g_strdup_printf("/ptimer/oneshot_with_load_0 policy=%s",
858                               policy_name),
859         g_memdup(&policy, 1), check_oneshot_with_load_0, g_free);
860     g_free(tmp);
861 }
862
863 static void add_all_ptimer_policies_comb_tests(void)
864 {
865     int last_policy = PTIMER_POLICY_TRIGGER_ONLY_ON_DECREMENT;
866     int policy = PTIMER_POLICY_DEFAULT;
867
868     for (; policy < (last_policy << 1); policy++) {
869         if ((policy & PTIMER_POLICY_TRIGGER_ONLY_ON_DECREMENT) &&
870             (policy & PTIMER_POLICY_NO_IMMEDIATE_TRIGGER)) {
871             /* Incompatible policy flag settings -- don't try to test them */
872             continue;
873         }
874         add_ptimer_tests(policy);
875     }
876 }
877
878 int main(int argc, char **argv)
879 {
880     int i;
881
882     g_test_init(&argc, &argv, NULL);
883
884     for (i = 0; i < QEMU_CLOCK_MAX; i++) {
885         main_loop_tlg.tl[i] = g_new0(QEMUTimerList, 1);
886     }
887
888     add_all_ptimer_policies_comb_tests();
889
890     qtest_allowed = true;
891
892     return g_test_run();
893 }
This page took 0.070809 seconds and 4 git commands to generate.