aboutsummaryrefslogtreecommitdiff
path: root/test/validation/api/timer
diff options
context:
space:
mode:
authorPetri Savolainen <petri.savolainen@nokia.com>2019-05-14 16:39:02 +0300
committerPetri Savolainen <petri.savolainen@nokia.com>2019-06-03 15:44:27 +0300
commit2600af0ade3c254ba00a935a38647d6d15611586 (patch)
treecd62c2e2b5621301479bfdeb8ce24b93b699160d /test/validation/api/timer
parent6280e54ea0a69276f3e1cbadd981f28dd2fb253a (diff)
validation: timer: use resolution capability
Limit min/max timeout values according to the used resolution. Most tests use the same resolution and min/max timeout settings. Signed-off-by: Petri Savolainen <petri.savolainen@nokia.com> Reviewed-by: Stanislaw Kardach <skardach@marvell.com>
Diffstat (limited to 'test/validation/api/timer')
-rw-r--r--test/validation/api/timer/timer.c152
1 files changed, 92 insertions, 60 deletions
diff --git a/test/validation/api/timer/timer.c b/test/validation/api/timer/timer.c
index ddccec2b1..1faef4e64 100644
--- a/test/validation/api/timer/timer.c
+++ b/test/validation/api/timer/timer.c
@@ -31,9 +31,7 @@
#define EXTRA_TIMERS 256
#define NAME "timer_pool"
-#define RES (10 * ODP_TIME_MSEC_IN_NS / 3)
-#define MIN_TMO (10 * ODP_TIME_MSEC_IN_NS / 3)
-#define MAX_TMO (1000000 * ODP_TIME_MSEC_IN_NS)
+#define THREE_POINT_THREE_MSEC (10 * ODP_TIME_MSEC_IN_NS / 3)
#define USER_PTR ((void *)0xdead)
#define TICK_INVALID (~(uint64_t)0)
@@ -46,19 +44,32 @@ struct test_timer {
};
typedef struct {
+ /* Default resolution / timeout parameters */
+ struct {
+ uint64_t res_ns;
+ uint64_t min_tmo;
+ uint64_t max_tmo;
+ } param;
+
/* Timeout pool handle used by all threads */
odp_pool_t tbp;
+
/* Timer pool handle used by all threads */
odp_timer_pool_t tp;
+
/* Barrier for thread synchronization */
odp_barrier_t test_barrier;
+
/* Count of timeouts delivered too late */
odp_atomic_u32_t ndelivtoolate;
+
/* Sum of all allocated timers from all threads. Thread-local
* caches may make this number lower than the capacity of the pool */
odp_atomic_u32_t timers_allocated;
+
/* Number of timers allocated per thread */
uint32_t timers_per_thread;
+
} global_shared_mem_t;
static global_shared_mem_t *global_mem;
@@ -68,6 +79,10 @@ static int timer_global_init(odp_instance_t *inst)
odp_shm_t global_shm;
odp_init_t init_param;
odph_helper_options_t helper_options;
+ odp_timer_capability_t capa;
+ odp_timer_res_capability_t res_capa;
+ uint64_t res_ns, min_tmo, max_tmo;
+ unsigned int range;
if (odph_options(&helper_options)) {
fprintf(stderr, "error: odph_options() failed.\n");
@@ -100,6 +115,46 @@ static int timer_global_init(odp_instance_t *inst)
/* Configure scheduler */
odp_schedule_config(NULL);
+ memset(&capa, 0, sizeof(capa));
+ if (odp_timer_capability(ODP_CLOCK_CPU, &capa)) {
+ fprintf(stderr, "Timer capability failed\n");
+ return -1;
+ }
+
+ /* By default 20 msec resolution */
+ res_ns = 20 * ODP_TIME_MSEC_IN_NS;
+ if (res_ns < capa.max_res.res_ns)
+ res_ns = capa.max_res.res_ns;
+
+ memset(&res_capa, 0, sizeof(res_capa));
+ res_capa.res_ns = res_ns;
+
+ if (odp_timer_res_capability(ODP_CLOCK_CPU, &res_capa)) {
+ fprintf(stderr, "Timer resolution capability failed\n");
+ return -1;
+ }
+
+ /* Try to keep min timeout error margin within +-20% */
+ min_tmo = 5 * res_ns;
+ if (min_tmo < res_capa.min_tmo)
+ min_tmo = res_capa.min_tmo;
+
+ /* Max 1 hour */
+ max_tmo = 3600 * ODP_TIME_SEC_IN_NS;
+ if (max_tmo > res_capa.max_tmo)
+ max_tmo = res_capa.max_tmo;
+
+ range = (RANGE_MS * 1000) + THREE_POINT_THREE_MSEC;
+ if ((max_tmo - min_tmo) < range) {
+ fprintf(stderr, "Validation test needs %u msec range\n", range);
+ return -1;
+ }
+
+ /* Default parameters for test cases */
+ global_mem->param.res_ns = res_ns;
+ global_mem->param.min_tmo = min_tmo;
+ global_mem->param.max_tmo = max_tmo;
+
return 0;
}
@@ -213,25 +268,19 @@ static void timer_test_timeout_pool_free(void)
static void timer_pool_create_destroy(void)
{
- odp_timer_capability_t timer_capa;
odp_timer_pool_param_t tparam;
odp_timer_pool_info_t info;
odp_timer_pool_t tp[2];
odp_timer_t tim;
odp_queue_t queue;
- uint64_t res_ns;
queue = odp_queue_create("timer_queue", NULL);
CU_ASSERT_FATAL(queue != ODP_QUEUE_INVALID);
- CU_ASSERT_FATAL(odp_timer_capability(ODP_CLOCK_CPU, &timer_capa) == 0);
-
- res_ns = 10 * timer_capa.highest_res_ns;
-
memset(&tparam, 0, sizeof(odp_timer_pool_param_t));
- tparam.res_ns = res_ns;
- tparam.min_tmo = 5 * res_ns;
- tparam.max_tmo = 10000 * tparam.min_tmo;
+ tparam.res_ns = global_mem->param.res_ns;
+ tparam.min_tmo = global_mem->param.min_tmo;
+ tparam.max_tmo = global_mem->param.max_tmo;
tparam.num_timers = 100;
tparam.priv = 0;
tparam.clk_src = ODP_CLOCK_CPU;
@@ -290,7 +339,6 @@ static void timer_test_event_type(odp_queue_type_t queue_type,
odp_pool_t pool;
odp_pool_param_t pool_param;
odp_queue_param_t queue_param;
- odp_timer_capability_t timer_capa;
odp_timer_pool_param_t timer_param;
odp_timer_pool_t timer_pool;
odp_queue_t queue;
@@ -299,24 +347,16 @@ static void timer_test_event_type(odp_queue_type_t queue_type,
odp_packet_t pkt;
odp_event_t ev;
odp_time_t t1, t2;
- uint64_t res_ns, period_ns, period_tick, duration_ns;
+ uint64_t period_ns, period_tick, duration_ns;
int i, ret, num_tmo;
int num = 5;
odp_timer_t timer[num];
- if (odp_timer_capability(ODP_CLOCK_CPU, &timer_capa))
- CU_FAIL_FATAL("Timer capability failed")
-
- res_ns = 20 * ODP_TIME_MSEC_IN_NS;
-
- if (timer_capa.highest_res_ns > res_ns)
- res_ns = timer_capa.highest_res_ns;
-
memset(&timer_param, 0, sizeof(timer_param));
- timer_param.res_ns = res_ns;
- timer_param.min_tmo = 5 * res_ns;
- period_ns = 2 * timer_param.min_tmo;
- timer_param.max_tmo = 100 * period_ns;
+ timer_param.res_ns = global_mem->param.res_ns;
+ timer_param.min_tmo = global_mem->param.min_tmo;
+ period_ns = 2 * global_mem->param.min_tmo;
+ timer_param.max_tmo = global_mem->param.max_tmo;
timer_param.num_timers = num;
timer_param.clk_src = ODP_CLOCK_CPU;
@@ -478,7 +518,6 @@ static void timer_test_queue_type(odp_queue_type_t queue_type)
uint64_t res_ns, period_ns, period_tick, test_period;
uint64_t diff_period, diff_test;
odp_pool_param_t params;
- odp_timer_capability_t timer_capa;
odp_time_t t0, t1, t2;
odp_pool_param_init(&params);
@@ -488,17 +527,11 @@ static void timer_test_queue_type(odp_queue_type_t queue_type)
pool = odp_pool_create("timeout_pool", &params);
CU_ASSERT_FATAL(pool != ODP_POOL_INVALID);
- if (odp_timer_capability(ODP_CLOCK_CPU, &timer_capa))
- CU_FAIL_FATAL("Timer capability failed")
-
- res_ns = 20 * ODP_TIME_MSEC_IN_NS;
+ res_ns = global_mem->param.res_ns;
- if (timer_capa.highest_res_ns > res_ns)
- res_ns = timer_capa.highest_res_ns;
-
- tparam.res_ns = res_ns;
- tparam.min_tmo = 5 * res_ns;
- tparam.max_tmo = 10000 * tparam.min_tmo;
+ tparam.res_ns = global_mem->param.res_ns;
+ tparam.min_tmo = global_mem->param.min_tmo;
+ tparam.max_tmo = global_mem->param.max_tmo;
tparam.num_timers = num + 1;
tparam.priv = 0;
tparam.clk_src = ODP_CLOCK_CPU;
@@ -641,7 +674,6 @@ static void timer_test_odp_timer_cancel(void)
odp_timeout_t tmo;
odp_timer_set_t rc;
uint64_t tick;
- odp_timer_capability_t timer_capa;
odp_pool_param_init(&params);
params.type = ODP_POOL_TIMEOUT;
@@ -652,13 +684,9 @@ static void timer_test_odp_timer_cancel(void)
if (pool == ODP_POOL_INVALID)
CU_FAIL_FATAL("Timeout pool create failed");
- if (odp_timer_capability(ODP_CLOCK_CPU, &timer_capa))
- CU_FAIL_FATAL("Get timer capability failed")
-
- tparam.res_ns = MAX(100 * ODP_TIME_MSEC_IN_NS,
- timer_capa.highest_res_ns);
- tparam.min_tmo = 1 * ODP_TIME_SEC_IN_NS;
- tparam.max_tmo = 10 * ODP_TIME_SEC_IN_NS;
+ tparam.res_ns = global_mem->param.res_ns;
+ tparam.min_tmo = global_mem->param.min_tmo;
+ tparam.max_tmo = global_mem->param.max_tmo;
tparam.num_timers = 1;
tparam.priv = 0;
tparam.clk_src = ODP_CLOCK_CPU;
@@ -682,7 +710,7 @@ static void timer_test_odp_timer_cancel(void)
if (ev == ODP_EVENT_INVALID)
CU_FAIL_FATAL("Failed to allocate timeout");
- tick = odp_timer_ns_to_tick(tp, 2 * ODP_TIME_SEC_IN_NS);
+ tick = odp_timer_ns_to_tick(tp, tparam.max_tmo / 2);
rc = odp_timer_set_rel(tim, tick, &ev);
if (rc != ODP_TIMER_SUCCESS)
@@ -826,6 +854,7 @@ static int worker_entrypoint(void *arg TEST_UNUSED)
odp_timer_pool_t tp = global_mem->tp;
odp_pool_t tbp = global_mem->tbp;
uint32_t num_timers = global_mem->timers_per_thread;
+ uint64_t min_tmo = global_mem->param.min_tmo;
queue = odp_queue_create("timer_queue", NULL);
if (queue == ODP_QUEUE_INVALID)
@@ -863,7 +892,8 @@ static int worker_entrypoint(void *arg TEST_UNUSED)
/* Initial set all timers with a random expiration time */
nset = 0;
for (i = 0; i < allocated; i++) {
- nsec = MIN_TMO + (rand_r(&seed) % RANGE_MS) * 1000000ULL;
+ nsec = min_tmo + THREE_POINT_THREE_MSEC +
+ (rand_r(&seed) % RANGE_MS) * 1000000ULL;
tck = odp_timer_current_tick(tp) +
odp_timer_ns_to_tick(tp, nsec);
timer_rc = odp_timer_set_abs(tt[i].tim, tck, &tt[i].ev);
@@ -918,7 +948,7 @@ static int worker_entrypoint(void *arg TEST_UNUSED)
/* Timer active => reset */
nreset++;
- nsec = MIN_TMO +
+ nsec = min_tmo + THREE_POINT_THREE_MSEC +
(rand_r(&seed) % RANGE_MS) * 1000000ULL;
tck = odp_timer_ns_to_tick(tp, nsec);
@@ -1018,7 +1048,7 @@ static void timer_test_odp_timer_all(void)
odp_cpumask_t unused;
odp_timer_pool_info_t tpinfo;
uint64_t ns, tick, ns2;
- uint64_t resolution_ns;
+ uint64_t res_ns, min_tmo, max_tmo;
uint32_t timers_allocated;
pthrd_arg thrdarg;
odp_pool_capability_t pool_capa;
@@ -1065,10 +1095,13 @@ static void timer_test_odp_timer_all(void)
tbp = global_mem->tbp;
/* Create a timer pool */
- resolution_ns = MAX(RES, timer_capa.highest_res_ns);
- tparam.res_ns = resolution_ns;
- tparam.min_tmo = MIN_TMO;
- tparam.max_tmo = MAX_TMO;
+ res_ns = global_mem->param.res_ns;
+ max_tmo = global_mem->param.max_tmo;
+ min_tmo = global_mem->param.min_tmo;
+
+ tparam.res_ns = res_ns;
+ tparam.min_tmo = min_tmo;
+ tparam.max_tmo = max_tmo;
tparam.num_timers = num_timers;
tparam.priv = 0;
tparam.clk_src = ODP_CLOCK_CPU;
@@ -1083,10 +1116,9 @@ static void timer_test_odp_timer_all(void)
if (odp_timer_pool_info(tp, &tpinfo) != 0)
CU_FAIL("odp_timer_pool_info");
CU_ASSERT(strcmp(tpinfo.name, NAME) == 0);
- CU_ASSERT(tpinfo.param.res_ns == MAX(RES,
- timer_capa.highest_res_ns));
- CU_ASSERT(tpinfo.param.min_tmo == MIN_TMO);
- CU_ASSERT(tpinfo.param.max_tmo == MAX_TMO);
+ CU_ASSERT(tpinfo.param.res_ns == res_ns);
+ CU_ASSERT(tpinfo.param.min_tmo == min_tmo);
+ CU_ASSERT(tpinfo.param.max_tmo == max_tmo);
CU_ASSERT(strcmp(tpinfo.name, NAME) == 0);
LOG_DBG("Timer pool handle: %" PRIu64 "\n", odp_timer_pool_to_u64(tp));
@@ -1106,17 +1138,17 @@ static void timer_test_odp_timer_all(void)
ns2 = odp_timer_tick_to_ns(tp, tick);
CU_ASSERT(ns2 == 0);
- for (ns = resolution_ns; ns < MAX_TMO; ns += resolution_ns) {
+ for (ns = res_ns; ns < max_tmo; ns += res_ns) {
tick = odp_timer_ns_to_tick(tp, ns);
ns2 = odp_timer_tick_to_ns(tp, tick);
- if (ns2 < ns - resolution_ns) {
+ if (ns2 < ns - res_ns) {
LOG_DBG("FAIL ns:%" PRIu64 " tick:%" PRIu64 " ns2:%"
PRIu64 "\n", ns, tick, ns2);
CU_FAIL("tick conversion: nsec too small\n");
}
- if (ns2 > ns + resolution_ns) {
+ if (ns2 > ns + res_ns) {
LOG_DBG("FAIL ns:%" PRIu64 " tick:%" PRIu64 " ns2:%"
PRIu64 "\n", ns, tick, ns2);
CU_FAIL("tick conversion: nsec too large\n");