All of lore.kernel.org
 help / color / mirror / Atom feed
From: Matthew Brost <matthew.brost@intel.com>
To: Himal Prasad Ghimiray <himal.prasad.ghimiray@intel.com>
Cc: <intel-xe@lists.freedesktop.org>,
	<thomas.hellstrom@linux.intel.com>, <stuart.summers@intel.com>,
	<arvind.yadav@intel.com>, <tejas.upadhyay@intel.com>
Subject: Re: [RFC 01/15] drm/xe: Add xe_usm_queue generic USM circular buffer
Date: Wed, 1 Apr 2026 14:28:13 -0700	[thread overview]
Message-ID: <ac2N7WrbfaInoIjk@gsse-cloud1.jf.intel.com> (raw)
In-Reply-To: <20260318074456.2839499-2-himal.prasad.ghimiray@intel.com>

On Wed, Mar 18, 2026 at 01:14:42PM +0530, Himal Prasad Ghimiray wrote:
> Introduce struct xe_usm_queue, a generic lock-protected circular FIFO
> used by USM consumers (page fault, access counter) to receive fixed-size
> entries from IRQ context and process them via a work_struct.
> 
> Provide three inline helpers in xe_usm_queue.h:
>   xe_usm_queue_full()  - CIRC_SPACE check (caller holds lock)
>   xe_usm_queue_pop()   - dequeue one entry (acquires lock internally)
>   xe_usm_queue_push()  - enqueue one entry (caller holds lock)
> 
> Suggested-by: Matthew Brost <matthew.brost@intel.com>
> Signed-off-by: Himal Prasad Ghimiray <himal.prasad.ghimiray@intel.com>

I think this is useful, but right after I suggested it, I changed the
semantics of the page-fault circular buffer to be a single buffer [1]
that multiple workers pull from. This eliminates HoQ blocking (e.g.,
five access events are pushed; the first one takes a really long time,
but the other four are much faster—yet the fifth event gets stuck behind
the long-running one). So maybe start with a single-queue +
multiple-workers-pulling design here? This likely matters considerably
less than the page-fault cases, but overall I think it’s a better
structure.

Also, maybe the xe_usm_queue can be reused by page faults, but the
management of that queue actually gets more convoluted in [2] to
implement the page-fault cache that greatly speeds up storms of faults.
So maybe drop the second patch in the series for now to avoid conflicts,
and if we can converge on a shared xe_usm_queue implementation later,
great..

Matt

[1] https://patchwork.freedesktop.org/patch/707293/?series=162167&rev=4
[2] https://patchwork.freedesktop.org/patch/707300/?series=162167&rev=4

> ---
>  drivers/gpu/drm/xe/xe_usm_queue.h | 100 ++++++++++++++++++++++++++++++
>  1 file changed, 100 insertions(+)
>  create mode 100644 drivers/gpu/drm/xe/xe_usm_queue.h
> 
> diff --git a/drivers/gpu/drm/xe/xe_usm_queue.h b/drivers/gpu/drm/xe/xe_usm_queue.h
> new file mode 100644
> index 000000000000..5dc2d692d8bb
> --- /dev/null
> +++ b/drivers/gpu/drm/xe/xe_usm_queue.h
> @@ -0,0 +1,100 @@
> +/* SPDX-License-Identifier: MIT */
> +/*
> + * Copyright © 2026 Intel Corporation
> + */
> +
> +#ifndef _XE_USM_QUEUE_H_
> +#define _XE_USM_QUEUE_H_
> +
> +#include <linux/circ_buf.h>
> +#include <linux/spinlock.h>
> +#include <linux/workqueue.h>
> +
> +/**
> + * struct xe_usm_queue - Generic USM circular FIFO queue
> + *
> + * A lock-protected circular buffer used by both the page fault consumer and
> + * the access counter consumer. Producers push fixed-size entries from IRQ
> + * context; a work_struct processes them asynchronously.
> + */
> +struct xe_usm_queue {
> +	/**
> +	 * @data: Raw byte buffer backing the queue, protected by @lock
> +	 */
> +	void *data;
> +	/** @size: Total size of @data in bytes */
> +	u32 size;
> +	/** @head: Write cursor in bytes, moved by producer, protected by @lock */
> +	u32 head;
> +	/** @tail: Read cursor in bytes, moved by consumer, protected by @lock */
> +	u32 tail;
> +	/** @lock: Protects the queue head/tail */
> +	spinlock_t lock;
> +	/** @worker: Work item scheduled to drain the queue */
> +	struct work_struct worker;
> +};
> +
> +/**
> + * xe_usm_queue_full - Check whether the queue has no room for one more entry
> + * @q: queue
> + * @size: exact size of one entry in bytes (sizeof the entry struct)
> + *
> + * Must be called with @q->lock held.
> + *
> + * Return: true if the queue is full
> + */
> +static inline bool xe_usm_queue_full(struct xe_usm_queue *q, u32 size)
> +{
> +	u32 entry_size = roundup_pow_of_two(size);
> +
> +	lockdep_assert_held(&q->lock);
> +
> +	return CIRC_SPACE(q->head, q->tail, q->size) <= entry_size;
> +}
> +/**
> + * xe_usm_queue_pop - Pop one entry from the queue into @out
> + * @q: queue
> + * @out: destination buffer, must be at least @size bytes
> + * @size: exact size of one entry in bytes (sizeof the entry struct)
> + *
> + * Acquires @q->lock internally with spin_lock_irq().
> + *
> + * Return: true if an entry was dequeued, false if the queue was empty
> + */
> +static inline bool xe_usm_queue_pop(struct xe_usm_queue *q, void *out,
> +				    u32 size)
> +{
> +	u32 entry_size = roundup_pow_of_two(size);
> +	bool found = false;
> +
> +	spin_lock_irq(&q->lock);
> +	if (q->tail != q->head) {
> +		memcpy(out, q->data + q->tail, size);
> +		q->tail = (q->tail + entry_size) % q->size;
> +		found = true;
> +	}
> +	spin_unlock_irq(&q->lock);
> +
> +	return found;
> +}
> +
> +/**
> + * xe_usm_queue_push - Push one entry into the queue
> + * @q: queue
> + * @in: source buffer, must be at least @size bytes
> + * @size: size of one entry of in bytes
> + *
> + * Must be called with @q->lock held.
> + * Caller must check xe_usm_queue_full() before calling.
> + */
> +static inline void xe_usm_queue_push(struct xe_usm_queue *q, const void *in,
> +				     u32 size)
> +{
> +	u32 entry_size = roundup_pow_of_two(size);
> +
> +	lockdep_assert_held(&q->lock);
> +
> +	memcpy(q->data + q->head, in, size);
> +	q->head = (q->head + entry_size) % q->size;
> +}
> +#endif
> -- 
> 2.34.1
> 

  reply	other threads:[~2026-04-01 21:28 UTC|newest]

Thread overview: 43+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2026-03-18  7:44 [RFC 00/15] drm/xe: Access counter consumer layer Himal Prasad Ghimiray
2026-03-18  7:34 ` ✗ CI.checkpatch: warning for " Patchwork
2026-03-18  7:35 ` ✗ CI.KUnit: failure " Patchwork
2026-03-18  7:44 ` [RFC 01/15] drm/xe: Add xe_usm_queue generic USM circular buffer Himal Prasad Ghimiray
2026-04-01 21:28   ` Matthew Brost [this message]
2026-04-06  4:46     ` Ghimiray, Himal Prasad
2026-03-18  7:44 ` [RFC 02/15] drm/xe/pagefault: Use xe_usm_queue helpers Himal Prasad Ghimiray
2026-03-18  7:44 ` [RFC 03/15] drm/xe: Stub out new access_counter layer Himal Prasad Ghimiray
2026-04-02 21:46   ` Matthew Brost
2026-04-06  5:28     ` Ghimiray, Himal Prasad
2026-04-14 20:06   ` Summers, Stuart
2026-03-18  7:44 ` [RFC 04/15] drm/xe: Implement xe_access_counter_init Himal Prasad Ghimiray
2026-03-18  7:44 ` [RFC 05/15] drm/xe: Implement xe_access_counter_handler Himal Prasad Ghimiray
2026-04-03  2:06   ` Matthew Brost
2026-03-18  7:44 ` [RFC 06/15] drm/xe: Extract xe_vma_lock_and_validate helper Himal Prasad Ghimiray
2026-04-01 22:03   ` Matthew Brost
2026-03-18  7:44 ` [RFC 07/15] drm/xe: Move ASID to FAULT VM lookup to xe_device Himal Prasad Ghimiray
2026-04-02 21:50   ` Matthew Brost
2026-04-07  6:41     ` Ghimiray, Himal Prasad
2026-03-18  7:44 ` [RFC 08/15] drm/xe: Implement xe_access_counter_queue_work Himal Prasad Ghimiray
2026-04-01 21:10   ` Matthew Brost
2026-04-01 22:01     ` Matthew Brost
2026-04-01 22:11   ` Matthew Brost
2026-04-02 22:06   ` Matthew Brost
2026-04-22 20:35   ` Summers, Stuart
2026-03-18  7:44 ` [RFC 09/15] drm/xe/trace: Add xe_vma_acc trace event for access counter notifications Himal Prasad Ghimiray
2026-04-03  1:01   ` Matthew Brost
2026-03-18  7:44 ` [RFC 10/15] drm/xe/svm: Handle svm ranges on access ctr trigger Himal Prasad Ghimiray
2026-04-03  0:25   ` Matthew Brost
2026-03-18  7:44 ` [RFC 11/15] drm/xe: Add xe_guc_access_counter layer Himal Prasad Ghimiray
2026-04-02 21:27   ` Matthew Brost
2026-04-14 21:24   ` Summers, Stuart
2026-04-22 20:38   ` Summers, Stuart
2026-03-18  7:44 ` [RFC 12/15] drm/xe/uapi: Add access counter parameter extension for exec queue Himal Prasad Ghimiray
2026-03-24 14:25   ` Francois Dugast
2026-04-01 14:46     ` Matthew Brost
2026-04-01 16:36       ` Ghimiray, Himal Prasad
2026-03-18  7:44 ` [RFC 13/15] drm/xe/lrc: Pass exec_queue to xe_lrc_create for access counter params Himal Prasad Ghimiray
2026-04-22 20:50   ` Summers, Stuart
2026-03-18  7:44 ` [RFC 14/15] drm/xe/vm: Add xe_vma_supports_access_ctr() helper Himal Prasad Ghimiray
2026-04-22 20:54   ` Summers, Stuart
2026-03-18  7:44 ` [RFC 15/15] drm/xe/pt: Set NC PTE bit for VMAs ineligible for access counting Himal Prasad Ghimiray
2026-04-03  0:09   ` Matthew Brost

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=ac2N7WrbfaInoIjk@gsse-cloud1.jf.intel.com \
    --to=matthew.brost@intel.com \
    --cc=arvind.yadav@intel.com \
    --cc=himal.prasad.ghimiray@intel.com \
    --cc=intel-xe@lists.freedesktop.org \
    --cc=stuart.summers@intel.com \
    --cc=tejas.upadhyay@intel.com \
    --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 an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.