[API-NEXT] test: random: adding thread based test for random

Message ID 1484308032-19366-1-git-send-email-christophe.milard@linaro.org
State New
Headers show

Commit Message

Christophe Milard Jan. 13, 2017, 11:47 a.m.
checking the thread safety of odp_random.

Signed-off-by: Christophe Milard <christophe.milard@linaro.org>

---
 test/common_plat/validation/api/random/random.c | 46 +++++++++++++++++++++++++
 test/common_plat/validation/api/random/random.h |  1 +
 2 files changed, 47 insertions(+)

-- 
2.7.4

Comments

Bill Fischofer Jan. 13, 2017, 12:51 p.m. | #1
On Fri, Jan 13, 2017 at 5:47 AM, Christophe Milard
<christophe.milard@linaro.org> wrote:
> checking the thread safety of odp_random.

>

> Signed-off-by: Christophe Milard <christophe.milard@linaro.org>

> ---

>  test/common_plat/validation/api/random/random.c | 46 +++++++++++++++++++++++++

>  test/common_plat/validation/api/random/random.h |  1 +

>  2 files changed, 47 insertions(+)

>

> diff --git a/test/common_plat/validation/api/random/random.c b/test/common_plat/validation/api/random/random.c

> index a0e2ef7..17234db 100644

> --- a/test/common_plat/validation/api/random/random.c

> +++ b/test/common_plat/validation/api/random/random.c

> @@ -8,6 +8,8 @@

>  #include <odp_cunit_common.h>

>  #include "random.h"

>

> +#define STRESS_TEST_SZ 100000

> +

>  void random_test_get_size(void)

>  {

>         int32_t ret;

> @@ -61,10 +63,54 @@ void random_test_repeat(void)

>         CU_ASSERT(memcmp(buf1, buf2, sizeof(buf1)) == 0);

>  }

>

> +/*

> + * thread part for the random_test_stress

> + */

> +static int run_test_stress(void *arg ODP_UNUSED)

> +{

> +       int32_t i;

> +       int32_t rc;

> +       uint8_t buf[4096];

> +

> +       odp_random_kind_t max_kind = odp_random_max_kind();

> +

> +       /* generate plenty of random data of different length and different

> +        * quality (using the 2 first bytes of the previous iteration buffer as

> +        * length and quality)


This may be a problem. If you're looking to stress the locking code
these should be the same quality level (max_kind) since I believe each
different kind may have its own locks. So spreading things out like
that will only result in less lock contention.

> +        */

> +       for (i = 0; i < STRESS_TEST_SZ; i++) {

> +               rc = odp_random_data(buf, buf[0] + 2, buf[1] % (max_kind + 1));

> +               CU_ASSERT(rc > 0);

> +       }

> +

> +       fflush(stdout);

> +       return CU_get_number_of_failures();

> +}

> +

> +/*

> + * stress tests

> + */

> +void random_test_stress(void)

> +{

> +       pthrd_arg thrdarg;

> +       odp_cpumask_t unused;

> +

> +       thrdarg.numthrds = odp_cpumask_default_worker(&unused, 0);

> +       if (thrdarg.numthrds > MAX_WORKERS)

> +               thrdarg.numthrds = MAX_WORKERS;

> +

> +       /* create threads */

> +       odp_cunit_thread_create(run_test_stress, &thrdarg);

> +

> +       /* wait for all thread endings: */

> +       CU_ASSERT(odp_cunit_thread_exit(&thrdarg) >= 0);

> +}

> +

>  odp_testinfo_t random_suite[] = {

>         ODP_TEST_INFO(random_test_get_size),

>         ODP_TEST_INFO(random_test_kind),

>         ODP_TEST_INFO(random_test_repeat),

> +       ODP_TEST_INFO(random_test_stress),

>         ODP_TEST_INFO_NULL,

>  };

>

> diff --git a/test/common_plat/validation/api/random/random.h b/test/common_plat/validation/api/random/random.h

