Skip to content

Commit

Permalink
performance measurements: extend perf meas state ipc
Browse files Browse the repository at this point in the history
Implement actual functionality for perf meas state ipc handling. This
enables changing the state of global performance measurements.

Signed-off-by: Tobiasz Dryjanski <tobiaszx.dryjanski@intel.com>
  • Loading branch information
tobonex committed Jun 6, 2024
1 parent c5eeae9 commit d09a79f
Show file tree
Hide file tree
Showing 3 changed files with 105 additions and 7 deletions.
17 changes: 10 additions & 7 deletions src/audio/base_fw.c
Original file line number Diff line number Diff line change
Expand Up @@ -406,20 +406,23 @@ int set_perf_meas_state(const char *data)
#ifdef CONFIG_SOF_TELEMETRY
enum ipc4_perf_measurements_state_set state = *data;

struct telemetry_wnd_data *wnd_data =
(struct telemetry_wnd_data *)ADSP_DW->slots[SOF_DW_TELEMETRY_SLOT];
struct system_tick_info *systick_info =
(struct system_tick_info *)wnd_data->system_tick_info;

switch (state) {
case IPC4_PERF_MEASUREMENTS_DISABLED:
disable_performance_counters();
perf_meas_set_state(IPC4_PERF_MEASUREMENTS_DISABLED);
break;
case IPC4_PERF_MEASUREMENTS_STOPPED:
for (int i = 0; i < CONFIG_MAX_CORE_COUNT; i++)
systick_info[i].peak_utilization = 0;
enable_performance_counters();
reset_performance_counters();
perf_meas_set_state(IPC4_PERF_MEASUREMENTS_STOPPED);
break;
case IPC4_PERF_MEASUREMENTS_STARTED:
enable_performance_counters();
perf_meas_set_state(IPC4_PERF_MEASUREMENTS_STARTED);
break;
case IPC4_PERF_MEASUREMENTS_PAUSED:
enable_performance_counters();
perf_meas_set_state(IPC4_PERF_MEASUREMENTS_PAUSED);
break;
default:
return -EINVAL;
Expand Down
88 changes: 88 additions & 0 deletions src/debug/telemetry/telemetry.c
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,9 @@
#include <stddef.h>
#include <stdint.h>

#include <sof/lib_manager.h>
#include <ipc4/base_fw_vendor.h>

LOG_MODULE_DECLARE(ipc, CONFIG_SOF_LOG_LEVEL);

#define PERFORMANCE_DATA_ENTRIES_COUNT (CONFIG_MEMORY_WIN_3_SIZE / sizeof(struct perf_data_item_comp))
Expand Down Expand Up @@ -280,6 +283,91 @@ int get_extended_performance_data(struct extended_global_perf_data * const ext_g
return IPC4_SUCCESS;
}

enum ipc4_perf_measurements_state_set perf_meas_get_state(void)
{
return perf_measurements_state;
}

void perf_meas_set_state(enum ipc4_perf_measurements_state_set state)
{
perf_measurements_state = state;
}

void disable_performance_counters(void)
{
for (size_t idx = 0; idx < perf_bitmap_get_size(&performance_data_bitmap); ++idx) {
if (perf_bitmap_is_bit_clear(&performance_data_bitmap, idx))
continue;
if (perf_data_[idx].item.is_removed)
perf_data_free(&perf_data_[idx]);
}
}

int enable_performance_counters(void)
{
struct sof_man_module *man_module;
struct comp_dev *dev;
uint32_t comp_id;
const struct sof_man_fw_desc *desc;

if (perf_measurements_state != IPC4_PERF_MEASUREMENTS_DISABLED)
return -EINVAL;

for (int lib_id = 0; lib_id < LIB_MANAGER_MAX_LIBS; ++lib_id) {
if (lib_id == 0) {
desc = basefw_vendor_get_manifest();
} else {
#if CONFIG_LIBRARY_MANAGER
desc = (struct sof_man_fw_desc *)lib_manager_get_library_manifest(lib_id);
#else
desc = NULL;
#endif
}
if (!desc)
continue;

for (int mod_id = 0 ; mod_id < desc->header.num_module_entries; mod_id++) {
man_module =
(struct sof_man_module *)(desc + SOF_MAN_MODULE_OFFSET(mod_id));

for (int inst_id = 0; inst_id < man_module->instance_max_count; inst_id++) {
comp_id = IPC4_COMP_ID(mod_id, inst_id);
dev = ipc4_get_comp_dev(comp_id);

if (dev)
comp_init_performance_data(dev);
}
}
}

/* TODO clear totaldspcycles here once implemented */
return IPC4_SUCCESS;
}

int reset_performance_counters(void)
{
if (perf_measurements_state == IPC4_PERF_MEASUREMENTS_DISABLED)
return -EINVAL;

struct telemetry_wnd_data *wnd_data =
(struct telemetry_wnd_data *)ADSP_DW->slots[SOF_DW_TELEMETRY_SLOT];
struct system_tick_info *systick_info =
(struct system_tick_info *)wnd_data->system_tick_info;

for (size_t core_id = 0; core_id < CONFIG_MAX_CORE_COUNT; ++core_id) {
if (!(cpu_enabled_cores() & BIT(core_id)))
continue;
systick_info[core_id].peak_utilization = 0;
}
for (size_t idx = 0; idx < perf_bitmap_get_size(&performance_data_bitmap); ++idx) {
if (!perf_bitmap_is_bit_clear(&performance_data_bitmap, idx))
perf_data_item_comp_reset(&perf_data_[idx]);
}
/* TODO clear totaldspcycles here once implemented */

return IPC4_SUCCESS;
}

/* Systic variables, one set per core */
static int telemetry_systick_counter[CONFIG_MAX_CORE_COUNT];
#ifdef CONFIG_SOF_TELEMETRY_PERFORMANCE_MEASUREMENTS
Expand Down
7 changes: 7 additions & 0 deletions src/include/sof/debug/telemetry/telemetry.h
Original file line number Diff line number Diff line change
Expand Up @@ -104,4 +104,11 @@ int get_performance_data(struct global_perf_data * const global_perf_data);

int get_extended_performance_data(struct extended_global_perf_data * const ext_global_perf_data);

int reset_performance_counters(void);
int enable_performance_counters(void);
void disable_performance_counters(void);

void perf_meas_set_state(enum ipc4_perf_measurements_state_set state);
enum ipc4_perf_measurements_state_set perf_meas_get_state(void);

#endif /*__SOF_TELEMETRY_H__ */

0 comments on commit d09a79f

Please sign in to comment.