File indexing completed on 2025-05-11 08:24:42
0001
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013
0014
0015
0016
0017
0018
0019
0020
0021
0022
0023
0024
0025
0026
0027
0028 #ifdef HAVE_CONFIG_H
0029 #include "config.h"
0030 #endif
0031
0032 #include "tmacros.h"
0033
0034 #include <rtems.h>
0035 #include <rtems/score/percpu.h>
0036 #include <rtems/score/smpimpl.h>
0037 #include <rtems/score/smpbarrier.h>
0038
0039 #include <assert.h>
0040 #include <stdlib.h>
0041
0042 const char rtems_test_name[] = "SMPFATAL 1";
0043
0044 #define MAX_CPUS 32
0045
0046 static uint32_t main_cpu;
0047
0048 static uint32_t other_cpu;
0049
0050 static SMP_barrier_Control barrier = SMP_BARRIER_CONTROL_INITIALIZER;
0051
0052 static void Init(rtems_task_argument arg)
0053 {
0054 assert(0);
0055 }
0056
0057 static void fatal_extension(
0058 rtems_fatal_source source,
0059 bool always_set_to_false,
0060 rtems_fatal_code code
0061 )
0062 {
0063 assert(!always_set_to_false);
0064
0065 if (source == RTEMS_FATAL_SOURCE_SMP) {
0066 SMP_barrier_State barrier_state = SMP_BARRIER_STATE_INITIALIZER;
0067 uint32_t cpu_count = rtems_scheduler_get_processor_maximum();
0068 uint32_t self = rtems_scheduler_get_processor();
0069
0070 if (self == other_cpu) {
0071 assert(code == SMP_FATAL_SHUTDOWN);
0072 } else {
0073 assert(code == SMP_FATAL_SHUTDOWN_RESPONSE);
0074 }
0075
0076 _SMP_barrier_Wait(&barrier, &barrier_state, cpu_count);
0077
0078 if (self == other_cpu) {
0079 uint32_t cpu;
0080
0081 for (cpu = 0; cpu < cpu_count; ++cpu) {
0082 const Per_CPU_Control *per_cpu = _Per_CPU_Get_by_index( cpu );
0083 Per_CPU_State state = _Per_CPU_Get_state(per_cpu);
0084
0085 assert(state == PER_CPU_STATE_SHUTDOWN);
0086 }
0087
0088 for (cpu = cpu_count; cpu < MAX_CPUS; ++cpu) {
0089 const Per_CPU_Control *per_cpu = _Per_CPU_Get_by_index( cpu );
0090 Per_CPU_State state = _Per_CPU_Get_state(per_cpu);
0091
0092 assert(state == PER_CPU_STATE_INITIAL);
0093 }
0094
0095 TEST_END();
0096 } else {
0097 _SMP_barrier_Wait(&barrier, &barrier_state, cpu_count);
0098 }
0099 }
0100 }
0101
0102 static void shutdown_handler(void *arg)
0103 {
0104 _SMP_Request_shutdown();
0105 _SMP_Fatal(SMP_FATAL_SHUTDOWN);
0106 }
0107
0108 static const Per_CPU_Job_context shutdown_context = {
0109 .handler = shutdown_handler
0110 };
0111
0112 static Per_CPU_Job shutdown_job = {
0113 .context = &shutdown_context
0114 };
0115
0116 static rtems_status_code test_driver_init(
0117 rtems_device_major_number major,
0118 rtems_device_minor_number minor,
0119 void *arg
0120 )
0121 {
0122 uint32_t self = rtems_scheduler_get_processor();
0123 uint32_t cpu_count = rtems_scheduler_get_processor_maximum();
0124 uint32_t cpu;
0125
0126 TEST_BEGIN();
0127
0128 assert(rtems_configuration_get_maximum_processors() == MAX_CPUS);
0129
0130 main_cpu = self;
0131 other_cpu = (self + 1) % cpu_count;
0132
0133 for (cpu = 0; cpu < MAX_CPUS; ++cpu) {
0134 const Per_CPU_Control *per_cpu = _Per_CPU_Get_by_index( cpu );
0135 Per_CPU_State state = _Per_CPU_Get_state(per_cpu);
0136
0137 if (cpu == self) {
0138 assert(state == PER_CPU_STATE_INITIAL);
0139 } else if (cpu < cpu_count) {
0140 assert(
0141 state == PER_CPU_STATE_INITIAL
0142 || state == PER_CPU_STATE_READY_TO_START_MULTITASKING
0143 );
0144 } else {
0145 assert(state == PER_CPU_STATE_INITIAL);
0146 }
0147 }
0148
0149 if (cpu_count > 1) {
0150 Per_CPU_Control *per_cpu = _Per_CPU_Get_by_index( other_cpu );
0151
0152 _Per_CPU_Submit_job(per_cpu, &shutdown_job);
0153 } else {
0154 TEST_END();
0155 exit(0);
0156 }
0157
0158 return RTEMS_SUCCESSFUL;
0159 }
0160
0161 #define CONFIGURE_APPLICATION_DOES_NOT_NEED_CLOCK_DRIVER
0162 #define CONFIGURE_APPLICATION_NEEDS_SIMPLE_CONSOLE_DRIVER
0163
0164 #define CONFIGURE_APPLICATION_EXTRA_DRIVERS \
0165 { .initialization_entry = test_driver_init }
0166
0167 #define CONFIGURE_INITIAL_EXTENSIONS \
0168 { .fatal = fatal_extension }, \
0169 RTEMS_TEST_INITIAL_EXTENSION
0170
0171 #define CONFIGURE_MAXIMUM_PROCESSORS MAX_CPUS
0172
0173 #define CONFIGURE_MAXIMUM_TASKS 1
0174
0175 #define CONFIGURE_RTEMS_INIT_TASKS_TABLE
0176
0177 #define CONFIGURE_INIT
0178
0179 #include <rtems/confdefs.h>