[lng-odp] [PATCH v4] validation: system: add validation tests for odp_cpu_cycles_* calls

2016-01-15 Thread Ivan Khoronzhuk
https://bugs.linaro.org/show_bug.cgi?id=1906

Signed-off-by: Ivan Khoronzhuk 
---
Since v3:
- modified log "wrap is not detected"
- increased try num for diff to match 16 seconds
- decreased try num for resolution to match 1 second
- allow resolution to be up to max / 1024
- correct wrap detection for resolution

Since v2:
- added c <= max
- replaced etalon on tmp
- added msg about skip
- handled resolution wrap

 test/validation/system/system.c | 139 
 test/validation/system/system.h |   4 ++
 2 files changed, 143 insertions(+)

diff --git a/test/validation/system/system.c b/test/validation/system/system.c
index 7dc2cc0..400889c 100644
--- a/test/validation/system/system.c
+++ b/test/validation/system/system.c
@@ -10,6 +10,9 @@
 #include "test_debug.h"
 #include "system.h"
 
+#define DIFF_TRY_NUM   160
+#define RES_TRY_NUM10
+
 void system_test_odp_version_numbers(void)
 {
int char_ok = 0;
@@ -40,6 +43,138 @@ void system_test_odp_cpu_count(void)
CU_ASSERT(0 < cpus);
 }
 
