source: rtems/cpukit/include/rtems/capture.h @ c9bd696

Last change on this file since c9bd696 was c9bd696, checked in by Andreas Dachsberger <andreas.dachsberger@…>, on Apr 3, 2019 at 6:31:25 AM

doxygen: New API subgroup Tracing

Update #3706.

  • Property mode set to 100644
File size: 32.3 KB
Line 
1/**
2 * @file
3 *
4 * @brief Capture Engine Component of the RTEMS Measurement and
5 * Monitoring System
6 *
7 * This is the Capture Engine component of the RTEMS Measurement and
8 * Monitoring system.
9 */
10
11/*
12  ------------------------------------------------------------------------
13
14  Copyright 2002, 2016 Chris Johns <chrisj@rtems.org>.
15  All rights reserved.
16
17  COPYRIGHT (c) 1989-2014
18  On-Line Applications Research Corporation (OAR).
19
20  The license and distribution terms for this file may be
21  found in the file LICENSE in this distribution.
22
23  This software with is provided ``as is'' and with NO WARRANTY.
24
25  ------------------------------------------------------------------------
26
27  RTEMS Performance Monitoring and Measurement Framework.
28  This is the Capture Engine component.
29
30*/
31
32#ifndef __CAPTURE_H_
33#define __CAPTURE_H_
34
35#include <rtems.h>
36#include <rtems/rtems/tasksimpl.h>
37#include <rtems/score/schedulerimpl.h>
38
39#include <string.h>
40
41/**
42 *  @defgroup libmisc_capture RTEMS Capture Engine
43 *
44 *  @ingroup RTEMSAPITracing
45 *
46 *  Capture Engine Component of the RTEMS Measurement and Monitoring System
47 */
48/**@{*/
49#ifdef __cplusplus
50extern "C" {
51#endif
52
53/*
54 * Global capture flags.
55 */
56#define RTEMS_CAPTURE_INIT           (1u << 0)
57#define RTEMS_CAPTURE_ON             (1U << 1)
58#define RTEMS_CAPTURE_NO_MEMORY      (1U << 2)
59#define RTEMS_CAPTURE_TRIGGERED      (1U << 3)
60#define RTEMS_CAPTURE_GLOBAL_WATCH   (1U << 4)
61#define RTEMS_CAPTURE_ONLY_MONITOR   (1U << 5)
62
63/*
64 * Per-CPU capture flags.
65 */
66#define RTEMS_CAPTURE_OVERFLOW       (1U << 0)
67#define RTEMS_CAPTURE_READER_ACTIVE  (1U << 1)
68#define RTEMS_CAPTURE_READER_WAITING (1U << 2)
69
70/**
71 * The number of tasks in a trigger group.
72 */
73#define RTEMS_CAPTURE_TRIGGER_TASKS (32)
74
75/**
76 * @brief A capture timestamp.
77 *
78 * This is a nanosecond capture timestamp
79 */
80typedef uint64_t rtems_capture_time;
81
82/**
83 * @brief Task id and mask for the from trigger.
84 *
85 * A from capture is a task id and a mask for the type of
86 * from trigger we are interested in. The mask uses the same
87 * bit maps as the flags field in the control structure. There
88 * will only be a from type trigger if the flags in the control
89 * structure has the specific *_BY bit set.
90 */
91typedef struct rtems_capture_from
92{
93  rtems_name name;
94  rtems_id   id;
95  uint32_t   trigger;
96} rtems_capture_from;
97
98/**
99 * @brief Capture control structure for a group of tasks.
100 *
101 * RTEMS control holds the trigger and watch configuration for a group of
102 * tasks with the same name. The flags hold global control flags.
103 *
104 * The to_triggers fields holds triggers TO this task. The from_triggers holds
105 * triggers from this task. The by_triggers is an OR or triggers which are
106 * caused BY the task listed TO this task. The by_valid flag which entries
107 * in by are valid.
108 */
109typedef struct rtems_capture_control
110{
111  rtems_name                    name;
112  rtems_id                      id;
113  uint32_t                      flags;
114  uint32_t                      to_triggers;
115  uint32_t                      from_triggers;
116  uint32_t                      by_triggers;
117  uint32_t                      by_valid;
118  rtems_capture_from            by[RTEMS_CAPTURE_TRIGGER_TASKS];
119  struct rtems_capture_control* next;
120} rtems_capture_control;
121
122/**
123 * The from_valid mask.
124 */
125#define RTEMS_CAPTURE_CONTROL_FROM_MASK(_s) \
126 (UINT32_C(1) << (RTEMS_CAPTURE_TRIGGER_TASKS - ((_s) + 1)))
127
128/**
129 * Control flags.
130 */
131#define RTEMS_CAPTURE_WATCH         (1U << 0)
132
133/**
134 * Control triggers.
135 */
136#define RTEMS_CAPTURE_SWITCH        (1 << 0)
137#define RTEMS_CAPTURE_CREATE        (1 << 1)
138#define RTEMS_CAPTURE_START         (1 << 2)
139#define RTEMS_CAPTURE_RESTART       (1 << 3)
140#define RTEMS_CAPTURE_DELETE        (1 << 4)
141#define RTEMS_CAPTURE_BEGIN         (1 << 5)
142#define RTEMS_CAPTURE_EXITTED       (1 << 6)
143#define RTEMS_CAPTURE_TERMINATED    (1 << 7)
144
145#define RTEMS_CAPTURE_FROM_TRIGS    (RTEMS_CAPTURE_SWITCH  | \
146                                     RTEMS_CAPTURE_CREATE | \
147                                     RTEMS_CAPTURE_START | \
148                                     RTEMS_CAPTURE_RESTART | \
149                                     RTEMS_CAPTURE_DELETE)
150
151#define RTEMS_CAPTURE_TO_TRIGS      (RTEMS_CAPTURE_SWITCH | \
152                                     RTEMS_CAPTURE_CREATE | \
153                                     RTEMS_CAPTURE_START | \
154                                     RTEMS_CAPTURE_RESTART | \
155                                     RTEMS_CAPTURE_DELETE | \
156                                     RTEMS_CAPTURE_BEGIN | \
157                                     RTEMS_CAPTURE_EXITTED)
158
159/**
160 * Task flags.
161 */
162#define RTEMS_CAPTURE_TRACED      (1U << 0)
163#define RTEMS_CAPTURE_INIT_TASK   (1U << 1)
164#define RTEMS_CAPTURE_RECORD_TASK (1U << 2)
165
166/*
167 * @brief Capture record.
168 *
169 * This is a record that is written into
170 * the buffer. The events includes the priority of the task
171 * at the time of the context switch.
172 */
173typedef struct rtems_capture_record
174{
175  size_t             size;
176  uint32_t           events;
177  rtems_id           task_id;
178  rtems_capture_time time;
179} RTEMS_PACKED rtems_capture_record;
180
181/*
182 * @brief Capture task record.
183 *
184 * This is a record that is written into
185 * the buffer. The events includes the priority of the task
186 * at the time of the context switch.
187 */
188typedef struct rtems_capture_task_record
189{
190  rtems_name          name;
191  rtems_task_priority start_priority;
192  uint32_t            stack_size;
193} RTEMS_PACKED rtems_capture_task_record;
194
195/**
196 * The capture record event flags.
197 */
198#define RTEMS_CAPTURE_REAL_PRI_EVENT_MASK UINT32_C (0x000000ff)
199#define RTEMS_CAPTURE_CURR_PRI_EVENT_MASK UINT32_C (0x0000ff00)
200#define RTEMS_CAPTURE_REAL_PRIORITY_EVENT (0)
201#define RTEMS_CAPTURE_CURR_PRIORITY_EVENT (8)
202#define RTEMS_CAPTURE_EVENT_START         (16)
203#define RTEMS_CAPTURE_CREATED_BY_EVENT    UINT32_C (0x00010000)
204#define RTEMS_CAPTURE_CREATED_EVENT       UINT32_C (0x00020000)
205#define RTEMS_CAPTURE_STARTED_BY_EVENT    UINT32_C (0x00040000)
206#define RTEMS_CAPTURE_STARTED_EVENT       UINT32_C (0x00080000)
207#define RTEMS_CAPTURE_RESTARTED_BY_EVENT  UINT32_C (0x00100000)
208#define RTEMS_CAPTURE_RESTARTED_EVENT     UINT32_C (0x00200000)
209#define RTEMS_CAPTURE_DELETED_BY_EVENT    UINT32_C (0x00400000)
210#define RTEMS_CAPTURE_DELETED_EVENT       UINT32_C (0x00800000)
211#define RTEMS_CAPTURE_TERMINATED_EVENT    UINT32_C (0x01000000)
212#define RTEMS_CAPTURE_BEGIN_EVENT         UINT32_C (0x02000000)
213#define RTEMS_CAPTURE_EXITTED_EVENT       UINT32_C (0x04000000)
214#define RTEMS_CAPTURE_SWITCHED_OUT_EVENT  UINT32_C (0x08000000)
215#define RTEMS_CAPTURE_SWITCHED_IN_EVENT   UINT32_C (0x10000000)
216#define RTEMS_CAPTURE_TIMESTAMP           UINT32_C (0x20000000)
217#define RTEMS_CAPTURE_EVENT_END           (29)
218
219/**
220 * @brief Capture trigger modes
221 *
222 * The types of trigger modes that exist.
223 */
224typedef enum rtems_capture_trigger_mode
225{
226  rtems_capture_to_any,
227  rtems_capture_from_any,
228  rtems_capture_from_to
229} rtems_capture_trigger_mode;
230
231/**
232 * @brief Capture trigger.
233 *
234 * The types of triggers that exist.
235 */
236typedef enum rtems_capture_trigger
237{
238  rtems_capture_switch,
239  rtems_capture_create,
240  rtems_capture_start,
241  rtems_capture_restart,
242  rtems_capture_delete,
243  rtems_capture_begin,
244  rtems_capture_exitted,
245  rtems_capture_terminated
246} rtems_capture_trigger;
247
248/**
249 * @brief Capture timestamp callout handler.
250 *
251 * This defines the callout handler to obtain a time stamp. The
252 * value returned is time count since the last read.
253 *
254 */
255
256typedef void (*rtems_capture_timestamp)(rtems_capture_time* time);
257
258/**
259 * @brief Capture record lock context.
260 *
261 * This structure is used to lock a per CPU buffer when opeining recording. The
262 * per CPU buffer is held locked until the record close is called. Locking
263 * masks interrupts so use this lock only when needed and do not hold it for
264 * long.
265 *
266 * The lock first masks the CPU interrupt before taking the interrupt
267 * lock. This stops a thread context taking the lock and then an interrupt on
268 * the same CPU attempting to take the lock so creating a deadlock.
269 *
270 */
271typedef struct {
272  rtems_interrupt_lock_context lock_context;
273  rtems_interrupt_lock*        lock;
274} rtems_capture_record_lock_context;
275
276/**
277 * @brief Capture open
278 *
279 * This function initialises the realtime trace manager allocating the
280 * capture buffer. It is assumed we have a working heap at stage of
281 * initialisation.
282 *
283 * @param[in] size The number of capture records to define.
284 * @param[in] timestamp The timestamp callout handler to use. If the
285 *            the handler is NULL a default  nano-second timestamp
286 *            will be used.
287 *
288 * @retval This method returns RTEMS_SUCCESSFUL if there was not an
289 *         error. Otherwise, a status code is returned indicating the
290 *         source of the error.
291 */
292rtems_status_code rtems_capture_open (uint32_t                size,
293                                      rtems_capture_timestamp timestamp);
294
295/**
296 * @brief Capture close
297 *
298 * This function shutdowns the tracer and release any claimed
299 * resources.
300 *
301 * @retval This method returns RTEMS_SUCCESSFUL if there was not an
302 *         error. Otherwise, a status code is returned indicating the
303 *         source of the error.
304 */
305rtems_status_code rtems_capture_close (void);
306
307/**
308 * @brief Capture control trace enable/disable.
309 *
310 * This function allows control of tracing at a global level.
311 *
312 * @param[in]  enable The trace enable/disable flag.
313 *
314 * @retval This method returns RTEMS_SUCCESSFUL if there was not an
315 *         error. Otherwise, a status code is returned indicating the
316 *         source of the error.
317 */
318rtems_status_code rtems_capture_set_control (bool enable);
319
320/**
321 * @brief Capture monitor enable/disable.
322 *
323 * This function enable the monitor mode. When in the monitor mode
324 * the tasks are monitored but no data is saved. This can be used
325 * to profile the load on a system.
326 *
327 * @param[in]  enable The monitor enable/disable flag.
328 *
329 * @retval This method returns RTEMS_SUCCESSFUL if there was not an
330 *         error. Otherwise, a status code is returned indicating the
331 *         source of the error.
332 */
333rtems_status_code rtems_capture_set_monitor (bool enable);
334
335/*
336 * @brief Capture flush trace buffer.
337 *
338 * This function flushes the trace buffer. The prime parameter allows the
339 * capture engine to also be primed again.
340 *
341 * @param[in]  prime The prime after flush flag.
342 *
343 * @retval This method returns RTEMS_SUCCESSFUL if there was not an
344 *         error. Otherwise, a status code is returned indicating the
345 *         source of the error.
346 */
347rtems_status_code rtems_capture_flush (bool prime);
348
349/**
350 * @brief Capture add watch
351 *
352 * This function defines a watch for a specific task given a name. A watch
353 * causes it to be traced either in or out of context. The watch can be
354 * optionally enabled or disabled with the set routine. It is disabled by
355 * default.
356 *
357 * @param[in]  name The name of the @a capture_controls entry
358 * @param[in]  id The id of the @a capture_controls entry.
359 *
360 * @retval This method returns RTEMS_SUCCESSFUL if there was not an
361 *         error. Otherwise, a status code is returned indicating the
362 *         source of the error.
363 */
364rtems_status_code rtems_capture_watch_add (rtems_name name, rtems_id id);
365
366/**
367 * @brief Capture delete watch.
368 *
369 * This function removes a watch for a specific task given a name. The task
370 * description will still exist if referenced by a trace record in the trace
371 * buffer or a global watch is defined.
372 *
373 * @param[in]  name The name of the @a capture_controls entry
374 * @param[in]  id The id of the @a capture_controls entry.
375 *
376 * @retval This method returns RTEMS_SUCCESSFUL if there was not an
377 *         error. Otherwise, a status code is returned indicating the
378 *         source of the error.
379 */
380rtems_status_code rtems_capture_watch_del (rtems_name name, rtems_id id);
381
382/**
383 * @brief Capture enable/disable watch.
384 *
385 * This function allows control of a watch. The watch can be enabled or
386 * disabled.
387 *
388 * @param[in]  name The name of the @a capture_controls entry
389 * @param[in]  id The id of the @a capture_controls entry.
390 * @param[in]  enable The enable/disable flag for the watch.
391 *
392 * @retval This method returns RTEMS_SUCCESSFUL if there was not an
393 *         error. Otherwise, a status code is returned indicating the
394 *         source of the error.
395 */
396rtems_status_code rtems_capture_watch_ctrl (rtems_name name,
397                                            rtems_id   id,
398                                            bool       enable);
399
400/**
401 * @brief Capture enable/disable global watch.
402 *
403 * This function allows control of a global watch. The watch can
404 * be enabled or disabled. A global watch configures all tasks below
405 * the ceiling and above the floor to be traced.
406 *
407 * @param[in]  enable The enable/disable flag for the watch.
408 *
409 * @retval This method returns RTEMS_SUCCESSFUL if there was not an
410 *         error. Otherwise, a status code is returned indicating the
411 *         source of the error.
412 */
413rtems_status_code rtems_capture_watch_global (bool enable);
414
415/**
416 * @brief Get global watch state
417 *
418 * This function returns the global watch state.
419 *
420 * @retval This method returns true  if the global watch
421 *         is on.  Otherwise, it returns false.
422 */
423bool rtems_capture_watch_global_on (void);
424
425/**
426 * @brief Set watch ceiling.
427 *
428 * This function sets a watch ceiling. Events from tasks at or greater
429 * than the ceiling priority are ignored. This is a simple way to
430 * monitor an application and exclude system tasks running at a higher
431 * priority level.
432 *
433 * @param[in] ceiling specifies the priority level immediately above
434 *     that at which events from tasks are not captured.
435 *
436 * @retval This method returns RTEMS_SUCCESSFUL if there was not an
437 *         error. Otherwise, a status code is returned indicating the
438 *         source of the error.
439 */
440rtems_status_code rtems_capture_watch_ceiling (rtems_task_priority ceiling);
441
442/**
443 * @brief Get watch ceiling.
444 *
445 * This function gets the watch ceiling.
446 *
447 * @retval The priority level immediately above that at which events
448 *         from tasks are not captured.
449 */
450rtems_task_priority rtems_capture_watch_get_ceiling (void);
451
452/**
453 * @brief Capture set watch floor.
454 *
455 * This function sets a watch floor. Tasks at or less than the
456 * floor priority are not watched. This is a simple way to monitor
457 * an application and exclude system tasks running at a lower
458 * priority level.
459 *
460 * @param[in] floor specifies the priority level immediately below
461 *     that at which events from tasks are not captured.
462 *
463 * @retval This method returns RTEMS_SUCCESSFUL if there was not an
464 *         error. Otherwise, a status code is returned indicating the
465 *         source of the error.
466 */
467rtems_status_code rtems_capture_watch_floor (rtems_task_priority floor);
468
469/**
470 * @brief Capture set watch floor
471 *
472 * This function gets the watch floor.
473 *
474 * @retval The priority level immediately below
475 *     that at which events from tasks are not captured.
476 */
477rtems_task_priority rtems_capture_watch_get_floor (void);
478
479/**
480 * @brief Capture set trigger
481 *
482 * This function sets a trigger.
483 *
484 * This set trigger routine will create a trace control for the
485 * target task. The task list is searched and any existing tasks
486 * are linked to the new control.
487 *
488 * We can have a number of tasks that have the same name so we
489 * search using names. This means a number of tasks can be
490 * linked to single control.
491 *
492 * Some events captured such as context switch include two
493 * tasks. These are referred to as being "from" and "to"
494 * Some events may only have one task specified.
495 *
496 * @param[in] from_name specifies the name of the from task.
497 * @param[in] from_id specifies the id of the from task.
498 * @param[in] to_name specifies the name of the to task.
499 * @param[in] to_id specifies the id of the to task.
500 * @param[in] mode specifies the trigger mode.
501 * @param[in] trigger specifies the type of trigger.
502 *
503 * @retval This method returns RTEMS_SUCCESSFUL if there was not an
504 *         error. Otherwise, a status code is returned indicating the
505 *         source of the error.
506 */
507rtems_status_code
508rtems_capture_set_trigger (rtems_name                 from_name,
509                           rtems_id                   from_id,
510                           rtems_name                 to_name,
511                           rtems_id                   to_id,
512                           rtems_capture_trigger_mode mode,
513                           rtems_capture_trigger      trigger);
514
515/**
516 * @brief Capture clear trigger.
517 *
518 * This function clears a trigger.
519 *
520 * This clear trigger routine will not clear a watch.
521 *
522 * @param[in] from_name specifies the name of the from task.
523 * @param[in] from_id specifies the id of the from task.
524 * @param[in] to_name specifies the name of the to task.
525 * @param[in] to_id specifies the id of the to task.
526 * @param[in] mode specifies the trigger mode.
527 * @param[in] trigger specifies the type of trigger.
528 *
529 * @retval This method returns RTEMS_SUCCESSFUL if there was not an
530 *         error. Otherwise, a status code is returned indicating the
531 *         source of the error.
532 */
533rtems_status_code
534rtems_capture_clear_trigger (rtems_name                 from_name,
535                             rtems_id                   from_id,
536                             rtems_name                 to_name,
537                             rtems_id                   to_id,
538                             rtems_capture_trigger_mode mode,
539                             rtems_capture_trigger      trigger);
540
541/**
542 * @brief Capture read records from capture buffer
543 *
544 * This function reads a number of records from the capture buffer.
545 *
546 * The function returns the number of record that is has that are
547 * in a continous block of memory. If the number of available records
548 * wrap then only those records are provided. This removes the need for
549 * caller to be concerned about buffer wrappings. If the number of
550 * requested records cannot be met due to the wrapping of the records
551 * less than the specified number will be returned.
552 *
553 * The user must release the records. This is achieved with a call to
554 * rtems_capture_release. Calls this function without a release will
555 * result in at least the same number of records being released.
556 *
557 * @param[in]  cpu The cpu number that the records were recorded on
558 * @param[out] read will contain the number of records read
559 * @param[out] recs The capture records that are read.
560 *
561 * @retval This method returns RTEMS_SUCCESSFUL if there was not an
562 *         error. Otherwise, a status code is returned indicating the
563 *         source of the error.
564 */
565rtems_status_code rtems_capture_read (uint32_t     cpu,
566                                      size_t*      read,
567                                      const void** recs);
568
569/**
570 * @brief Capture release records.
571 *
572 * This function releases the requested number of record slots back
573 * to the capture engine. The count must match the number read.
574 *
575 * @param[in] count The number of record slots to release
576 *
577 * @retval This method returns RTEMS_SUCCESSFUL if there was not an
578 *         error. Otherwise, a status code is returned indicating the
579 *         source of the error.
580 */
581rtems_status_code rtems_capture_release (uint32_t cpu, uint32_t count);
582
583/**
584 * @brief Capture filter
585 *
586 * This function this function specifies if the given task and events should be
587 * logged.
588 *
589 * @param[in] task specifies the capture task control block
590 * @param[in] events specifies the events
591 *
592 * @retval This method returns true if this data should be filtered from the
593 *         log. It returns false if this data should be logged.
594 */
595bool rtems_capture_filter (rtems_tcb* task, uint32_t events);
596
597/**
598 * @brief Capture returns the current time.
599 *
600 * This function returns the current time. If a handler is provided
601 * by the user the time is gotten from that.
602 *
603 * @param[in] time specifies the capture time
604 *
605 * @retval This method returns a nano-second time if no user handler
606 * is provided.  Otherwise, it returns a resolution defined by the handler.
607 */
608void rtems_capture_get_time (rtems_capture_time* time);
609
610/**
611 * @brief Capture get event text.
612 *
613 * This function returns a string for an event based on the bit in the
614 * event. The functions takes the bit offset as a number not the bit
615 * set in a bit map.
616 *
617 * @param[in] event specifies the event to describe
618 *
619 * @retval This method returns a string description of the given event.
620 */
621const char* rtems_capture_event_text (int event);
622
623/**
624 * @brief Capture initialize task
625 *
626 * This function initializes capture control in the tcb.
627 *
628 * @param[in] tcb is the task control block for the task
629 */
630void rtems_capture_initialize_task (rtems_tcb* tcb);
631
632/**
633 * @brief Capture record task.
634 *
635 * This function records a new capture task record.
636 *
637 * @param[in] tcb is the task control block for the task
638 */
639void rtems_capture_record_task (rtems_tcb* tcb);
640
641/**
642 * @brief Capture record lock.
643 *
644 * This does a lock acquire which will remain in effect until
645 * rtems_capture_record_unlock is called.
646 *
647 * @param[out] context specifies the record context
648 */
649void rtems_capture_record_lock (rtems_capture_record_lock_context* context);
650
651/**
652 * @brief Capture record unlock.
653 *
654 * This unlocks the record lock.
655 *
656 * @param[in] context specifies the record context
657 */
658void rtems_capture_record_unlock (rtems_capture_record_lock_context* context);
659
660/**
661 * @brief Capture record open.
662 *
663 * This function allocates a record and fills in the header information. It
664 * does a lock acquire which will remain in effect until
665 * rtems_capture_record_close is called. The size is the amount of user data
666 * being recorded. The record header is internally managed.
667 *
668 * @param[in] task specifies the caputre task block
669 * @param[in] events specifies the events
670 * @param[in] size specifies the user's capture data size
671 * @param[out] context specifies the record context
672 *
673 * @retval This method returns a pointer to the next location in
674 * the capture record to store data.
675 */
676void* rtems_capture_record_open (rtems_tcb*                         task,
677                                 uint32_t                           events,
678                                 size_t                             size,
679                                 rtems_capture_record_lock_context* context);
680
681/**
682 * @brief Capture record close.
683 *
684 * This function closes writing to capure record and releases the lock that was
685 * held on the per CPU buffer.
686 *
687 * @param[out] context specifies the record context
688 */
689void rtems_capture_record_close (rtems_capture_record_lock_context* context);
690
691/**
692 * @brief Capture append to record to the per CPU buffer.
693 *
694 * This function appends data of a specifed size into a capture buffer.
695 *
696 * @param[in] rec specifies the next write point in the capture record
697 * @param[in] data specifies the data to write
698 * @param[in] size specifies the size of the data
699 *
700 * @retval This method returns the next write point in the capture record.
701 */
702static inline void*
703rtems_capture_record_append (void* rec, const void* data, size_t size)
704{
705  memcpy (rec, data, size);
706  return ((uint8_t*) rec) + size;
707}
708
709/**
710 * @brief Capture read a record from the per CPU buffer.
711 *
712 * This function reads data of a  specifed size from a capture buffer.
713 *
714 * @param[in] rec specifies the next read point in the capture record
715 * @param[in] data specifies where to write the data
716 * @param[in] size specifies the size of the data
717 *
718 * @retval This method returns the next write point in the capture record.
719 */
720static inline void*
721rtems_capture_record_extract (const void* rec, void* data, size_t size)
722{
723  memcpy (data, rec, size);
724  return ((uint8_t*) rec) + size;
725}
726
727/**
728 * @brief Capture task recorded
729 *
730 * This function returns true if this task information has been
731 * recorded.
732 *
733 * @param[in] tcb is the task control block for the task
734 */
735static inline bool rtems_capture_task_recorded (rtems_tcb* tcb) {
736  return ((tcb->Capture.flags & RTEMS_CAPTURE_RECORD_TASK) != 0);
737}
738
739/**
740 * @brief Capture task initialized
741 *
742 * This function returns true if this task information has been
743 * initialized.
744 *
745 * @param[in] tcb is the task control block for the task
746 */
747static inline bool rtems_capture_task_initialized (rtems_tcb* tcb) {
748  return ((tcb->Capture.flags & RTEMS_CAPTURE_INIT_TASK) != 0);
749}
750
751/**
752 * @brief Capture get task id.
753 *
754 * This function returns the task id.
755 *
756 * @param[in] task The capture task.
757 *
758 * @retval This function returns the task id.
759 */
760static inline rtems_id
761rtems_capture_task_id (rtems_tcb* tcb)
762{
763  return tcb->Object.id;
764}
765
766/**
767 * @brief Capture get task API.
768 *
769 * This function returns the task API as an int.
770 *
771 * @param[in] task The capture task.
772 *
773 * @retval This function returns the task API as an int.
774 */
775static inline int
776rtems_capture_task_api (rtems_id id)
777{
778  return _Objects_Get_API (id);
779}
780
781/**
782 * @brief Capture get task state.
783 *
784 * This function returns the task state.
785 *
786 * @param[in] task The capture task.
787 *
788 * @retval This function returns the task state.
789 */
790static inline States_Control
791rtems_capture_task_state (rtems_tcb* tcb)
792{
793  if (tcb)
794    return tcb->current_state;
795  return 0;
796}
797
798/**
799 * @brief Capture get task name.
800 *
801 * This function returns the task name.
802 *
803 * @param[in] task The capture task.
804 *
805 * @retval This function returns the task name.
806 */
807static inline rtems_name
808rtems_capture_task_name (rtems_tcb* tcb)
809{
810  rtems_name  name;
811  rtems_object_get_classic_name( tcb->Object.id, &name );
812  return name;
813}
814
815/**
816 * @brief Capture get task flags.
817 *
818 * This function returns the task flags.
819 *
820 * @param[in] task The capture task.
821 *
822 * @retval This function returns the task flags.
823 */
824static inline uint32_t
825rtems_capture_task_flags (rtems_tcb* tcb)
826{
827  return tcb->Capture.flags;
828}
829
830/**
831 * @brief Capture get task control
832 *
833 * This function returns the task control if present.
834 *
835 * @param[in] task The capture task.
836 *
837 * @retval This function returns the task control if present.
838 */
839static inline rtems_capture_control*
840rtems_capture_task_control (rtems_tcb* tcb)
841{
842  return tcb->Capture.control;
843}
844
845/**
846 * @brief Capture get task control flags.
847 *
848 * This function returns the task control flags if a control is present.
849 *
850 * @param[in] task The capture task.
851 *
852 * @retval This function returns the task control flags if a control is present.
853 */
854static inline uint32_t
855rtems_capture_task_control_flags (rtems_tcb* tcb)
856{
857  rtems_capture_control*  control = tcb->Capture.control;
858  if (!control)
859    return 0;
860  return control->flags;
861}
862
863/**
864 * @brief Capture get task start priority.
865 *
866 * This function returns the tasks start priority. The tracer needs this
867 * to track where the task's priority goes.
868 *
869 * @param[in] task The capture task.
870 *
871 * @retval This function returns the tasks start priority. The tracer needs this
872 * to track where the task's priority goes.
873 */
874static inline rtems_task_priority
875rtems_capture_task_start_priority (rtems_tcb* tcb)
876{
877  return _RTEMS_Priority_From_core (_Thread_Scheduler_get_home( tcb ),
878                                    tcb->Start.initial_priority);
879}
880
881/**
882 * @brief Capture get task real priority.
883 *
884 * This function returns the tasks real priority.
885 *
886 * @param[in] task The capture task.
887 *
888 * @retval This function returns the tasks real priority.
889 */
890static inline rtems_task_priority
891rtems_capture_task_real_priority (rtems_tcb* tcb)
892{
893  return SCHEDULER_PRIORITY_UNMAP (tcb->Real_priority.priority);
894}
895
896/**
897 * @brief Capture get task current priority.
898 *
899 * This function returns the tasks current priority.
900 *
901 * @param[in] task The capture task.
902 *
903 * @retval This function returns the tasks current priority.
904 */
905static inline rtems_task_priority
906rtems_capture_task_curr_priority (rtems_tcb* tcb)
907{
908  return SCHEDULER_PRIORITY_UNMAP (_Thread_Get_priority (tcb));
909}
910
911/**
912 * @brief Capture get control list.
913 *
914 * This function returns the head of the list of controls in the
915 * capture engine.
916 *
917 * @retval This function returns the head of the list of controls in the
918 * capture engine.
919 */
920rtems_capture_control*
921rtems_capture_get_control_list (void);
922
923/**
924 * @brief Capture get next capture control.
925 *
926 * This function returns the pointer to the next control in the list. The
927 * pointer NULL terminates the list.
928 *
929 * @param[in] control the current capture control.
930 *
931 * @retval This function returns the pointer to the next control in the list. The
932 * pointer NULL terminates the list.
933 */
934static inline rtems_capture_control*
935rtems_capture_next_control (rtems_capture_control* control)
936{
937  return control->next;
938}
939
940/**
941 * @brief Capture get capture control id.
942 *
943 * This function returns the control id.
944 *
945 * @param[in] control the capture control.
946 *
947 * @retval This function returns the control id.
948 */
949static inline rtems_id
950rtems_capture_control_id (rtems_capture_control* control)
951{
952  return control->id;
953}
954
955/**
956 * @brief Capture get capture control name.
957 *
958 * This function returns the control name.
959 *
960 * @param[in] control the capture control.
961 *
962 * @retval This function returns the control name.
963 */
964static inline rtems_name
965rtems_capture_control_name (rtems_capture_control* control)
966{
967  return control->name;
968}
969
970/**
971 * @brief Capture get capture control flags.
972 *
973 * This function returns the control flags.
974 *
975 * @param[in] control the capture control.
976 *
977 * @retval This function returns the control flags.
978 */
979static inline uint32_t
980rtems_capture_control_flags (rtems_capture_control* control)
981{
982  return control->flags;
983}
984
985/**
986 * @brief Capture get capture control to triggers.
987 *
988 * This function returns the task control to triggers.
989 *
990 * @param[in] control the capture control.
991 *
992 * @retval This function returns the task control to triggers.
993 */
994static inline uint32_t
995rtems_capture_control_to_triggers (rtems_capture_control* control)
996{
997  return control->to_triggers;
998}
999
1000/**
1001 * @brief Capture get capture control from triggers.
1002 *
1003 * This function returns the task control from triggers.
1004 *
1005 * @param[in] control the capture control.
1006 *
1007 * @retval This function returns the task control from triggers.
1008 */
1009static inline uint32_t
1010rtems_capture_control_from_triggers (rtems_capture_control* control)
1011{
1012  return control->from_triggers;
1013}
1014
1015/**
1016 * @brief Capture get capture control by triggers.
1017 *
1018 * This function returns the task control by triggers.
1019 *
1020 * @param[in] control the capture control.
1021 *
1022 * @retval This function returns the task control by triggers.
1023 */
1024static inline uint32_t
1025rtems_capture_control_all_by_triggers (rtems_capture_control* control)
1026{
1027  return control->by_triggers;
1028}
1029
1030/**
1031 * @brief Capture get capture control valid by flags.
1032 *
1033 * This function returns the control valid BY flags.
1034 *
1035 * @param[in] control The capture control.
1036 * @param[in] slot The slot.
1037 *
1038 * @retval This function returns the control valid BY flags.
1039 */
1040static inline int
1041rtems_capture_control_by_valid (rtems_capture_control* control, int slot)
1042{
1043  return control->by_valid & RTEMS_CAPTURE_CONTROL_FROM_MASK (slot);
1044}
1045
1046/**
1047 * @brief Capture get capture control by task name.
1048 *
1049 * This function returns the control @a by task name.
1050 *
1051 * @param[in] control The capture control.
1052 * @param[in] by The by index.
1053 *
1054 * @retval This function returns the control @a by task name.
1055 */
1056static inline rtems_name
1057rtems_capture_control_by_name (rtems_capture_control* control, int by)
1058{
1059  if (by < RTEMS_CAPTURE_TRIGGER_TASKS)
1060    return control->by[by].name;
1061  return control->by[0].name;
1062}
1063
1064/**
1065 * @brief Capture get capture control by task id.
1066 *
1067 * This function returns the control @a by task id
1068 *
1069 * @retval This function returns the control @a by task id.
1070 */
1071static inline rtems_id
1072rtems_capture_control_by_id (rtems_capture_control* control, int by)
1073{
1074  if (by < RTEMS_CAPTURE_TRIGGER_TASKS)
1075    return control->by[by].id;
1076  return control->by[0].id;
1077}
1078
1079/**
1080 * @brief Capture get capture control by task triggers.
1081 *
1082 * This function returns the control @a by task triggers.
1083 *
1084 * @retval This function returns the control @a by task triggers.
1085 */
1086static inline uint32_t
1087rtems_capture_control_by_triggers (rtems_capture_control* control,
1088                                   int                      by)
1089{
1090  if (by < RTEMS_CAPTURE_TRIGGER_TASKS)
1091    return control->by[by].trigger;
1092  return control->by[0].trigger;
1093}
1094
1095/**
1096 * @brief Capture get capture control count.
1097 *
1098 * This function returns the number of controls the capture
1099 * engine has.
1100 *
1101 * @retval This function returns the number of controls the capture
1102 * engine has.
1103 */
1104static inline uint32_t
1105rtems_capture_control_count (void)
1106{
1107  rtems_capture_control* control = rtems_capture_get_control_list ();
1108  uint32_t               count = 0;
1109
1110  while (control)
1111  {
1112    count++;
1113    control = rtems_capture_next_control (control);
1114  }
1115
1116  return count;
1117}
1118
1119#ifdef __cplusplus
1120}
1121#endif
1122/**@}*/
1123
1124#endif
Note: See TracBrowser for help on using the repository browser.