From: Matthew Auld <matthew.auld@intel.com>
To: "Thomas Hellström" <thomas.hellstrom@linux.intel.com>,
intel-xe@lists.freedesktop.org
Cc: Matthew Brost <matthew.brost@intel.com>,
Dave Airlie <airlied@redhat.com>,
Rodrigo Vivi <rodrigo.vivi@intel.com>,
stable@vger.kernel.org
Subject: Re: [PATCH] drm/xe/dma-buf: Validate BOs on export to charge the exporter
Date: Wed, 11 Nov 2026 12:18:45 +0000 [thread overview]
Message-ID: <fc3a08df-bc2e-47bf-a0f8-a7e284e5f3c2@intel.com> (raw)
In-Reply-To: <20261111100929.2228-1-thomas.hellstrom@linux.intel.com>
On 11/11/2026 10:09, Thomas Hellström wrote:
> xe_gem_prime_export() calls ttm_bo_setup_export() to make sure the
> exporter is charged for the memory backing an exported BO. However,
> that only populates a TTM_PL_SYSTEM tt. A BO that has been evicted, or
> that has deferred backing, will instead get its memory allocated when
> the importer maps it. For p2p imports this happens through
> xe_bo_validate() in xe_dma_buf_map(), so the importer, not the
> exporter, is charged for the allocation.
>
> Call xe_bo_validate() at export time instead, so that the BO is moved
> into its preferred placement and the exporter is charged.
Is it maybe also worth mentioning somewhere the unreclaimable pages
angle? I could be mistaken here, but I think that was maybe also the
issue I saw in a workload. For example:
1. Create say 100G VRAM buffer. Use DEFERRED. This leaves lingering tt
structure.
2. Validate it on native side. This is now resident in VRAM. But still
has lingering tt.
3. Export it. This now populates 100G worth of TT pages due to lingering
tt. But we now have a populated VRAM buffer which is also populated with
100G TT pages. That 100G TT pages is not reclaimable and is hidden from
shrinker since this still just looks like normal VRAM buffer.
>
> Do the purgeable checks and the validation in the same
> xe_validation_guard() transaction, to avoid locking the BO twice.
>
> The commit message and code was drafted using LLM.
>
> Link: https://patchwork.freedesktop.org/patch/747480/?series=172524&rev=1
> Fixes: 91494dee1091 ("xe: populate buffers before exporting them.")
> Cc: Matthew Brost <matthew.brost@intel.com>
> Cc: Matthew Auld <matthew.auld@intel.com>
> Cc: Dave Airlie <airlied@redhat.com>
> Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
> Cc: intel-xe@lists.freedesktop.org
> Cc: <stable@vger.kernel.org> # v6.18+
> Signed-off-by: Thomas Hellström <thomas.hellstrom@linux.intel.com>
Reviewed-by: Matthew Auld <matthew.auld@intel.com>
> ---
> drivers/gpu/drm/xe/xe_dma_buf.c | 76 +++++++++++++++++----------------
> 1 file changed, 39 insertions(+), 37 deletions(-)
>
> diff --git a/drivers/gpu/drm/xe/xe_dma_buf.c b/drivers/gpu/drm/xe/xe_dma_buf.c
> index 5bf13dc4b61d..90c9b90de552 100644
> --- a/drivers/gpu/drm/xe/xe_dma_buf.c
> +++ b/drivers/gpu/drm/xe/xe_dma_buf.c
> @@ -263,60 +263,62 @@ struct drm_gem_object *xe_dma_buf_to_gem(struct drm_device *dev,
> struct dma_buf *xe_gem_prime_export(struct drm_gem_object *obj, int flags)
> {
> struct xe_bo *bo = gem_to_xe_bo(obj);
> + struct xe_validation_ctx ctx;
> + struct drm_exec exec;
> struct dma_buf *buf;
> - struct ttm_operation_ctx ctx = {
> - .interruptible = true,
> - .no_wait_gpu = true,
> - /* We opt to avoid OOM on system pages allocations */
> - .gfp_retry_mayfail = true,
> - .allow_res_evict = false,
> - };
> - int ret;
> + int ret = 0;
>
> if (bo->vm)
> return ERR_PTR(-EPERM);
>
> - /*
> - * Reject exporting purgeable BOs. DONTNEED BOs can be purged
> - * at any time, making the exported dma-buf unusable. Purged BOs
> - * have no backing store and are permanently invalid.
> - */
> - ret = xe_bo_lock(bo, true);
> - if (ret)
> - return ERR_PTR(ret);
> + xe_validation_guard(&ctx, &xe_bo_device(bo)->val, &exec,
> + (struct xe_val_flags) {.interruptible = true}, ret) {
> + ret = drm_exec_lock_obj(&exec, &bo->ttm.base);
> + drm_exec_retry_on_contention(&exec);
> + if (ret)
> + break;
>
> - if (xe_bo_madv_is_dontneed(bo)) {
> - ret = -EBUSY;
> - goto out_unlock;
> - }
> + /*
> + * Reject exporting purgeable BOs. DONTNEED BOs can be purged
> + * at any time, making the exported dma-buf unusable. Purged BOs
> + * have no backing store and are permanently invalid.
> + */
> + if (xe_bo_madv_is_dontneed(bo)) {
> + ret = -EBUSY;
> + break;
> + }
>
> - if (xe_bo_is_purged(bo)) {
> - ret = -EINVAL;
> - goto out_unlock;
> - }
> + if (xe_bo_is_purged(bo)) {
> + ret = -EINVAL;
> + break;
> + }
>
> - xe_bo_willneed_get_locked(bo);
> - xe_bo_unlock(bo);
> + /*
> + * Make sure the BO is backed in its preferred placement so that
> + * the exporter, rather than the importer, is charged for the
> + * memory allocation.
> + */
> + ret = xe_bo_validate(bo, NULL, false, &exec);
> + drm_exec_retry_on_contention(&exec);
> + xe_validation_retry_on_oom(&ctx, &ret);
> + if (ret)
> + break;
>
> - ret = ttm_bo_setup_export(&bo->ttm, &ctx);
> + xe_bo_willneed_get_locked(bo);
> + }
> if (ret)
> - goto out_put;
> + return ERR_PTR(ret);
>
> buf = drm_gem_prime_export(obj, flags);
> if (IS_ERR(buf)) {
> - ret = PTR_ERR(buf);
> - goto out_put;
> + xe_bo_lock(bo, false);
> + xe_bo_willneed_put_locked(bo);
> + xe_bo_unlock(bo);
> + return buf;
> }
>
> buf->ops = &xe_dmabuf_ops;
> return buf;
> -
> -out_put:
> - xe_bo_lock(bo, false);
> - xe_bo_willneed_put_locked(bo);
> -out_unlock:
> - xe_bo_unlock(bo);
> - return ERR_PTR(ret);
> }
>
> static struct drm_gem_object *
next prev parent reply other threads:[~2026-11-11 12:18 UTC|newest]
Thread overview: 3+ messages / expand[flat|nested] mbox.gz Atom feed top
2026-11-11 10:09 [PATCH] drm/xe/dma-buf: Validate BOs on export to charge the exporter Thomas Hellström
2026-11-11 12:18 ` Matthew Auld [this message]
2026-11-11 12:22 ` Thomas Hellström
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=fc3a08df-bc2e-47bf-a0f8-a7e284e5f3c2@intel.com \
--to=matthew.auld@intel.com \
--cc=airlied@redhat.com \
--cc=intel-xe@lists.freedesktop.org \
--cc=matthew.brost@intel.com \
--cc=rodrigo.vivi@intel.com \
--cc=stable@vger.kernel.org \
--cc=thomas.hellstrom@linux.intel.com \
/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