@@ -317,6 +317,7 @@ class ISwapchain : public IBackendObject
317
317
//
318
318
inline uint64_t getAcquireCount () const {return m_acquireCounter;}
319
319
320
+ using void_refctd_ptr = core::smart_refctd_ptr<core::IReferenceCounted>;
320
321
// acquire
321
322
struct SAcquireInfo
322
323
{
@@ -357,7 +358,12 @@ class ISwapchain : public IBackendObject
357
358
case ACQUIRE_IMAGE_RESULT::SUBOPTIMAL:
358
359
m_acquireCounter++;
359
360
// assert(!unacquired(out_imgIx)); // should happen in the impl anyway
360
- m_frameResources[*out_imgIx] = nullptr ;
361
+ {
362
+ auto semaphoreArray = core::make_refctd_dynamic_array<core::smart_refctd_dynamic_array<void_refctd_ptr>>(info.signalSemaphores .size ());
363
+ for (auto i=0ull ; i<info.signalSemaphores .size (); i++)
364
+ semaphoreArray->operator [](i) = void_refctd_ptr (info.signalSemaphores [i].semaphore );
365
+ m_frameResources[*out_imgIx] = std::move (semaphoreArray);
366
+ }
361
367
if (m_oldSwapchain && m_acquireCounter>core::max (m_oldSwapchain->getImageCount (),m_imageCount) && !m_oldSwapchain->acquiredImagesAwaitingPresent ())
362
368
m_oldSwapchain = nullptr ;
363
369
break ;
@@ -381,10 +387,11 @@ class ISwapchain : public IBackendObject
381
387
SUBOPTIMAL,
382
388
_ERROR
383
389
};
384
- inline PRESENT_RESULT present (SPresentInfo info, core::smart_refctd_ptr<core::IReferenceCounted>&& frameResources=nullptr )
390
+ // If `FATAL_ERROR` returned then the `frameResources` are not latched until the next acquire of the same image index or swapchain destruction (whichever comes first)
391
+ inline PRESENT_RESULT present (SPresentInfo info, void_refctd_ptr&& _frameResources=nullptr )
385
392
{
386
393
if (!info.queue || info.imgIndex >=m_imageCount)
387
- return PRESENT_RESULT::_ERROR ;
394
+ return PRESENT_RESULT::FATAL_ERROR ;
388
395
389
396
auto * threadsafeQ = dynamic_cast <CThreadSafeQueueAdapter*>(info.queue );
390
397
if (threadsafeQ)
@@ -400,7 +407,16 @@ class ISwapchain : public IBackendObject
400
407
// - on the next acquire of the same index
401
408
// - when dropping the swapchain entirely, but need to wait on all previous presents to finish (some manageable UB)
402
409
if (retval!=PRESENT_RESULT::FATAL_ERROR)
410
+ {
411
+ auto frameResources = core::make_refctd_dynamic_array<core::smart_refctd_dynamic_array<void_refctd_ptr>>(info.waitSemaphores .size ()+2 );
412
+ frameResources->operator [](0 ) = std::move (m_frameResources[info.imgIndex ]);
413
+ frameResources->operator [](1 ) = std::move (_frameResources);
414
+ for (auto i=0ull ; i<info.waitSemaphores .size (); i++)
415
+ frameResources->operator [](i+2 ) = void_refctd_ptr (info.waitSemaphores [i].semaphore );
403
416
m_frameResources[info.imgIndex ] = std::move (frameResources);
417
+ }
418
+ else
419
+ m_frameResources[info.imgIndex ] = nullptr ;
404
420
return retval;
405
421
}
406
422
@@ -486,7 +502,7 @@ class ISwapchain : public IBackendObject
486
502
const uint8_t m_imageCount;
487
503
uint64_t m_acquireCounter = 0 ;
488
504
// resource to hold onto until a frame is done rendering (between; just before presenting, and next acquire of the same image index)
489
- std::array<core::smart_refctd_ptr<core::IReferenceCounted> ,ILogicalDevice::MaxQueueFamilies> m_frameResources = {};
505
+ std::array<void_refctd_ptr ,ILogicalDevice::MaxQueueFamilies> m_frameResources = {};
490
506
};
491
507
492
508
}
0 commit comments