From: Vinay Belgaumkar Date: Wed, 4 Feb 2026 19:03:14 +0000 (-0800) Subject: drm/xe: Add forcewake status to powergate_info X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=91be6115e4677ad69bf8186988972b319d32ae61;p=thirdparty%2Flinux.git drm/xe: Add forcewake status to powergate_info Dump forcewake status and ref counts for all domains as part of this debugfs. This is the sample output from gt1- $ cat /sys/kernel/debug/dri//0/gt1/powergate_info Media Power Gating Enabled: yes Media Slice0 Power Gate Status: down GSC Power Gate Status: down GT.ref_count=0, GT.forcewake=0x10000 VDBox0.ref_count=0, VDBox0.forcewake=0x10000 VEBox0.ref_count=0, VEBox0.forcewake=0x10000 GSC.ref_count=0, GSC.forcewake=0x10000 v2: Fix checkpatch issues Reviewed-by: Badal Nilawar Signed-off-by: Vinay Belgaumkar Link: https://patch.msgid.link/20260204190314.2904009-3-vinay.belgaumkar@intel.com --- diff --git a/drivers/gpu/drm/xe/xe_force_wake.c b/drivers/gpu/drm/xe/xe_force_wake.c index 76e054f314ee1..197e2197bd0a3 100644 --- a/drivers/gpu/drm/xe/xe_force_wake.c +++ b/drivers/gpu/drm/xe/xe_force_wake.c @@ -148,12 +148,6 @@ static int domain_sleep_wait(struct xe_gt *gt, return __domain_wait(gt, domain, false); } -#define for_each_fw_domain_masked(domain__, mask__, fw__, tmp__) \ - for (tmp__ = (mask__); tmp__; tmp__ &= ~BIT(ffs(tmp__) - 1)) \ - for_each_if((domain__ = ((fw__)->domains + \ - (ffs(tmp__) - 1))) && \ - domain__->reg_ctl.addr) - /** * xe_force_wake_get() : Increase the domain refcount * @fw: struct xe_force_wake @@ -266,3 +260,43 @@ void xe_force_wake_put(struct xe_force_wake *fw, unsigned int fw_ref) xe_gt_WARN(gt, ack_fail, "Forcewake domain%s %#x failed to acknowledge sleep request\n", str_plural(hweight_long(ack_fail)), ack_fail); } + +const char *xe_force_wake_domain_to_str(enum xe_force_wake_domain_id id) +{ + switch (id) { + case XE_FW_DOMAIN_ID_GT: + return "GT"; + case XE_FW_DOMAIN_ID_RENDER: + return "Render"; + case XE_FW_DOMAIN_ID_MEDIA: + return "Media"; + case XE_FW_DOMAIN_ID_MEDIA_VDBOX0: + return "VDBox0"; + case XE_FW_DOMAIN_ID_MEDIA_VDBOX1: + return "VDBox1"; + case XE_FW_DOMAIN_ID_MEDIA_VDBOX2: + return "VDBox2"; + case XE_FW_DOMAIN_ID_MEDIA_VDBOX3: + return "VDBox3"; + case XE_FW_DOMAIN_ID_MEDIA_VDBOX4: + return "VDBox4"; + case XE_FW_DOMAIN_ID_MEDIA_VDBOX5: + return "VDBox5"; + case XE_FW_DOMAIN_ID_MEDIA_VDBOX6: + return "VDBox6"; + case XE_FW_DOMAIN_ID_MEDIA_VDBOX7: + return "VDBox7"; + case XE_FW_DOMAIN_ID_MEDIA_VEBOX0: + return "VEBox0"; + case XE_FW_DOMAIN_ID_MEDIA_VEBOX1: + return "VEBox1"; + case XE_FW_DOMAIN_ID_MEDIA_VEBOX2: + return "VEBox2"; + case XE_FW_DOMAIN_ID_MEDIA_VEBOX3: + return "VEBox3"; + case XE_FW_DOMAIN_ID_GSC: + return "GSC"; + default: + return "Unknown"; + } +} diff --git a/drivers/gpu/drm/xe/xe_force_wake.h b/drivers/gpu/drm/xe/xe_force_wake.h index 1e2198f6a0078..e2721f205d6c5 100644 --- a/drivers/gpu/drm/xe/xe_force_wake.h +++ b/drivers/gpu/drm/xe/xe_force_wake.h @@ -19,6 +19,17 @@ unsigned int __must_check xe_force_wake_get(struct xe_force_wake *fw, enum xe_force_wake_domains domains); void xe_force_wake_put(struct xe_force_wake *fw, unsigned int fw_ref); +const char *xe_force_wake_domain_to_str(enum xe_force_wake_domain_id id); + +#define for_each_fw_domain_masked(domain__, mask__, fw__, tmp__) \ + for (tmp__ = (mask__); tmp__; tmp__ &= ~BIT(ffs(tmp__) - 1)) \ + for_each_if(((domain__) = ((fw__)->domains + \ + (ffs(tmp__) - 1))) && \ + (domain__)->reg_ctl.addr) + +#define for_each_fw_domain(domain__, fw__, tmp__) \ + for_each_fw_domain_masked((domain__), (fw__)->initialized_domains, (fw__), (tmp__)) + static inline int xe_force_wake_ref(struct xe_force_wake *fw, enum xe_force_wake_domains domain) diff --git a/drivers/gpu/drm/xe/xe_gt_idle.c b/drivers/gpu/drm/xe/xe_gt_idle.c index 94d3403ec11ed..4a2d9edb6a4c0 100644 --- a/drivers/gpu/drm/xe/xe_gt_idle.c +++ b/drivers/gpu/drm/xe/xe_gt_idle.c @@ -168,6 +168,24 @@ void xe_gt_idle_disable_pg(struct xe_gt *gt) xe_mmio_write32(>->mmio, POWERGATE_ENABLE, gtidle->powergate_enable); } +static void force_wake_domains_show(struct xe_gt *gt, struct drm_printer *p) +{ + struct xe_force_wake_domain *domain; + struct xe_force_wake *fw = gt_to_fw(gt); + unsigned int tmp; + unsigned long flags; + + spin_lock_irqsave(&fw->lock, flags); + for_each_fw_domain(domain, fw, tmp) { + drm_printf(p, "%s.ref_count=%u, %s.fwake=0x%x\n", + xe_force_wake_domain_to_str(domain->id), + READ_ONCE(domain->ref), + xe_force_wake_domain_to_str(domain->id), + xe_mmio_read32(>->mmio, domain->reg_ctl)); + } + spin_unlock_irqrestore(&fw->lock, flags); +} + /** * xe_gt_idle_pg_print - Xe powergating info * @gt: GT object @@ -259,6 +277,8 @@ int xe_gt_idle_pg_print(struct xe_gt *gt, struct drm_printer *p) str_up_down(pg_status & GSC_AWAKE_STATUS)); } + force_wake_domains_show(gt, p); + return 0; }