diff options
Diffstat (limited to 'jrt/tests/com/yahoo/jrt/SchedulerTest.java')
-rw-r--r-- | jrt/tests/com/yahoo/jrt/SchedulerTest.java | 238 |
1 files changed, 238 insertions, 0 deletions
diff --git a/jrt/tests/com/yahoo/jrt/SchedulerTest.java b/jrt/tests/com/yahoo/jrt/SchedulerTest.java new file mode 100644 index 00000000000..785bc3ff719 --- /dev/null +++ b/jrt/tests/com/yahoo/jrt/SchedulerTest.java @@ -0,0 +1,238 @@ +// Copyright 2016 Yahoo Inc. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. +package com.yahoo.jrt; + +import java.util.Random; + +public class SchedulerTest extends junit.framework.TestCase { + + long now; // fake time + Scheduler scheduler; + + private class MyTask implements Runnable { + private Task task; + private long target; + private long actual = 0; + private boolean done = false; + private boolean multiple = false; + + public MyTask(long target) { + task = new Task(scheduler, this); + this.target = target; + } + + public void schedule() { + task.schedule(target / 1000.0); + } + + public boolean unschedule() { + return task.unschedule(); + } + + public boolean kill() { + return task.kill(); + } + + public boolean done() { + return done; + } + + public boolean check() { + if (!done || multiple) { + return false; + } + if (actual < target) { + return false; + } + // 2 * Scheduler.TICK == 200 + return ((actual - target) <= 200); + } + + public void run() { + multiple = done; + done = true; + actual = now; + } + } + + private class RTTask implements Runnable { + private Task task; + private int cnt = 0; + + public RTTask() { + task = new Task(scheduler, this); + } + + public Task task() { + return task; + } + + public void schedule() { + task.scheduleNow(); + } + + public boolean unschedule() { + return task.unschedule(); + } + + public boolean kill() { + return task.kill(); + } + + public int cnt() { + return cnt; + } + + public void run() { + cnt++; + task.scheduleNow(); + } + } + + public SchedulerTest(String name) { + super(name); + } + + public void setUp() { + now = 0; + scheduler = new Scheduler(now); + } + + public void tearDown() { + scheduler = null; + } + + public void testTimeliness() { + Random rand = new Random(73201242); + + RTTask rt1 = new RTTask(); + RTTask rt2 = new RTTask(); + RTTask rt3 = new RTTask(); + rt1.schedule(); + rt2.schedule(); + rt3.schedule(); + + MyTask[] tasks = new MyTask[250000]; + for (int i = 0; i < tasks.length; i++) { + tasks[i] = new MyTask(rand.nextInt(131072)); + tasks[i].schedule(); + } + int iterations = 0; + while (now < 135000) { + now += 10; + scheduler.checkTasks(now); + iterations++; + } + assertEquals(iterations, rt1.cnt()); + assertEquals(iterations, rt2.cnt()); + assertEquals(iterations, rt3.cnt()); + for (int i = 0; i < tasks.length; i++) { + assertTrue(tasks[i].check()); + } + } + + public void testUnschedule() { + MyTask t1 = new MyTask(1000); + MyTask t2 = new MyTask(1000); + MyTask t3 = new MyTask(1000); + MyTask t4 = new MyTask(1000); + MyTask t5 = new MyTask(1000); + + RTTask rt1 = new RTTask(); + RTTask rt2 = new RTTask(); + RTTask rt3 = new RTTask(); + RTTask rt4 = new RTTask(); + RTTask rt5 = new RTTask(); + + assertFalse(t4.kill()); + + t1.schedule(); + t2.schedule(); + t3.schedule(); + t4.schedule(); + t5.schedule(); + + assertFalse(rt4.kill()); + + rt1.schedule(); + rt2.schedule(); + rt3.schedule(); + rt4.schedule(); + rt5.schedule(); + + assertTrue(t2.unschedule()); + assertTrue(t1.unschedule()); + assertTrue(t5.unschedule()); + + assertFalse(t2.unschedule()); + assertFalse(t1.unschedule()); + assertFalse(t5.unschedule()); + + t2.schedule(); + t1.schedule(); + assertTrue(t2.kill()); + t2.schedule(); + assertFalse(t2.kill()); + + int cnt = 0; + while (now < 5000) { + scheduler.checkTasks(now); + now += 10; + cnt++; + } + int old_cnt = cnt; + assertTrue(rt1.kill()); + assertTrue(rt3.unschedule()); + assertTrue(rt2.unschedule()); + rt1.schedule(); + rt2.schedule(); + while (now < 10000) { + scheduler.checkTasks(now); + now += 10; + cnt++; + } + + assertTrue(t1.check()); + assertFalse(t2.done()); + assertTrue(t3.check()); + assertFalse(t4.done()); + assertFalse(t5.done()); + + assertEquals(old_cnt, rt1.cnt()); + assertEquals(cnt, rt2.cnt()); + assertEquals(old_cnt, rt3.cnt()); + assertEquals(0, rt4.cnt()); + assertEquals(cnt, rt5.cnt()); + } + + public void testSlowEventLoop() { + scheduler.checkTasks(now); + now += 10000; + MyTask task1 = new MyTask(5000); + task1.schedule(); + int cnt1 = 0; + while (true) { + scheduler.checkTasks(now); + if (task1.done()) { + break; + } + cnt1++; + now += 10; + } + assertTrue(cnt1 > 400 && cnt1 < 500); + + scheduler.checkTasks(now); + now += 10000; + MyTask task2 = new MyTask(5000); + task2.schedule(); + int cnt2 = 0; + while (true) { + scheduler.checkTasks(now); + if (task2.done()) { + break; + } + cnt2++; + now += 10000; + } + assertTrue(cnt2 > 10 && cnt2 < 30); + } +} |