source: rtems/cpukit/score/src/threadqextract.c @ e8fffc2d

4.115
Last change on this file since e8fffc2d was 91e7b0c, checked in by Sebastian Huber <sebastian.huber@…>, on 03/27/14 at 08:04:47

score: PR2172: _Thread_queue_Extract()

Add _Thread_queue_Extract_with_return_code(). On SMP this sequence in
_Thread_queue_Process_timeout() was broken:

[...]

/*

  • After we enable interrupts here, a lot may happen in the
  • meantime, e.g. nested interrupts may release the resource that
  • times out here. So we enter _Thread_queue_Extract()
  • speculatively. Inside this function we check the actual status
  • under ISR disable protection. This ensures that exactly one
  • executing context performs the extract operation (other parties
  • may call _Thread_queue_Dequeue()). If this context won, then
  • we have a timeout. *
  • We can use the_thread_queue pointer here even if
  • the_thread->Wait.queue is already set to NULL since the extract
  • operation will only use the thread queue discipline to select
  • the right extract operation. The timeout status is set during
  • thread queue initialization. */

we_did_it = _Thread_queue_Extract( the_thread_queue, the_thread );
if ( we_did_it ) {

the_thread->Wait.return_code = the_thread_queue->timeout_status;

}

[...]

In case _Thread_queue_Extract() successfully extracted a thread, then
this thread may start execution on a remote processor immediately and
read the the_thread->Wait.return_code before we update it here with the
timeout status. Thus it observes a successful operation even if it
timed out.

  • Property mode set to 100644
File size: 1.2 KB
Line 
1/**
2 * @file
3 *
4 * @brief Extracts Thread from Thread Queue
5 *
6 * @ingroup ScoreThreadQ
7 */
8
9/*
10 *  COPYRIGHT (c) 1989-2008.
11 *  On-Line Applications Research Corporation (OAR).
12 *
13 *  The license and distribution terms for this file may be
14 *  found in the file LICENSE in this distribution or at
15 *  http://www.rtems.org/license/LICENSE.
16 */
17
18#if HAVE_CONFIG_H
19#include "config.h"
20#endif
21
22#include <rtems/score/threadqimpl.h>
23
24void _Thread_queue_Extract_with_return_code(
25  Thread_queue_Control *the_thread_queue,
26  Thread_Control       *the_thread,
27  uint32_t              return_code
28)
29{
30  /*
31   * Can not use indirect function pointer here since Extract priority
32   * is a macro and the underlying methods do not have the same signature.
33   */
34  if  ( the_thread_queue->discipline == THREAD_QUEUE_DISCIPLINE_PRIORITY )
35    return _Thread_queue_Extract_priority( the_thread, return_code );
36  else /* must be THREAD_QUEUE_DISCIPLINE_FIFO */
37    return _Thread_queue_Extract_fifo( the_thread, return_code );
38
39}
40
41void _Thread_queue_Extract(
42  Thread_queue_Control *the_thread_queue,
43  Thread_Control       *the_thread
44)
45{
46  _Thread_queue_Extract_with_return_code(
47    the_thread_queue,
48    the_thread,
49    the_thread->Wait.return_code
50  );
51}
Note: See TracBrowser for help on using the repository browser.