source: rtems/cpukit/score/src/schedulerprioritysmp.c @ 1c2d178

5
Last change on this file since 1c2d178 was 3aad9d9b, checked in by Sebastian Huber <sebastian.huber@…>, on 09/03/18 at 07:31:19

score: Generalize SMP scheduler block support

Add extract from scheduled function to the _Scheduler_SMP_Block()
operation. This allows a scheduler implementation to do extra work in
case a scheduled node is blocked.

  • Property mode set to 100644
File size: 7.4 KB
Line 
1/**
2 * @file
3 *
4 * @ingroup ScoreSchedulerPrioritySMP
5 *
6 * @brief Deterministic Priority SMP Scheduler Implementation
7 */
8
9/*
10 * Copyright (c) 2013-2014 embedded brains GmbH.  All rights reserved.
11 *
12 *  embedded brains GmbH
13 *  Dornierstr. 4
14 *  82178 Puchheim
15 *  Germany
16 *  <rtems@embedded-brains.de>
17 *
18 * The license and distribution terms for this file may be
19 * found in the file LICENSE in this distribution or at
20 * http://www.rtems.org/license/LICENSE.
21 */
22
23#if HAVE_CONFIG_H
24  #include "config.h"
25#endif
26
27#include <rtems/score/schedulerprioritysmpimpl.h>
28
29static Scheduler_priority_SMP_Context *
30_Scheduler_priority_SMP_Get_context( const Scheduler_Control *scheduler )
31{
32  return (Scheduler_priority_SMP_Context *) _Scheduler_Get_context( scheduler );
33}
34
35void _Scheduler_priority_SMP_Initialize( const Scheduler_Control *scheduler )
36{
37  Scheduler_priority_SMP_Context *self =
38    _Scheduler_priority_SMP_Get_context( scheduler );
39
40  _Scheduler_SMP_Initialize( &self->Base );
41  _Priority_bit_map_Initialize( &self->Bit_map );
42  _Scheduler_priority_Ready_queue_initialize(
43    &self->Ready[ 0 ],
44    scheduler->maximum_priority
45  );
46}
47
48void _Scheduler_priority_SMP_Node_initialize(
49  const Scheduler_Control *scheduler,
50  Scheduler_Node          *node,
51  Thread_Control          *the_thread,
52  Priority_Control         priority
53)
54{
55  Scheduler_Context              *context;
56  Scheduler_priority_SMP_Context *self;
57  Scheduler_priority_SMP_Node    *the_node;
58
59  the_node = _Scheduler_priority_SMP_Node_downcast( node );
60  _Scheduler_SMP_Node_initialize(
61    scheduler,
62    &the_node->Base,
63    the_thread,
64    priority
65  );
66
67  context = _Scheduler_Get_context( scheduler );
68  self = _Scheduler_priority_SMP_Get_self( context );
69  _Scheduler_priority_Ready_queue_update(
70    &the_node->Ready_queue,
71    SCHEDULER_PRIORITY_UNMAP( priority ),
72    &self->Bit_map,
73    &self->Ready[ 0 ]
74  );
75}
76
77static Scheduler_Node *_Scheduler_priority_SMP_Get_highest_ready(
78  Scheduler_Context *context,
79  Scheduler_Node    *node
80)
81{
82  Scheduler_priority_SMP_Context *self =
83    _Scheduler_priority_SMP_Get_self( context );
84
85  (void) node;
86
87  return (Scheduler_Node *) _Scheduler_priority_Ready_queue_first(
88    &self->Bit_map,
89    &self->Ready[ 0 ]
90  );
91}
92
93void _Scheduler_priority_SMP_Block(
94  const Scheduler_Control *scheduler,
95  Thread_Control          *thread,
96  Scheduler_Node          *node
97)
98{
99  Scheduler_Context *context = _Scheduler_Get_context( scheduler );
100
101  _Scheduler_SMP_Block(
102    context,
103    thread,
104    node,
105    _Scheduler_SMP_Extract_from_scheduled,
106    _Scheduler_priority_SMP_Extract_from_ready,
107    _Scheduler_priority_SMP_Get_highest_ready,
108    _Scheduler_priority_SMP_Move_from_ready_to_scheduled,
109    _Scheduler_SMP_Allocate_processor_lazy
110  );
111}
112
113static bool _Scheduler_priority_SMP_Enqueue(
114  Scheduler_Context *context,
115  Scheduler_Node    *node,
116  Priority_Control   insert_priority
117)
118{
119  return _Scheduler_SMP_Enqueue(
120    context,
121    node,
122    insert_priority,
123    _Scheduler_SMP_Priority_less_equal,
124    _Scheduler_priority_SMP_Insert_ready,
125    _Scheduler_SMP_Insert_scheduled,
126    _Scheduler_priority_SMP_Move_from_scheduled_to_ready,
127    _Scheduler_SMP_Get_lowest_scheduled,
128    _Scheduler_SMP_Allocate_processor_lazy
129  );
130}
131
132static bool _Scheduler_priority_SMP_Enqueue_scheduled(
133  Scheduler_Context *context,
134  Scheduler_Node    *node,
135  Priority_Control   insert_priority
136)
137{
138  return _Scheduler_SMP_Enqueue_scheduled(
139    context,
140    node,
141    insert_priority,
142    _Scheduler_SMP_Priority_less_equal,
143    _Scheduler_priority_SMP_Extract_from_ready,
144    _Scheduler_priority_SMP_Get_highest_ready,
145    _Scheduler_priority_SMP_Insert_ready,
146    _Scheduler_SMP_Insert_scheduled,
147    _Scheduler_priority_SMP_Move_from_ready_to_scheduled,
148    _Scheduler_SMP_Allocate_processor_lazy
149  );
150}
151
152void _Scheduler_priority_SMP_Unblock(
153  const Scheduler_Control *scheduler,
154  Thread_Control          *thread,
155  Scheduler_Node          *node
156)
157{
158  Scheduler_Context *context = _Scheduler_Get_context( scheduler );
159
160  _Scheduler_SMP_Unblock(
161    context,
162    thread,
163    node,
164    _Scheduler_priority_SMP_Do_update,
165    _Scheduler_priority_SMP_Enqueue
166  );
167}
168
169static bool _Scheduler_priority_SMP_Do_ask_for_help(
170  Scheduler_Context *context,
171  Thread_Control    *the_thread,
172  Scheduler_Node    *node
173)
174{
175  return _Scheduler_SMP_Ask_for_help(
176    context,
177    the_thread,
178    node,
179    _Scheduler_SMP_Priority_less_equal,
180    _Scheduler_priority_SMP_Insert_ready,
181    _Scheduler_SMP_Insert_scheduled,
182    _Scheduler_priority_SMP_Move_from_scheduled_to_ready,
183    _Scheduler_SMP_Get_lowest_scheduled,
184    _Scheduler_SMP_Allocate_processor_lazy
185  );
186}
187
188void _Scheduler_priority_SMP_Update_priority(
189  const Scheduler_Control *scheduler,
190  Thread_Control          *thread,
191  Scheduler_Node          *node
192)
193{
194  Scheduler_Context *context = _Scheduler_Get_context( scheduler );
195
196  _Scheduler_SMP_Update_priority(
197    context,
198    thread,
199    node,
200    _Scheduler_priority_SMP_Extract_from_ready,
201    _Scheduler_priority_SMP_Do_update,
202    _Scheduler_priority_SMP_Enqueue,
203    _Scheduler_priority_SMP_Enqueue_scheduled,
204    _Scheduler_priority_SMP_Do_ask_for_help
205  );
206}
207
208bool _Scheduler_priority_SMP_Ask_for_help(
209  const Scheduler_Control *scheduler,
210  Thread_Control          *the_thread,
211  Scheduler_Node          *node
212)
213{
214  Scheduler_Context *context = _Scheduler_Get_context( scheduler );
215
216  return _Scheduler_priority_SMP_Do_ask_for_help( context, the_thread, node );
217}
218
219void _Scheduler_priority_SMP_Reconsider_help_request(
220  const Scheduler_Control *scheduler,
221  Thread_Control          *the_thread,
222  Scheduler_Node          *node
223)
224{
225  Scheduler_Context *context = _Scheduler_Get_context( scheduler );
226
227  _Scheduler_SMP_Reconsider_help_request(
228    context,
229    the_thread,
230    node,
231    _Scheduler_priority_SMP_Extract_from_ready
232  );
233}
234
235void _Scheduler_priority_SMP_Withdraw_node(
236  const Scheduler_Control *scheduler,
237  Thread_Control          *the_thread,
238  Scheduler_Node          *node,
239  Thread_Scheduler_state   next_state
240)
241{
242  Scheduler_Context *context = _Scheduler_Get_context( scheduler );
243
244  _Scheduler_SMP_Withdraw_node(
245    context,
246    the_thread,
247    node,
248    next_state,
249    _Scheduler_priority_SMP_Extract_from_ready,
250    _Scheduler_priority_SMP_Get_highest_ready,
251    _Scheduler_priority_SMP_Move_from_ready_to_scheduled,
252    _Scheduler_SMP_Allocate_processor_lazy
253  );
254}
255
256void _Scheduler_priority_SMP_Add_processor(
257  const Scheduler_Control *scheduler,
258  Thread_Control          *idle
259)
260{
261  Scheduler_Context *context = _Scheduler_Get_context( scheduler );
262
263  _Scheduler_SMP_Add_processor(
264    context,
265    idle,
266    _Scheduler_priority_SMP_Has_ready,
267    _Scheduler_priority_SMP_Enqueue_scheduled,
268    _Scheduler_SMP_Do_nothing_register_idle
269  );
270}
271
272Thread_Control *_Scheduler_priority_SMP_Remove_processor(
273  const Scheduler_Control *scheduler,
274  Per_CPU_Control         *cpu
275)
276{
277  Scheduler_Context *context = _Scheduler_Get_context( scheduler );
278
279  return _Scheduler_SMP_Remove_processor(
280    context,
281    cpu,
282    _Scheduler_priority_SMP_Extract_from_ready,
283    _Scheduler_priority_SMP_Enqueue
284  );
285}
286
287void _Scheduler_priority_SMP_Yield(
288  const Scheduler_Control *scheduler,
289  Thread_Control          *thread,
290  Scheduler_Node          *node
291)
292{
293  Scheduler_Context *context = _Scheduler_Get_context( scheduler );
294
295  _Scheduler_SMP_Yield(
296    context,
297    thread,
298    node,
299    _Scheduler_priority_SMP_Extract_from_ready,
300    _Scheduler_priority_SMP_Enqueue,
301    _Scheduler_priority_SMP_Enqueue_scheduled
302  );
303}
Note: See TracBrowser for help on using the repository browser.