Use the bare-metal agent by calling the following public API functions.
barman_initializeThe function that you use to call barman_initialize(), and the parameters that you pass, depend on which datastore you are using.
When using the linear or circular RAM buffer:
BM_NONNULL((1, 3, 4))
bm_bool barman_initialize(bm_uint8 * buffer, bm_uintptr buffer_length,
When using STM:
BM_NONNULL((2, 3, 4))
bm_bool barman_initialize_with_stm_interface(void * stm_configuration_registers, void * stm_extended_stimulus_ports,
When using ITM on Arm® M-profile architectures:
BM_NONNULL((1, 2))
bm_bool barman_initialize_with_itm_interface(
When using ITM on Arm A- or R-profile architectures:
BM_NONNULL((1, 2, 3))
bm_bool barman_initialize_with_itm_interface(void * itm_registers,
The remaining parameters for each datastore are the same:
const char * target_name,
const struct bm_protocol_clock_info * clock_info,
#if BM_CONFIG_MAX_TASK_INFOS > 0
bm_uint32 num_task_entries,
const struct bm_protocol_task_info * task_entries,
#endif
#if BM_CONFIG_MAX_MMAP_LAYOUTS > 0
bm_uint32 num_mmap_entries,
const struct bm_protocol_mmap_layout * mmap_entries,
#endif
bm_uint32 timer_sample_rate);
The parameters are:
bufferPointer to in memory buffer.
buffer_lengthLength of the in memory buffer.
stm_configuration_registersBase address of the STM configuration registers. This parameter can be NULL if it is initialized elsewhere, for example by the debugger.
stm_extended_stimulus_portsBase address of the STM extended stimulus ports.
itm_registersBase address of the ITM registers.
datastore_configPointer to the configuration to pass to barman_ext_datastore_initialize.
target_nameName of the target device.
clock_infoInformation about the monotonic clock used for timestamps.
num_task_entriesLength of the array of task entries in task_entries. If this value is greater than BM_CONFIG_MAX_TASK_INFOS, it is truncated.
task_entriesThe task information descriptors. Can be NULL.
num_mmap_entriesThe length of the array of mmap entries in mmap_entries. If this value is greater than BM_CONFIG_MAX_MMAP_LAYOUT, it is truncated.
mmap_entriesThe mmap image layout descriptors. Can be NULL.
timer_sample_rateTimer-based sampling rate in Hertz. Zero indicates no timer-based sampling (assumes a maximum 4GHz sample rate). This value is informative only, and is used for reporting the timer frequency in the Streamline UI.
The function returns:
BM_TRUEOn success.
BM_FALSEOn failure.
Note
If BM_CONFIG_MAX_TASK_INFOS ≤ 0, num_task_entries and task_entries are not present.
If BM_CONFIG_MAX_MMAP_LAYOUTS ≤ 0, num_mmap_entries and mmap_entries are not present.
barman_enable_samplingEnables sampling. Call when all PMUs are enabled and the data store is configured.
void barman_enable_sampling(void);
barman_disable_samplingDisables sampling without reconfiguring the PMU. To resume sampling, call barman_enable_sampling().
void barman_disable_sampling(void);
barman_sample_countersReads the configured PMU counters for the current processing element and inserts them into the data store. Can also insert a Program Counter record using the return address as the PC sample.
void barman_sample_counters(bm_bool sample_return_address);
The parameters are:
sample_return_addressBM_TRUE to sample the return address as PC.
BM_FALSE to ignore.
Note
The Call Paths view displays the PC values. This view is blank if the application does not call barman_sample_counters() with sample_return_address == BM_TRUE, or barman_sample_counters_with_program_counter() with pc != BM_NULL.
Application code that is not doing periodic sampling typically calls this function with sample_return_address == BM_TRUE.
This function must be run on the processing element for the PMU that it intends to sample from. It must not be migrated to another processing element for the duration of the call. This is necessary as it needs to program the per processing element PMU registers.
barman_sample_counters_with_program_counterReads the configured PMU counters for the current processing element and inserts them into the data store.
void barman_sample_counters_with_program_counter(const void * pc);
The parameters are:
pcThe PC value to record. The PC entry is not inserted if pc == BM_NULL.
Note
The Call Paths view displays the PC values. This view is blank if the application does not call barman_sample_counters_with_program_counter() with pc != BM_NULL, or barman_sample_counters() with sample_return_address == BM_TRUE.
A periodic interrupt handler typically calls this function, with pc == <the_exception_return_address>.
This function must be run on the processing element for the PMU that it intends to sample from. It must not be migrated to another processing element for the duration of the call. This is necessary as it needs to program the per processing element PMU registers.
These functions for task information records are available if BM_CONFIG_MAX_TASK_INFOS > 0.
barman_add_task_recordAdds a task information record.
bm_bool barman_add_task_record(bm_uint64 timestamp, const struct bm_protocol_task_info * task_entry);
The parameters are:
timestampThe timestamp at which the record is inserted.
task_entryThe new task entry.
The function returns:
BM_TRUEOn success.
BM_FALSEOn failure.
barman_record_task_switchRecords that a task switch has occurred.
Call this function after the new task is made the current task, so a call to barman_ext_get_current_task_id() returns the new task ID. For example, insert it into the scheduler of an RTOS just after the new task is selected to record the task switch.
void barman_record_task_switch(enum bm_task_switch_reason reason);
The parameters are:
reasonReason for the task switch.
Note
Call after the task switch has occurred so that bm_ext_get_current_task() returns the task_id of the switched to task.
This function for MMAP records is available if BM_CONFIG_MAX_MMAP_LAYOUTS > 0.
barman_add_mmap_recordAdds a mmap information record.
bm_bool barman_add_mmap_record(bm_uint64 timestamp, const struct bm_protocol_mmap_layout * mmap_entry);
The parameters are:
timestampThe timestamp at which the record is inserted.
mmap_entryThe new mmap entry.
The function returns:
BM_TRUEOn success.
BM_FALSEOn failure.
bm_protocol_clock_infoDefines information about the monotonic clock used in the trace. Timestamp information is stored in arbitrary units within samples. Arbitrary units reduce the overhead of making the trace by removing the need to transform the timestamp into nanoseconds at the point the sample is recorded. The host expects timestamps to be in nanoseconds. The arbitrary timestamp information is transformed to nanoseconds according to the following formula:
bm_uint64 nanoseconds = (((timestamp - timestamp_base) * timestamp_multiplier) / timestamp_divisor);
For a clock that already returns time in nanoseconds, set timestamp_multiplier and timestamp_divisor to 1 and 1. If the clock counts in microseconds, set the multiplier and divisor to 1000 and 1. If the clock counts at a rate of n Hertz, set the multiplier to 1000000000 and the divisor to n.
struct bm_protocol_clock_info
{
bm_uint64 timestamp_base;
bm_uint64 timestamp_multiplier;
bm_uint64 timestamp_divisor;
bm_uint64 unix_base_ns;
};
The members are:
timestamp_baseThe base value of the timestamp so that this value is zero in the trace.
timestamp_multiplierThe clock rate ratio multiplier.
timestamp_divisorThe clock rate ratio divisor
unix_base_nsThe Unix timestamp base value, in nanoseconds, so a timestamp_base maps to a unix_base Unix time value.
bm_protocol_task_infoA task information record. Describes information about a unique task within the system.
struct bm_protocol_task_info
{
bm_task_id_t task_id;
const char * task_name;
};
The members are:
task_idThe task ID.
task_nameThe name of the task.
bm_protocol_mmap_layoutAn MMAP layout record. Describes the position of an executable image (or section thereof) in memory, allowing the host to map PC values to the appropriate executable image.
struct bm_protocol_mmap_layout
{
#if BM_CONFIG_MAX_TASK_INFOS > 0
bm_task_id_t task_id;
#endif
bm_uintptr base_address;
bm_uintptr length;
bm_uintptr image_offset;
const char * image_name;
};
The members are:
task_idThe task ID to associate with the map.
base_addressThe base address of the image, or image section.
lengthThe length of the image, or image section.
image_offsetThe image section offset.
image_nameThe name of the image.
bm_task_switch_reasonReason for a task switch.
enum bm_task_switch_reason
{
BM_TASK_SWITCH_REASON_PREEMPTED = 0,
BM_TASK_SWITCH_REASON_WAIT = 1
};
The members are:
BM_TASK_SWITCH_REASON_PREEMPTEDThread is preempted.
BM_TASK_SWITCH_REASON_WAITThread is blocked waiting, for example on I/O.
barman_wfiWraps WFI instruction and sends events before and after the WFI to log the time in WFI. This function is safe to use in place of the usual WFI asm instruction, as it degenerates to just a WFI instruction when Barman is disabled.
void barman_wfi(void);
barman_wfeWraps WFE instruction and sends events before and after the WFE to log the time in WFE. This function is safe to use in place of the usual WFE asm instruction as it degenerates to just a WFE instruction when Barman is disabled.
void barman_wfe(void);
barman_before_idleCall before a WFI or WFE, or other similar halting event, to log entry into the paused state. Can be used in situations where barman_wfi() or barman_wfe() is not suitable.
void barman_before_idle(void);
Note
You must use barman_before_idle() with barman_after_idle().
Using barman_wfi() or barman_wfe() is usually preferred, as it takes care of calling the before and after functions.
barman_after_idleCall after a WFI or WFE, or other similar halting event, to log exit from the paused state. Can be used in situations where barman_wfi() or barman_wfe() is not suitable.
void barman_after_idle(void);
Note
You must use barman_after_idle() with barman_before_idle().
Using barman_wfi() or barman_wfe() is usually preferred, as it takes care of calling the before and after functions.
barman_annotate_channelAdds a string annotation with a display color, and assigns it to a channel.
void barman_annotate_channel(bm_uint32 channel, bm_uint32 color, const char * string)
The parameters are:
channelThe channel number.
colorThe annotation color from bm_annotation_colors().
textThe annotation text, or null to end the previous annotation.
Note
Annotation channels and groups are used to organize annotations within the threads and processes section of the Timeline view. Each annotation channel appears in its own row under the thread. Channels can also be grouped and displayed under a group name, using the barman_annotate_name_group() function.
barman_annotate_name_channelDefines a channel and attaches it to an existing group.
void barman_annotate_name_channel(bm_uint32 channel, bm_uint32 group, const char * name)
The parameters are:
channelThe channel number.
groupThe group number.
nameThe name of the channel.
Note
The channel number must be unique within the task.
barman_annotate_name_groupDefines an annotation group.
void barman_annotate_name_group(bm_uint32 group, const char * name)
The parameters are:
groupThe group number.
nameThe name of the group.
Note
The group identifier, group, must be unique within the task.
barman_annotate_markerAdds a bookmark with a string and a color to the Timeline view and Log view. The string is displayed in the Timeline view when you hover over the bookmark, and in the Message column in the Log view.
void barman_annotate_marker(bm_uint32 color, const char * text)
The parameters are:
colorThe marker color from bm_annotation_colors().
textThe marker text, or null for no text.
bm_annotation_colors
Color macros for annotations.
See Annotation #defines.