source: rtems/cpukit/libmisc/capture/capture_user_extension.c @ 3d5bcded

4.115
Last change on this file since 3d5bcded was 3d5bcded, checked in by Jennifer Averett <jennifer.averett@…>, on 10/03/14 at 19:01:44

capture: Move logging of task record to occur after filter check.

The catpture task record is now logged just prior to the first
log entry using that task instead of the first time the task
is seen. This involved splitting the record task method into
an initialize task and a record task.

  • Property mode set to 100644
File size: 8.1 KB
Line 
1/*
2  ------------------------------------------------------------------------
3
4  Copyright Objective Design Systems Pty Ltd, 2002
5  All rights reserved Objective Design Systems Pty Ltd, 2002
6  Chris Johns (ccj@acm.org)
7
8  COPYRIGHT (c) 1989-2009.
9  On-Line Applications Research Corporation (OAR).
10
11  The license and distribution terms for this file may be
12  found in the file LICENSE in this distribution.
13
14  This software with is provided ``as is'' and with NO WARRANTY.
15
16  ------------------------------------------------------------------------
17
18  RTEMS Performance Monitoring and Measurement Framework.
19
20  This is the Capture Engine component.
21rtems_status_code rtems_capture_user_extension_open(void);
22rtems_status_code rtems_capture_user_extension_close(void);
23
24
25*/
26
27#ifdef HAVE_CONFIG_H
28#include "config.h"
29#endif
30
31#include <stdlib.h>
32#include <string.h>
33#include <rtems/rtems/tasksimpl.h>
34
35#include "captureimpl.h"
36
37#include <rtems/score/statesimpl.h>
38#include <rtems/score/todimpl.h>
39
40
41/*
42 * RTEMS Capture User Extension Data.
43 */
44static rtems_id                 capture_id;
45
46static bool
47rtems_capture_create_task (rtems_tcb* current_task,
48                           rtems_tcb* new_task);
49
50static void
51rtems_capture_start_task (rtems_tcb* current_task,
52                          rtems_tcb* started_task);
53
54static void
55rtems_capture_restart_task (rtems_tcb* current_task,
56                            rtems_tcb* restarted_task);
57
58static void
59rtems_capture_delete_task (rtems_tcb* current_task,
60                           rtems_tcb* deleted_task);
61
62static void
63rtems_capture_switch_task (rtems_tcb* current_task,
64                           rtems_tcb* heir_task);
65
66static void
67rtems_capture_begin_task (rtems_tcb* begin_task);
68
69static void
70rtems_capture_exitted_task (rtems_tcb* exitted_task);
71
72static void
73rtems_capture_terminated_task (rtems_tcb* terminated_task);
74
75static const rtems_extensions_table capture_extensions = {
76  .thread_create    = rtems_capture_create_task,
77  .thread_start     = rtems_capture_start_task,
78  .thread_restart   = rtems_capture_restart_task,
79  .thread_delete    = rtems_capture_delete_task,
80  .thread_switch    = rtems_capture_switch_task,
81  .thread_begin     = rtems_capture_begin_task,
82  .thread_exitted   = rtems_capture_exitted_task,
83  .fatal            = NULL,
84  .thread_terminate = rtems_capture_terminated_task
85};
86
87static inline void rtems_capture_record (
88  rtems_tcb*    tcb,
89  uint32_t      events
90)
91{
92  rtems_capture_record_t*  rec;
93  void*                    ptr;
94  size_t                   size = sizeof(*rec);
95
96  if (rtems_capture_filter( tcb, events) )
97    return;
98 
99  if (!rtems_capture_task_recorded (tcb))
100    rtems_capture_record_task (tcb);
101
102  rtems_capture_begin_add_record (tcb, events, size, &ptr);
103  rtems_capture_end_add_record ( ptr );
104}
105
106
107rtems_status_code rtems_capture_user_extension_open(void)
108{
109  rtems_status_code sc;
110  rtems_name        name;
111  int               index;
112
113  /*
114   * Register the user extension handlers for the CAPture Engine.
115   */
116  name = rtems_build_name ('C', 'A', 'P', 'E');
117  sc   = rtems_extension_create (name, &capture_extensions, &capture_id);
118  if (sc != RTEMS_SUCCESSFUL)
119    capture_id = 0;
120  else {
121    index = rtems_object_id_get_index (capture_id);
122    rtems_capture_set_extension_index( index );
123  }
124
125  return sc;
126}
127
128rtems_status_code rtems_capture_user_extension_close(void)
129{
130  rtems_status_code sc;
131  sc = rtems_extension_delete (capture_id);
132  return sc;
133}
134
135/*
136 * This function is called when a task is created.
137 */
138static bool
139rtems_capture_create_task (rtems_tcb* ct,
140                           rtems_tcb* nt)
141{
142  /*
143   * The task pointers may not be known as the task may have
144   * been created before the capture engine was open. Add them.
145   */
146
147  if (!rtems_capture_task_initialized (ct))
148    rtems_capture_initialize_task (ct);
149
150  /*
151   * Create the new task's capture control block.
152   */
153  rtems_capture_initialize_task (nt);
154
155  if (rtems_capture_trigger (ct, nt, RTEMS_CAPTURE_CREATE))
156  {
157    rtems_capture_record (ct, RTEMS_CAPTURE_CREATED_BY_EVENT);
158    rtems_capture_record (nt, RTEMS_CAPTURE_CREATED_EVENT);
159  }
160
161  return 1 == 1;
162}
163
164/*
165 * This function is called when a task is started.
166 */
167static void
168rtems_capture_start_task (rtems_tcb* ct,
169                          rtems_tcb* st)
170{
171  /*
172   * The task pointers may not be known as the task may have
173   * been created before the capture engine was open. Add them.
174   */
175
176  if (!rtems_capture_task_initialized (ct))
177    rtems_capture_initialize_task (ct);
178
179  if (st == NULL)
180    rtems_capture_initialize_task (st);
181
182  if (rtems_capture_trigger (ct, st, RTEMS_CAPTURE_START))
183  {
184    rtems_capture_record (ct, RTEMS_CAPTURE_STARTED_BY_EVENT);
185    rtems_capture_record (st, RTEMS_CAPTURE_STARTED_EVENT);
186  }
187}
188
189/*
190 * This function is called when a task is restarted.
191 */
192static void
193rtems_capture_restart_task (rtems_tcb* ct,
194                            rtems_tcb* rt)
195{
196  /*
197   * The task pointers may not be known as the task may have
198   * been created before the capture engine was open. Add them.
199   */
200
201  if (!rtems_capture_task_initialized (ct))
202    rtems_capture_initialize_task (ct);
203
204  if (!rtems_capture_task_initialized (rt))
205    rtems_capture_initialize_task (rt);
206
207  if (rtems_capture_trigger (ct, rt, RTEMS_CAPTURE_RESTART))
208  {
209    rtems_capture_record (ct, RTEMS_CAPTURE_RESTARTED_BY_EVENT);
210    rtems_capture_record (rt, RTEMS_CAPTURE_RESTARTED_EVENT);
211  }
212}
213
214/*
215 * This function is called when a task is deleted.
216 */
217static void
218rtems_capture_delete_task (rtems_tcb* ct,
219                           rtems_tcb* dt)
220{
221  if (!rtems_capture_task_initialized (ct))
222    rtems_capture_initialize_task (ct);
223
224  if (!rtems_capture_task_initialized (dt))
225    rtems_capture_initialize_task (dt);
226
227  if (rtems_capture_trigger (ct, dt, RTEMS_CAPTURE_DELETE))
228  {
229    rtems_capture_record (ct, RTEMS_CAPTURE_DELETED_BY_EVENT);
230    rtems_capture_record (dt, RTEMS_CAPTURE_DELETED_EVENT);
231  }
232}
233
234/*
235 * This function is called when a task is begun.
236 */
237static void
238rtems_capture_begin_task (rtems_tcb* bt)
239{
240  /*
241   * The task pointers may not be known as the task may have
242   * been created before the capture engine was open. Add them.
243   */
244
245  if (!rtems_capture_task_initialized (bt))
246    rtems_capture_initialize_task (bt);
247
248  if (rtems_capture_trigger (NULL, bt, RTEMS_CAPTURE_BEGIN))
249    rtems_capture_record (bt, RTEMS_CAPTURE_BEGIN_EVENT);
250}
251
252/*
253 * This function is called when a task is exitted. That is
254 * returned rather than was deleted.
255 */
256static void
257rtems_capture_exitted_task (rtems_tcb* et)
258{
259  /*
260   * The task pointers may not be known as the task may have
261   * been created before the capture engine was open. Add them.
262   */
263
264  if (!rtems_capture_task_initialized (et))
265    rtems_capture_initialize_task (et);
266
267  if (rtems_capture_trigger (NULL, et, RTEMS_CAPTURE_EXITTED))
268    rtems_capture_record (et, RTEMS_CAPTURE_EXITTED_EVENT);
269}
270
271/*
272 * This function is called when a termination request is identified.
273 */
274static void
275rtems_capture_terminated_task (rtems_tcb* tt)
276{
277  /*
278   * The task pointers may not be known as the task may have
279   * been created before the capture engine was open. Add them.
280   */
281
282  if (!rtems_capture_task_initialized (tt))
283    rtems_capture_initialize_task (tt);
284
285  if (rtems_capture_trigger (NULL, tt, RTEMS_CAPTURE_TERMINATED))
286    rtems_capture_record (tt, RTEMS_CAPTURE_TERMINATED_EVENT);
287}
288
289/*
290 * This function is called when a context is switched.
291 */
292static void
293rtems_capture_switch_task (rtems_tcb* ct,
294                           rtems_tcb* ht)
295{
296  uint32_t flags = rtems_capture_get_flags();
297
298  /*
299   * Only perform context switch trace processing if tracing is
300   * enabled.
301   */
302  if (flags & RTEMS_CAPTURE_ON)
303  {
304    rtems_capture_time_t time;
305
306    if (!rtems_capture_task_initialized (ct))
307      rtems_capture_initialize_task (ct);
308
309    if (!rtems_capture_task_initialized (ht))
310      rtems_capture_initialize_task (ht);
311
312    /*
313     * Update the execution time. Assume the time will not overflow
314     * for now. This may need to change.
315     */
316    rtems_capture_get_time (&time);
317
318    if (rtems_capture_trigger (ct, ht, RTEMS_CAPTURE_SWITCH))
319    {
320      rtems_capture_record (ct, RTEMS_CAPTURE_SWITCHED_OUT_EVENT);
321      rtems_capture_record (ht, RTEMS_CAPTURE_SWITCHED_IN_EVENT);
322    }
323  }
324}
Note: See TracBrowser for help on using the repository browser.