amd-drm-fixes-6.19-2026-01-29:

amdgpu:
 - SMU 13 fixes
 - SMU 14 fixes
 - GPUVM fault filter fix
 - Powergating fix
 - HDMI debounce fix
 - Xclk fix for soc21 APUs
 - Fix COND_EXEC handling for GC 11
 - GC 10-12 KGQ init fixes
 - GC 11-12 KGQ reset fixes
 -----BEGIN PGP SIGNATURE-----
 
 iHUEABYKAB0WIQQgO5Idg2tXNTSZAr293/aFa7yZ2AUCaXvKlQAKCRC93/aFa7yZ
 2KljAP94YzUJFMrUyeWw/8HcNkXju8bl/LtCw2UPBhn79e9H3wEA3MbVjNgqrH2Y
 OpeyB0IpVfbWxC8HFIULYeLiYSYK+gc=
 =AS9D
 -----END PGP SIGNATURE-----

Merge tag 'amd-drm-fixes-6.19-2026-01-29' of https://gitlab.freedesktop.org/agd5f/linux into drm-fixes

amd-drm-fixes-6.19-2026-01-29:

amdgpu:
- SMU 13 fixes
- SMU 14 fixes
- GPUVM fault filter fix
- Powergating fix
- HDMI debounce fix
- Xclk fix for soc21 APUs
- Fix COND_EXEC handling for GC 11
- GC 10-12 KGQ init fixes
- GC 11-12 KGQ reset fixes

Signed-off-by: Dave Airlie <airlied@redhat.com>

From: Alex Deucher <alexander.deucher@amd.com>
Link: https://patch.msgid.link/20260129212518.22274-1-alexander.deucher@amd.com
master
Dave Airlie 2026-01-30 10:43:35 +10:00
commit 016bf66866
12 changed files with 59 additions and 34 deletions

View File