+void system_test_odp_cpu_cycles(void)
+{
+   uint64_t c2, c1;
+
+   c1 = odp_cpu_cycles();
+   odp_time_wait_ns(100);
+   c2 = odp_cpu_cycles();
+
+   CU_ASSERT(c2 != c1);
+}
+
+void system_test_odp_cpu_cycles_max(void)
+{
+   uint64_t c2, c1;
+   uint64_t max1, max2;
+
+   max1 = odp_cpu_cycles_max();
+   odp_time_wait_ns(100);
+   max2 = odp_cpu_cycles_max();
+
+   CU_ASSERT(max1 >= UINT32_MAX / 2);
+   CU_ASSERT(max1 == max2);
+
+   c1 = odp_cpu_cycles();
+   odp_time_wait_ns(1000);
+   c2 = odp_cpu_cycles();
+
+   CU_ASSERT(c1 <= max1 && c2 <= max1);
+}
+
+void system_test_odp_cpu_cycles_diff(void)
+{
+   int i;
+   uint64_t c2, c1, c3;
+   uint64_t tmp, diff;
+
+   c2 = 100;
+   c1 = 39;
+
+   diff = odp_cpu_cycles_diff(c2, c2);
+   CU_ASSERT(diff == 0);
+
+   tmp = c2 - c1;
+   diff = odp_cpu_cycles_diff(c2, c1);
+   CU_ASSERT(diff == tmp);
+
+   tmp = c1 + (odp_cpu_cycles_max() - c2) + 1;
+   diff = odp_cpu_cycles_diff(c1, c2);
+   CU_ASSERT(diff == tmp);
+
+   c3 = odp_cpu_cycles();
+
+   /* must handle one wrap */
+   for (i = 0; i < DIFF_TRY_NUM; i++) {
+   c1 = odp_cpu_cycles();
+   odp_time_wait_ns(100 * ODP_TIME_MSEC_IN_NS + i);
+   c2 = odp_cpu_cycles();
+
+   CU_ASSERT(c2 != c1);
+
+   if (c2 > c1)
+   tmp = c2 - c1;
+   else
+   tmp = c2 + (odp_cpu_cycles_max() - c1) + 1;
+
+   diff = odp_cpu_cycles_diff(c2, c1);
+   CU_ASSERT(diff == tmp);
+
+   /* wrap is detected and verified */
+   if (c2 < c1)
+   break;
+   }
+
+   /* wrap was detected, no need to continue */
+   if (i < DIFF_TRY_NUM)
+   return;
+
+   CU_ASSERT(odp_cpu_cycles_max() > UINT32_MAX);
+   CU_ASSERT((odp_cpu_cycles_max() - c3) > UINT32_MAX);
+
+   printf("wrap was not detected...");
+}
+
+void system_test_odp_cpu_cycles_resolution(void)
+{
+   int i;
+   uint64_t rest;
+   uint64_t res, diff;
+   uint64_t c2, c1, max;
+
+   max = odp_cpu_cycles_max();
+
+   res = odp_cpu_cycles_resolution();
+   CU_ASSERT(res != 0);
+   CU_ASSERT(res < max / 1024);
+
+   /* check resolution for wrap */
+   c1 = max - 2 * res;
+   do
+   c2 = odp_cpu_cycles();
+   while (c1 < c2);
+
+   diff = odp_cpu_cycles_diff(c1, c2);
+   rest = diff % res;
+   CU_ASSERT(rest == 0);
+
+   /*
+* must be a multiple of resolution in
+* whole interval till wrap, in another
+* case resolution is set incorrectly
+*/
+   for (i = 0; i < RES_TRY_NUM; i++) {
+   c1 = odp_cpu_cycles();
+   odp_time_wait_ns(100 * ODP_TIME_MSEC_IN_NS + i);
+   c2 = odp_cpu_cycles();
+
+   diff = odp_cpu_cycles_diff(c2, c1);
+   rest = diff % res;
+   CU_ASSERT(rest == 0);
+
+   rest = c1 % res;
+   CU_ASSERT(rest == 0);
+
+   rest = c2 % res;
+   CU_ASSERT(rest == 0);
+
+   /* wrap is detected and verified */
+   if (c2 < c1)
+   break;
+   }
+}
+
 void system_test_odp_sys_cache_line_size(void)
 {
uint64_t cache_size;
@@ -91,6 +226,10 @@ odp_testinfo_t system_suite[] = {
ODP_TEST_INFO(system_test_odp_sys_page_size),
ODP_TEST_INFO(system_test_odp_sys_huge_page_size),
ODP_TEST_INFO(system_test_odp_sys_cpu_hz),
+   ODP_TEST_INFO(system_test_odp_cpu_cycles),
+   ODP_TEST_INFO(system_test_odp_cpu_cycles_max),
+   ODP_TEST_INFO(system_test_odp_cpu_cycles_diff),
+   ODP_TEST_INFO(system_test_odp_cpu_cycles_resolution),
ODP_TEST_INFO_NULL,
 };
 
diff --git a/test/

Re: [lng-odp] [PATCH v4] validation: system: add validation tests for odp_cpu_cycles_* calls

2016-01-15 Thread Ivan Khoronzhuk

forget to remove comment for resolution loop.
so v5 is relevant.

On 15.01.16 16:50, Ivan Khoronzhuk wrote:

https://bugs.linaro.org/show_bug.cgi?id=1906

Signed-off-by: Ivan Khoronzhuk 
---
Since v3:
- modified log "wrap is not detected"
- increased try num for diff to match 16 seconds
- decreased try num for resolution to match 1 second
- allow resolution to be up to max / 1024
- correct wrap detection for resolution

Since v2:
- added c <= max
- replaced etalon on tmp
- added msg about skip
- handled resolution wrap

  test/validation/system/system.c | 139 
  test/validation/system/system.h |   4 ++
  2 files changed, 143 insertions(+)

diff --git a/test/validation/system/system.c b/test/validation/system/system.c
index 7dc2cc0..400889c 100644
--- a/test/validation/system/system.c
+++ b/test/validation/system/system.c
@@ -10,6 +10,9 @@
  #include "test_debug.h"
  #include "system.h"

+#define DIFF_TRY_NUM   160
+#define RES_TRY_NUM10
+
  void system_test_odp_version_numbers(void)
  {
int char_ok = 0;
@@ -40,6 +43,138 @@ void system_test_odp_cpu_count(void)
CU_ASSERT(0 < cpus);
  }

+void system_test_odp_cpu_cycles(void)
+{
+   uint64_t c2, c1;
+
+   c1 = odp_cpu_cycles();
+   odp_time_wait_ns(100);
+   c2 = odp_cpu_cycles();
+
+   CU_ASSERT(c2 != c1);
+}
+
+void system_test_odp_cpu_cycles_max(void)
+{
+   uint64_t c2, c1;
+   uint64_t max1, max2;
+
+   max1 = odp_cpu_cycles_max();
+   odp_time_wait_ns(100);
+   max2 = odp_cpu_cycles_max();
+
+   CU_ASSERT(max1 >= UINT32_MAX / 2);
+   CU_ASSERT(max1 == max2);
+
+   c1 = odp_cpu_cycles();
+   odp_time_wait_ns(1000);
+   c2 = odp_cpu_cycles();
+
+   CU_ASSERT(c1 <= max1 && c2 <= max1);
+}
+
+void system_test_odp_cpu_cycles_diff(void)
+{
+   int i;
+   uint64_t c2, c1, c3;
+   uint64_t tmp, diff;
+
+   c2 = 100;
+   c1 = 39;
+
+   diff = odp_cpu_cycles_diff(c2, c2);
+   CU_ASSERT(diff == 0);
+
+   tmp = c2 - c1;
+   diff = odp_cpu_cycles_diff(c2, c1);
+   CU_ASSERT(diff == tmp);
+
+   tmp = c1 + (odp_cpu_cycles_max() - c2) + 1;
+   diff = odp_cpu_cycles_diff(c1, c2);
+   CU_ASSERT(diff == tmp);
+
+   c3 = odp_cpu_cycles();
+
+   /* must handle one wrap */
+   for (i = 0; i < DIFF_TRY_NUM; i++) {
+   c1 = odp_cpu_cycles();
+   odp_time_wait_ns(100 * ODP_TIME_MSEC_IN_NS + i);
+   c2 = odp_cpu_cycles();
+
+   CU_ASSERT(c2 != c1);
+
+   if (c2 > c1)
+   tmp = c2 - c1;
+   else
+   tmp = c2 + (odp_cpu_cycles_max() - c1) + 1;
+
+   diff = odp_cpu_cycles_diff(c2, c1);
+   CU_ASSERT(diff == tmp);
+
+   /* wrap is detected and verified */
+   if (c2 < c1)
+   break;
+   }
+
+   /* wrap was detected, no need to continue */
+   if (i < DIFF_TRY_NUM)
+   return;
+
+   CU_ASSERT(odp_cpu_cycles_max() > UINT32_MAX);
+   CU_ASSERT((odp_cpu_cycles_max() - c3) > UINT32_MAX);
+
+   printf("wrap was not detected...");
+}
+
+void system_test_odp_cpu_cycles_resolution(void)
+{
+   int i;
+   uint64_t rest;
+   uint64_t res, diff;
+   uint64_t c2, c1, max;
+
+   max = odp_cpu_cycles_max();
+
+   res = odp_cpu_cycles_resolution();
+   CU_ASSERT(res != 0);
+   CU_ASSERT(res < max / 1024);
+
+   /* check resolution for wrap */
+   c1 = max - 2 * res;
+   do
+   c2 = odp_cpu_cycles();
+   while (c1 < c2);
+
+   diff = odp_cpu_cycles_diff(c1, c2);
+   rest = diff % res;
+   CU_ASSERT(rest == 0);
+
+   /*
+* must be a multiple of resolution in
+* whole interval till wrap, in another
+* case resolution is set incorrectly
+*/
+   for (i = 0; i < RES_TRY_NUM; i++) {
+   c1 = odp_cpu_cycles();
+   odp_time_wait_ns(100 * ODP_TIME_MSEC_IN_NS + i);
+   c2 = odp_cpu_cycles();
+
+   diff = odp_cpu_cycles_diff(c2, c1);
+   rest = diff % res;
+   CU_ASSERT(rest == 0);
+
+   rest = c1 % res;
+   CU_ASSERT(rest == 0);
+
+   rest = c2 % res;
+   CU_ASSERT(rest == 0);
+
+   /* wrap is detected and verified */
+   if (c2 < c1)
+   break;
+   }
+}
+
  void system_test_odp_sys_cache_line_size(void)
  {
uint64_t cache_size;
@@ -91,6 +226,10 @@ odp_testinfo_t system_suite[] = {
ODP_TEST_INFO(system_test_odp_sys_page_size),
ODP_TEST_INFO(system_test_odp_sys_huge_page_size),
ODP_TEST_INFO(system_test_odp_sys_cpu_hz),
+   ODP_TEST_INFO(system_test_odp_cpu_cycles),
+   ODP_TEST_INFO(system_test_odp_cpu_cycles_max),
+   ODP_TEST_INFO(system_test_odp_cpu_cycles_dif