@@ -521,17 +521,19 @@ pi_result _pi_context::finalize() {
521
521
return PI_SUCCESS;
522
522
}
523
523
524
- pi_result
525
- _pi_queue::resetCommandListFenceEntry (ze_command_list_handle_t ZeCommandList,
526
- bool MakeAvailable) {
527
- // Event has been signalled: If the fence for the associated command list
528
- // is signalled, then reset the fence and command list and add them to the
529
- // available list for ruse in PI calls.
530
- ZE_CALL (zeFenceReset (this ->ZeCommandListFenceMap [ZeCommandList]));
531
- ZE_CALL (zeCommandListReset (ZeCommandList));
524
+ pi_result _pi_queue::resetCommandListFenceEntry (
525
+ _pi_queue::command_list_fence_map_t ::value_type &MapEntry,
526
+ bool MakeAvailable) {
527
+ // Fence had been signalled meaning the associated command-list completed.
528
+ // Reset the fence and put the command list into a cache for reuse in PI
529
+ // calls.
530
+ ZE_CALL (zeFenceReset (MapEntry.second .ZeFence ));
531
+ ZE_CALL (zeCommandListReset (MapEntry.first ));
532
+ MapEntry.second .InUse = false ;
533
+
532
534
if (MakeAvailable) {
533
535
std::lock_guard<std::mutex> lock (this ->Context ->ZeCommandListCacheMutex );
534
- this ->Context ->ZeCommandListCache .push_back (ZeCommandList );
536
+ this ->Context ->ZeCommandListCache .push_back (MapEntry. first );
535
537
}
536
538
537
539
return PI_SUCCESS;
@@ -597,14 +599,15 @@ pi_result _pi_context::getAvailableCommandList(
597
599
*ZeCommandList = Queue->Context ->ZeCommandListCache .front ();
598
600
auto it = Queue->ZeCommandListFenceMap .find (*ZeCommandList);
599
601
if (it != Queue->ZeCommandListFenceMap .end ()) {
600
- *ZeFence = it->second ;
602
+ *ZeFence = it->second .ZeFence ;
603
+ it->second .InUse = true ;
601
604
} else {
602
605
// If there is a command list available on this device, but no
603
606
// fence yet associated, then we must create a fence/list
604
607
// reference for this Queue. This can happen if two Queues reuse
605
608
// a device which did not have the resources freed.
606
609
ZE_CALL (zeFenceCreate (Queue->ZeCommandQueue , &ZeFenceDesc, ZeFence));
607
- Queue->ZeCommandListFenceMap [*ZeCommandList] = *ZeFence;
610
+ Queue->ZeCommandListFenceMap [*ZeCommandList] = { *ZeFence, true } ;
608
611
}
609
612
Queue->Context ->ZeCommandListCache .pop_front ();
610
613
return PI_SUCCESS;
@@ -617,12 +620,14 @@ pi_result _pi_context::getAvailableCommandList(
617
620
// if a command list has completed dispatch of its commands and is ready for
618
621
// reuse. If a command list is found to have been signalled, then the
619
622
// command list & fence are reset and we return.
620
- for (const auto &MapEntry : Queue->ZeCommandListFenceMap ) {
621
- ze_result_t ZeResult = ZE_CALL_NOCHECK (zeFenceQueryStatus (MapEntry.second ));
623
+ for (auto &MapEntry : Queue->ZeCommandListFenceMap ) {
624
+ ze_result_t ZeResult =
625
+ ZE_CALL_NOCHECK (zeFenceQueryStatus (MapEntry.second .ZeFence ));
622
626
if (ZeResult == ZE_RESULT_SUCCESS) {
623
- Queue->resetCommandListFenceEntry (MapEntry. first , false );
627
+ Queue->resetCommandListFenceEntry (MapEntry, false );
624
628
*ZeCommandList = MapEntry.first ;
625
- *ZeFence = MapEntry.second ;
629
+ *ZeFence = MapEntry.second .ZeFence ;
630
+ MapEntry.second .InUse = true ;
626
631
return PI_SUCCESS;
627
632
}
628
633
}
@@ -642,8 +647,8 @@ pi_result _pi_context::getAvailableCommandList(
642
647
Queue->Device ->Platform ->ZeGlobalCommandListCount ++;
643
648
ZE_CALL (zeFenceCreate (Queue->ZeCommandQueue , &ZeFenceDesc, ZeFence));
644
649
Queue->ZeCommandListFenceMap .insert (
645
- std::pair<ze_command_list_handle_t , ze_fence_handle_t >(*ZeCommandList,
646
- *ZeFence));
650
+ std::pair<ze_command_list_handle_t , _pi_queue:: command_list_fence_t >(
651
+ *ZeCommandList, { *ZeFence, false } ));
647
652
pi_result = PI_SUCCESS;
648
653
}
649
654
@@ -2161,14 +2166,21 @@ pi_result piQueueRelease(pi_queue Queue) {
2161
2166
2162
2167
if (RefCountZero) {
2163
2168
// It is possible to get to here and still have an open command list
2164
- // if no wait or finish ever occurred for this queue. But still need
2165
- // // TODO: o make sure commands get executed.
2169
+ // if no wait or finish ever occurred for this queue.
2166
2170
if (auto Res = Queue->executeOpenCommandList ())
2167
2171
return Res;
2168
2172
2173
+ // Make sure all commands get executed.
2174
+ zeCommandQueueSynchronize (Queue->ZeCommandQueue , UINT64_MAX);
2175
+
2169
2176
// Destroy all the fences created associated with this queue.
2170
- for (const auto &MapEntry : Queue->ZeCommandListFenceMap ) {
2171
- ZE_CALL (zeFenceDestroy (MapEntry.second ));
2177
+ for (auto &MapEntry : Queue->ZeCommandListFenceMap ) {
2178
+ // This fence wasn't yet signalled when we polled it for recycling
2179
+ // the command-list, so need to release the command-list too.
2180
+ if (MapEntry.second .InUse ) {
2181
+ Queue->resetCommandListFenceEntry (MapEntry, true );
2182
+ }
2183
+ ZE_CALL (zeFenceDestroy (MapEntry.second .ZeFence ));
2172
2184
}
2173
2185
Queue->ZeCommandListFenceMap .clear ();
2174
2186
ZE_CALL (zeCommandQueueDestroy (Queue->ZeCommandQueue ));
@@ -3793,10 +3805,14 @@ static pi_result cleanupAfterEvent(pi_event Event) {
3793
3805
// is signalled, then reset the fence and command list and add them to the
3794
3806
// available list for reuse in PI calls.
3795
3807
if (Queue->RefCount > 0 ) {
3796
- ze_result_t ZeResult = ZE_CALL_NOCHECK (
3797
- zeFenceQueryStatus (Queue->ZeCommandListFenceMap [EventCommandList]));
3808
+ auto it = Queue->ZeCommandListFenceMap .find (EventCommandList);
3809
+ if (it == Queue->ZeCommandListFenceMap .end ()) {
3810
+ die (" Missing command-list completition fence" );
3811
+ }
3812
+ ze_result_t ZeResult =
3813
+ ZE_CALL_NOCHECK (zeFenceQueryStatus (it->second .ZeFence ));
3798
3814
if (ZeResult == ZE_RESULT_SUCCESS) {
3799
- Queue->resetCommandListFenceEntry (EventCommandList , true );
3815
+ Queue->resetCommandListFenceEntry (*it , true );
3800
3816
Event->ZeCommandList = nullptr ;
3801
3817
}
3802
3818
}
0 commit comments