On 9/1/2026 9:23 AM, Matthew Brost wrote:
On Thu, Aug 27, 2026 at 05:02:43PM +0800, Huang, Honglei wrote:
On 8/27/2026 3:30 PM, Matthew Brost wrote:
On Thu, Aug 27, 2026 at 03:14:45PM +0800, Honglei Huang wrote:
Make the HMM fault step of drm_gpusvm_get_pages(), including its -EBUSY
retry loop, into a helper drm_gpusvm_hmm_fault(). The existing logic of
the public drm_gpusvm_get_pages() is not changed, only relocated, so
there is no functional change. Keeping the retry loop in common code
also means drivers never have to open-code their own fault/retry loop.
A single fault can later be shared by several drm_gpusvm_pages instances
that mirror the same CPU range. This prepares get_pages() to split the
shared MM-level fault from the per-device DMA mapping. No functional
change intended.
I think you might want to just wait on this until Sunday for this
series. I think this patch [1] is in the core MM tree so when drm-tip
moves to 7.3.rc1, Sunday, we will have a version of this helper to core
MM used in gpusvm.
Got it, will wait until Sunday. Thanks for the information.
It looks like the core MM helpers have landed in drm-tip [2] but not
gpusvm bits.
If it isn't too much trouble can you pull in version of [3] at the base
of this series, credit Stanislav as the author, and then rebase this
series on top?
We can then merge all of this together into drm-tip.
Not any trouble at all. And it seems like [3] has already merged in
latest drm-tip.
So I just rebased this series on top of drm-tip. Happy
to help if there are some other rebase works, just let me know,
will do it ASAP.
And this series has been rebased and sent out, rebase and test took
some times, sorry about that.
And I have a question about the XE CI, I always get a warning:
Warning: Your patch series was applied on top of the
307e9559fc1b95a477f00a767ea053b78d263548 kernel commit
Actually I can not find this commit anywhere in drm-tip
or xe-next, it is very helpful if you can let me know how to get the CI
code apply base line.
Regards,
Honglei
Matt
[2] 121170831228 mm/hmm: add hmm_range_fault_unlocked_timeout() for mmap
lock-drop support
[3]
https://lore.freedesktop.org/nouveau/[email protected]/T/#m68f663ce3e802d7692363c70e6364569134cd6c7
Regards,
Honglei
Matt
[1]
https://lore.freedesktop.org/nouveau/[email protected]/T/#m68f663ce3e802d7692363c70e6364569134cd6c7
Suggested-by: Matthew Brost <[email protected]>
Signed-off-by: Honglei Huang <[email protected]>
---
drivers/gpu/drm/drm_gpusvm.c | 67 ++++++++++++++++++++++++------------
1 file changed, 45 insertions(+), 22 deletions(-)
diff --git a/drivers/gpu/drm/drm_gpusvm.c b/drivers/gpu/drm/drm_gpusvm.c
index fcfe635bc195..507ef6f0a60e 100644
--- a/drivers/gpu/drm/drm_gpusvm.c
+++ b/drivers/gpu/drm/drm_gpusvm.c
@@ -1442,6 +1442,50 @@ static bool drm_gpusvm_pages_valid_unlocked(struct
drm_gpusvm *gpusvm,
return pages_valid;
}
+/**
+ * drm_gpusvm_hmm_fault() - Run the shared HMM fault for a CPU range
+ * @gpusvm: Pointer to the GPU SVM structure
+ * @mm: The mm corresponding to the CPU range
+ * @hmm_range: The hmm_range to fault.
+ * @pfns: The pfn array to populate (size @npages)
+ * @timeout: jiffies deadline for the -EBUSY retry loop
+ *
+ * Fault the CPU pages of the range into @pfns. This is the MM level step.
+ *
+ * Return: 0 on success, negative error code on failure.
+ */
+static int drm_gpusvm_hmm_fault(struct drm_gpusvm *gpusvm,
+ struct mm_struct *mm,
+ struct hmm_range *hmm_range,
+ unsigned long *pfns,
+ unsigned long timeout)
+{
+ int err;
+
+ if (!mmget_not_zero(mm))
+ return -EFAULT;
+
+ hmm_range->hmm_pfns = pfns;
+ while (true) {
+ mmap_read_lock(mm);
+ err = hmm_range_fault(hmm_range);
+ mmap_read_unlock(mm);
+
+ if (err == -EBUSY) {
+ if (time_after(jiffies, timeout))
+ break;
+
+ hmm_range->notifier_seq =
+ mmu_interval_read_begin(hmm_range->notifier);
+ continue;
+ }
+ break;
+ }
+ mmput(mm);
+
+ return err;
+}
+
/**
* drm_gpusvm_get_pages() - Get pages and populate GPU SVM pages struct
* @gpusvm: Pointer to the GPU SVM structure
@@ -1503,28 +1547,7 @@ int drm_gpusvm_get_pages(struct drm_gpusvm *gpusvm,
if (!pfns)
return -ENOMEM;
- if (!mmget_not_zero(mm)) {
- err = -EFAULT;
- goto err_free;
- }
-
- hmm_range.hmm_pfns = pfns;
- while (true) {
- mmap_read_lock(mm);
- err = hmm_range_fault(&hmm_range);
- mmap_read_unlock(mm);
-
- if (err == -EBUSY) {
- if (time_after(jiffies, timeout))
- break;
-
- hmm_range.notifier_seq =
- mmu_interval_read_begin(notifier);
- continue;
- }
- break;
- }
- mmput(mm);
+ err = drm_gpusvm_hmm_fault(gpusvm, mm, &hmm_range, pfns, timeout);
if (err)
goto err_free;
--
2.34.1