Intel-XE Archive on lore.kernel.org
 help / color / mirror / Atom feed
From: sashiko-bot@kernel.org
To: "Riana Tauro" <riana.tauro@intel.com>, intel-xe@lists.freedesktop.org
Subject: Re: [PATCH v2 2/9] drm/xe/hw_error: Initialize hw_error_work per tile
Date: Mon, 26 Oct 2026 09:37:10 +0000	[thread overview]
Message-ID: <sashiko-outbox-184810@kernel.org> (raw)
In-Reply-To: <20261026060459.771448-13-riana.tauro@intel.com>

Thank you for your contribution! Sashiko AI review found 3 potential issue(s) to consider:
- [High] drm/xe/hw_error: devres teardown race in xe_hw_error_work_disable()
- [Medium] drm/xe/hw_error: unchecked devm_add_action_or_reset() in xe_hw_error_init()
- [Medium] drm/xe/hw_error: uninitialized delayed_work in xe_hw_error_work_disable()
--

commit eb5d3c525869285977a7b6ae0cced93702f4f61e
Author: Raag Jadav <raag.jadav@intel.com>

drm/xe/hw_error: Initialize hw_error_work per tile

This commit initializes tile->hw_error_work across all tiles in
xe_hw_error_init() rather than only on the root tile, and registers a
xe_hw_error_work_disable() callback with devm_add_action_or_reset() to
disable the delayed work on teardown.

> diff --git a/drivers/gpu/drm/xe/xe_hw_error.c b/drivers/gpu/drm/xe/xe_hw_error.c
> index 41ddd997478b8..f7799c3c08aac 100644
> --- a/drivers/gpu/drm/xe/xe_hw_error.c
> +++ b/drivers/gpu/drm/xe/xe_hw_error.c
> @@ -537,6 +537,23 @@ static void process_hw_errors(struct xe_device *xe)
>  	}
>  }
>  
> +/**
> + * xe_hw_error_work_disable - Disable hw error work
> + * @arg: xe device instance
> + *
> + * This function disables the delayed work for hardware error handling
> + * for all tiles.
> + */
> +void xe_hw_error_work_disable(void *arg)
> +{
> +	struct xe_device *xe = arg;
> +	struct xe_tile *tile;
> +	u8 id;
> +
> +	for_each_tile(tile, xe, id)
> +		disable_delayed_work_sync(&tile->hw_error_work);
> +}

[Severity: Medium]
Should xe_hw_error_work_disable() also check !IS_DGFX(xe) || IS_SRIOV_VF(xe)
before calling disable_delayed_work_sync()?

In xe_hw_error_init(), tile->hw_error_work is only initialized via
INIT_DELAYED_WORK() when IS_DGFX(xe) && !IS_SRIOV_VF(xe):

drivers/gpu/drm/xe/xe_hw_error.c:xe_hw_error_init()
	if (!IS_DGFX(xe) || IS_SRIOV_VF(xe))
		return;

	for_each_tile(tile, xe, id)
		INIT_DELAYED_WORK(&tile->hw_error_work, hw_error_work);

However, xe_hw_error_work_disable() is exported in drivers/gpu/drm/xe/xe_hw_error.h
without that guard. In the commit "drm/xe/xe_ras: Disable hw error worker when
AER handling is in progress", xe_pci_error_detected() in
drivers/gpu/drm/xe/xe_pci_error.c calls xe_hw_error_work_disable(xe) whenever
XE_DEVICE_WA(xe, 14028434957) && is_aer_internal_error(pdev) is true.

Because Crescent Island (cri_desc) sets .has_sriov = true and enables
workaround 14028434957 at the platform level in xe_device_probe_early() before
xe_sriov_probe_early(), an SR-IOV VF on Crescent Island has
XE_DEVICE_WA(xe, 14028434957) set while tile->hw_error_work remains
uninitialized.

If pcie_do_recovery() invokes xe_pci_error_detected() on the VF, won't
xe_hw_error_work_disable() pass an uninitialized tile->hw_error_work (with
work->func == NULL) to disable_delayed_work_sync() -> __cancel_work_sync() ->
__flush_work(), triggering WARN_ON(!work->func) in kernel/workqueue.c?

