[PATCH 18/18] score: Add _SMP_Unicast_action()

Sebastian Huber sebastian.huber at embedded-brains.de
Mon May 20 07:33:44 UTC 2019


---
 cpukit/Makefile.am                                 |  1 +
 cpukit/include/rtems/score/smpimpl.h               | 15 ++++
 cpukit/score/src/smpunicastaction.c                | 51 +++++++++++
 testsuites/smptests/smpmulticast01/init.c          | 95 +++++++++++++++++++--
 .../smptests/smpmulticast01/smpmulticast01.scn     | 99 +++++++++++++---------
 5 files changed, 218 insertions(+), 43 deletions(-)
 create mode 100644 cpukit/score/src/smpunicastaction.c

diff --git a/cpukit/Makefile.am b/cpukit/Makefile.am
index b4315819ac..8573f8fb64 100644
--- a/cpukit/Makefile.am
+++ b/cpukit/Makefile.am
@@ -1118,6 +1118,7 @@ librtemscpu_a_SOURCES += score/src/schedulerstrongapa.c
 librtemscpu_a_SOURCES += score/src/smp.c
 librtemscpu_a_SOURCES += score/src/smplock.c
 librtemscpu_a_SOURCES += score/src/smpmulticastaction.c
+librtemscpu_a_SOURCES += score/src/smpunicastaction.c
 librtemscpu_a_SOURCES += score/src/schedulerdefaultaskforhelp.c
 librtemscpu_a_SOURCES += score/src/schedulerdefaultsetaffinity.c
 librtemscpu_a_SOURCES += score/src/schedulersmp.c
diff --git a/cpukit/include/rtems/score/smpimpl.h b/cpukit/include/rtems/score/smpimpl.h
index 5fbe82baad..889ef5be58 100644
--- a/cpukit/include/rtems/score/smpimpl.h
+++ b/cpukit/include/rtems/score/smpimpl.h
@@ -260,6 +260,21 @@ void _SMP_Othercast_action(
   void               *arg
 );
 