@ -498,8 +498,13 @@ void amdgpu_gmc_filter_faults_remove(struct amdgpu_device *adev, uint64_t addr,
if (adev->irq.retry_cam_enabled)
return;
else if (adev->irq.ih1.ring_size)
ih = &adev->irq.ih1;
else if (adev->irq.ih_soft.enabled)
ih = &adev->irq.ih_soft;
else
return;
ih = &adev->irq.ih1;
/* Get the WPTR of the last entry in IH ring */
last_wptr = amdgpu_ih_get_wptr(adev, ih);
/* Order wptr with ring data. */

View File

@ -235,7 +235,7 @@ int amdgpu_ib_schedule(struct amdgpu_ring *ring, unsigned int num_ibs,
amdgpu_ring_ib_begin(ring);
if (ring->funcs->emit_gfx_shadow)
if (ring->funcs->emit_gfx_shadow && adev->gfx.cp_gfx_shadow)
amdgpu_ring_emit_gfx_shadow(ring, shadow_va, csa_va, gds_va,
init_shadow, vmid);
@ -291,7 +291,8 @@ int amdgpu_ib_schedule(struct amdgpu_ring *ring, unsigned int num_ibs,
fence_flags | AMDGPU_FENCE_FLAG_64BIT);
}
if (ring->funcs->emit_gfx_shadow && ring->funcs->init_cond_exec) {
if (ring->funcs->emit_gfx_shadow && ring->funcs->init_cond_exec &&
adev->gfx.cp_gfx_shadow) {
amdgpu_ring_emit_gfx_shadow(ring, 0, 0, 0, false, 0);
amdgpu_ring_init_cond_exec(ring, ring->cond_exe_gpu_addr);
}

View File

@ -6879,7 +6879,7 @@ static int gfx_v10_0_kgq_init_queue(struct amdgpu_ring *ring, bool reset)
memcpy_toio(mqd, adev->gfx.me.mqd_backup[mqd_idx], sizeof(*mqd));
/* reset the ring */
ring->wptr = 0;
*ring->wptr_cpu_addr = 0;
atomic64_set((atomic64_t *)ring->wptr_cpu_addr, 0);
amdgpu_ring_clear_ring(ring);
}

View File

@ -4201,7 +4201,7 @@ static int gfx_v11_0_kgq_init_queue(struct amdgpu_ring *ring, bool reset)
memcpy_toio(mqd, adev->gfx.me.mqd_backup[mqd_idx], sizeof(*mqd));
/* reset the ring */
ring->wptr = 0;
*ring->wptr_cpu_addr = 0;
atomic64_set((atomic64_t *)ring->wptr_cpu_addr, 0);
amdgpu_ring_clear_ring(ring);
}
@ -6823,11 +6823,12 @@ static int gfx_v11_0_reset_kgq(struct amdgpu_ring *ring,
struct amdgpu_fence *timedout_fence)
{
struct amdgpu_device *adev = ring->adev;
bool use_mmio = false;
int r;
amdgpu_ring_reset_helper_begin(ring, timedout_fence);
r = amdgpu_mes_reset_legacy_queue(ring->adev, ring, vmid, false);
r = amdgpu_mes_reset_legacy_queue(ring->adev, ring, vmid, use_mmio);
if (r) {
dev_warn(adev->dev, "reset via MES failed and try pipe reset %d\n", r);
@ -6836,16 +6837,18 @@ static int gfx_v11_0_reset_kgq(struct amdgpu_ring *ring,
return r;
}
r = gfx_v11_0_kgq_init_queue(ring, true);
if (r) {
dev_err(adev->dev, "failed to init kgq\n");
return r;
}
if (use_mmio) {
r = gfx_v11_0_kgq_init_queue(ring, true);
if (r) {
dev_err(adev->dev, "failed to init kgq\n");
return r;
}
r = amdgpu_mes_map_legacy_queue(adev, ring);
if (r) {
dev_err(adev->dev, "failed to remap kgq\n");
return r;
r = amdgpu_mes_map_legacy_queue(adev, ring);
if (r) {
dev_err(adev->dev, "failed to remap kgq\n");
return r;
}
}
return amdgpu_ring_reset_helper_end(ring, timedout_fence);

View File

@ -3079,7 +3079,7 @@ static int gfx_v12_0_kgq_init_queue(struct amdgpu_ring *ring, bool reset)
memcpy_toio(mqd, adev->gfx.me.mqd_backup[mqd_idx], sizeof(*mqd));
/* reset the ring */
ring->wptr = 0;
*ring->wptr_cpu_addr = 0;
atomic64_set((atomic64_t *)ring->wptr_cpu_addr, 0);
amdgpu_ring_clear_ring(ring);
}
@ -5297,11 +5297,12 @@ static int gfx_v12_0_reset_kgq(struct amdgpu_ring *ring,
struct amdgpu_fence *timedout_fence)
{
struct amdgpu_device *adev = ring->adev;
bool use_mmio = false;
int r;
amdgpu_ring_reset_helper_begin(ring, timedout_fence);
r = amdgpu_mes_reset_legacy_queue(ring->adev, ring, vmid, false);
r = amdgpu_mes_reset_legacy_queue(ring->adev, ring, vmid, use_mmio);
if (r) {
dev_warn(adev->dev, "reset via MES failed and try pipe reset %d\n", r);
r = gfx_v12_reset_gfx_pipe(ring);
@ -5309,16 +5310,18 @@ static int gfx_v12_0_reset_kgq(struct amdgpu_ring *ring,
return r;
}
r = gfx_v12_0_kgq_init_queue(ring, true);
if (r) {
dev_err(adev->dev, "failed to init kgq\n");
return r;
}
if (use_mmio) {
r = gfx_v12_0_kgq_init_queue(ring, true);
if (r) {
dev_err(adev->dev, "failed to init kgq\n");
return r;
}
r = amdgpu_mes_map_legacy_queue(adev, ring);
if (r) {
dev_err(adev->dev, "failed to remap kgq\n");
return r;
r = amdgpu_mes_map_legacy_queue(adev, ring);
if (r) {
dev_err(adev->dev, "failed to remap kgq\n");
return r;
}
}
return amdgpu_ring_reset_helper_end(ring, timedout_fence);

View File

@ -225,7 +225,13 @@ static u32 soc21_get_config_memsize(struct amdgpu_device *adev)
static u32 soc21_get_xclk(struct amdgpu_device *adev)
{
return adev->clock.spll.reference_freq;
u32 reference_clock = adev->clock.spll.reference_freq;
/* reference clock is actually 99.81 Mhz rather than 100 Mhz */
if ((adev->flags & AMD_IS_APU) && reference_clock == 10000)
return 9981;
return reference_clock;
}

View File

@ -7754,10 +7754,12 @@ static void amdgpu_dm_connector_destroy(struct drm_connector *connector)
drm_dp_mst_topology_mgr_destroy(&aconnector->mst_mgr);
/* Cancel and flush any pending HDMI HPD debounce work */
cancel_delayed_work_sync(&aconnector->hdmi_hpd_debounce_work);
if (aconnector->hdmi_prev_sink) {
dc_sink_release(aconnector->hdmi_prev_sink);
aconnector->hdmi_prev_sink = NULL;
if (aconnector->hdmi_hpd_debounce_delay_ms) {
cancel_delayed_work_sync(&aconnector->hdmi_hpd_debounce_work);
if (aconnector->hdmi_prev_sink) {
dc_sink_release(aconnector->hdmi_prev_sink);
aconnector->hdmi_prev_sink = NULL;
}
}
if (aconnector->bl_idx != -1) {

View File

@ -80,15 +80,15 @@ int amdgpu_dpm_set_powergating_by_smu(struct amdgpu_device *adev,
enum ip_power_state pwr_state = gate ? POWER_STATE_OFF : POWER_STATE_ON;
bool is_vcn = block_type == AMD_IP_BLOCK_TYPE_VCN;
mutex_lock(&adev->pm.mutex);
if (atomic_read(&adev->pm.pwr_state[block_type]) == pwr_state &&
(!is_vcn || adev->vcn.num_vcn_inst == 1)) {
dev_dbg(adev->dev, "IP block%d already in the target %s state!",
block_type, gate ? "gate" : "ungate");
return 0;
goto out_unlock;
}
mutex_lock(&adev->pm.mutex);
switch (block_type) {
case AMD_IP_BLOCK_TYPE_UVD:
case AMD_IP_BLOCK_TYPE_VCE:
@ -115,6 +115,7 @@ int amdgpu_dpm_set_powergating_by_smu(struct amdgpu_device *adev,
if (!ret)
atomic_set(&adev->pm.pwr_state[block_type], pwr_state);
out_unlock:
mutex_unlock(&adev->pm.mutex);
return ret;

View File

@ -56,6 +56,7 @@
#define SMUQ10_TO_UINT(x) ((x) >> 10)
#define SMUQ10_FRAC(x) ((x) & 0x3ff)
#define SMUQ10_ROUND(x) ((SMUQ10_TO_UINT(x)) + ((SMUQ10_FRAC(x)) >= 0x200))
#define SMU_V13_SOFT_FREQ_ROUND(x) ((x) + 1)
extern const int pmfw_decoded_link_speed[5];
extern const int pmfw_decoded_link_width[7];

View File

@ -57,6 +57,7 @@ extern const int decoded_link_width[8];
#define DECODE_GEN_SPEED(gen_speed_idx) (decoded_link_speed[gen_speed_idx])
#define DECODE_LANE_WIDTH(lane_width_idx) (decoded_link_width[lane_width_idx])
#define SMU_V14_SOFT_FREQ_ROUND(x) ((x) + 1)
struct smu_14_0_max_sustainable_clocks {
uint32_t display_clock;

View File

@ -1555,6 +1555,7 @@ int smu_v13_0_set_soft_freq_limited_range(struct smu_context *smu,
return clk_id;
if (max > 0) {
max = SMU_V13_SOFT_FREQ_ROUND(max);
if (automatic)
param = (uint32_t)((clk_id << 16) | 0xffff);
else

View File

@ -1178,6 +1178,7 @@ int smu_v14_0_set_soft_freq_limited_range(struct smu_context *smu,
return clk_id;
if (max > 0) {
max = SMU_V14_SOFT_FREQ_ROUND(max);
if (automatic)
param = (uint32_t)((clk_id << 16) | 0xffff);
else