msm: kgsl: Make snapshot resilient to a non-existent ib1base
During snapshot, we may encounter an invalid IB1 base which is not found in the current rb. In that case, dump the entire ringbuffer from start to end and all the IBs in it to get a more complete picture of the failure. Change-Id: I4393c7de6f8f4890870fa6e2b5e69073dce922b7 Signed-off-by: Harshdeep Dhatt <hdhatt@codeaurora.org>
This commit is contained in:
parent
55946b6985
commit
b0d56ee1cb
1 changed files with 54 additions and 0 deletions
|
@ -244,6 +244,48 @@ static inline bool iommu_is_setstate_addr(struct kgsl_device *device,
|
|||
size);
|
||||
}
|
||||
|
||||
static void dump_all_ibs(struct kgsl_device *device,
|
||||
struct adreno_ringbuffer *rb,
|
||||
struct kgsl_snapshot *snapshot)
|
||||
{
|
||||
int index = 0;
|
||||
unsigned int *rbptr;
|
||||
struct adreno_device *adreno_dev = ADRENO_DEVICE(device);
|
||||
|
||||
rbptr = rb->buffer_desc.hostptr;
|
||||
|
||||
for (index = 0; index < KGSL_RB_DWORDS;) {
|
||||
|
||||
if (adreno_cmd_is_ib(adreno_dev, rbptr[index])) {
|
||||
uint64_t ibaddr;
|
||||
uint64_t ibsize;
|
||||
|
||||
if (ADRENO_LEGACY_PM4(adreno_dev)) {
|
||||
ibaddr = rbptr[index + 1];
|
||||
ibsize = rbptr[index + 2];
|
||||
index += 3;
|
||||
} else {
|
||||
ibaddr = rbptr[index + 2];
|
||||
ibaddr = ibaddr << 32 | rbptr[index + 1];
|
||||
ibsize = rbptr[index + 3];
|
||||
index += 4;
|
||||
}
|
||||
|
||||
/* Don't parse known global IBs */
|
||||
if (iommu_is_setstate_addr(device, ibaddr, ibsize))
|
||||
continue;
|
||||
|
||||
if (kgsl_gpuaddr_in_memdesc(&adreno_dev->pwron_fixup,
|
||||
ibaddr, ibsize))
|
||||
continue;
|
||||
|
||||
parse_ib(device, snapshot, snapshot->process, ibaddr,
|
||||
ibsize);
|
||||
} else
|
||||
index = index + 1;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* snapshot_rb_ibs() - Dump rb data and capture the IB's in the RB as well
|
||||
* @rb: The RB to dump
|
||||
|
@ -295,6 +337,18 @@ static void snapshot_rb_ibs(struct adreno_ringbuffer *rb,
|
|||
break;
|
||||
} while (index != rb->wptr);
|
||||
|
||||
/*
|
||||
* If the ib1 was not found, for example, if ib1base was restored
|
||||
* incorrectly after preemption, then simply dump the entire
|
||||
* ringbuffer along with all the IBs in the ringbuffer.
|
||||
*/
|
||||
|
||||
if (index == rb->wptr) {
|
||||
memcpy(data, rb->buffer_desc.hostptr, KGSL_RB_SIZE);
|
||||
dump_all_ibs(device, rb, snapshot);
|
||||
return;
|
||||
}
|
||||
|
||||
/*
|
||||
* index points at the last submitted IB. We can only trust that the
|
||||
* memory between the context switch and the hanging IB is valid, so
|
||||
|
|
Loading…
Add table
Reference in a new issue