mirror of
https://github.com/torvalds/linux.git
synced 2026-06-02 03:24:19 +02:00
amd-drm-fixes-6.18-2025-10-16:
amdgpu: - Backlight fix - SI fixes - CIK fix - Make CE support debug only - IP discovery fix - Ring reset fixes - GPUVM fault memory barrier fix - Drop unused structures in amdgpu_drm.h - JPEG debugfs fix - VRAM handling fixes for GPUs without VRAM - GC 12 MES fixes amdkfd: - MES fix -----BEGIN PGP SIGNATURE----- iHUEABYKAB0WIQQgO5Idg2tXNTSZAr293/aFa7yZ2AUCaPDwuAAKCRC93/aFa7yZ 2CyaAP9Xwuar8fw2+CaoL7zdvo7MkqQpwOVBkyoQkKOQlZK9gQEAzotisG8jHkls hAfx8eqFoNSQevdKkShgVubIHna5hAw= =nbWU -----END PGP SIGNATURE----- Merge tag 'amd-drm-fixes-6.18-2025-10-16' of https://gitlab.freedesktop.org/agd5f/linux into drm-fixes amd-drm-fixes-6.18-2025-10-16: amdgpu: - Backlight fix - SI fixes - CIK fix - Make CE support debug only - IP discovery fix - Ring reset fixes - GPUVM fault memory barrier fix - Drop unused structures in amdgpu_drm.h - JPEG debugfs fix - VRAM handling fixes for GPUs without VRAM - GC 12 MES fixes amdkfd: - MES fix Signed-off-by: Dave Airlie <airlied@redhat.com> From: Alex Deucher <alexander.deucher@amd.com> Link: https://lore.kernel.org/r/20251016132224.2534946-1-alexander.deucher@amd.com
This commit is contained in:
commit
520133b0ba
|
|
@ -1290,6 +1290,7 @@ struct amdgpu_device {
|
|||
bool debug_disable_gpu_ring_reset;
|
||||
bool debug_vm_userptr;
|
||||
bool debug_disable_ce_logs;
|
||||
bool debug_enable_ce_cs;
|
||||
|
||||
/* Protection for the following isolation structure */
|
||||
struct mutex enforce_isolation_mutex;
|
||||
|
|
|
|||
|
|
@ -2329,10 +2329,9 @@ void amdgpu_amdkfd_gpuvm_unmap_gtt_bo_from_kernel(struct kgd_mem *mem)
|
|||
int amdgpu_amdkfd_gpuvm_get_vm_fault_info(struct amdgpu_device *adev,
|
||||
struct kfd_vm_fault_info *mem)
|
||||
{
|
||||
if (atomic_read(&adev->gmc.vm_fault_info_updated) == 1) {
|
||||
if (atomic_read_acquire(&adev->gmc.vm_fault_info_updated) == 1) {
|
||||
*mem = *adev->gmc.vm_fault_info;
|
||||
mb(); /* make sure read happened */
|
||||
atomic_set(&adev->gmc.vm_fault_info_updated, 0);
|
||||
atomic_set_release(&adev->gmc.vm_fault_info_updated, 0);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -364,6 +364,12 @@ static int amdgpu_cs_p2_ib(struct amdgpu_cs_parser *p,
|
|||
if (p->uf_bo && ring->funcs->no_user_fence)
|
||||
return -EINVAL;
|
||||
|
||||
if (!p->adev->debug_enable_ce_cs &&
|
||||
chunk_ib->flags & AMDGPU_IB_FLAG_CE) {
|
||||
dev_err_ratelimited(p->adev->dev, "CE CS is blocked, use debug=0x400 to override\n");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
if (chunk_ib->ip_type == AMDGPU_HW_IP_GFX &&
|
||||
chunk_ib->flags & AMDGPU_IB_FLAG_PREEMPT) {
|
||||
if (chunk_ib->flags & AMDGPU_IB_FLAG_CE)
|
||||
|
|
@ -702,7 +708,7 @@ static void amdgpu_cs_get_threshold_for_moves(struct amdgpu_device *adev,
|
|||
*/
|
||||
const s64 us_upper_bound = 200000;
|
||||
|
||||
if (!adev->mm_stats.log2_max_MBps) {
|
||||
if ((!adev->mm_stats.log2_max_MBps) || !ttm_resource_manager_used(&adev->mman.vram_mgr.manager)) {
|
||||
*max_bytes = 0;
|
||||
*max_vis_bytes = 0;
|
||||
return;
|
||||
|
|
|
|||
|
|
@ -1882,6 +1882,13 @@ static bool amdgpu_device_pcie_dynamic_switching_supported(struct amdgpu_device
|
|||
|
||||
static bool amdgpu_device_aspm_support_quirk(struct amdgpu_device *adev)
|
||||
{
|
||||
/* Enabling ASPM causes randoms hangs on Tahiti and Oland on Zen4.
|
||||
* It's unclear if this is a platform-specific or GPU-specific issue.
|
||||
* Disable ASPM on SI for the time being.
|
||||
*/
|
||||
if (adev->family == AMDGPU_FAMILY_SI)
|
||||
return true;
|
||||
|
||||
#if IS_ENABLED(CONFIG_X86)
|
||||
struct cpuinfo_x86 *c = &cpu_data(0);
|
||||
|
||||
|
|
|
|||
|
|
@ -1033,7 +1033,9 @@ static uint8_t amdgpu_discovery_get_harvest_info(struct amdgpu_device *adev,
|
|||
/* Until a uniform way is figured, get mask based on hwid */
|
||||
switch (hw_id) {
|
||||
case VCN_HWID:
|
||||
harvest = ((1 << inst) & adev->vcn.inst_mask) == 0;
|
||||
/* VCN vs UVD+VCE */
|
||||
if (!amdgpu_ip_version(adev, VCE_HWIP, 0))
|
||||
harvest = ((1 << inst) & adev->vcn.inst_mask) == 0;
|
||||
break;
|
||||
case DMU_HWID:
|
||||
if (adev->harvest_ip_mask & AMD_HARVEST_IP_DMU_MASK)
|
||||
|
|
@ -2565,7 +2567,9 @@ int amdgpu_discovery_set_ip_blocks(struct amdgpu_device *adev)
|
|||
amdgpu_discovery_init(adev);
|
||||
vega10_reg_base_init(adev);
|
||||
adev->sdma.num_instances = 2;
|
||||
adev->sdma.sdma_mask = 3;
|
||||
adev->gmc.num_umc = 4;
|
||||
adev->gfx.xcc_mask = 1;
|
||||
adev->ip_versions[MMHUB_HWIP][0] = IP_VERSION(9, 0, 0);
|
||||
adev->ip_versions[ATHUB_HWIP][0] = IP_VERSION(9, 0, 0);
|
||||
adev->ip_versions[OSSSYS_HWIP][0] = IP_VERSION(4, 0, 0);
|
||||
|
|
@ -2592,7 +2596,9 @@ int amdgpu_discovery_set_ip_blocks(struct amdgpu_device *adev)
|
|||
amdgpu_discovery_init(adev);
|
||||
vega10_reg_base_init(adev);
|
||||
adev->sdma.num_instances = 2;
|
||||
adev->sdma.sdma_mask = 3;
|
||||
adev->gmc.num_umc = 4;
|
||||
adev->gfx.xcc_mask = 1;
|
||||
adev->ip_versions[MMHUB_HWIP][0] = IP_VERSION(9, 3, 0);
|
||||
adev->ip_versions[ATHUB_HWIP][0] = IP_VERSION(9, 3, 0);
|
||||
adev->ip_versions[OSSSYS_HWIP][0] = IP_VERSION(4, 0, 1);
|
||||
|
|
@ -2619,8 +2625,10 @@ int amdgpu_discovery_set_ip_blocks(struct amdgpu_device *adev)
|
|||
amdgpu_discovery_init(adev);
|
||||
vega10_reg_base_init(adev);
|
||||
adev->sdma.num_instances = 1;
|
||||
adev->sdma.sdma_mask = 1;
|
||||
adev->vcn.num_vcn_inst = 1;
|
||||
adev->gmc.num_umc = 2;
|
||||
adev->gfx.xcc_mask = 1;
|
||||
if (adev->apu_flags & AMD_APU_IS_RAVEN2) {
|
||||
adev->ip_versions[MMHUB_HWIP][0] = IP_VERSION(9, 2, 0);
|
||||
adev->ip_versions[ATHUB_HWIP][0] = IP_VERSION(9, 2, 0);
|
||||
|
|
@ -2665,7 +2673,9 @@ int amdgpu_discovery_set_ip_blocks(struct amdgpu_device *adev)
|
|||
amdgpu_discovery_init(adev);
|
||||
vega20_reg_base_init(adev);
|
||||
adev->sdma.num_instances = 2;
|
||||
adev->sdma.sdma_mask = 3;
|
||||
adev->gmc.num_umc = 8;
|
||||
adev->gfx.xcc_mask = 1;
|
||||
adev->ip_versions[MMHUB_HWIP][0] = IP_VERSION(9, 4, 0);
|
||||
adev->ip_versions[ATHUB_HWIP][0] = IP_VERSION(9, 4, 0);
|
||||
adev->ip_versions[OSSSYS_HWIP][0] = IP_VERSION(4, 2, 0);
|
||||
|
|
@ -2693,8 +2703,10 @@ int amdgpu_discovery_set_ip_blocks(struct amdgpu_device *adev)
|
|||
amdgpu_discovery_init(adev);
|
||||
arct_reg_base_init(adev);
|
||||
adev->sdma.num_instances = 8;
|
||||
adev->sdma.sdma_mask = 0xff;
|
||||
adev->vcn.num_vcn_inst = 2;
|
||||
adev->gmc.num_umc = 8;
|
||||
adev->gfx.xcc_mask = 1;
|
||||
adev->ip_versions[MMHUB_HWIP][0] = IP_VERSION(9, 4, 1);
|
||||
adev->ip_versions[ATHUB_HWIP][0] = IP_VERSION(9, 4, 1);
|
||||
adev->ip_versions[OSSSYS_HWIP][0] = IP_VERSION(4, 2, 1);
|
||||
|
|
@ -2726,8 +2738,10 @@ int amdgpu_discovery_set_ip_blocks(struct amdgpu_device *adev)
|
|||
amdgpu_discovery_init(adev);
|
||||
aldebaran_reg_base_init(adev);
|
||||
adev->sdma.num_instances = 5;
|
||||
adev->sdma.sdma_mask = 0x1f;
|
||||
adev->vcn.num_vcn_inst = 2;
|
||||
adev->gmc.num_umc = 4;
|
||||
adev->gfx.xcc_mask = 1;
|
||||
adev->ip_versions[MMHUB_HWIP][0] = IP_VERSION(9, 4, 2);
|
||||
adev->ip_versions[ATHUB_HWIP][0] = IP_VERSION(9, 4, 2);
|
||||
adev->ip_versions[OSSSYS_HWIP][0] = IP_VERSION(4, 4, 0);
|
||||
|
|
@ -2762,6 +2776,8 @@ int amdgpu_discovery_set_ip_blocks(struct amdgpu_device *adev)
|
|||
} else {
|
||||
cyan_skillfish_reg_base_init(adev);
|
||||
adev->sdma.num_instances = 2;
|
||||
adev->sdma.sdma_mask = 3;
|
||||
adev->gfx.xcc_mask = 1;
|
||||
adev->ip_versions[MMHUB_HWIP][0] = IP_VERSION(2, 0, 3);
|
||||
adev->ip_versions[ATHUB_HWIP][0] = IP_VERSION(2, 0, 3);
|
||||
adev->ip_versions[OSSSYS_HWIP][0] = IP_VERSION(5, 0, 1);
|
||||
|
|
|
|||
|
|
@ -144,7 +144,8 @@ enum AMDGPU_DEBUG_MASK {
|
|||
AMDGPU_DEBUG_DISABLE_GPU_RING_RESET = BIT(6),
|
||||
AMDGPU_DEBUG_SMU_POOL = BIT(7),
|
||||
AMDGPU_DEBUG_VM_USERPTR = BIT(8),
|
||||
AMDGPU_DEBUG_DISABLE_RAS_CE_LOG = BIT(9)
|
||||
AMDGPU_DEBUG_DISABLE_RAS_CE_LOG = BIT(9),
|
||||
AMDGPU_DEBUG_ENABLE_CE_CS = BIT(10)
|
||||
};
|
||||
|
||||
unsigned int amdgpu_vram_limit = UINT_MAX;
|
||||
|
|
@ -2289,6 +2290,11 @@ static void amdgpu_init_debug_options(struct amdgpu_device *adev)
|
|||
pr_info("debug: disable kernel logs of correctable errors\n");
|
||||
adev->debug_disable_ce_logs = true;
|
||||
}
|
||||
|
||||
if (amdgpu_debug_mask & AMDGPU_DEBUG_ENABLE_CE_CS) {
|
||||
pr_info("debug: allowing command submission to CE engine\n");
|
||||
adev->debug_enable_ce_cs = true;
|
||||
}
|
||||
}
|
||||
|
||||
static unsigned long amdgpu_fix_asic_type(struct pci_dev *pdev, unsigned long flags)
|
||||
|
|
|
|||
|
|
@ -758,11 +758,42 @@ void amdgpu_fence_driver_force_completion(struct amdgpu_ring *ring)
|
|||
* @fence: fence of the ring to signal
|
||||
*
|
||||
*/
|
||||
void amdgpu_fence_driver_guilty_force_completion(struct amdgpu_fence *fence)
|
||||
void amdgpu_fence_driver_guilty_force_completion(struct amdgpu_fence *af)
|
||||
{
|
||||
dma_fence_set_error(&fence->base, -ETIME);
|
||||
amdgpu_fence_write(fence->ring, fence->seq);
|
||||
amdgpu_fence_process(fence->ring);
|
||||
struct dma_fence *unprocessed;
|
||||
struct dma_fence __rcu **ptr;
|
||||
struct amdgpu_fence *fence;
|
||||
struct amdgpu_ring *ring = af->ring;
|
||||
unsigned long flags;
|
||||
u32 seq, last_seq;
|
||||
|
||||
last_seq = amdgpu_fence_read(ring) & ring->fence_drv.num_fences_mask;
|
||||
seq = ring->fence_drv.sync_seq & ring->fence_drv.num_fences_mask;
|
||||
|
||||
/* mark all fences from the guilty context with an error */
|
||||
spin_lock_irqsave(&ring->fence_drv.lock, flags);
|
||||
do {
|
||||
last_seq++;
|
||||
last_seq &= ring->fence_drv.num_fences_mask;
|
||||
|
||||
ptr = &ring->fence_drv.fences[last_seq];
|
||||
rcu_read_lock();
|
||||
unprocessed = rcu_dereference(*ptr);
|
||||
|
||||
if (unprocessed && !dma_fence_is_signaled_locked(unprocessed)) {
|
||||
fence = container_of(unprocessed, struct amdgpu_fence, base);
|
||||
|
||||
if (fence == af)
|
||||
dma_fence_set_error(&fence->base, -ETIME);
|
||||
else if (fence->context == af->context)
|
||||
dma_fence_set_error(&fence->base, -ECANCELED);
|
||||
}
|
||||
rcu_read_unlock();
|
||||
} while (last_seq != seq);
|
||||
spin_unlock_irqrestore(&ring->fence_drv.lock, flags);
|
||||
/* signal the guilty fence */
|
||||
amdgpu_fence_write(ring, af->seq);
|
||||
amdgpu_fence_process(ring);
|
||||
}
|
||||
|
||||
void amdgpu_fence_save_wptr(struct dma_fence *fence)
|
||||
|
|
@ -790,14 +821,19 @@ void amdgpu_ring_backup_unprocessed_commands(struct amdgpu_ring *ring,
|
|||
struct dma_fence *unprocessed;
|
||||
struct dma_fence __rcu **ptr;
|
||||
struct amdgpu_fence *fence;
|
||||
u64 wptr, i, seqno;
|
||||
u64 wptr;
|
||||
u32 seq, last_seq;
|
||||
|
||||
seqno = amdgpu_fence_read(ring);
|
||||
last_seq = amdgpu_fence_read(ring) & ring->fence_drv.num_fences_mask;
|
||||
seq = ring->fence_drv.sync_seq & ring->fence_drv.num_fences_mask;
|
||||
wptr = ring->fence_drv.signalled_wptr;
|
||||
ring->ring_backup_entries_to_copy = 0;
|
||||
|
||||
for (i = seqno + 1; i <= ring->fence_drv.sync_seq; ++i) {
|
||||
ptr = &ring->fence_drv.fences[i & ring->fence_drv.num_fences_mask];
|
||||
do {
|
||||
last_seq++;
|
||||
last_seq &= ring->fence_drv.num_fences_mask;
|
||||
|
||||
ptr = &ring->fence_drv.fences[last_seq];
|
||||
rcu_read_lock();
|
||||
unprocessed = rcu_dereference(*ptr);
|
||||
|
||||
|
|
@ -813,7 +849,7 @@ void amdgpu_ring_backup_unprocessed_commands(struct amdgpu_ring *ring,
|
|||
wptr = fence->wptr;
|
||||
}
|
||||
rcu_read_unlock();
|
||||
}
|
||||
} while (last_seq != seq);
|
||||
}
|
||||
|
||||
/*
|
||||
|
|
|
|||
|
|
@ -371,7 +371,7 @@ static int amdgpu_debugfs_jpeg_sched_mask_set(void *data, u64 val)
|
|||
for (i = 0; i < adev->jpeg.num_jpeg_inst; ++i) {
|
||||
for (j = 0; j < adev->jpeg.num_jpeg_rings; ++j) {
|
||||
ring = &adev->jpeg.inst[i].ring_dec[j];
|
||||
if (val & (BIT_ULL(1) << ((i * adev->jpeg.num_jpeg_rings) + j)))
|
||||
if (val & (BIT_ULL((i * adev->jpeg.num_jpeg_rings) + j)))
|
||||
ring->sched.ready = true;
|
||||
else
|
||||
ring->sched.ready = false;
|
||||
|
|
|
|||
|
|
@ -758,7 +758,8 @@ int amdgpu_info_ioctl(struct drm_device *dev, void *data, struct drm_file *filp)
|
|||
ui64 = atomic64_read(&adev->num_vram_cpu_page_faults);
|
||||
return copy_to_user(out, &ui64, min(size, 8u)) ? -EFAULT : 0;
|
||||
case AMDGPU_INFO_VRAM_USAGE:
|
||||
ui64 = ttm_resource_manager_usage(&adev->mman.vram_mgr.manager);
|
||||
ui64 = ttm_resource_manager_used(&adev->mman.vram_mgr.manager) ?
|
||||
ttm_resource_manager_usage(&adev->mman.vram_mgr.manager) : 0;
|
||||
return copy_to_user(out, &ui64, min(size, 8u)) ? -EFAULT : 0;
|
||||
case AMDGPU_INFO_VIS_VRAM_USAGE:
|
||||
ui64 = amdgpu_vram_mgr_vis_usage(&adev->mman.vram_mgr);
|
||||
|
|
@ -804,8 +805,8 @@ int amdgpu_info_ioctl(struct drm_device *dev, void *data, struct drm_file *filp)
|
|||
mem.vram.usable_heap_size = adev->gmc.real_vram_size -
|
||||
atomic64_read(&adev->vram_pin_size) -
|
||||
AMDGPU_VM_RESERVED_VRAM;
|
||||
mem.vram.heap_usage =
|
||||
ttm_resource_manager_usage(vram_man);
|
||||
mem.vram.heap_usage = ttm_resource_manager_used(&adev->mman.vram_mgr.manager) ?
|
||||
ttm_resource_manager_usage(vram_man) : 0;
|
||||
mem.vram.max_allocation = mem.vram.usable_heap_size * 3 / 4;
|
||||
|
||||
mem.cpu_accessible_vram.total_heap_size =
|
||||
|
|
|
|||
|
|
@ -409,7 +409,7 @@ int amdgpu_mes_detect_and_reset_hung_queues(struct amdgpu_device *adev,
|
|||
return -EINVAL;
|
||||
|
||||
/* Clear the doorbell array before detection */
|
||||
memset(adev->mes.hung_queue_db_array_cpu_addr, 0,
|
||||
memset(adev->mes.hung_queue_db_array_cpu_addr, AMDGPU_MES_INVALID_DB_OFFSET,
|
||||
adev->mes.hung_queue_db_array_size * sizeof(u32));
|
||||
input.queue_type = queue_type;
|
||||
input.detect_only = detect_only;
|
||||
|
|
@ -420,12 +420,17 @@ int amdgpu_mes_detect_and_reset_hung_queues(struct amdgpu_device *adev,
|
|||
dev_err(adev->dev, "failed to detect and reset\n");
|
||||
} else {
|
||||
*hung_db_num = 0;
|
||||
for (i = 0; i < adev->mes.hung_queue_db_array_size; i++) {
|
||||
for (i = 0; i < adev->mes.hung_queue_hqd_info_offset; i++) {
|
||||
if (db_array[i] != AMDGPU_MES_INVALID_DB_OFFSET) {
|
||||
hung_db_array[i] = db_array[i];
|
||||
*hung_db_num += 1;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* TODO: return HQD info for MES scheduled user compute queue reset cases
|
||||
* stored in hung_db_array hqd info offset to full array size
|
||||
*/
|
||||
}
|
||||
|
||||
return r;
|
||||
|
|
@ -686,14 +691,11 @@ int amdgpu_mes_init_microcode(struct amdgpu_device *adev, int pipe)
|
|||
bool amdgpu_mes_suspend_resume_all_supported(struct amdgpu_device *adev)
|
||||
{
|
||||
uint32_t mes_rev = adev->mes.sched_version & AMDGPU_MES_VERSION_MASK;
|
||||
bool is_supported = false;
|
||||
|
||||
if (amdgpu_ip_version(adev, GC_HWIP, 0) >= IP_VERSION(11, 0, 0) &&
|
||||
amdgpu_ip_version(adev, GC_HWIP, 0) < IP_VERSION(12, 0, 0) &&
|
||||
mes_rev >= 0x63)
|
||||
is_supported = true;
|
||||
|
||||
return is_supported;
|
||||
return ((amdgpu_ip_version(adev, GC_HWIP, 0) >= IP_VERSION(11, 0, 0) &&
|
||||
amdgpu_ip_version(adev, GC_HWIP, 0) < IP_VERSION(12, 0, 0) &&
|
||||
mes_rev >= 0x63) ||
|
||||
amdgpu_ip_version(adev, GC_HWIP, 0) >= IP_VERSION(12, 0, 0));
|
||||
}
|
||||
|
||||
/* Fix me -- node_id is used to identify the correct MES instances in the future */
|
||||
|
|
|
|||
|
|
@ -149,6 +149,7 @@ struct amdgpu_mes {
|
|||
void *resource_1_addr[AMDGPU_MAX_MES_PIPES];
|
||||
|
||||
int hung_queue_db_array_size;
|
||||
int hung_queue_hqd_info_offset;
|
||||
struct amdgpu_bo *hung_queue_db_array_gpu_obj;
|
||||
uint64_t hung_queue_db_array_gpu_addr;
|
||||
void *hung_queue_db_array_cpu_addr;
|
||||
|
|
|
|||
|
|
@ -811,7 +811,7 @@ int amdgpu_ring_reset_helper_end(struct amdgpu_ring *ring,
|
|||
if (r)
|
||||
return r;
|
||||
|
||||
/* signal the fence of the bad job */
|
||||
/* signal the guilty fence and set an error on all fences from the context */
|
||||
if (guilty_fence)
|
||||
amdgpu_fence_driver_guilty_force_completion(guilty_fence);
|
||||
/* Re-emit the non-guilty commands */
|
||||
|
|
|
|||
|
|
@ -155,7 +155,7 @@ extern const struct drm_sched_backend_ops amdgpu_sched_ops;
|
|||
void amdgpu_fence_driver_clear_job_fences(struct amdgpu_ring *ring);
|
||||
void amdgpu_fence_driver_set_error(struct amdgpu_ring *ring, int error);
|
||||
void amdgpu_fence_driver_force_completion(struct amdgpu_ring *ring);
|
||||
void amdgpu_fence_driver_guilty_force_completion(struct amdgpu_fence *fence);
|
||||
void amdgpu_fence_driver_guilty_force_completion(struct amdgpu_fence *af);
|
||||
void amdgpu_fence_save_wptr(struct dma_fence *fence);
|
||||
|
||||
int amdgpu_fence_driver_init_ring(struct amdgpu_ring *ring);
|
||||
|
|
|
|||
|
|
@ -598,8 +598,8 @@ static int amdgpu_virt_write_vf2pf_data(struct amdgpu_device *adev)
|
|||
vf2pf_info->driver_cert = 0;
|
||||
vf2pf_info->os_info.all = 0;
|
||||
|
||||
vf2pf_info->fb_usage =
|
||||
ttm_resource_manager_usage(&adev->mman.vram_mgr.manager) >> 20;
|
||||
vf2pf_info->fb_usage = ttm_resource_manager_used(&adev->mman.vram_mgr.manager) ?
|
||||
ttm_resource_manager_usage(&adev->mman.vram_mgr.manager) >> 20 : 0;
|
||||
vf2pf_info->fb_vis_usage =
|
||||
amdgpu_vram_mgr_vis_usage(&adev->mman.vram_mgr) >> 20;
|
||||
vf2pf_info->fb_size = adev->gmc.real_vram_size >> 20;
|
||||
|
|
|
|||
|
|
@ -234,6 +234,9 @@ static umode_t amdgpu_vram_attrs_is_visible(struct kobject *kobj,
|
|||
!adev->gmc.vram_vendor)
|
||||
return 0;
|
||||
|
||||
if (!ttm_resource_manager_used(&adev->mman.vram_mgr.manager))
|
||||
return 0;
|
||||
|
||||
return attr->mode;
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -5862,8 +5862,6 @@ static void gfx_v11_0_ring_emit_ib_gfx(struct amdgpu_ring *ring,
|
|||
unsigned vmid = AMDGPU_JOB_GET_VMID(job);
|
||||
u32 header, control = 0;
|
||||
|
||||
BUG_ON(ib->flags & AMDGPU_IB_FLAG_CE);
|
||||
|
||||
header = PACKET3(PACKET3_INDIRECT_BUFFER, 2);
|
||||
|
||||
control |= ib->length_dw | (vmid << 24);
|
||||
|
|
|
|||
|
|
@ -4419,8 +4419,6 @@ static void gfx_v12_0_ring_emit_ib_gfx(struct amdgpu_ring *ring,
|
|||
unsigned vmid = AMDGPU_JOB_GET_VMID(job);
|
||||
u32 header, control = 0;
|
||||
|
||||
BUG_ON(ib->flags & AMDGPU_IB_FLAG_CE);
|
||||
|
||||
header = PACKET3(PACKET3_INDIRECT_BUFFER, 2);
|
||||
|
||||
control |= ib->length_dw | (vmid << 24);
|
||||
|
|
|
|||
|
|
@ -1068,7 +1068,7 @@ static int gmc_v7_0_sw_init(struct amdgpu_ip_block *ip_block)
|
|||
GFP_KERNEL);
|
||||
if (!adev->gmc.vm_fault_info)
|
||||
return -ENOMEM;
|
||||
atomic_set(&adev->gmc.vm_fault_info_updated, 0);
|
||||
atomic_set_release(&adev->gmc.vm_fault_info_updated, 0);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
|
@ -1290,7 +1290,7 @@ static int gmc_v7_0_process_interrupt(struct amdgpu_device *adev,
|
|||
vmid = REG_GET_FIELD(status, VM_CONTEXT1_PROTECTION_FAULT_STATUS,
|
||||
VMID);
|
||||
if (amdgpu_amdkfd_is_kfd_vmid(adev, vmid)
|
||||
&& !atomic_read(&adev->gmc.vm_fault_info_updated)) {
|
||||
&& !atomic_read_acquire(&adev->gmc.vm_fault_info_updated)) {
|
||||
struct kfd_vm_fault_info *info = adev->gmc.vm_fault_info;
|
||||
u32 protections = REG_GET_FIELD(status,
|
||||
VM_CONTEXT1_PROTECTION_FAULT_STATUS,
|
||||
|
|
@ -1306,8 +1306,7 @@ static int gmc_v7_0_process_interrupt(struct amdgpu_device *adev,
|
|||
info->prot_read = protections & 0x8 ? true : false;
|
||||
info->prot_write = protections & 0x10 ? true : false;
|
||||
info->prot_exec = protections & 0x20 ? true : false;
|
||||
mb();
|
||||
atomic_set(&adev->gmc.vm_fault_info_updated, 1);
|
||||
atomic_set_release(&adev->gmc.vm_fault_info_updated, 1);
|
||||
}
|
||||
|
||||
return 0;
|
||||
|
|
|
|||
|
|
@ -1183,7 +1183,7 @@ static int gmc_v8_0_sw_init(struct amdgpu_ip_block *ip_block)
|
|||
GFP_KERNEL);
|
||||
if (!adev->gmc.vm_fault_info)
|
||||
return -ENOMEM;
|
||||
atomic_set(&adev->gmc.vm_fault_info_updated, 0);
|
||||
atomic_set_release(&adev->gmc.vm_fault_info_updated, 0);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
|
@ -1478,7 +1478,7 @@ static int gmc_v8_0_process_interrupt(struct amdgpu_device *adev,
|
|||
vmid = REG_GET_FIELD(status, VM_CONTEXT1_PROTECTION_FAULT_STATUS,
|
||||
VMID);
|
||||
if (amdgpu_amdkfd_is_kfd_vmid(adev, vmid)
|
||||
&& !atomic_read(&adev->gmc.vm_fault_info_updated)) {
|
||||
&& !atomic_read_acquire(&adev->gmc.vm_fault_info_updated)) {
|
||||
struct kfd_vm_fault_info *info = adev->gmc.vm_fault_info;
|
||||
u32 protections = REG_GET_FIELD(status,
|
||||
VM_CONTEXT1_PROTECTION_FAULT_STATUS,
|
||||
|
|
@ -1494,8 +1494,7 @@ static int gmc_v8_0_process_interrupt(struct amdgpu_device *adev,
|
|||
info->prot_read = protections & 0x8 ? true : false;
|
||||
info->prot_write = protections & 0x10 ? true : false;
|
||||
info->prot_exec = protections & 0x20 ? true : false;
|
||||
mb();
|
||||
atomic_set(&adev->gmc.vm_fault_info_updated, 1);
|
||||
atomic_set_release(&adev->gmc.vm_fault_info_updated, 1);
|
||||
}
|
||||
|
||||
return 0;
|
||||
|
|
|
|||
|
|
@ -208,10 +208,10 @@ static int mes_userq_detect_and_reset(struct amdgpu_device *adev,
|
|||
struct amdgpu_userq_mgr *uqm, *tmp;
|
||||
unsigned int hung_db_num = 0;
|
||||
int queue_id, r, i;
|
||||
u32 db_array[4];
|
||||
u32 db_array[8];
|
||||
|
||||
if (db_array_size > 4) {
|
||||
dev_err(adev->dev, "DB array size (%d vs 4) too small\n",
|
||||
if (db_array_size > 8) {
|
||||
dev_err(adev->dev, "DB array size (%d vs 8) too small\n",
|
||||
db_array_size);
|
||||
return -EINVAL;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -66,7 +66,8 @@ static int mes_v11_0_kiq_hw_fini(struct amdgpu_device *adev);
|
|||
#define GFX_MES_DRAM_SIZE 0x80000
|
||||
#define MES11_HW_RESOURCE_1_SIZE (128 * AMDGPU_GPU_PAGE_SIZE)
|
||||
|
||||
#define MES11_HUNG_DB_OFFSET_ARRAY_SIZE 4
|
||||
#define MES11_HUNG_DB_OFFSET_ARRAY_SIZE 8 /* [0:3] = db offset, [4:7] = hqd info */
|
||||
#define MES11_HUNG_HQD_INFO_OFFSET 4
|
||||
|
||||
static void mes_v11_0_ring_set_wptr(struct amdgpu_ring *ring)
|
||||
{
|
||||
|
|
@ -1720,8 +1721,9 @@ static int mes_v11_0_early_init(struct amdgpu_ip_block *ip_block)
|
|||
struct amdgpu_device *adev = ip_block->adev;
|
||||
int pipe, r;
|
||||
|
||||
adev->mes.hung_queue_db_array_size =
|
||||
MES11_HUNG_DB_OFFSET_ARRAY_SIZE;
|
||||
adev->mes.hung_queue_db_array_size = MES11_HUNG_DB_OFFSET_ARRAY_SIZE;
|
||||
adev->mes.hung_queue_hqd_info_offset = MES11_HUNG_HQD_INFO_OFFSET;
|
||||
|
||||
for (pipe = 0; pipe < AMDGPU_MAX_MES_PIPES; pipe++) {
|
||||
if (!adev->enable_mes_kiq && pipe == AMDGPU_MES_KIQ_PIPE)
|
||||
continue;
|
||||
|
|
|
|||
|
|
@ -47,7 +47,8 @@ static int mes_v12_0_kiq_hw_fini(struct amdgpu_device *adev);
|
|||
|
||||
#define MES_EOP_SIZE 2048
|
||||
|
||||
#define MES12_HUNG_DB_OFFSET_ARRAY_SIZE 4
|
||||
#define MES12_HUNG_DB_OFFSET_ARRAY_SIZE 8 /* [0:3] = db offset [4:7] hqd info */
|
||||
#define MES12_HUNG_HQD_INFO_OFFSET 4
|
||||
|
||||
static void mes_v12_0_ring_set_wptr(struct amdgpu_ring *ring)
|
||||
{
|
||||
|
|
@ -228,7 +229,12 @@ static int mes_v12_0_submit_pkt_and_poll_completion(struct amdgpu_mes *mes,
|
|||
pipe, x_pkt->header.opcode);
|
||||
|
||||
r = amdgpu_fence_wait_polling(ring, seq, timeout);
|
||||
if (r < 1 || !*status_ptr) {
|
||||
|
||||
/*
|
||||
* status_ptr[31:0] == 0 (fail) or status_ptr[63:0] == 1 (success).
|
||||
* If status_ptr[31:0] == 0 then status_ptr[63:32] will have debug error information.
|
||||
*/
|
||||
if (r < 1 || !(lower_32_bits(*status_ptr))) {
|
||||
|
||||
if (misc_op_str)
|
||||
dev_err(adev->dev, "MES(%d) failed to respond to msg=%s (%s)\n",
|
||||
|
|
@ -1899,8 +1905,9 @@ static int mes_v12_0_early_init(struct amdgpu_ip_block *ip_block)
|
|||
struct amdgpu_device *adev = ip_block->adev;
|
||||
int pipe, r;
|
||||
|
||||
adev->mes.hung_queue_db_array_size =
|
||||
MES12_HUNG_DB_OFFSET_ARRAY_SIZE;
|
||||
adev->mes.hung_queue_db_array_size = MES12_HUNG_DB_OFFSET_ARRAY_SIZE;
|
||||
adev->mes.hung_queue_hqd_info_offset = MES12_HUNG_HQD_INFO_OFFSET;
|
||||
|
||||
for (pipe = 0; pipe < AMDGPU_MAX_MES_PIPES; pipe++) {
|
||||
r = amdgpu_mes_init_microcode(adev, pipe);
|
||||
if (r)
|
||||
|
|
|
|||
|
|
@ -1209,6 +1209,15 @@ static int evict_process_queues_cpsch(struct device_queue_manager *dqm,
|
|||
pr_debug_ratelimited("Evicting process pid %d queues\n",
|
||||
pdd->process->lead_thread->pid);
|
||||
|
||||
if (dqm->dev->kfd->shared_resources.enable_mes) {
|
||||
pdd->last_evict_timestamp = get_jiffies_64();
|
||||
retval = suspend_all_queues_mes(dqm);
|
||||
if (retval) {
|
||||
dev_err(dev, "Suspending all queues failed");
|
||||
goto out;
|
||||
}
|
||||
}
|
||||
|
||||
/* Mark all queues as evicted. Deactivate all active queues on
|
||||
* the qpd.
|
||||
*/
|
||||
|
|
@ -1221,23 +1230,27 @@ static int evict_process_queues_cpsch(struct device_queue_manager *dqm,
|
|||
decrement_queue_count(dqm, qpd, q);
|
||||
|
||||
if (dqm->dev->kfd->shared_resources.enable_mes) {
|
||||
int err;
|
||||
|
||||
err = remove_queue_mes(dqm, q, qpd);
|
||||
if (err) {
|
||||
retval = remove_queue_mes(dqm, q, qpd);
|
||||
if (retval) {
|
||||
dev_err(dev, "Failed to evict queue %d\n",
|
||||
q->properties.queue_id);
|
||||
retval = err;
|
||||
goto out;
|
||||
}
|
||||
}
|
||||
}
|
||||
pdd->last_evict_timestamp = get_jiffies_64();
|
||||
if (!dqm->dev->kfd->shared_resources.enable_mes)
|
||||
|
||||
if (!dqm->dev->kfd->shared_resources.enable_mes) {
|
||||
pdd->last_evict_timestamp = get_jiffies_64();
|
||||
retval = execute_queues_cpsch(dqm,
|
||||
qpd->is_debug ?
|
||||
KFD_UNMAP_QUEUES_FILTER_ALL_QUEUES :
|
||||
KFD_UNMAP_QUEUES_FILTER_DYNAMIC_QUEUES, 0,
|
||||
USE_DEFAULT_GRACE_PERIOD);
|
||||
} else {
|
||||
retval = resume_all_queues_mes(dqm);
|
||||
if (retval)
|
||||
dev_err(dev, "Resuming all queues failed");
|
||||
}
|
||||
|
||||
out:
|
||||
dqm_unlock(dqm);
|
||||
|
|
@ -3098,61 +3111,17 @@ int kfd_dqm_suspend_bad_queue_mes(struct kfd_node *knode, u32 pasid, u32 doorbel
|
|||
return ret;
|
||||
}
|
||||
|
||||
static int kfd_dqm_evict_pasid_mes(struct device_queue_manager *dqm,
|
||||
struct qcm_process_device *qpd)
|
||||
{
|
||||
struct device *dev = dqm->dev->adev->dev;
|
||||
int ret = 0;
|
||||
|
||||
/* Check if process is already evicted */
|
||||
dqm_lock(dqm);
|
||||
if (qpd->evicted) {
|
||||
/* Increment the evicted count to make sure the
|
||||
* process stays evicted before its terminated.
|
||||
*/
|
||||
qpd->evicted++;
|
||||
dqm_unlock(dqm);
|
||||
goto out;
|
||||
}
|
||||
dqm_unlock(dqm);
|
||||
|
||||
ret = suspend_all_queues_mes(dqm);
|
||||
if (ret) {
|
||||
dev_err(dev, "Suspending all queues failed");
|
||||
goto out;
|
||||
}
|
||||
|
||||
ret = dqm->ops.evict_process_queues(dqm, qpd);
|
||||
if (ret) {
|
||||
dev_err(dev, "Evicting process queues failed");
|
||||
goto out;
|
||||
}
|
||||
|
||||
ret = resume_all_queues_mes(dqm);
|
||||
if (ret)
|
||||
dev_err(dev, "Resuming all queues failed");
|
||||
|
||||
out:
|
||||
return ret;
|
||||
}
|
||||
|
||||
int kfd_evict_process_device(struct kfd_process_device *pdd)
|
||||
{
|
||||
struct device_queue_manager *dqm;
|
||||
struct kfd_process *p;
|
||||
int ret = 0;
|
||||
|
||||
p = pdd->process;
|
||||
dqm = pdd->dev->dqm;
|
||||
|
||||
WARN(debug_evictions, "Evicting pid %d", p->lead_thread->pid);
|
||||
|
||||
if (dqm->dev->kfd->shared_resources.enable_mes)
|
||||
ret = kfd_dqm_evict_pasid_mes(dqm, &pdd->qpd);
|
||||
else
|
||||
ret = dqm->ops.evict_process_queues(dqm, &pdd->qpd);
|
||||
|
||||
return ret;
|
||||
return dqm->ops.evict_process_queues(dqm, &pdd->qpd);
|
||||
}
|
||||
|
||||
int reserve_debug_trap_vmid(struct device_queue_manager *dqm,
|
||||
|
|
|
|||
|
|
@ -2085,8 +2085,6 @@ static int amdgpu_dm_init(struct amdgpu_device *adev)
|
|||
|
||||
dc_hardware_init(adev->dm.dc);
|
||||
|
||||
adev->dm.restore_backlight = true;
|
||||
|
||||
adev->dm.hpd_rx_offload_wq = hpd_rx_irq_create_workqueue(adev);
|
||||
if (!adev->dm.hpd_rx_offload_wq) {
|
||||
drm_err(adev_to_drm(adev), "failed to create hpd rx offload workqueue.\n");
|
||||
|
|
@ -3442,7 +3440,6 @@ static int dm_resume(struct amdgpu_ip_block *ip_block)
|
|||
dc_set_power_state(dm->dc, DC_ACPI_CM_POWER_STATE_D0);
|
||||
|
||||
dc_resume(dm->dc);
|
||||
adev->dm.restore_backlight = true;
|
||||
|
||||
amdgpu_dm_irq_resume_early(adev);
|
||||
|
||||
|
|
@ -9969,6 +9966,7 @@ static void amdgpu_dm_commit_streams(struct drm_atomic_state *state,
|
|||
bool mode_set_reset_required = false;
|
||||
u32 i;
|
||||
struct dc_commit_streams_params params = {dc_state->streams, dc_state->stream_count};
|
||||
bool set_backlight_level = false;
|
||||
|
||||
/* Disable writeback */
|
||||
for_each_old_connector_in_state(state, connector, old_con_state, i) {
|
||||
|
|
@ -10088,6 +10086,7 @@ static void amdgpu_dm_commit_streams(struct drm_atomic_state *state,
|
|||
acrtc->hw_mode = new_crtc_state->mode;
|
||||
crtc->hwmode = new_crtc_state->mode;
|
||||
mode_set_reset_required = true;
|
||||
set_backlight_level = true;
|
||||
} else if (modereset_required(new_crtc_state)) {
|
||||
drm_dbg_atomic(dev,
|
||||
"Atomic commit: RESET. crtc id %d:[%p]\n",
|
||||
|
|
@ -10144,16 +10143,13 @@ static void amdgpu_dm_commit_streams(struct drm_atomic_state *state,
|
|||
* to fix a flicker issue.
|
||||
* It will cause the dm->actual_brightness is not the current panel brightness
|
||||
* level. (the dm->brightness is the correct panel level)
|
||||
* So we set the backlight level with dm->brightness value after initial
|
||||
* set mode. Use restore_backlight flag to avoid setting backlight level
|
||||
* for every subsequent mode set.
|
||||
* So we set the backlight level with dm->brightness value after set mode
|
||||
*/
|
||||
if (dm->restore_backlight) {
|
||||
if (set_backlight_level) {
|
||||
for (i = 0; i < dm->num_of_edps; i++) {
|
||||
if (dm->backlight_dev[i])
|
||||
amdgpu_dm_backlight_set_level(dm, i, dm->brightness[i]);
|
||||
}
|
||||
dm->restore_backlight = false;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -630,13 +630,6 @@ struct amdgpu_display_manager {
|
|||
*/
|
||||
u32 actual_brightness[AMDGPU_DM_MAX_NUM_EDP];
|
||||
|
||||
/**
|
||||
* @restore_backlight:
|
||||
*
|
||||
* Flag to indicate whether to restore backlight after modeset.
|
||||
*/
|
||||
bool restore_backlight;
|
||||
|
||||
/**
|
||||
* @aux_hpd_discon_quirk:
|
||||
*
|
||||
|
|
|
|||
|
|
@ -3500,6 +3500,11 @@ static void si_apply_state_adjust_rules(struct amdgpu_device *adev,
|
|||
* for these GPUs to calculate bandwidth requirements.
|
||||
*/
|
||||
if (high_pixelclock_count) {
|
||||
/* Work around flickering lines at the bottom edge
|
||||
* of the screen when using a single 4K 60Hz monitor.
|
||||
*/
|
||||
disable_mclk_switching = true;
|
||||
|
||||
/* On Oland, we observe some flickering when two 4K 60Hz
|
||||
* displays are connected, possibly because voltage is too low.
|
||||
* Raise the voltage by requiring a higher SCLK.
|
||||
|
|
|
|||
|
|
@ -5444,8 +5444,7 @@ static int smu7_get_thermal_temperature_range(struct pp_hwmgr *hwmgr,
|
|||
thermal_data->max = table_info->cac_dtp_table->usSoftwareShutdownTemp *
|
||||
PP_TEMPERATURE_UNITS_PER_CENTIGRADES;
|
||||
else if (hwmgr->pp_table_version == PP_TABLE_V0)
|
||||
thermal_data->max = data->thermal_temp_setting.temperature_shutdown *
|
||||
PP_TEMPERATURE_UNITS_PER_CENTIGRADES;
|
||||
thermal_data->max = data->thermal_temp_setting.temperature_shutdown;
|
||||
|
||||
thermal_data->sw_ctf_threshold = thermal_data->max;
|
||||
|
||||
|
|
|
|||
|
|
@ -1555,27 +1555,6 @@ struct drm_amdgpu_info_hw_ip {
|
|||
__u32 userq_num_slots;
|
||||
};
|
||||
|
||||
/* GFX metadata BO sizes and alignment info (in bytes) */
|
||||
struct drm_amdgpu_info_uq_fw_areas_gfx {
|
||||
/* shadow area size */
|
||||
__u32 shadow_size;
|
||||
/* shadow area base virtual mem alignment */
|
||||
__u32 shadow_alignment;
|
||||
/* context save area size */
|
||||
__u32 csa_size;
|
||||
/* context save area base virtual mem alignment */
|
||||
__u32 csa_alignment;
|
||||
};
|
||||
|
||||
/* IP specific fw related information used in the
|
||||
* subquery AMDGPU_INFO_UQ_FW_AREAS
|
||||
*/
|
||||
struct drm_amdgpu_info_uq_fw_areas {
|
||||
union {
|
||||
struct drm_amdgpu_info_uq_fw_areas_gfx gfx;
|
||||
};
|
||||
};
|
||||
|
||||
struct drm_amdgpu_info_num_handles {
|
||||
/** Max handles as supported by firmware for UVD */
|
||||
__u32 uvd_max_handles;
|
||||
|
|
|
|||
Loading…
Reference in New Issue
Block a user