RTEMS
scheduleraddprocessor.c
1 /*
2  * Copyright (c) 2016 embedded brains GmbH. All rights reserved.
3  *
4  * embedded brains GmbH
5  * Dornierstr. 4
6  * 82178 Puchheim
7  * Germany
8  * <rtems@embedded-brains.de>
9  *
10  * The license and distribution terms for this file may be
11  * found in the file LICENSE in this distribution or at
12  * http://www.rtems.org/license/LICENSE.
13  */
14 
15 #ifdef HAVE_CONFIG_H
16 #include "config.h"
17 #endif
18 
19 #include <rtems/rtems/tasks.h>
20 #include <rtems/score/assert.h>
22 #include <rtems/config.h>
23 
25  rtems_id scheduler_id,
26  uint32_t cpu_index
27 )
28 {
29  uint32_t scheduler_index;
30 #if defined(RTEMS_SMP)
31  Per_CPU_Control *cpu;
32  rtems_status_code status;
33 #endif
34 
35  scheduler_index = _Scheduler_Get_index_by_id( scheduler_id );
36 
37  if ( scheduler_index >= _Scheduler_Count ) {
38  return RTEMS_INVALID_ID;
39  }
40 
41  if ( cpu_index >= rtems_configuration_get_maximum_processors() ) {
42  return RTEMS_NOT_CONFIGURED;
43  }
44 
45 #if defined(RTEMS_SMP)
46  cpu = _Per_CPU_Get_by_index( cpu_index );
47 
48  if ( _Scheduler_Initial_assignments[ cpu_index ].scheduler == NULL ) {
49  return RTEMS_NOT_CONFIGURED;
50  }
51 
52  if ( !_Per_CPU_Is_processor_online( cpu ) ) {
53  return RTEMS_INCORRECT_STATE;
54  }
55 
57 
58  if ( cpu->Scheduler.control == NULL ) {
59  const Scheduler_Control *scheduler;
60  Scheduler_Context *scheduler_context;
61  Priority_Control idle_priority;
62  Thread_Control *idle;
63  Scheduler_Node *scheduler_node;
64  ISR_lock_Context lock_context;
65  Per_CPU_Control *cpu_self;
66 
67  scheduler = &_Scheduler_Table[ scheduler_index ];
68  scheduler_context = _Scheduler_Get_context( scheduler );
69  idle_priority =
70  _Scheduler_Map_priority( scheduler, scheduler->maximum_priority );
71 
72  idle = cpu->Scheduler.idle_if_online_and_unused;
73  _Assert( idle != NULL );
74  cpu->Scheduler.idle_if_online_and_unused = NULL;
75 
76  idle->Scheduler.home_scheduler = scheduler;
77  idle->Start.initial_priority = idle_priority;
78  scheduler_node =
79  _Thread_Scheduler_get_node_by_index( idle, scheduler_index );
80  _Priority_Node_set_priority( &idle->Real_priority, idle_priority );
82  &scheduler_node->Wait.Priority,
83  &idle->Real_priority
84  );
87  &idle->Scheduler.Wait_nodes,
88  &scheduler_node->Thread.Wait_node
89  );
93  &scheduler_node->Thread.Scheduler_node.Chain
94  );
95 
96  _ISR_lock_ISR_disable( &lock_context );
97  _Scheduler_Acquire_critical( scheduler, &lock_context );
98  _Processor_mask_Set( &scheduler_context->Processors, cpu_index );
99  cpu->Scheduler.control = scheduler;
100  cpu->Scheduler.context = scheduler_context;
101  ( *scheduler->Operations.add_processor )( scheduler, idle );
102  cpu_self = _Thread_Dispatch_disable_critical( &lock_context );
103  _Scheduler_Release_critical( scheduler, &lock_context );
104  _ISR_lock_ISR_enable( &lock_context );
105  _Thread_Dispatch_direct( cpu_self );
106  status = RTEMS_SUCCESSFUL;
107  } else {
108  status = RTEMS_RESOURCE_IN_USE;
109  }
110 
112  return status;
113 #else
114  return RTEMS_RESOURCE_IN_USE;
115 #endif
116 }
static __inline__ void _Objects_Allocator_unlock(void)
Unlocks the object allocator mutex.
Definition: objectimpl.h:846
const struct _Scheduler_Control * home_scheduler
The home scheduler of this thread.
Definition: thread.h:258
static __inline__ void _Priority_Initialize_one(Priority_Aggregation *aggregation, Priority_Node *node)
Initializes the priority aggregation with the given information.
Definition: priorityimpl.h:232
uint64_t Priority_Control
The thread priority control.
Definition: priority.h:70
static __inline__ void _Scheduler_Acquire_critical(const Scheduler_Control *scheduler, ISR_lock_Context *lock_context)
Acquires the scheduler instance inside a critical section (interrupts disabled).
Scheduler context.
Definition: scheduler.h:247
static __inline__ Scheduler_Node * _Thread_Scheduler_get_node_by_index(const Thread_Control *the_thread, size_t scheduler_index)
Gets the thread&#39;s scheduler node by index.
Definition: threadimpl.h:1460
void _Thread_Dispatch_direct(Per_CPU_Control *cpu_self)
Directly do a thread dispatch.
struct _Thread_Control * idle_if_online_and_unused
The idle thread for this processor in case it is online and currently not used by a scheduler instanc...
Definition: percpu.h:528
static __inline__ Priority_Control _Scheduler_Map_priority(const Scheduler_Control *scheduler, Priority_Control priority)
Maps a thread priority from the user domain to the scheduler domain.
Thread_Start_information Start
Definition: thread.h:825
This status code indicates that the object still had resources in use.
Definition: status.h:149
Inlined Routines Associated with the Manipulation of the Scheduler.
This header file defines parts of the application configuration information API.
#define _ISR_lock_ISR_enable(_context)
Restores the saved interrupt state of the ISR lock context.
Definition: isrlock.h:416
Thread_Scheduler_control Scheduler
Scheduler related control.
Definition: thread.h:764
const struct Scheduler_Context * context
The scheduler context of the scheduler owning this processor.
Definition: percpu.h:522
void(* add_processor)(const Scheduler_Control *scheduler, Thread_Control *idle)
Add processor operation.
Definition: scheduler.h:173
struct Scheduler_Node::@19 Thread
Block to register and manage this scheduler node in the thread control block of the owner of this sch...
static __inline__ void _Objects_Allocator_lock(void)
Locks the object allocator mutex.
Definition: objectimpl.h:834
Information for the Assert Handler.
Chain_Node Wait_node
Node to add this scheduler node to Thread_Control::Scheduler::Wait_nodes.
This status code indicates successful completion.
Definition: status.h:86
rtems_status_code rtems_scheduler_add_processor(rtems_id scheduler_id, uint32_t cpu_index)
Adds the processor to the set of processors owned by the scheduler instance.
static __inline__ void _Scheduler_Release_critical(const Scheduler_Control *scheduler, ISR_lock_Context *lock_context)
Releases the scheduler instance inside a critical section (interrupts disabled).
const Scheduler_Assignment _Scheduler_Initial_assignments[]
The scheduler assignments.
static __inline__ Per_CPU_Control * _Thread_Dispatch_disable_critical(const ISR_lock_Context *lock_context)
Disables thread dispatching inside a critical section (interrupts disabled).
rtems_status_code
This enumeration provides status codes for directives of the Classic API.
Definition: status.h:82
Per CPU Core Structure.
Definition: percpu.h:347
Priority_Control maximum_priority
The maximum priority value of this scheduler.
Definition: scheduler.h:281
This status code indicates that an object was in wrong state for the requested operation.
Definition: status.h:160
Processor_mask Processors
Lock to protect this scheduler instance.
Definition: scheduler.h:257
This header file defines the main parts of the Tasks Manager API.
const struct _Scheduler_Control * control
The scheduler control of the scheduler owning this processor.
Definition: percpu.h:514
const Scheduler_Control _Scheduler_Table[]
This table contains the configured schedulers.
static __inline__ void _Priority_Node_set_priority(Priority_Node *node, Priority_Control priority)
Sets the priority of the priority node to the given priority.
Definition: priorityimpl.h:171
Priority_Control initial_priority
Definition: thread.h:195
Chain_Control Scheduler_nodes
Scheduler nodes immediately available to the schedulers for this thread.
Definition: thread.h:294
static __inline__ void _Chain_Initialize_one(Chain_Control *the_chain, Chain_Node *the_node)
Initializes this chain to contain exactly the specified node.
Definition: chainimpl.h:528
struct Scheduler_Node::@20 Wait
Thread wait support block.
This status code indicates that an object identifier was invalid.
Definition: status.h:106
Objects_Id rtems_id
Values of this type identify an RTEMS object.
Definition: types.h:99
This status code indicates that the directive was not configured.
Definition: status.h:205
Scheduler_Operations Operations
The scheduler operations.
Definition: scheduler.h:273
const size_t _Scheduler_Count
This constant contains the count of configured schedulers.
Scheduler control.
Definition: scheduler.h:264
Scheduler node for per-thread data.
Definition: schedulernode.h:79
static __inline__ Scheduler_Context * _Scheduler_Get_context(const Scheduler_Control *scheduler)
Gets the context of the scheduler.
Definition: schedulerimpl.h:85
#define _ISR_lock_ISR_disable(_context)
Disables interrupts and saves the previous interrupt state in the ISR lock context.
Definition: isrlock.h:392
static __inline__ uint32_t _Scheduler_Get_index_by_id(Objects_Id id)
Gets the scheduler index from the given object build id.
Chain_Control Wait_nodes
Scheduler nodes immediately available to the thread by its home scheduler and due to thread queue own...
Definition: thread.h:279
Local ISR lock context for acquire and release pairs.
Definition: isrlock.h:65
#define rtems_configuration_get_maximum_processors()
Returns the maximum number of processors which are configured for this application.
Definition: config.h:194
static __inline__ bool _Chain_Is_empty(const Chain_Control *the_chain)
Checks if the chain is empty.
Definition: chainimpl.h:393
Priority_Node Real_priority
The base priority of this thread in its home scheduler instance.
Definition: thread.h:754
union Scheduler_Node::@19::@22 Scheduler_node
Node to add this scheduler node to Thread_Control::Scheduler::Scheduler_nodes or a temporary remove l...
#define _Assert(_e)
Assertion similar to assert() controlled via RTEMS_DEBUG instead of NDEBUG.
Definition: assert.h:100
RTEMS_INLINE_ROUTINE void _Processor_mask_Set(Processor_mask *mask, uint32_t index)
Sets the specified index bit of the mask.