[PATCH umr] Add UVD/VCN IB detection to pm4 stream decoder

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



Signed-off-by: Tom St Denis <tom.stdenis at amd.com>
---
 src/lib/umr_read_pm4_stream.c | 49 ++++++++++++++++++++++++++++++++++++++++++-
 1 file changed, 48 insertions(+), 1 deletion(-)

diff --git a/src/lib/umr_read_pm4_stream.c b/src/lib/umr_read_pm4_stream.c
index b17f232a5381..9da804fc6793 100644
--- a/src/lib/umr_read_pm4_stream.c
+++ b/src/lib/umr_read_pm4_stream.c
@@ -161,6 +161,14 @@ void umr_free_pm4_stream(struct umr_pm4_stream *stream)
 struct umr_pm4_stream *umr_pm4_decode_stream(struct umr_asic *asic, int vmid, uint32_t *stream, uint32_t nwords)
 {
 	struct umr_pm4_stream *ops, *ps;
+	struct {
+		int n;
+		uint32_t
+			size,
+			vmid;
+		uint64_t
+			addr;
+	} uvd_ib;
 
 	ps = ops = calloc(1, sizeof *ops);
 	if (!ps) {
@@ -168,6 +176,8 @@ struct umr_pm4_stream *umr_pm4_decode_stream(struct umr_asic *asic, int vmid, ui
 		return NULL;
 	}
 
+	memset(&uvd_ib, 0, sizeof uvd_ib);
+
 	while (nwords) {
 		// fetch basics out of header
 		ps->pkttype = *stream >> 30;
@@ -184,8 +194,45 @@ struct umr_pm4_stream *umr_pm4_decode_stream(struct umr_asic *asic, int vmid, ui
 		memcpy(ps->words, &stream[1], ps->n_words * sizeof(stream[0]));
 
 		// decode specific packets
-		if (ps->pkttype == 3)
+		if (ps->pkttype == 3) {
 			parse_pm4(asic, vmid, ps);
+		} else {
+			char *name;
+			name = umr_reg_name(asic, ps->pkt0off);
+
+			// look for UVD IBs
+			if (strstr(name, "mmUVD_LMI_RBC_IB_VMID")) {
+				uvd_ib.vmid = ps->words[0] | ((asic->family <= FAMILY_VI) ? 0 : UMR_MM_HUB);
+				uvd_ib.n |= 1;
+			} else if (strstr(name, "mmUVD_LMI_RBC_IB_64BIT_BAR_LOW")) {
+				uvd_ib.addr |= ps->words[0];
+				uvd_ib.n |= 2;
+			} else if (strstr(name, "mmUVD_LMI_RBC_IB_64BIT_BAR_HIGH")) {
+				uvd_ib.addr |= (uint64_t)ps->words[0] << 32;
+				uvd_ib.n |= 4;
+			} else if (strstr(name, "mmUVD_RBC_IB_SIZE")) {
+				uvd_ib.size = ps->words[0] * 4;
+				uvd_ib.n |= 8;
+			}
+
+			// if we have everything but the VMID assume vmid 0
+			if (uvd_ib.n == (2|4|8)) {
+				uvd_ib.vmid = 0;
+				uvd_ib.n = 15;
+			}
+
+			// we have everything we need to point to an IB
+			if (uvd_ib.n == 15) {
+				void *buf;
+				buf = calloc(1, uvd_ib.size);
+				if (umr_read_vram(asic, uvd_ib.vmid, uvd_ib.addr, uvd_ib.size, buf) < 0)
+					fprintf(stderr, "[ERROR]: Could not read IB at %u:0x%llx\n", (unsigned)uvd_ib.vmid, (unsigned long long)uvd_ib.addr);
+				else
+					ps->ib = umr_pm4_decode_stream(asic, uvd_ib.vmid, buf, uvd_ib.size / 4);
+				free(buf);
+				memset(&uvd_ib, 0, sizeof uvd_ib);
+			}
+		}
 
 		// advance stream
 		nwords -= 1 + ps->n_words;
-- 
2.14.4



[Index of Archives]     [Linux USB Devel]     [Linux Audio Users]     [Yosemite News]     [Linux Kernel]     [Linux SCSI]

  Powered by Linux