+/**
+ * @brief Initiates an SMP action on the specified target processor.
+ *
+ * This is an optimized variant of _SMP_Multicast_action().
+ *
+ * @param cpu_index The index of the target processor.
+ * @param handler The action handler.
+ * @param arg The action argument.
+ */
+void _SMP_Unicast_action(
+  uint32_t            cpu_index,
+  SMP_Action_handler  handler,
+  void               *arg
+);
+
 /**
  * @brief Ensures that all store operations issued by the current processor
  * before the call this function are visible to all other online processors.
diff --git a/cpukit/score/src/smpunicastaction.c b/cpukit/score/src/smpunicastaction.c
new file mode 100644
index 0000000000..1b170cabd2
--- /dev/null
+++ b/cpukit/score/src/smpunicastaction.c
@@ -0,0 +1,51 @@
+/*
+ * SPDX-License-Identifier: BSD-2-Clause
+ *
+ * Copyright (C) 2019 embedded brains GmbH
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <rtems/score/smpimpl.h>
+
+void _SMP_Unicast_action(
+  uint32_t            cpu_index,
+  SMP_Action_handler  handler,
+  void               *arg
+)
+{
+  Per_CPU_Control     *cpu;
+  Per_CPU_Job_context  context;
+  Per_CPU_Job          job;
+
+  context.handler = handler;
+  context.arg = arg;
+  job.context = &context;
+  cpu = _Per_CPU_Get_by_index( cpu_index );
+  _Per_CPU_Add_job( cpu, &job );
+  _SMP_Send_message( cpu_index, SMP_MESSAGE_PERFORM_JOBS );
+  _Per_CPU_Wait_for_job( cpu, &job );
+}
diff --git a/testsuites/smptests/smpmulticast01/init.c b/testsuites/smptests/smpmulticast01/init.c
index e7c533027f..34f88abaf2 100644
--- a/testsuites/smptests/smpmulticast01/init.c
+++ b/testsuites/smptests/smpmulticast01/init.c
@@ -59,6 +59,32 @@ static void clear_ids_by_worker(test_context *ctx, size_t worker_index)
   memset(&ctx->id[worker_index][0], 0, sizeof(ctx->id[worker_index]));
 }
 
+static void unicast_action_irq_disabled(
+  uint32_t cpu_index,
+  SMP_Action_handler handler,
+  void *arg
+)
+{
+  rtems_interrupt_level level;
+
+  rtems_interrupt_local_disable(level);
+  _SMP_Unicast_action(cpu_index, handler, arg);
+  rtems_interrupt_local_enable(level);
+}
+
+static void unicast_action_dispatch_disabled(
+  uint32_t cpu_index,
+  SMP_Action_handler handler,
+  void *arg
+)
+{
+  Per_CPU_Control *cpu_self;
+
+  cpu_self = _Thread_Dispatch_disable();
+  _SMP_Unicast_action(cpu_index, handler, arg);
+  _Thread_Dispatch_enable(cpu_self);
+}
+
 static void multicast_action_irq_disabled(
   const Processor_mask *targets,
   SMP_Action_handler handler,
@@ -130,6 +156,43 @@ static void action(void *arg)
 }
 
 static void test_unicast(
+  test_context *ctx,
+  void (*unicast_action)(uint32_t, SMP_Action_handler, void *)
+)
+{
+  uint32_t step;
+  uint32_t i;
+  uint32_t n;
+
+  T_plan(1);
+  step = 0;
+  n = rtems_scheduler_get_processor_maximum();
+
+  for (i = 0; i < n; ++i) {
+    uint32_t j;
+
+    clear_ids_by_worker(ctx, 0);
+
+    (*unicast_action)(i, action, &ctx->id[0][0]);
+
+    for (j = 0; j < n; ++j) {
+      unsigned id;
+
+      ++step;
+      id = _Atomic_Load_uint(&ctx->id[0][j], ATOMIC_ORDER_RELAXED);
+
+      if (j == i) {
+        T_quiet_eq_uint(j + 1, id);
+      } else {
+        T_quiet_eq_uint(0, id);
+      }
+    }
+  }
+
+  T_step_eq_u32(0, step, n * n);
+}
+
+static void test_multicast(
   test_context *ctx,
   void (*multicast_action)(const Processor_mask *, SMP_Action_handler, void *)
 )
@@ -271,15 +334,27 @@ static void test_before_multitasking(void)
   ctx = &test_instance;
 
   T_case_begin("UnicastBeforeMultitasking", NULL);
-  test_unicast(ctx, _SMP_Multicast_action);
+  test_unicast(ctx, _SMP_Unicast_action);
   T_case_end();
 
   T_case_begin("UnicastBeforeMultitaskingIRQDisabled", NULL);
-  test_unicast(ctx, multicast_action_irq_disabled);
+  test_unicast(ctx, unicast_action_irq_disabled);
   T_case_end();
 
   T_case_begin("UnicastBeforeMultitaskingDispatchDisabled", NULL);
-  test_unicast(ctx, multicast_action_dispatch_disabled);
+  test_unicast(ctx, unicast_action_dispatch_disabled);
+  T_case_end();
+
+  T_case_begin("MulticastBeforeMultitasking", NULL);
+  test_multicast(ctx, _SMP_Multicast_action);
+  T_case_end();
+
+  T_case_begin("MulticastBeforeMultitaskingIRQDisabled", NULL);
+  test_multicast(ctx, multicast_action_irq_disabled);
+  T_case_end();
+
+  T_case_begin("MulticastBeforeMultitaskingDispatchDisabled", NULL);
+  test_multicast(ctx, multicast_action_dispatch_disabled);
   T_case_end();
 
   T_case_begin("BroadcastBeforeMultitasking", NULL);
@@ -437,12 +512,22 @@ T_TEST_CASE(AddJobInJob)
 
 T_TEST_CASE(UnicastDuringMultitaskingIRQDisabled)
 {
-  test_unicast(&test_instance, multicast_action_irq_disabled);
+  test_unicast(&test_instance, unicast_action_irq_disabled);
 }
 
 T_TEST_CASE(UnicastDuringMultitaskingDispatchDisabled)
 {
-  test_unicast(&test_instance, multicast_action_dispatch_disabled);
+  test_unicast(&test_instance, unicast_action_dispatch_disabled);
+}
+
+T_TEST_CASE(MulticastDuringMultitaskingIRQDisabled)
+{
+  test_multicast(&test_instance, multicast_action_irq_disabled);
+}
+
+T_TEST_CASE(MulticastDuringMultitaskingDispatchDisabled)
+{
+  test_multicast(&test_instance, multicast_action_dispatch_disabled);
 }
 
 T_TEST_CASE(BroadcastDuringMultitaskingIRQDisabled)
diff --git a/testsuites/smptests/smpmulticast01/smpmulticast01.scn b/testsuites/smptests/smpmulticast01/smpmulticast01.scn
index 9433775dba..49e1e6123f 100644
--- a/testsuites/smptests/smpmulticast01/smpmulticast01.scn
+++ b/testsuites/smptests/smpmulticast01/smpmulticast01.scn
@@ -1,60 +1,83 @@
 *** BEGIN OF TEST SMPMULTICAST 1 ***
-*** TEST VERSION: 5.0.0.d9c9d1af7a885bc402c57e88919635b27b363111
+*** TEST VERSION: 5.0.0.41cddcc6e194be27d1e4125b961acb94e278552b
 *** TEST STATE: EXPECTED-PASS
 *** TEST BUILD: RTEMS_POSIX_API RTEMS_SMP
-*** TEST TOOLS: 7.4.0 20181206 (RTEMS 5, RSB e0aec65182449a4e22b820e773087636edaf5b32, Newlib 1d35a003f)
+*** TEST TOOLS: 7.4.1 20190514 (RTEMS 5, RSB 7a80d6ced664748e66904cd98250f6a9c727361b, Newlib 1d35a003f)
 A:SMPMultiCast
 S:Platform:RTEMS
-S:Compiler:7.4.0 20181206 (RTEMS 5, RSB e0aec65182449a4e22b820e773087636edaf5b32, Newlib 1d35a003f)
-S:Version:5.0.0.d9c9d1af7a885bc402c57e88919635b27b363111
-S:BSP:qoriq_e6500_32
-S:RTEMS_DEBUG:0
+S:Compiler:7.4.1 20190514 (RTEMS 5, RSB 7a80d6ced664748e66904cd98250f6a9c727361b, Newlib 1d35a003f)
+S:Version:5.0.0.39862d4adf604fb4dccf3a852d66fe5b71966c47-modified
+S:BSP:leon3
+S:RTEMS_DEBUG:1
 S:RTEMS_MULTIPROCESSING:0
 S:RTEMS_POSIX_API:1
 S:RTEMS_PROFILING:0
 S:RTEMS_SMP:1
 B:UnicastBeforeMultitasking
-P:0:0:IDLE:init.c:142
-E:UnicastBeforeMultitasking:N:1:F:0:D:0.002206
+P:0:0:IDLE:init.c:192
+E:UnicastBeforeMultitasking:N:1:F:0:D:0.000118
 B:UnicastBeforeMultitaskingIRQDisabled
-P:0:0:IDLE:init.c:142
-E:UnicastBeforeMultitaskingIRQDisabled:N:1:F:0:D:0.002184
+P:0:0:IDLE:init.c:192
+E:UnicastBeforeMultitaskingIRQDisabled:N:1:F:0:D:0.000121
 B:UnicastBeforeMultitaskingDispatchDisabled
-P:0:0:IDLE:init.c:142
-E:UnicastBeforeMultitaskingDispatchDisabled:N:1:F:0:D:0.002198
+P:0:0:IDLE:init.c:192
+E:UnicastBeforeMultitaskingDispatchDisabled:N:1:F:0:D:0.000123
+B:MulticastBeforeMultitasking
+P:0:0:IDLE:init.c:232
+E:MulticastBeforeMultitasking:N:1:F:0:D:0.000126
+B:MulticastBeforeMultitaskingIRQDisabled
+P:0:0:IDLE:init.c:232
+E:MulticastBeforeMultitaskingIRQDisabled:N:1:F:0:D:0.000126
+B:MulticastBeforeMultitaskingDispatchDisabled
+P:0:0:IDLE:init.c:232
+E:MulticastBeforeMultitaskingDispatchDisabled:N:1:F:0:D:0.000129
 B:BroadcastBeforeMultitasking
-P:0:0:IDLE:init.c:174
-E:BroadcastBeforeMultitasking:N:1:F:0:D:0.004153
+P:0:0:IDLE:init.c:264
+E:BroadcastBeforeMultitasking:N:1:F:0:D:0.000180
 B:BroadcastBeforeMultitaskingIRQDisabled
-P:0:0:IDLE:init.c:174
-E:BroadcastBeforeMultitaskingIRQDisabled:N:1:F:0:D:0.004135
+P:0:0:IDLE:init.c:264
+E:BroadcastBeforeMultitaskingIRQDisabled:N:1:F:0:D:0.000180
 B:BroadcastBeforeMultitaskingDispatchDisabled
-P:0:0:IDLE:init.c:174
-E:BroadcastBeforeMultitaskingDispatchDisabled:N:1:F:0:D:0.004123
-B:UnicastDuringMultitasking
-P:0:23:UI1:init.c:142
-E:UnicastDuringMultitasking:N:1:F:0:D:0.002270
+P:0:0:IDLE:init.c:264
+E:BroadcastBeforeMultitaskingDispatchDisabled:N:1:F:0:D:0.000187
 B:UnicastDuringMultitaskingIRQDisabled
-P:0:23:UI1:init.c:142
-E:UnicastDuringMultitaskingIRQDisabled:N:1:F:0:D:0.002272
+P:0:3:UI1:init.c:192
+E:UnicastDuringMultitaskingIRQDisabled:N:1:F:0:D:0.000150
 B:UnicastDuringMultitaskingDispatchDisabled
-P:0:23:UI1:init.c:142
-E:UnicastDuringMultitaskingDispatchDisabled:N:1:F:0:D:0.002271
-B:BroadcastDuringMultitasking
-P:0:23:UI1:init.c:174
-E:BroadcastDuringMultitasking:N:1:F:0:D:0.003904
+P:0:3:UI1:init.c:192
+E:UnicastDuringMultitaskingDispatchDisabled:N:1:F:0:D:0.000154
+B:ParallelBroadcast
+E:ParallelBroadcast:N:0:F:0:D:3.995722
+B:MulticastDuringMultitaskingIRQDisabled
+P:0:0:UI1:init.c:232
+E:MulticastDuringMultitaskingIRQDisabled:N:1:F:0:D:0.000154
+B:MulticastDuringMultitaskingDispatchDisabled
+P:0:0:UI1:init.c:232
+E:MulticastDuringMultitaskingDispatchDisabled:N:1:F:0:D:0.000157
+B:JobOrder
+P:0:0:UI1:init.c:467
+P:1:0:ISR:init.c:435
+P:2:0:ISR:init.c:440
+P:3:0:ISR:init.c:445
+E:JobOrder:N:4:F:0:D:0.000259
 B:BroadcastDuringMultitaskingIRQDisabled
-P:0:23:UI1:init.c:174
-E:BroadcastDuringMultitaskingIRQDisabled:N:1:F:0:D:0.003949
+P:0:0:UI1:init.c:264
+E:BroadcastDuringMultitaskingIRQDisabled:N:1:F:0:D:0.000228
 B:BroadcastDuringMultitaskingDispatchDisabled
-P:0:23:UI1:init.c:174
-E:BroadcastDuringMultitaskingDispatchDisabled:N:1:F:0:D:0.003914
+P:0:0:UI1:init.c:264
+E:BroadcastDuringMultitaskingDispatchDisabled:N:1:F:0:D:0.000244
+B:AddJobInJob
+P:0:0:UI1:init.c:506
+P:1:0:ISR:init.c:478
+P:2:0:UI1:init.c:508
+P:3:0:ISR:init.c:484
+E:AddJobInJob:N:4:F:0:D:0.000267
 B:WrongCPUStateToPerformJobs
-P:0:0:ISR:init.c:226
-P:1:23:UI1:init.c:310
-P:2:23:UI1:init.c:311
-P:3:23:UI1:init.c:312
-E:WrongCPUStateToPerformJobs:N:4:F:0:D:0.007911
-Z:SMPMultiCast:C:13:N:16:F:0:D:0.153651
+P:0:1:ISR:init.c:391
+P:1:0:UI1:init.c:564
+P:2:0:UI1:init.c:565
+P:3:0:UI1:init.c:566
+E:WrongCPUStateToPerformJobs:N:4:F:0:D:0.000255
+Z:SMPMultiCast:C:19:N:27:F:0:D:4.002547
 
 *** END OF TEST SMPMULTICAST 1 ***
-- 
2.16.4




More information about the devel mailing list