intel/decoder: Print more information in shader's headline
Some checks are pending
macOS-CI / macOS-CI (dri) (push) Waiting to run
macOS-CI / macOS-CI (xlib) (push) Waiting to run

Print out the kernel start pointer (KSP) and the hash of
referenced shader in its headline. This saves some search
in GPU hang dumps,  base on the work of

72bc74f0be and
fd11e4b4d3

An example from a decoded GPU hang dump:

0xeffeffefe19c:  0x10000002:  MI_STORE_DATA_IMM
0xeffeffefe19c:  0x10000002 : Dword 0
    DWord Length: 2
    Force Write Completion Check : false
    Store Qword: 0
    Use Global GTT: false
0xeffeffefe1a0:  0xffe000c0 : Dword 1
    Core Mode Enable: 0
0xeffeffefe1a4:  0x0000effe : Dword 2
    Address: 0xeffeffe000c0
0xeffeffefe1a8:  0x82f94895 : Dword 3 <--- No need to search here
0xeffeffefe1ac:  0x72080025 : Dword 4
    Immediate Data: 2197375125
0xeffeffefe1ac:  0x72080025:  COMPUTE_WALKER
0xeffeffefe1ac:  0x72080025 : Dword 0
...
    body: <struct COMPUTE_WALKER_BODY>
...
    Interface Descriptor: <struct INTERFACE_DESCRIPTOR_DATA>
...
0xeffeffefe1f4:  0x00001f40 : Dword 0
    Kernel Start Pointer: 0x00001f40 <--- No need to search here
...
0xeffeffefe244:  0x00000000 : Dword 37
    Inline Data[7]: 0

Referenced compute shader (ksp: 0x1f40 hash: 0x7208002582f94895): <- ksp & hash printed here
send(1)         g3UD            g2UD            nullUD ...
                ugm MsgDesc: ( load, a64, d32, V64, ...
add(1)          g16<2>UD        g2<0,1,0>UD     0x00000100UD

Note: Shader hash output rquires 'ANV_DEBUG=shader-hash' when running
the workload.

Signed-off-by: Jianxun Zhang <jianxun.zhang@intel.com>
Reviewed-by: Lionel Landwerlin <lionel.g.landwerlin@intel.com>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/40418>
This commit is contained in:
Jianxun Zhang 2026-03-17 12:42:13 -07:00 committed by Marge Bot
parent e74b92b3da
commit 2a681c4f8b
3 changed files with 51 additions and 1 deletions

View file

@ -1231,6 +1231,27 @@ decode_load_register_imm(struct intel_batch_decode_ctx *ctx, const uint32_t *p)
}
}
static void
decode_store_data_imm(struct intel_batch_decode_ctx *ctx, const uint32_t *p)
{
/* Record a _potential_ shader hash. (We won't know if the data is a hash
* from a dummy MI_STORE_DATA_IMM or a real case of the same command until
* the next command gets parsed.)
*
* Since shader hash injection is supported, a hash was 32 bit and then
* is extended to 64 bit. There is a chance that a decoder supporting 64
* bit hash is used to parse an older dump generated with 32 bit hash. We
* have to look into the dword length field (bits 9:0 of BG 0) to
* determine the width of the hash.
*
* So far, dword 3 and 4 of MI_STORE_DATA_IMM are defined same way among
* all GFX generations, so we simply use the hard-coded indexes to get
* their values.
*/
uint64_t hash_hi = (*p & 0x3ff) == 2 ? 0 : p[4];
ctx->shader_hash.hash = (hash_hi << 32) + p[3];
}
static void
disasm_program_from_group(struct intel_batch_decode_ctx *ctx,
struct intel_group *strct, const void *map,
@ -1515,6 +1536,7 @@ struct custom_decoder custom_decoders[] = {
{ "3DSTATE_SCISSOR_STATE_POINTERS", decode_3dstate_scissor_state_pointers },
{ "3DSTATE_SLICE_TABLE_STATE_POINTERS", decode_3dstate_slice_table_state_pointers },
{ "MI_LOAD_REGISTER_IMM", decode_load_register_imm },
{ "MI_STORE_DATA_IMM", decode_store_data_imm },
{ "3DSTATE_PIPELINED_POINTERS", decode_pipelined_pointers },
{ "3DSTATE_CPS_POINTERS", decode_cps_pointers },
{ "CONSTANT_BUFFER", decode_gfx4_constant_buffer },
@ -1745,6 +1767,8 @@ intel_print_batch(struct intel_batch_decode_ctx *ctx,
} else if (strcmp(inst->name, "MI_BATCH_BUFFER_END") == 0) {
break;
}
ctx->shader_hash.last_inst = inst;
}
ctx->n_batch_buffer_start--;

View file

@ -21,7 +21,25 @@ ctx_disassemble_program_gen(struct intel_batch_decode_ctx *ctx,
if (!bo.map)
return;
fprintf(ctx->fp, "\nReferenced %s:\n", name);
fprintf(ctx->fp, "\nReferenced %s (ksp: 0x%" PRIx32, name, ksp);
if (ctx->shader_hash.last_inst &&
!strcmp(ctx->shader_hash.last_inst->name, "MI_STORE_DATA_IMM")) {
/* We only consider a recorded hash valid when the previously parsed
* instruction is the token.
*/
fprintf(ctx->fp, " hash: 0x%" PRIx64 "): \n", ctx->shader_hash.hash);
/* FIXME: Only the hash of the first shader is available now.
*
* For a targeted shader submission command which can have more than
* one shader, the dummy MI_STORE_DATA_IMM token instruction only
* contains the hash of the first shader. In this case, we invalidate
* the last instruction here so that the following shaders won't be
* printed out with the hash of the first.
*/
ctx->shader_hash.last_inst = NULL;
} else {
fprintf(ctx->fp, "):\n");
}
const int size = gen_find_shader_size(&ctx->devinfo, bo.map, 0, bo.size);
if (size > 0) {

View file

@ -255,6 +255,13 @@ struct intel_batch_decode_bo {
const void *map;
};
struct intel_batch_decode_hash {
/* Record the previous parsed command for cross-instruction tracking.
*/
const struct intel_group *last_inst;
uint64_t hash;
};
struct intel_batch_decode_ctx {
/**
* Return information about the buffer containing the given address.
@ -297,6 +304,7 @@ struct intel_batch_decode_ctx {
struct hash_table *commands;
struct hash_table *filters;
struct hash_table *stats;
struct intel_batch_decode_hash shader_hash;
void (*disassemble_program)(struct intel_batch_decode_ctx *ctx,
uint32_t ksp,