> index c4bca78..f9538aa 100644

> --- a/test/common_plat/validation/api/random/random.h

> +++ b/test/common_plat/validation/api/random/random.h

> @@ -13,6 +13,7 @@

>  void random_test_get_size(void);

>  void random_test_kind(void);

>  void random_test_repeat(void);

> +void random_test_stress(void);

>

>  /* test arrays: */

>  extern odp_testinfo_t random_suite[];

> --

> 2.7.4

>
Maxim Uvarov Jan. 13, 2017, 1:12 p.m. | #2
On 01/13/17 14:47, Christophe Milard wrote:
> checking the thread safety of odp_random.

> 

> Signed-off-by: Christophe Milard <christophe.milard@linaro.org>

> ---

>  test/common_plat/validation/api/random/random.c | 46 +++++++++++++++++++++++++

>  test/common_plat/validation/api/random/random.h |  1 +

>  2 files changed, 47 insertions(+)

> 

> diff --git a/test/common_plat/validation/api/random/random.c b/test/common_plat/validation/api/random/random.c

> index a0e2ef7..17234db 100644

> --- a/test/common_plat/validation/api/random/random.c

> +++ b/test/common_plat/validation/api/random/random.c

> @@ -8,6 +8,8 @@

>  #include <odp_cunit_common.h>

>  #include "random.h"

>  

> +#define STRESS_TEST_SZ 100000

> +

>  void random_test_get_size(void)

>  {

>  	int32_t ret;

> @@ -61,10 +63,54 @@ void random_test_repeat(void)

>  	CU_ASSERT(memcmp(buf1, buf2, sizeof(buf1)) == 0);

>  }

>  

> +/*

> + * thread part for the random_test_stress

> + */

> +static int run_test_stress(void *arg ODP_UNUSED)

> +{

> +	int32_t i;

> +	int32_t rc;

> +	uint8_t buf[4096];

> +

> +	odp_random_kind_t max_kind = odp_random_max_kind();

> +

> +	/* generate plenty of random data of different length and different

> +	 * quality (using the 2 first bytes of the previous iteration buffer as

> +	 * length and quality)

> +	 */

> +	for (i = 0; i < STRESS_TEST_SZ; i++) {

> +		rc = odp_random_data(buf, buf[0] + 2, buf[1] % (max_kind + 1));

> +		CU_ASSERT(rc > 0);

> +	}

> +

> +	fflush(stdout);



is fflush() for ASSERT? isn't it stderr?

> +	return CU_get_number_of_failures();

> +}

> +

> +/*

> + * stress tests

> + */

> +void random_test_stress(void)

> +{

> +	pthrd_arg thrdarg;

> +	odp_cpumask_t unused;

> +

> +	thrdarg.numthrds = odp_cpumask_default_worker(&unused, 0);

> +	if (thrdarg.numthrds > MAX_WORKERS)

> +		thrdarg.numthrds = MAX_WORKERS;

> +

> +	/* create threads */

> +	odp_cunit_thread_create(run_test_stress, &thrdarg);

> +

> +	/* wait for all thread endings: */

> +	CU_ASSERT(odp_cunit_thread_exit(&thrdarg) >= 0);

> +}

> +

>  odp_testinfo_t random_suite[] = {

>  	ODP_TEST_INFO(random_test_get_size),

>  	ODP_TEST_INFO(random_test_kind),

>  	ODP_TEST_INFO(random_test_repeat),

> +	ODP_TEST_INFO(random_test_stress),

>  	ODP_TEST_INFO_NULL,

>  };

>  

> diff --git a/test/common_plat/validation/api/random/random.h b/test/common_plat/validation/api/random/random.h

> index c4bca78..f9538aa 100644

> --- a/test/common_plat/validation/api/random/random.h

> +++ b/test/common_plat/validation/api/random/random.h

> @@ -13,6 +13,7 @@

>  void random_test_get_size(void);

>  void random_test_kind(void);

>  void random_test_repeat(void);

> +void random_test_stress(void);

>  

>  /* test arrays: */

>  extern odp_testinfo_t random_suite[];

>
Christophe Milard Jan. 13, 2017, 1:20 p.m. | #3
I our case, you are right (I have actually modified this test to hunt
our problem), but in general itsn't it better with a mix?
Alternatively, I could do a test for each entropy. That would increase
the chances to see thread problems for one entropy but decrease the
chances to see inter-entropy problems.

your pick.

On 13 January 2017 at 13:51, Bill Fischofer <bill.fischofer@linaro.org> wrote:
> On Fri, Jan 13, 2017 at 5:47 AM, Christophe Milard

> <christophe.milard@linaro.org> wrote:

>> checking the thread safety of odp_random.

>>

>> Signed-off-by: Christophe Milard <christophe.milard@linaro.org>

>> ---

>>  test/common_plat/validation/api/random/random.c | 46 +++++++++++++++++++++++++

>>  test/common_plat/validation/api/random/random.h |  1 +

>>  2 files changed, 47 insertions(+)

>>

>> diff --git a/test/common_plat/validation/api/random/random.c b/test/common_plat/validation/api/random/random.c

>> index a0e2ef7..17234db 100644

>> --- a/test/common_plat/validation/api/random/random.c

>> +++ b/test/common_plat/validation/api/random/random.c

>> @@ -8,6 +8,8 @@

>>  #include <odp_cunit_common.h>

>>  #include "random.h"

>>

>> +#define STRESS_TEST_SZ 100000

>> +

>>  void random_test_get_size(void)

>>  {

>>         int32_t ret;

>> @@ -61,10 +63,54 @@ void random_test_repeat(void)

>>         CU_ASSERT(memcmp(buf1, buf2, sizeof(buf1)) == 0);

>>  }

>>

>> +/*

>> + * thread part for the random_test_stress

>> + */

>> +static int run_test_stress(void *arg ODP_UNUSED)

>> +{

>> +       int32_t i;

>> +       int32_t rc;

>> +       uint8_t buf[4096];

>> +

>> +       odp_random_kind_t max_kind = odp_random_max_kind();

>> +

>> +       /* generate plenty of random data of different length and different

>> +        * quality (using the 2 first bytes of the previous iteration buffer as

>> +        * length and quality)

>

> This may be a problem. If you're looking to stress the locking code

> these should be the same quality level (max_kind) since I believe each

> different kind may have its own locks. So spreading things out like

> that will only result in less lock contention.

>

>> +        */

>> +       for (i = 0; i < STRESS_TEST_SZ; i++) {

>> +               rc = odp_random_data(buf, buf[0] + 2, buf[1] % (max_kind + 1));

>> +               CU_ASSERT(rc > 0);

>> +       }

>> +

>> +       fflush(stdout);

>> +       return CU_get_number_of_failures();

>> +}

>> +

>> +/*

>> + * stress tests

>> + */

>> +void random_test_stress(void)

>> +{

>> +       pthrd_arg thrdarg;

>> +       odp_cpumask_t unused;

>> +

>> +       thrdarg.numthrds = odp_cpumask_default_worker(&unused, 0);

>> +       if (thrdarg.numthrds > MAX_WORKERS)

>> +               thrdarg.numthrds = MAX_WORKERS;

>> +

>> +       /* create threads */

>> +       odp_cunit_thread_create(run_test_stress, &thrdarg);

>> +

>> +       /* wait for all thread endings: */

>> +       CU_ASSERT(odp_cunit_thread_exit(&thrdarg) >= 0);

>> +}

>> +

>>  odp_testinfo_t random_suite[] = {

>>         ODP_TEST_INFO(random_test_get_size),

>>         ODP_TEST_INFO(random_test_kind),

>>         ODP_TEST_INFO(random_test_repeat),

>> +       ODP_TEST_INFO(random_test_stress),

>>         ODP_TEST_INFO_NULL,

>>  };

