Compute vrr_vsync_start/end, which sets the position
for hardware to send the Vsync at a fixed position
relative to the end of the Vblank.
--v2:
- Updated VSYNC_START/END macros to VRR_VSYNC_START/END. (Ankit)
- Updated bit fields of VRR_VSYNC_START/END. (Ankit)
--v3:
- Add PIPE_CONF_CHECK_I(vrr.vsync_start/end).
- Read/write vrr_vsync params only when we intend to send
adaptive_sync sdp.
--v4:
- Use VRR_SYNC_START/END macros correctly.
--v5:
- Send AS SDP only when VRR is enabled.
--v6:
- Add TRANS_VRR_VSYNC before enabling VRR as per bspec. (Ankit)
Signed-off-by: Mitul Golani <mitulkumar.ajitkumar.golani@intel.com>
Reviewed-by: Arun R Murthy <arun.r.murthy@intel.com>
Reviewed-by: Ankit Nautiyal <ankit.k.nautiyal@intel.com>
Signed-off-by: Ankit Nautiyal <ankit.k.nautiyal@intel.com>
Link: https://patchwork.freedesktop.org/patch/msgid/20240322031157.3823909-9-mitulkumar.ajitkumar.golani@intel.com
Add the atomic state during a modeset required to enable the DP tunnel
BW allocation mode on links where such a tunnel was detected. This state
applies to an already enabled output, the state added for a newly
enabled output will be computed and added/cleared to/from the atomic
state in a follow-up patch.
v2:
- s/old_crtc_state/crtc_state in intel_crtc_duplicate_state().
- Move intel_dp_tunnel_atomic_cleanup_inherited_state() to a follow-up
patch adding the corresponding state. (Ville)
- Move intel_dp_tunnel_atomic_clear_stream_bw() to a follow-up
patch adding the corresponding state.
Cc: Ville Syrjälä <ville.syrjala@linux.intel.com>
Reviewed-by: Uma Shankar <uma.shankar@intel.com>
Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>
Signed-off-by: Imre Deak <imre.deak@intel.com>
Link: https://patchwork.freedesktop.org/patch/msgid/20240220211841.448846-14-imre.deak@intel.com
On shared (Thunderbolt) links with DP tunnels, the modeset may need to
be retried on all connectors on the link due to a link BW limitation
arising only after the atomic check phase. To support this add a helper
function queuing a work to retry the modeset on a given port's connector
and at the same time any MST connector with streams through the same
port. A follow-up change enabling the DP tunnel Bandwidth Allocation
Mode will take this into use.
v2:
- Send the uevent only to enabled MST connectors. (Jouni)
Cc: Jouni Högander <jouni.hogander@intel.com>
Reviewed-by: Uma Shankar <uma.shankar@intel.com>
Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>
Signed-off-by: Imre Deak <imre.deak@intel.com>
Link: https://patchwork.freedesktop.org/patch/msgid/20240220211841.448846-5-imre.deak@intel.com
The system resume display mode restoration should happen with an output
configuration matching that of the suspend time saved mode. Since the
restored mode configuration is subject to the bpp fallback logic,
starting out with an unlimited bpp and reducing the bpp as required by
any (MST) link BW limit, the resulting bpp will match the one during
suspend only if the BW limit checks during suspend and resume are
applied in an identical way. The latter is not guaranteed at the moment,
since the pre-suspend MST topology may not be in place during resume
(for instance if the MST sink was disconnected while being suspended),
which makes the MST link BW check accept the unlimited bpp mode
configuration unconditionally without ensuring that the required BW fits
into the available MST link BW.
To fix the above, initialize the bpp fallback logic with the max link
bpp / force-FEC limits left behind by the suspend time mode save.
Reviewed-by: Uma Shankar <uma.shankar@intel.com>
Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com>
Signed-off-by: Imre Deak <imre.deak@intel.com>
Link: https://patchwork.freedesktop.org/patch/msgid/20240220211841.448846-4-imre.deak@intel.com
On MTL the GOP (for whatever reason) likes to bind its framebuffer
high up in the ggtt address space. This can conflict with whatever
ggtt_reserve_guc_top() is trying to do, and the result is that
ggtt_reserve_guc_top() fails and then we proceed to explode when
trying to tear down the driver. Thus far I haven't analyzed what
causes the actual fireworks, but it's not super important as even
if it didn't explode we'd still fail the driver load and the user
would be left with an unusable GPU.
To remedy this (without having to figure out exactly what
ggtt_reserve_guc_top() is trying to achieve) we can attempt to
relocate the BIOS framebuffer to a lower ggtt address. We can do
this at this early point in driver init because nothing else is
supposed to be clobbering the ggtt yet. So we simply change where
in the ggtt we pin the vma, the original PTEs will be left as is,
and the new PTEs will get written with the same dma addresses.
The plane will keep on scanning out from the original PTEs until
we are done with the whole process, and at that point we rewrite
the plane's surface address register to point at the new ggtt
address.
Since we don't need a specific ggtt address for the plane
(apart from needing it to land in the mappable region for
normal stolen objects) we'll just try to pin it without a fixed
offset first. It should end up at the lowest available address
(which really should be 0 at this point in the driver init).
If that fails we'll fall back to just pinning it exactly to the
origianal address.
To make sure we don't accidentlally pin it partially over the
original ggtt range (as that would corrupt the original PTEs)
we reserve the original range temporarily during this process.
v2: Try to pin explicitly to ggtt offset 0 as otherwise DG2 puts it
even higher (atm we have no PIN_LOW flag to force it low)
v3: "fix" xe
Reviewed-by: Andrzej Hajda <andrzej.hajda@intel.com>
Tested-by: Paz Zcharya <pazz@chromium.org>
Signed-off-by: Ville Syrjälä <ville.syrjala@linux.intel.com>
Link: https://patchwork.freedesktop.org/patch/msgid/20240202224340.30647-16-ville.syrjala@linux.intel.com
Acked-by: Lucas De Marchi <lucas.demarchi@intel.com>
Instead of injecting extra crtc commits to serialize the global
state let's hand roll a bit of commit machinery to take care of
the hardware synchronization.
Rather than basing everything on the crtc commits we track these
as their own thing. I think this makes more sense as the hardware
blocks we are working with are not in any way tied to the pipes,
so the completion should not be tied in with the vblank machinery
either.
The difference to the old behaviour is that:
- we no longer pull extra crtcs into the commit which should
make drm_atomic_check_only() happier
- since those crtcs don't get pulled in we also don't end up
reprogamming them and thus don't need to wait their vblanks
to pass/etc. So this should be tad faster as well.
TODO: perhaps have each global object complete its own commit
once the post-plane update phase is done?
Closes: https://gitlab.freedesktop.org/drm/intel/-/issues/6728
Signed-off-by: Ville Syrjälä <ville.syrjala@linux.intel.com>
Link: https://patchwork.freedesktop.org/patch/msgid/20231219130756.25986-3-ville.syrjala@linux.intel.com
Reviewed-by: Stanislav Lisovskiy <stanislav.lisovskiy@intel.com>
An unexpected modeset or connector detection by a user (user space or FB
console) during the initialization/shutdown sequence is possible either
via a hotplug IRQ handling work or via the connector sysfs
(status/detect) interface. These modesets/detections should be prevented
by disabling/flushing all related hotplug handling work and
unregistering the interfaces that can start them at the beginning of the
shutdown sequence. Some of this - disabling all related intel_hotplug
work - will be done by the next patch, but others - for instance
disabling the MST hotplug works - require a bigger rework.
It makes sense - for diagnostic purpose, even with all the above work and
interface disabled - to detect and reject any such user access. This
patch does that for modeset accesses and a follow-up patch for connector
detection.
During driver loading/unloading/system suspend/shutdown and during
system resume after calling intel_display_driver_disable_user_access()
or intel_display_driver_resume_access() correspondigly, the current
thread is allowed to modeset (as this thread requires to do an
initial/restoring modeset or a disabling modeset), other threads (the
user threads) are not allowed to modeset.
During driver loading/system resume after calling
intel_display_driver_enable_user_access() all threads are allowed to
modeset.
During driver unloading/system suspend/shutdown after calling
intel_display_driver_suspend_access() no threads are allowed to modeset
(as the HW got disabled and should stay in this state).
v2: Call intel_display_driver_suspend_access()/resume_access() only
for HAS_DISPLAY(). (CI)
v3: (Jouni)
- Add commit log comments explaining how the permission of modeset
changes during HW init/deinit wrt. to the current and other user
processes.
Link: https://patchwork.freedesktop.org/patch/msgid/20240104132335.2766434-1-imre.deak@intel.com
Reviewed-by: Jouni Högander <jouni.hogander@intel.com>
Signed-off-by: Imre Deak <imre.deak@intel.com>
Invoke drm_plane_helper_funcs.end_fb_access before
drm_atomic_helper_commit_hw_done(). The latter function hands over
ownership of the plane state to the following commit, which might
free it. Releasing resources in end_fb_access then operates on undefined
state. This bug has been observed with non-blocking commits when they
are being queued up quickly.
Here is an example stack trace from the bug report. The plane state has
been free'd already, so the pages for drm_gem_fb_vunmap() are gone.
Unable to handle kernel paging request at virtual address 0000000100000049
[...]
drm_gem_fb_vunmap+0x18/0x74
drm_gem_end_shadow_fb_access+0x1c/0x2c
drm_atomic_helper_cleanup_planes+0x58/0xd8
drm_atomic_helper_commit_tail+0x90/0xa0
commit_tail+0x15c/0x188
commit_work+0x14/0x20
Fix this by running end_fb_access immediately after updating all planes
in drm_atomic_helper_commit_planes(). The existing clean-up helper
drm_atomic_helper_cleanup_planes() now only handles cleanup_fb.
For aborted commits, roll back from drm_atomic_helper_prepare_planes()
in the new helper drm_atomic_helper_unprepare_planes(). This case is
different from regular cleanup, as we have to release the new state;
regular cleanup releases the old state. The new helper also invokes
cleanup_fb for all planes.
The changes mostly involve DRM's atomic helpers. Only two drivers, i915
and nouveau, implement their own commit function. Update them to invoke
drm_atomic_helper_unprepare_planes(). Drivers with custom commit_tail
function do not require changes.
v4:
* fix documentation (kernel test robot)
v3:
* add drm_atomic_helper_unprepare_planes() for rolling back
* use correct state for end_fb_access
v2:
* fix test in drm_atomic_helper_cleanup_planes()
Reported-by: Alyssa Ross <hi@alyssa.is>
Closes: https://lore.kernel.org/dri-devel/87leazm0ya.fsf@alyssa.is/
Suggested-by: Daniel Vetter <daniel@ffwll.ch>
Fixes: 94d879eaf7 ("drm/atomic-helper: Add {begin,end}_fb_access to plane helpers")
Tested-by: Alyssa Ross <hi@alyssa.is>
Reviewed-by: Alyssa Ross <hi@alyssa.is>
Signed-off-by: Thomas Zimmermann <tzimmermann@suse.de>
Cc: <stable@vger.kernel.org> # v6.2+
Link: https://patchwork.freedesktop.org/patch/msgid/20231204083247.22006-1-tzimmermann@suse.de