diff options
author | WeiY <wei.a.yang@gmail.com> | 2013-09-01 18:28:35 +0800 |
---|---|---|
committer | Sebastian Huber <sebastian.huber@embedded-brains.de> | 2013-09-01 15:17:01 +0200 |
commit | 4238affc5f19ca8a0e15077e4fdd44443b6876a7 (patch) | |
tree | d8df54325f3c2f04bdef5c71897c63ac244dbf30 /testsuites | |
parent | smp: Add and use _Assert_Owner_of_giant() (diff) | |
download | rtems-4238affc5f19ca8a0e15077e4fdd44443b6876a7.tar.bz2 |
add atomic sub, and, or, compare_exchange test cases into smpatomic08
Diffstat (limited to 'testsuites')
-rw-r--r-- | testsuites/smptests/smpatomic08/init.c | 164 | ||||
-rw-r--r-- | testsuites/smptests/smpatomic08/smpatomic08.scn | 12 |
2 files changed, 175 insertions, 1 deletions
diff --git a/testsuites/smptests/smpatomic08/init.c b/testsuites/smptests/smpatomic08/init.c index 19c81e6bf1..d9256cf2c8 100644 --- a/testsuites/smptests/smpatomic08/init.c +++ b/testsuites/smptests/smpatomic08/init.c @@ -78,6 +78,8 @@ typedef struct { size_t worker_count; rtems_id stop_worker_timer_id; Atomic_Uint global_uint; + Atomic_Uint global_swap; + uint_fast32_t global_swap_t; uint_fast32_t per_worker_uint[CPU_COUNT]; uint32_t flag_counter; Atomic_Flag global_flag; @@ -207,9 +209,169 @@ static void test_atomic_flag_fini(test_context *ctx) rtems_test_assert(expected_counter == actual_counter); } +static void test_atomic_sub_init(test_context *ctx) +{ + _Atomic_Init_uint(&ctx->global_uint, 0xffffffff); +} + +static void test_atomic_sub_body(test_context *ctx, size_t worker_index) +{ + uint_fast32_t counter = 0xffffffff; + + while (!stop(ctx)) { + --counter; + _Atomic_Fetch_sub_uint(&ctx->global_uint, 1, ATOMIC_ORDER_RELAXED); + } + + ctx->per_worker_uint[worker_index] = 0xffffffff - counter; +} + +static void test_atomic_sub_fini(test_context *ctx) +{ + uint_fast32_t expected_counter = 0; + uint_fast32_t actual_counter; + size_t worker_index; + + printf("=== atomic sub test case ==\n"); + + for (worker_index = 0; worker_index < ctx->worker_count; ++worker_index) { + uint_fast32_t worker_counter = ctx->per_worker_uint[worker_index]; + + expected_counter += worker_counter; + + printf( + "atomic sub worker %zu counter: %" PRIuFAST32 "\n", + worker_index, + worker_counter + ); + } + + actual_counter = _Atomic_Load_uint(&ctx->global_uint, ATOMIC_ORDER_RELAXED); + actual_counter = 0xffffffff - actual_counter; + + printf( + "global counter: expected = %" PRIuFAST32 ", actual = %" PRIuFAST32 "\n", + expected_counter, + actual_counter + ); + + rtems_test_assert(expected_counter == actual_counter); +} + +static void test_atomic_compare_exchange_init(test_context *ctx) +{ + _Atomic_Init_uint(&ctx->global_swap, 0xffffffff); + ctx->global_swap_t = 0xffffffff; + ctx->flag_counter = 0; +} + +static void test_atomic_compare_exchange_body(test_context *ctx, size_t worker_index) +{ + uint_fast32_t counter = 0; + + while (!stop(ctx)) { + while (_Atomic_Compare_exchange_uint(&ctx->global_swap, &ctx->global_swap_t, + worker_index, ATOMIC_ORDER_ACQUIRE, ATOMIC_ORDER_RELAXED)) { + /* Wait */ + } + ++counter; + ++ctx->flag_counter; + _Atomic_Store_uint(&ctx->global_swap, 0, ATOMIC_ORDER_RELEASE); + } + + ctx->per_worker_uint[worker_index] = counter; +} + +static void test_atomic_compare_exchange_fini(test_context *ctx) +{ + uint_fast32_t expected_counter = 0; + uint_fast32_t actual_counter; + size_t worker_index; + + printf("=== atomic compare_exchange test case ==\n"); + + for (worker_index = 0; worker_index < ctx->worker_count; ++worker_index) { + uint_fast32_t worker_counter = ctx->per_worker_uint[worker_index]; + + expected_counter += worker_counter; + + printf( + "atomic compare_exchange worker %zu counter: %" PRIuFAST32 "\n", + worker_index, + worker_counter + ); + } + + actual_counter = ctx->flag_counter; + + printf( + "global counter: expected = %" PRIuFAST32 ", actual = %" PRIuFAST32 "\n", + expected_counter, + actual_counter + ); + + rtems_test_assert(expected_counter == actual_counter); +} + +static void test_atomic_or_and_init(test_context *ctx) +{ + _Atomic_Init_uint(&ctx->global_uint, 0); +} + +static void test_atomic_or_and_body(test_context *ctx, size_t worker_index) +{ + uint_fast32_t counter = 0; + + while (!stop(ctx)) { + _Atomic_Fetch_or_uint(&ctx->global_uint, (1 << worker_index), ATOMIC_ORDER_RELAXED); + counter = 1; + if (!stop(ctx)) + break; + _Atomic_Fetch_and_uint(&ctx->global_uint, ~(1 << worker_index), ATOMIC_ORDER_RELAXED); + counter = 0; + } + + ctx->per_worker_uint[worker_index] = counter; +} + +static void test_atomic_or_and_fini(test_context *ctx) +{ + uint_fast32_t expected_counter = 0; + uint_fast32_t actual_counter; + size_t worker_index; + + printf("=== atomic or_and test case ==\n"); + + for (worker_index = 0; worker_index < ctx->worker_count; ++worker_index) { + uint_fast32_t worker_counter = ctx->per_worker_uint[worker_index]; + + expected_counter |= ( worker_counter << worker_index ); + + printf( + "atomic or_and worker %zu counter: %" PRIuFAST32 "\n", + worker_index, + worker_counter + ); + } + + actual_counter = _Atomic_Load_uint(&ctx->global_uint, ATOMIC_ORDER_RELAXED); + + printf( + "global counter: expected = %" PRIuFAST32 ", actual = %" PRIuFAST32 "\n", + expected_counter, + actual_counter + ); + + rtems_test_assert(expected_counter == actual_counter); +} + static const test_case test_cases[] = { { test_atomic_add_init, test_atomic_add_body, test_atomic_add_fini }, - { test_atomic_flag_init, test_atomic_flag_body, test_atomic_flag_fini } + { test_atomic_flag_init, test_atomic_flag_body, test_atomic_flag_fini }, + { test_atomic_sub_init, test_atomic_sub_body, test_atomic_sub_fini }, + { test_atomic_compare_exchange_init, test_atomic_compare_exchange_body, + test_atomic_compare_exchange_fini }, + { test_atomic_or_and_init, test_atomic_or_and_body, test_atomic_or_and_fini }, }; #define TEST_COUNT RTEMS_ARRAY_SIZE(test_cases) diff --git a/testsuites/smptests/smpatomic08/smpatomic08.scn b/testsuites/smptests/smpatomic08/smpatomic08.scn index 70aeef176b..97ea7d48e3 100644 --- a/testsuites/smptests/smpatomic08/smpatomic08.scn +++ b/testsuites/smptests/smpatomic08/smpatomic08.scn @@ -7,4 +7,16 @@ global counter: expected = 54907, actual = 54907 atomic flag worker 0 counter: 7388 atomic flag worker 1 counter: 17280 global flag counter: expected = 24668, actual = 24668 +=== atomic sub test case == +atomic sub worker 0 counter: 18583 +atomic sub worker 1 counter: 36324 +global counter: expected = 54907, actual = 54907 +=== atomic compare_exchange test case == +atomic compare_exchange worker 0 counter: 3467 +atomic compare_exchange worker 1 counter: 19635 +global counter: expected = 23102, actual = 23102 +=== atomic or_and test case == +atomic or_and worker 0 counter: 1 +atomic or_and worker 1 counter: 1 +global counter: expected = 3, actual = 3 *** END OF TEST SMPATOMIC 8 *** |