summaryrefslogtreecommitdiffstats
path: root/testsuites/smptests/smpfatal01/init.c
diff options
context:
space:
mode:
authorSebastian Huber <sebastian.huber@embedded-brains.de>2014-02-18 13:40:39 +0100
committerSebastian Huber <sebastian.huber@embedded-brains.de>2014-03-06 09:43:57 +0100
commit7336be9d78266adfb540170e5105caf8eb003d2f (patch)
tree5dc7ab7a5c3c33c7e007a8e8e48cb1167187b0ca /testsuites/smptests/smpfatal01/init.c
parentbsp/leon3: Unmask IPI only on secondary processor (diff)
downloadrtems-7336be9d78266adfb540170e5105caf8eb003d2f.tar.bz2
score: SMP initialization and shutdown changes
Rename _SMP_Request_other_cores_to_perform_first_context_switch() into _SMP_Request_start_multitasking() since this requests now a multitasking start on all configured and available processors. The name corresponds _Thread_Start_multitasking() and _SMP_Start_multitasking_on_secondary_processor() actions issued in response to this request. Move in source file to right place. Rename PER_CPU_STATE_READY_TO_BEGIN_MULTITASKING into PER_CPU_STATE_READY_TO_START_MULTITASKING. Rename PER_CPU_STATE_BEGIN_MULTITASKING into PER_CPU_STATE_REQUEST_START_MULTITASKING. Rename _SMP_Request_other_cores_to_shutdown() into _SMP_Request_shutdown(). Add a per-CPU state lock to protect all changes. This was necessary to offer a controlled shutdown of the system (atomic read/writes alone are not sufficient for this kind of synchronization). Add documentation for Per_CPU_State. Delete debug output. New tests smptests/smpfatal01 and smptests/smpfatal02.
Diffstat (limited to '')
-rw-r--r--testsuites/smptests/smpfatal01/init.c130
1 files changed, 130 insertions, 0 deletions
diff --git a/testsuites/smptests/smpfatal01/init.c b/testsuites/smptests/smpfatal01/init.c
new file mode 100644
index 0000000000..c78b29fbe8
--- /dev/null
+++ b/testsuites/smptests/smpfatal01/init.c
@@ -0,0 +1,130 @@
+/*
+ * Copyright (c) 2014 embedded brains GmbH. All rights reserved.
+ *
+ * embedded brains GmbH
+ * Dornierstr. 4
+ * 82178 Puchheim
+ * Germany
+ * <rtems@embedded-brains.de>
+ *
+ * The license and distribution terms for this file may be
+ * found in the file LICENSE in this distribution or at
+ * http://www.rtems.com/license/LICENSE.
+ */
+
+#ifdef HAVE_CONFIG_H
+ #include "config.h"
+#endif
+
+#include <rtems.h>
+#include <rtems/score/percpu.h>
+#include <rtems/score/smpimpl.h>
+
+#include <assert.h>
+#include <stdlib.h>
+
+#define MAX_CPUS 32
+
+static uint32_t main_cpu;
+
+static void Init(rtems_task_argument arg)
+{
+ assert(0);
+}
+
+static void end_of_test(void)
+{
+ printk( "*** END OF TEST SMPFATAL 1 ***\n" );
+}
+
+static void fatal_extension(
+ rtems_fatal_source source,
+ bool is_internal,
+ rtems_fatal_code code
+)
+{
+ if (source == RTEMS_FATAL_SOURCE_SMP) {
+ uint32_t self = rtems_smp_get_current_processor();
+
+ assert(!is_internal);
+ assert(code == SMP_FATAL_SHUTDOWN);
+
+ if (self == main_cpu) {
+ uint32_t cpu;
+
+ for (cpu = 0; cpu < MAX_CPUS; ++cpu) {
+ const Per_CPU_Control *per_cpu = _Per_CPU_Get_by_index( cpu );
+ Per_CPU_State state = per_cpu->state;
+
+ assert(state == PER_CPU_STATE_SHUTDOWN);
+ }
+
+ end_of_test();
+ }
+ }
+}
+
+static rtems_status_code test_driver_init(
+ rtems_device_major_number major,
+ rtems_device_minor_number minor,
+ void *arg
+)
+{
+ uint32_t self = rtems_smp_get_current_processor();
+ uint32_t cpu_count = rtems_smp_get_processor_count();
+ uint32_t cpu;
+
+ printk("\n\n*** TEST SMPFATAL 1 ***\n");
+
+ assert(rtems_configuration_get_maximum_processors() == MAX_CPUS);
+
+ main_cpu = self;
+
+ for (cpu = 0; cpu < MAX_CPUS; ++cpu) {
+ const Per_CPU_Control *per_cpu = _Per_CPU_Get_by_index( cpu );
+ Per_CPU_State state = per_cpu->state;
+
+ if (cpu == self) {
+ assert(state == PER_CPU_STATE_INITIAL);
+ } else if (cpu < cpu_count) {
+ assert(
+ state == PER_CPU_STATE_INITIAL
+ || state == PER_CPU_STATE_READY_TO_START_MULTITASKING
+ );
+ } else {
+ assert(state == PER_CPU_STATE_INITIAL);
+ }
+ }
+
+ if (cpu_count > 1) {
+ uint32_t other = (self + 1) % cpu_count;
+ Per_CPU_Control *per_cpu = _Per_CPU_Get_by_index( other );
+
+ per_cpu->state = PER_CPU_STATE_SHUTDOWN;
+ } else {
+ end_of_test();
+ exit(0);
+ }
+
+ return RTEMS_SUCCESSFUL;
+}
+
+#define CONFIGURE_APPLICATION_DOES_NOT_NEED_CLOCK_DRIVER
+#define CONFIGURE_APPLICATION_NEEDS_CONSOLE_DRIVER
+
+#define CONFIGURE_APPLICATION_EXTRA_DRIVERS \
+ { .initialization_entry = test_driver_init }
+
+#define CONFIGURE_INITIAL_EXTENSIONS { .fatal = fatal_extension }
+
+#define CONFIGURE_SMP_APPLICATION
+
+#define CONFIGURE_SMP_MAXIMUM_PROCESSORS MAX_CPUS
+
+#define CONFIGURE_MAXIMUM_TASKS 1
+
+#define CONFIGURE_RTEMS_INIT_TASKS_TABLE
+
+#define CONFIGURE_INIT
+
+#include <rtems/confdefs.h>