> +
>  /**
>   * xe_hw_error_init - Initialize hw errors
>   * @xe: xe device instance
> @@ -546,12 +563,15 @@ static void process_hw_errors(struct xe_device *xe)
>   */
>  void xe_hw_error_init(struct xe_device *xe)
>  {
> -	struct xe_tile *tile = xe_device_get_root_tile(xe);
> +	struct xe_tile *tile;
> +	u8 id;
>  
>  	if (!IS_DGFX(xe) || IS_SRIOV_VF(xe))
>  		return;
>  
> -	INIT_DELAYED_WORK(&tile->hw_error_work, hw_error_work);
> +	for_each_tile(tile, xe, id)
> +		INIT_DELAYED_WORK(&tile->hw_error_work, hw_error_work);
>  
>  	process_hw_errors(xe);
> +	devm_add_action_or_reset(xe->drm.dev, xe_hw_error_work_disable, xe);
>  }

[Severity: High]
Can registering xe_hw_error_work_disable() via devm_add_action_or_reset() race
with an in-flight hw_error_work() callback during devres teardown and leave
behind dangling devres nodes and sysfs attributes after struct xe_device is
freed?

When devres teardown runs during probe failure unwind, driver unbind
(__device_release_driver() -> xe_pci_remove() -> device_unbind_cleanup() ->
devres_release_all()), or PCI slot reset (xe_pci_error_slot_reset() ->
devres_release_group()), drivers/base/devres.c moves all queued nodes from
dev->devres_head onto a local todo list before running any release callbacks:

drivers/base/devres.c:devres_release_all()
	spin_lock_irqsave(&dev->devres_lock, flags);
	cnt = remove_nodes(dev, dev->devres_head.next, &dev->devres_head, &todo);
	spin_unlock_irqrestore(&dev->devres_lock, flags);

	release_nodes(dev, &todo);

If tile->hw_error_work was scheduled by process_hw_errors() or an interrupt and
begins executing before release_nodes() invokes xe_hw_error_work_disable()
(including while xe_hw_error_work_disable() is waiting inside
disable_delayed_work_sync(&tile->hw_error_work) for the running worker to
finish), the worker executes:

drivers/gpu/drm/xe/xe_hw_error.c:hw_error_work()
  -> xe_survivability_mode_runtime_enable(xe)
    -> create_survivability_sysfs(pdev)

Inside drivers/gpu/drm/xe/xe_survivability_mode.c:create_survivability_sysfs(),
the worker creates sysfs files and registers new devres actions on
xe->drm.dev:

	ret = device_create_file(dev, &dev_attr_survivability_mode);
	if (ret)
		goto failed;

	ret = devm_add_action_or_reset(xe->drm.dev,
				       xe_survivability_mode_fini, xe);
	if (ret)
		goto failed;

	if (needs_info) {
		ret = devm_device_add_group(dev, &survivability_info_group);
		if (ret)
			goto failed;
	}

Because remove_nodes() already drained dev->devres_head into todo before
release_nodes() started, those newly registered devres actions are appended to
dev->devres_head and are not run by the active release_nodes(dev, &todo) pass,
while devm_drm_dev_init_release on todo frees struct xe_device *xe.

Wouldn't this leave the survivability_mode and survivability_info sysfs files
exposed on pdev->dev after xe is freed and drvdata is cleared (leading to a
NULL pointer dereference or use-after-free in survivability_mode_show() and
survivability_info_show()), leave xe_survivability_mode_fini(xe) queued on
dev->devres_head with a dangling xe pointer, and cause subsequent driver
re-probing in really_probe() to fail with -EBUSY because dev->devres_head is
non-empty?

Additionally, what happens in xe_hw_error_init() if devm_add_action_or_reset()
fails with -ENOMEM?

include/linux/device/devres.h:__devm_add_action_or_reset()
	ret = __devm_add_action(dev, action, data, name);
	if (ret)
		action(data);

	return ret;

On allocation failure, __devm_add_action_or_reset() immediately runs
xe_hw_error_work_disable(xe), which cancels any delayed work just scheduled by
process_hw_errors(xe) (after the hardware error registers and GFX_MSTR_IRQ
have already been cleared) and permanently disables tile->hw_error_work across
all tiles via WORK_CANCEL_DISABLE. Because xe_hw_error_init() returns void and
ignores the return value, xe_irq_install() and xe_device_probe() continue probing
with tile->hw_error_work permanently disabled for the lifetime of the device.
Should xe_hw_error_init() propagate the error to xe_irq_install()?