>>

>> diff --git a/test/common_plat/validation/api/random/random.h b/test/common_plat/validation/api/random/random.h

>> index c4bca78..f9538aa 100644

>> --- a/test/common_plat/validation/api/random/random.h

>> +++ b/test/common_plat/validation/api/random/random.h

>> @@ -13,6 +13,7 @@

>>  void random_test_get_size(void);

>>  void random_test_kind(void);

>>  void random_test_repeat(void);

>> +void random_test_stress(void);

>>

>>  /* test arrays: */

>>  extern odp_testinfo_t random_suite[];

>> --

>> 2.7.4

>>
Christophe Milard Jan. 13, 2017, 1:23 p.m. | #4
On 13 January 2017 at 14:12, Maxim Uvarov <maxim.uvarov@linaro.org> wrote:
> On 01/13/17 14:47, Christophe Milard wrote:

>> checking the thread safety of odp_random.

>>

>> Signed-off-by: Christophe Milard <christophe.milard@linaro.org>

>> ---

>>  test/common_plat/validation/api/random/random.c | 46 +++++++++++++++++++++++++

>>  test/common_plat/validation/api/random/random.h |  1 +

>>  2 files changed, 47 insertions(+)

>>

>> diff --git a/test/common_plat/validation/api/random/random.c b/test/common_plat/validation/api/random/random.c

>> index a0e2ef7..17234db 100644

>> --- a/test/common_plat/validation/api/random/random.c

>> +++ b/test/common_plat/validation/api/random/random.c

>> @@ -8,6 +8,8 @@

>>  #include <odp_cunit_common.h>

>>  #include "random.h"

>>

>> +#define STRESS_TEST_SZ 100000

>> +

>>  void random_test_get_size(void)

>>  {

>>       int32_t ret;

>> @@ -61,10 +63,54 @@ void random_test_repeat(void)

>>       CU_ASSERT(memcmp(buf1, buf2, sizeof(buf1)) == 0);

>>  }

>>

>> +/*

>> + * thread part for the random_test_stress

>> + */

>> +static int run_test_stress(void *arg ODP_UNUSED)

>> +{

>> +     int32_t i;

>> +     int32_t rc;

>> +     uint8_t buf[4096];

>> +

>> +     odp_random_kind_t max_kind = odp_random_max_kind();

>> +

>> +     /* generate plenty of random data of different length and different

>> +      * quality (using the 2 first bytes of the previous iteration buffer as

>> +      * length and quality)

>> +      */

>> +     for (i = 0; i < STRESS_TEST_SZ; i++) {

>> +             rc = odp_random_data(buf, buf[0] + 2, buf[1] % (max_kind + 1));

>> +             CU_ASSERT(rc > 0);

>> +     }

>> +

>> +     fflush(stdout);

>

>

> is fflush() for ASSERT? isn't it stderr?


It helps for debug output (ODP_DBG and I guess ODP_PRINT), I noticed.
I can remove it if you dont like it :-)

>

>> +     return CU_get_number_of_failures();

>> +}

>> +

>> +/*

>> + * stress tests

>> + */

>> +void random_test_stress(void)

>> +{

>> +     pthrd_arg thrdarg;

>> +     odp_cpumask_t unused;

>> +

>> +     thrdarg.numthrds = odp_cpumask_default_worker(&unused, 0);

>> +     if (thrdarg.numthrds > MAX_WORKERS)

>> +             thrdarg.numthrds = MAX_WORKERS;

>> +

>> +     /* create threads */

>> +     odp_cunit_thread_create(run_test_stress, &thrdarg);

>> +

>> +     /* wait for all thread endings: */

>> +     CU_ASSERT(odp_cunit_thread_exit(&thrdarg) >= 0);

>> +}

