[v2,1/1] validation: timer: fix test failure

Message ID 1518631213-21228-2-git-send-email-odpbot@yandex.ru
State Superseded
Headers show
Series
  • [v2,1/1] validation: timer: fix test failure
Related show

Commit Message

Github ODP bot Feb. 14, 2018, 6 p.m.
From: Dmitry Eremin-Solenikov <dmitry.ereminsolenikov@linaro.org>


timer_main test was regularly failing due to worker code receiving
timeout events for cancelled timers. I'm fixing worker code to handle
these events correctly, however this might signify a loophole in API
definition or in linux-generic implementation. Should application be able
to copy with timers that are cancelled after expiration (but before
event reception)? Should implementation mark such timers as non-fresh?

Signed-off-by: Dmitry Eremin-Solenikov <dmitry.ereminsolenikov@linaro.org>

Fixes: https://bugs.linaro.org/show_bug.cgi?id=3517
Signed-off-by: Dmitry Eremin-Solenikov <dmitry.ereminsolenikov@linaro.org>

---
/** Email created from pull request 479 (lumag:timer-fix)
 ** https://github.com/Linaro/odp/pull/479
 ** Patch: https://github.com/Linaro/odp/pull/479.patch
 ** Base sha: 41b3fa2cd994a7ef68290a07dcde5564e4640847
 ** Merge commit sha: d02fe9568e6e46919379706028fddba66ebe6865
 **/
 test/validation/api/timer/timer.c | 33 ++++++++++++++++++++++++---------
 1 file changed, 24 insertions(+), 9 deletions(-)

Patch

diff --git a/test/validation/api/timer/timer.c b/test/validation/api/timer/timer.c
index 7ea508aa0..da2dc05ca 100644
--- a/test/validation/api/timer/timer.c
+++ b/test/validation/api/timer/timer.c
@@ -282,15 +282,28 @@  static void handle_tmo(odp_event_t ev, bool stale, uint64_t prev_tick)
 		if (ttp && ttp->tick != TICK_INVALID)
 			CU_FAIL("Stale timeout for active timer");
 	} else {
-		if (!odp_timeout_fresh(tmo))
-			CU_FAIL("Wrong status (stale) for fresh timeout");
-		/* Fresh timeout => local timer must have matching tick */
-		if (ttp && ttp->tick != tick) {
-			LOG_DBG("Wrong tick: expected %" PRIu64
-				" actual %" PRIu64 "\n",
-				ttp->tick, tick);
-			CU_FAIL("odp_timeout_tick() wrong tick");
+		if (ttp && ttp->tick == TICK_INVALID) {
+			/* Timer was cancelled when it has already expired */
+
+			if (odp_timeout_fresh(tmo))
+				CU_FAIL("Wrong status (fresh) "
+					"for cancelled timeout");
+		} else {
+			if (!odp_timeout_fresh(tmo))
+				CU_FAIL("Wrong status (stale) "
+					"for fresh timeout");
+
+			/* Fresh timeout => local timer must have matching tick
+			 */
+			if (ttp && ttp->tick != tick) {
+				LOG_DBG("Wrong tick: expected %" PRIu64
+					" actual %" PRIu64 "\n",
+					ttp->tick, tick);
+				CU_FAIL("odp_timeout_tick() wrong tick");
+			}
 		}
+		if (ttp && ttp->ev != ODP_EVENT_INVALID)
+			CU_FAIL("Wrong state for fresh timer (event)");
 		/* Check that timeout was delivered 'timely' */
 		if (tick > odp_timer_current_tick(tp))
 			CU_FAIL("Timeout delivered early");
@@ -401,9 +414,11 @@  static int worker_entrypoint(void *arg TEST_UNUSED)
 		    (rand_r(&seed) % 2 == 0)) {
 			/* Timer active, cancel it */
 			rc = odp_timer_cancel(tt[i].tim, &tt[i].ev);
-			if (rc != 0)
+			if (rc != 0) {
 				/* Cancel failed, timer already expired */
 				ntoolate++;
+				LOG_DBG("Failed to cancel timer, probably already expired\n");
+			}
 			tt[i].tick = TICK_INVALID;
 			ncancel++;
 		} else {