-- 
Sashiko AI review · https://sashiko.dev/#/patchset/20261026060459.771448-11-riana.tauro@intel.com?part=2

  reply	other threads:[~2026-10-26  9:37 UTC|newest]

Thread overview: 42+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2026-10-26  6:04 [PATCH v2 0/9] Handle non-fatal errors routed via IRQ Riana Tauro
2026-10-26  6:05 ` [PATCH v2 1/9] drm/xe/hw_error: Reuse CSC worker for generic error handling Riana Tauro
2026-10-27 13:01   ` Mallesh, Koujalagi
2026-10-29  8:07     ` Tauro, Riana
2026-10-26  6:05 ` [PATCH v2 2/9] drm/xe/hw_error: Initialize hw_error_work per tile Riana Tauro
2026-10-26  9:37   ` sashiko-bot [this message]
2026-10-27 14:51   ` Mallesh, Koujalagi
2026-10-29  8:11     ` Tauro, Riana
2026-10-28 16:07   ` Andi Shyti
2026-10-26  6:05 ` [PATCH v2 3/9] drm/xe: Add wa_14028434957 to Graphics Version 35.11 Riana Tauro
2026-10-28  6:16   ` Mallesh, Koujalagi
2026-10-29  8:12     ` Tauro, Riana
2026-10-28 14:19   ` Gustavo Sousa
2026-10-29  8:32     ` Tauro, Riana
2026-10-26  6:05 ` [PATCH v2 4/9] drm/xe/xe_hw_error: Handle non-fatal errors routed via direct IRQ Riana Tauro
2026-10-26 10:09   ` sashiko-bot
2026-10-26 10:49   ` Upadhyay, Tejas
2026-10-26 14:08     ` Tauro, Riana
2026-10-29  6:36       ` Mallesh, Koujalagi
2026-10-29  8:17         ` Tauro, Riana
2026-10-28 16:15   ` Andi Shyti
2026-10-29  8:23     ` Tauro, Riana
2026-10-28 16:17   ` Andi Shyti
2026-10-29  8:20     ` Tauro, Riana
2026-10-26  6:05 ` [PATCH v2 5/9] drm/xe/ras: Treat non-fatal PCIe errors as recovered Riana Tauro
2026-10-28  9:24   ` Mallesh, Koujalagi
2026-10-29  8:27     ` Tauro, Riana
2026-10-26  6:05 ` [PATCH v2 6/9] drm/xe/pci: Add upstream switch port lookup helper Riana Tauro
2026-10-28  9:45   ` Mallesh, Koujalagi
2026-10-28 16:19   ` Andi Shyti
2026-10-29  8:28     ` Tauro, Riana
2026-10-26  6:05 ` [PATCH v2 7/9] drm/xe/xe_ras: Disable hw error worker when AER handling is in progress Riana Tauro
2026-10-26 10:32   ` sashiko-bot
2026-10-26  6:05 ` [PATCH v2 8/9] drm/xe/xe_ras: Trigger SBR for all device errors Riana Tauro
2026-10-28 16:25   ` Andi Shyti
2026-10-29  5:18   ` Mallesh, Koujalagi
2026-10-26  6:05 ` [PATCH v2 9/9] drm/xe/ras: Skip double-bit ECC page offlining on AER path Riana Tauro
2026-10-28 16:26   ` Andi Shyti
2026-10-29  5:25   ` Mallesh, Koujalagi
2026-10-26  6:30 ` ✓ CI.KUnit: success for Handle non-fatal errors routed via IRQ (rev2) Patchwork
2026-10-26  7:05 ` ✓ Xe.CI.BAT: " Patchwork
2026-10-26  8:55 ` ✗ Xe.CI.FULL: failure " Patchwork

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=sashiko-outbox-184810@kernel.org \
    --to=sashiko-bot@kernel.org \
    --cc=intel-xe@lists.freedesktop.org \
    --cc=riana.tauro@intel.com \
    --cc=sashiko-reviews@lists.linux.dev \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox