From: Maarten Lankhorst <maarten.lankhorst@linux.intel.com>
To: intel-gfx@lists.freedesktop.org
Subject: Re: [PATCH 02/19] drm/i915: Remove stallcheck special handling, v2.
Date: Thu, 28 Apr 2016 12:20:09 +0200 [thread overview]
Message-ID: <58bc52b0-e464-b6d9-8a97-e55d9a14c38f@linux.intel.com> (raw)
In-Reply-To: <20160428095446.GA5964@patrik-desktop.isw.intel.com>
Op 28-04-16 om 11:54 schreef Patrik Jakobsson:
> On Thu, Apr 28, 2016 at 10:48:55AM +0200, Maarten Lankhorst wrote:
>> Op 27-04-16 om 15:24 schreef Patrik Jakobsson:
>>> On Tue, Apr 19, 2016 at 09:52:22AM +0200, Maarten Lankhorst wrote:
>>>> Both intel_unpin_work.pending and intel_unpin_work.enable_stall_check
>>>> were used to see if work should be enabled. By only using pending
>>>> some special cases are gone, and access to unpin_work can be simplified.
>>>>
>>>> Use this to only access work members untilintel_mark_page_flip_active
>>>> is called, or intel_queue_mmio_flip is used. This will prevent
>>>> use-after-free, and makes it easier to verify accesses.
>>>>
>>>> Changes since v1:
>>>> - Reword commit message.
>>>> - Do not access unpin_work after intel_mark_page_flip_active.
>>>> - Add the right memory barriers.
>>>>
>>>> Signed-off-by: Maarten Lankhorst <maarten.lankhorst@linux.intel.com>
>>>> ---
>>>> drivers/gpu/drm/i915/i915_debugfs.c | 11 +++---
>>>> drivers/gpu/drm/i915/intel_display.c | 71 ++++++++++++++----------------------
>>>> drivers/gpu/drm/i915/intel_drv.h | 1 -
>>>> 3 files changed, 34 insertions(+), 49 deletions(-)
>>>>
>>>> diff --git a/drivers/gpu/drm/i915/i915_debugfs.c b/drivers/gpu/drm/i915/i915_debugfs.c
>>>> index 931dc6086f3b..0092aaf47c43 100644
>>>> --- a/drivers/gpu/drm/i915/i915_debugfs.c
>>>> +++ b/drivers/gpu/drm/i915/i915_debugfs.c
>>>> @@ -612,9 +612,14 @@ static int i915_gem_pageflip_info(struct seq_file *m, void *data)
>>>> seq_printf(m, "No flip due on pipe %c (plane %c)\n",
>>>> pipe, plane);
>>>> } else {
>>>> + u32 pending;
>>>> u32 addr;
>>>>
>>>> - if (atomic_read(&work->pending) < INTEL_FLIP_COMPLETE) {
>>>> + pending = atomic_read(&work->pending);
>>>> + if (pending == INTEL_FLIP_INACTIVE) {
>>>> + seq_printf(m, "Flip ioctl preparing on pipe %c (plane %c)\n",
>>>> + pipe, plane);
>>>> + } else if (pending >= INTEL_FLIP_COMPLETE) {
>>>> seq_printf(m, "Flip queued on pipe %c (plane %c)\n",
>>>> pipe, plane);
>>>> } else {
>>>> @@ -636,10 +641,6 @@ static int i915_gem_pageflip_info(struct seq_file *m, void *data)
>>>> work->flip_queued_vblank,
>>>> work->flip_ready_vblank,
>>>> drm_crtc_vblank_count(&crtc->base));
>>>> - if (work->enable_stall_check)
>>>> - seq_puts(m, "Stall check enabled, ");
>>>> - else
>>>> - seq_puts(m, "Stall check waiting for page flip ioctl, ");
>>>> seq_printf(m, "%d prepares\n", atomic_read(&work->pending));
>>>>
>>>> if (INTEL_INFO(dev)->gen >= 4)
>>>> diff --git a/drivers/gpu/drm/i915/intel_display.c b/drivers/gpu/drm/i915/intel_display.c
>>>> index 4cb830e2a62e..97a8418f6539 100644
>>>> --- a/drivers/gpu/drm/i915/intel_display.c
>>>> +++ b/drivers/gpu/drm/i915/intel_display.c
>>>> @@ -3896,8 +3896,6 @@ static void page_flip_completed(struct intel_crtc *intel_crtc)
>>>> struct drm_i915_private *dev_priv = to_i915(intel_crtc->base.dev);
>>>> struct intel_unpin_work *work = intel_crtc->unpin_work;
>>>>
>>>> - /* ensure that the unpin work is consistent wrt ->pending. */
>>>> - smp_rmb();
>>>> intel_crtc->unpin_work = NULL;
>>>>
>>>> if (work->event)
>>>> @@ -10980,16 +10978,13 @@ static void do_intel_finish_page_flip(struct drm_device *dev,
>>>> spin_lock_irqsave(&dev->event_lock, flags);
>>>> work = intel_crtc->unpin_work;
>>>>
>>>> - /* Ensure we don't miss a work->pending update ... */
>>>> - smp_rmb();
>>>> + if (work && atomic_read(&work->pending) >= INTEL_FLIP_COMPLETE) {
>>>> + /* ensure that the unpin work is consistent wrt ->pending. */
>>>> + smp_mb__after_atomic();
>>> The docs on smp_mb__after/before_atomic() states that they are used with atomic
>>> functions that do not return a value. Why are we using it together with
>>> atomic_read() here?
>> From Documentation/atomic_ops.txt:
>>
>> *** WARNING: atomic_read() and atomic_set() DO NOT IMPLY BARRIERS! ***
>>
>> Plus a whole warning below how the atomic ops may be reordered. The memory
>> barriers are definitely required.
> Yes, the barriers are required. My point is that _after/before_atomic() should
> only be used with set/clear/inc etc atomic operations. For atomic operations
> that return a value you should use other macros. At least that is how I
> interpret the documentation.
>
> Here's the part from Documentation/atomic_ops.txt:
>
> --
>
> If a caller requires memory barrier semantics around an atomic_t
> operation which does not return a value, a set of interfaces are
> defined which accomplish this:
>
> void smp_mb__before_atomic(void);
> void smp_mb__after_atomic(void);
>
> --
>
> So I interpret this as, there's no guarantee that you'll get a full memory
> barrier from these macros.
>
>>>> static void intel_mmio_flip_work_func(struct work_struct *work)
>>>> @@ -11529,15 +11517,14 @@ static bool __intel_pageflip_stall_check(struct drm_device *dev,
>>>> struct intel_crtc *intel_crtc = to_intel_crtc(crtc);
>>>> struct intel_unpin_work *work = intel_crtc->unpin_work;
>>>> u32 addr;
>>>> + u32 pending;
>>>>
>>>> - if (atomic_read(&work->pending) >= INTEL_FLIP_COMPLETE)
>>>> - return true;
>>>> -
>>>> - if (atomic_read(&work->pending) < INTEL_FLIP_PENDING)
>>>> - return false;
>>>> + pending = atomic_read(&work->pending);
>>>> + /* ensure that the unpin work is consistent wrt ->pending. */
>>>> + smp_mb__after_atomic();
>>> Why paired with atomic_read()?
>> See above. ^
>>>>
>>>> - if (!work->enable_stall_check)
>>>> - return false;
>>>> + if (pending != INTEL_FLIP_PENDING)
>>>> + return pending == INTEL_FLIP_COMPLETE;
>>> Am I correct in assuming that we can remove the enable_stall_check test here
>>> since it's always enabled? If so, that would be useful to explain in the commit
>>> message.
>> The commit message says stallcheck special handling is removed entirely. I thought it would
>> imply that the special case, where a flip may be queued but stallcheck not yet active, is removed entirely.
>>
>> ~Maarten
> The commit message tells what the patch does but not why. This might be obvious
> if you're familiar with the code. I stumbled a bit here so I guess I'm not :)
>
> "Both intel_unpin_work.pending and intel_unpin_work.enable_stall_check were used
> to see if work should be enabled"
>
> From this I imply that both checks are needed.
>
> "By only using pending some special cases are gone"
>
> This is what I don't find intuitive. Why can we suddently skip the
> enable_stall_check test? It would have been useful to know about the special
> case where a flip may be queued but stallcheck not yet active, and that it's no
> longer valid (and possibly why).
It looks like the pending member was added later to fix a race. It made enable_stall_check obsolete,
but I'm not 100% sure that this was the reason.
In any case for flips we set pending right before queueing, which eliminates the race.
~Maarten
_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx
next prev parent reply other threads:[~2016-04-28 10:20 UTC|newest]
Thread overview: 57+ messages / expand[flat|nested] mbox.gz Atom feed top
2016-04-19 7:52 [PATCH 00/19] Rework page flip, remove cs flips, async unpin and unified pageflip Maarten Lankhorst
2016-04-19 7:52 ` [PATCH 01/19] drm/core: Add drm_accurate_vblank_count, v4 Maarten Lankhorst
2016-04-25 4:35 ` Mario Kleiner
2016-04-25 6:32 ` [PATCH 01/19] drm/core: Add drm_accurate_vblank_count, v5 Maarten Lankhorst
2016-04-25 7:49 ` Mario Kleiner
2016-04-27 23:02 ` Mario Kleiner
2016-04-25 12:26 ` [PATCH 01/19] drm/core: Add drm_accurate_vblank_count, v4 Ville Syrjälä
2016-04-19 7:52 ` [PATCH 02/19] drm/i915: Remove stallcheck special handling, v2 Maarten Lankhorst
2016-04-27 13:24 ` Patrik Jakobsson
2016-04-28 8:48 ` Maarten Lankhorst
2016-04-28 9:54 ` Patrik Jakobsson
2016-04-28 10:20 ` Maarten Lankhorst [this message]
2016-05-03 13:48 ` Patrik Jakobsson
2016-05-03 14:15 ` Maarten Lankhorst
2016-04-19 7:52 ` [PATCH 03/19] drm/i915: Remove intel_prepare_page_flip, v2 Maarten Lankhorst
2016-04-25 23:14 ` Patrik Jakobsson
2016-04-28 9:24 ` Maarten Lankhorst
2016-04-19 7:52 ` [PATCH 04/19] drm/i915: Add support for detecting vblanks when hw frame counter is unavailable Maarten Lankhorst
2016-04-27 14:06 ` Patrik Jakobsson
2016-04-27 14:23 ` Ville Syrjälä
2016-05-10 12:30 ` Patrik Jakobsson
2016-04-19 7:52 ` [PATCH 05/19] drm/i915: Unify unpin_work and mmio_work into flip_work Maarten Lankhorst
2016-04-29 12:47 ` Patrik Jakobsson
2016-04-19 7:52 ` [PATCH 06/19] Revert "drm/i915: Avoid stalling on pending flips for legacy cursor updates" Maarten Lankhorst
2016-05-10 12:31 ` Patrik Jakobsson
2016-04-19 7:52 ` [PATCH 07/19] drm/i915: Allow mmio updates on all platforms, v2 Maarten Lankhorst
2016-04-19 12:48 ` Ville Syrjälä
2016-04-19 13:37 ` Maarten Lankhorst
2016-05-12 11:49 ` [RFC PATCH " Maarten Lankhorst
2016-04-19 7:52 ` [PATCH 08/19] drm/i915: Convert flip_work to a list Maarten Lankhorst
2016-05-02 9:22 ` Patrik Jakobsson
2016-05-02 11:07 ` Maarten Lankhorst
2016-04-19 7:52 ` [PATCH 09/19] drm/i915: Add the exclusive fence to plane_state Maarten Lankhorst
2016-05-03 12:47 ` Patrik Jakobsson
2016-04-19 7:52 ` [PATCH 10/19] drm/i915: Rework intel_crtc_page_flip to be almost atomic, v3 Maarten Lankhorst
2016-04-19 7:52 ` [PATCH 11/19] drm/i915: Remove cs based page flip support Maarten Lankhorst
2016-04-19 7:52 ` [PATCH 12/19] drm/i915: Remove use_mmio_flip kernel parameter Maarten Lankhorst
2016-05-11 8:48 ` Patrik Jakobsson
2016-04-19 7:52 ` [PATCH 13/19] drm/i915: Remove queue_flip pointer Maarten Lankhorst
2016-05-11 8:49 ` Patrik Jakobsson
2016-04-19 7:52 ` [PATCH 14/19] drm/i915: Pass atomic states to fbc update functions Maarten Lankhorst
2016-05-11 9:13 ` Patrik Jakobsson
2016-04-19 7:52 ` [PATCH 15/19] drm/i915: Prepare MST connector removal for async unpin Maarten Lankhorst
2016-05-11 9:26 ` Patrik Jakobsson
2016-04-19 7:52 ` [PATCH 16/19] drm/i915: Make unpin async Maarten Lankhorst
2016-04-25 16:26 ` Lionel Landwerlin
2016-04-25 16:26 ` Lionel Landwerlin
2016-04-26 7:14 ` Maarten Lankhorst
2016-04-19 7:52 ` [PATCH 17/19] Reapply "drm/i915: Avoid stalling on pending flips for legacy cursor updates" Maarten Lankhorst
2016-04-19 7:52 ` [PATCH 18/19] drm/i915: Check for unpin correctness Maarten Lankhorst
2016-04-19 7:52 ` [PATCH 19/19] drm/i915: Allow async update of pageflips Maarten Lankhorst
2016-04-19 8:19 ` Chris Wilson
2016-04-19 12:26 ` Maarten Lankhorst
2016-04-20 13:24 ` Daniel Vetter
2016-04-20 13:45 ` Chris Wilson
2016-04-20 7:39 ` Maarten Lankhorst
2016-04-19 8:27 ` ✗ Fi.CI.BAT: failure for Rework page flip, remove cs flips, async unpin and unified pageflip 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=58bc52b0-e464-b6d9-8a97-e55d9a14c38f@linux.intel.com \
--to=maarten.lankhorst@linux.intel.com \
--cc=intel-gfx@lists.freedesktop.org \
/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.