>> +

>>  odp_testinfo_t random_suite[] = {

>>       ODP_TEST_INFO(random_test_get_size),

>>       ODP_TEST_INFO(random_test_kind),

>>       ODP_TEST_INFO(random_test_repeat),

>> +     ODP_TEST_INFO(random_test_stress),

>>       ODP_TEST_INFO_NULL,

>>  };

>>

>> diff --git a/test/common_plat/validation/api/random/random.h b/test/common_plat/validation/api/random/random.h

>> index c4bca78..f9538aa 100644

>> --- a/test/common_plat/validation/api/random/random.h

>> +++ b/test/common_plat/validation/api/random/random.h

>> @@ -13,6 +13,7 @@

>>  void random_test_get_size(void);

>>  void random_test_kind(void);

>>  void random_test_repeat(void);

>> +void random_test_stress(void);

>>

>>  /* test arrays: */

>>  extern odp_testinfo_t random_suite[];

>>

>

Patch

diff --git a/test/common_plat/validation/api/random/random.c b/test/common_plat/validation/api/random/random.c
index a0e2ef7..17234db 100644
--- a/test/common_plat/validation/api/random/random.c
+++ b/test/common_plat/validation/api/random/random.c
@@ -8,6 +8,8 @@ 
 #include <odp_cunit_common.h>
 #include "random.h"
 
+#define STRESS_TEST_SZ 100000
+
 void random_test_get_size(void)
 {
 	int32_t ret;
@@ -61,10 +63,54 @@  void random_test_repeat(void)
 	CU_ASSERT(memcmp(buf1, buf2, sizeof(buf1)) == 0);
 }
 
+/*
+ * thread part for the random_test_stress
+ */
+static int run_test_stress(void *arg ODP_UNUSED)
+{
+	int32_t i;
+	int32_t rc;
+	uint8_t buf[4096];
+
+	odp_random_kind_t max_kind = odp_random_max_kind();
+
+	/* generate plenty of random data of different length and different
+	 * quality (using the 2 first bytes of the previous iteration buffer as
+	 * length and quality)
+	 */
+	for (i = 0; i < STRESS_TEST_SZ; i++) {
+		rc = odp_random_data(buf, buf[0] + 2, buf[1] % (max_kind + 1));
+		CU_ASSERT(rc > 0);
+	}
+
+	fflush(stdout);
+	return CU_get_number_of_failures();
+}
+
+/*
+ * stress tests
+ */
+void random_test_stress(void)
+{
+	pthrd_arg thrdarg;
+	odp_cpumask_t unused;
+
+	thrdarg.numthrds = odp_cpumask_default_worker(&unused, 0);
+	if (thrdarg.numthrds > MAX_WORKERS)
+		thrdarg.numthrds = MAX_WORKERS;
+
+	/* create threads */
+	odp_cunit_thread_create(run_test_stress, &thrdarg);
+
+	/* wait for all thread endings: */
+	CU_ASSERT(odp_cunit_thread_exit(&thrdarg) >= 0);
+}
+
 odp_testinfo_t random_suite[] = {
 	ODP_TEST_INFO(random_test_get_size),
 	ODP_TEST_INFO(random_test_kind),
 	ODP_TEST_INFO(random_test_repeat),
+	ODP_TEST_INFO(random_test_stress),
 	ODP_TEST_INFO_NULL,
 };
 
diff --git a/test/common_plat/validation/api/random/random.h b/test/common_plat/validation/api/random/random.h
index c4bca78..f9538aa 100644
--- a/test/common_plat/validation/api/random/random.h
+++ b/test/common_plat/validation/api/random/random.h
@@ -13,6 +13,7 @@ 
 void random_test_get_size(void);
 void random_test_kind(void);
 void random_test_repeat(void);
+void random_test_stress(void);
 
 /* test arrays: */
 extern odp_testinfo_t random_suite[];