@@ -61,6 +61,8 @@ static int amdgpu_cs_parser_init(struct amdgpu_cs_parser *p,
61
61
amdgpu_ctx_put (p -> ctx );
62
62
return - ECANCELED ;
63
63
}
64
+
65
+ amdgpu_sync_create (& p -> sync );
64
66
return 0 ;
65
67
}
66
68
@@ -452,18 +454,6 @@ static int amdgpu_syncobj_lookup_and_add(struct amdgpu_cs_parser *p,
452
454
}
453
455
454
456
r = amdgpu_sync_fence (& p -> sync , fence );
455
- if (r )
456
- goto error ;
457
-
458
- /*
459
- * When we have an explicit dependency it might be necessary to insert a
460
- * pipeline sync to make sure that all caches etc are flushed and the
461
- * next job actually sees the results from the previous one.
462
- */
463
- if (fence -> context == p -> gang_leader -> base .entity -> fence_context )
464
- r = amdgpu_sync_fence (& p -> gang_leader -> explicit_sync , fence );
465
-
466
- error :
467
457
dma_fence_put (fence );
468
458
return r ;
469
459
}
@@ -1188,10 +1178,19 @@ static int amdgpu_cs_vm_handling(struct amdgpu_cs_parser *p)
1188
1178
static int amdgpu_cs_sync_rings (struct amdgpu_cs_parser * p )
1189
1179
{
1190
1180
struct amdgpu_fpriv * fpriv = p -> filp -> driver_priv ;
1181
+ struct drm_gpu_scheduler * sched ;
1191
1182
struct amdgpu_bo_list_entry * e ;
1183
+ struct dma_fence * fence ;
1192
1184
unsigned int i ;
1193
1185
int r ;
1194
1186
1187
+ r = amdgpu_ctx_wait_prev_fence (p -> ctx , p -> entities [p -> gang_leader_idx ]);
1188
+ if (r ) {
1189
+ if (r != - ERESTARTSYS )
1190
+ DRM_ERROR ("amdgpu_ctx_wait_prev_fence failed.\n" );
1191
+ return r ;
1192
+ }
1193
+
1195
1194
list_for_each_entry (e , & p -> validated , tv .head ) {
1196
1195
struct amdgpu_bo * bo = ttm_to_amdgpu_bo (e -> tv .bo );
1197
1196
struct dma_resv * resv = bo -> tbo .base .resv ;
@@ -1211,10 +1210,24 @@ static int amdgpu_cs_sync_rings(struct amdgpu_cs_parser *p)
1211
1210
return r ;
1212
1211
}
1213
1212
1214
- r = amdgpu_ctx_wait_prev_fence (p -> ctx , p -> entities [p -> gang_leader_idx ]);
1215
- if (r && r != - ERESTARTSYS )
1216
- DRM_ERROR ("amdgpu_ctx_wait_prev_fence failed.\n" );
1217
- return r ;
1213
+ sched = p -> gang_leader -> base .entity -> rq -> sched ;
1214
+ while ((fence = amdgpu_sync_get_fence (& p -> sync ))) {
1215
+ struct drm_sched_fence * s_fence = to_drm_sched_fence (fence );
1216
+
1217
+ /*
1218
+ * When we have an dependency it might be necessary to insert a
1219
+ * pipeline sync to make sure that all caches etc are flushed and the
1220
+ * next job actually sees the results from the previous one
1221
+ * before we start executing on the same scheduler ring.
1222
+ */
1223
+ if (!s_fence || s_fence -> sched != sched )
1224
+ continue ;
1225
+
1226
+ r = amdgpu_sync_fence (& p -> gang_leader -> explicit_sync , fence );
1227
+ if (r )
1228
+ return r ;
1229
+ }
1230
+ return 0 ;
1218
1231
}
1219
1232
1220
1233
static void amdgpu_cs_post_dependencies (struct amdgpu_cs_parser * p )
@@ -1347,6 +1360,7 @@ static void amdgpu_cs_parser_fini(struct amdgpu_cs_parser *parser)
1347
1360
{
1348
1361
unsigned i ;
1349
1362
1363
+ amdgpu_sync_free (& parser -> sync );
1350
1364
for (i = 0 ; i < parser -> num_post_deps ; i ++ ) {
1351
1365
drm_syncobj_put (parser -> post_deps [i ].syncobj );
1352
1366
kfree (parser -> post_deps [i ].chain );
0 commit comments