mirror of
https://gitlab.freedesktop.org/mesa/mesa.git
synced 2026-05-05 16:08:04 +02:00
anv: add support for command buffer tagging in traces
Signed-off-by: Lionel Landwerlin <lionel.g.landwerlin@intel.com> Reviewed-by: Emma Anholt <emma@anholt.net> Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/16655>
This commit is contained in:
parent
662e05c9fb
commit
28b15fa9e7
4 changed files with 131 additions and 6 deletions
|
|
@ -195,12 +195,15 @@ send_descriptors(IntelRenderpassDataSource::TraceContext &ctx,
|
|||
PERFETTO_LOG("Sending renderstage descriptors");
|
||||
|
||||
device->event_id = 0;
|
||||
device->current_app_event_iid = device->start_app_event_iids;
|
||||
u_vector_foreach(queue, &device->queues) {
|
||||
for (uint32_t s = 0; s < ARRAY_SIZE(queue->stages); s++) {
|
||||
queue->stages[s].start_ns[0] = 0;
|
||||
}
|
||||
}
|
||||
|
||||
_mesa_hash_table_clear(device->app_events, NULL);
|
||||
|
||||
{
|
||||
auto packet = ctx.NewTracePacket();
|
||||
|
||||
|
|
@ -271,13 +274,46 @@ begin_event(struct intel_ds_queue *queue, uint64_t ts_ns,
|
|||
return;
|
||||
}
|
||||
|
||||
if (level >= (ARRAY_SIZE(queue->stages[stage_id].start_ns) - 1))
|
||||
return;
|
||||
|
||||
queue->stages[stage_id].start_ns[level] = ts_ns;
|
||||
queue->stages[stage_id].level++;
|
||||
}
|
||||
|
||||
static uint64_t
|
||||
add_app_event(IntelRenderpassDataSource::TraceContext &tctx,
|
||||
struct intel_ds_device *device,
|
||||
const char *app_event)
|
||||
{
|
||||
struct hash_entry *entry =
|
||||
_mesa_hash_table_search(device->app_events, app_event);
|
||||
if (entry)
|
||||
return (uint64_t) entry->data;
|
||||
|
||||
/* Allocate a new iid for the string */
|
||||
uint64_t iid = device->current_app_event_iid++;
|
||||
_mesa_hash_table_insert(device->app_events, app_event, (void*)(uintptr_t)iid);
|
||||
|
||||
/* Send the definition of iid/string to perfetto */
|
||||
{
|
||||
auto packet = tctx.NewTracePacket();
|
||||
auto interned_data = packet->set_interned_data();
|
||||
|
||||
auto desc = interned_data->add_gpu_specifications();
|
||||
desc->set_iid(iid);
|
||||
desc->set_name(app_event);
|
||||
}
|
||||
|
||||
return iid;
|
||||
}
|
||||
|
||||
static void
|
||||
end_event(struct intel_ds_queue *queue, uint64_t ts_ns,
|
||||
enum intel_ds_queue_stage stage_id,
|
||||
uint32_t submission_id, const void* payload = nullptr,
|
||||
uint32_t submission_id,
|
||||
const char *app_event,
|
||||
const void* payload = nullptr,
|
||||
trace_payload_as_extra_func payload_as_extra = nullptr)
|
||||
{
|
||||
struct intel_ds_device *device = queue->device;
|
||||
|
|
@ -310,6 +346,13 @@ end_event(struct intel_ds_queue *queue, uint64_t ts_ns,
|
|||
|
||||
uint64_t evt_id = device->event_id++;
|
||||
|
||||
/* If this is an application event, we might need to generate a new
|
||||
* stage_iid if not already seen. Otherwise, it's a driver event and we
|
||||
* have use the internal stage_iid.
|
||||
*/
|
||||
uint64_t stage_iid = app_event ?
|
||||
add_app_event(tctx, queue->device, app_event) : stage->stage_iid;
|
||||
|
||||
auto packet = tctx.NewTracePacket();
|
||||
|
||||
packet->set_timestamp(start_ns);
|
||||
|
|
@ -321,7 +364,7 @@ end_event(struct intel_ds_queue *queue, uint64_t ts_ns,
|
|||
event->set_gpu_id(queue->device->gpu_id);
|
||||
|
||||
event->set_hw_queue_iid(stage->queue_iid);
|
||||
event->set_stage_iid(stage->stage_iid);
|
||||
event->set_stage_iid(stage_iid);
|
||||
event->set_context(queue->device->iid);
|
||||
event->set_event_id(evt_id);
|
||||
event->set_duration(ts_ns - start_ns);
|
||||
|
|
@ -403,7 +446,7 @@ extern "C" {
|
|||
const struct intel_ds_flush_data *flush = \
|
||||
(const struct intel_ds_flush_data *) flush_data; \
|
||||
end_event(flush->queue, ts_ns, stage, flush->submission_id, \
|
||||
payload, \
|
||||
NULL, payload, \
|
||||
(trace_payload_as_extra_func) \
|
||||
&trace_payload_as_extra_intel_end_##event_name); \
|
||||
} \
|
||||
|
|
@ -430,6 +473,29 @@ CREATE_DUAL_EVENT_CALLBACK(compute, INTEL_DS_QUEUE_STAGE_COMPUTE)
|
|||
CREATE_DUAL_EVENT_CALLBACK(generate_draws, INTEL_DS_QUEUE_STAGE_GENERATE_DRAWS)
|
||||
CREATE_DUAL_EVENT_CALLBACK(trace_copy, INTEL_DS_QUEUE_STAGE_BLORP)
|
||||
|
||||
void
|
||||
intel_ds_begin_cmd_buffer_annotation(struct intel_ds_device *device,
|
||||
uint64_t ts_ns,
|
||||
const void *flush_data,
|
||||
const struct trace_intel_begin_cmd_buffer_annotation *payload)
|
||||
{
|
||||
const struct intel_ds_flush_data *flush =
|
||||
(const struct intel_ds_flush_data *) flush_data;
|
||||
begin_event(flush->queue, ts_ns, INTEL_DS_QUEUE_STAGE_CMD_BUFFER);
|
||||
}
|
||||
|
||||
void
|
||||
intel_ds_end_cmd_buffer_annotation(struct intel_ds_device *device,
|
||||
uint64_t ts_ns,
|
||||
const void *flush_data,
|
||||
const struct trace_intel_end_cmd_buffer_annotation *payload)
|
||||
{
|
||||
const struct intel_ds_flush_data *flush =
|
||||
(const struct intel_ds_flush_data *) flush_data;
|
||||
end_event(flush->queue, ts_ns, INTEL_DS_QUEUE_STAGE_CMD_BUFFER,
|
||||
flush->submission_id, payload->str, NULL, NULL);
|
||||
}
|
||||
|
||||
void
|
||||
intel_ds_begin_stall(struct intel_ds_device *device,
|
||||
uint64_t ts_ns,
|
||||
|
|
@ -450,7 +516,7 @@ intel_ds_end_stall(struct intel_ds_device *device,
|
|||
const struct intel_ds_flush_data *flush =
|
||||
(const struct intel_ds_flush_data *) flush_data;
|
||||
end_event(flush->queue, ts_ns, INTEL_DS_QUEUE_STAGE_STALL,
|
||||
flush->submission_id, payload,
|
||||
flush->submission_id, NULL, payload,
|
||||
(trace_payload_as_extra_func)custom_trace_payload_as_extra_end_stall);
|
||||
}
|
||||
|
||||
|
|
@ -510,10 +576,10 @@ intel_driver_ds_init_once(void)
|
|||
}
|
||||
|
||||
static once_flag intel_driver_ds_once_flag = ONCE_FLAG_INIT;
|
||||
static uint64_t iid = 1;
|
||||
|
||||
static uint64_t get_iid()
|
||||
{
|
||||
static uint64_t iid = 1;
|
||||
return iid++;
|
||||
}
|
||||
|
||||
|
|
@ -541,12 +607,18 @@ intel_ds_device_init(struct intel_ds_device *device,
|
|||
device->iid = get_iid();
|
||||
device->api = api;
|
||||
u_vector_init(&device->queues, 4, sizeof(struct intel_ds_queue));
|
||||
|
||||
/* Reserve iids for the application generated events */
|
||||
device->start_app_event_iids = 1ull << 32;
|
||||
device->app_events =
|
||||
_mesa_hash_table_create(NULL, _mesa_hash_string, _mesa_key_string_equal);
|
||||
}
|
||||
|
||||
void
|
||||
intel_ds_device_fini(struct intel_ds_device *device)
|
||||
{
|
||||
u_trace_context_fini(&device->trace_context);
|
||||
_mesa_hash_table_destroy(device->app_events, NULL);
|
||||
u_vector_finish(&device->queues);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -103,9 +103,24 @@ struct intel_ds_device {
|
|||
/* Unique perfetto identifier for the context */
|
||||
uint64_t iid;
|
||||
|
||||
/* Event ID generator */
|
||||
/* Event ID generator (manipulate only inside
|
||||
* IntelRenderpassDataSource::Trace)
|
||||
*/
|
||||
uint64_t event_id;
|
||||
|
||||
/* Start of unique IID for device generated events */
|
||||
uint64_t start_app_event_iids;
|
||||
|
||||
/* Last app event iid (manipulate only inside
|
||||
* IntelRenderpassDataSource::Trace)
|
||||
*/
|
||||
uint64_t current_app_event_iid;
|
||||
|
||||
/* Hash table of application generated events (string -> iid) (manipulate
|
||||
* only inside IntelRenderpassDataSource::Trace)
|
||||
*/
|
||||
struct hash_table *app_events;
|
||||
|
||||
struct u_trace_context trace_context;
|
||||
|
||||
/* List of intel_ds_queue */
|
||||
|
|
|
|||
|
|
@ -57,6 +57,14 @@ def define_tracepoints(args):
|
|||
tp_args=[Arg(type='uint8_t', var='level', c_format='%hhu'),],
|
||||
end_pipelined=False)
|
||||
|
||||
# Annotations for Cmd(Begin|End)DebugUtilsLabelEXT
|
||||
begin_end_tp('cmd_buffer_annotation',
|
||||
tp_args=[ArgStruct(type='unsigned', var='len'),
|
||||
ArgStruct(type='const char *', var='str'),],
|
||||
tp_struct=[Arg(type='uint8_t', name='dummy', var='0', c_format='%hhu'),
|
||||
Arg(type='char', name='str', var='str', c_format='%s', length_arg='len + 1', copy_func='strncpy'),],
|
||||
end_pipelined=True)
|
||||
|
||||
begin_end_tp('xfb',
|
||||
end_pipelined=False)
|
||||
|
||||
|
|
|
|||
|
|
@ -23,8 +23,11 @@
|
|||
|
||||
#include "anv_private.h"
|
||||
|
||||
#include "ds/intel_tracepoints.h"
|
||||
#include "perf/intel_perf.h"
|
||||
|
||||
#include "vulkan/runtime/vk_common_entrypoints.h"
|
||||
|
||||
static uint32_t
|
||||
command_buffers_count_utraces(struct anv_device *device,
|
||||
uint32_t cmd_buffer_count,
|
||||
|
|
@ -332,3 +335,30 @@ anv_pipe_flush_bit_to_ds_stall_flag(enum anv_pipe_bits bits)
|
|||
|
||||
return ret;
|
||||
}
|
||||
|
||||
void anv_CmdBeginDebugUtilsLabelEXT(
|
||||
VkCommandBuffer _commandBuffer,
|
||||
const VkDebugUtilsLabelEXT *pLabelInfo)
|
||||
{
|
||||
VK_FROM_HANDLE(anv_cmd_buffer, cmd_buffer, _commandBuffer);
|
||||
|
||||
vk_common_CmdBeginDebugUtilsLabelEXT(_commandBuffer, pLabelInfo);
|
||||
|
||||
trace_intel_begin_cmd_buffer_annotation(&cmd_buffer->trace);
|
||||
}
|
||||
|
||||
void anv_CmdEndDebugUtilsLabelEXT(VkCommandBuffer _commandBuffer)
|
||||
{
|
||||
VK_FROM_HANDLE(anv_cmd_buffer, cmd_buffer, _commandBuffer);
|
||||
|
||||
if (cmd_buffer->vk.labels.size > 0) {
|
||||
const VkDebugUtilsLabelEXT *label =
|
||||
util_dynarray_top_ptr(&cmd_buffer->vk.labels, VkDebugUtilsLabelEXT);
|
||||
|
||||
trace_intel_end_cmd_buffer_annotation(&cmd_buffer->trace,
|
||||
strlen(label->pLabelName),
|
||||
label->pLabelName);
|
||||
}
|
||||
|
||||
vk_common_CmdEndDebugUtilsLabelEXT(_commandBuffer);
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue