Skip to content

Commit dac0b8c

Browse files
committed
Merge tag 'drm-fixes-2026-07-04' of https://gitlab.freedesktop.org/drm/kernel
Pull drm fixes from Dave Airlie: "Weekly fixes for drm. This is large for rc2 but it's just a lot of small fixes across a bunch of drivers, xe, amdgpu as usual, plus some sashiko-inspired fixes for panthor, and some dma-fence updates. core: - kernel doc fix - include types.h in drm_ras.h dma-fence: - fix NULL ptr dereference - use correct callback - make dma_fence_dedup_array more robust dp: - handle torn down topology gracefully - fix kernel doc i915: - Input validation fixes for BIOS and EDID - Fix HDCP code buffer overflow and seq_num_v monotonic increase check - Fix near-NULL deref in i915_active during GFP_ATOMIC exhaustion xe: - Wedge from the timeout handler only after releasing the queue - Fix a NULL pointer dereference - Remove redundant exec_queue_suspended - RTP / OA whitelist fixes - Return error on non-migratable faults requiring devmem - Skip FORCE_WC and vm_bound check for external dma-bufs - Hold notifier lock for write on inject test path - Drop bogus static from finish in force_invalidate - Fix double-free of managed BO in error path - Don't attempt to process FAST_REQ or EVENT relays - Fix NPD in bo_meminfo - Prevent invalid cursor access for purged BOs - Fix offset alignment for MERT WHITELST_OA_MERT_MMIO_TRG amdgpu: - Soc24 aborted suspend fix - Drop unecessary BUG() and BUG_ON() from error paths - SCPM fix - Power reporting fix - DCE HDR fix - UVD boundary checks - VCN boundary checks - VCE boundary checks - DCN 4.2 fixes - Large stack allocation fixes - Fix aperture mapping leak - UserQ fixes - Ignore_damage_clips fix - ACP fixes - DC boundary checks - GPUVM fixes - JPEG idle check fixes - Userptr fix - GC 11.7 updates - Non-4K page fix - SMU 13 fixes - DP alt mode fix amdkfd: - Boundary checks - CRIU fixes amdxdna: - fix device removal issues - fix use after free in debug BO imagination: - fix double call to scheduler fini - fix ioctl return values - fix user array stride virtio: - handle EDIDs better panthor: - irq safe fence lock fix - reset work fix - fix invalid pointer - fix iomem access in suspended state - sched resume fix - unplug suspend fix - drop needless check - eviction leak fix - bail on group start/resume fix - keep irqs masked malidp: - use clock bulk API komeda: - clock prepare fixes" * tag 'drm-fixes-2026-07-04' of https://gitlab.freedesktop.org/drm/kernel: (105 commits) drm/xe/oa: Fix offset alignment for MERT WHITELIST_OA_MERT_MMIO_TRG drm/xe/pt: prevent invalid cursor access for purged BOs drm/xe: fix NPD in bo_meminfo() drm/xe/pf: Don't attempt to process FAST_REQ or EVENT relays drm/xe/hw_engine: Fix double-free of managed BO in error path drm/xe/userptr: Drop bogus static from finish in force_invalidate drm/xe/userptr: Hold notifier_lock for write on inject test path drm/xe/display: skip FORCE_WC and vm_bound check for external dma-bufs drm/xe: Return error on non-migratable faults requiring devmem drm/xe/rtp: Ensure locking/ref counting for OA whitelists drm/xe/oa: (De-)whitelist OA registers on OA stream open/release drm/xe/rtp: (De-)whitelist OA registers for all hwe's for a gt drm/xe/rtp: Toggle 'deny' bit to (de-)whitelist OA regs drm/xe/rtp: Save OA nonpriv registers to register save/restore lists drm/xe/rtp: Generalize whitelist_apply_to_hwe drm/xe/rtp: Keep track of non-OA nonpriv slots drm/xe/rtp: Maintain OA whitelists separately drm/xe/rtp: Fix build error with clang < 21 and non-const initializers drm/imagination: Fix user array stride in pvr_set_uobj_array() drm/imagination: Fix returned size for DRM_IOCTL_PVR_DEV_QUERY ...
2 parents e6174e9 + acd7c71 commit dac0b8c

115 files changed

Lines changed: 1227 additions & 642 deletions

File tree

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

drivers/accel/amdxdna/aie2_ctx.c

Lines changed: 50 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -59,6 +59,18 @@ static bool aie2_tdr_detect(struct amdxdna_dev *xdna)
5959
return false;
6060
}
6161

62+
static void aie2_cmd_release(struct kref *ref)
63+
{
64+
struct amdxdna_drv_cmd *drv_cmd = container_of(ref, struct amdxdna_drv_cmd, refcnt);
65+
66+
kfree(drv_cmd);
67+
}
68+
69+
static void aie2_cmd_put(struct amdxdna_drv_cmd *drv_cmd)
70+
{
71+
kref_put(&drv_cmd->refcnt, aie2_cmd_release);
72+
}
73+
6274
static void aie2_job_release(struct kref *ref)
6375
{
6476
struct amdxdna_sched_job *job;
@@ -70,6 +82,8 @@ static void aie2_job_release(struct kref *ref)
7082
wake_up(&job->hwctx->priv->job_free_wq);
7183
if (job->out_fence)
7284
dma_fence_put(job->out_fence);
85+
if (job->drv_cmd)
86+
aie2_cmd_put(job->drv_cmd);
7387
kfree(job->aie2_job_health);
7488
kfree(job);
7589
}
@@ -901,7 +915,7 @@ static int aie2_hwctx_cfg_debug_bo(struct amdxdna_hwctx *hwctx, u32 bo_hdl,
901915
{
902916
struct amdxdna_client *client = hwctx->client;
903917
struct amdxdna_dev *xdna = client->xdna;
904-
struct amdxdna_drv_cmd cmd = { 0 };
918+
struct amdxdna_drv_cmd *cmd;
905919
struct amdxdna_gem_obj *abo;
906920
u64 seq;
907921
int ret;
@@ -912,32 +926,39 @@ static int aie2_hwctx_cfg_debug_bo(struct amdxdna_hwctx *hwctx, u32 bo_hdl,
912926
return -EINVAL;
913927
}
914928

929+
cmd = kzalloc_obj(*cmd);
930+
if (!cmd) {
931+
ret = -ENOMEM;
932+
goto put_obj;
933+
}
934+
kref_init(&cmd->refcnt);
935+
915936
if (attach) {
916937
if (abo->assigned_hwctx != AMDXDNA_INVALID_CTX_HANDLE) {
917938
ret = -EBUSY;
918-
goto put_obj;
939+
goto put_cmd;
919940
}
920-
cmd.opcode = ATTACH_DEBUG_BO;
941+
cmd->opcode = ATTACH_DEBUG_BO;
921942
} else {
922943
if (abo->assigned_hwctx != hwctx->id) {
923944
ret = -EINVAL;
924-
goto put_obj;
945+
goto put_cmd;
925946
}
926-
cmd.opcode = DETACH_DEBUG_BO;
947+
cmd->opcode = DETACH_DEBUG_BO;
927948
}
928949

929-
ret = amdxdna_cmd_submit(client, &cmd, AMDXDNA_INVALID_BO_HANDLE,
950+
ret = amdxdna_cmd_submit(client, cmd, AMDXDNA_INVALID_BO_HANDLE,
930951
&bo_hdl, 1, hwctx->id, &seq);
931952
if (ret) {
932953
XDNA_ERR(xdna, "Submit command failed");
933-
goto put_obj;
954+
goto put_cmd;
934955
}
935956

936957
aie2_cmd_wait(hwctx, seq);
937-
if (cmd.result) {
938-
XDNA_ERR(xdna, "Response failure 0x%x", cmd.result);
958+
if (cmd->result) {
959+
XDNA_ERR(xdna, "Response failure 0x%x", cmd->result);
939960
ret = -EINVAL;
940-
goto put_obj;
961+
goto put_cmd;
941962
}
942963

943964
if (attach)
@@ -947,6 +968,8 @@ static int aie2_hwctx_cfg_debug_bo(struct amdxdna_hwctx *hwctx, u32 bo_hdl,
947968

948969
XDNA_DBG(xdna, "Config debug BO %d to %s", bo_hdl, hwctx->name);
949970

971+
put_cmd:
972+
aie2_cmd_put(cmd);
950973
put_obj:
951974
amdxdna_gem_put_obj(abo);
952975
return ret;
@@ -974,25 +997,32 @@ int aie2_hwctx_sync_debug_bo(struct amdxdna_hwctx *hwctx, u32 debug_bo_hdl)
974997
{
975998
struct amdxdna_client *client = hwctx->client;
976999
struct amdxdna_dev *xdna = client->xdna;
977-
struct amdxdna_drv_cmd cmd = { 0 };
1000+
struct amdxdna_drv_cmd *cmd;
9781001
u64 seq;
9791002
int ret;
9801003

981-
cmd.opcode = SYNC_DEBUG_BO;
982-
ret = amdxdna_cmd_submit(client, &cmd, AMDXDNA_INVALID_BO_HANDLE,
1004+
cmd = kzalloc_obj(*cmd);
1005+
if (!cmd)
1006+
return -ENOMEM;
1007+
kref_init(&cmd->refcnt);
1008+
1009+
cmd->opcode = SYNC_DEBUG_BO;
1010+
ret = amdxdna_cmd_submit(client, cmd, AMDXDNA_INVALID_BO_HANDLE,
9831011
&debug_bo_hdl, 1, hwctx->id, &seq);
9841012
if (ret) {
9851013
XDNA_ERR(xdna, "Submit command failed");
986-
return ret;
1014+
goto put_cmd;
9871015
}
9881016

9891017
aie2_cmd_wait(hwctx, seq);
990-
if (cmd.result) {
991-
XDNA_ERR(xdna, "Response failure 0x%x", cmd.result);
992-
return -EINVAL;
1018+
if (cmd->result) {
1019+
XDNA_ERR(xdna, "Response failure 0x%x", cmd->result);
1020+
ret = -EINVAL;
9931021
}
9941022

995-
return 0;
1023+
put_cmd:
1024+
aie2_cmd_put(cmd);
1025+
return ret;
9961026
}
9971027

9981028
static int aie2_populate_range(struct amdxdna_gem_obj *abo)
@@ -1142,6 +1172,8 @@ int aie2_cmd_submit(struct amdxdna_hwctx *hwctx, struct amdxdna_sched_job *job,
11421172
dma_resv_add_fence(job->bos[i]->resv, job->out_fence, DMA_RESV_USAGE_WRITE);
11431173
job->seq = hwctx->priv->seq++;
11441174
kref_get(&job->refcnt);
1175+
if (job->drv_cmd)
1176+
kref_get(&job->drv_cmd->refcnt);
11451177
drm_sched_entity_push_job(&job->base);
11461178

11471179
*seq = job->seq;

drivers/accel/amdxdna/amdxdna_ctx.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -132,6 +132,7 @@ enum amdxdna_job_opcode {
132132
struct amdxdna_drv_cmd {
133133
enum amdxdna_job_opcode opcode;
134134
u32 result;
135+
struct kref refcnt;
135136
};
136137

137138
struct app_health_report;

drivers/accel/amdxdna/amdxdna_iommu.c

Lines changed: 29 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@
44
*/
55

66
#include <drm/amdxdna_accel.h>
7+
#include <drm/drm_managed.h>
78
#include <linux/iommu.h>
89
#include <linux/iova.h>
910

@@ -153,10 +154,30 @@ void amdxdna_iommu_free(struct amdxdna_dev *xdna, size_t size,
153154
free_pages((unsigned long)cpu_addr, get_order(size));
154155
}
155156

157+
static void amdxdna_cleanup_force_iova(struct drm_device *dev, void *res)
158+
{
159+
struct amdxdna_dev *xdna = to_xdna_dev(dev);
160+
161+
if (xdna->domain) {
162+
iommu_detach_group(xdna->domain, xdna->group);
163+
put_iova_domain(&xdna->iovad);
164+
iova_cache_put();
165+
iommu_domain_free(xdna->domain);
166+
}
167+
168+
iommu_group_put(xdna->group);
169+
}
170+
171+
void amdxdna_iommu_fini(struct amdxdna_dev *xdna)
172+
{
173+
if (xdna->group && !xdna->domain)
174+
iommu_group_put(xdna->group);
175+
}
176+
156177
int amdxdna_iommu_init(struct amdxdna_dev *xdna)
157178
{
158179
unsigned long order;
159-
int ret;
180+
int ret = 0;
160181

161182
xdna->group = iommu_group_get(xdna->ddev.dev);
162183
if (!xdna->group || !force_iova)
@@ -182,29 +203,23 @@ int amdxdna_iommu_init(struct amdxdna_dev *xdna)
182203
if (ret)
183204
goto put_iova;
184205

206+
ret = drmm_add_action(&xdna->ddev, amdxdna_cleanup_force_iova, NULL);
207+
if (ret)
208+
goto detach_group;
209+
185210
return 0;
186211

212+
detach_group:
213+
iommu_detach_group(xdna->domain, xdna->group);
187214
put_iova:
188215
put_iova_domain(&xdna->iovad);
189216
iova_cache_put();
190217
free_domain:
191218
iommu_domain_free(xdna->domain);
192219
put_group:
193220
iommu_group_put(xdna->group);
221+
xdna->group = NULL;
194222
xdna->domain = NULL;
195223

196224
return ret;
197225
}
198-
199-
void amdxdna_iommu_fini(struct amdxdna_dev *xdna)
200-
{
201-
if (xdna->domain) {
202-
iommu_detach_group(xdna->domain, xdna->group);
203-
put_iova_domain(&xdna->iovad);
204-
iova_cache_put();
205-
iommu_domain_free(xdna->domain);
206-
}
207-
208-
if (xdna->group)
209-
iommu_group_put(xdna->group);
210-
}

drivers/accel/amdxdna/amdxdna_pci_drv.c

Lines changed: 17 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -138,9 +138,11 @@ static int amdxdna_drm_open(struct drm_device *ddev, struct drm_file *filp)
138138
xdna->dev_info->dev_heap_max_size);
139139
mutex_init(&client->mm_lock);
140140

141+
mutex_lock(&xdna->client_lock);
141142
mutex_lock(&xdna->dev_lock);
142143
list_add_tail(&client->node, &xdna->client_list);
143144
mutex_unlock(&xdna->dev_lock);
145+
mutex_unlock(&xdna->client_lock);
144146

145147
filp->driver_priv = client;
146148
client->filp = filp;
@@ -174,18 +176,14 @@ static void amdxdna_drm_close(struct drm_device *ddev, struct drm_file *filp)
174176
{
175177
struct amdxdna_client *client = filp->driver_priv;
176178
struct amdxdna_dev *xdna = to_xdna_dev(ddev);
177-
int idx;
178179

179180
XDNA_DBG(xdna, "closing pid %d", client->pid);
180181

181-
if (!drm_dev_enter(&xdna->ddev, &idx))
182-
return;
183-
182+
mutex_lock(&xdna->client_lock);
184183
mutex_lock(&xdna->dev_lock);
185184
amdxdna_client_cleanup(client);
186185
mutex_unlock(&xdna->dev_lock);
187-
188-
drm_dev_exit(idx);
186+
mutex_unlock(&xdna->client_lock);
189187
}
190188

191189
static int amdxdna_drm_get_info_ioctl(struct drm_device *dev, void *data, struct drm_file *filp)
@@ -371,6 +369,10 @@ static int amdxdna_probe(struct pci_dev *pdev, const struct pci_device_id *id)
371369
if (!xdna->dev_info)
372370
return -ENODEV;
373371

372+
ret = drmm_mutex_init(ddev, &xdna->client_lock);
373+
if (ret)
374+
return ret;
375+
374376
drmm_mutex_init(ddev, &xdna->dev_lock);
375377
init_rwsem(&xdna->notifier_lock);
376378
INIT_LIST_HEAD(&xdna->client_list);
@@ -390,9 +392,9 @@ static int amdxdna_probe(struct pci_dev *pdev, const struct pci_device_id *id)
390392
if (ret)
391393
return ret;
392394

393-
xdna->notifier_wq = alloc_ordered_workqueue("notifier_wq", WQ_MEM_RECLAIM);
394-
if (!xdna->notifier_wq) {
395-
ret = -ENOMEM;
395+
xdna->notifier_wq = drmm_alloc_ordered_workqueue(ddev, "notifier_wq", WQ_MEM_RECLAIM);
396+
if (IS_ERR(xdna->notifier_wq)) {
397+
ret = PTR_ERR(xdna->notifier_wq);
396398
goto iommu_fini;
397399
}
398400

@@ -401,7 +403,7 @@ static int amdxdna_probe(struct pci_dev *pdev, const struct pci_device_id *id)
401403
mutex_unlock(&xdna->dev_lock);
402404
if (ret) {
403405
XDNA_ERR(xdna, "Hardware init failed, ret %d", ret);
404-
goto destroy_notifier_wq;
406+
goto iommu_fini;
405407
}
406408

407409
ret = amdxdna_sysfs_init(xdna);
@@ -425,8 +427,6 @@ static int amdxdna_probe(struct pci_dev *pdev, const struct pci_device_id *id)
425427
mutex_lock(&xdna->dev_lock);
426428
xdna->dev_info->ops->fini(xdna);
427429
mutex_unlock(&xdna->dev_lock);
428-
destroy_notifier_wq:
429-
destroy_workqueue(xdna->notifier_wq);
430430
iommu_fini:
431431
amdxdna_iommu_fini(xdna);
432432
return ret;
@@ -437,23 +437,19 @@ static void amdxdna_remove(struct pci_dev *pdev)
437437
struct amdxdna_dev *xdna = pci_get_drvdata(pdev);
438438
struct amdxdna_client *client;
439439

440-
destroy_workqueue(xdna->notifier_wq);
441-
442440
drm_dev_unplug(&xdna->ddev);
443441
amdxdna_sysfs_fini(xdna);
444442

443+
mutex_lock(&xdna->client_lock);
445444
mutex_lock(&xdna->dev_lock);
446-
client = list_first_entry_or_null(&xdna->client_list,
447-
struct amdxdna_client, node);
448-
while (client) {
449-
amdxdna_client_cleanup(client);
450-
451-
client = list_first_entry_or_null(&xdna->client_list,
452-
struct amdxdna_client, node);
445+
list_for_each_entry(client, &xdna->client_list, node) {
446+
amdxdna_hwctx_remove_all(client);
447+
amdxdna_sva_fini(client);
453448
}
454449

455450
xdna->dev_info->ops->fini(xdna);
456451
mutex_unlock(&xdna->dev_lock);
452+
mutex_unlock(&xdna->client_lock);
457453

458454
amdxdna_iommu_fini(xdna);
459455
}

drivers/accel/amdxdna/amdxdna_pci_drv.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -120,6 +120,7 @@ struct amdxdna_dev {
120120

121121
struct mutex dev_lock; /* per device lock */
122122
struct list_head client_list;
123+
struct mutex client_lock; /* client_list */
123124
struct amdxdna_fw_ver fw_ver;
124125
struct rw_semaphore notifier_lock; /* for mmu notifier*/
125126
struct workqueue_struct *notifier_wq;

drivers/dma-buf/dma-fence-unwrap.c

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -97,6 +97,9 @@ int dma_fence_dedup_array(struct dma_fence **fences, int num_fences)
9797
{
9898
int i, j;
9999

100+
if (!num_fences)
101+
return 0;
102+
100103
sort(fences, num_fences, sizeof(*fences), fence_cmp, NULL);
101104

102105
/*

drivers/dma-buf/dma-fence.c

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1168,7 +1168,7 @@ const char __rcu *dma_fence_driver_name(struct dma_fence *fence)
11681168

11691169
/* RCU protection is required for safe access to returned string */
11701170
ops = rcu_dereference(fence->ops);
1171-
if (!dma_fence_test_signaled_flag(fence))
1171+
if (ops)
11721172
return (const char __rcu *)ops->get_driver_name(fence);
11731173
else
11741174
return (const char __rcu *)"detached-driver";
@@ -1201,8 +1201,8 @@ const char __rcu *dma_fence_timeline_name(struct dma_fence *fence)
12011201

12021202
/* RCU protection is required for safe access to returned string */
12031203
ops = rcu_dereference(fence->ops);
1204-
if (!dma_fence_test_signaled_flag(fence))
1205-
return (const char __rcu *)ops->get_driver_name(fence);
1204+
if (ops)
1205+
return (const char __rcu *)ops->get_timeline_name(fence);
12061206
else
12071207
return (const char __rcu *)"signaled-timeline";
12081208
}

0 commit comments

Comments
 (0)