diff --git a/external/vcpkg b/external/vcpkg index e140b1f..c3867e7 160000 --- a/external/vcpkg +++ b/external/vcpkg @@ -1 +1 @@ -Subproject commit e140b1fde236eb682b0d47f905e65008a191800f +Subproject commit c3867e714dd3a51c272826eea77267876517ed99 diff --git a/include/RenderGraph/BufferData.hpp b/include/RenderGraph/BufferData.hpp index 19cec33..c089b28 100644 --- a/include/RenderGraph/BufferData.hpp +++ b/include/RenderGraph/BufferData.hpp @@ -16,14 +16,27 @@ namespace crg { std::string name; BufferCreateInfo info; + uint32_t maxPages{ 1u }; + uint32_t allocatedPages{}; - explicit BufferData( std::string name = {} - , BufferCreateFlags flags = {} - , DeviceSize size = {} - , BufferUsageFlags usage = {} - , MemoryPropertyFlags memory = MemoryPropertyFlags::eDeviceLocal ) - : name{ std::move( name ) } - , info{ flags, size, usage, memory } + explicit BufferData( std::string pname = {} + , BufferCreateFlags pflags = {} + , DeviceSize psize = {} + , uint32_t pmaxPages = 1u + , BufferUsageFlags pusage = {} + , MemoryPropertyFlags pmemory = MemoryPropertyFlags::eDeviceLocal ) + : name{ std::move( pname ) } + , info{ pflags, psize, pusage, pmemory } + , maxPages{ pmaxPages } + { + } + + explicit BufferData( std::string pname = {} + , BufferCreateFlags pflags = {} + , DeviceSize psize = {} + , BufferUsageFlags pusage = {} + , MemoryPropertyFlags pmemory = MemoryPropertyFlags::eDeviceLocal ) + : BufferData{ std::move( pname ), pflags, psize, 1u, pusage, pmemory } { } diff --git a/include/RenderGraph/FrameGraph.hpp b/include/RenderGraph/FrameGraph.hpp index 07b2fc6..f67c3e8 100644 --- a/include/RenderGraph/FrameGraph.hpp +++ b/include/RenderGraph/FrameGraph.hpp @@ -41,10 +41,10 @@ namespace crg * Resource creation. */ /**@{*/ - CRG_API BufferId createBuffer( BufferData const & img ); - CRG_API BufferViewId createView( BufferViewData const & view ); - CRG_API ImageId createImage( ImageData const & img ); - CRG_API ImageViewId createView( ImageViewData const & view ); + CRG_API BufferId createBufferId( BufferData const & img ); + CRG_API BufferViewId createViewId( BufferViewData const & view ); + CRG_API ImageId createImageId( ImageData const & img ); + CRG_API ImageViewId createViewId( ImageViewData const & view ); /**@}*/ /** *\name diff --git a/include/RenderGraph/FrameGraphBase.hpp b/include/RenderGraph/FrameGraphBase.hpp index 6c1f874..06ddfe9 100644 --- a/include/RenderGraph/FrameGraphBase.hpp +++ b/include/RenderGraph/FrameGraphBase.hpp @@ -48,18 +48,21 @@ namespace crg struct LayoutState; struct PipelineState; struct RootNode; + struct Sampler; struct SamplerDesc; struct SemaphoreWait; struct Texcoord; struct VertexBuffer; struct WriteDescriptorSet; + class Buffer; class ContextResourcesCache; class Exception; class Fence; class FrameGraph; class FramePassTimer; class GraphVisitor; + class Image; class ImageCopy; class PipelinePass; class RecordContext; @@ -92,6 +95,38 @@ namespace crg using PassDependencyCache = std::unordered_map< FramePass const *, DependencyCache >; using DeviceSize = VkDeviceSize; + struct BufferMemory + { + explicit BufferMemory( VkBuffer buf = {} + , VkDeviceMemory mem = {} )noexcept + : buffer{ buf } + , memory{ mem } + { + } + + VkBuffer buffer{}; + VkDeviceMemory memory{}; + + private: + friend bool operator==( BufferMemory const & lhs, BufferMemory const & rhs ) = default; + }; + + struct ImageMemory + { + explicit ImageMemory( VkImage img = {} + , VkDeviceMemory mem = {} )noexcept + : image{ img } + , memory{ mem } + { + } + + VkImage image{}; + VkDeviceMemory memory{}; + + private: + friend bool operator==( ImageMemory const & lhs, ImageMemory const & rhs ) = default; + }; + using AttachmentPtr = std::unique_ptr< Attachment >; using FramePassPtr = std::unique_ptr< FramePass >; using FramePassGroupPtr = std::unique_ptr< FramePassGroup >; @@ -127,20 +162,9 @@ namespace crg using GraphNodePtrArray = std::vector< GraphNodePtr >; using WriteDescriptorSetArray = std::vector< WriteDescriptorSet >; using AttachmentsNodeMap = std::map< ConstGraphAdjacentNode, AttachmentTransitions >; - using BufferMemoryMap = std::map< BufferId, std::pair< VkBuffer, VkDeviceMemory > >; - using BufferViewMap = std::map< BufferViewId, VkBufferView >; - using ImageMemoryMap = std::map< ImageId, std::pair< VkImage, VkDeviceMemory > >; - using ImageViewMap = std::map< ImageViewId, VkImageView >; using ImageViewIdArray = std::vector< ImageViewId >; using SemaphoreWaitArray = std::vector< SemaphoreWait >; - template< typename DataT > - using IdDataOwnerCont = std::map< Id< DataT >, std::unique_ptr< DataT > >; - using BufferIdDataOwnerCont = IdDataOwnerCont< BufferData >; - using BufferViewIdDataOwnerCont = IdDataOwnerCont< BufferViewData >; - using ImageIdDataOwnerCont = IdDataOwnerCont< ImageData >; - using ImageViewIdDataOwnerCont = IdDataOwnerCont< ImageViewData >; - using VkAttachmentDescriptionArray = std::vector< VkAttachmentDescription >; using VkAttachmentReferenceArray = std::vector< VkAttachmentReference >; using VkBufferArray = std::vector< VkBuffer >; diff --git a/include/RenderGraph/FrameGraphFunctions.hpp b/include/RenderGraph/FrameGraphFunctions.hpp index dde318f..76e3878 100644 --- a/include/RenderGraph/FrameGraphFunctions.hpp +++ b/include/RenderGraph/FrameGraphFunctions.hpp @@ -34,6 +34,7 @@ namespace crg CRG_API ImageAspectFlags getAspectFlags( ImageViewId const & image )noexcept; CRG_API ImageSubresourceRange const & getSubresourceRange( ImageViewId const & image )noexcept; CRG_API BufferSubresourceRange const & getSubresourceRange( BufferViewId const & buffer )noexcept; + CRG_API std::pair< uint32_t, uint32_t > getBufferPageRange( BufferId bufferId, BufferSubresourceRange const & range ); CRG_API AccessFlags getAccessMask( ImageLayout layout )noexcept; CRG_API PipelineStageFlags getStageMask( ImageLayout layout )noexcept; CRG_API PipelineState getPipelineState( PipelineStageFlags flags )noexcept; diff --git a/include/RenderGraph/FrameGraphPrerequisites.hpp b/include/RenderGraph/FrameGraphPrerequisites.hpp index da3ae06..d57fd55 100644 --- a/include/RenderGraph/FrameGraphPrerequisites.hpp +++ b/include/RenderGraph/FrameGraphPrerequisites.hpp @@ -13,12 +13,6 @@ namespace crg template< typename TypeT > static inline const TypeT defaultV = DefaultValueGetterT< TypeT >::get(); - template< typename TypeT > - static inline TypeT getDefaultV() - { - return DefaultValueGetterT< TypeT >::get(); - } - template<> struct DefaultValueGetterT< VkPipelineVertexInputStateCreateInfo > { diff --git a/include/RenderGraph/FramePassGroup.hpp b/include/RenderGraph/FramePassGroup.hpp index f758d23..a7d7024 100644 --- a/include/RenderGraph/FramePassGroup.hpp +++ b/include/RenderGraph/FramePassGroup.hpp @@ -67,21 +67,21 @@ namespace crg CRG_API LayoutState getFinalLayoutState( ImageViewId view , uint32_t passIndex = 0u )const; /** - *\copydoc crg::FrameGraph::createBuffer + *\copydoc crg::FrameGraph::createBufferId */ - CRG_API BufferId createBuffer( BufferData const & img )const; + CRG_API BufferId createBufferId( BufferData const & img )const; /** - *\copydoc crg::FrameGraph::createView + *\copydoc crg::FrameGraph::createViewId */ - CRG_API BufferViewId createView( BufferViewData const & view )const; + CRG_API BufferViewId createViewId( BufferViewData const & view )const; /** - *\copydoc crg::FrameGraph::createImage + *\copydoc crg::FrameGraph::createImageId */ - CRG_API ImageId createImage( ImageData const & img )const; + CRG_API ImageId createImageId( ImageData const & img )const; /** - *\copydoc crg::FrameGraph::createView + *\copydoc crg::FrameGraph::createViewId */ - CRG_API ImageViewId createView( ImageViewData const & view )const; + CRG_API ImageViewId createViewId( ImageViewData const & view )const; /** *\copydoc crg::FrameGraph::addInput */ diff --git a/include/RenderGraph/FramePassTimer.hpp b/include/RenderGraph/FramePassTimer.hpp index 347c4a7..47328bb 100644 --- a/include/RenderGraph/FramePassTimer.hpp +++ b/include/RenderGraph/FramePassTimer.hpp @@ -177,7 +177,8 @@ namespace crg bool written{}; bool started{}; }; - std::array< Query, 2u > m_queries; + std::array< Query, 4u > m_queries; + uint32_t m_queryIndex{ 0 }; }; } diff --git a/include/RenderGraph/LayerLayoutStatesHandler.hpp b/include/RenderGraph/LayerLayoutStatesHandler.hpp index 76f5e81..678659f 100644 --- a/include/RenderGraph/LayerLayoutStatesHandler.hpp +++ b/include/RenderGraph/LayerLayoutStatesHandler.hpp @@ -14,6 +14,8 @@ namespace crg CRG_API explicit LayerLayoutStatesHandler( LayerLayoutStatesMap const & rhs ); CRG_API void addStates( LayerLayoutStatesHandler const & data ); + CRG_API void clear(); + CRG_API void setLayoutState( ImageId image , ImageViewType viewType , ImageSubresourceRange const & subresourceRange diff --git a/include/RenderGraph/RecordContext.hpp b/include/RenderGraph/RecordContext.hpp index 26fff42..ea7a396 100644 --- a/include/RenderGraph/RecordContext.hpp +++ b/include/RenderGraph/RecordContext.hpp @@ -38,6 +38,12 @@ namespace crg CRG_API explicit RecordContext( ContextResourcesCache & resources ); CRG_API explicit RecordContext( ResourceHandler & handler ); /** + *\name Lifetime + */ + //@{ + CRG_API void reset(); + //@} + /** *\name States */ //@{ @@ -104,6 +110,8 @@ namespace crg *\name Memory barriers */ //@{ + CRG_API void beginBatchBarriers(); + CRG_API void flushBatchBarriers( VkCommandBuffer commandBuffer ); /** *\name Images */ @@ -264,6 +272,15 @@ namespace crg return m_nextPipelineState; } + bool isBatching() const + { + return m_isBatching; + } + + private: + RecordContext( ResourceHandler & handler + , ContextResourcesCache * resources ); + private: ResourceHandler * m_handler; ContextResourcesCache * m_resources; @@ -276,5 +293,10 @@ namespace crg PipelineState m_currPipelineState{}; PipelineState m_nextPipelineState{}; LayerLayoutStatesHandler m_nextImages; + std::vector< VkImageMemoryBarrier > m_batchedImageBarriers; + std::vector< VkBufferMemoryBarrier > m_batchedBufferBarriers; + VkPipelineStageFlags m_batchSrcStages{}; + VkPipelineStageFlags m_batchDstStages{}; + bool m_isBatching{ false }; }; } diff --git a/include/RenderGraph/ResourceHandler.hpp b/include/RenderGraph/ResourceHandler.hpp index bdf1810..709de18 100644 --- a/include/RenderGraph/ResourceHandler.hpp +++ b/include/RenderGraph/ResourceHandler.hpp @@ -3,7 +3,8 @@ See LICENSE file in root folder. */ #pragma once -#include "RenderGraph/FrameGraphPrerequisites.hpp" +#include "RenderGraph/BufferData.hpp" +#include "RenderGraph/ImageData.hpp" #pragma warning( push ) #pragma warning( disable: 4365 ) @@ -21,14 +22,120 @@ namespace crg std::string name; }; + class Buffer + { + friend class ResourceHandler; + + public: + Buffer( Buffer const & ) = delete; + Buffer( Buffer && )noexcept = delete; + Buffer & operator=( Buffer const & ) = delete; + Buffer & operator=( Buffer && )noexcept = delete; + ~Buffer()noexcept = default; + + CRG_API Buffer( ResourceHandler & handler + , GraphContext & context + , BufferId bufferId + , BufferMemory firstPage )noexcept; + + CRG_API DeviceSize getPageSize()const noexcept; + CRG_API DeviceSize getMaxSize()const noexcept; + CRG_API DeviceSize getAllocatedSize()const noexcept; + CRG_API uint32_t getAllocatedPageCount()const noexcept; + CRG_API uint32_t getMaxPageCount()const noexcept; + CRG_API void resize( DeviceSize newSize ); + CRG_API void update(); + + VkBuffer getBuffer( uint32_t pageIndex = 0u )const noexcept + { + return m_pages[pageIndex].buffer; + } + + BufferMemory getPage( uint32_t pageIndex = 0u )const noexcept + { + return m_pages[pageIndex]; + } + + BufferId getBufferId()const noexcept + { + return m_bufferId; + } + + private: + friend bool operator==( Buffer const & lhs, Buffer const & rhs ) = default; + + private: + ResourceHandler * m_handler{}; + GraphContext * m_context{}; + BufferId m_bufferId{}; + std::vector< BufferMemory > m_pages; + DeviceSize m_neededSize{}; + }; + + class Image + { + public: + Image( Image const & ) = delete; + Image( Image && )noexcept = delete; + Image & operator=( Image const & ) = delete; + Image & operator=( Image && )noexcept = delete; + ~Image()noexcept = default; + + CRG_API Image( ResourceHandler & handler + , GraphContext & context + , ImageId imageId + , ImageMemory imageMemory ); + + VkImage getImage()const noexcept + { + return m_imageMemory.image; + } + + VkDeviceMemory getMemory()const noexcept + { + return m_imageMemory.memory; + } + + ImageId getImageId()const noexcept + { + return m_imageId; + } + + private: + friend bool operator==( Image const & lhs, Image const & rhs ) = default; + + private: + ResourceHandler * m_handler{}; + GraphContext * m_context{}; + ImageId m_imageId{}; + ImageMemory m_imageMemory{}; + }; + class ResourceHandler { + private: + friend class Buffer; + + template< typename DataT > + using IdDataOwnerCont = std::map< Id< DataT >, std::unique_ptr< DataT > >; + + using BufferIdDataOwnerCont = IdDataOwnerCont< BufferData >; + using BufferViewIdDataOwnerCont = IdDataOwnerCont< BufferViewData >; + using BufferPtr = std::unique_ptr< Buffer >; + using BufferMap = std::map< BufferId, BufferPtr >; + using BufferViewMap = std::map< BufferViewId, VkBufferView >; + + using ImageIdDataOwnerCont = IdDataOwnerCont< ImageData >; + using ImageViewIdDataOwnerCont = IdDataOwnerCont< ImageViewData >; + using ImagePtr = std::unique_ptr< Image >; + using ImageMap = std::map< ImageId, ImagePtr >; + using ImageViewMap = std::map< ImageViewId, VkImageView >; + template< typename ValueT > struct CreatedT { bool created{}; - ValueT resource{}; - VkDeviceMemory memory{}; + ValueT * resource{}; }; template< typename ValueT > @@ -51,11 +158,11 @@ namespace crg CRG_API ImageId createImageId( ImageData const & img ); CRG_API ImageViewId createViewId( ImageViewData const & view ); - CRG_API CreatedT< VkBuffer > createBuffer( GraphContext & context + CRG_API CreatedT< Buffer > createBuffer( GraphContext & context , BufferId bufferId ); CRG_API CreatedViewT< VkBufferView > createBufferView( GraphContext & context , BufferViewId viewId ); - CRG_API CreatedT< VkImage > createImage( GraphContext & context + CRG_API CreatedT< Image > createImage( GraphContext & context , ImageId imageId ); CRG_API CreatedViewT< VkImageView > createImageView( GraphContext & context , ImageViewId viewId ); @@ -79,27 +186,38 @@ namespace crg CRG_API void destroyVertexBuffer( GraphContext & context , VertexBuffer const * buffer ); + std::vector< Buffer * > const & getPagedBuffers()const noexcept + { + return m_pagedBuffers; + } + private: + BufferMemory createBufferMemory( GraphContext & context, BufferId bufferId ); + ImageMemory createImageMemory( GraphContext & context, ImageId imageId ); + mutable std::mutex m_buffersMutex; BufferIdDataOwnerCont m_bufferIds; mutable std::mutex m_bufferViewsMutex; BufferViewIdDataOwnerCont m_bufferViewIds; - BufferMemoryMap m_buffers; + BufferMap m_buffers; BufferViewMap m_bufferViews; mutable std::mutex m_imagesMutex; ImageIdDataOwnerCont m_imageIds; mutable std::mutex m_imageViewsMutex; ImageViewIdDataOwnerCont m_imageViewIds; - ImageMemoryMap m_images; + ImageMap m_images; ImageViewMap m_imageViews; std::mutex m_samplersMutex; std::unordered_map< VkSampler, Sampler > m_samplers; std::mutex m_vertexBuffersMutex; std::unordered_set< VertexBufferPtr > m_vertexBuffers; + std::vector< Buffer * > m_pagedBuffers; }; class ContextResourcesCache { + friend class Buffer; + public: ContextResourcesCache( ContextResourcesCache const & ) = delete; ContextResourcesCache & operator=( ContextResourcesCache const & ) = delete; @@ -110,15 +228,15 @@ namespace crg , GraphContext & context ); CRG_API ~ContextResourcesCache()noexcept; - CRG_API VkBuffer createBuffer( BufferId const & bufferId ); - CRG_API VkBuffer createBuffer( BufferId const & bufferId, VkDeviceMemory & memory ); + CRG_API Buffer & createBuffer( BufferId const & bufferId ); CRG_API VkBufferView createBufferView( BufferViewId const & viewId ); - CRG_API bool destroyBuffer( BufferId const & imageId ); + CRG_API bool destroyBuffer( Buffer const & buffer ); + CRG_API bool destroyBuffer( BufferId const & bufferId ); CRG_API bool destroyBufferView( BufferViewId const & viewId ); - CRG_API VkImage createImage( ImageId const & imageId ); - CRG_API VkImage createImage( ImageId const & imageId, VkDeviceMemory & memory ); + CRG_API Image & createImage( ImageId const & imageId ); CRG_API VkImageView createImageView( ImageViewId const & viewId ); + CRG_API bool destroyImage( Image const & image ); CRG_API bool destroyImage( ImageId const & imageId ); CRG_API bool destroyImageView( ImageViewId const & viewId ); @@ -142,16 +260,16 @@ namespace crg } private: - using VkBufferIdMap = std::map< BufferId, VkBuffer >; + using BufferIdMap = std::map< BufferId, Buffer * >; using VkBufferViewIdMap = std::map< BufferViewId, VkBufferView >; - using VkImageIdMap = std::map< ImageId, VkImage >; + using ImageIdMap = std::map< ImageId, Image * >; using VkImageViewIdMap = std::map< ImageViewId, VkImageView >; ResourceHandler & m_handler; GraphContext & m_context; - VkBufferIdMap m_buffers; + BufferIdMap m_buffers; VkBufferViewIdMap m_bufferViews; - VkImageIdMap m_images; + ImageIdMap m_images; VkImageViewIdMap m_imageViews; std::unordered_map< size_t, VkSampler > m_samplers; std::unordered_map< size_t, VertexBuffer const * > m_vertexBuffers; @@ -162,11 +280,10 @@ namespace crg public: CRG_API explicit ResourcesCache( ResourceHandler & handler ); - CRG_API VkBuffer createBuffer( GraphContext & context + CRG_API void destroyContext( GraphContext & context ); + + CRG_API Buffer & createBuffer( GraphContext & context , BufferId const & bufferId ); - CRG_API VkBuffer createBuffer( GraphContext & context - , BufferId const & bufferId - , VkDeviceMemory & memory ); CRG_API VkBufferView createBufferView( GraphContext & context , BufferViewId const & viewId ); CRG_API bool destroyBuffer( BufferId const & bufferId ); @@ -176,11 +293,8 @@ namespace crg CRG_API bool destroyBufferView( GraphContext & context , BufferViewId const & viewId ); - CRG_API VkImage createImage( GraphContext & context + CRG_API Image & createImage( GraphContext & context , ImageId const & imageId ); - CRG_API VkImage createImage( GraphContext & context - , ImageId const & imageId - , VkDeviceMemory & memory ); CRG_API VkImageView createImageView( GraphContext & context , ImageViewId const & viewId ); CRG_API bool destroyImage( ImageId const & imageId ); diff --git a/include/RenderGraph/RunnableGraph.hpp b/include/RenderGraph/RunnableGraph.hpp index 2b4997e..6231cb8 100644 --- a/include/RenderGraph/RunnableGraph.hpp +++ b/include/RenderGraph/RunnableGraph.hpp @@ -64,9 +64,9 @@ namespace crg CRG_API SemaphoreWaitArray run( SemaphoreWaitArray const & toWait , VkQueue queue ); - CRG_API VkBuffer createBuffer( BufferId const & buffer ); + CRG_API Buffer & createBuffer( BufferId const & buffer ); CRG_API VkBufferView createBufferView( BufferViewId const & view ); - CRG_API VkImage createImage( ImageId const & image ); + CRG_API Image & createImage( ImageId const & image ); CRG_API VkImageView createImageView( ImageViewId const & view ); CRG_API VkSampler createSampler( SamplerDesc const & samplerDesc ); CRG_API VertexBuffer const & createQuadTriVertexBuffer( bool texCoords @@ -154,6 +154,16 @@ namespace crg return m_context; } + private: + RecordContext & getRecordContext() + { + if ( !m_recordContext ) + m_recordContext = std::make_unique< RecordContext >( m_resources ); + else + m_recordContext->reset(); + return *m_recordContext; + } + private: FrameGraph & m_graph; GraphContext & m_context; @@ -169,5 +179,9 @@ namespace crg VkSemaphore m_semaphore{}; Fence m_fence; FramePassTimer m_timer; + std::unique_ptr< RecordContext > m_recordContext; + // Reusable buffers to avoid per-frame allocations + mutable std::vector< VkSemaphore > m_cachedSemaphores; + mutable std::vector< VkPipelineStageFlags > m_cachedDstStageMasks; }; } diff --git a/include/RenderGraph/RunnablePass.hpp b/include/RenderGraph/RunnablePass.hpp index fbfe676..858f3bd 100644 --- a/include/RenderGraph/RunnablePass.hpp +++ b/include/RenderGraph/RunnablePass.hpp @@ -143,6 +143,77 @@ namespace crg } }; + + using InitialiseCallback = std::function< void( uint32_t /*passIndex*/ ) >; + template<> + struct DefaultValueGetterT< InitialiseCallback > + { + static InitialiseCallback get() + { + InitialiseCallback const result{ []( uint32_t ){} }; + return result; + } + }; + + using RecordCallback = std::function< void( RecordContext &, VkCommandBuffer, uint32_t /*passIndex*/ ) >; + template<> + struct DefaultValueGetterT< RecordCallback > + { + static RecordCallback get() + { + RecordCallback const result{ []( RecordContext &, VkCommandBuffer, uint32_t ){} }; + return result; + } + }; + + struct PipelineStateT; + using GetPipelineStateCallback = GetValueCallbackT< PipelineStateT, PipelineState >; + template<> + struct DefaultValueGetterT< GetPipelineStateCallback > + { + static GetPipelineStateCallback get() + { + GetPipelineStateCallback const result{ [](){ return PipelineState{ AccessFlags::eShaderRead, PipelineStageFlags::eFragmentShader }; } }; + return result; + } + }; + + struct PassIndexT; + using GetPassIndexCallback = GetValueCallbackT< PassIndexT, uint32_t >; + template<> + struct DefaultValueGetterT< GetPassIndexCallback > + { + static GetPassIndexCallback get() + { + GetPassIndexCallback const result{ [](){ return 0u; } }; + return result; + } + }; + + struct EnabledT; + using IsEnabledCallback = GetValueCallbackT< EnabledT, bool >; + template<> + struct DefaultValueGetterT< IsEnabledCallback > + { + static IsEnabledCallback get() + { + IsEnabledCallback const result{ [](){ return true; } }; + return result; + } + }; + + struct ComputePassT; + using IsComputePassCallback = GetValueCallbackT< ComputePassT, bool >; + template<> + struct DefaultValueGetterT< IsComputePassCallback > + { + static IsComputePassCallback get() + { + IsComputePassCallback const result{ [](){ return false; } }; + return result; + } + }; + class RunnablePass { public: @@ -166,55 +237,52 @@ namespace crg AccessState to; }; - struct PassIndexT - { - }; - struct PipelineStateT - { - }; - struct EnabledT - { - }; - struct ComputePassT + struct Callbacks { - }; + CRG_API Callbacks(); - using InitialiseCallback = std::function< void( uint32_t passIndex ) >; - using RecordCallback = std::function< void( RecordContext &, VkCommandBuffer, uint32_t ) >; - using GetPipelineStateCallback = GetValueCallbackT< PipelineStateT, PipelineState >; - using GetPassIndexCallback = GetValueCallbackT< PassIndexT, uint32_t >; - using IsEnabledCallback = GetValueCallbackT< EnabledT, bool >; - using IsComputePassCallback = GetValueCallbackT< ComputePassT, bool >; + Callbacks & onInitialise( std::function< void( uint32_t passIndex ) > config ) + { + initialise = std::move( config ); + return *this; + } - struct Callbacks - { - CRG_API Callbacks( InitialiseCallback initialise - , GetPipelineStateCallback getPipelineState ); - CRG_API Callbacks( InitialiseCallback initialise - , GetPipelineStateCallback getPipelineState - , RecordCallback record ); - CRG_API Callbacks( InitialiseCallback initialise - , GetPipelineStateCallback getPipelineState - , RecordCallback record - , GetPassIndexCallback getPassIndex ); - CRG_API Callbacks( InitialiseCallback initialise - , GetPipelineStateCallback getPipelineState - , RecordCallback record - , GetPassIndexCallback getPassIndex - , IsEnabledCallback isEnabled ); - CRG_API Callbacks( InitialiseCallback initialise - , GetPipelineStateCallback getPipelineState - , RecordCallback record - , GetPassIndexCallback getPassIndex - , IsEnabledCallback isEnabled - , IsComputePassCallback isComputePass ); - - InitialiseCallback initialise; - GetPipelineStateCallback getPipelineState; - RecordCallback record; - GetPassIndexCallback getPassIndex; - IsEnabledCallback isEnabled; - IsComputePassCallback isComputePass; + Callbacks & onGetPipelineState( std::function< PipelineState() > config ) + { + getPipelineState = GetPipelineStateCallback{ std::move( config ) }; + return *this; + } + + Callbacks & onRecord( std::function< void( RecordContext &, VkCommandBuffer, uint32_t ) > config ) + { + record = std::move( config ); + return *this; + } + + Callbacks & onGetPassIndex( std::function< uint32_t() > config ) + { + getPassIndex = GetPassIndexCallback{ std::move( config ) }; + return *this; + } + + Callbacks & onIsEnabled( std::function< bool() > config ) + { + isEnabled = IsEnabledCallback{ std::move( config ) }; + return *this; + } + + Callbacks & onIsComputePass( std::function< bool() > config ) + { + isComputePass = IsComputePassCallback{ std::move( config ) }; + return *this; + } + + InitialiseCallback initialise = defaultV< InitialiseCallback >; + GetPipelineStateCallback getPipelineState = defaultV < GetPipelineStateCallback >; + RecordCallback record = defaultV < RecordCallback >; + GetPassIndexCallback getPassIndex = defaultV < GetPassIndexCallback >; + IsEnabledCallback isEnabled = defaultV < IsEnabledCallback >; + IsComputePassCallback isComputePass = defaultV < IsComputePassCallback >; }; static constexpr uint32_t InvalidIndex = ~0u; @@ -375,64 +443,4 @@ namespace crg LayerLayoutStatesHandler m_imageLayouts; AccessStateMap m_bufferAccesses; }; - - template<> - struct DefaultValueGetterT< RunnablePass::InitialiseCallback > - { - static RunnablePass::InitialiseCallback get() - { - RunnablePass::InitialiseCallback const result{ []( uint32_t ){} }; - return result; - } - }; - - template<> - struct DefaultValueGetterT< RunnablePass::GetPipelineStateCallback > - { - static RunnablePass::GetPipelineStateCallback get() - { - RunnablePass::GetPipelineStateCallback const result{ [](){ return PipelineState{ AccessFlags::eShaderRead, PipelineStageFlags::eFragmentShader }; } }; - return result; - } - }; - - template<> - struct DefaultValueGetterT< RunnablePass::RecordCallback > - { - static RunnablePass::RecordCallback get() - { - RunnablePass::RecordCallback const result{ []( RecordContext &, VkCommandBuffer, uint32_t ){} }; - return result; - } - }; - - template<> - struct DefaultValueGetterT< RunnablePass::GetPassIndexCallback > - { - static RunnablePass::GetPassIndexCallback get() - { - RunnablePass::GetPassIndexCallback const result{ [](){ return 0u; } }; - return result; - } - }; - - template<> - struct DefaultValueGetterT< RunnablePass::IsEnabledCallback > - { - static RunnablePass::IsEnabledCallback get() - { - RunnablePass::IsEnabledCallback const result{ [](){ return true; } }; - return result; - } - }; - - template<> - struct DefaultValueGetterT< RunnablePass::IsComputePassCallback > - { - static RunnablePass::IsComputePassCallback get() - { - RunnablePass::IsComputePassCallback const result{ [](){ return false; } }; - return result; - } - }; } diff --git a/include/RenderGraph/RunnablePasses/ComputePass.hpp b/include/RenderGraph/RunnablePasses/ComputePass.hpp index 0cced02..7510505 100644 --- a/include/RenderGraph/RunnablePasses/ComputePass.hpp +++ b/include/RenderGraph/RunnablePasses/ComputePass.hpp @@ -116,7 +116,7 @@ namespace crg *\param[in] config * The pass index callback. */ - auto & getPassIndex( RunnablePass::GetPassIndexCallback const & config ) + auto & getPassIndex( GetPassIndexCallback const & config ) { m_getPassIndex = config; return *this; @@ -125,7 +125,7 @@ namespace crg *\param[in] config * The callback checking the enable status of the pass. */ - auto & isEnabled( RunnablePass::IsEnabledCallback const & config ) + auto & isEnabled( IsEnabledCallback const & config ) { m_isEnabled = config; return *this; @@ -134,7 +134,7 @@ namespace crg *\param[in] config * The callback recording the pass. */ - auto & recordInto( RunnablePass::RecordCallback const & config ) + auto & recordInto( RecordCallback const & config ) { m_recordInto = config; return *this; @@ -143,7 +143,7 @@ namespace crg *\param[in] config * The callback initialising the pass. */ - auto & initialise( RunnablePass::InitialiseCallback const & config ) + auto & initialise( InitialiseCallback const & config ) { m_initialise = config; return *this; @@ -152,7 +152,7 @@ namespace crg *\param[in] config * The callback ending the pass. */ - auto & end( RunnablePass::RecordCallback const & config ) + auto & end( RecordCallback const & config ) { m_end = config; return *this; @@ -222,12 +222,12 @@ namespace crg } pp::ConfigT< WrapperT > m_baseConfig{}; - WrapperT< RunnablePass::InitialiseCallback > m_initialise{}; + WrapperT< InitialiseCallback > m_initialise{}; WrapperT< bool const * > m_enabled{}; - WrapperT< RunnablePass::IsEnabledCallback > m_isEnabled{}; - WrapperT< RunnablePass::GetPassIndexCallback > m_getPassIndex{}; - WrapperT< RunnablePass::RecordCallback > m_recordInto{}; - WrapperT< RunnablePass::RecordCallback > m_end{}; + WrapperT< IsEnabledCallback > m_isEnabled{}; + WrapperT< GetPassIndexCallback > m_getPassIndex{}; + WrapperT< RecordCallback > m_recordInto{}; + WrapperT< RecordCallback > m_end{}; WrapperT< uint32_t > m_groupCountX{}; WrapperT< uint32_t > m_groupCountY{}; WrapperT< uint32_t > m_groupCountZ{}; @@ -240,12 +240,12 @@ namespace crg template<> struct ConfigT< RawTypeT > { - RawTypeT< RunnablePass::InitialiseCallback > initialise{}; + RawTypeT< InitialiseCallback > initialise{}; RawTypeT< bool const * > enabled{ nullptr }; - std::optional< RunnablePass::IsEnabledCallback > isEnabled{}; - RawTypeT< RunnablePass::GetPassIndexCallback > getPassIndex{}; - RawTypeT< RunnablePass::RecordCallback > recordInto{}; - RawTypeT< RunnablePass::RecordCallback > end{}; + std::optional< IsEnabledCallback > isEnabled{}; + RawTypeT< GetPassIndexCallback > getPassIndex{}; + RawTypeT< RecordCallback > recordInto{}; + RawTypeT< RecordCallback > end{}; RawTypeT< uint32_t > groupCountX{ 1u }; RawTypeT< uint32_t > groupCountY{ 1u }; RawTypeT< uint32_t > groupCountZ{ 1u }; diff --git a/include/RenderGraph/RunnablePasses/PipelineHolder.hpp b/include/RenderGraph/RunnablePasses/PipelineHolder.hpp index fd44ef3..4b9c620 100644 --- a/include/RenderGraph/RunnablePasses/PipelineHolder.hpp +++ b/include/RenderGraph/RunnablePasses/PipelineHolder.hpp @@ -78,6 +78,7 @@ namespace crg { WriteDescriptorSetArray writes{}; VkDescriptorSet set{}; + size_t hash{}; }; private: diff --git a/include/RenderGraph/RunnablePasses/RenderMeshConfig.hpp b/include/RenderGraph/RunnablePasses/RenderMeshConfig.hpp index d163542..8171829 100644 --- a/include/RenderGraph/RunnablePasses/RenderMeshConfig.hpp +++ b/include/RenderGraph/RunnablePasses/RenderMeshConfig.hpp @@ -117,7 +117,7 @@ namespace crg *\param[in] config * The pass index callback. */ - auto & getPassIndex( RunnablePass::GetPassIndexCallback const & config ) + auto & getPassIndex( GetPassIndexCallback const & config ) { m_getPassIndex = config; return *this; @@ -126,7 +126,7 @@ namespace crg *\param[in] config * The callback checking the enable status of the pass. */ - auto & isEnabled( RunnablePass::IsEnabledCallback const & config ) + auto & isEnabled( IsEnabledCallback const & config ) { m_isEnabled = config; return *this; @@ -135,7 +135,7 @@ namespace crg *\param[in] config * The callback recording the pass. */ - auto & recordInto( RunnablePass::RecordCallback const & config ) + auto & recordInto( RecordCallback const & config ) { m_recordInto = config; return *this; @@ -144,7 +144,7 @@ namespace crg *\param[in] config * The callback ending the pass. */ - auto & end( RunnablePass::RecordCallback const & config ) + auto & end( RecordCallback const & config ) { m_end = config; return *this; @@ -216,10 +216,10 @@ namespace crg pp::ConfigT< WrapperT > m_baseConfig{}; WrapperT< Offset2D > m_renderPosition{}; WrapperT< VkPipelineDepthStencilStateCreateInfo > m_depthStencilState{}; - WrapperT< RunnablePass::GetPassIndexCallback > m_getPassIndex{}; - WrapperT< RunnablePass::IsEnabledCallback > m_isEnabled{}; - WrapperT< RunnablePass::RecordCallback > m_recordInto{}; - WrapperT< RunnablePass::RecordCallback > m_end{}; + WrapperT< GetPassIndexCallback > m_getPassIndex{}; + WrapperT< IsEnabledCallback > m_isEnabled{}; + WrapperT< RecordCallback > m_recordInto{}; + WrapperT< RecordCallback > m_end{}; WrapperT< GetPrimitiveCountCallback > m_getPrimitiveCount{}; WrapperT< GetVertexCountCallback > m_getVertexCount{}; WrapperT< GetIndexTypeCallback > m_getIndexType{}; @@ -235,10 +235,10 @@ namespace crg { RawTypeT< Offset2D > renderPosition{}; RawTypeT< VkPipelineDepthStencilStateCreateInfo > depthStencilState{}; - RawTypeT< RunnablePass::GetPassIndexCallback > getPassIndex{}; - RawTypeT< RunnablePass::IsEnabledCallback > isEnabled{}; - RawTypeT< RunnablePass::RecordCallback > recordInto{}; - RawTypeT< RunnablePass::RecordCallback > end{}; + RawTypeT< GetPassIndexCallback > getPassIndex{}; + RawTypeT< IsEnabledCallback > isEnabled{}; + RawTypeT< RecordCallback > recordInto{}; + RawTypeT< RecordCallback > end{}; RawTypeT< GetPrimitiveCountCallback > getPrimitiveCount{}; RawTypeT< GetVertexCountCallback > getVertexCount{}; RawTypeT< GetIndexTypeCallback > getIndexType{}; diff --git a/include/RenderGraph/RunnablePasses/RenderPass.hpp b/include/RenderGraph/RunnablePasses/RenderPass.hpp index a7fc0d3..f0269ac 100644 --- a/include/RenderGraph/RunnablePasses/RenderPass.hpp +++ b/include/RenderGraph/RunnablePasses/RenderPass.hpp @@ -24,6 +24,18 @@ namespace crg return result; } + struct SubpassContentsT; + using GetSubpassContentsCallback = GetValueCallbackT< SubpassContentsT, VkSubpassContents >; + template<> + struct DefaultValueGetterT< GetSubpassContentsCallback > + { + static GetSubpassContentsCallback get() + { + GetSubpassContentsCallback const result{ [](){ return VK_SUBPASS_CONTENTS_INLINE; } }; + return result; + } + }; + class RenderPass : public RunnablePass { @@ -31,33 +43,47 @@ namespace crg template< typename ConfigT, typename BuilderT > friend class RenderQuadBuilderT; - struct SubpassContentsT; - using GetSubpassContentsCallback = GetValueCallbackT< SubpassContentsT, VkSubpassContents >; - struct Callbacks { - CRG_API Callbacks( InitialiseCallback initialise - , RecordCallback record ); - CRG_API Callbacks( InitialiseCallback initialise - , RecordCallback record - , GetSubpassContentsCallback getSubpassContents ); - CRG_API Callbacks( InitialiseCallback initialise - , RecordCallback record - , GetSubpassContentsCallback getSubpassContents - , GetPassIndexCallback getPassIndex ); - CRG_API Callbacks( InitialiseCallback initialise - , RecordCallback record - , GetSubpassContentsCallback getSubpassContents - , GetPassIndexCallback getPassIndex - , IsEnabledCallback isEnabled ); + CRG_API Callbacks(); + + Callbacks & onInitialise( std::function< void( uint32_t passIndex ) > config ) + { + initialise = InitialiseCallback{ std::move( config ) }; + return *this; + } + + Callbacks & onRecord( std::function< void( RecordContext &, VkCommandBuffer, uint32_t ) > config ) + { + record = RecordCallback{ std::move( config ) }; + return *this; + } + + Callbacks & onGetSubpassContents( std::function< VkSubpassContents() > config ) + { + getSubpassContents = GetSubpassContentsCallback{ std::move( config ) }; + return *this; + } + + Callbacks & onGetPassIndex( std::function< uint32_t() > config ) + { + getPassIndex = GetPassIndexCallback{ std::move( config ) }; + return *this; + } + + Callbacks & onIsEnabled( std::function< bool() > config ) + { + isEnabled = IsEnabledCallback{ std::move( config ) }; + return *this; + } // RenderPass specifics - RunnablePass::InitialiseCallback initialise; - RunnablePass::RecordCallback record; - GetSubpassContentsCallback getSubpassContents; + InitialiseCallback initialise{ defaultV< InitialiseCallback > }; + RecordCallback record{ defaultV< RecordCallback > }; + GetSubpassContentsCallback getSubpassContents{ defaultV< GetSubpassContentsCallback > }; // Passed to RunnablePass - RunnablePass::GetPassIndexCallback getPassIndex; - RunnablePass::IsEnabledCallback isEnabled; + GetPassIndexCallback getPassIndex{ defaultV< GetPassIndexCallback > }; + IsEnabledCallback isEnabled{ defaultV< IsEnabledCallback > }; }; public: @@ -98,14 +124,4 @@ namespace crg Callbacks m_rpCallbacks; RenderPassHolder m_holder; }; - - template<> - struct DefaultValueGetterT< RenderPass::GetSubpassContentsCallback > - { - static RenderPass::GetSubpassContentsCallback get() - { - RenderPass::GetSubpassContentsCallback const result{ [](){ return VK_SUBPASS_CONTENTS_INLINE; } }; - return result; - } - }; } diff --git a/include/RenderGraph/RunnablePasses/RenderQuad.hpp b/include/RenderGraph/RunnablePasses/RenderQuad.hpp index 73740cc..52c4995 100644 --- a/include/RenderGraph/RunnablePasses/RenderQuad.hpp +++ b/include/RenderGraph/RunnablePasses/RenderQuad.hpp @@ -114,7 +114,7 @@ namespace crg *\param[in] config * The callback checking the enable status of the pass. */ - auto & isEnabled( RunnablePass::IsEnabledCallback config ) + auto & isEnabled( IsEnabledCallback config ) { m_config.isEnabled( config ); return static_cast< BuilderT & >( *this ); @@ -123,7 +123,7 @@ namespace crg *\param[in] config * The callback to recording the pass. */ - auto & recordInto( RunnablePass::RecordCallback config ) + auto & recordInto( RecordCallback config ) { m_config.recordInto( config ); return static_cast< BuilderT & >( *this ); diff --git a/include/RenderGraph/RunnablePasses/RenderQuadConfig.hpp b/include/RenderGraph/RunnablePasses/RenderQuadConfig.hpp index 4bfde68..6ad66be 100644 --- a/include/RenderGraph/RunnablePasses/RenderQuadConfig.hpp +++ b/include/RenderGraph/RunnablePasses/RenderQuadConfig.hpp @@ -145,7 +145,7 @@ namespace crg *\param[in] config * The callback checking the enable status of the pass. */ - auto & isEnabled( RunnablePass::IsEnabledCallback const & config ) + auto & isEnabled( IsEnabledCallback const & config ) { m_isEnabled = config; return *this; @@ -154,7 +154,7 @@ namespace crg *\param[in] config * The callback recording the pass. */ - auto & recordInto( RunnablePass::RecordCallback const & config ) + auto & recordInto( RecordCallback const & config ) { m_recordInto = config; return *this; @@ -163,7 +163,7 @@ namespace crg *\param[in] config * The callback ending the pass. */ - auto & end( RunnablePass::RecordCallback const & config ) + auto & end( RecordCallback const & config ) { m_end = config; return *this; @@ -193,9 +193,9 @@ namespace crg WrapperT< VkPipelineDepthStencilStateCreateInfo > m_depthStencilState{}; WrapperT< uint32_t const * > m_passIndex{}; WrapperT< bool const * > m_enabled{}; - WrapperT< RunnablePass::IsEnabledCallback > m_isEnabled{}; - WrapperT< RunnablePass::RecordCallback > m_recordInto{}; - WrapperT< RunnablePass::RecordCallback > m_end{}; + WrapperT< IsEnabledCallback > m_isEnabled{}; + WrapperT< RecordCallback > m_recordInto{}; + WrapperT< RecordCallback > m_end{}; WrapperT< uint32_t > m_instances{}; WrapperT< Extent2D > m_renderSize{}; WrapperT< IndirectBuffer > m_indirectBuffer{}; @@ -209,9 +209,9 @@ namespace crg RawTypeT< VkPipelineDepthStencilStateCreateInfo > depthStencilState; RawTypeT< uint32_t const * > passIndex; RawTypeT< bool const * > enabled; - std::optional< RunnablePass::IsEnabledCallback > isEnabled; - RawTypeT< RunnablePass::RecordCallback > recordInto; - RawTypeT< RunnablePass::RecordCallback > end; + std::optional< IsEnabledCallback > isEnabled; + RawTypeT< RecordCallback > recordInto; + RawTypeT< RecordCallback > end; RawTypeT< uint32_t > m_instances; RawTypeT< IndirectBuffer > indirectBuffer{ BufferViewId{}, 0u }; }; diff --git a/source/RenderGraph/FrameGraph.cpp b/source/RenderGraph/FrameGraph.cpp index 49075a4..be6cb73 100644 --- a/source/RenderGraph/FrameGraph.cpp +++ b/source/RenderGraph/FrameGraph.cpp @@ -185,28 +185,28 @@ namespace crg return m_defaultGroup->createPassGroup( groupName ); } - BufferId FrameGraph::createBuffer( BufferData const & img ) + BufferId FrameGraph::createBufferId( BufferData const & img ) { auto result = m_handler.createBufferId( img ); m_buffers.insert( result ); return result; } - BufferViewId FrameGraph::createView( BufferViewData const & view ) + BufferViewId FrameGraph::createViewId( BufferViewData const & view ) { auto result = m_handler.createViewId( view ); m_bufferViews.insert( result ); return result; } - ImageId FrameGraph::createImage( ImageData const & img ) + ImageId FrameGraph::createImageId( ImageData const & img ) { auto result = m_handler.createImageId( img ); m_images.insert( result ); return result; } - ImageViewId FrameGraph::createView( ImageViewData const & view ) + ImageViewId FrameGraph::createViewId( ImageViewData const & view ) { auto result = m_handler.createViewId( view ); m_imageViews.insert( result ); @@ -247,7 +247,7 @@ namespace crg } } - return createView( data ); + return createViewId( data ); } BufferViewId FrameGraph::mergeViews( BufferViewIdArray const & views ) @@ -255,7 +255,7 @@ namespace crg BufferViewData data; for ( auto & view : views ) fgph::mergeViewData( view, data ); - return createView( data ); + return createViewId( data ); } Attachment const * FrameGraph::mergeAttachments( AttachmentArray const & attachments diff --git a/source/RenderGraph/FrameGraph.natvis b/source/RenderGraph/FrameGraph.natvis index c01a624..175aa88 100644 --- a/source/RenderGraph/FrameGraph.natvis +++ b/source/RenderGraph/FrameGraph.natvis @@ -2,11 +2,15 @@ - {name,sb} fmt={info.size} + {name,sb} size={info.size * allocatedPages}/{info.size * maxPages} + {name,sb} size={info.size} name info.flags - info.size + info.size + allocatedPages + maxPages + info.size info.usage diff --git a/source/RenderGraph/FrameGraphPrerequisites.cpp b/source/RenderGraph/FrameGraphPrerequisites.cpp index a5be77e..81f8e3f 100644 --- a/source/RenderGraph/FrameGraphPrerequisites.cpp +++ b/source/RenderGraph/FrameGraphPrerequisites.cpp @@ -488,7 +488,7 @@ namespace crg DeviceSize getSize( BufferId const & buffer )noexcept { - return buffer.data->info.size; + return buffer.data->info.size * buffer.data->allocatedPages; } DeviceSize getSize( BufferViewId const & buffer )noexcept @@ -565,6 +565,18 @@ namespace crg return buffer.data->info.subresourceRange; } + std::pair< uint32_t, uint32_t > getBufferPageRange( BufferId bufferId, BufferSubresourceRange const & range ) + { + auto pageSize = bufferId.data->info.size; + auto basePage = uint32_t( range.offset / pageSize ); + + if ( range.size == VK_WHOLE_SIZE ) + return { basePage, bufferId.data->allocatedPages - basePage }; + + auto pageCount = uint32_t( ( range.offset + range.size + pageSize - 1 ) / pageSize ) - basePage; + return { basePage, pageCount }; + } + AccessFlags getAccessMask( ImageLayout layout )noexcept { AccessFlags result{ 0u }; diff --git a/source/RenderGraph/FramePassGroup.cpp b/source/RenderGraph/FramePassGroup.cpp index 649c618..7251e7d 100644 --- a/source/RenderGraph/FramePassGroup.cpp +++ b/source/RenderGraph/FramePassGroup.cpp @@ -142,24 +142,24 @@ namespace crg return m_graph.getFinalLayoutState( view, passIndex ); } - BufferId FramePassGroup::createBuffer( BufferData const & img )const + BufferId FramePassGroup::createBufferId( BufferData const & img )const { - return m_graph.createBuffer( img ); + return m_graph.createBufferId( img ); } - BufferViewId FramePassGroup::createView( BufferViewData const & view )const + BufferViewId FramePassGroup::createViewId( BufferViewData const & view )const { - return m_graph.createView( view ); + return m_graph.createViewId( view ); } - ImageId FramePassGroup::createImage( ImageData const & img )const + ImageId FramePassGroup::createImageId( ImageData const & img )const { - return m_graph.createImage( img ); + return m_graph.createImageId( img ); } - ImageViewId FramePassGroup::createView( ImageViewData const & view )const + ImageViewId FramePassGroup::createViewId( ImageViewData const & view )const { - return m_graph.createView( view ); + return m_graph.createViewId( view ); } void FramePassGroup::addInput( ImageId image diff --git a/source/RenderGraph/FramePassTimer.cpp b/source/RenderGraph/FramePassTimer.cpp index 7e8b06a..2fedd33 100644 --- a/source/RenderGraph/FramePassTimer.cpp +++ b/source/RenderGraph/FramePassTimer.cpp @@ -41,9 +41,12 @@ namespace crg , m_name{ name } , m_colour{ context.getNextRainbowColour() } , m_timerQueries{ timerQueries } - , m_queries{ { { baseQueryOffset, false, false }, { baseQueryOffset + 2u, false, false } } } + , m_queries{ { { baseQueryOffset + 0u, false, false } + , { baseQueryOffset + 2u, false, false } + , { baseQueryOffset + 4u, false, false } + , { baseQueryOffset + 6u, false, false } } } { - baseQueryOffset += 4u; + baseQueryOffset += 8u; } FramePassTimer::FramePassTimer( GraphContext & context @@ -53,9 +56,12 @@ namespace crg , m_scope{ scope } , m_name{ name } , m_colour{ context.getNextRainbowColour() } - , m_timerQueries{ createQueryPool( context, name, 4u ) } + , m_timerQueries{ createQueryPool( context, name, 8u ) } , m_ownPool{ true } - , m_queries{ { { 0u, false, false }, { 2u, false, false } } } + , m_queries{ { { 0u, false, false } + , { 2u, false, false } + , { 4u, false, false } + , { 6u, false, false } } } { } @@ -87,7 +93,7 @@ namespace crg void FramePassTimer::notifyPassRender( [[maybe_unused]] uint32_t passIndex )noexcept { - auto & query = m_queries.front(); + auto & query = m_queries[m_queryIndex]; query.started = true; } @@ -113,8 +119,8 @@ namespace crg , { "[" + std::to_string( passId ) + "] " + groupName , m_colour } ); #pragma GCC diagnostic pop - std::swap( m_queries.front(), m_queries.back() ); - auto const & query = m_queries.front(); + m_queryIndex = ( m_queryIndex + 1u ) % uint32_t( m_queries.size() ); + auto const & query = m_queries[m_queryIndex]; m_context.vkCmdResetQueryPool( commandBuffer , m_timerQueries , query.offset @@ -127,7 +133,7 @@ namespace crg void FramePassTimer::endPass( VkCommandBuffer commandBuffer )noexcept { - auto & query = m_queries.front(); + auto & query = m_queries[m_queryIndex]; m_context.vkCmdWriteTimestamp( commandBuffer , VK_PIPELINE_STAGE_BOTTOM_OF_PIPE_BIT , m_timerQueries @@ -143,7 +149,8 @@ namespace crg auto before = Clock::now(); m_gpuTime = 0ns; - if ( auto & query = m_queries.front(); query.started && query.written ) + if ( auto & query = m_queries[m_queryIndex]; + query.started && query.written ) { std::array< uint64_t, 2u > values{ 0u, 0u }; m_context.vkGetQueryPoolResults( m_context.device diff --git a/source/RenderGraph/LayerLayoutStatesHandler.cpp b/source/RenderGraph/LayerLayoutStatesHandler.cpp index 1d2836a..927a665 100644 --- a/source/RenderGraph/LayerLayoutStatesHandler.cpp +++ b/source/RenderGraph/LayerLayoutStatesHandler.cpp @@ -23,6 +23,11 @@ namespace crg } } + void LayerLayoutStatesHandler::clear() + { + images.clear(); + } + void LayerLayoutStatesHandler::setLayoutState( ImageId image , ImageViewType viewType , ImageSubresourceRange const & subresourceRange diff --git a/source/RenderGraph/RecordContext.cpp b/source/RenderGraph/RecordContext.cpp index b626ed4..b31862e 100644 --- a/source/RenderGraph/RecordContext.cpp +++ b/source/RenderGraph/RecordContext.cpp @@ -49,21 +49,55 @@ namespace crg //************************************************************************************************ - RecordContext::RecordContext( ContextResourcesCache & resources ) - : m_handler{ &resources.getHandler() } - , m_resources{ &resources } + RecordContext::RecordContext( ResourceHandler & handler + , ContextResourcesCache * resources ) + : m_handler{ &handler } + , m_resources{ resources } , m_prevPipelineState{ AccessFlags::eNone, PipelineStageFlags::eBottomOfPipe } , m_currPipelineState{ AccessFlags::eNone, PipelineStageFlags::eBottomOfPipe } , m_nextPipelineState{ AccessFlags::eNone, PipelineStageFlags::eBottomOfPipe } + { + // Pre-allocate capacity to reduce reallocations during frame recording + m_implicitImageTransitions.reserve( 64 ); + m_implicitBufferTransitions.reserve( 32 ); + m_batchedImageBarriers.reserve( 32 ); + m_batchedBufferBarriers.reserve( 16 ); + } + + RecordContext::RecordContext( ContextResourcesCache & resources ) + : RecordContext{ resources.getHandler(), &resources } { } RecordContext::RecordContext( ResourceHandler & handler ) - : m_handler{ &handler } - , m_resources{ nullptr } + : RecordContext{ handler, nullptr } { } + void RecordContext::reset() + { + // Clear other state + m_images.clear(); + m_buffers.clear(); + m_state.clear(); + m_nextImages.clear(); + + // Clear vectors but retain capacity to avoid reallocations + m_implicitImageTransitions.clear(); + m_implicitBufferTransitions.clear(); + m_batchedImageBarriers.clear(); + m_batchedBufferBarriers.clear(); + + // Reset pipeline states + m_prevPipelineState = { AccessFlags::eNone, PipelineStageFlags::eBottomOfPipe }; + m_currPipelineState = { AccessFlags::eNone, PipelineStageFlags::eBottomOfPipe }; + m_nextPipelineState = { AccessFlags::eNone, PipelineStageFlags::eBottomOfPipe }; + + m_batchSrcStages = 0; + m_batchDstStages = 0; + m_isBatching = false; + } + void RecordContext::addStates( RecordContext const & data ) { m_images.addStates( data.m_images ); @@ -171,8 +205,10 @@ namespace crg if ( it != m_implicitImageTransitions.end() ) { auto pass = it->pass; - auto action = it->action; - m_implicitImageTransitions.erase( it ); + auto action = std::move( it->action ); + if ( it != m_implicitImageTransitions.end() - 1 ) + *it = std::move( m_implicitImageTransitions.back() ); + m_implicitImageTransitions.pop_back(); if ( !pass->isEnabled() ) { @@ -195,8 +231,10 @@ namespace crg if ( it != m_implicitBufferTransitions.end() ) { auto pass = it->pass; - auto action = it->action; - m_implicitBufferTransitions.erase( it ); + auto action = std::move( it->action ); + if ( it != m_implicitBufferTransitions.end() - 1 ) + *it = std::move( m_implicitBufferTransitions.back() ); + m_implicitBufferTransitions.pop_back(); if ( !pass->isEnabled() ) { @@ -235,6 +273,42 @@ namespace crg return dummy; } + void RecordContext::beginBatchBarriers() + { + m_isBatching = true; + m_batchedImageBarriers.clear(); + m_batchedBufferBarriers.clear(); + m_batchedImageBarriers.reserve( 32 ); + m_batchedBufferBarriers.reserve( 16 ); + m_batchSrcStages = 0; + m_batchDstStages = 0; + } + + void RecordContext::flushBatchBarriers( VkCommandBuffer commandBuffer ) + { + if ( m_isBatching && ( !m_batchedImageBarriers.empty() || !m_batchedBufferBarriers.empty() ) ) + { + ContextResourcesCache const & resources = getResources(); + resources->vkCmdPipelineBarrier( commandBuffer + , m_batchSrcStages + , m_batchDstStages + , VK_DEPENDENCY_BY_REGION_BIT + , 0u + , nullptr + , static_cast< uint32_t >( m_batchedBufferBarriers.size() ) + , m_batchedBufferBarriers.data() + , static_cast< uint32_t >( m_batchedImageBarriers.size() ) + , m_batchedImageBarriers.data() ); + + m_batchedImageBarriers.clear(); + m_batchedBufferBarriers.clear(); + m_batchSrcStages = 0; + m_batchDstStages = 0; + } + + m_isBatching = false; + } + void RecordContext::memoryBarrier( VkCommandBuffer commandBuffer , ImageViewId const & view , ImageLayout initialLayout @@ -301,18 +375,29 @@ namespace crg , convert( wantedState.layout ) , VK_QUEUE_FAMILY_IGNORED , VK_QUEUE_FAMILY_IGNORED - , resources.createImage( image ) + , resources.createImage( image ).getImage() , convert( range ) }; - resources->vkCmdPipelineBarrier( commandBuffer - , getPipelineStageFlags( from.state.pipelineStage ) - , getPipelineStageFlags( wantedState.state.pipelineStage ) - , VK_DEPENDENCY_BY_REGION_BIT - , 0u - , nullptr - , 0u - , nullptr - , 1u - , &barrier ); + + if ( m_isBatching ) + { + m_batchedImageBarriers.push_back( barrier ); + m_batchSrcStages |= getPipelineStageFlags( from.state.pipelineStage ); + m_batchDstStages |= getPipelineStageFlags( wantedState.state.pipelineStage ); + } + else + { + resources->vkCmdPipelineBarrier( commandBuffer + , getPipelineStageFlags( from.state.pipelineStage ) + , getPipelineStageFlags( wantedState.state.pipelineStage ) + , VK_DEPENDENCY_BY_REGION_BIT + , 0u + , nullptr + , 0u + , nullptr + , 1u + , &barrier ); + } + setLayoutState( image , viewType , range @@ -378,13 +463,13 @@ namespace crg } void RecordContext::memoryBarrier( VkCommandBuffer commandBuffer - , BufferId buffer + , BufferId bufferId , BufferSubresourceRange const & subresourceRange , AccessState const & initialState , AccessState const & wantedState , bool force ) { - auto from = getAccessState( buffer + auto from = getAccessState( bufferId , subresourceRange ); if ( checkFlag( from.pipelineStage, PipelineStageFlags::eBottomOfPipe ) ) @@ -397,26 +482,48 @@ namespace crg || from.pipelineStage != wantedState.pipelineStage ) ) { auto & resources = getResources(); - VkBufferMemoryBarrier barrier{ VK_STRUCTURE_TYPE_BUFFER_MEMORY_BARRIER - , nullptr - , getAccessFlags( from.access ) - , getAccessFlags( wantedState.access ) - , VK_QUEUE_FAMILY_IGNORED - , VK_QUEUE_FAMILY_IGNORED - , resources.createBuffer( buffer ) - , subresourceRange.offset - , subresourceRange.size }; - resources->vkCmdPipelineBarrier( commandBuffer - , getPipelineStageFlags( from.pipelineStage ) - , getPipelineStageFlags( wantedState.pipelineStage ) - , VK_DEPENDENCY_BY_REGION_BIT - , 0u - , nullptr - , 1u - , &barrier - , 0u - , nullptr ); - setAccessState( buffer + auto buffer = &resources.createBuffer( bufferId ); + auto [pageMin, pageCount] = getBufferPageRange( bufferId, subresourceRange ); + auto offset = subresourceRange.offset - pageMin * buffer->getPageSize(); + auto size = subresourceRange.size; + + for ( uint32_t pageIndex = pageMin; pageIndex < std::min( pageMin + pageCount, buffer->getAllocatedPageCount() ); ++pageIndex ) + { + auto actualSize = std::min( size, buffer->getPageSize() - offset ); + VkBufferMemoryBarrier barrier{ VK_STRUCTURE_TYPE_BUFFER_MEMORY_BARRIER + , nullptr + , getAccessFlags( from.access ) + , getAccessFlags( wantedState.access ) + , VK_QUEUE_FAMILY_IGNORED + , VK_QUEUE_FAMILY_IGNORED + , buffer->getBuffer( pageIndex ) + , offset + , actualSize }; + size -= actualSize; + offset = 0u; + + if ( m_isBatching ) + { + m_batchedBufferBarriers.push_back( barrier ); + m_batchSrcStages |= getPipelineStageFlags( from.pipelineStage ); + m_batchDstStages |= getPipelineStageFlags( wantedState.pipelineStage ); + } + else + { + resources->vkCmdPipelineBarrier( commandBuffer + , getPipelineStageFlags( from.pipelineStage ) + , getPipelineStageFlags( wantedState.pipelineStage ) + , VK_DEPENDENCY_BY_REGION_BIT + , 0u + , nullptr + , 1u + , &barrier + , 0u + , nullptr ); + } + } + + setAccessState( bufferId , subresourceRange , wantedState ); } @@ -481,8 +588,8 @@ namespace crg memoryBarrier( commandBuffer, dstView, makeLayoutState( ImageLayout::eTransferDst ) ); auto & resources = getResources(); resources->vkCmdCopyImage( commandBuffer - , resources.createImage( srcView.data->image ), VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL - , resources.createImage( dstView.data->image ), VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL + , resources.createImage( srcView.data->image ).getImage(), VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL + , resources.createImage( dstView.data->image ).getImage(), VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL , 1u, ®ion ); if ( finalLayout != ImageLayout::eUndefined ) @@ -507,8 +614,8 @@ namespace crg VkImageBlit region{ getSubresourceLayer( srcSubresource ), { VkOffset3D{ srcRect.offset.x, srcRect.offset.y, 0u }, VkOffset3D{ int32_t( srcRect.extent.width ), int32_t( srcRect.extent.height ), 1 } } , getSubresourceLayer( dstSubresource ), { VkOffset3D{ dstRect.offset.x, dstRect.offset.y, 0u }, VkOffset3D{ int32_t( dstRect.extent.width ), int32_t( dstRect.extent.height ), 1 } } }; resources->vkCmdBlitImage( commandBuffer - , resources.createImage( srcView.data->image ), VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL - , resources.createImage( dstView.data->image ), VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL + , resources.createImage( srcView.data->image ).getImage(), VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL + , resources.createImage( dstView.data->image ).getImage(), VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL , 1u, ®ion, convert( filter ) ); if ( finalLayout != ImageLayout::eUndefined ) @@ -526,7 +633,7 @@ namespace crg assert( isColourFormat( getFormat( dstView ) ) ); auto vkClearValue = convert( clearValue ); resources->vkCmdClearColorImage( commandBuffer - , resources.createImage( dstView.data->image ), VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL + , resources.createImage( dstView.data->image ).getImage(), VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL , &vkClearValue, 1u, &subresourceRange ); if ( finalLayout != ImageLayout::eUndefined ) @@ -544,7 +651,7 @@ namespace crg assert( isDepthOrStencilFormat( getFormat( dstView ) ) ); auto vkClearValue = convert( clearValue ); resources->vkCmdClearDepthStencilImage( commandBuffer - , resources.createImage( dstView.data->image ), VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL + , resources.createImage( dstView.data->image ).getImage(), VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL , &vkClearValue, 1u, &subresourceRange ); if ( finalLayout != ImageLayout::eUndefined ) @@ -563,10 +670,23 @@ namespace crg memoryBarrier( commandBuffer, srcView, { AccessFlags::eTransferRead, PipelineStageFlags::eTransfer } ); memoryBarrier( commandBuffer, dstView, { AccessFlags::eTransferWrite, PipelineStageFlags::eTransfer } ); auto & resources = getResources(); - VkBufferCopy region{ srcOffset, dstOffset, size }; + auto [srcPageMin, srcPageCount] = getBufferPageRange( srcView.data->buffer, { srcOffset, size } ); + auto [dstPageMin, dstPageCount] = getBufferPageRange( dstView.data->buffer, { dstOffset, size } ); + + if ( srcPageCount > 1 || dstPageCount > 1 ) + { + Logger::logError( "RecordContext::copyBuffer - Source [" + srcView.data->name + "] or destination [" + dstView.data->name + "] buffer views have more than one page, this is currently unsupported." ); + return; + } + + auto srcPageSize = srcView.data->buffer.data->info.size; + auto dstPageSize = dstView.data->buffer.data->info.size; + auto srcBuffer = &resources.createBuffer( srcView.data->buffer ); + auto dstBuffer = &resources.createBuffer( dstView.data->buffer ); + VkBufferCopy region{ srcOffset - srcPageMin * srcPageSize, dstOffset - dstPageMin * dstPageSize, size }; resources->vkCmdCopyBuffer( commandBuffer - , resources.createBuffer( srcView.data->buffer ) - , resources.createBuffer( dstView.data->buffer ) + , srcBuffer->getBuffer( srcPageMin ) + , dstBuffer->getBuffer( dstPageMin ) , 1u, ®ion ); if ( finalState != AccessState{} ) @@ -581,10 +701,21 @@ namespace crg auto & resources = getResources(); memoryBarrier( commandBuffer, dstView, { AccessFlags::eTransferWrite, PipelineStageFlags::eTransfer } ); auto subresourceRange = getSubresourceRange( dstView ); - resources->vkCmdFillBuffer( commandBuffer - , resources.createBuffer( dstView.data->buffer ) - , subresourceRange.offset, subresourceRange.size - , clearValue ); + auto [dstPageMin, dstPageCount] = getBufferPageRange( dstView.data->buffer, subresourceRange ); + auto remainingSize = subresourceRange.size; + auto pageSize = dstView.data->buffer.data->info.size; + auto buffer = &resources.createBuffer( dstView.data->buffer ); + + for ( uint32_t pageIndex = dstPageMin; pageIndex < dstPageMin + dstPageCount; ++pageIndex ) + { + auto currentPageSize = std::min( pageSize - subresourceRange.offset, remainingSize ); + resources->vkCmdFillBuffer( commandBuffer + , buffer->getBuffer( pageIndex ) + , subresourceRange.offset, currentPageSize + , clearValue ); + subresourceRange.offset = 0u; + remainingSize -= currentPageSize; + } if ( finalState != AccessState{} ) memoryBarrier( commandBuffer, dstView, finalState ); diff --git a/source/RenderGraph/ResourceHandler.cpp b/source/RenderGraph/ResourceHandler.cpp index f12d998..782f93d 100644 --- a/source/RenderGraph/ResourceHandler.cpp +++ b/source/RenderGraph/ResourceHandler.cpp @@ -4,9 +4,10 @@ See LICENSE file in root folder. #include "RenderGraph/ResourceHandler.hpp" #include "RenderGraph/Attachment.hpp" -#include "RenderGraph/GraphContext.hpp" #include "RenderGraph/BufferData.hpp" #include "RenderGraph/BufferViewData.hpp" +#include "RenderGraph/Exception.hpp" +#include "RenderGraph/GraphContext.hpp" #include "RenderGraph/Hash.hpp" #include "RenderGraph/ImageData.hpp" #include "RenderGraph/ImageViewData.hpp" @@ -90,6 +91,75 @@ namespace crg //********************************************************************************************* + Buffer::Buffer( ResourceHandler & handler + , GraphContext & context + , BufferId bufferId + , BufferMemory firstPage )noexcept + : m_handler{ &handler } + , m_context{ &context } + , m_bufferId{ bufferId } + { + m_pages.emplace_back( std::move( firstPage ) ); + } + + DeviceSize Buffer::getPageSize()const noexcept + { + return m_bufferId.data->info.size; + } + + DeviceSize Buffer::getMaxSize()const noexcept + { + return m_bufferId.data->maxPages * getPageSize(); + } + + DeviceSize Buffer::getAllocatedSize()const noexcept + { + return m_bufferId.data->allocatedPages * getPageSize(); + } + + uint32_t Buffer::getAllocatedPageCount()const noexcept + { + return uint32_t( m_pages.size() ); + } + + uint32_t Buffer::getMaxPageCount()const noexcept + { + return m_bufferId.data->maxPages; + } + + void Buffer::resize( DeviceSize newSize ) + { + if ( newSize > getMaxSize() ) + { + Logger::logError( "Can't resize to a sizer larger than maximum allocatable size for buffer [" + m_bufferId.data->name + "]" ); + } + + m_neededSize = std::min( std::max( m_neededSize, newSize ), getMaxSize() ); + } + + void Buffer::update() + { + while ( m_neededSize > getAllocatedSize() ) + { + m_pages.push_back( m_handler->createBufferMemory( *m_context, m_bufferId ) ); + } + } + + //********************************************************************************************* + + Image::Image( ResourceHandler & handler + , GraphContext & context + , ImageId imageId + , ImageMemory imageMemory ) + : m_handler{ &handler } + , m_context{ &context } + , m_imageId{ imageId } + , m_imageMemory{ imageMemory } + { + } + + //********************************************************************************************* + ResourceHandler::~ResourceHandler()noexcept { for ( auto const & [data, _] : m_bufferViews ) @@ -128,10 +198,16 @@ namespace crg } } - BufferId ResourceHandler::createBufferId( BufferData const & img ) + BufferId ResourceHandler::createBufferId( BufferData const & buf ) { + if ( buf.maxPages < 1u ) + { + Logger::logError( "createBufferId - At least one page is needed to create a buffer" ); + CRG_Exception( "createBufferId - At least one page is needed to create a buffer" ); + } + lock_type lock( m_buffersMutex ); - auto data = std::make_unique< BufferData >( img ); + auto data = std::make_unique< BufferData >( buf ); BufferId result{ uint32_t( m_bufferIds.size() + 1u ), data.get() }; m_bufferIds.try_emplace( result, std::move( data ) ); return result; @@ -162,62 +238,25 @@ namespace crg return result; } - ResourceHandler::CreatedT< VkBuffer > ResourceHandler::createBuffer( GraphContext & context + ResourceHandler::CreatedT< Buffer > ResourceHandler::createBuffer( GraphContext & context , BufferId bufferId ) { - ResourceHandler::CreatedT< VkBuffer > result{}; + CreatedT< Buffer > result{}; + lock_type lock( m_buffersMutex ); + auto [it, ins] = m_buffers.try_emplace( bufferId, nullptr ); - if ( context.vkCreateBuffer ) + if ( ins ) { - lock_type lock( m_buffersMutex ); - auto [it, ins] = m_buffers.try_emplace( bufferId, std::pair< VkBuffer, VkDeviceMemory >{} ); + it->second = std::make_unique< Buffer >( *this, context, bufferId, createBufferMemory( context, bufferId ) ); + result.created = true; - if ( ins && context.device ) + if ( bufferId.data->maxPages > 1u ) { - // Create buffer - auto createInfo = reshdl::convert( *bufferId.data ); - auto res = context.vkCreateBuffer( context.device - , &createInfo - , context.allocator - , &it->second.first ); - result.resource = it->second.first; - checkVkResult( res, "Buffer creation" ); - crgRegisterObjectName( context, bufferId.data->name, result.resource ); - - // Create Buffer memory - VkMemoryRequirements requirements{}; - context.vkGetBufferMemoryRequirements( context.device - , result.resource - , &requirements ); - uint32_t deduced = context.deduceMemoryType( requirements.memoryTypeBits - , getMemoryPropertyFlags( bufferId.data->info.memory ) ); - VkMemoryAllocateInfo allocateInfo{ VK_STRUCTURE_TYPE_MEMORY_ALLOCATE_INFO - , nullptr - , requirements.size - , deduced }; - res = context.vkAllocateMemory( context.device - , &allocateInfo - , context.allocator - , &it->second.second ); - result.memory = it->second.second; - checkVkResult( res, "Buffer memory allocation" ); - crgRegisterObjectName( context, bufferId.data->name, result.memory ); - - // Bind buffer and memory - res = context.vkBindBufferMemory( context.device - , result.resource - , result.memory - , 0u ); - checkVkResult( res, "Buffer memory binding" ); - result.created = true; - } - else - { - result.resource = it->second.first; - result.memory = it->second.second; + m_pagedBuffers.push_back( it->second.get() ); } } + result.resource = it->second.get(); return result; } @@ -226,6 +265,12 @@ namespace crg { ResourceHandler::CreatedViewT< VkBufferView > result{}; + if ( view.data->buffer.data->maxPages > 1 ) + { + Logger::logError( "Can't create a vertex buffer from a paged buffer" ); + return result; + } + if ( context.vkCreateBufferView ) { lock_type lock( m_bufferViewsMutex ); @@ -233,7 +278,7 @@ namespace crg if ( ins ) { - auto buffer = createBuffer( context, view.data->buffer ).resource; + auto buffer = createBuffer( context, view.data->buffer ).resource->getBuffer(); auto createInfo = reshdl::convert( *view.data, buffer ); auto res = context.vkCreateBufferView( context.device , &createInfo @@ -287,62 +332,20 @@ namespace crg return result; } - ResourceHandler::CreatedT< VkImage > ResourceHandler::createImage( GraphContext & context + ResourceHandler::CreatedT< Image > ResourceHandler::createImage( GraphContext & context , ImageId imageId ) { - ResourceHandler::CreatedT< VkImage > result{}; + CreatedT< Image > result{}; + lock_type lock( m_imagesMutex ); + auto [it, ins] = m_images.try_emplace( imageId, nullptr ); - if ( context.vkCreateImage ) + if ( ins ) { - lock_type lock( m_imagesMutex ); - auto [it, ins] = m_images.try_emplace( imageId, std::pair< VkImage, VkDeviceMemory >{} ); - - if ( ins && context.device ) - { - // Create image - auto createInfo = reshdl::convert( *imageId.data ); - auto res = context.vkCreateImage( context.device - , &createInfo - , context.allocator - , &it->second.first ); - result.resource = it->second.first; - checkVkResult( res, "Image creation" ); - crgRegisterObjectName( context, imageId.data->name, result.resource ); - - // Create Image memory - VkMemoryRequirements requirements{}; - context.vkGetImageMemoryRequirements( context.device - , result.resource - , &requirements ); - uint32_t deduced = context.deduceMemoryType( requirements.memoryTypeBits - , getMemoryPropertyFlags( imageId.data->info.memory ) ); - VkMemoryAllocateInfo allocateInfo{ VK_STRUCTURE_TYPE_MEMORY_ALLOCATE_INFO - , nullptr - , requirements.size - , deduced }; - res = context.vkAllocateMemory( context.device - , &allocateInfo - , context.allocator - , &it->second.second ); - result.memory = it->second.second; - checkVkResult( res, "Image memory allocation" ); - crgRegisterObjectName( context, imageId.data->name, result.memory ); - - // Bind image and memory - res = context.vkBindImageMemory( context.device - , result.resource - , result.memory - , 0u ); - checkVkResult( res, "Image memory binding" ); - result.created = true; - } - else - { - result.resource = it->second.first; - result.memory = it->second.second; - } + it->second = std::make_unique< Image >( *this, context, imageId, createImageMemory( context, imageId ) ); + result.created = true; } + result.resource = it->second.get(); return result; } @@ -358,7 +361,7 @@ namespace crg if ( ins ) { - auto image = createImage( context, view.data->image ).resource; + auto image = createImage( context, view.data->image ).resource->getImage(); auto createInfo = reshdl::convert( *view.data, image ); auto res = context.vkCreateImageView( context.device , &createInfo @@ -437,20 +440,20 @@ namespace crg , bufferId , { 0u, bufferId.data->info.size } } ) ); vertexBuffer = result.get(); + auto buffer = createBuffer( context, vertexBuffer->buffer.data->buffer ).resource->m_pages[0]; if ( context.device ) { - auto created = createBuffer( context, vertexBuffer->buffer.data->buffer ); - reshdl::Quad::Vertex * buffer{}; + reshdl::Quad::Vertex * bufferData{}; auto res = context.vkMapMemory( context.device - , created.memory + , buffer.memory , 0u , VK_WHOLE_SIZE , 0u - , reinterpret_cast< void ** >( &buffer ) ); + , reinterpret_cast< void ** >( &bufferData ) ); checkVkResult( res, "Buffer memory mapping" ); - if ( buffer ) + if ( bufferData ) { auto rangeU = 1.0; auto minU = 0.0; @@ -466,34 +469,34 @@ namespace crg { reshdl::Quad::Vertex{ reshdl::Quad::Data{ -1.0f, -3.0f }, reshdl::Quad::Data{ realMinU, realMinV } } , reshdl::Quad::Vertex{ reshdl::Quad::Data{ -1.0f, +1.0f }, reshdl::Quad::Data{ realMinU, realMaxV } } , reshdl::Quad::Vertex{ reshdl::Quad::Data{ +3.0f, +1.0f }, reshdl::Quad::Data{ realMaxU, realMaxV } } }; - std::copy( vertexData.begin(), vertexData.end(), buffer ); + std::copy( vertexData.begin(), vertexData.end(), bufferData ); VkMappedMemoryRange memoryRange{ VK_STRUCTURE_TYPE_MAPPED_MEMORY_RANGE , nullptr - , created.memory + , buffer.memory , 0u , VK_WHOLE_SIZE }; context.vkFlushMappedMemoryRanges( context.device, 1u, &memoryRange ); - context.vkUnmapMemory( context.device, created.memory ); + context.vkUnmapMemory( context.device, buffer.memory ); } + } - vertexBuffer->vertexAttribs.push_back( { 0u, 0u, VK_FORMAT_R32G32_SFLOAT, offsetof( reshdl::Quad::Vertex, position ) } ); - - if ( texCoords ) - { - vertexBuffer->vertexAttribs.push_back( { 1u, 0u, VK_FORMAT_R32G32_SFLOAT, offsetof( reshdl::Quad::Vertex, texture ) } ); - } + vertexBuffer->vertexAttribs.push_back( { 0u, 0u, VK_FORMAT_R32G32_SFLOAT, offsetof( reshdl::Quad::Vertex, position ) } ); - vertexBuffer->vertexBindings.push_back( { 0u, sizeof( reshdl::Quad::Vertex ), VK_VERTEX_INPUT_RATE_VERTEX } ); - vertexBuffer->inputState = VkPipelineVertexInputStateCreateInfo{ VK_STRUCTURE_TYPE_PIPELINE_VERTEX_INPUT_STATE_CREATE_INFO - , nullptr - , 0u - , uint32_t( vertexBuffer->vertexBindings.size() ) - , vertexBuffer->vertexBindings.data() - , uint32_t( vertexBuffer->vertexAttribs.size() ) - , vertexBuffer->vertexAttribs.data() }; + if ( texCoords ) + { + vertexBuffer->vertexAttribs.push_back( { 1u, 0u, VK_FORMAT_R32G32_SFLOAT, offsetof( reshdl::Quad::Vertex, texture ) } ); } + vertexBuffer->vertexBindings.push_back( { 0u, sizeof( reshdl::Quad::Vertex ), VK_VERTEX_INPUT_RATE_VERTEX } ); + vertexBuffer->inputState = VkPipelineVertexInputStateCreateInfo{ VK_STRUCTURE_TYPE_PIPELINE_VERTEX_INPUT_STATE_CREATE_INFO + , nullptr + , 0u + , uint32_t( vertexBuffer->vertexBindings.size() ) + , vertexBuffer->vertexBindings.data() + , uint32_t( vertexBuffer->vertexAttribs.size() ) + , vertexBuffer->vertexAttribs.data() }; + m_vertexBuffers.emplace( std::move( result ) ); } @@ -508,14 +511,28 @@ namespace crg if ( it != m_buffers.end() ) { - if ( context.vkDestroyBuffer && it->second.first ) + if ( bufferId.data->maxPages > 1u ) { - context.vkDestroyBuffer( context.device, it->second.first, context.allocator ); + if ( auto itPaged = std::find( m_pagedBuffers.begin(), m_pagedBuffers.end(), it->second.get() ); + itPaged != m_pagedBuffers.end() ) + { + m_pagedBuffers.erase( itPaged ); + } } - if ( context.vkFreeMemory && it->second.second ) + for ( uint32_t pageIndex = 0u; pageIndex < it->second->getAllocatedPageCount(); ++pageIndex ) { - context.vkFreeMemory( context.device, it->second.second, context.allocator ); + auto page = it->second->getPage( pageIndex ); + + if ( context.vkDestroyBuffer && page.buffer ) + { + context.vkDestroyBuffer( context.device, page.buffer, context.allocator ); + } + + if ( context.vkFreeMemory && page.memory ) + { + context.vkFreeMemory( context.device, page.memory, context.allocator ); + } } m_buffers.erase( it ); @@ -547,14 +564,16 @@ namespace crg if ( it != m_images.end() ) { - if ( context.vkDestroyImage && it->second.first ) + if ( auto image = it->second->getImage(); + context.vkDestroyImage && image ) { - context.vkDestroyImage( context.device, it->second.first, context.allocator ); + context.vkDestroyImage( context.device, image, context.allocator ); } - if ( context.vkFreeMemory && it->second.second ) + if ( auto memory = it->second->getMemory(); + context.vkFreeMemory && memory ) { - context.vkFreeMemory( context.device, it->second.second, context.allocator ); + context.vkFreeMemory( context.device, memory, context.allocator ); } m_images.erase( it ); @@ -617,6 +636,121 @@ namespace crg } } + BufferMemory ResourceHandler::createBufferMemory( GraphContext & context + , BufferId bufferId ) + { + auto itId = m_bufferIds.find( bufferId ); + + if ( itId == m_bufferIds.end() ) + { + Logger::logError( "Can't create a buffer from a buffer ID not handled by this resource handler" ); + CRG_Exception( "Can't create a buffer from a buffer ID not handled by this resource handler" ); + } + + BufferMemory result{}; + + if ( context.vkCreateBuffer + && context.vkGetBufferMemoryRequirements + && context.vkAllocateMemory + && context.vkBindBufferMemory ) + { + // Create buffer + auto createInfo = reshdl::convert( *bufferId.data ); + auto res = context.vkCreateBuffer( context.device + , &createInfo + , context.allocator + , &result.buffer ); + checkVkResult( res, "Buffer creation" ); + crgRegisterObjectName( context, bufferId.data->name, result.buffer ); + + // Create Buffer memory + VkMemoryRequirements requirements{}; + context.vkGetBufferMemoryRequirements( context.device + , result.buffer + , &requirements ); + uint32_t deduced = context.deduceMemoryType( requirements.memoryTypeBits + , getMemoryPropertyFlags( bufferId.data->info.memory ) ); + VkMemoryAllocateInfo allocateInfo{ VK_STRUCTURE_TYPE_MEMORY_ALLOCATE_INFO + , nullptr + , requirements.size + , deduced }; + res = context.vkAllocateMemory( context.device + , &allocateInfo + , context.allocator + , &result.memory ); + checkVkResult( res, "Buffer memory allocation" ); + crgRegisterObjectName( context, bufferId.data->name, result.memory ); + + // Bind buffer and memory + res = context.vkBindBufferMemory( context.device + , result.buffer + , result.memory + , 0u ); + checkVkResult( res, "Buffer memory binding" ); + + // Update allocated pages count + auto bufferData = itId->second.get(); + ++bufferData->allocatedPages; + } + + return result; + } + + ImageMemory ResourceHandler::createImageMemory( GraphContext & context + , ImageId imageId ) + { + if ( auto itId = m_imageIds.find( imageId ); + itId == m_imageIds.end() ) + { + Logger::logError( "Can't create an image from an image ID not handled by this resource handler" ); + CRG_Exception( "Can't create an image from an image ID not handled by this resource handler" ); + } + + ImageMemory result{}; + + if ( context.vkCreateImage + && context.vkGetImageMemoryRequirements + && context.vkAllocateMemory + && context.vkBindImageMemory ) + { + // Create image + auto createInfo = reshdl::convert( *imageId.data ); + auto res = context.vkCreateImage( context.device + , &createInfo + , context.allocator + , &result.image ); + checkVkResult( res, "Image creation" ); + crgRegisterObjectName( context, imageId.data->name, result.image ); + + // Create Image memory + VkMemoryRequirements requirements{}; + context.vkGetImageMemoryRequirements( context.device + , result.image + , &requirements ); + uint32_t deduced = context.deduceMemoryType( requirements.memoryTypeBits + , getMemoryPropertyFlags( imageId.data->info.memory ) ); + VkMemoryAllocateInfo allocateInfo{ VK_STRUCTURE_TYPE_MEMORY_ALLOCATE_INFO + , nullptr + , requirements.size + , deduced }; + res = context.vkAllocateMemory( context.device + , &allocateInfo + , context.allocator + , &result.memory ); + checkVkResult( res, "Image memory allocation" ); + crgRegisterObjectName( context, imageId.data->name, result.memory ); + + // Bind image and memory + res = context.vkBindImageMemory( context.device + , result.image + , result.memory + , 0u ); + checkVkResult( res, "Image memory binding" ); + } + + return result; + } + //********************************************************************************************* ContextResourcesCache::ContextResourcesCache( ResourceHandler & handler @@ -659,23 +793,16 @@ namespace crg } } - VkBuffer ContextResourcesCache::createBuffer( BufferId const & buffer ) - { - VkDeviceMemory memory{}; - return createBuffer( buffer, memory ); - } - - VkBuffer ContextResourcesCache::createBuffer( BufferId const & buffer, VkDeviceMemory & memory ) + Buffer & ContextResourcesCache::createBuffer( BufferId const & bufferId ) { - auto [created, result, mem] = m_handler.createBuffer( m_context, buffer ); + auto [created, buffer] = m_handler.createBuffer( m_context, bufferId ); if ( created ) { - m_buffers[buffer] = result; + m_buffers.try_emplace( bufferId, buffer ); } - memory = mem; - return result; + return *buffer; } VkBufferView ContextResourcesCache::createBufferView( BufferViewId const & view ) @@ -684,19 +811,25 @@ namespace crg if ( created ) { - m_bufferViews[view] = result; + m_bufferViews.try_emplace( view, result ); } return result; } + bool ContextResourcesCache::destroyBuffer( Buffer const & buffer ) + { + return destroyBuffer( buffer.getBufferId() ); + } + bool ContextResourcesCache::destroyBuffer( BufferId const & bufferId ) { - auto it = m_buffers.find( bufferId ); - auto result = it != m_buffers.end(); + bool result{}; - if ( result ) + if ( auto it = m_buffers.find( bufferId ); + it != m_buffers.end() ) { + result = true; m_handler.destroyBuffer( m_context, bufferId ); } @@ -716,23 +849,16 @@ namespace crg return result; } - VkImage ContextResourcesCache::createImage( ImageId const & image ) + Image & ContextResourcesCache::createImage( ImageId const & imageId ) { - VkDeviceMemory memory{}; - return createImage( image, memory ); - } - - VkImage ContextResourcesCache::createImage( ImageId const & image, VkDeviceMemory & memory ) - { - auto [created, result, mem] = m_handler.createImage( m_context, image ); + auto [created, image] = m_handler.createImage( m_context, imageId ); if ( created ) { - m_images[image] = result; + m_images.try_emplace( imageId, image ); } - memory = mem; - return result; + return *image; } VkImageView ContextResourcesCache::createImageView( ImageViewId const & view ) @@ -747,6 +873,11 @@ namespace crg return result; } + bool ContextResourcesCache::destroyImage( Image const & image ) + { + return destroyImage( image.getImageId() ); + } + bool ContextResourcesCache::destroyImage( ImageId const & imageId ) { auto it = m_images.find( imageId ); @@ -812,15 +943,16 @@ namespace crg { } - VkBuffer ResourcesCache::createBuffer( GraphContext & context - , BufferId const & bufferId - , VkDeviceMemory & memory ) + void ResourcesCache::destroyContext( GraphContext & context ) { - auto & cache = getContextCache( context ); - return cache.createBuffer( bufferId, memory ); + if ( auto it = m_caches.find( &context ); + it != m_caches.end() ) + { + m_caches.erase( it ); + } } - VkBuffer ResourcesCache::createBuffer( GraphContext & context + Buffer & ResourcesCache::createBuffer( GraphContext & context , BufferId const & bufferId ) { auto & cache = getContextCache( context ); @@ -870,15 +1002,7 @@ namespace crg return cache.destroyBufferView( viewId ); } - VkImage ResourcesCache::createImage( GraphContext & context - , ImageId const & imageId - , VkDeviceMemory & memory ) - { - auto & cache = getContextCache( context ); - return cache.createImage( imageId, memory ); - } - - VkImage ResourcesCache::createImage( GraphContext & context + Image & ResourcesCache::createImage( GraphContext & context , ImageId const & imageId ) { auto & cache = getContextCache( context ); diff --git a/source/RenderGraph/RunnableGraph.cpp b/source/RenderGraph/RunnableGraph.cpp index 8238738..d118266 100644 --- a/source/RenderGraph/RunnableGraph.cpp +++ b/source/RenderGraph/RunnableGraph.cpp @@ -181,23 +181,45 @@ namespace crg , uint32_t index , RunnableGraph & graph ) { + auto bufferViewId = attach.buffer( index ); WriteDescriptorSet result{ binding , 0u - , count + , count * bufferViewId.data->buffer.data->maxPages , getDescriptorType( attach ) }; - auto bufferViewId = attach.buffer( index ); - VkDescriptorBufferInfo info{ graph.createBuffer( bufferViewId.data->buffer ) - , getSubresourceRange( bufferViewId ).offset - , getSubresourceRange( bufferViewId ).size }; + auto subresourceRange = getSubresourceRange( bufferViewId ); + Buffer const & buffer = graph.createBuffer( bufferViewId.data->buffer ); if ( attach.isView() ) { + VkDescriptorBufferInfo info{ buffer.getBuffer() + , subresourceRange.offset + , subresourceRange.size }; result.bufferViewInfo.push_back( info ); result.texelBufferView.push_back( graph.createBufferView( bufferViewId ) ); } else { - result.bufferInfo.push_back( info ); + auto remainingSize = uint32_t( subresourceRange.size ); + auto pageSize = uint32_t( bufferViewId.data->buffer.data->info.size ); + + // Bind the allocated pages + for ( uint32_t pageIndex = 0u; pageIndex < bufferViewId.data->buffer.data->allocatedPages; ++pageIndex ) + { + uint32_t currentSize = std::min( remainingSize, pageSize - uint32_t( subresourceRange.offset ) ); + VkDescriptorBufferInfo info{ buffer.getBuffer( pageIndex ) + , subresourceRange.offset, currentSize }; + result.bufferInfo.push_back( info ); + subresourceRange.offset = 0; + remainingSize -= currentSize; + } + + // To prevent validation errors when we don't have enough allocated pages, we need to add dummy descriptors for the remaining pages. + for ( uint32_t pageIndex = bufferViewId.data->buffer.data->allocatedPages; pageIndex < bufferViewId.data->buffer.data->maxPages; ++pageIndex ) + { + VkDescriptorBufferInfo info{ buffer.getBuffer( 0u ) + , 0u, pageSize }; + result.bufferInfo.push_back( info ); + } } return result; @@ -243,7 +265,7 @@ namespace crg , m_nodes{ std::move( nodes ) } , m_rootNode{ std::move( rootNode ) } , m_timerQueries{ m_context - , createQueryPool( m_context, m_graph.getName() + "TimerQueries", uint32_t( ( m_nodes.size() + 1u ) * 2u * 2u ) ) + , createQueryPool( m_context, m_graph.getName() + "TimerQueries", uint32_t( ( m_nodes.size() + 1u ) * 2u * 8u ) ) , []( GraphContext & ctx, VkQueryPool & object )noexcept { crgUnregisterObject( ctx, object ); @@ -358,7 +380,7 @@ namespace crg { auto block( m_timer.start() ); m_states.clear(); - RecordContext recordContext{ m_resources }; + RecordContext & recordContext = getRecordContext(); for ( auto & dependency : m_graph.getDependencies() ) { @@ -432,10 +454,17 @@ namespace crg SemaphoreWaitArray RunnableGraph::run( SemaphoreWaitArray const & toWait , VkQueue queue ) { + ResourceHandler const & handler = m_graph.getHandler(); + for ( auto & pagedBuffer : handler.getPagedBuffers() ) + { + pagedBuffer->update(); + } + record(); - std::vector< VkSemaphore > semaphores; - std::vector< VkPipelineStageFlags > dstStageMasks; - convert( toWait, semaphores, dstStageMasks ); + // Reuse member vectors instead of allocating new ones each frame + m_cachedSemaphores.clear(); + m_cachedDstStageMasks.clear(); + convert( toWait, m_cachedSemaphores, m_cachedDstStageMasks ); m_timer.notifyPassRender(); for ( auto const & pass : m_passes ) @@ -445,9 +474,9 @@ namespace crg VkSubmitInfo submitInfo{ VK_STRUCTURE_TYPE_SUBMIT_INFO , nullptr - , uint32_t( semaphores.size() ) - , semaphores.data() - , dstStageMasks.data() + , uint32_t( m_cachedSemaphores.size() ) + , m_cachedSemaphores.data() + , m_cachedDstStageMasks.data() , 1u , &m_commandBuffer , 1u @@ -462,7 +491,7 @@ namespace crg , m_graph.getFinalStates().getCurrPipelineState().pipelineStage } }; } - VkBuffer RunnableGraph::createBuffer( BufferId const & buffer ) + Buffer & RunnableGraph::createBuffer( BufferId const & buffer ) { return m_resources.createBuffer( buffer ); } @@ -472,7 +501,7 @@ namespace crg return m_resources.createBufferView( view ); } - VkImage RunnableGraph::createImage( ImageId const & image ) + Image & RunnableGraph::createImage( ImageId const & image ) { return m_resources.createImage( image ); } diff --git a/source/RenderGraph/RunnablePass.cpp b/source/RenderGraph/RunnablePass.cpp index cc09fc7..c5b31d8 100644 --- a/source/RenderGraph/RunnablePass.cpp +++ b/source/RenderGraph/RunnablePass.cpp @@ -120,6 +120,12 @@ namespace crg if ( attach.isClearableImage() ) { + auto wasBatching = recordContext.isBatching(); + if ( wasBatching ) + { + recordContext.flushBatchBarriers( commandBuffer ); + } + recordContext.memoryBarrier( commandBuffer , view , currentLayout.layout @@ -130,7 +136,7 @@ namespace crg { VkClearColorValue colour{}; recordContext->vkCmdClearColorImage( commandBuffer - , graph.createImage( view.data->image ) + , graph.createImage( view.data->image ).getImage() , VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL , &colour , 1u, &subresourceRange ); @@ -139,7 +145,7 @@ namespace crg { VkClearDepthStencilValue depthStencil{}; recordContext->vkCmdClearDepthStencilImage( commandBuffer - , graph.createImage( view.data->image ) + , graph.createImage( view.data->image ).getImage() , VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL , &depthStencil , 1u, &subresourceRange ); @@ -148,6 +154,11 @@ namespace crg currentLayout.layout = ImageLayout::eTransferDst; currentLayout.state.access = AccessFlags::eTransferWrite; currentLayout.state.pipelineStage = PipelineStageFlags::eTransfer; + + if ( wasBatching ) + { + recordContext.beginBatchBarriers(); + } } recordContext.memoryBarrier( commandBuffer @@ -157,6 +168,39 @@ namespace crg } } + static AccessState clearBuffer( VkCommandBuffer commandBuffer + , BufferId bufferId + , BufferSubresourceRange const & range + , AccessState const & currentState + , RunnableGraph & graph + , RecordContext & recordContext ) + { + recordContext.memoryBarrier( commandBuffer + , bufferId + , range + , currentState + , { AccessFlags::eTransferWrite, PipelineStageFlags::eTransfer } ); + auto [pageMin, pageCount] = getBufferPageRange( bufferId, range ); + auto pageSize = details::getAlignedSize( bufferId.data->info.size, 4u ); + auto offset = DeviceSize( range.offset == 0u ? 0u : details::getAlignedSize( range.offset, 4u ) ); + auto remainingSize = DeviceSize( range.size == VK_WHOLE_SIZE ? VK_WHOLE_SIZE : details::getAlignedSize( range.size, 4u ) ); + auto buffer = &graph.createBuffer( bufferId ); + + for ( uint32_t pageIndex = pageMin; pageIndex < std::min( pageMin + pageCount, buffer->getAllocatedPageCount() ); ++pageIndex ) + { + auto currentPageSize = range.size == VK_WHOLE_SIZE ? VK_WHOLE_SIZE : std::min( pageSize - offset, remainingSize ); + recordContext->vkCmdFillBuffer( commandBuffer + , buffer->getBuffer( pageIndex ) + , 0, currentPageSize + , 0u ); + offset = 0; + remainingSize -= ( range.size == VK_WHOLE_SIZE ? 0 : currentPageSize ); + } + + return AccessState{ .access = AccessFlags::eTransferWrite + , .pipelineStage = PipelineStageFlags::eTransfer }; + } + static void prepareBuffer( VkCommandBuffer commandBuffer , uint32_t index , Attachment const & attach @@ -172,28 +216,28 @@ namespace crg if ( !attach.isNoTransition() && ( attach.isStorageBuffer() || attach.isTransferBuffer() || attach.isTransitionBuffer() ) ) { - auto buffer = view.data->buffer; + auto bufferId = view.data->buffer; auto & range = getSubresourceRange( view ); auto currentState = recordContext.getAccessState( view ); if ( attach.isClearableBuffer() ) { - recordContext.memoryBarrier( commandBuffer - , buffer - , range - , currentState - , { AccessFlags::eTransferWrite, PipelineStageFlags::eTransfer } ); - recordContext->vkCmdFillBuffer( commandBuffer - , graph.createBuffer( buffer ) - , range.offset == 0u ? 0u : details::getAlignedSize( range.offset, 4u ) - , range.size == VK_WHOLE_SIZE ? VK_WHOLE_SIZE : details::getAlignedSize( range.size, 4u ) - , 0u ); - currentState.access = AccessFlags::eTransferWrite; - currentState.pipelineStage = PipelineStageFlags::eTransfer; + auto wasBatching = recordContext.isBatching(); + if ( wasBatching ) + { + recordContext.flushBatchBarriers( commandBuffer ); + } + + currentState = clearBuffer( commandBuffer, bufferId, range, currentState, graph, recordContext ); + + if ( wasBatching ) + { + recordContext.beginBatchBarriers(); + } } recordContext.memoryBarrier( commandBuffer - , buffer + , bufferId , range , currentState , { attach.getAccessMask(), attach.getPipelineStageFlags( isComputePass ) } ); @@ -208,6 +252,8 @@ namespace crg , RunnablePass::Callbacks const & callbacks , GraphContext const & graphContext ) { + recordContext.beginBatchBarriers(); + for ( auto & [binding, attach] : pass.getSampled() ) prepareImage( commandBuffer, index, *attach.attach, graphContext.separateDepthStencilLayouts, graph, recordContext ); for ( auto & [binding, attach] : pass.getUniforms() ) @@ -229,6 +275,8 @@ namespace crg prepareBuffer( commandBuffer, index, *attach, callbacks.isComputePass(), graph, recordContext ); for ( auto & attach : pass.getTargets() ) prepareImage( commandBuffer, index, *attach, graphContext.separateDepthStencilLayouts, graph, recordContext ); + + recordContext.flushBatchBarriers( commandBuffer ); } } @@ -265,70 +313,7 @@ namespace crg //********************************************************************************************* - RunnablePass::Callbacks::Callbacks( InitialiseCallback initialise - , GetPipelineStateCallback getPipelineState ) - : Callbacks{ std::move( initialise ) - , std::move( getPipelineState ) - , getDefaultV< RecordCallback >() - , getDefaultV< GetPassIndexCallback >() - , getDefaultV< IsEnabledCallback >() - , getDefaultV< IsComputePassCallback >() } - { - } - - RunnablePass::Callbacks::Callbacks( InitialiseCallback initialise - , GetPipelineStateCallback getPipelineState - , RecordCallback record ) - : Callbacks{ std::move( initialise ) - , std::move( getPipelineState ) - , std::move( record ) - , getDefaultV< GetPassIndexCallback >() - , getDefaultV< IsEnabledCallback >() - , getDefaultV< IsComputePassCallback >() } - { - } - - RunnablePass::Callbacks::Callbacks( InitialiseCallback initialise - , GetPipelineStateCallback getPipelineState - , RecordCallback record - , GetPassIndexCallback getPassIndex ) - : Callbacks{ std::move( initialise ) - , std::move( getPipelineState ) - , std::move( record ) - , std::move( getPassIndex ) - , getDefaultV< IsEnabledCallback >() - , getDefaultV< IsComputePassCallback >() } - { - } - - RunnablePass::Callbacks::Callbacks( InitialiseCallback initialise - , GetPipelineStateCallback getPipelineState - , RecordCallback record - , GetPassIndexCallback getPassIndex - , IsEnabledCallback isEnabled ) - : Callbacks{ std::move( initialise ) - , std::move( getPipelineState ) - , std::move( record ) - , std::move( getPassIndex ) - , std::move( isEnabled ) - , getDefaultV< IsComputePassCallback >() } - { - } - - RunnablePass::Callbacks::Callbacks( InitialiseCallback initialise - , GetPipelineStateCallback getPipelineState - , RecordCallback record - , GetPassIndexCallback getPassIndex - , IsEnabledCallback isEnabled - , IsComputePassCallback isComputePass ) - : initialise{ std::move( initialise ) } - , getPipelineState{ std::move( getPipelineState ) } - , record{ std::move( record ) } - , getPassIndex{ std::move( getPassIndex ) } - , isEnabled{ std::move( isEnabled ) } - , isComputePass{ std::move( isComputePass ) } - { - } + RunnablePass::Callbacks::Callbacks() = default; //********************************************************************************************* diff --git a/source/RenderGraph/RunnablePasses/BufferCopy.cpp b/source/RenderGraph/RunnablePasses/BufferCopy.cpp index 0c6e810..3f2017a 100644 --- a/source/RenderGraph/RunnablePasses/BufferCopy.cpp +++ b/source/RenderGraph/RunnablePasses/BufferCopy.cpp @@ -5,6 +5,7 @@ See LICENSE file in root folder. #include "RenderGraph/RunnablePasses/BufferCopy.hpp" #include "RenderGraph/GraphContext.hpp" +#include "RenderGraph/Log.hpp" #include "RenderGraph/RunnableGraph.hpp" #include @@ -22,22 +23,30 @@ namespace crg : RunnablePass{ pass , context , graph - , { defaultV< InitialiseCallback > - , GetPipelineStateCallback( [](){ return crg::getPipelineState( PipelineStageFlags::eTransfer ); } ) - , [this]( RecordContext & recContext, VkCommandBuffer cb, uint32_t i ){ doRecordInto( recContext, cb, i ); } - , std::move( passIndex ) - , std::move( isEnabled ) } + , RunnablePass::Callbacks{} + .onGetPipelineState( [](){ return crg::getPipelineState( PipelineStageFlags::eTransfer ); } ) + .onRecord( [this]( RecordContext & recContext, VkCommandBuffer cb, uint32_t i ){ doRecordInto( recContext, cb, i ); } ) + .onGetPassIndex( std::move( passIndex ) ) + .onIsEnabled( std::move( isEnabled ) ) , std::move( ruConfig ) } , m_copyOffset{ copyOffset } , m_copyRange{ copyRange } { - assert( getPass().getInputs().size() == getPass().getOutputs().size() ); + if ( getPass().getInputs().size() != getPass().getOutputs().size() ) + { + Logger::logError( "BufferCopy - Inputs and outputs sizes are different." ); + } } void BufferCopy::doRecordInto( RecordContext & context , VkCommandBuffer commandBuffer , uint32_t index )const { + if ( getPass().getInputs().size() != getPass().getOutputs().size() ) + { + return; + } + auto srcIt = getPass().getInputs().begin(); auto dstIt = getPass().getOutputs().begin(); @@ -48,30 +57,36 @@ namespace crg auto dstView{ dstIt->second->buffer( index ) }; auto srcBufferRange{ getSubresourceRange( srcView ) }; auto dstBufferRange{ getSubresourceRange( dstView ) }; - auto srcBuffer{ getGraph().createBuffer( srcView.data->buffer ) }; - auto dstBuffer{ getGraph().createBuffer( dstView.data->buffer ) }; - // Copy source to target. - VkBufferCopy copyRegion{ srcBufferRange.offset + m_copyOffset - , dstBufferRange.offset + m_copyOffset - , m_copyRange }; - context.memoryBarrier( commandBuffer - , srcView - , { AccessFlags::eShaderWrite, PipelineStageFlags::eFragmentShader } + auto [srcPageMin, srcPageCount] = getBufferPageRange( srcView.data->buffer, { srcBufferRange.offset + m_copyOffset, m_copyRange } ); + auto [dstPageMin, dstPageCount] = getBufferPageRange( dstView.data->buffer, { dstBufferRange.offset + m_copyOffset, m_copyRange } ); + + if ( srcPageCount > 1 || dstPageCount > 1 ) + { + Logger::logError( "BufferCopy - Source [" + srcView.data->name + "] or destination [" + dstView.data->name + "] buffer views have more than one page, this is currently unsupported." ); + } + else + { + auto srcPageSize = srcView.data->buffer.data->info.size; + auto dstPageSize = dstView.data->buffer.data->info.size; + auto srcBuffer{ &getGraph().createBuffer( srcView.data->buffer ) }; + auto dstBuffer{ &getGraph().createBuffer( dstView.data->buffer ) }; + // Copy source to target. + VkBufferCopy copyRegion{ srcBufferRange.offset + m_copyOffset - srcPageMin * srcPageSize + , dstBufferRange.offset + m_copyOffset - dstPageMin * dstPageSize + , m_copyRange }; + context.memoryBarrier( commandBuffer + , srcView + , { AccessFlags::eShaderWrite, PipelineStageFlags::eFragmentShader } , { AccessFlags::eTransferRead, PipelineStageFlags::eTransfer } ); - context.memoryBarrier( commandBuffer - , dstView - , { AccessFlags::eTransferWrite, PipelineStageFlags::eTransfer } ); - context->vkCmdCopyBuffer( commandBuffer - , srcBuffer - , dstBuffer - , 1u - , ©Region ); - context.memoryBarrier( commandBuffer - , dstView - , { AccessFlags::eShaderRead, PipelineStageFlags::eComputeShader } ); - context.memoryBarrier( commandBuffer - , srcView - , { AccessFlags::eShaderWrite, PipelineStageFlags::eFragmentShader } ); + context.memoryBarrier( commandBuffer + , dstView + , { AccessFlags::eTransferWrite, PipelineStageFlags::eTransfer } ); + context->vkCmdCopyBuffer( commandBuffer + , srcBuffer->getBuffer( srcPageMin ) + , dstBuffer->getBuffer( dstPageMin ) + , 1u + , ©Region ); + } ++srcIt; ++dstIt; } diff --git a/source/RenderGraph/RunnablePasses/BufferToImageCopy.cpp b/source/RenderGraph/RunnablePasses/BufferToImageCopy.cpp index c8800d0..3458850 100644 --- a/source/RenderGraph/RunnablePasses/BufferToImageCopy.cpp +++ b/source/RenderGraph/RunnablePasses/BufferToImageCopy.cpp @@ -5,6 +5,7 @@ See LICENSE file in root folder. #include "RenderGraph/RunnablePasses/BufferToImageCopy.hpp" #include "RenderGraph/GraphContext.hpp" +#include "RenderGraph/Log.hpp" #include "RenderGraph/RunnableGraph.hpp" #include @@ -22,22 +23,30 @@ namespace crg : RunnablePass{ pass , context , graph - , { defaultV< InitialiseCallback > - , GetPipelineStateCallback( [](){ return crg::getPipelineState( PipelineStageFlags::eTransfer ); } ) - , [this]( RecordContext const & recContext, VkCommandBuffer cb, uint32_t i ){ doRecordInto( recContext, cb, i ); } - , std::move( passIndex ) - , std::move( isEnabled ) } + , RunnablePass::Callbacks{} + .onGetPipelineState( [](){ return crg::getPipelineState( PipelineStageFlags::eTransfer ); } ) + .onRecord( [this]( RecordContext const & recContext, VkCommandBuffer cb, uint32_t i ){ doRecordInto( recContext, cb, i ); } ) + .onGetPassIndex( std::move( passIndex ) ) + .onIsEnabled( std::move( isEnabled ) ) , std::move( ruConfig ) } , m_copyOffset{ convert( copyOffset ) } , m_copySize{ convert( copySize ) } { - assert( getPass().getInputs().size() == getPass().getOutputs().size() ); + if ( getPass().getInputs().size() != getPass().getOutputs().size() ) + { + Logger::logError( "BufferToImageCopy - Inputs and outputs sizes are different." ); + } } void BufferToImageCopy::doRecordInto( RecordContext const & context , VkCommandBuffer commandBuffer , uint32_t index )const { + if ( getPass().getInputs().size() != getPass().getOutputs().size() ) + { + return; + } + auto srcIt = getPass().getInputs().begin(); auto dstIt = getPass().getOutputs().begin(); @@ -46,8 +55,13 @@ namespace crg { auto srcAttach{ srcIt->second->buffer( index ) }; auto dstAttach{ dstIt->second->view( index ) }; - auto srcBuffer{ getGraph().createBuffer( srcAttach.data->buffer ) }; - auto dstImage{ getGraph().createImage( dstAttach.data->image ) }; + auto dstImage{ &getGraph().createImage( dstAttach.data->image ) }; + auto srcBuffer{ &getGraph().createBuffer( srcAttach.data->buffer ) }; + if ( srcAttach.data->buffer.data->maxPages > 1 ) + { + Logger::logWarning( "BufferToImageCopy - Source buffer [" + srcAttach.data->name + "] has more than one page, only the first one will be used." ); + } + // Copy source to target. auto range = getSubresourceLayers( getSubresourceRange( dstAttach ) ); VkBufferImageCopy copyRegion{ 0ULL @@ -57,8 +71,8 @@ namespace crg , m_copyOffset , m_copySize }; context->vkCmdCopyBufferToImage( commandBuffer - , srcBuffer - , dstImage + , srcBuffer->getBuffer() + , dstImage->getImage() , VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL , 1u , ©Region ); diff --git a/source/RenderGraph/RunnablePasses/ComputePass.cpp b/source/RenderGraph/RunnablePasses/ComputePass.cpp index 1ea4664..89394ec 100644 --- a/source/RenderGraph/RunnablePasses/ComputePass.cpp +++ b/source/RenderGraph/RunnablePasses/ComputePass.cpp @@ -4,6 +4,7 @@ See LICENSE file in root folder. #include "RenderGraph/RunnablePasses/ComputePass.hpp" #include "RenderGraph/GraphContext.hpp" +#include "RenderGraph/Log.hpp" #include "RenderGraph/RunnableGraph.hpp" #include @@ -26,26 +27,27 @@ namespace crg : RunnablePass{ pass , context , graph - , { [this]( uint32_t index ){ doInitialise( index ); } - , GetPipelineStateCallback( [](){ return crg::getPipelineState( PipelineStageFlags::eComputeShader ); } ) - , [this]( RecordContext & recContext, VkCommandBuffer cb, uint32_t i ){ doRecordInto( recContext, cb, i ); } - , GetPassIndexCallback( [this](){ return doGetPassIndex(); } ) - , IsEnabledCallback( [this](){ return doIsEnabled(); } ) - , IsComputePassCallback( [](){ return true; } ) } + , RunnablePass::Callbacks{} + .onInitialise( [this]( uint32_t index ){ doInitialise( index ); } ) + .onGetPipelineState( [](){ return crg::getPipelineState( PipelineStageFlags::eComputeShader ); } ) + .onRecord( [this]( RecordContext & recContext, VkCommandBuffer cb, uint32_t i ){ doRecordInto( recContext, cb, i ); } ) + .onGetPassIndex( [this](){ return doGetPassIndex(); } ) + .onIsEnabled( [this](){ return doIsEnabled(); } ) + .onIsComputePass( [](){ return true; } ) , ruConfig } - , m_cpConfig{ cpConfig.m_initialise ? std::move( *cpConfig.m_initialise ) : getDefaultV< RunnablePass::InitialiseCallback >() - , cpConfig.m_enabled.has_value() ? std::move( *cpConfig.m_enabled ) : getDefaultV< bool const * >() + , m_cpConfig{ cpConfig.m_initialise ? *cpConfig.m_initialise : defaultV< InitialiseCallback > + , cpConfig.m_enabled.has_value() ? std::move( *cpConfig.m_enabled ) : defaultV< bool const * > , cpConfig.m_isEnabled - , cpConfig.m_getPassIndex ? std::move( *cpConfig.m_getPassIndex ) : getDefaultV< RunnablePass::GetPassIndexCallback >() - , cpConfig.m_recordInto ? std::move( *cpConfig.m_recordInto ) : getDefaultV< RunnablePass::RecordCallback >() - , cpConfig.m_end ? std::move( *cpConfig.m_end ) : getDefaultV< RunnablePass::RecordCallback >() + , cpConfig.m_getPassIndex ? *cpConfig.m_getPassIndex : defaultV< GetPassIndexCallback > + , cpConfig.m_recordInto ? *cpConfig.m_recordInto : defaultV< RecordCallback > + , cpConfig.m_end ? *cpConfig.m_end : defaultV< RecordCallback > , cpConfig.m_groupCountX.has_value() ? *cpConfig.m_groupCountX : 1u , cpConfig.m_groupCountY.has_value() ? *cpConfig.m_groupCountY : 1u , cpConfig.m_groupCountZ.has_value() ? *cpConfig.m_groupCountZ : 1u , cpConfig.m_getGroupCountX ? std::optional< cp::GetGroupCountCallback >( std::move( *cpConfig.m_getGroupCountX ) ) : std::nullopt , cpConfig.m_getGroupCountY ? std::optional< cp::GetGroupCountCallback >( std::move( *cpConfig.m_getGroupCountY ) ) : std::nullopt , cpConfig.m_getGroupCountZ ? std::optional< cp::GetGroupCountCallback >( std::move( *cpConfig.m_getGroupCountZ ) ) : std::nullopt - , cpConfig.m_indirectBuffer ? *cpConfig.m_indirectBuffer : getDefaultV < IndirectBuffer >() } + , cpConfig.m_indirectBuffer ? *cpConfig.m_indirectBuffer : defaultV < IndirectBuffer > } , m_pipeline{ pass , context , graph @@ -97,7 +99,12 @@ namespace crg if ( m_cpConfig.indirectBuffer != defaultV< IndirectBuffer > ) { - auto indirectBuffer = getGraph().createBuffer( m_cpConfig.indirectBuffer.buffer.data->buffer ); + if ( m_cpConfig.indirectBuffer.buffer.data->buffer.data->maxPages > 1 ) + { + Logger::logWarning( "ComputePass - Indirect buffer [" + m_cpConfig.indirectBuffer.buffer.data->name + "] has more than one page, only the first one will be used." ); + } + + auto indirectBuffer = getGraph().createBuffer( m_cpConfig.indirectBuffer.buffer.data->buffer ).getBuffer(); context->vkCmdDispatchIndirect( commandBuffer, indirectBuffer, getSubresourceRange( m_cpConfig.indirectBuffer.buffer ).offset ); } else diff --git a/source/RenderGraph/RunnablePasses/GenerateMipmaps.cpp b/source/RenderGraph/RunnablePasses/GenerateMipmaps.cpp index 6e3f47f..dccb225 100644 --- a/source/RenderGraph/RunnablePasses/GenerateMipmaps.cpp +++ b/source/RenderGraph/RunnablePasses/GenerateMipmaps.cpp @@ -30,11 +30,11 @@ namespace crg : RunnablePass{ pass , context , graph - , { defaultV< InitialiseCallback > - , GetPipelineStateCallback( [](){ return crg::getPipelineState( PipelineStageFlags::eTransfer ); } ) - , [this]( RecordContext & recContext, VkCommandBuffer cb, uint32_t i ){ doRecordInto( recContext, cb, i ); } - , std::move( passIndex ) - , std::move( isEnabled ) } + , RunnablePass::Callbacks{} + .onGetPipelineState( [](){ return crg::getPipelineState( PipelineStageFlags::eTransfer ); } ) + .onRecord( [this]( RecordContext & recContext, VkCommandBuffer cb, uint32_t i ){ doRecordInto( recContext, cb, i ); } ) + .onGetPassIndex( std::move( passIndex ) ) + .onIsEnabled( std::move( isEnabled ) ) , std::move( ruConfig ) } , m_outputLayout{ makeLayoutState( outputLayout ) } { @@ -53,7 +53,7 @@ namespace crg , ImageViewId viewId )const { auto imageId{ viewId.data->image }; - auto image{ getGraph().createImage( imageId ) }; + auto image{ &getGraph().createImage( imageId ) }; auto extent = getExtent( imageId ); auto format = getFormat( imageId ); auto baseArrayLayer = getSubresourceRange( viewId ).baseArrayLayer; @@ -122,9 +122,9 @@ namespace crg // Perform blit context->vkCmdBlitImage( commandBuffer - , image + , image->getImage() , VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL - , image + , image->getImage() , VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL , 1u , &imageBlit diff --git a/source/RenderGraph/RunnablePasses/ImageBlit.cpp b/source/RenderGraph/RunnablePasses/ImageBlit.cpp index 885a73d..483fda1 100644 --- a/source/RenderGraph/RunnablePasses/ImageBlit.cpp +++ b/source/RenderGraph/RunnablePasses/ImageBlit.cpp @@ -23,11 +23,11 @@ namespace crg : RunnablePass{ pass , context , graph - , { defaultV< InitialiseCallback > - , GetPipelineStateCallback( [](){ return crg::getPipelineState( PipelineStageFlags::eTransfer ); } ) - , [this]( RecordContext const & recContext, VkCommandBuffer cb, uint32_t i ){ doRecordInto( recContext, cb, i ); } - , std::move( passIndex ) - , std::move( isEnabled ) } + , RunnablePass::Callbacks{} + .onGetPipelineState( [](){ return crg::getPipelineState( PipelineStageFlags::eTransfer ); } ) + .onRecord( [this]( RecordContext const & recContext, VkCommandBuffer cb, uint32_t i ){ doRecordInto( recContext, cb, i ); } ) + .onGetPassIndex( std::move( passIndex ) ) + .onIsEnabled( std::move( isEnabled ) ) , std::move( ruConfig ) } , m_srcOffset{ convert( blitSrc.offset ) } , m_srcSize{ convert( blitSrc.extent ) } @@ -50,16 +50,16 @@ namespace crg { auto srcAttach{ srcIt->second->view( index ) }; auto dstAttach{ dstIt->second->view( index ) }; - auto srcImage{ getGraph().createImage( srcAttach.data->image ) }; - auto dstImage{ getGraph().createImage( dstAttach.data->image ) }; + auto srcImage{ &getGraph().createImage( srcAttach.data->image ) }; + auto dstImage{ &getGraph().createImage( dstAttach.data->image ) }; VkImageBlit blitRegion{ getSubresourceLayers( getSubresourceRange( srcAttach ) ) , { m_srcOffset, VkOffset3D{ int32_t( m_srcSize.width ), int32_t( m_srcSize.height ), int32_t( m_srcSize.depth ) } } , getSubresourceLayers( getSubresourceRange( dstAttach ) ) , { m_dstOffset, VkOffset3D{ int32_t( m_dstSize.width ), int32_t( m_dstSize.height ), int32_t( m_dstSize.depth ) } } }; context->vkCmdBlitImage( commandBuffer - , srcImage + , srcImage->getImage() , VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL - , dstImage + , dstImage->getImage() , VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL , 1u , &blitRegion diff --git a/source/RenderGraph/RunnablePasses/ImageCopy.cpp b/source/RenderGraph/RunnablePasses/ImageCopy.cpp index fa28c7f..da380b3 100644 --- a/source/RenderGraph/RunnablePasses/ImageCopy.cpp +++ b/source/RenderGraph/RunnablePasses/ImageCopy.cpp @@ -22,11 +22,11 @@ namespace crg : RunnablePass{ pass , context , graph - , { defaultV< InitialiseCallback > - , GetPipelineStateCallback( [](){ return crg::getPipelineState( PipelineStageFlags::eTransfer ); } ) - , [this]( RecordContext & recContext, VkCommandBuffer cb, uint32_t i ){ doRecordInto( recContext, cb, i ); } - , std::move( passIndex ) - , std::move( isEnabled ) } + , RunnablePass::Callbacks{} + .onGetPipelineState( [](){ return crg::getPipelineState( PipelineStageFlags::eTransfer ); } ) + .onRecord( [this]( RecordContext & recContext, VkCommandBuffer cb, uint32_t i ){ doRecordInto( recContext, cb, i ); } ) + .onGetPassIndex( std::move( passIndex ) ) + .onIsEnabled( std::move( isEnabled ) ) , std::move( ruConfig ) } , m_copySize{ convert( copySize ) } , m_finalOutputLayout{ finalOutputLayout } @@ -81,8 +81,8 @@ namespace crg { auto srcAttach{ srcIt->second->view( index ) }; auto dstAttach{ dstIt->second->view( index ) }; - auto srcImage{ getGraph().createImage( srcAttach.data->image ) }; - auto dstImage{ getGraph().createImage( dstAttach.data->image ) }; + auto srcImage{ &getGraph().createImage( srcAttach.data->image ) }; + auto dstImage{ &getGraph().createImage( dstAttach.data->image ) }; // Copy source to target. VkImageCopy copyRegion{ getSubresourceLayers( getSubresourceRange( srcAttach ) ) , {} @@ -90,9 +90,9 @@ namespace crg , {} , m_copySize }; context->vkCmdCopyImage( commandBuffer - , srcImage + , srcImage->getImage() , VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL - , dstImage + , dstImage->getImage() , VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL , 1u , ©Region ); @@ -116,21 +116,21 @@ namespace crg std::vector< VkImageCopy > copyRegions; auto dstIt = getPass().getOutputs().begin(); auto dstAttach{ dstIt->second->view( index ) }; - auto dstImage{ getGraph().createImage( dstAttach.data->image ) }; + auto dstImage{ &getGraph().createImage( dstAttach.data->image ) }; auto dstSubresourceRange = getSubresourceLayers( getSubresourceRange( dstAttach ) ); - auto prvSrcImage{ getGraph().createImage( getPass().getInputs().begin()->second->view( index ).data->image ) }; + auto prvSrcImage{ &getGraph().createImage( getPass().getInputs().begin()->second->view( index ).data->image ) }; for ( auto const & [_, attach] : getPass().getInputs() ) { auto srcAttach{ attach->view( index ) }; - if ( auto srcImage{ getGraph().createImage( srcAttach.data->image ) }; + if ( auto srcImage{ &getGraph().createImage( srcAttach.data->image ) }; srcImage != prvSrcImage ) { context->vkCmdCopyImage( commandBuffer - , prvSrcImage + , prvSrcImage->getImage() , VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL - , dstImage + , dstImage->getImage() , VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL , uint32_t( copyRegions.size() ) , copyRegions.data() ); @@ -148,9 +148,9 @@ namespace crg if ( !copyRegions.empty() ) { context->vkCmdCopyImage( commandBuffer - , prvSrcImage + , prvSrcImage->getImage() , VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL - , dstImage + , dstImage->getImage() , VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL , uint32_t( copyRegions.size() ) , copyRegions.data() ); @@ -171,21 +171,21 @@ namespace crg std::vector< VkImageCopy > copyRegions; auto srcIt = getPass().getInputs().begin(); auto srcAttach{ srcIt->second->view( index ) }; - auto srcImage{ getGraph().createImage( srcAttach.data->image ) }; + auto srcImage{ &getGraph().createImage( srcAttach.data->image ) }; auto srcSubresourceRange = getSubresourceLayers( getSubresourceRange( srcAttach ) ); - auto prvDstImage{ getGraph().createImage( getPass().getOutputs().begin()->second->view( index ).data->image ) }; + auto prvDstImage{ &getGraph().createImage( getPass().getOutputs().begin()->second->view( index ).data->image ) }; for ( auto const & [_, attach] : getPass().getOutputs() ) { auto dstAttach{ attach->view( index ) }; - if ( auto dstImage{ getGraph().createImage( dstAttach.data->image ) }; + if ( auto dstImage{ &getGraph().createImage( dstAttach.data->image ) }; dstImage != prvDstImage ) { context->vkCmdCopyImage( commandBuffer - , srcImage + , srcImage->getImage() , VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL - , prvDstImage + , prvDstImage->getImage() , VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL , uint32_t( copyRegions.size() ) , copyRegions.data() ); @@ -203,9 +203,9 @@ namespace crg if ( !copyRegions.empty() ) { context->vkCmdCopyImage( commandBuffer - , srcImage + , srcImage->getImage() , VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL - , prvDstImage + , prvDstImage->getImage() , VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL , uint32_t( copyRegions.size() ) , copyRegions.data() ); diff --git a/source/RenderGraph/RunnablePasses/ImageToBufferCopy.cpp b/source/RenderGraph/RunnablePasses/ImageToBufferCopy.cpp index a79a7c9..6757a62 100644 --- a/source/RenderGraph/RunnablePasses/ImageToBufferCopy.cpp +++ b/source/RenderGraph/RunnablePasses/ImageToBufferCopy.cpp @@ -5,6 +5,7 @@ See LICENSE file in root folder. #include "RenderGraph/RunnablePasses/ImageToBufferCopy.hpp" #include "RenderGraph/GraphContext.hpp" +#include "RenderGraph/Log.hpp" #include "RenderGraph/RunnableGraph.hpp" #include @@ -22,21 +23,30 @@ namespace crg : RunnablePass{ pass , context , graph - , { defaultV< InitialiseCallback > - , GetPipelineStateCallback( [](){ return crg::getPipelineState( PipelineStageFlags::eTransfer ); } ) - , [this]( RecordContext const & recContext, VkCommandBuffer cb, uint32_t i ){ doRecordInto( recContext, cb, i ); } - , std::move( passIndex ) - , std::move( isEnabled ) } + , RunnablePass::Callbacks{} + .onGetPipelineState( [](){ return crg::getPipelineState( PipelineStageFlags::eTransfer ); } ) + .onRecord( [this]( RecordContext const & recContext, VkCommandBuffer cb, uint32_t i ){ doRecordInto( recContext, cb, i ); } ) + .onGetPassIndex( std::move( passIndex ) ) + .onIsEnabled( std::move( isEnabled ) ) , std::move( ruConfig ) } , m_copyOffset{ convert( copyOffset ) } , m_copySize{ convert( copySize ) } { + if ( getPass().getInputs().size() != getPass().getOutputs().size() ) + { + Logger::logError( "BufferCopy - Inputs and outputs sizes are different." ); + } } void ImageToBufferCopy::doRecordInto( RecordContext const & context , VkCommandBuffer commandBuffer , uint32_t index )const { + if ( getPass().getInputs().size() != getPass().getOutputs().size() ) + { + return; + } + auto srcIt = getPass().getInputs().begin(); auto dstIt = getPass().getOutputs().begin(); @@ -45,8 +55,14 @@ namespace crg { auto srcAttach{ srcIt->second->view( index ) }; auto dstAttach{ dstIt->second->buffer( index ) }; - auto srcImage{ getGraph().createImage( srcAttach.data->image ) }; - auto dstBuffer{ getGraph().createBuffer( dstAttach.data->buffer ) }; + auto srcImage{ &getGraph().createImage( srcAttach.data->image ) }; + auto dstBuffer{ &getGraph().createBuffer( dstAttach.data->buffer ) }; + + if ( dstAttach.data->buffer.data->maxPages > 1 ) + { + Logger::logWarning( "ImageToBufferCopy - Destination buffer [" + dstAttach.data->name + "] has more than one page, only the first one will be used." ); + } + // Copy source to target. auto range = getSubresourceLayers( getSubresourceRange( srcAttach ) ); VkBufferImageCopy copyRegion{ 0ULL @@ -56,9 +72,9 @@ namespace crg , m_copyOffset , m_copySize }; context->vkCmdCopyImageToBuffer( commandBuffer - , srcImage + , srcImage->getImage() , VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL - , dstBuffer + , dstBuffer->getBuffer() , 1u , ©Region ); ++srcIt; diff --git a/source/RenderGraph/RunnablePasses/PipelineHolder.cpp b/source/RenderGraph/RunnablePasses/PipelineHolder.cpp index 8f4af30..9b15338 100644 --- a/source/RenderGraph/RunnablePasses/PipelineHolder.cpp +++ b/source/RenderGraph/RunnablePasses/PipelineHolder.cpp @@ -4,6 +4,7 @@ See LICENSE file in root folder. #include "RenderGraph/RunnablePasses/PipelineHolder.hpp" #include "RenderGraph/GraphContext.hpp" +#include "RenderGraph/Hash.hpp" #include "RenderGraph/RunnableGraph.hpp" #include "RenderGraph/RunnablePasses/RenderPass.hpp" @@ -13,6 +14,41 @@ namespace crg { namespace pphdr { + enum class DescriptorType : uint8_t + { + eStorageImage, + eCombinedImageSampler, + eUniformTexelBuffer, + eStorageTexelBuffer, + eUniformBuffer, + eStorageBuffer, + }; + + static DescriptorType getDescriptorType( BufferAttachment const & attach ) + { + if ( attach.isUniformView() ) + return DescriptorType::eUniformTexelBuffer; + if ( attach.isStorageView() ) + return DescriptorType::eStorageTexelBuffer; + if ( attach.isUniform() ) + return DescriptorType::eUniformBuffer; + return DescriptorType::eStorageBuffer; + } + + static DescriptorType getDescriptorType( ImageAttachment const & attach ) + { + if ( attach.isStorageView() ) + return DescriptorType::eStorageImage; + return DescriptorType::eCombinedImageSampler; + } + + static DescriptorType getDescriptorType( Attachment const & attach ) + { + if ( attach.isImage() ) + return getDescriptorType( attach.imageAttach ); + return getDescriptorType( attach.bufferAttach ); + } + static bool isDescriptor( Attachment const & attach ) { return attach.isStorageImageView() || attach.isSampledImageView() @@ -54,6 +90,16 @@ namespace crg } } + static uint32_t getDescriptorTotalCount( Attachment const & attach ) + { + return attach.isBuffer() ? attach.buffer().data->buffer.data->maxPages : 1u; + } + + static uint32_t getDescriptorAllocatedCount( Attachment const & attach ) + { + return attach.isBuffer() ? attach.buffer().data->buffer.data->allocatedPages : 1u; + } + static void createDescriptorBindings( std::map< uint32_t, Attachment const * > const & attaches , VkShaderStageFlags shaderStage , RunnableGraph const & graph @@ -64,9 +110,62 @@ namespace crg if ( isDescriptor( *attach ) ) descriptorBindings.push_back( { binding , graph.getDescriptorType( *attach ) - , 1u, shaderStage, nullptr } ); + , getDescriptorTotalCount( *attach ), shaderStage, nullptr } ); } } + + static uint32_t getDescriptorId( Attachment const & attach + , uint32_t index ) + { + if ( attach.isImage() ) + return attach.view( index ).id; + return attach.buffer( index ).id; + } + + static_assert( sizeof( size_t ) >= sizeof( uint64_t ) ); + + static size_t getDescriptorHash( uint32_t binding + , Attachment const & attach + , uint32_t index ) + { + return ( ( uint64_t( getDescriptorId( attach, index ) ) & 0xFFFFFFFFull ) << 32u ) // 32 bits for resource ID + | ( ( uint64_t( getDescriptorType( attach ) ) & 0xFFull ) << 24u ) // 8 bits for descriptor type + | ( ( uint64_t( getDescriptorAllocatedCount( attach ) ) & 0xFFull ) << 16u ) // 8 bits for descriptor count + | ( ( uint64_t( binding ) & 0xFFFFull ) << 0u ); // 16 bits for descriptor binding + } + + static size_t getDescriptorsHash( std::map< uint32_t, FramePass::SampledAttachment > const & attaches + , uint32_t index ) + { + size_t result{}; + for ( auto & [binding, attach] : attaches ) + result = hashCombine( result, getDescriptorHash( binding, *attach.attach, index ) ); + return result; + } + + static size_t getDescriptorsHash( std::map< uint32_t, Attachment const * > const & attaches + , uint32_t index ) + { + size_t result{}; + for ( auto & [binding, attach] : attaches ) + { + if ( isDescriptor( *attach ) ) + result = hashCombine( result, getDescriptorHash( binding, *attach, index ) ); + } + return result; + } + + static size_t makeDescriptorSetHash( crg::FramePass const & pass + , uint32_t index ) + { + size_t result{}; + result = hashCombine( result, pphdr::getDescriptorsHash( pass.getUniforms(), index ) ); + result = hashCombine( result, pphdr::getDescriptorsHash( pass.getSampled(), index ) ); + result = hashCombine( result, pphdr::getDescriptorsHash( pass.getInputs(), index ) ); + result = hashCombine( result, pphdr::getDescriptorsHash( pass.getInouts(), index ) ); + result = hashCombine( result, pphdr::getDescriptorsHash( pass.getOutputs(), index ) ); + return result; + } } PipelineHolder::PipelineHolder( FramePass const & pass @@ -321,12 +420,28 @@ namespace crg void PipelineHolder::createDescriptorSet( uint32_t index ) { auto & descriptorSet = m_descriptorSets[index]; + auto hash = pphdr::makeDescriptorSetHash( m_pass, index ); - if ( descriptorSet.set != VkDescriptorSet{} ) + if ( descriptorSet.set != VkDescriptorSet{} + && descriptorSet.hash == hash ) { return; } + if ( descriptorSet.set != VkDescriptorSet{} ) + { + auto ds = descriptorSet.set; + auto pool = m_descriptorSetPool; + m_context.delQueue.push( [ds, pool]( GraphContext & context ) + { + context.vkFreeDescriptorSets( context.device, pool, 1u, &ds ); + } ); + descriptorSet.writes.clear(); + descriptorSet.set = {}; + } + + descriptorSet.hash = hash; + pphdr::createDescriptorWrites( m_pass.getUniforms(), index, m_graph, descriptorSet.writes ); pphdr::createDescriptorWrites( m_pass.getSampled(), index, m_graph, descriptorSet.writes ); pphdr::createDescriptorWrites( m_pass.getInputs(), index, m_graph, descriptorSet.writes ); @@ -423,11 +538,13 @@ namespace crg if ( m_context.vkCreateDescriptorPool ) { assert( m_descriptorSetLayout ); - auto sizes = getBindingsSizes( m_descriptorBindings, uint32_t( m_descriptorSets.size() ) ); + // x2 to account for descriptor set changes (the deallocation is deferred) + auto maxSets = uint32_t( m_descriptorSets.size() * 2u ); + auto sizes = getBindingsSizes( m_descriptorBindings, maxSets ); VkDescriptorPoolCreateInfo createInfo{ VK_STRUCTURE_TYPE_DESCRIPTOR_POOL_CREATE_INFO , nullptr , 0u - , uint32_t( m_descriptorSets.size() ) + , maxSets , uint32_t( sizes.size() ) , sizes.data() }; auto res = m_context.vkCreateDescriptorPool( m_context.device diff --git a/source/RenderGraph/RunnablePasses/RenderMesh.cpp b/source/RenderGraph/RunnablePasses/RenderMesh.cpp index 8bb9376..cfa492c 100644 --- a/source/RenderGraph/RunnablePasses/RenderMesh.cpp +++ b/source/RenderGraph/RunnablePasses/RenderMesh.cpp @@ -14,11 +14,11 @@ namespace crg : RunnablePass{ pass , context , graph - , { defaultV< InitialiseCallback > - , GetPipelineStateCallback( [](){ return crg::getPipelineState( PipelineStageFlags::eColorAttachmentOutput ); } ) - , [this]( RecordContext & recContext, VkCommandBuffer cb, uint32_t i ){ doRecordInto( recContext, cb, i ); } - , GetPassIndexCallback( [this](){ return m_renderMesh.getPassIndex(); } ) - , IsEnabledCallback( [this](){ return m_renderMesh.isEnabled(); } ) } + , RunnablePass::Callbacks{} + .onGetPipelineState( [](){ return crg::getPipelineState( PipelineStageFlags::eColorAttachmentOutput ); } ) + .onRecord( [this]( RecordContext & recContext, VkCommandBuffer cb, uint32_t i ){ doRecordInto( recContext, cb, i ); } ) + .onGetPassIndex( GetPassIndexCallback( [this](){ return m_renderMesh.getPassIndex(); } ) ) + .onIsEnabled( IsEnabledCallback( [this](){ return m_renderMesh.isEnabled(); } ) ) , { ruConfig.maxPassCount , true /*resettable*/ , ruConfig.prePassActions diff --git a/source/RenderGraph/RunnablePasses/RenderMeshHolder.cpp b/source/RenderGraph/RunnablePasses/RenderMeshHolder.cpp index c3f21d3..3548567 100644 --- a/source/RenderGraph/RunnablePasses/RenderMeshHolder.cpp +++ b/source/RenderGraph/RunnablePasses/RenderMeshHolder.cpp @@ -4,6 +4,8 @@ See LICENSE file in root folder. */ #include "RenderGraph/RunnablePasses/RenderMeshHolder.hpp" +#include "RenderGraph/Log.hpp" + namespace crg { //********************************************************************************************* @@ -14,26 +16,26 @@ namespace crg , rm::Config config , uint32_t maxPassCount ) : m_graph{ graph } - , m_config{ config.m_renderPosition ? std::move( *config.m_renderPosition ) : getDefaultV< Offset2D >() - , config.m_depthStencilState ? std::move( *config.m_depthStencilState ) : getDefaultV< VkPipelineDepthStencilStateCreateInfo >() - , config.m_getPassIndex ? std::move( *config.m_getPassIndex ) : getDefaultV< RunnablePass::GetPassIndexCallback >() - , config.m_isEnabled ? std::move( *config.m_isEnabled ) : getDefaultV< RunnablePass::IsEnabledCallback >() - , config.m_recordInto ? std::move( *config.m_recordInto ) : getDefaultV< RunnablePass::RecordCallback >() - , config.m_end ? std::move( *config.m_end ) : getDefaultV< RunnablePass::RecordCallback >() - , config.m_getPrimitiveCount ? std::move( *config.m_getPrimitiveCount ) : getDefaultV< GetPrimitiveCountCallback >() - , config.m_getVertexCount ? std::move( *config.m_getVertexCount ) : getDefaultV< GetVertexCountCallback >() - , config.m_getIndexType ? std::move( *config.m_getIndexType ) : getDefaultV< GetIndexTypeCallback >() - , config.m_getCullMode ? std::move( *config.m_getCullMode ) : getDefaultV< GetCullModeCallback >() - , config.m_vertexBuffer ? std::move( *config.m_vertexBuffer ) : getDefaultV< VertexBuffer >() - , config.m_indexBuffer ? std::move( *config.m_indexBuffer ) : getDefaultV< IndexBuffer >() - , config.m_indirectBuffer ? *config.m_indirectBuffer : getDefaultV< IndirectBuffer >() } + , m_config{ config.m_renderPosition ? *config.m_renderPosition : defaultV< Offset2D > + , config.m_depthStencilState ? *config.m_depthStencilState : defaultV< VkPipelineDepthStencilStateCreateInfo > + , config.m_getPassIndex ? *config.m_getPassIndex : defaultV< GetPassIndexCallback > + , config.m_isEnabled ? *config.m_isEnabled : defaultV< IsEnabledCallback > + , config.m_recordInto ? *config.m_recordInto : defaultV< RecordCallback > + , config.m_end ? *config.m_end : defaultV< RecordCallback > + , config.m_getPrimitiveCount ? *config.m_getPrimitiveCount : defaultV< GetPrimitiveCountCallback > + , config.m_getVertexCount ? *config.m_getVertexCount : defaultV< GetVertexCountCallback > + , config.m_getIndexType ? *config.m_getIndexType : defaultV< GetIndexTypeCallback > + , config.m_getCullMode ? *config.m_getCullMode : defaultV< GetCullModeCallback > + , config.m_vertexBuffer ? *config.m_vertexBuffer : defaultV< VertexBuffer > + , config.m_indexBuffer ? *config.m_indexBuffer : defaultV< IndexBuffer > + , config.m_indirectBuffer ? *config.m_indirectBuffer : defaultV< IndirectBuffer > } , m_pipeline{ pass , context , graph , config.m_baseConfig , VK_PIPELINE_BIND_POINT_GRAPHICS , maxPassCount } - , m_renderSize{ config.m_renderSize ? *config.m_renderSize : getDefaultV< Extent2D >() } + , m_renderSize{ config.m_renderSize ? *config.m_renderSize : defaultV< Extent2D > } { m_iaState = { VK_STRUCTURE_TYPE_PIPELINE_INPUT_ASSEMBLY_STATE_CREATE_INFO , nullptr @@ -132,16 +134,31 @@ namespace crg if ( m_config.vertexBuffer.buffer != BufferViewId{} ) { - auto vkBuffer = m_graph.createBuffer( m_config.vertexBuffer.buffer.data->buffer ); + if ( m_config.vertexBuffer.buffer.data->buffer.data->maxPages > 1 ) + { + Logger::logWarning( "RenderMeshHolder - Vertex buffer [" + m_config.vertexBuffer.buffer.data->name + "] has more than one page, only the first one will be used." ); + } + + auto vkBuffer = m_graph.createBuffer( m_config.vertexBuffer.buffer.data->buffer ).getBuffer(); context->vkCmdBindVertexBuffers( commandBuffer, 0u, 1u, &vkBuffer, &getSubresourceRange( m_config.vertexBuffer.buffer ).offset ); } if ( m_config.indirectBuffer != defaultV< IndirectBuffer > ) { - auto indirectBuffer = m_graph.createBuffer( m_config.indirectBuffer.buffer.data->buffer ); + if ( m_config.indirectBuffer.buffer.data->buffer.data->maxPages > 1 ) + { + Logger::logWarning( "RenderMeshHolder - Indirect buffer [" + m_config.indirectBuffer.buffer.data->name + "] has more than one page, only the first one will be used." ); + } + + auto indirectBuffer = m_graph.createBuffer( m_config.indirectBuffer.buffer.data->buffer ).getBuffer(); if ( m_config.indexBuffer != defaultV< IndexBuffer > ) { - auto indexBuffer = m_graph.createBuffer( m_config.indexBuffer.buffer.data->buffer ); + if ( m_config.indexBuffer.buffer.data->buffer.data->maxPages > 1 ) + { + Logger::logWarning( "RenderMeshHolder - Index buffer [" + m_config.indexBuffer.buffer.data->name + "] has more than one page, only the first one will be used." ); + } + + auto indexBuffer = m_graph.createBuffer( m_config.indexBuffer.buffer.data->buffer ).getBuffer(); context->vkCmdBindIndexBuffer( commandBuffer, indexBuffer, getSubresourceRange( m_config.indexBuffer.buffer ).offset, m_config.getIndexType() ); context->vkCmdDrawIndexedIndirect( commandBuffer, indirectBuffer, getSubresourceRange( m_config.indirectBuffer.buffer ).offset, 1u, m_config.indirectBuffer.stride ); } @@ -152,7 +169,12 @@ namespace crg } else if ( m_config.indexBuffer != defaultV< IndexBuffer > ) { - auto indexBuffer = m_graph.createBuffer( m_config.indexBuffer.buffer.data->buffer ); + if ( m_config.indexBuffer.buffer.data->buffer.data->maxPages > 1 ) + { + Logger::logWarning( "RenderMeshHolder - Index buffer [" + m_config.indexBuffer.buffer.data->name + "] has more than one page, only the first one will be used." ); + } + + auto indexBuffer = m_graph.createBuffer( m_config.indexBuffer.buffer.data->buffer ).getBuffer(); context->vkCmdBindIndexBuffer( commandBuffer, indexBuffer, getSubresourceRange( m_config.indexBuffer.buffer ).offset, m_config.getIndexType() ); context->vkCmdDrawIndexed( commandBuffer, m_config.getPrimitiveCount(), 1u, 0u, 0u, 0u ); } diff --git a/source/RenderGraph/RunnablePasses/RenderPass.cpp b/source/RenderGraph/RunnablePasses/RenderPass.cpp index a190ba2..321733c 100644 --- a/source/RenderGraph/RunnablePasses/RenderPass.cpp +++ b/source/RenderGraph/RunnablePasses/RenderPass.cpp @@ -36,51 +36,7 @@ namespace crg //********************************************************************************************* - RenderPass::Callbacks::Callbacks( InitialiseCallback initialise - , RecordCallback record ) - : Callbacks{ std::move( initialise ) - , std::move( record ) - , getDefaultV< GetSubpassContentsCallback >() - , getDefaultV< GetPassIndexCallback >() - , getDefaultV< IsEnabledCallback >() } - { - } - - RenderPass::Callbacks::Callbacks( InitialiseCallback initialise - , RecordCallback record - , GetSubpassContentsCallback getSubpassContents ) - : Callbacks{ std::move( initialise ) - , std::move( record ) - , std::move( getSubpassContents ) - , getDefaultV< GetPassIndexCallback >() - , getDefaultV< IsEnabledCallback >() } - { - } - - RenderPass::Callbacks::Callbacks( InitialiseCallback initialise - , RecordCallback record - , GetSubpassContentsCallback getSubpassContents - , GetPassIndexCallback getPassIndex ) - : Callbacks{ std::move( initialise ) - , std::move( record ) - , std::move( getSubpassContents ) - , std::move( getPassIndex ) - , getDefaultV< IsEnabledCallback >() } - { - } - - RenderPass::Callbacks::Callbacks( InitialiseCallback initialise - , RecordCallback record - , GetSubpassContentsCallback getSubpassContents - , GetPassIndexCallback getPassIndex - , IsEnabledCallback isEnabled ) - : initialise{ std::move( initialise ) } - , record{ std::move( record ) } - , getSubpassContents{ std::move( getSubpassContents ) } - , getPassIndex{ std::move( getPassIndex ) } - , isEnabled{ std::move( isEnabled ) } - { - } + RenderPass::Callbacks::Callbacks() = default; //********************************************************************************************* @@ -93,11 +49,11 @@ namespace crg : RunnablePass{ pass , context , graph - , { defaultV< InitialiseCallback > - , GetPipelineStateCallback( [](){ return crg::getPipelineState( PipelineStageFlags::eColorAttachmentOutput ); } ) - , [this]( RecordContext & recContext, VkCommandBuffer cb, uint32_t i ){ doRecordInto( recContext, cb, i ); } - , std::move( callbacks.getPassIndex ) - , std::move( callbacks.isEnabled ) } + , RunnablePass::Callbacks{} + .onRecord( [this]( RecordContext & recContext, VkCommandBuffer cb, uint32_t i ){ doRecordInto( recContext, cb, i ); } ) + .onGetPipelineState( [](){ return crg::getPipelineState( PipelineStageFlags::eColorAttachmentOutput ); } ) + .onGetPassIndex( std::move( callbacks.getPassIndex ) ) + .onIsEnabled( std::move( callbacks.isEnabled ) ) , ruConfig } , m_rpCallbacks{ std::move( callbacks ) } , m_holder{ pass diff --git a/source/RenderGraph/RunnablePasses/RenderQuad.cpp b/source/RenderGraph/RunnablePasses/RenderQuad.cpp index 3fdd0a9..6d2568e 100644 --- a/source/RenderGraph/RunnablePasses/RenderQuad.cpp +++ b/source/RenderGraph/RunnablePasses/RenderQuad.cpp @@ -14,11 +14,11 @@ namespace crg : RunnablePass{ pass , context , graph - , { defaultV< InitialiseCallback > - , GetPipelineStateCallback( [](){ return crg::getPipelineState( PipelineStageFlags::eColorAttachmentOutput ); } ) - , [this]( RecordContext & recContext, VkCommandBuffer cb, uint32_t i ){ doRecordInto( recContext, cb, i ); } - , GetPassIndexCallback( [this](){ return m_renderQuad.getPassIndex(); } ) - , IsEnabledCallback( [this](){ return m_renderQuad.isEnabled(); } ) } + , RunnablePass::Callbacks{} + .onGetPipelineState( [](){ return crg::getPipelineState( PipelineStageFlags::eColorAttachmentOutput ); } ) + .onRecord( [this]( RecordContext & recContext, VkCommandBuffer cb, uint32_t i ){ doRecordInto( recContext, cb, i ); } ) + .onGetPassIndex( [this](){ return m_renderQuad.getPassIndex(); } ) + .onIsEnabled( [this](){ return m_renderQuad.isEnabled(); } ) , { ruConfig.maxPassCount , true /*resettable*/ , ruConfig.prePassActions @@ -34,7 +34,7 @@ namespace crg , context , graph , ruConfig.maxPassCount - , rqConfig.m_renderSize ? *rqConfig.m_renderSize : getDefaultV< Extent2D >() } + , rqConfig.m_renderSize ? *rqConfig.m_renderSize : defaultV< Extent2D > } { } diff --git a/source/RenderGraph/RunnablePasses/RenderQuadHolder.cpp b/source/RenderGraph/RunnablePasses/RenderQuadHolder.cpp index 7a652ec..46f0e43 100644 --- a/source/RenderGraph/RunnablePasses/RenderQuadHolder.cpp +++ b/source/RenderGraph/RunnablePasses/RenderQuadHolder.cpp @@ -5,6 +5,7 @@ See LICENSE file in root folder. #include "RenderGraph/RunnablePasses/RenderQuadHolder.hpp" #include "RenderGraph/GraphContext.hpp" +#include "RenderGraph/Log.hpp" namespace crg { @@ -21,16 +22,16 @@ namespace crg , RunnableGraph & graph , rq::Config config , uint32_t maxPassCount ) - : m_config{ config.m_texcoordConfig ? std::move( *config.m_texcoordConfig ) : getDefaultV< Texcoord >() - , config.m_renderPosition ? std::move( *config.m_renderPosition ) : getDefaultV< Offset2D >() - , config.m_depthStencilState ? std::move( *config.m_depthStencilState ) : getDefaultV< VkPipelineDepthStencilStateCreateInfo >() - , config.m_passIndex.has_value() ? *config.m_passIndex : getDefaultV< uint32_t const * >() - , config.m_enabled.has_value() ? *config.m_enabled : getDefaultV< bool const * >() + : m_config{ config.m_texcoordConfig ? *config.m_texcoordConfig : defaultV< Texcoord > + , config.m_renderPosition ? *config.m_renderPosition : defaultV< Offset2D > + , config.m_depthStencilState ? *config.m_depthStencilState : defaultV< VkPipelineDepthStencilStateCreateInfo > + , config.m_passIndex.has_value() ? *config.m_passIndex : defaultV< uint32_t const * > + , config.m_enabled.has_value() ? *config.m_enabled : defaultV< bool const * > , config.m_isEnabled - , config.m_recordInto ? std::move( *config.m_recordInto ) : getDefaultV< RunnablePass::RecordCallback >() - , config.m_end ? std::move( *config.m_end ) : getDefaultV< RunnablePass::RecordCallback >() + , config.m_recordInto ? *config.m_recordInto : defaultV< RecordCallback > + , config.m_end ? *config.m_end : defaultV< RecordCallback > , config.m_instances.has_value() ? *config.m_instances : 1u - , config.m_indirectBuffer ? *config.m_indirectBuffer : getDefaultV < IndirectBuffer >() } + , config.m_indirectBuffer ? *config.m_indirectBuffer : defaultV< IndirectBuffer > } , m_graph{ graph } , m_pipeline{ pass , context @@ -133,14 +134,19 @@ namespace crg if ( m_vertexBuffer ) { - auto vkBuffer = m_graph.createBuffer( m_vertexBuffer->buffer.data->buffer ); + auto vkBuffer = m_graph.createBuffer( m_vertexBuffer->buffer.data->buffer ).getBuffer(); context->vkCmdBindVertexBuffers( commandBuffer, 0u, 1u , &vkBuffer, &getSubresourceRange( m_vertexBuffer->buffer ).offset ); } if ( m_config.indirectBuffer != defaultV< IndirectBuffer > ) { - auto indirectBuffer = m_graph.createBuffer( m_config.indirectBuffer.buffer.data->buffer ); + if ( m_config.indirectBuffer.buffer.data->buffer.data->maxPages > 1 ) + { + Logger::logWarning( "RenderQuadHolder - Indirect buffer [" + m_config.indirectBuffer.buffer.data->name + "] has more than one page, only the first one will be used." ); + } + + auto indirectBuffer = m_graph.createBuffer( m_config.indirectBuffer.buffer.data->buffer ).getBuffer(); context->vkCmdDrawIndirect( commandBuffer, indirectBuffer, getSubresourceRange( m_config.indirectBuffer.buffer ).offset, 1u, m_config.indirectBuffer.stride ); } else diff --git a/test/Common.cpp b/test/Common.cpp index d6487d3..3fc6ab0 100644 --- a/test/Common.cpp +++ b/test/Common.cpp @@ -72,11 +72,12 @@ namespace test } } - crg::BufferData createBuffer( std::string name ) + crg::BufferData createBuffer( std::string name + , uint32_t maxPages ) { return crg::BufferData{ std::move( name ) , crg::BufferCreateFlags::eNone - , 1024 + , 1024, maxPages , ( crg::BufferUsageFlags::eUniformBuffer | crg::BufferUsageFlags::eStorageBuffer | crg::BufferUsageFlags::eUniformTexelBuffer @@ -85,11 +86,12 @@ namespace test crg::BufferViewData createView( std::string name , crg::BufferId buffer - , crg::PixelFormat format ) + , crg::PixelFormat format + , uint32_t pageCount ) { return createView( std::move( name ) , buffer - , 0u, buffer.data->info.size + , 0u, buffer.data->info.size * pageCount , format ); } @@ -675,11 +677,35 @@ namespace test : crg::RunnablePass{ framePass , context , runGraph - , { crg::defaultV< crg::RunnablePass::InitialiseCallback > - , crg::RunnablePass::GetPipelineStateCallback( [this](){ return crg::getPipelineState( m_pipelineStageFlags ); } ) - , crg::RunnablePass::RecordCallback( [this]( crg::RecordContext & ctx, VkCommandBuffer cb, uint32_t i ){ doRecordInto( ctx, cb, i ); } ) - , crg::RunnablePass::GetPassIndexCallback( [index](){ return index; } ) - , crg::RunnablePass::IsEnabledCallback( [enabled](){ return enabled; } ) } + , RunnablePass::Callbacks{} + .onGetPipelineState( [this](){ return crg::getPipelineState( m_pipelineStageFlags ); } ) + .onRecord( [this]( crg::RecordContext & recContext, VkCommandBuffer cb, uint32_t i ){ doRecordInto( recContext, cb, i ); } ) + .onGetPassIndex( [index](){ return index; } ) + .onIsEnabled( [enabled](){ return enabled; } ) + , std::move( config ) } + , m_testCounts{ testCounts } + , m_pipelineStageFlags{ pipelineStageFlags } + , m_checkViews{ std::move( checkViews ) } + { + } + + DummyRunnable( crg::FramePass const & framePass + , crg::GraphContext & context + , crg::RunnableGraph & runGraph + , test::TestCounts & testCounts + , crg::PipelineStageFlags pipelineStageFlags + , CheckViews checkViews + , uint32_t index + , bool const * enabled + , crg::ru::Config config ) + : crg::RunnablePass{ framePass + , context + , runGraph + , RunnablePass::Callbacks{} + .onGetPipelineState( [this](){ return crg::getPipelineState( m_pipelineStageFlags ); } ) + .onRecord( [this]( crg::RecordContext & recContext, VkCommandBuffer cb, uint32_t i ){ doRecordInto( recContext, cb, i ); } ) + .onGetPassIndex( [index](){ return index; } ) + .onIsEnabled( [enabled](){ return *enabled; } ) , std::move( config ) } , m_testCounts{ testCounts } , m_pipelineStageFlags{ pipelineStageFlags } @@ -698,10 +724,10 @@ namespace test : crg::RunnablePass{ framePass , context , runGraph - , { crg::defaultV< crg::RunnablePass::InitialiseCallback > - , crg::RunnablePass::GetPipelineStateCallback( [this](){ return crg::getPipelineState( m_pipelineStageFlags ); } ) - , crg::RunnablePass::RecordCallback( [this]( crg::RecordContext & ctx, VkCommandBuffer cb, uint32_t i ){ doRecordInto( ctx, cb, i ); } ) - , crg::RunnablePass::GetPassIndexCallback( [index](){ return index; } ) } + , RunnablePass::Callbacks{} + .onGetPipelineState( [this](){ return crg::getPipelineState( m_pipelineStageFlags ); } ) + .onRecord( [this]( crg::RecordContext & recContext, VkCommandBuffer cb, uint32_t i ){ doRecordInto( recContext, cb, i ); } ) + .onGetPassIndex( [index](){ return index; } ) , std::move( config ) } , m_testCounts{ testCounts } , m_pipelineStageFlags{ pipelineStageFlags } @@ -719,9 +745,9 @@ namespace test : crg::RunnablePass{ framePass , context , runGraph - , { crg::defaultV< crg::RunnablePass::InitialiseCallback > - , crg::RunnablePass::GetPipelineStateCallback( [this](){ return crg::getPipelineState( m_pipelineStageFlags ); } ) - , crg::RunnablePass::RecordCallback( [this]( crg::RecordContext & ctx, VkCommandBuffer cb, uint32_t i ){ doRecordInto( ctx, cb, i ); } ) } + , RunnablePass::Callbacks{} + .onGetPipelineState( [this](){ return crg::getPipelineState( m_pipelineStageFlags ); } ) + .onRecord( [this]( crg::RecordContext & recContext, VkCommandBuffer cb, uint32_t i ){ doRecordInto( recContext, cb, i ); } ) , std::move( config ) } , m_testCounts{ testCounts } , m_pipelineStageFlags{ pipelineStageFlags } @@ -738,9 +764,9 @@ namespace test : crg::RunnablePass{ framePass , context , runGraph - , { crg::defaultV< crg::RunnablePass::InitialiseCallback > - , crg::RunnablePass::GetPipelineStateCallback( [this](){ return crg::getPipelineState( m_pipelineStageFlags ); } ) - , crg::RunnablePass::RecordCallback( [this]( crg::RecordContext & ctx, VkCommandBuffer cb, uint32_t i ){ doRecordTargetsInto( ctx, cb, i ); } ) } + , RunnablePass::Callbacks{} + .onGetPipelineState( [this](){ return crg::getPipelineState( m_pipelineStageFlags ); } ) + .onRecord( [this]( crg::RecordContext & recContext, VkCommandBuffer cb, uint32_t i ){ doRecordTargetsInto( recContext, cb, i ); } ) , std::move( config ) } , m_testCounts{ testCounts } , m_pipelineStageFlags{ pipelineStageFlags } @@ -858,8 +884,8 @@ namespace test : crg::RunnablePass{ framePass , context , runGraph - , { crg::defaultV< crg::RunnablePass::InitialiseCallback > - , crg::RunnablePass::GetPipelineStateCallback( [this](){ return crg::getPipelineState( m_pipelineStageFlags ); } ) } + , RunnablePass::Callbacks{} + .onGetPipelineState( [this](){ return crg::getPipelineState( m_pipelineStageFlags ); } ) , std::move( config ) } , m_pipelineStageFlags{ pipelineStageFlags } { @@ -889,6 +915,27 @@ namespace test , std::move( config ) ); } + crg::RunnablePassPtr createDummy( test::TestCounts & testCounts + , crg::FramePass const & framePass + , crg::GraphContext & context + , crg::RunnableGraph & runGraph + , crg::PipelineStageFlags pipelineStageFlags + , CheckViews checkViews + , uint32_t index + , bool const * enabled + , crg::ru::Config config ) + { + return std::make_unique< DummyRunnable >( framePass + , context + , runGraph + , testCounts + , pipelineStageFlags + , checkViews + , index + , enabled + , std::move( config ) ); + } + crg::RunnablePassPtr createDummy( test::TestCounts & testCounts , crg::FramePass const & framePass , crg::GraphContext & context diff --git a/test/Common.hpp b/test/Common.hpp index ea823ef..75ee72c 100644 --- a/test/Common.hpp +++ b/test/Common.hpp @@ -9,10 +9,12 @@ namespace test { - crg::BufferData createBuffer( std::string name ); + crg::BufferData createBuffer( std::string name + , uint32_t maxPages = 1u ); crg::BufferViewData createView( std::string name , crg::BufferId buffer - , crg::PixelFormat format = crg::PixelFormat::eUNDEFINED ); + , crg::PixelFormat format = crg::PixelFormat::eUNDEFINED + , uint32_t pageCount = 1u ); crg::BufferViewData createView( std::string name , crg::BufferId buffer , crg::DeviceSize offset, crg::DeviceSize size @@ -89,6 +91,15 @@ namespace test , uint32_t index , bool enabled , crg::ru::Config config = {} ); + crg::RunnablePassPtr createDummy( test::TestCounts & testCounts + , crg::FramePass const & framePass + , crg::GraphContext & context + , crg::RunnableGraph & runGraph + , crg::PipelineStageFlags pipelineStageFlags + , CheckViews checkViews + , uint32_t index + , bool const * enabled + , crg::ru::Config config = {} ); crg::RunnablePassPtr createDummy( test::TestCounts & testCounts , crg::FramePass const & framePass , crg::GraphContext & context diff --git a/test/TestAttachment.cpp b/test/TestAttachment.cpp index d1db1e4..d2c93c9 100644 --- a/test/TestAttachment.cpp +++ b/test/TestAttachment.cpp @@ -16,13 +16,18 @@ namespace eStorage, }; + crg::GraphContext & getContext() + { + return test::getDummyContext(); + } + TEST( Attachment, SampledAttachment ) { testBegin( "testSampledAttachment" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); auto tmpAttach1 = crg::Attachment::createDefault( view ); auto tmpAttach2 = crg::Attachment::createDefault( view ); @@ -62,8 +67,8 @@ namespace testBegin( "testSampledAttachmentT" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); auto tmpAttach1 = crg::Attachment::createDefault( view ); auto tmpAttach2 = crg::Attachment::createDefault( view ); @@ -103,8 +108,8 @@ namespace testBegin( "testSampledImage" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); pass.addInputSampledImage( view, 1u ); require( pass.getSampled().size() == 1u ) @@ -139,8 +144,8 @@ namespace testBegin( "testSampledImageT" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); pass.addInputSampledImageT( view, Binding::eSampled ); require( pass.getSampled().size() == 1u ) @@ -175,10 +180,10 @@ namespace testBegin( "testImplicitColourAttachment" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( crg::ImageData{ "Test", crg::ImageCreateFlags::eNone, crg::ImageType::e3D, crg::PixelFormat::eR32G32B32A32_SFLOAT, { 1024, 1024, 1024 }, crg::ImageUsageFlags::eSampled, 1u, 1u } ); + auto image = graph.createImageId( crg::ImageData{ "Test", crg::ImageCreateFlags::eNone, crg::ImageType::e3D, crg::PixelFormat::eR32G32B32A32_SFLOAT, { 1024, 1024, 1024 }, crg::ImageUsageFlags::eSampled, 1u, 1u } ); auto range = crg::getVirtualRange( image, crg::ImageViewType::e3D, { crg::ImageAspectFlags::eColor, 0u, 1u, 0u, 1u } ); check( range.baseArrayLayer == 0 ) - auto view = graph.createView( test::createView( "Test", image ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); auto viewAttach = crg::Attachment::createDefault( view ); auto imageLayout = crg::ImageLayout::eShaderReadOnly; @@ -213,8 +218,8 @@ namespace testBegin( "testImplicitDepthAttachment" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eD32_SFLOAT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eD32_SFLOAT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); auto viewAttach = crg::Attachment::createDefault( view ); auto imageLayout = crg::ImageLayout::ePreinitialized; @@ -249,8 +254,8 @@ namespace testBegin( "testImplicitDepthStencilAttachment" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); auto viewAttach = crg::Attachment::createDefault( view ); auto imageLayout = crg::ImageLayout::eShaderReadOnly; @@ -285,8 +290,8 @@ namespace testBegin( "testInStorageAttachment" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); auto viewAttach = crg::Attachment::createDefault( view ); pass.addInputStorage( viewAttach, 1u ); @@ -321,8 +326,8 @@ namespace testBegin( "testInStorageAttachmentT" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); auto viewAttach = crg::Attachment::createDefault( view ); pass.addInputStorageT( viewAttach, Binding::eStorage ); @@ -357,8 +362,8 @@ namespace testBegin( "testInStorageImage" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); pass.addInputStorageImage( view, 1u ); require( pass.getInputs().size() == 1u ) @@ -392,8 +397,8 @@ namespace testBegin( "testInStorageImageT" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); pass.addInputStorageImageT( view, Binding::eStorage ); require( pass.getInputs().size() == 1u ) @@ -427,8 +432,8 @@ namespace testBegin( "testInStorageBuffer" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto buffer = graph.createBuffer( test::createBuffer( "Test" ) ); - auto view = graph.createView( test::createView( "Test", buffer ) ); + auto buffer = graph.createBufferId( test::createBuffer( "Test" ) ); + auto view = graph.createViewId( test::createView( "Test", buffer ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); pass.addInputStorageBuffer( view, 1u ); require( pass.getInputs().size() == 1u ) @@ -453,8 +458,8 @@ namespace testBegin( "testInStorageBufferT" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto buffer = graph.createBuffer( test::createBuffer( "Test" ) ); - auto view = graph.createView( test::createView( "Test", buffer ) ); + auto buffer = graph.createBufferId( test::createBuffer( "Test" ) ); + auto view = graph.createViewId( test::createView( "Test", buffer ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); pass.addInputStorageBufferT( view, Binding::eStorage ); require( pass.getInputs().size() == 1u ) @@ -479,8 +484,8 @@ namespace testBegin( "testUniformAttachment" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto buffer = graph.createBuffer( test::createBuffer( "Test" ) ); - auto view = graph.createView( test::createView( "Test", buffer ) ); + auto buffer = graph.createBufferId( test::createBuffer( "Test" ) ); + auto view = graph.createViewId( test::createView( "Test", buffer ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); check( &pass.getGraph() == &graph ) auto tmpAttach1 = crg::Attachment::createDefault( view ); @@ -512,8 +517,8 @@ namespace testBegin( "testUniformAttachmentT" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto buffer = graph.createBuffer( test::createBuffer( "Test" ) ); - auto view = graph.createView( test::createView( "Test", buffer ) ); + auto buffer = graph.createBufferId( test::createBuffer( "Test" ) ); + auto view = graph.createViewId( test::createView( "Test", buffer ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); auto tmpAttach1 = crg::Attachment::createDefault( view ); auto tmpAttach2 = crg::Attachment::createDefault( view ); @@ -544,8 +549,8 @@ namespace testBegin( "testOutStorageAttachment" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); pass.addOutputStorageImage( view, 1u ); require( pass.getOutputs().size() == 1u ) @@ -579,8 +584,8 @@ namespace testBegin( "testOutStorageAttachmentT" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); pass.addOutputStorageImageT( view, Binding::eStorage ); require( pass.getOutputs().size() == 1u ) @@ -614,8 +619,8 @@ namespace testBegin( "testClearOutStorageAttachment" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); pass.addClearableOutputStorageImage( view, 1u ); require( pass.getOutputs().size() == 1u ) @@ -649,8 +654,8 @@ namespace testBegin( "testClearOutStorageAttachmentT" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); pass.addClearableOutputStorageImageT( view, Binding::eStorage ); require( pass.getOutputs().size() == 1u ) @@ -684,8 +689,8 @@ namespace testBegin( "testInOutStorageAttachment" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); auto viewAttach = crg::Attachment::createDefault( view ); pass.addInOutStorage( viewAttach, 1u ); @@ -720,8 +725,8 @@ namespace testBegin( "testInOutStorageAttachmentT" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); auto viewAttach = crg::Attachment::createDefault( view ); pass.addInOutStorageT( viewAttach, Binding::eStorage ); @@ -756,8 +761,8 @@ namespace testBegin( "testInTransferAttachment" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); auto viewAttach = crg::Attachment::createDefault( view ); pass.addInputTransfer( viewAttach ); @@ -791,8 +796,8 @@ namespace testBegin( "testInTransferImage" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); pass.addInputTransferImage( view ); require( pass.getInputs().size() == 1u ) @@ -825,8 +830,8 @@ namespace testBegin( "testInTransferBuffer" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto buffer = graph.createBuffer( test::createBuffer( "Test" ) ); - auto view = graph.createView( test::createView( "Test", buffer ) ); + auto buffer = graph.createBufferId( test::createBuffer( "Test" ) ); + auto view = graph.createViewId( test::createView( "Test", buffer ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); pass.addInputTransferBuffer( view ); require( pass.getInputs().size() == 1u ) @@ -849,8 +854,8 @@ namespace testBegin( "testOutTransferAttachment" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); pass.addOutputTransferImage( view ); require( pass.getOutputs().size() == 1u ) @@ -883,8 +888,8 @@ namespace testBegin( "testInOutTransferAttachment" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); auto viewAttach = crg::Attachment::createDefault( view ); pass.addInOutTransfer( viewAttach ); @@ -918,8 +923,8 @@ namespace testBegin( "testInColourAttachment" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); auto viewAttach = crg::Attachment::createDefault( view ); pass.addInputColourTarget( viewAttach ); @@ -957,8 +962,8 @@ namespace testBegin( "testInColourImage" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); pass.addInputColourTargetImage( view ); require( pass.getTargets().size() == 1u ) @@ -995,8 +1000,8 @@ namespace testBegin( "testOutColourAttachment" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); pass.addOutputColourTarget( view ); require( pass.getTargets().size() == 1u ) @@ -1033,8 +1038,8 @@ namespace testBegin( "testInOutColourAttachment" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); auto viewAttach = crg::Attachment::createDefault( view ); pass.addInOutColourTarget( viewAttach ); @@ -1072,8 +1077,8 @@ namespace testBegin( "testInDepthAttachment" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eD32_SFLOAT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eD32_SFLOAT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); auto viewAttach = crg::Attachment::createDefault( view ); pass.addInputDepthTarget( viewAttach ); @@ -1111,8 +1116,8 @@ namespace testBegin( "testInDepthImage" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eD32_SFLOAT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eD32_SFLOAT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); pass.addInputDepthTargetImage( view ); require( !pass.getTargets().empty() ) @@ -1149,8 +1154,8 @@ namespace testBegin( "testOutDepthAttachment" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eD32_SFLOAT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eD32_SFLOAT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); pass.addOutputDepthTarget( view ); require( !pass.getTargets().empty() ) @@ -1187,8 +1192,8 @@ namespace testBegin( "testInOutDepthAttachment" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eD32_SFLOAT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eD32_SFLOAT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); auto viewAttach = crg::Attachment::createDefault( view ); pass.addInOutDepthTarget( viewAttach ); @@ -1226,8 +1231,8 @@ namespace testBegin( "testInDepthStencilAttachment" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); auto viewAttach = crg::Attachment::createDefault( view ); pass.addInputDepthStencilTarget( viewAttach ); @@ -1265,8 +1270,8 @@ namespace testBegin( "testInDepthStencilImage" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); pass.addInputDepthStencilTargetImage( view ); require( !pass.getTargets().empty() ) @@ -1303,8 +1308,8 @@ namespace testBegin( "testOutDepthStencilAttachment" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); pass.addOutputDepthStencilTarget( view ); require( !pass.getTargets().empty() ) @@ -1341,8 +1346,8 @@ namespace testBegin( "testInOutDepthStencilAttachment" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); auto viewAttach = crg::Attachment::createDefault( view ); pass.addInOutDepthStencilTarget( viewAttach ); @@ -1380,8 +1385,8 @@ namespace testBegin( "testInStencilAttachment" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eS8_UINT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eS8_UINT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); auto viewAttach = crg::Attachment::createDefault( view ); pass.addInputStencilTarget( viewAttach ); @@ -1419,8 +1424,8 @@ namespace testBegin( "testInStencilImage" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eS8_UINT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eS8_UINT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); pass.addInputStencilTargetImage( view ); require( !pass.getTargets().empty() ) @@ -1457,8 +1462,8 @@ namespace testBegin( "testOutStencilAttachment" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eS8_UINT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eS8_UINT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); pass.addOutputStencilTarget( view ); require( !pass.getTargets().empty() ) @@ -1495,8 +1500,8 @@ namespace testBegin( "testInOutStencilAttachment" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eS8_UINT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eS8_UINT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); auto viewAttach = crg::Attachment::createDefault( view ); pass.addInOutStencilTarget( viewAttach ); @@ -1534,8 +1539,8 @@ namespace testBegin( "testImageAttachment" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto image = graph.createImage( test::createImage( "Test", crg::PixelFormat::eS8_UINT ) ); - auto view = graph.createView( test::createView( "Test", image ) ); + auto image = graph.createImageId( test::createImage( "Test", crg::PixelFormat::eS8_UINT ) ); + auto view = graph.createViewId( test::createView( "Test", image ) ); auto const attachment = crg::Attachment::createDefault( view ); check( attachment.isImage() ) check( !attachment.isInput() ) @@ -1568,8 +1573,8 @@ namespace testBegin( "testImplicitBufferAttachment" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto buffer = graph.createBuffer( test::createBuffer( "Test" ) ); - auto bufferv = graph.createView( test::createView( "Test", buffer ) ); + auto buffer = graph.createBufferId( test::createBuffer( "Test" ) ); + auto bufferv = graph.createViewId( test::createView( "Test", buffer ) ); crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); auto bufferAttach = crg::Attachment::createDefault( bufferv ); crg::AccessState accessState{}; @@ -1577,6 +1582,8 @@ namespace require( pass.getInputs().size() == 1u ) auto attachIt = pass.getInputs().begin(); auto const & attachment = attachIt->second; + checkEqual( getSize( buffer ), 0u ) + handler.createBuffer( getContext(), buffer ); checkEqual( getSize( buffer ), 1024u ) checkEqual( getSize( bufferv ), 1024u ) check( attachment->isBuffer() ) @@ -1605,8 +1612,8 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); - auto buffer = graph.createBuffer( test::createBuffer( "Test" ) ); - auto bufferv = graph.createView( test::createView( "Test", buffer ) ); + auto buffer = graph.createBufferId( test::createBuffer( "Test" ) ); + auto bufferv = graph.createViewId( test::createView( "Test", buffer ) ); pass.addInputUniformBuffer( bufferv, 1u ); require( pass.getUniforms().size() == 1u ) auto attachIt = pass.getUniforms().begin(); @@ -1636,8 +1643,8 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); - auto buffer = graph.createBuffer( test::createBuffer( "Test" ) ); - auto bufferv = graph.createView( test::createView( "Test", buffer ) ); + auto buffer = graph.createBufferId( test::createBuffer( "Test" ) ); + auto bufferv = graph.createViewId( test::createView( "Test", buffer ) ); pass.addInputUniformBufferT( bufferv, Binding::eUniform ); require( pass.getUniforms().size() == 1u ) auto attachIt = pass.getUniforms().begin(); @@ -1667,8 +1674,8 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); - auto buffer = graph.createBuffer( test::createBuffer( "Test" ) ); - auto bufferv = graph.createView( test::createView( "Test", buffer ) ); + auto buffer = graph.createBufferId( test::createBuffer( "Test" ) ); + auto bufferv = graph.createViewId( test::createView( "Test", buffer ) ); auto bufferAttach = crg::Attachment::createDefault( bufferv ); pass.addInputStorage( bufferAttach, 1u ); require( pass.getInputs().size() == 1u ) @@ -1699,8 +1706,8 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); - auto buffer = graph.createBuffer( test::createBuffer( "Test" ) ); - auto bufferv = graph.createView( test::createView( "Test", buffer ) ); + auto buffer = graph.createBufferId( test::createBuffer( "Test" ) ); + auto bufferv = graph.createViewId( test::createView( "Test", buffer ) ); auto bufferAttach = crg::Attachment::createDefault( bufferv ); pass.addInputStorageT( bufferAttach, Binding::eStorage ); require( pass.getInputs().size() == 1u ) @@ -1731,8 +1738,8 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); - auto buffer = graph.createBuffer( test::createBuffer( "Test" ) ); - auto bufferv = graph.createView( test::createView( "Test", buffer ) ); + auto buffer = graph.createBufferId( test::createBuffer( "Test" ) ); + auto bufferv = graph.createViewId( test::createView( "Test", buffer ) ); pass.addOutputStorageBuffer( bufferv, 1u ); require( pass.getOutputs().size() == 1u ) auto attachIt = pass.getOutputs().begin(); @@ -1762,8 +1769,8 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); - auto buffer = graph.createBuffer( test::createBuffer( "Test" ) ); - auto bufferv = graph.createView( test::createView( "Test", buffer ) ); + auto buffer = graph.createBufferId( test::createBuffer( "Test" ) ); + auto bufferv = graph.createViewId( test::createView( "Test", buffer ) ); pass.addOutputStorageBufferT( bufferv, Binding::eStorage ); require( pass.getOutputs().size() == 1u ) auto attachIt = pass.getOutputs().begin(); @@ -1793,8 +1800,8 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); - auto buffer = graph.createBuffer( test::createBuffer( "Test" ) ); - auto bufferv = graph.createView( test::createView( "Test", buffer ) ); + auto buffer = graph.createBufferId( test::createBuffer( "Test" ) ); + auto bufferv = graph.createViewId( test::createView( "Test", buffer ) ); pass.addClearableOutputStorageBuffer( bufferv, 1u ); require( pass.getOutputs().size() == 1u ) auto attachIt = pass.getOutputs().begin(); @@ -1824,8 +1831,8 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); - auto buffer = graph.createBuffer( test::createBuffer( "Test" ) ); - auto bufferv = graph.createView( test::createView( "Test", buffer ) ); + auto buffer = graph.createBufferId( test::createBuffer( "Test" ) ); + auto bufferv = graph.createViewId( test::createView( "Test", buffer ) ); pass.addClearableOutputStorageBufferT( bufferv, Binding::eStorage ); require( pass.getOutputs().size() == 1u ) auto attachIt = pass.getOutputs().begin(); @@ -1855,8 +1862,8 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); - auto buffer = graph.createBuffer( test::createBuffer( "Test" ) ); - auto bufferv = graph.createView( test::createView( "Test", buffer ) ); + auto buffer = graph.createBufferId( test::createBuffer( "Test" ) ); + auto bufferv = graph.createViewId( test::createView( "Test", buffer ) ); auto bufferAttach = crg::Attachment::createDefault( bufferv ); pass.addInOutStorage( bufferAttach, 1u ); require( pass.getInouts().size() == 1u ) @@ -1887,8 +1894,8 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); - auto buffer = graph.createBuffer( test::createBuffer( "Test" ) ); - auto bufferv = graph.createView( test::createView( "Test", buffer ) ); + auto buffer = graph.createBufferId( test::createBuffer( "Test" ) ); + auto bufferv = graph.createViewId( test::createView( "Test", buffer ) ); auto bufferAttach = crg::Attachment::createDefault( bufferv ); pass.addInOutStorageT( bufferAttach, Binding::eStorage ); require( pass.getInouts().size() == 1u ) @@ -1919,8 +1926,8 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); - auto buffer = graph.createBuffer( test::createBuffer( "Test" ) ); - auto bufferv = graph.createView( test::createView( "Test", buffer, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto buffer = graph.createBufferId( test::createBuffer( "Test" ) ); + auto bufferv = graph.createViewId( test::createView( "Test", buffer, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); auto bufferAttach = crg::Attachment::createDefault( bufferv ); pass.addImplicit( bufferAttach, crg::AccessState{} ); require( pass.getInputs().size() == 1u ) @@ -1950,8 +1957,8 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); - auto buffer = graph.createBuffer( test::createBuffer( "Test" ) ); - auto bufferv = graph.createView( test::createView( "Test", buffer, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto buffer = graph.createBufferId( test::createBuffer( "Test" ) ); + auto bufferv = graph.createViewId( test::createView( "Test", buffer, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); pass.addInputUniformBuffer( bufferv, 1u ); require( !pass.getUniforms().empty() ) auto attachIt = pass.getUniforms().begin(); @@ -1981,8 +1988,8 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); - auto buffer = graph.createBuffer( test::createBuffer( "Test" ) ); - auto bufferv = graph.createView( test::createView( "Test", buffer, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto buffer = graph.createBufferId( test::createBuffer( "Test" ) ); + auto bufferv = graph.createViewId( test::createView( "Test", buffer, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); pass.addInputUniformBufferT( bufferv, Binding::eUniform ); require( !pass.getUniforms().empty() ) auto attachIt = pass.getUniforms().begin(); @@ -2012,8 +2019,8 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); - auto buffer = graph.createBuffer( test::createBuffer( "Test" ) ); - auto bufferv = graph.createView( test::createView( "Test", buffer, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto buffer = graph.createBufferId( test::createBuffer( "Test" ) ); + auto bufferv = graph.createViewId( test::createView( "Test", buffer, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); auto bufferAttach = crg::Attachment::createDefault( bufferv ); pass.addInputStorage( bufferAttach, 1u ); require( pass.getInputs().size() == 1u ) @@ -2044,8 +2051,8 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); - auto buffer = graph.createBuffer( test::createBuffer( "Test" ) ); - auto bufferv = graph.createView( test::createView( "Test", buffer, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto buffer = graph.createBufferId( test::createBuffer( "Test" ) ); + auto bufferv = graph.createViewId( test::createView( "Test", buffer, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); auto bufferAttach = crg::Attachment::createDefault( bufferv ); pass.addInputStorageT( bufferAttach, Binding::eStorage ); require( pass.getInputs().size() == 1u ) @@ -2076,8 +2083,8 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); - auto buffer = graph.createBuffer( test::createBuffer( "Test" ) ); - auto bufferv = graph.createView( test::createView( "Test", buffer, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto buffer = graph.createBufferId( test::createBuffer( "Test" ) ); + auto bufferv = graph.createViewId( test::createView( "Test", buffer, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); pass.addOutputStorageBuffer( bufferv, 1u ); require( pass.getOutputs().size() == 1u ) auto attachIt = pass.getOutputs().begin(); @@ -2107,8 +2114,8 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); - auto buffer = graph.createBuffer( test::createBuffer( "Test" ) ); - auto bufferv = graph.createView( test::createView( "Test", buffer, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto buffer = graph.createBufferId( test::createBuffer( "Test" ) ); + auto bufferv = graph.createViewId( test::createView( "Test", buffer, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); pass.addOutputStorageBufferT( bufferv, Binding::eStorage ); require( pass.getOutputs().size() == 1u ) auto attachIt = pass.getOutputs().begin(); @@ -2138,8 +2145,8 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); - auto buffer = graph.createBuffer( test::createBuffer( "Test" ) ); - auto bufferv = graph.createView( test::createView( "Test", buffer, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto buffer = graph.createBufferId( test::createBuffer( "Test" ) ); + auto bufferv = graph.createViewId( test::createView( "Test", buffer, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); pass.addClearableOutputStorageBuffer( bufferv, 1u ); require( pass.getOutputs().size() == 1u ) auto attachIt = pass.getOutputs().begin(); @@ -2169,8 +2176,8 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); - auto buffer = graph.createBuffer( test::createBuffer( "Test" ) ); - auto bufferv = graph.createView( test::createView( "Test", buffer, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto buffer = graph.createBufferId( test::createBuffer( "Test" ) ); + auto bufferv = graph.createViewId( test::createView( "Test", buffer, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); pass.addClearableOutputStorageBufferT( bufferv, Binding::eStorage ); require( pass.getOutputs().size() == 1u ) auto attachIt = pass.getOutputs().begin(); @@ -2200,8 +2207,8 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); - auto buffer = graph.createBuffer( test::createBuffer( "Test" ) ); - auto bufferv = graph.createView( test::createView( "Test", buffer, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto buffer = graph.createBufferId( test::createBuffer( "Test" ) ); + auto bufferv = graph.createViewId( test::createView( "Test", buffer, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); auto bufferAttach = crg::Attachment::createDefault( bufferv ); pass.addInOutStorage( bufferAttach, 1u ); require( pass.getInouts().size() == 1u ) @@ -2232,8 +2239,8 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); - auto buffer = graph.createBuffer( test::createBuffer( "Test" ) ); - auto bufferv = graph.createView( test::createView( "Test", buffer, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto buffer = graph.createBufferId( test::createBuffer( "Test" ) ); + auto bufferv = graph.createViewId( test::createView( "Test", buffer, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); auto bufferAttach = crg::Attachment::createDefault( bufferv ); pass.addInOutStorageT( bufferAttach, Binding::eStorage ); require( pass.getInouts().size() == 1u ) @@ -2264,8 +2271,8 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); - auto buffer = graph.createBuffer( test::createBuffer( "Test" ) ); - auto bufferv = graph.createView( test::createView( "Test", buffer ) ); + auto buffer = graph.createBufferId( test::createBuffer( "Test" ) ); + auto bufferv = graph.createViewId( test::createView( "Test", buffer ) ); auto bufferAttach = crg::Attachment::createDefault( bufferv ); pass.addInputTransfer( bufferAttach ); require( pass.getInputs().size() == 1u ) @@ -2295,8 +2302,8 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); - auto buffer = graph.createBuffer( test::createBuffer( "Test" ) ); - auto bufferv = graph.createView( test::createView( "Test", buffer ) ); + auto buffer = graph.createBufferId( test::createBuffer( "Test" ) ); + auto bufferv = graph.createViewId( test::createView( "Test", buffer ) ); pass.addOutputTransferBuffer( bufferv ); require( pass.getOutputs().size() == 1u ) auto attachIt = pass.getOutputs().begin(); @@ -2325,8 +2332,8 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; crg::FramePass & pass = graph.createPass( "test", crg::RunnablePassCreator{} ); - auto buffer = graph.createBuffer( test::createBuffer( "Test" ) ); - auto bufferv = graph.createView( test::createView( "Test", buffer ) ); + auto buffer = graph.createBufferId( test::createBuffer( "Test" ) ); + auto bufferv = graph.createViewId( test::createView( "Test", buffer ) ); auto bufferAttach = crg::Attachment::createDefault( bufferv ); pass.addInOutTransfer( bufferAttach ); require( pass.getInouts().size() == 1u ) @@ -2355,8 +2362,8 @@ namespace testBegin( "testBufferAttachment" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto buffer = graph.createBuffer( test::createBuffer( "Test" ) ); - auto bufferv = graph.createView( test::createView( "Test", buffer ) ); + auto buffer = graph.createBufferId( test::createBuffer( "Test" ) ); + auto bufferv = graph.createViewId( test::createView( "Test", buffer ) ); auto attachment = crg::Attachment::createDefault( bufferv ); check( attachment.isBuffer() ) check( !attachment.isInput() ) @@ -2380,12 +2387,12 @@ namespace testBegin( "testAttachmentMerge" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto buffer = graph.createBuffer( test::createBuffer( "buffer1" ) ); - auto buffer1v = graph.createView( test::createView( "buffer1v", buffer, 0u, 512u ) ); - auto buffer2v = graph.createView( test::createView( "buffer2v", buffer, 512u, 512u ) ); - auto image = graph.createImage( test::createImage( "image1", crg::PixelFormat::eR32G32B32A32_SFLOAT, 2u, 2u ) ); - auto image1v = graph.createView( test::createView( "image1v", image, 0u, 1u, 0u, 1u ) ); - auto image2v = graph.createView( test::createView( "image2v", image, 1u, 1u, 1u, 1u ) ); + auto buffer = graph.createBufferId( test::createBuffer( "buffer1" ) ); + auto buffer1v = graph.createViewId( test::createView( "buffer1v", buffer, 0u, 512u ) ); + auto buffer2v = graph.createViewId( test::createView( "buffer2v", buffer, 512u, 512u ) ); + auto image = graph.createImageId( test::createImage( "image1", crg::PixelFormat::eR32G32B32A32_SFLOAT, 2u, 2u ) ); + auto image1v = graph.createViewId( test::createView( "image1v", image, 0u, 1u, 0u, 1u ) ); + auto image2v = graph.createViewId( test::createView( "image2v", image, 1u, 1u, 1u, 1u ) ); { // Empty attachment list check( graph.mergeAttachments( {} ) == nullptr ) diff --git a/test/TestBases.cpp b/test/TestBases.cpp index 7222822..b3f6f11 100644 --- a/test/TestBases.cpp +++ b/test/TestBases.cpp @@ -281,8 +281,8 @@ TEST( Bases, FramePassTimer ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; crg::RunnablePass * runPass{}; - auto buffer = graph.createBuffer( test::createBuffer( "buffer" ) ); - auto bufferv = graph.createView( test::createView( "bufferv", buffer ) ); + auto buffer = graph.createBufferId( test::createBuffer( "buffer" ) ); + auto bufferv = graph.createViewId( test::createView( "bufferv", buffer ) ); auto & testPass = graph.createPass( "Mesh" , [&testCounts, &runPass]( crg::FramePass const & framePass , crg::GraphContext & context @@ -352,28 +352,35 @@ TEST( Bases, ImplicitActions ) testBegin( "testImplicitActions" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto depth1 = graph.createImage( test::createImage( "depth1", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); - auto depth1v = graph.createView( test::createView( "depth1v", depth1, crg::PixelFormat::eD32_SFLOAT_S8_UINT, 0u, 1u, 0u, 1u ) ); - auto depth2 = graph.createImage( test::createImage( "depth2", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); - auto depth2v = graph.createView( test::createView( "depth2v", depth2, crg::PixelFormat::eD32_SFLOAT_S8_UINT, 0u, 1u, 0u, 1u ) ); - auto colour1 = graph.createImage( test::createImage( "colour1", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto colour1v = graph.createView( test::createView( "colour1v", colour1, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto colour2 = graph.createImage( test::createImage( "colour2", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto colour2v = graph.createView( test::createView( "colour2v", colour2, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto colour3 = graph.createImage( test::createImage( "colour3", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto colour3v = graph.createView( test::createView( "colour3v", colour3, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto colour4 = graph.createImage( test::createImage( "colour4", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto colour4v = graph.createView( test::createView( "colour4v", colour4, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto buffer1 = graph.createBuffer( test::createBuffer( "buffer1" ) ); - auto buffer1v = graph.createView( test::createView( "buffer1v", buffer1 ) ); - auto buffer2 = graph.createBuffer( test::createBuffer( "buffer2" ) ); - auto buffer2v = graph.createView( test::createView( "buffer2v", buffer2 ) ); - auto buffer3 = graph.createBuffer( test::createBuffer( "buffer3" ) ); - auto buffer3v = graph.createView( test::createView( "buffer3v", buffer3 ) ); - auto buffer4 = graph.createBuffer( test::createBuffer( "buffer4" ) ); - auto buffer4v = graph.createView( test::createView( "buffer4v", buffer4 ) ); + auto depth1 = graph.createImageId( test::createImage( "depth1", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); + auto depth1v = graph.createViewId( test::createView( "depth1v", depth1, crg::PixelFormat::eD32_SFLOAT_S8_UINT, 0u, 1u, 0u, 1u ) ); + auto depth2 = graph.createImageId( test::createImage( "depth2", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); + auto depth2v = graph.createViewId( test::createView( "depth2v", depth2, crg::PixelFormat::eD32_SFLOAT_S8_UINT, 0u, 1u, 0u, 1u ) ); + auto colour1 = graph.createImageId( test::createImage( "colour1", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto colour1v = graph.createViewId( test::createView( "colour1v", colour1, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto colour2 = graph.createImageId( test::createImage( "colour2", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto colour2v = graph.createViewId( test::createView( "colour2v", colour2, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto colour3 = graph.createImageId( test::createImage( "colour3", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto colour3v = graph.createViewId( test::createView( "colour3v", colour3, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto colour4 = graph.createImageId( test::createImage( "colour4", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto colour4v = graph.createViewId( test::createView( "colour4v", colour4, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto buffer1 = graph.createBufferId( test::createBuffer( "buffer1" ) ); + auto buffer1v = graph.createViewId( test::createView( "buffer1v", buffer1 ) ); + auto buffer2 = graph.createBufferId( test::createBuffer( "buffer2" ) ); + auto buffer2v = graph.createViewId( test::createView( "buffer2v", buffer2 ) ); + auto buffer3 = graph.createBufferId( test::createBuffer( "buffer3" ) ); + auto buffer3v = graph.createViewId( test::createView( "buffer3v", buffer3 ) ); + auto buffer4 = graph.createBufferId( test::createBuffer( "buffer4" ) ); + auto buffer4v = graph.createViewId( test::createView( "buffer4v", buffer4 ) ); + auto buffer5 = graph.createBufferId( test::createBuffer( "buffer5", 2u ) ); + auto buffer5v = graph.createViewId( test::createView( "buffer5v", buffer5 ) ); + auto buffer6 = graph.createBufferId( test::createBuffer( "buffer6", 2u ) ); + auto buf6 = handler.createBuffer( getContext(), buffer6 ).resource; + buf6->resize( buf6->getMaxSize() ); + buf6->update(); + auto buffer6v = graph.createViewId( test::createView( "buffer6v", buffer6, crg::PixelFormat::eUNDEFINED, buf6->getAllocatedPageCount() ) ); auto & testPass1 = graph.createPass( "Mesh" - , [&testCounts, depth2v, colour1v, colour2v, colour3v, colour4v, buffer1v, buffer2v, buffer3v]( crg::FramePass const & framePass + , [&testCounts, depth2v, colour1v, colour2v, colour3v, colour4v, buffer1v, buffer2v, buffer3v, buffer5v, buffer6v]( crg::FramePass const & framePass , crg::GraphContext & context , crg::RunnableGraph & runGraph ) { @@ -395,7 +402,9 @@ TEST( Bases, ImplicitActions ) .implicitAction( colour3v, crg::RecordContext::copyImage( colour2v, colour3v, extent2D, crg::ImageLayout::eShaderReadOnly ) ) .implicitAction( buffer1v, crg::RecordContext::clearBuffer( buffer1v, { crg::AccessFlags::eShaderWrite, crg::PipelineStageFlags::eFragmentShader } ) ) .implicitAction( buffer2v, crg::RecordContext::clearBuffer( buffer2v, 18u, { crg::AccessFlags::eShaderWrite, crg::PipelineStageFlags::eFragmentShader } ) ) - .implicitAction( buffer3v, crg::RecordContext::copyBuffer( buffer1v, buffer3v, 0u, 0u, 48u, { crg::AccessFlags::eShaderWrite, crg::PipelineStageFlags::eFragmentShader } ) ) ); + .implicitAction( buffer3v, crg::RecordContext::copyBuffer( buffer1v, buffer3v, 0u, 0u, 48u, { crg::AccessFlags::eShaderWrite, crg::PipelineStageFlags::eFragmentShader } ) ) + .implicitAction( buffer5v, crg::RecordContext::copyBuffer( buffer1v, buffer5v, 0u, 0u, getSize( buffer5v ), { crg::AccessFlags::eShaderWrite, crg::PipelineStageFlags::eFragmentShader } ) ) + .implicitAction( buffer6v, crg::RecordContext::copyBuffer( buffer1v, buffer6v, 0u, 0u, getSize( buffer6v ), { crg::AccessFlags::eShaderWrite, crg::PipelineStageFlags::eFragmentShader } ) ) ); } ); auto depth1a = testPass1.addOutputDepthStencilTarget( depth1v ); auto colour1a = testPass1.addOutputColourTarget( colour1v ); @@ -407,6 +416,8 @@ TEST( Bases, ImplicitActions ) auto buffer3a = testPass1.addOutputStorageBuffer( buffer3v, 2 ); auto buffer4a = testPass1.addOutputStorageBuffer( buffer4v, 3 ); auto buffer1a = testPass1.addOutputStorageBuffer( buffer1v, 4 ); + auto buffer5a = testPass1.addOutputStorageBuffer( buffer5v, 5 ); + auto buffer6a = testPass1.addOutputStorageBuffer( buffer6v, 6 ); auto & testPass2 = graph.createPass( "Pass" , [&testCounts]( crg::FramePass const & framePass @@ -428,6 +439,8 @@ TEST( Bases, ImplicitActions ) testPass2.addInOutStorage( *buffer3a, 2 ); testPass2.addInOutStorage( *buffer4a, 3 ); testPass2.addInOutStorage( *buffer1a, 4 ); + testPass2.addInOutStorage( *buffer5a, 5 ); + testPass2.addInOutStorage( *buffer6a, 6 ); auto runnable = graph.compile( getContext() ); test::checkRunnable( testCounts, runnable ); @@ -439,18 +452,18 @@ TEST( Bases, PrePassActions ) testBegin( "testPrePassActions" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto depth1 = graph.createImage( test::createImage( "depth1", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); - auto depth1v = graph.createView( test::createView( "depth1v", depth1, crg::PixelFormat::eD32_SFLOAT_S8_UINT, 0u, 1u, 0u, 1u ) ); - auto depth2 = graph.createImage( test::createImage( "depth2", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); - auto depth2v = graph.createView( test::createView( "depth2v", depth2, crg::PixelFormat::eD32_SFLOAT_S8_UINT, 0u, 1u, 0u, 1u ) ); - auto colour1 = graph.createImage( test::createImage( "colour1", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto colour1v = graph.createView( test::createView( "colour1v", colour1, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto colour2 = graph.createImage( test::createImage( "colour2", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto colour2v = graph.createView( test::createView( "colour2v", colour2, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto colour3 = graph.createImage( test::createImage( "colour3", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto colour3v = graph.createView( test::createView( "colour3v", colour3, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto colour4 = graph.createImage( test::createImage( "colour4", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto colour4v = graph.createView( test::createView( "colour4v", colour4, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto depth1 = graph.createImageId( test::createImage( "depth1", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); + auto depth1v = graph.createViewId( test::createView( "depth1v", depth1, crg::PixelFormat::eD32_SFLOAT_S8_UINT, 0u, 1u, 0u, 1u ) ); + auto depth2 = graph.createImageId( test::createImage( "depth2", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); + auto depth2v = graph.createViewId( test::createView( "depth2v", depth2, crg::PixelFormat::eD32_SFLOAT_S8_UINT, 0u, 1u, 0u, 1u ) ); + auto colour1 = graph.createImageId( test::createImage( "colour1", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto colour1v = graph.createViewId( test::createView( "colour1v", colour1, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto colour2 = graph.createImageId( test::createImage( "colour2", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto colour2v = graph.createViewId( test::createView( "colour2v", colour2, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto colour3 = graph.createImageId( test::createImage( "colour3", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto colour3v = graph.createViewId( test::createView( "colour3v", colour3, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto colour4 = graph.createImageId( test::createImage( "colour4", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto colour4v = graph.createViewId( test::createView( "colour4v", colour4, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); auto & testPass1 = graph.createPass( "Mesh" , [&testCounts, depth2v, colour1v, colour2v, colour3v, colour4v]( crg::FramePass const & framePass , crg::GraphContext & context @@ -505,18 +518,18 @@ TEST( Bases, PostPassActions ) testBegin( "testPrePassActions" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto depth1 = graph.createImage( test::createImage( "depth1", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); - auto depth1v = graph.createView( test::createView( "depth1v", depth1, crg::PixelFormat::eD32_SFLOAT_S8_UINT, 0u, 1u, 0u, 1u ) ); - auto depth2 = graph.createImage( test::createImage( "depth2", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); - auto depth2v = graph.createView( test::createView( "depth2v", depth2, crg::PixelFormat::eD32_SFLOAT_S8_UINT, 0u, 1u, 0u, 1u ) ); - auto colour1 = graph.createImage( test::createImage( "colour1", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto colour1v = graph.createView( test::createView( "colour1v", colour1, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto colour2 = graph.createImage( test::createImage( "colour2", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto colour2v = graph.createView( test::createView( "colour2v", colour2, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto colour3 = graph.createImage( test::createImage( "colour3", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto colour3v = graph.createView( test::createView( "colour3v", colour3, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto colour4 = graph.createImage( test::createImage( "colour4", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto colour4v = graph.createView( test::createView( "colour4v", colour4, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto depth1 = graph.createImageId( test::createImage( "depth1", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); + auto depth1v = graph.createViewId( test::createView( "depth1v", depth1, crg::PixelFormat::eD32_SFLOAT_S8_UINT, 0u, 1u, 0u, 1u ) ); + auto depth2 = graph.createImageId( test::createImage( "depth2", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); + auto depth2v = graph.createViewId( test::createView( "depth2v", depth2, crg::PixelFormat::eD32_SFLOAT_S8_UINT, 0u, 1u, 0u, 1u ) ); + auto colour1 = graph.createImageId( test::createImage( "colour1", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto colour1v = graph.createViewId( test::createView( "colour1v", colour1, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto colour2 = graph.createImageId( test::createImage( "colour2", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto colour2v = graph.createViewId( test::createView( "colour2v", colour2, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto colour3 = graph.createImageId( test::createImage( "colour3", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto colour3v = graph.createViewId( test::createView( "colour3v", colour3, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto colour4 = graph.createImageId( test::createImage( "colour4", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto colour4v = graph.createViewId( test::createView( "colour4v", colour4, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); crg::RunnablePass const * runPass{}; auto & testPass1 = graph.createPass( "Mesh" , [&runPass , &testCounts, depth2v, colour1v, colour2v, colour3v, colour4v]( crg::FramePass const & framePass @@ -574,12 +587,12 @@ TEST( Bases, GraphDeps ) testBegin( "testGraphDeps" ) crg::ResourceHandler handler; crg::FrameGraph graph1{ handler, testCounts.testName + "1" }; - auto colour = graph1.createImage( test::createImage( "colour", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto colourv = graph1.createView( test::createView( "colourv", colour, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto iocolour = graph1.createImage( test::createImage( "iocolour", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto iocolourv = graph1.createView( test::createView( "iocolourv", iocolour, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto buffer = graph1.createBuffer( test::createBuffer( "buffer" ) ); - auto bufferv = graph1.createView( test::createView( "bufferv", buffer ) ); + auto colour = graph1.createImageId( test::createImage( "colour", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto colourv = graph1.createViewId( test::createView( "colourv", colour, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto iocolour = graph1.createImageId( test::createImage( "iocolour", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto iocolourv = graph1.createViewId( test::createView( "iocolourv", iocolour, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto buffer = graph1.createBufferId( test::createBuffer( "buffer" ) ); + auto bufferv = graph1.createViewId( test::createView( "bufferv", buffer ) ); auto & testPass1 = graph1.createPass( "Mesh" , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -624,10 +637,10 @@ TEST( Bases, 2PassGraphDeps ) testBegin( "test2PassGraphDeps" ) crg::ResourceHandler handler; crg::FrameGraph graph1{ handler, testCounts.testName + "1" }; - auto buffer = graph1.createBuffer( test::createBuffer( "buffer" ) ); - auto bufferv = graph1.createView( test::createView( "bufferv", buffer ) ); - auto colour = graph1.createImage( test::createImage( "colour", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto colourv = graph1.createView( test::createView( "colourv", colour, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto buffer = graph1.createBufferId( test::createBuffer( "buffer" ) ); + auto bufferv = graph1.createViewId( test::createView( "bufferv", buffer ) ); + auto colour = graph1.createImageId( test::createImage( "colour", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto colourv = graph1.createViewId( test::createView( "colourv", colour, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); auto & testPass11 = graph1.createPass( "Pass1" , [&testCounts]( crg::FramePass const & framePass @@ -694,10 +707,10 @@ TEST( Bases, PassGroupDeps ) crg::ResourceHandler handler; crg::FrameGraph graph1{ handler, testCounts.testName + "1" }; auto & group1 = graph1.getDefaultGroup(); - auto colour = group1.createImage( test::createImage( "colour", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto colourv = group1.createView( test::createView( "colourv", colour, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto buffer = graph1.createBuffer( test::createBuffer( "buffer" ) ); - auto bufferv = graph1.createView( test::createView( "bufferv", buffer ) ); + auto colour = group1.createImageId( test::createImage( "colour", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto colourv = group1.createViewId( test::createView( "colourv", colour, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto buffer = graph1.createBufferId( test::createBuffer( "buffer" ) ); + auto bufferv = graph1.createViewId( test::createView( "bufferv", buffer ) ); auto & testPass1 = group1.createPass( "Mesh" , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -740,10 +753,10 @@ TEST( Bases, PassGroups ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; auto & group1 = graph.createPassGroup( "First" ); - auto colour = group1.createImage( test::createImage( "colour", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto colourv = group1.createView( test::createView( "colourv", colour, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto buffer = group1.createBuffer( test::createBuffer( "buffer" ) ); - auto bufferv = group1.createView( test::createView( "bufferv", buffer ) ); + auto colour = group1.createImageId( test::createImage( "colour", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto colourv = group1.createViewId( test::createView( "colourv", colour, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto buffer = group1.createBufferId( test::createBuffer( "buffer" ) ); + auto bufferv = group1.createViewId( test::createView( "bufferv", buffer ) ); auto & testPass1 = group1.createPass( "Mesh" , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -774,6 +787,38 @@ TEST( Bases, PassGroups ) testEnd() } +TEST( Bases, PagedBuffers ) +{ + testBegin( "testPagedBuffers" ) + auto & context = getContext(); + crgUnregisterObject( context, VkBuffer( 1 ) ); + crg::ResourceHandler handler; + crg::ResourcesCache resources{ handler }; + { + checkThrow( handler.createBufferId( test::createBuffer( "buffer", 0u ) ), crg::Exception ) + auto bufferId = handler.createBufferId( test::createBuffer( "buffer", 2u ) ); + auto bufferv1 = handler.createViewId( test::createView( "bufferv1", bufferId, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + checkEqual( handler.createBufferView( context, bufferv1 ).created, false ) + auto & buffer = resources.createBuffer( context, bufferId ); + auto pageSize = buffer.getPageSize(); + checkEqual( pageSize * 2u, buffer.getMaxSize() ) + checkEqual( buffer.getAllocatedPageCount(), 1u ) + buffer.resize( pageSize * 2u ); + buffer.update(); + checkEqual( buffer.getAllocatedPageCount(), 2u ) + buffer.resize( pageSize * 3u ); + buffer.update(); + checkEqual( buffer.getAllocatedPageCount(), 2u ) + + auto bufferv2 = handler.createViewId( test::createView( "bufferv2", bufferId, crg::PixelFormat::eR16G16B16A16_SFLOAT, 2u ) ); + checkEqual( crg::getBufferPageRange( bufferId, crg::getSubresourceRange( bufferv2 ) ), std::make_pair( 0u, 2u ) ) + checkEqual( crg::getBufferPageRange( bufferId, crg::BufferSubresourceRange{ 0u, VK_WHOLE_SIZE } ), std::make_pair( 0u, 2u ) ) + checkEqual( crg::getBufferPageRange( bufferId, crg::BufferSubresourceRange{ getSize( bufferId ), VK_WHOLE_SIZE } ), std::make_pair( 2u, 0u ) ) + checkEqual( crg::getBufferPageRange( bufferId, crg::BufferSubresourceRange{ bufferId.data->info.size, VK_WHOLE_SIZE } ), std::make_pair( 1u, 1u ) ) + } + testEnd() +} + TEST( Bases, ResourcesCache ) { testBegin( "testResourcesCache" ) @@ -785,16 +830,47 @@ TEST( Bases, ResourcesCache ) auto & context = getContext(); crgUnregisterObject( context, VkBuffer( 1 ) ); checkThrow( context.deduceMemoryType( 0u, 0u ), crg::Exception ) + { + crg::ResourceHandler handler; + crg::ResourcesCache resources{ handler }; + auto bufferId = handler.createBufferId( test::createBuffer( "buffer" ) ); + auto imageId = handler.createImageId( test::createImage( "image", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + crg::Buffer const & buffer = resources.createBuffer( context, bufferId ); + crg::Image const & image = resources.createImage( context, imageId ); + { + auto & contextCache = resources.getContextCache( context ); + contextCache.destroyBuffer( buffer ); + contextCache.destroyImage( image ); + } + resources.destroyContext( context ); + } + { + crg::ResourceHandler handler1; + crg::ResourceHandler handler2; + crg::ResourcesCache resources1{ handler1 }; + crg::ResourcesCache resources2{ handler2 }; + auto buffer = handler1.createBufferId( test::createBuffer( "buffer" ) ); + checkThrow( resources2.createBuffer( context, buffer ), crg::Exception ) + crg::Buffer const & buf = resources1.createBuffer( context, buffer ); + checkEqual( buf.getMaxPageCount(), 1u ) + auto image = handler1.createImageId( test::createImage( "image", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + checkThrow( resources2.createImage( context, image ), crg::Exception ) + crg::Image const & img = resources1.createImage( context, image ); + checkEqual( resources2.destroyBuffer( buf.getBufferId() ), false ) + checkEqual( resources2.destroyImage( img.getImageId() ), false ) + checkEqual( resources1.destroyBuffer( buf.getBufferId() ), true ) + checkEqual( resources1.destroyImage( img.getImageId() ), true ) + } { crg::ResourceHandler handler; auto sampled = handler.createImageId( test::createImage( "sampled", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); auto sampledv = handler.createViewId( test::createView( "sampledv", sampled, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto buffer = handler.createBufferId( test::createBuffer( "buffer" ) ); - auto bufferv = handler.createViewId( test::createView( "bufferv", buffer, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto buffer1 = handler.createBufferId( test::createBuffer( "buffer1" ) ); + auto buffer1v = handler.createViewId( test::createView( "buffer1v", buffer1, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); handler.createImage( context, sampled ); handler.createImageView( context, sampledv ); - handler.createBuffer( context, buffer ); - handler.createBufferView( context, bufferv ); + handler.createBuffer( context, buffer1 ); + handler.createBufferView( context, buffer1v ); handler.createQuadTriVertexBuffer( context, "test", false, {} ); handler.createQuadTriVertexBuffer( context, "test", true, {} ); handler.createSampler( context, "test", crg::SamplerDesc{} ); @@ -810,7 +886,8 @@ TEST( Bases, ResourcesCache ) resources.destroyImage( context, sampled ); auto buffer = handler.createBufferId( test::createBuffer( "buffer" ) ); auto bufferv = handler.createViewId( test::createView( "bufferv", buffer, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - resources.createBuffer( context, buffer ); + crg::Buffer const & buf = resources.createBuffer( context, buffer ); + checkEqual( buf.getAllocatedSize(), buf.getMaxSize() ) resources.createBufferView( context, bufferv ); resources.destroyBufferView( context, bufferv ); resources.destroyBuffer( context, buffer ); @@ -824,7 +901,6 @@ TEST( Bases, ResourcesCache ) resources.destroyImage( result ); auto buffer = handler.createBufferId( test::createBuffer( "resbuffer" ) ); auto bufferv = handler.createViewId( test::createView( "resbufferv", buffer, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - resources.createBuffer( context, buffer ); resources.createBufferView( context, bufferv ); resources.destroyBufferView( bufferv ); resources.destroyBuffer( buffer ); diff --git a/test/TestRenderGraph.cpp b/test/TestRenderGraph.cpp index a516909..e91e5bd 100644 --- a/test/TestRenderGraph.cpp +++ b/test/TestRenderGraph.cpp @@ -66,8 +66,8 @@ TEST( RenderGraph, NoPass ) auto graph1 = buildNoPassGraph( testCounts, handler ); crg::FrameGraph graph{ std::move( graph1 ) }; - auto rt = graph.createImage( test::createImage( "rt", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto rtv = graph.createView( test::createView( "rtv", rt ) ); + auto rt = graph.createImageId( test::createImage( "rt", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto rtv = graph.createViewId( test::createView( "rtv", rt ) ); auto & pass = graph.createPass( "pass1C" , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -85,8 +85,8 @@ TEST( RenderGraph, OnePass ) testBegin( "testOnePass" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto rt = graph.createImage( test::createImage( "rt", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto rtv = graph.createView( test::createView( "rtv", rt ) ); + auto rt = graph.createImageId( test::createImage( "rt", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto rtv = graph.createViewId( test::createView( "rtv", rt ) ); auto & pass = graph.createPass( "pass1C" , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -134,15 +134,17 @@ TEST( RenderGraph, OneDependency ) testBegin( "testOneDependency" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto rt = graph.createImage( test::createImage( "rt", crg::PixelFormat::eR32G32B32A32_SFLOAT, 1u, 4u ) ); - auto dep = graph.createImage( test::createImage( "dep", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); - auto rtv0 = graph.createView( test::createView( "rtv0", rt, 0u, 1u, 0u, 1u ) ); - auto rtv1 = graph.createView( test::createView( "rtv1", rt, 0u, 1u, 1u, 1u ) ); - auto rtv2 = graph.createView( test::createView( "rtv2", rt, 0u, 1u, 2u, 1u ) ); - auto rtv3 = graph.createView( test::createView( "rtv3", rt, 0u, 1u, 3u, 1u ) ); - auto depv = graph.createView( test::createView( "depv", dep ) ); - auto buf = graph.createBuffer( test::createBuffer( "buf" ) ); - auto bufv = graph.createView( test::createView( "bufv", buf ) ); + auto rt = graph.createImageId( test::createImage( "rt", crg::PixelFormat::eR32G32B32A32_SFLOAT, 1u, 4u ) ); + auto dep = graph.createImageId( test::createImage( "dep", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); + auto rtv0 = graph.createViewId( test::createView( "rtv0", rt, 0u, 1u, 0u, 1u ) ); + auto rtv1 = graph.createViewId( test::createView( "rtv1", rt, 0u, 1u, 1u, 1u ) ); + auto rtv2 = graph.createViewId( test::createView( "rtv2", rt, 0u, 1u, 2u, 1u ) ); + auto rtv3 = graph.createViewId( test::createView( "rtv3", rt, 0u, 1u, 3u, 1u ) ); + auto depv = graph.createViewId( test::createView( "depv", dep ) ); + auto buf1 = graph.createBufferId( test::createBuffer( "buf1" ) ); + auto buf1v = graph.createViewId( test::createView( "buf1v", buf1 ) ); + auto buf2 = graph.createBufferId( test::createBuffer( "buf2", 2u ) ); + auto buf2v = graph.createViewId( test::createView( "buf2v", buf2 ) ); auto & pass1 = graph.createPass( "pass1C" , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -151,12 +153,13 @@ TEST( RenderGraph, OneDependency ) return createDummy( testCounts , framePass, context, runGraph, crg::PipelineStageFlags::eFragmentShader ); } ); - pass1.addInputUniformBuffer( bufv, 1u ); + pass1.addInputUniformBuffer( buf1v, 1u ); + auto bufa = pass1.addOutputStorageBuffer( buf2v, 2u ); auto rta = pass1.addOutputColourTarget( graph.mergeViews( { rtv0, rtv1, rtv2, rtv3 } ) ); auto depa = pass1.addOutputDepthStencilTarget( depv ); - auto out = graph.createImage( test::createImage( "out", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto outv = graph.createView( test::createView( "outv", out ) ); + auto out = graph.createImageId( test::createImage( "out", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto outv = graph.createViewId( test::createView( "outv", out ) ); auto & pass2 = graph.createPass( "pass2C" , []( crg::FramePass const & framePass , crg::GraphContext & context @@ -165,7 +168,8 @@ TEST( RenderGraph, OneDependency ) return test::createDummyNoRecord( framePass, context, runGraph, crg::PipelineStageFlags::eFragmentShader ); } ); pass2.addInputSampled( *rta, 0u ); - pass2.addInputUniformBuffer( bufv, 1u ); + pass2.addInputUniformBuffer( buf1v, 1u ); + pass2.addInputStorage( *bufa, 2u ); pass2.addOutputColourTarget( outv ); pass2.addInputDepthStencilTarget( *depa ); @@ -189,10 +193,13 @@ TEST( RenderGraph, OneDependency ) "Transition to\npass2C/depv/IRds" [ shape=box ]; "pass1C" -> "Transition to\npass2C/depv/IRds" [ label="depv" ]; "Transition to\npass2C/depv/IRds" -> "pass2C" [ label="depv" ]; + "Transition to\npass2C/buf2v/IStr" [ shape=box ]; + "pass1C" -> "Transition to\npass2C/buf2v/IStr" [ label="buf2v" ]; + "Transition to\npass2C/buf2v/IStr" -> "pass2C" [ label="buf2v" ]; "ExternalSource" [ shape=ellipse ]; - "Transition to\npass1C/bufv/UB" [ shape=box ]; - "ExternalSource" -> "Transition to\npass1C/bufv/UB" [ label="bufv" ]; - "Transition to\npass1C/bufv/UB" -> "pass1C" [ label="bufv" ]; + "Transition to\npass1C/buf1v/UB" [ shape=box ]; + "ExternalSource" -> "Transition to\npass1C/buf1v/UB" [ label="buf1v" ]; + "Transition to\npass1C/buf1v/UB" -> "pass1C" [ label="buf1v" ]; } )"; checkEqualSortedLines( stream, ref ) @@ -204,8 +211,8 @@ TEST( RenderGraph, CycleDependency ) testBegin( "testCycleDependency" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto rt = graph.createImage( test::createImage( "rt", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto rtv = graph.createView( test::createView( "rtv", rt ) ); + auto rt = graph.createImageId( test::createImage( "rt", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto rtv = graph.createViewId( test::createView( "rtv", rt ) ); auto & pass1 = graph.createPass( "pass1C" , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -216,8 +223,8 @@ TEST( RenderGraph, CycleDependency ) } ); auto rta = pass1.addOutputColourTarget( rtv ); - auto out = graph.createImage( test::createImage( "out", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto outv = graph.createView( test::createView( "outv", out ) ); + auto out = graph.createImageId( test::createImage( "out", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto outv = graph.createViewId( test::createView( "outv", out ) ); auto & pass2 = graph.createPass( "pass2C" , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -263,8 +270,8 @@ TEST( RenderGraph, ChainedDependencies ) testBegin( "testChainedDependencies" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto d0 = graph.createImage( test::createImage( "d0", crg::PixelFormat::eR32G32B32_SFLOAT ) ); - auto d0v = graph.createView( test::createView( "d0v", d0 ) ); + auto d0 = graph.createImageId( test::createImage( "d0", crg::PixelFormat::eR32G32B32_SFLOAT ) ); + auto d0v = graph.createViewId( test::createView( "d0v", d0 ) ); auto & pass0 = graph.createPass( "pass0" , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -275,8 +282,8 @@ TEST( RenderGraph, ChainedDependencies ) } ); auto d0a = pass0.addOutputColourTarget( d0v ); - auto d1 = graph.createImage( test::createImage( "d1", crg::PixelFormat::eR32G32B32_SFLOAT ) ); - auto d1v = graph.createView( test::createView( "d1v", d1 ) ); + auto d1 = graph.createImageId( test::createImage( "d1", crg::PixelFormat::eR32G32B32_SFLOAT ) ); + auto d1v = graph.createViewId( test::createView( "d1v", d1 ) ); auto & pass1 = graph.createPass( "pass1" , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -288,8 +295,8 @@ TEST( RenderGraph, ChainedDependencies ) pass1.addInputSampled( *d0a, 0u ); auto d1a = pass1.addOutputColourTarget( d1v ); - auto buf = graph.createBuffer( test::createBuffer( "buf" ) ); - auto bufv = graph.createView( test::createView( "bufv", buf ) ); + auto buf = graph.createBufferId( test::createBuffer( "buf" ) ); + auto bufv = graph.createViewId( test::createView( "bufv", buf ) ); auto & pass2 = graph.createPass( "pass2" , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -332,12 +339,12 @@ TEST( RenderGraph, SharedDependencies ) testBegin( "testSharedDependencies" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto d = graph.createImage( test::createImage( "d", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); - auto dstv1 = graph.createView( test::createView( "dstv1", d ) ); - auto buf = graph.createBuffer( test::createBuffer( "buf" ) ); - auto bufv1 = graph.createView( test::createView( "bufv1", buf ) ); - auto d0 = graph.createImage( test::createImage( "d0", crg::PixelFormat::eR32G32B32_SFLOAT ) ); - auto d0v = graph.createView( test::createView( "d0v", d0 ) ); + auto d = graph.createImageId( test::createImage( "d", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); + auto dstv1 = graph.createViewId( test::createView( "dstv1", d ) ); + auto buf = graph.createBufferId( test::createBuffer( "buf" ) ); + auto bufv1 = graph.createViewId( test::createView( "bufv1", buf ) ); + auto d0 = graph.createImageId( test::createImage( "d0", crg::PixelFormat::eR32G32B32_SFLOAT ) ); + auto d0v = graph.createViewId( test::createView( "d0v", d0 ) ); auto & pass0 = graph.createPass( "pass0" , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -350,10 +357,10 @@ TEST( RenderGraph, SharedDependencies ) pass0.addOutputDepthTarget( dstv1 ); auto d0a = pass0.addOutputColourTarget( d0v ); - auto dstv2 = graph.createView( test::createView( "dstv2", d ) ); - auto bufv2 = graph.createView( test::createView( "bufv2", buf ) ); - auto d1 = graph.createImage( test::createImage( "d1", crg::PixelFormat::eR32G32B32_SFLOAT ) ); - auto d1v = graph.createView( test::createView( "d1v", d1 ) ); + auto dstv2 = graph.createViewId( test::createView( "dstv2", d ) ); + auto bufv2 = graph.createViewId( test::createView( "bufv2", buf ) ); + auto d1 = graph.createImageId( test::createImage( "d1", crg::PixelFormat::eR32G32B32_SFLOAT ) ); + auto d1v = graph.createViewId( test::createView( "d1v", d1 ) ); auto & pass1 = graph.createPass( "pass1" , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -367,8 +374,8 @@ TEST( RenderGraph, SharedDependencies ) auto dsta = pass1.addOutputDepthTarget ( dstv2 ); auto d1a = pass1.addOutputColourTarget( d1v ); - auto d2 = graph.createImage( test::createImage( "d2", crg::PixelFormat::eR32G32B32_SFLOAT ) ); - auto d2v = graph.createView( test::createView( "d2v", d2 ) ); + auto d2 = graph.createImageId( test::createImage( "d2", crg::PixelFormat::eR32G32B32_SFLOAT ) ); + auto d2v = graph.createViewId( test::createView( "d2v", d2 ) ); auto & pass2 = graph.createPass( "pass2" , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -424,9 +431,9 @@ TEST( RenderGraph, 2MipDependencies ) testBegin( "test2MipDependencies" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto lp = graph.createImage( test::createImage( "lp", crg::PixelFormat::eR32G32B32_SFLOAT, 3u ) ); - auto m0v = graph.createView( test::createView( "m0v", lp, 0u ) ); - auto m1v = graph.createView( test::createView( "m1v", lp, 1u ) ); + auto lp = graph.createImageId( test::createImage( "lp", crg::PixelFormat::eR32G32B32_SFLOAT, 3u ) ); + auto m0v = graph.createViewId( test::createView( "m0v", lp, 0u ) ); + auto m1v = graph.createViewId( test::createView( "m1v", lp, 1u ) ); auto m0a = crg::Attachment::createDefault( m0v ); graph.addInput( m0v, makeLayoutState( crg::ImageLayout::eShaderReadOnly ) ); auto & ssaoMinifyPass1 = graph.createPass( "ssaoMinifyPass1" @@ -440,7 +447,7 @@ TEST( RenderGraph, 2MipDependencies ) ssaoMinifyPass1.addInputSampled( m0a, 0 ); auto m1a = ssaoMinifyPass1.addOutputColourTarget( m1v ); - auto m2v = graph.createView( test::createView( "m2v", lp, 2u ) ); + auto m2v = graph.createViewId( test::createView( "m2v", lp, 2u ) ); auto & ssaoMinifyPass2 = graph.createPass( "ssaoMinifyPass2" , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -475,9 +482,9 @@ TEST( RenderGraph, 3MipDependencies ) testBegin( "test3MipDependencies" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto lp = graph.createImage( test::createImage( "lp", crg::PixelFormat::eR32G32B32_SFLOAT, 4u ) ); - auto m0v = graph.createView( test::createView( "m0v", lp, crg::PixelFormat::eR32G32B32_SFLOAT, 0u ) ); - auto m1v = graph.createView( test::createView( "m1v", lp, crg::PixelFormat::eR32G32B32_SFLOAT, 1u ) ); + auto lp = graph.createImageId( test::createImage( "lp", crg::PixelFormat::eR32G32B32_SFLOAT, 4u ) ); + auto m0v = graph.createViewId( test::createView( "m0v", lp, crg::PixelFormat::eR32G32B32_SFLOAT, 0u ) ); + auto m1v = graph.createViewId( test::createView( "m1v", lp, crg::PixelFormat::eR32G32B32_SFLOAT, 1u ) ); auto m0a = crg::Attachment::createDefault( m0v ); auto & ssaoMinifyPass1 = graph.createPass( "ssaoMinifyPass1" , [&testCounts]( crg::FramePass const & framePass @@ -490,7 +497,7 @@ TEST( RenderGraph, 3MipDependencies ) ssaoMinifyPass1.addInputSampled( m0a, 0 ); auto m1a = ssaoMinifyPass1.addOutputColourTarget( m1v ); - auto m2v = graph.createView( test::createView( "m2v", lp, crg::PixelFormat::eR32G32B32_SFLOAT, 2u ) ); + auto m2v = graph.createViewId( test::createView( "m2v", lp, crg::PixelFormat::eR32G32B32_SFLOAT, 2u ) ); auto & ssaoMinifyPass2 = graph.createPass( "ssaoMinifyPass2" , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -502,7 +509,7 @@ TEST( RenderGraph, 3MipDependencies ) ssaoMinifyPass2.addInputSampled( *m1a, 0 ); auto m2a = ssaoMinifyPass2.addOutputColourTarget( m2v ); - auto m3v = graph.createView( test::createView( "m3v", lp, crg::PixelFormat::eR32G32B32_SFLOAT, 3u ) ); + auto m3v = graph.createViewId( test::createView( "m3v", lp, crg::PixelFormat::eR32G32B32_SFLOAT, 3u ) ); auto & ssaoMinifyPass3 = graph.createPass( "ssaoMinifyPass3" , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -541,10 +548,10 @@ TEST( RenderGraph, LoopDependencies ) testBegin( "testLoopDependencies" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto a = graph.createImage( test::createImage( "a", crg::PixelFormat::eR32G32B32_SFLOAT ) ); - auto av = graph.createView( test::createView( "av", a, crg::PixelFormat::eR32G32B32_SFLOAT ) ); - auto b = graph.createImage( test::createImage( "b", crg::PixelFormat::eR32G32B32_SFLOAT ) ); - auto bv = graph.createView( test::createView( "bv", b, crg::PixelFormat::eR32G32B32_SFLOAT ) ); + auto a = graph.createImageId( test::createImage( "a", crg::PixelFormat::eR32G32B32_SFLOAT ) ); + auto av = graph.createViewId( test::createView( "av", a, crg::PixelFormat::eR32G32B32_SFLOAT ) ); + auto b = graph.createImageId( test::createImage( "b", crg::PixelFormat::eR32G32B32_SFLOAT ) ); + auto bv = graph.createViewId( test::createView( "bv", b, crg::PixelFormat::eR32G32B32_SFLOAT ) ); auto ba = crg::Attachment::createDefault( bv ); auto & pass1 = graph.createPass( "pass1" , [&testCounts]( crg::FramePass const & framePass @@ -578,8 +585,8 @@ TEST( RenderGraph, LoopDependenciesWithRoot ) testBegin( "testLoopDependenciesWithRoot" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto b = graph.createImage( test::createImage( "b", crg::PixelFormat::eR32G32B32_SFLOAT ) ); - auto bv = graph.createView( test::createView( "bv", b, crg::PixelFormat::eR32G32B32_SFLOAT ) ); + auto b = graph.createImageId( test::createImage( "b", crg::PixelFormat::eR32G32B32_SFLOAT ) ); + auto bv = graph.createViewId( test::createView( "bv", b, crg::PixelFormat::eR32G32B32_SFLOAT ) ); auto & pass0 = graph.createPass( "pass0" , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -590,8 +597,8 @@ TEST( RenderGraph, LoopDependenciesWithRoot ) } ); auto ba = pass0.addOutputColourTarget( bv ); - auto a = graph.createImage( test::createImage( "a", crg::PixelFormat::eR32G32B32_SFLOAT ) ); - auto av = graph.createView( test::createView( "av", a, crg::PixelFormat::eR32G32B32_SFLOAT ) ); + auto a = graph.createImageId( test::createImage( "a", crg::PixelFormat::eR32G32B32_SFLOAT ) ); + auto av = graph.createViewId( test::createView( "av", a, crg::PixelFormat::eR32G32B32_SFLOAT ) ); auto & pass1 = graph.createPass( "pass1" , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -624,8 +631,8 @@ TEST( RenderGraph, LoopDependenciesWithRootAndLeaf ) testBegin( "testLoopDependenciesWithRootAndLeaf" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto c = graph.createImage( test::createImage( "c", crg::PixelFormat::eR32G32B32_SFLOAT ) ); - auto cv = graph.createView( test::createView( "cv", c, crg::PixelFormat::eR32G32B32_SFLOAT ) ); + auto c = graph.createImageId( test::createImage( "c", crg::PixelFormat::eR32G32B32_SFLOAT ) ); + auto cv = graph.createViewId( test::createView( "cv", c, crg::PixelFormat::eR32G32B32_SFLOAT ) ); auto & pass0 = graph.createPass( "pass0" , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -636,10 +643,10 @@ TEST( RenderGraph, LoopDependenciesWithRootAndLeaf ) } ); auto ca = pass0.addOutputColourTarget( cv ); - auto a = graph.createImage( test::createImage( "a", crg::PixelFormat::eR32G32B32_SFLOAT ) ); - auto av = graph.createView( test::createView( "av", a, crg::PixelFormat::eR32G32B32_SFLOAT ) ); - auto b = graph.createImage( test::createImage( "b", crg::PixelFormat::eR32G32B32_SFLOAT ) ); - auto bv = graph.createView( test::createView( "bv", b, crg::PixelFormat::eR32G32B32_SFLOAT ) ); + auto a = graph.createImageId( test::createImage( "a", crg::PixelFormat::eR32G32B32_SFLOAT ) ); + auto av = graph.createViewId( test::createView( "av", a, crg::PixelFormat::eR32G32B32_SFLOAT ) ); + auto b = graph.createImageId( test::createImage( "b", crg::PixelFormat::eR32G32B32_SFLOAT ) ); + auto bv = graph.createViewId( test::createView( "bv", b, crg::PixelFormat::eR32G32B32_SFLOAT ) ); auto ba = crg::Attachment::createDefault( bv ); auto & pass1 = graph.createPass( "pass1" , [&testCounts]( crg::FramePass const & framePass @@ -665,8 +672,8 @@ TEST( RenderGraph, LoopDependenciesWithRootAndLeaf ) pass2.addInputSampled( *ca, 1 ); pass2.addOutputColourTarget( bv ); - auto buf = graph.createBuffer( test::createBuffer( "buf" ) ); - auto bufv = graph.createView( test::createView( "bufv", buf ) ); + auto buf = graph.createBufferId( test::createBuffer( "buf" ) ); + auto bufv = graph.createViewId( test::createView( "bufv", buf ) ); auto & pass3 = graph.createPass( "pass3" , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -708,8 +715,8 @@ crg::Attachment const * buildSsaoPass( test::TestCounts & testCounts , crg::Attachment const & lda , crg::FrameGraph & graph ) { - auto lp = graph.createImage( test::createImage( "lp", crg::PixelFormat::eR32_SFLOAT, 4u ) ); - auto m0v = graph.createView( test::createView( "m0v", lp, crg::PixelFormat::eR32_SFLOAT, 0u ) ); + auto lp = graph.createImageId( test::createImage( "lp", crg::PixelFormat::eR32_SFLOAT, 4u ) ); + auto m0v = graph.createViewId( test::createView( "m0v", lp, crg::PixelFormat::eR32_SFLOAT, 0u ) ); auto & ssaoLinearisePass = graph.createPass( "ssaoLinearisePass" , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -721,7 +728,7 @@ crg::Attachment const * buildSsaoPass( test::TestCounts & testCounts ssaoLinearisePass.addInputSampled( lda, 0 ); auto m0a = ssaoLinearisePass.addOutputColourTarget( m0v ); - auto m1v = graph.createView( test::createView( "m1v", lp, crg::PixelFormat::eR32_SFLOAT, 1u ) ); + auto m1v = graph.createViewId( test::createView( "m1v", lp, crg::PixelFormat::eR32_SFLOAT, 1u ) ); auto & ssaoMinifyPass1 = graph.createPass( "ssaoMinifyPass1" , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -733,7 +740,7 @@ crg::Attachment const * buildSsaoPass( test::TestCounts & testCounts ssaoMinifyPass1.addInputSampled( *m0a, 0 ); auto m1a = ssaoMinifyPass1.addOutputColourTarget( m1v ); - auto m2v = graph.createView( test::createView( "m2v", lp, crg::PixelFormat::eR32G32B32_SFLOAT, 2u ) ); + auto m2v = graph.createViewId( test::createView( "m2v", lp, crg::PixelFormat::eR32G32B32_SFLOAT, 2u ) ); auto & ssaoMinifyPass2 = graph.createPass( "ssaoMinifyPass2" , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -745,7 +752,7 @@ crg::Attachment const * buildSsaoPass( test::TestCounts & testCounts ssaoMinifyPass2.addInputSampled( *m1a, 0 ); auto m2a = ssaoMinifyPass2.addOutputColourTarget( m2v ); - auto m3v = graph.createView( test::createView( "m3v", lp, crg::PixelFormat::eR32G32B32_SFLOAT, 3u ) ); + auto m3v = graph.createViewId( test::createView( "m3v", lp, crg::PixelFormat::eR32G32B32_SFLOAT, 3u ) ); auto & ssaoMinifyPass3 = graph.createPass( "ssaoMinifyPass3" , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -757,8 +764,8 @@ crg::Attachment const * buildSsaoPass( test::TestCounts & testCounts ssaoMinifyPass3.addInputSampled( *m2a, 0 ); auto m3a = ssaoMinifyPass3.addOutputColourTarget( m3v ); - auto rs = graph.createImage( test::createImage( "rs", crg::PixelFormat::eR32_SFLOAT ) ); - auto rsv = graph.createView( test::createView( "rsv", rs, crg::PixelFormat::eR32_SFLOAT ) ); + auto rs = graph.createImageId( test::createImage( "rs", crg::PixelFormat::eR32_SFLOAT ) ); + auto rsv = graph.createViewId( test::createView( "rsv", rs, crg::PixelFormat::eR32_SFLOAT ) ); auto & ssaoRawPass = graph.createPass( "ssaoRawPass" , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -771,8 +778,8 @@ crg::Attachment const * buildSsaoPass( test::TestCounts & testCounts ssaoRawPass.addInputSampled( *m3a, 1 ); auto rsa = ssaoRawPass.addOutputColourTarget( rsv ); - auto bl = graph.createImage( test::createImage( "b1", crg::PixelFormat::eR32_SFLOAT ) ); - auto blv = graph.createView( test::createView( "b1v", bl, crg::PixelFormat::eR32_SFLOAT ) ); + auto bl = graph.createImageId( test::createImage( "b1", crg::PixelFormat::eR32_SFLOAT ) ); + auto blv = graph.createViewId( test::createView( "b1v", bl, crg::PixelFormat::eR32_SFLOAT ) ); auto & ssaoBlurPass = graph.createPass( "ssaoBlurPass" , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -791,20 +798,20 @@ TEST( RenderGraph, SsaoPass ) testBegin( "testSsaoPass" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto d = graph.createImage( test::createImage( "d", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); - auto dtv = graph.createView( test::createView( "dtv", d, crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); - auto ld = graph.createImage( test::createImage( "ld", crg::PixelFormat::eR32_SFLOAT ) ); - auto ldv = graph.createView( test::createView( "ldv", ld, crg::PixelFormat::eR32_SFLOAT ) ); - auto v = graph.createImage( test::createImage( "v", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto vv = graph.createView( test::createView( "vv", v, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto d1 = graph.createImage( test::createImage( "d1", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto d1v = graph.createView( test::createView( "d1v", d1, crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto d2 = graph.createImage( test::createImage( "d2", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto d2v = graph.createView( test::createView( "d2v", d2, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto d3 = graph.createImage( test::createImage( "d3", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto d3v = graph.createView( test::createView( "d3v", d3, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto d4 = graph.createImage( test::createImage( "d4", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto d4v = graph.createView( test::createView( "d4v", d4, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto d = graph.createImageId( test::createImage( "d", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); + auto dtv = graph.createViewId( test::createView( "dtv", d, crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); + auto ld = graph.createImageId( test::createImage( "ld", crg::PixelFormat::eR32_SFLOAT ) ); + auto ldv = graph.createViewId( test::createView( "ldv", ld, crg::PixelFormat::eR32_SFLOAT ) ); + auto v = graph.createImageId( test::createImage( "v", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto vv = graph.createViewId( test::createView( "vv", v, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto d1 = graph.createImageId( test::createImage( "d1", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto d1v = graph.createViewId( test::createView( "d1v", d1, crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto d2 = graph.createImageId( test::createImage( "d2", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto d2v = graph.createViewId( test::createView( "d2v", d2, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto d3 = graph.createImageId( test::createImage( "d3", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto d3v = graph.createViewId( test::createView( "d3v", d3, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto d4 = graph.createImageId( test::createImage( "d4", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto d4v = graph.createViewId( test::createView( "d4v", d4, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); auto & geometryPass = graph.createPass( "geometryPass" , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -825,8 +832,8 @@ TEST( RenderGraph, SsaoPass ) , *lda , graph ); - auto of = graph.createImage( test::createImage( "of", crg::PixelFormat::eR32G32B32_SFLOAT ) ); - auto ofv = graph.createView( test::createView( "ofv", of, crg::PixelFormat::eR32G32B32_SFLOAT ) ); + auto of = graph.createImageId( test::createImage( "of", crg::PixelFormat::eR32G32B32_SFLOAT ) ); + auto ofv = graph.createViewId( test::createView( "ofv", of, crg::PixelFormat::eR32G32B32_SFLOAT ) ); auto & ambientPass = graph.createPass( "ambientPass" , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -898,21 +905,21 @@ TEST( RenderGraph, BloomPostEffect ) testBegin( "testBloomPostEffect" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto scene = graph.createImage( test::createImage( "scene", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto scenev = graph.createView( test::createView( "scenev", scene, crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto scene = graph.createImageId( test::createImage( "scene", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto scenev = graph.createViewId( test::createView( "scenev", scene, crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); auto scenea = crg::Attachment::createDefault( scenev ); - auto output = graph.createImage( test::createImage( "output", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto outputv = graph.createView( test::createView( "outputv", output, crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto hi = graph.createImage( test::createImage( "hi", crg::PixelFormat::eR32G32B32A32_SFLOAT, 4u ) ); - auto hi0v = graph.createView( test::createView( "hi0v", hi, crg::PixelFormat::eR32G32B32A32_SFLOAT, 0u ) ); - auto hi1v = graph.createView( test::createView( "hi1v", hi, crg::PixelFormat::eR32G32B32A32_SFLOAT, 1u ) ); - auto hi2v = graph.createView( test::createView( "hi2v", hi, crg::PixelFormat::eR32G32B32A32_SFLOAT, 2u ) ); - auto hi3v = graph.createView( test::createView( "hi3v", hi, crg::PixelFormat::eR32G32B32A32_SFLOAT, 3u ) ); - auto bl = graph.createImage( test::createImage( "bl", crg::PixelFormat::eR32G32B32A32_SFLOAT, 4u ) ); - auto bl0v = graph.createView( test::createView( "bl0v", bl, crg::PixelFormat::eR32G32B32A32_SFLOAT, 0u ) ); - auto bl1v = graph.createView( test::createView( "bl1v", bl, crg::PixelFormat::eR32G32B32A32_SFLOAT, 1u ) ); - auto bl2v = graph.createView( test::createView( "bl2v", bl, crg::PixelFormat::eR32G32B32A32_SFLOAT, 2u ) ); - auto bl3v = graph.createView( test::createView( "bl3v", bl, crg::PixelFormat::eR32G32B32A32_SFLOAT, 3u ) ); + auto output = graph.createImageId( test::createImage( "output", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto outputv = graph.createViewId( test::createView( "outputv", output, crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto hi = graph.createImageId( test::createImage( "hi", crg::PixelFormat::eR32G32B32A32_SFLOAT, 4u ) ); + auto hi0v = graph.createViewId( test::createView( "hi0v", hi, crg::PixelFormat::eR32G32B32A32_SFLOAT, 0u ) ); + auto hi1v = graph.createViewId( test::createView( "hi1v", hi, crg::PixelFormat::eR32G32B32A32_SFLOAT, 1u ) ); + auto hi2v = graph.createViewId( test::createView( "hi2v", hi, crg::PixelFormat::eR32G32B32A32_SFLOAT, 2u ) ); + auto hi3v = graph.createViewId( test::createView( "hi3v", hi, crg::PixelFormat::eR32G32B32A32_SFLOAT, 3u ) ); + auto bl = graph.createImageId( test::createImage( "bl", crg::PixelFormat::eR32G32B32A32_SFLOAT, 4u ) ); + auto bl0v = graph.createViewId( test::createView( "bl0v", bl, crg::PixelFormat::eR32G32B32A32_SFLOAT, 0u ) ); + auto bl1v = graph.createViewId( test::createView( "bl1v", bl, crg::PixelFormat::eR32G32B32A32_SFLOAT, 1u ) ); + auto bl2v = graph.createViewId( test::createView( "bl2v", bl, crg::PixelFormat::eR32G32B32A32_SFLOAT, 2u ) ); + auto bl3v = graph.createViewId( test::createView( "bl3v", bl, crg::PixelFormat::eR32G32B32A32_SFLOAT, 3u ) ); auto & hiPass = graph.createPass( "hiPass" , [&testCounts]( crg::FramePass const & framePass @@ -1036,14 +1043,14 @@ crg::Attachment const * buildDeferred( test::TestCounts & testCounts , crg::ImageViewId const & vtv , crg::FrameGraph & graph ) { - auto d1 = graph.createImage( test::createImage( "d1", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto d1v = graph.createView( test::createView( "d1v", d1, crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto d2 = graph.createImage( test::createImage( "d2", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto d2v = graph.createView( test::createView( "d2v", d2, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto d3 = graph.createImage( test::createImage( "d3", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto d3v = graph.createView( test::createView( "d3v", d3, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto d4 = graph.createImage( test::createImage( "d4", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto d4v = graph.createView( test::createView( "d4v", d4, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto d1 = graph.createImageId( test::createImage( "d1", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto d1v = graph.createViewId( test::createView( "d1v", d1, crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto d2 = graph.createImageId( test::createImage( "d2", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto d2v = graph.createViewId( test::createView( "d2v", d2, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto d3 = graph.createImageId( test::createImage( "d3", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto d3v = graph.createViewId( test::createView( "d3v", d3, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto d4 = graph.createImageId( test::createImage( "d4", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto d4v = graph.createViewId( test::createView( "d4v", d4, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); auto & geometryPass = graph.createPass( "geometryPass" , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -1065,10 +1072,10 @@ crg::Attachment const * buildDeferred( test::TestCounts & testCounts else dta = geometryPass.addOutputDepthStencilTarget( dtv ); - auto df = graph.createImage( test::createImage( "df", crg::PixelFormat::eR32G32B32_SFLOAT ) ); - auto dfv = graph.createView( test::createView( "dfv", df, crg::PixelFormat::eR32G32B32_SFLOAT ) ); - auto sp = graph.createImage( test::createImage( "sp", crg::PixelFormat::eR32G32B32_SFLOAT ) ); - auto spv = graph.createView( test::createView( "spv", sp, crg::PixelFormat::eR32G32B32_SFLOAT ) ); + auto df = graph.createImageId( test::createImage( "df", crg::PixelFormat::eR32G32B32_SFLOAT ) ); + auto dfv = graph.createViewId( test::createView( "dfv", df, crg::PixelFormat::eR32G32B32_SFLOAT ) ); + auto sp = graph.createImageId( test::createImage( "sp", crg::PixelFormat::eR32G32B32_SFLOAT ) ); + auto spv = graph.createViewId( test::createView( "spv", sp, crg::PixelFormat::eR32G32B32_SFLOAT ) ); auto & lightingPass = graph.createPass( "lightingPass" , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -1085,8 +1092,8 @@ crg::Attachment const * buildDeferred( test::TestCounts & testCounts auto dfa = lightingPass.addOutputColourTarget( dfv ); auto spa = lightingPass.addOutputColourTarget( spv ); - auto of = graph.createImage( test::createImage( "of", crg::PixelFormat::eR32G32B32_SFLOAT ) ); - auto ofv = graph.createView( test::createView( "ofv", of, crg::PixelFormat::eR32G32B32_SFLOAT ) ); + auto of = graph.createImageId( test::createImage( "of", crg::PixelFormat::eR32G32B32_SFLOAT ) ); + auto ofv = graph.createViewId( test::createView( "ofv", of, crg::PixelFormat::eR32G32B32_SFLOAT ) ); if constexpr ( EnableSsao ) { @@ -1138,10 +1145,10 @@ crg::Attachment const * buildWeightedBlended( test::TestCounts & testCounts , crg::ImageViewId const & dtv , crg::FrameGraph & graph ) { - auto a = graph.createImage( test::createImage( "a", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto av = graph.createView( test::createView( "av", a, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto r = graph.createImage( test::createImage( "r", crg::PixelFormat::eR16_SFLOAT ) ); - auto rv = graph.createView( test::createView( "rv", r, crg::PixelFormat::eR16_SFLOAT ) ); + auto a = graph.createImageId( test::createImage( "a", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto av = graph.createViewId( test::createView( "av", a, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto r = graph.createImageId( test::createImage( "r", crg::PixelFormat::eR16_SFLOAT ) ); + auto rv = graph.createViewId( test::createView( "rv", r, crg::PixelFormat::eR16_SFLOAT ) ); auto & accumulationPass = graph.createPass( "accumulationPass" , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -1157,8 +1164,8 @@ crg::Attachment const * buildWeightedBlended( test::TestCounts & testCounts else dta = accumulationPass.addOutputDepthStencilTarget( dtv ); - auto c = graph.createImage( test::createImage( "c", crg::PixelFormat::eR32G32B32_SFLOAT ) ); - auto cv = graph.createView( test::createView( "cv", c, crg::PixelFormat::eR32G32B32_SFLOAT ) ); + auto c = graph.createImageId( test::createImage( "c", crg::PixelFormat::eR32G32B32_SFLOAT ) ); + auto cv = graph.createViewId( test::createView( "cv", c, crg::PixelFormat::eR32G32B32_SFLOAT ) ); auto & combinePass = graph.createPass( "combinePass" , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -1236,10 +1243,10 @@ TYPED_TEST( RenderGraphT, Render ) + ( EnableTransparent ? std::string{ "Transparent" } : std::string{} ) ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto d = graph.createImage( test::createImage( "d", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); - auto dtv = graph.createView( test::createView( "dtv", d, crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); - auto ld = graph.createImage( test::createImage( "ld", crg::PixelFormat::eR32_SFLOAT ) ); - auto ldv = graph.createView( test::createView( "ldv", ld, crg::PixelFormat::eR32_SFLOAT ) ); + auto d = graph.createImageId( test::createImage( "d", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); + auto dtv = graph.createViewId( test::createView( "dtv", d, crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); + auto ld = graph.createImageId( test::createImage( "ld", crg::PixelFormat::eR32_SFLOAT ) ); + auto ldv = graph.createViewId( test::createView( "ldv", ld, crg::PixelFormat::eR32_SFLOAT ) ); crg::Attachment const * dta{}; crg::Attachment const * lda{}; @@ -1257,13 +1264,13 @@ TYPED_TEST( RenderGraphT, Render ) dta = depthPrepass.addOutputDepthTarget ( dtv ); } - auto o = graph.createImage( test::createImage( "o", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto otv = graph.createView( test::createView( "otv", o, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto o = graph.createImageId( test::createImage( "o", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto otv = graph.createViewId( test::createView( "otv", o, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); if constexpr ( EnableOpaque ) { - auto v = graph.createImage( test::createImage( "v", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto vv = graph.createView( test::createView( "vv", v, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto v = graph.createImageId( test::createImage( "v", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto vv = graph.createViewId( test::createView( "vv", v, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); auto dca = buildDeferred< EnableSsao >( testCounts , lda , dta @@ -1874,20 +1881,20 @@ TEST( RenderGraph, VarianceShadowMap ) crg::FrameGraph graph{ handler, testCounts.testName }; auto & dirGroup = graph.createPassGroup( "Directional" ); - auto dirShadowMap = dirGroup.createImage( test::createImage( "dirShadowMap", crg::PixelFormat::eX8_D24_UNORM, 1u, 4u ) ); - auto dirVarianceMap = dirGroup.createImage( test::createImage( "dirVarianceMap", crg::PixelFormat::eR32G32_SFLOAT, 1u, 4u ) ); - auto buffer = dirGroup.createBuffer( test::createBuffer( "buffer" ) ); - auto bufferv = dirGroup.createView( test::createView( "bufferv", buffer ) ); + auto dirShadowMap = dirGroup.createImageId( test::createImage( "dirShadowMap", crg::PixelFormat::eX8_D24_UNORM, 1u, 4u ) ); + auto dirVarianceMap = dirGroup.createImageId( test::createImage( "dirVarianceMap", crg::PixelFormat::eR32G32_SFLOAT, 1u, 4u ) ); + auto buffer = dirGroup.createBufferId( test::createBuffer( "buffer" ) ); + auto bufferv = dirGroup.createViewId( test::createView( "bufferv", buffer ) ); crg::AttachmentArray dirShadows; crg::AttachmentArray dirVariances; { - auto intermediate = dirGroup.createImage( test::createImage( "dirIntermediate", crg::PixelFormat::eR32G32_SFLOAT ) ); - auto intermediatev = dirGroup.createView( test::createView( "dirIntermediatev", intermediate, crg::PixelFormat::eR32G32_SFLOAT ) ); + auto intermediate = dirGroup.createImageId( test::createImage( "dirIntermediate", crg::PixelFormat::eR32G32_SFLOAT ) ); + auto intermediatev = dirGroup.createViewId( test::createView( "dirIntermediatev", intermediate, crg::PixelFormat::eR32G32_SFLOAT ) ); for ( uint32_t index = 0u; index < 4u; ++index ) { - auto shadowMapv = dirGroup.createView( test::createView( "dirShadowMapv" + std::to_string( index ), dirShadowMap, crg::PixelFormat::eX8_D24_UNORM, 0u, 1u, index ) ); - auto varianceMapv = dirGroup.createView( test::createView( "dirVarianceMapv" + std::to_string( index ), dirVarianceMap, crg::PixelFormat::eR32G32_SFLOAT, 0u, 1u, index ) ); + auto shadowMapv = dirGroup.createViewId( test::createView( "dirShadowMapv" + std::to_string( index ), dirShadowMap, crg::PixelFormat::eX8_D24_UNORM, 0u, 1u, index ) ); + auto varianceMapv = dirGroup.createViewId( test::createView( "dirVarianceMapv" + std::to_string( index ), dirVarianceMap, crg::PixelFormat::eR32G32_SFLOAT, 0u, 1u, index ) ); auto & shadowPass = dirGroup.createPass( "dirShadowPass" + std::to_string( index ) , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -1931,18 +1938,18 @@ TEST( RenderGraph, VarianceShadowMap ) } } auto & pntGroup = graph.createPassGroup( "Point" ); - auto pntShadowMap = pntGroup.createImage( test::createImage( "pntShadowMap", crg::PixelFormat::eX8_D24_UNORM, 1u, 36u ) ); - auto pntVarianceMap = pntGroup.createImage( test::createImage( "pntVarianceMap", crg::PixelFormat::eR32G32_SFLOAT, 1u, 36u ) ); + auto pntShadowMap = pntGroup.createImageId( test::createImage( "pntShadowMap", crg::PixelFormat::eX8_D24_UNORM, 1u, 36u ) ); + auto pntVarianceMap = pntGroup.createImageId( test::createImage( "pntVarianceMap", crg::PixelFormat::eR32G32_SFLOAT, 1u, 36u ) ); crg::AttachmentArray pntShadows; crg::AttachmentArray pntVariances; { - auto intermediate = pntGroup.createImage( test::createImage( "pntIntermediate", crg::PixelFormat::eR32G32_SFLOAT ) ); - auto intermediatev = pntGroup.createView( test::createView( "pntIntermediatev", intermediate, crg::PixelFormat::eR32G32_SFLOAT ) ); + auto intermediate = pntGroup.createImageId( test::createImage( "pntIntermediate", crg::PixelFormat::eR32G32_SFLOAT ) ); + auto intermediatev = pntGroup.createViewId( test::createView( "pntIntermediatev", intermediate, crg::PixelFormat::eR32G32_SFLOAT ) ); for ( uint32_t index = 0u; index < 36u; ++index ) { - auto shadowMapv = pntGroup.createView( test::createView( "pntShadowMapv" + std::to_string( index ), pntShadowMap, crg::PixelFormat::eX8_D24_UNORM, 0u, 1u, index ) ); - auto varianceMapv = pntGroup.createView( test::createView( "pntVarianceMapv" + std::to_string( index ), pntVarianceMap, crg::PixelFormat::eR32G32_SFLOAT, 0u, 1u, index ) ); + auto shadowMapv = pntGroup.createViewId( test::createView( "pntShadowMapv" + std::to_string( index ), pntShadowMap, crg::PixelFormat::eX8_D24_UNORM, 0u, 1u, index ) ); + auto varianceMapv = pntGroup.createViewId( test::createView( "pntVarianceMapv" + std::to_string( index ), pntVarianceMap, crg::PixelFormat::eR32G32_SFLOAT, 0u, 1u, index ) ); auto & shadowPass = pntGroup.createPass( "pntShadowPass" + std::to_string( index ) , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -1986,18 +1993,18 @@ TEST( RenderGraph, VarianceShadowMap ) } } auto & sptGroup = graph.createPassGroup( "Spot" ); - auto sptShadowMap = sptGroup.createImage( test::createImage( "sptShadowMap", crg::PixelFormat::eX8_D24_UNORM, 1u, 10u ) ); - auto sptVarianceMap = sptGroup.createImage( test::createImage( "pntVarianceMap", crg::PixelFormat::eR32G32_SFLOAT, 1u, 10u ) ); + auto sptShadowMap = sptGroup.createImageId( test::createImage( "sptShadowMap", crg::PixelFormat::eX8_D24_UNORM, 1u, 10u ) ); + auto sptVarianceMap = sptGroup.createImageId( test::createImage( "pntVarianceMap", crg::PixelFormat::eR32G32_SFLOAT, 1u, 10u ) ); crg::AttachmentArray sptShadows; crg::AttachmentArray sptVariances; { - auto intermediate = sptGroup.createImage( test::createImage( "sptIntermediate", crg::PixelFormat::eR32G32_SFLOAT ) ); - auto intermediatev = sptGroup.createView( test::createView( "sptIntermediatev", intermediate, crg::PixelFormat::eR32G32_SFLOAT ) ); + auto intermediate = sptGroup.createImageId( test::createImage( "sptIntermediate", crg::PixelFormat::eR32G32_SFLOAT ) ); + auto intermediatev = sptGroup.createViewId( test::createView( "sptIntermediatev", intermediate, crg::PixelFormat::eR32G32_SFLOAT ) ); for ( uint32_t index = 0u; index < 10u; ++index ) { - auto shadowMapv = sptGroup.createView( test::createView( "sptShadowMapv" + std::to_string( index ), sptShadowMap, crg::PixelFormat::eX8_D24_UNORM, 0u, 1u, index ) ); - auto varianceMapv = sptGroup.createView( test::createView( "sptVarianceMapv" + std::to_string( index ), sptVarianceMap, crg::PixelFormat::eR32G32_SFLOAT, 0u, 1u, index ) ); + auto shadowMapv = sptGroup.createViewId( test::createView( "sptShadowMapv" + std::to_string( index ), sptShadowMap, crg::PixelFormat::eX8_D24_UNORM, 0u, 1u, index ) ); + auto varianceMapv = sptGroup.createViewId( test::createView( "sptVarianceMapv" + std::to_string( index ), sptVarianceMap, crg::PixelFormat::eR32G32_SFLOAT, 0u, 1u, index ) ); auto & shadowPass = sptGroup.createPass( "sptShadowPass" + std::to_string( index ) , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -2043,8 +2050,8 @@ TEST( RenderGraph, VarianceShadowMap ) } auto & objGroup = graph.createPassGroup( "Objects" ); - auto depth = graph.createImage( test::createImage( "depth", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); - auto depthv = graph.createView( test::createView( "depthv", depth, crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); + auto depth = graph.createImageId( test::createImage( "depth", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); + auto depthv = graph.createViewId( test::createView( "depthv", depth, crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); auto & depthPrepass = graph.createPass( "depthPrepass" , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -2055,8 +2062,8 @@ TEST( RenderGraph, VarianceShadowMap ) } ); auto deptha = depthPrepass.addOutputDepthTarget ( depthv ); - auto colour = graph.createImage( test::createImage( "colour", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto colourv = graph.createView( test::createView( "colourv", colour, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto colour = graph.createImageId( test::createImage( "colour", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto colourv = graph.createViewId( test::createView( "colourv", colour, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); auto & backgroundPass = graph.createPass( "backgroundPass" , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -2101,11 +2108,9 @@ TEST( RenderGraph, VarianceShadowMap ) crg::ResourcesCache cache{ handler }; auto & context = getContext(); - VkDeviceMemory bufferMemory; - cache.createBuffer( context, buffer, bufferMemory ); + cache.createBuffer( context, buffer ); cache.createBufferView( context, bufferv ); - VkDeviceMemory imageMemory; - cache.createImage( context, depth, imageMemory ); + cache.createImage( context, depth ); cache.createImageView( context, depthv ); handler.createBuffer( context, buffer ); @@ -2121,13 +2126,13 @@ TEST( RenderGraph, EnvironmentMap ) testBegin( "testEnvironmentMap" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto depth = graph.createImage( test::createImage( "depth", crg::PixelFormat::eD32_SFLOAT_S8_UINT, 1u, 6u ) ); - auto cube = graph.createImage( test::createImageCube( "cube", crg::PixelFormat::eR16G16B16A16_SFLOAT, 8u, 1u ) ); - auto cubev = graph.createView( test::createView( "cubev", cube, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0, 8u, 0u, 6u ) ); - auto cubes = graph.createImage( test::createImageCube( "cubes", crg::PixelFormat::eR16G16B16A16_SFLOAT, 8u, 6u ) ); - auto cubesv = graph.createView( test::createView( "cubesv", cube, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0, 8u, 0u, 36u ) ); - auto colour = graph.createImage( test::createImage1D( "colour", crg::PixelFormat::eR16G16B16A16_SFLOAT, 8u, 6u ) ); - auto colourv = graph.createView( test::createView( "colourv", colour, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 8u, 0u, 6u ) ); + auto depth = graph.createImageId( test::createImage( "depth", crg::PixelFormat::eD32_SFLOAT_S8_UINT, 1u, 6u ) ); + auto cube = graph.createImageId( test::createImageCube( "cube", crg::PixelFormat::eR16G16B16A16_SFLOAT, 8u, 1u ) ); + auto cubev = graph.createViewId( test::createView( "cubev", cube, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0, 8u, 0u, 6u ) ); + auto cubes = graph.createImageId( test::createImageCube( "cubes", crg::PixelFormat::eR16G16B16A16_SFLOAT, 8u, 6u ) ); + auto cubesv = graph.createViewId( test::createView( "cubesv", cube, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0, 8u, 0u, 36u ) ); + auto colour = graph.createImageId( test::createImage1D( "colour", crg::PixelFormat::eR16G16B16A16_SFLOAT, 8u, 6u ) ); + auto colourv = graph.createViewId( test::createView( "colourv", colour, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 8u, 0u, 6u ) ); crg::AttachmentArray colourViews; crg::AttachmentArray cubeViews; crg::AttachmentArray cubesViews; @@ -2135,10 +2140,10 @@ TEST( RenderGraph, EnvironmentMap ) for ( auto index = 0u; index < 6u; ++index ) { auto strIndex = std::to_string( index ); - auto colourvn = graph.createView( test::createView( "colourv" + strIndex, colour, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, index, 1u ) ); - auto cubevn = graph.createView( test::createView( "cubev" + strIndex, cube, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, index, 1u ) ); - auto cubesvn = graph.createView( test::createView( "cubesv" + strIndex, cubes, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, index * 6u, 6u ) ); - auto depthvn = graph.createView( test::createView( "depthv" + strIndex, depth, crg::PixelFormat::eD32_SFLOAT_S8_UINT, 0u, 1u, index, 1u ) ); + auto colourvn = graph.createViewId( test::createView( "colourv" + strIndex, colour, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, index, 1u ) ); + auto cubevn = graph.createViewId( test::createView( "cubev" + strIndex, cube, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, index, 1u ) ); + auto cubesvn = graph.createViewId( test::createView( "cubesv" + strIndex, cubes, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, index * 6u, 6u ) ); + auto depthvn = graph.createViewId( test::createView( "depthv" + strIndex, depth, crg::PixelFormat::eD32_SFLOAT_S8_UINT, 0u, 1u, index, 1u ) ); auto & opaquePass = graph.createPass( "EnvOpaquePass" + strIndex , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -2207,24 +2212,25 @@ TEST( RenderGraph, DisabledPasses ) testBegin( "testDisabledPasses" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto depth = graph.createImage( test::createImage( "depth", crg::PixelFormat::eD32_SFLOAT_S8_UINT, 1u, 6u ) ); - auto cube = graph.createImage( test::createImageCube( "cube", crg::PixelFormat::eR16G16B16A16_SFLOAT, 8u, 1u ) ); - auto cubev = graph.createView( test::createView( "cubev", cube, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0, 8u, 0u, 6u ) ); - auto cubes = graph.createImage( test::createImageCube( "cubes", crg::PixelFormat::eR16G16B16A16_SFLOAT, 8u, 6u ) ); - auto cubesv = graph.createView( test::createView( "cubesv", cube, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0, 8u, 0u, 36u ) ); - auto colour = graph.createImage( test::createImage1D( "colour", crg::PixelFormat::eR16G16B16A16_SFLOAT, 8u, 6u ) ); - auto colourv = graph.createView( test::createView( "colourv", colour, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 8u, 0u, 6u ) ); + auto depth = graph.createImageId( test::createImage( "depth", crg::PixelFormat::eD32_SFLOAT_S8_UINT, 1u, 6u ) ); + auto cube = graph.createImageId( test::createImageCube( "cube", crg::PixelFormat::eR16G16B16A16_SFLOAT, 8u, 1u ) ); + auto cubev = graph.createViewId( test::createView( "cubev", cube, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0, 8u, 0u, 6u ) ); + auto cubes = graph.createImageId( test::createImageCube( "cubes", crg::PixelFormat::eR16G16B16A16_SFLOAT, 8u, 6u ) ); + auto cubesv = graph.createViewId( test::createView( "cubesv", cube, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0, 8u, 0u, 36u ) ); + auto colour = graph.createImageId( test::createImage1D( "colour", crg::PixelFormat::eR16G16B16A16_SFLOAT, 8u, 6u ) ); + auto colourv = graph.createViewId( test::createView( "colourv", colour, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 8u, 0u, 6u ) ); crg::AttachmentArray colourViews; crg::AttachmentArray cubeViews; crg::AttachmentArray cubesViews; + bool transparentEnabled{ true }; for ( auto index = 0u; index < 6u; ++index ) { auto strIndex = std::to_string( index ); - auto colourvn = graph.createView( test::createView( "colourv" + strIndex, colour, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, index, 1u ) ); - auto cubevn = graph.createView( test::createView( "cubev" + strIndex, cube, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, index, 1u ) ); - auto cubesvn = graph.createView( test::createView( "cubesv" + strIndex, cubes, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, index * 6u, 6u ) ); - auto depthvn = graph.createView( test::createView( "depthv" + strIndex, depth, crg::PixelFormat::eD32_SFLOAT_S8_UINT, 0u, 1u, index, 1u ) ); + auto colourvn = graph.createViewId( test::createView( "colourv" + strIndex, colour, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, index, 1u ) ); + auto cubevn = graph.createViewId( test::createView( "cubev" + strIndex, cube, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, index, 1u ) ); + auto cubesvn = graph.createViewId( test::createView( "cubesv" + strIndex, cubes, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, index * 6u, 6u ) ); + auto depthvn = graph.createViewId( test::createView( "depthv" + strIndex, depth, crg::PixelFormat::eD32_SFLOAT_S8_UINT, 0u, 1u, index, 1u ) ); auto & opaquePass = graph.createPass( "EnvOpaquePass" + strIndex , [&testCounts]( crg::FramePass const & framePass , crg::GraphContext & context @@ -2253,13 +2259,13 @@ TEST( RenderGraph, DisabledPasses ) cubesan = backgroundPass.addInOutColourTarget( *cubesan ); auto & transparentPass = graph.createPass( "EnvTransparentPass" + strIndex - , [&testCounts]( crg::FramePass const & framePass + , [&testCounts, &transparentEnabled]( crg::FramePass const & framePass , crg::GraphContext & context , crg::RunnableGraph & runGraph ) { return createDummy( testCounts , framePass, context, runGraph, crg::PipelineStageFlags::eFragmentShader - , test::checkDummy, 0u, false ); + , test::checkDummy, 0u, &transparentEnabled ); } ); transparentPass.addInputDepthTarget( *depthan ); colourViews.push_back( transparentPass.addInOutColourTarget( *colouran ) ); @@ -2284,6 +2290,8 @@ TEST( RenderGraph, DisabledPasses ) auto runnable = graph.compile( getContext() ); test::checkRunnable( testCounts, runnable ); + transparentEnabled = false; + test::checkRunnable( testCounts, runnable ); testEnd() } diff --git a/test/TestRenderPass.cpp b/test/TestRenderPass.cpp index 6a4b448..4f3b92c 100644 --- a/test/TestRenderPass.cpp +++ b/test/TestRenderPass.cpp @@ -65,8 +65,8 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; auto & pass = graph.createPass( "1C", crg::RunnablePassCreator{} ); - auto rt = graph.createImage( test::createImage( "rt", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto rtv = graph.createView( test::createView( "rtv", rt ) ); + auto rt = graph.createImageId( test::createImage( "rt", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto rtv = graph.createViewId( test::createView( "rtv", rt ) ); pass.addOutputColourTarget( rtv ); check( pass.getName() == "1C" ) @@ -81,12 +81,12 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; auto & pass = graph.createPass( "2C", crg::RunnablePassCreator{} ); - auto rt1 = graph.createImage( test::createImage( "rt1", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto rtv1 = graph.createView( test::createView( "rtv1", rt1 ) ); + auto rt1 = graph.createImageId( test::createImage( "rt1", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto rtv1 = graph.createViewId( test::createView( "rtv1", rt1 ) ); pass.addOutputColourTarget( rtv1 ); - auto rt2 = graph.createImage( test::createImage( "rt2", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto rtv2 = graph.createView( test::createView( "rtv2", rt2 ) ); + auto rt2 = graph.createImageId( test::createImage( "rt2", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto rtv2 = graph.createViewId( test::createView( "rtv2", rt2 ) ); pass.addOutputColourTarget( rtv2 ); check( pass.getName() == "2C" ) @@ -102,8 +102,8 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; auto & pass = graph.createPass( "0C_1I", crg::RunnablePassCreator{} ); - auto in = graph.createImage( test::createImage( "in", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto inv = graph.createView( test::createView( "inv", in ) ); + auto in = graph.createImageId( test::createImage( "in", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto inv = graph.createViewId( test::createView( "inv", in ) ); auto attach = crg::Attachment::createDefault( inv ); pass.addInputSampled( attach, 1u ); @@ -119,13 +119,13 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; auto & pass = graph.createPass( "0C_2I", crg::RunnablePassCreator{} ); - auto in1 = graph.createImage( test::createImage( "in1", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto inv1 = graph.createView( test::createView( "inv1", in1 ) ); + auto in1 = graph.createImageId( test::createImage( "in1", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto inv1 = graph.createViewId( test::createView( "inv1", in1 ) ); auto attach1 = crg::Attachment::createDefault( inv1 ); pass.addInputSampled( attach1, 1u ); - auto in2 = graph.createImage( test::createImage( "in2", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto inv2 = graph.createView( test::createView( "inv2", in2 ) ); + auto in2 = graph.createImageId( test::createImage( "in2", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto inv2 = graph.createViewId( test::createView( "inv2", in2 ) ); auto attach2 = crg::Attachment::createDefault( inv2 ); pass.addInputSampled( attach2, 2u ); @@ -142,12 +142,12 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; auto & pass = graph.createPass( "1C_1I", crg::RunnablePassCreator{} ); - auto rt = graph.createImage( test::createImage( "rt", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto rtv = graph.createView( test::createView( "rtv", rt ) ); + auto rt = graph.createImageId( test::createImage( "rt", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto rtv = graph.createViewId( test::createView( "rtv", rt ) ); pass.addOutputColourTarget( rtv ); - auto in = graph.createImage( test::createImage( "in", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto inv = graph.createView( test::createView( "inv", in ) ); + auto in = graph.createImageId( test::createImage( "in", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto inv = graph.createViewId( test::createView( "inv", in ) ); auto attach = crg::Attachment::createDefault( inv ); pass.addInputSampled( attach, 1u ); @@ -165,17 +165,17 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; auto & pass = graph.createPass( "1C_2I", crg::RunnablePassCreator{} ); - auto rt = graph.createImage( test::createImage( "rt", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto rtv = graph.createView( test::createView( "rtv", rt ) ); + auto rt = graph.createImageId( test::createImage( "rt", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto rtv = graph.createViewId( test::createView( "rtv", rt ) ); pass.addOutputColourTarget( rtv ); - auto in1 = graph.createImage( test::createImage( "in1", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto inv1 = graph.createView( test::createView( "inv1", in1 ) ); + auto in1 = graph.createImageId( test::createImage( "in1", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto inv1 = graph.createViewId( test::createView( "inv1", in1 ) ); auto attach1 = crg::Attachment::createDefault( inv1 ); pass.addInputSampled( attach1, 1u ); - auto in2 = graph.createImage( test::createImage( "in2", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto inv2 = graph.createView( test::createView( "inv2", in2 ) ); + auto in2 = graph.createImageId( test::createImage( "in2", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto inv2 = graph.createViewId( test::createView( "inv2", in2 ) ); auto attach2 = crg::Attachment::createDefault( inv2 ); pass.addInputSampled( attach2, 2u ); @@ -194,16 +194,16 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; auto & pass = graph.createPass( "2C_1I", crg::RunnablePassCreator{} ); - auto rt1 = graph.createImage( test::createImage( "rt1", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto rtv1 = graph.createView( test::createView( "rtv1", rt1 ) ); + auto rt1 = graph.createImageId( test::createImage( "rt1", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto rtv1 = graph.createViewId( test::createView( "rtv1", rt1 ) ); pass.addOutputColourTarget( rtv1 ); - auto rt2 = graph.createImage( test::createImage( "rt2", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto rtv2 = graph.createView( test::createView( "rtv2", rt2 ) ); + auto rt2 = graph.createImageId( test::createImage( "rt2", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto rtv2 = graph.createViewId( test::createView( "rtv2", rt2 ) ); pass.addOutputColourTarget( rtv2 ); - auto in = graph.createImage( test::createImage( "in", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto inv = graph.createView( test::createView( "inv", in ) ); + auto in = graph.createImageId( test::createImage( "in", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto inv = graph.createViewId( test::createView( "inv", in ) ); auto attach = crg::Attachment::createDefault( inv ); pass.addInputSampled( attach, 1u ); @@ -222,21 +222,21 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; auto & pass = graph.createPass( "2C_2I", crg::RunnablePassCreator{} ); - auto rt1 = graph.createImage( test::createImage( "rt1", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto rtv1 = graph.createView( test::createView( "rtv1", rt1 ) ); + auto rt1 = graph.createImageId( test::createImage( "rt1", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto rtv1 = graph.createViewId( test::createView( "rtv1", rt1 ) ); pass.addOutputColourTarget( rtv1 ); - auto rt2 = graph.createImage( test::createImage( "rt2", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto rtv2 = graph.createView( test::createView( "rtv2", rt2 ) ); + auto rt2 = graph.createImageId( test::createImage( "rt2", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto rtv2 = graph.createViewId( test::createView( "rtv2", rt2 ) ); pass.addOutputColourTarget( rtv2 ); - auto in1 = graph.createImage( test::createImage( "in1", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto inv1 = graph.createView( test::createView( "inv1", in1 ) ); + auto in1 = graph.createImageId( test::createImage( "in1", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto inv1 = graph.createViewId( test::createView( "inv1", in1 ) ); auto attach1 = crg::Attachment::createDefault( inv1 ); pass.addInputSampled( attach1, 1u ); - auto in2 = graph.createImage( test::createImage( "in2", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto inv2 = graph.createView( test::createView( "inv2", in2 ) ); + auto in2 = graph.createImageId( test::createImage( "in2", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto inv2 = graph.createViewId( test::createView( "inv2", in2 ) ); auto attach2 = crg::Attachment::createDefault( inv2 ); pass.addInputSampled( attach2, 2u ); @@ -256,8 +256,8 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; auto & pass = graph.createPass( "0C_DS", crg::RunnablePassCreator{} ); - auto ds = graph.createImage( test::createImage( "ds", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); - auto dsv = graph.createView( test::createView( "dsv", ds ) ); + auto ds = graph.createImageId( test::createImage( "ds", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); + auto dsv = graph.createViewId( test::createView( "dsv", ds ) ); pass.addOutputDepthStencilTarget( dsv ); check( pass.getName() == "0C_DS" ) @@ -272,12 +272,12 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; auto & pass = graph.createPass( "1C_DS", crg::RunnablePassCreator{} ); - auto rt = graph.createImage( test::createImage( "rt", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto rtv = graph.createView( test::createView( "rtv", rt ) ); + auto rt = graph.createImageId( test::createImage( "rt", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto rtv = graph.createViewId( test::createView( "rtv", rt ) ); pass.addOutputColourTarget( rtv ); - auto ds = graph.createImage( test::createImage( "ds", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); - auto dsv = graph.createView( test::createView( "dsv", ds ) ); + auto ds = graph.createImageId( test::createImage( "ds", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); + auto dsv = graph.createViewId( test::createView( "dsv", ds ) ); pass.addOutputDepthStencilTarget( dsv ); check( pass.getName() == "1C_DS" ) @@ -293,16 +293,16 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; auto & pass = graph.createPass( "2C_DS", crg::RunnablePassCreator{} ); - auto rt1 = graph.createImage( test::createImage( "rt1", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto rtv1 = graph.createView( test::createView( "rtv1", rt1 ) ); + auto rt1 = graph.createImageId( test::createImage( "rt1", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto rtv1 = graph.createViewId( test::createView( "rtv1", rt1 ) ); pass.addOutputColourTarget( rtv1 ); - auto rt2 = graph.createImage( test::createImage( "rt2", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto rtv2 = graph.createView( test::createView( "rtv2", rt2 ) ); + auto rt2 = graph.createImageId( test::createImage( "rt2", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto rtv2 = graph.createViewId( test::createView( "rtv2", rt2 ) ); pass.addOutputColourTarget( rtv2 ); - auto ds = graph.createImage( test::createImage( "ds", crg::PixelFormat::eD32_SFLOAT ) ); - auto dsv = graph.createView( test::createView( "dsv", ds ) ); + auto ds = graph.createImageId( test::createImage( "ds", crg::PixelFormat::eD32_SFLOAT ) ); + auto dsv = graph.createViewId( test::createView( "dsv", ds ) ); pass.addOutputDepthStencilTarget( dsv ); check( pass.getName() == "2C_DS" ) @@ -319,13 +319,13 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; auto & pass = graph.createPass( "0C_1I_DS", crg::RunnablePassCreator{} ); - auto in = graph.createImage( test::createImage( "in", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto inv = graph.createView( test::createView( "inv", in ) ); + auto in = graph.createImageId( test::createImage( "in", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto inv = graph.createViewId( test::createView( "inv", in ) ); auto attach = crg::Attachment::createDefault( inv ); pass.addInputSampled( attach, 1u ); - auto ds = graph.createImage( test::createImage( "ds", crg::PixelFormat::eD32_SFLOAT ) ); - auto dsv = graph.createView( test::createView( "dsv", ds ) ); + auto ds = graph.createImageId( test::createImage( "ds", crg::PixelFormat::eD32_SFLOAT ) ); + auto dsv = graph.createViewId( test::createView( "dsv", ds ) ); pass.addOutputDepthStencilTarget( dsv ); check( pass.getName() == "0C_1I_DS" ) @@ -342,18 +342,18 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; auto & pass = graph.createPass( "0C_2I_DS", crg::RunnablePassCreator{} ); - auto in1 = graph.createImage( test::createImage( "in1", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto inv1 = graph.createView( test::createView( "inv1", in1 ) ); + auto in1 = graph.createImageId( test::createImage( "in1", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto inv1 = graph.createViewId( test::createView( "inv1", in1 ) ); auto attach1 = crg::Attachment::createDefault( inv1 ); pass.addInputSampled( attach1, 1u ); - auto in2 = graph.createImage( test::createImage( "in2", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto inv2 = graph.createView( test::createView( "inv2", in2 ) ); + auto in2 = graph.createImageId( test::createImage( "in2", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto inv2 = graph.createViewId( test::createView( "inv2", in2 ) ); auto attach2 = crg::Attachment::createDefault( inv2 ); pass.addInputSampled( attach2, 2u ); - auto ds = graph.createImage( test::createImage( "ds", crg::PixelFormat::eD32_SFLOAT ) ); - auto dsv = graph.createView( test::createView( "dsv", ds ) ); + auto ds = graph.createImageId( test::createImage( "ds", crg::PixelFormat::eD32_SFLOAT ) ); + auto dsv = graph.createViewId( test::createView( "dsv", ds ) ); pass.addOutputDepthStencilTarget( dsv ); check( pass.getName() == "0C_2I_DS" ) @@ -371,17 +371,17 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; auto & pass = graph.createPass( "1C_1I_DS", crg::RunnablePassCreator{} ); - auto rt = graph.createImage( test::createImage( "rt", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto rtv = graph.createView( test::createView( "rtv", rt ) ); + auto rt = graph.createImageId( test::createImage( "rt", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto rtv = graph.createViewId( test::createView( "rtv", rt ) ); pass.addOutputColourTarget( rtv ); - auto in = graph.createImage( test::createImage( "in", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto inv = graph.createView( test::createView( "inv", in ) ); + auto in = graph.createImageId( test::createImage( "in", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto inv = graph.createViewId( test::createView( "inv", in ) ); auto attach = crg::Attachment::createDefault( inv ); pass.addInputSampled( attach, 1u ); - auto ds = graph.createImage( test::createImage( "ds", crg::PixelFormat::eD32_SFLOAT ) ); - auto dsv = graph.createView( test::createView( "dsv", ds ) ); + auto ds = graph.createImageId( test::createImage( "ds", crg::PixelFormat::eD32_SFLOAT ) ); + auto dsv = graph.createViewId( test::createView( "dsv", ds ) ); pass.addOutputDepthStencilTarget( dsv ); check( pass.getName() == "1C_1I_DS" ) @@ -399,22 +399,22 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; auto & pass = graph.createPass( "1C_2I_DS", crg::RunnablePassCreator{} ); - auto rt = graph.createImage( test::createImage( "rt", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto rtv = graph.createView( test::createView( "rtv", rt ) ); + auto rt = graph.createImageId( test::createImage( "rt", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto rtv = graph.createViewId( test::createView( "rtv", rt ) ); pass.addOutputColourTarget( rtv ); - auto in1 = graph.createImage( test::createImage( "in1", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto inv1 = graph.createView( test::createView( "inv1", in1 ) ); + auto in1 = graph.createImageId( test::createImage( "in1", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto inv1 = graph.createViewId( test::createView( "inv1", in1 ) ); auto attach1 = crg::Attachment::createDefault( inv1 ); pass.addInputSampled( attach1, 1u ); - auto in2 = graph.createImage( test::createImage( "in2", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto inv2 = graph.createView( test::createView( "inv2", in2 ) ); + auto in2 = graph.createImageId( test::createImage( "in2", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto inv2 = graph.createViewId( test::createView( "inv2", in2 ) ); auto attach2 = crg::Attachment::createDefault( inv2 ); pass.addInputSampled( attach2, 2u ); - auto ds = graph.createImage( test::createImage( "ds", crg::PixelFormat::eD32_SFLOAT ) ); - auto dsv = graph.createView( test::createView( "dsv", ds ) ); + auto ds = graph.createImageId( test::createImage( "ds", crg::PixelFormat::eD32_SFLOAT ) ); + auto dsv = graph.createViewId( test::createView( "dsv", ds ) ); pass.addOutputDepthStencilTarget( dsv ); check( pass.getName() == "1C_2I_DS" ) @@ -433,21 +433,21 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; auto & pass = graph.createPass( "2C_1I_DS", crg::RunnablePassCreator{} ); - auto rt1 = graph.createImage( test::createImage( "rt1", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto rtv1 = graph.createView( test::createView( "rtv1", rt1 ) ); + auto rt1 = graph.createImageId( test::createImage( "rt1", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto rtv1 = graph.createViewId( test::createView( "rtv1", rt1 ) ); pass.addOutputColourTarget( rtv1 ); - auto rt2 = graph.createImage( test::createImage( "rt2", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto rtv2 = graph.createView( test::createView( "rtv2", rt2 ) ); + auto rt2 = graph.createImageId( test::createImage( "rt2", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto rtv2 = graph.createViewId( test::createView( "rtv2", rt2 ) ); pass.addOutputColourTarget( rtv2 ); - auto in = graph.createImage( test::createImage( "in", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto inv = graph.createView( test::createView( "inv", in ) ); + auto in = graph.createImageId( test::createImage( "in", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto inv = graph.createViewId( test::createView( "inv", in ) ); auto attach = crg::Attachment::createDefault( inv ); pass.addInputSampled( attach, 1u ); - auto ds = graph.createImage( test::createImage( "ds", crg::PixelFormat::eD32_SFLOAT ) ); - auto dsv = graph.createView( test::createView( "dsv", ds ) ); + auto ds = graph.createImageId( test::createImage( "ds", crg::PixelFormat::eD32_SFLOAT ) ); + auto dsv = graph.createViewId( test::createView( "dsv", ds ) ); pass.addOutputDepthStencilTarget( dsv ); check( pass.getName() == "2C_1I_DS" ) @@ -466,26 +466,26 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; auto & pass = graph.createPass( "2C_2I_DS", crg::RunnablePassCreator{} ); - auto rt1 = graph.createImage( test::createImage( "rt1", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto rtv1 = graph.createView( test::createView( "rtv1", rt1 ) ); + auto rt1 = graph.createImageId( test::createImage( "rt1", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto rtv1 = graph.createViewId( test::createView( "rtv1", rt1 ) ); pass.addOutputColourTarget( rtv1 ); - auto rt2 = graph.createImage( test::createImage( "rt2", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto rtv2 = graph.createView( test::createView( "rtv2", rt2 ) ); + auto rt2 = graph.createImageId( test::createImage( "rt2", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto rtv2 = graph.createViewId( test::createView( "rtv2", rt2 ) ); pass.addOutputColourTarget( rtv2 ); - auto in1 = graph.createImage( test::createImage( "in1", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto inv1 = graph.createView( test::createView( "inv1", in1 ) ); + auto in1 = graph.createImageId( test::createImage( "in1", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto inv1 = graph.createViewId( test::createView( "inv1", in1 ) ); auto attach1 = crg::Attachment::createDefault( inv1 ); pass.addInputSampled( attach1, 1u ); - auto in2 = graph.createImage( test::createImage( "in2", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); - auto inv2 = graph.createView( test::createView( "inv2", in2 ) ); + auto in2 = graph.createImageId( test::createImage( "in2", crg::PixelFormat::eR32G32B32A32_SFLOAT ) ); + auto inv2 = graph.createViewId( test::createView( "inv2", in2 ) ); auto attach2 = crg::Attachment::createDefault( inv2 ); pass.addInputSampled( attach2, 2u ); - auto ds = graph.createImage( test::createImage( "ds", crg::PixelFormat::eD32_SFLOAT ) ); - auto dsv = graph.createView( test::createView( "dsv", ds ) ); + auto ds = graph.createImageId( test::createImage( "ds", crg::PixelFormat::eD32_SFLOAT ) ); + auto dsv = graph.createViewId( test::createView( "dsv", ds ) ); pass.addOutputDepthStencilTarget( dsv ); check( pass.getName() == "2C_2I_DS" ) diff --git a/test/TestRunnablePass.cpp b/test/TestRunnablePass.cpp index 611c207..e6b7d91 100644 --- a/test/TestRunnablePass.cpp +++ b/test/TestRunnablePass.cpp @@ -31,10 +31,10 @@ namespace { crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto buffer1 = graph.createBuffer( test::createBuffer( "buffer1" ) ); - auto buffer2 = graph.createBuffer( test::createBuffer( "buffer2" ) ); - auto buffer1v = graph.createView( test::createView( "buffer1v", buffer1 ) ); - auto buffer2v = graph.createView( test::createView( "buffer2v", buffer2 ) ); + auto buffer1 = graph.createBufferId( test::createBuffer( "buffer1" ) ); + auto buffer2 = graph.createBufferId( test::createBuffer( "buffer2" ) ); + auto buffer1v = graph.createViewId( test::createView( "buffer1v", buffer1 ) ); + auto buffer2v = graph.createViewId( test::createView( "buffer2v", buffer2 ) ); auto buffer1a = crg::Attachment::createDefault( buffer1v ); auto & testPass = graph.createPass( "Pass" , []( crg::FramePass const & pass @@ -53,16 +53,81 @@ namespace testEnd() } + TEST( RunnablePass, BufferCopy_InOutMismatch ) + { + testBegin( "BufferCopy_InOutMismatch" ) + { + crg::ResourceHandler handler; + crg::FrameGraph graph{ handler, testCounts.testName }; + auto buffer1 = graph.createBufferId( test::createBuffer( "buffer1" ) ); + auto buffer2 = graph.createBufferId( test::createBuffer( "buffer2" ) ); + auto buffer3 = graph.createBufferId( test::createBuffer( "buffer3" ) ); + auto buffer1v = graph.createViewId( test::createView( "buffer1v", buffer1 ) ); + auto buffer2v = graph.createViewId( test::createView( "buffer2v", buffer2 ) ); + auto buffer3v = graph.createViewId( test::createView( "buffer3v", buffer3 ) ); + auto buffer1a = crg::Attachment::createDefault( buffer1v ); + auto & testPass = graph.createPass( "Pass" + , []( crg::FramePass const & pass + , crg::GraphContext & context + , crg::RunnableGraph & runGraph ) + { + return std::make_unique< crg::BufferCopy >( pass, context, runGraph + , 0u, 1024u ); + } ); + testPass.addInputTransfer( buffer1a ); + testPass.addOutputTransferBuffer( buffer2v ); + testPass.addOutputTransferBuffer( buffer3v ); + + auto runnable = graph.compile( getContext() ); + test::checkRunnable( testCounts, runnable ); + } + testEnd() + } + + TEST( RunnablePass, BufferCopy_PagedBuffer ) + { + testBegin( "BufferCopy_PagedBuffer" ) + { + crg::ResourceHandler handler; + crg::FrameGraph graph{ handler, testCounts.testName }; + auto buffer1 = graph.createBufferId( test::createBuffer( "buffer1", 2u ) ); + auto buffer2 = graph.createBufferId( test::createBuffer( "buffer2", 2u ) ); + auto buf1 = handler.createBuffer( getContext(), buffer1 ).resource; + buf1->resize( buf1->getMaxSize() ); + buf1->update(); + auto buf2 = handler.createBuffer( getContext(), buffer2 ).resource; + buf2->resize( buf2->getMaxSize() ); + buf2->update(); + auto buffer1v = graph.createViewId( test::createView( "buffer1v", buffer1 ) ); + auto buffer2v = graph.createViewId( test::createView( "buffer2v", buffer2 ) ); + auto buffer1a = crg::Attachment::createDefault( buffer1v ); + auto & testPass = graph.createPass( "Pass" + , [&buffer1]( crg::FramePass const & pass + , crg::GraphContext & context + , crg::RunnableGraph & runGraph ) + { + return std::make_unique< crg::BufferCopy >( pass, context, runGraph + , 0u, getSize( buffer1 ) * 2u ); + } ); + testPass.addInputTransfer( buffer1a ); + testPass.addOutputTransferBuffer( buffer2v ); + + auto runnable = graph.compile( getContext() ); + test::checkRunnable( testCounts, runnable ); + } + testEnd() + } + TEST( RunnablePass, BufferCopy_IO_IO ) { testBegin( "testBufferCopy_IO_IO" ) { crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto buffer1 = graph.createBuffer( test::createBuffer( "buffer1" ) ); - auto buffer2 = graph.createBuffer( test::createBuffer( "buffer2" ) ); - auto buffer1v = graph.createView( test::createView( "buffer1v", buffer1 ) ); - auto buffer2v = graph.createView( test::createView( "buffer2v", buffer2 ) ); + auto buffer1 = graph.createBufferId( test::createBuffer( "buffer1" ) ); + auto buffer2 = graph.createBufferId( test::createBuffer( "buffer2" ) ); + auto buffer1v = graph.createViewId( test::createView( "buffer1v", buffer1 ) ); + auto buffer2v = graph.createViewId( test::createView( "buffer2v", buffer2 ) ); auto buffer1a = crg::Attachment::createDefault( buffer1v ); auto buffer2a = crg::Attachment::createDefault( buffer2v ); auto & testPass = graph.createPass( "Pass" @@ -87,10 +152,36 @@ namespace testBegin( "testBufferToImageCopy" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto result = graph.createImage( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto buffer = graph.createBuffer( test::createBuffer( "buffer" ) ); - auto resultv = graph.createView( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto bufferv = graph.createView( test::createView( "bufferv", buffer ) ); + auto result = graph.createImageId( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto buffer = graph.createBufferId( test::createBuffer( "buffer" ) ); + auto resultv = graph.createViewId( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto bufferv = graph.createViewId( test::createView( "bufferv", buffer ) ); + auto buffera = crg::Attachment::createDefault( bufferv ); + auto & testPass = graph.createPass( "Pass" + , []( crg::FramePass const & pass + , crg::GraphContext & context + , crg::RunnableGraph & runGraph ) + { + return std::make_unique< crg::BufferToImageCopy >( pass, context, runGraph + , crg::Offset3D{}, crg::Extent3D{ 1024, 1024, 1u } ); + } ); + testPass.addInputTransfer( buffera ); + testPass.addOutputTransferImage( resultv ); + + auto runnable = graph.compile( getContext() ); + test::checkRunnable( testCounts, runnable ); + testEnd() + } + + TEST( RunnablePass, BufferToImageCopy_PagedBuffer ) + { + testBegin( "BufferToImageCopy_PagedBuffer" ) + crg::ResourceHandler handler; + crg::FrameGraph graph{ handler, testCounts.testName }; + auto result = graph.createImageId( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto buffer = graph.createBufferId( test::createBuffer( "buffer", 2u ) ); + auto resultv = graph.createViewId( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto bufferv = graph.createViewId( test::createView( "bufferv", buffer ) ); auto buffera = crg::Attachment::createDefault( bufferv ); auto & testPass = graph.createPass( "Pass" , []( crg::FramePass const & pass @@ -108,13 +199,42 @@ namespace testEnd() } + TEST( RunnablePass, BufferToImageCopy_InOutMismatch ) + { + testBegin( "BufferToImageCopy_InOutMismatch" ) + crg::ResourceHandler handler; + crg::FrameGraph graph{ handler, testCounts.testName }; + auto result0 = graph.createImageId( test::createImage( "result0", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto result1 = graph.createImageId( test::createImage( "result1", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto buffer = graph.createBufferId( test::createBuffer( "buffer" ) ); + auto result0v = graph.createViewId( test::createView( "result0v", result0, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto result1v = graph.createViewId( test::createView( "result1v", result1, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto bufferv = graph.createViewId( test::createView( "bufferv", buffer ) ); + auto buffera = crg::Attachment::createDefault( bufferv ); + auto & testPass = graph.createPass( "Pass" + , []( crg::FramePass const & pass + , crg::GraphContext & context + , crg::RunnableGraph & runGraph ) + { + return std::make_unique< crg::BufferToImageCopy >( pass, context, runGraph + , crg::Offset3D{}, crg::Extent3D{ 1024, 1024, 1u } ); + } ); + testPass.addInputTransfer( buffera ); + testPass.addOutputTransferImage( result0v ); + testPass.addOutputTransferImage( result1v ); + + auto runnable = graph.compile( getContext() ); + test::checkRunnable( testCounts, runnable ); + testEnd() + } + TEST( RunnablePass, GenerateMipmaps ) { testBegin( "testGenerateMipmaps" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto result = graph.createImage( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT, 10u ) ); - auto resultv = graph.createView( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 10u, 0u, 1u ) ); + auto result = graph.createImageId( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT, 10u ) ); + auto resultv = graph.createViewId( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 10u, 0u, 1u ) ); auto resulta = crg::Attachment::createDefault( resultv ); auto & testPass = graph.createPass( "Pass" , []( crg::FramePass const & pass @@ -135,10 +255,10 @@ namespace testBegin( "testImageBlit" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto input = graph.createImage( test::createImage( "input", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto result = graph.createImage( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto inputv = graph.createView( test::createView( "inputv", input, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto resultv = graph.createView( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto input = graph.createImageId( test::createImage( "input", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto result = graph.createImageId( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto inputv = graph.createViewId( test::createView( "inputv", input, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto resultv = graph.createViewId( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); auto inputa = crg::Attachment::createDefault( inputv ); auto & testPass = graph.createPass( "Pass" , [inputv, resultv]( crg::FramePass const & pass @@ -163,10 +283,10 @@ namespace testBegin( "testImage3DBlit" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto input = graph.createImage( test::createImage3D( "input", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto result = graph.createImage( test::createImage3D( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto inputv = graph.createView( test::createView( "inputv", input, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto resultv = graph.createView( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto input = graph.createImageId( test::createImage3D( "input", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto result = graph.createImageId( test::createImage3D( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto inputv = graph.createViewId( test::createView( "inputv", input, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto resultv = graph.createViewId( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); auto inputa = crg::Attachment::createDefault( inputv ); auto & testPass = graph.createPass( "Pass" , [inputv, resultv]( crg::FramePass const & pass @@ -192,10 +312,10 @@ namespace { crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto input = graph.createImage( test::createImage( "input", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto result = graph.createImage( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto inputv = graph.createView( test::createView( "inputv", input, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto resultv = graph.createView( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto input = graph.createImageId( test::createImage( "input", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto result = graph.createImageId( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto inputv = graph.createViewId( test::createView( "inputv", input, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto resultv = graph.createViewId( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); auto inputa = crg::Attachment::createDefault( inputv ); auto & testPass = graph.createPass( "Pass" , [inputv]( crg::FramePass const & pass @@ -220,15 +340,15 @@ namespace { crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto input = graph.createImage( test::createImage( "input", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto result = graph.createImage( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT, 1u, 6u ) ); - auto inputv = graph.createView( test::createView( "inputv", input, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto resultv0 = graph.createView( test::createView( "result0v", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto resultv1 = graph.createView( test::createView( "result1v", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 1u, 1u ) ); - auto resultv2 = graph.createView( test::createView( "result2v", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 2u, 1u ) ); - auto resultv3 = graph.createView( test::createView( "result3v", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 3u, 1u ) ); - auto resultv4 = graph.createView( test::createView( "result4v", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 4u, 1u ) ); - auto resultv5 = graph.createView( test::createView( "result5v", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 5u, 1u ) ); + auto input = graph.createImageId( test::createImage( "input", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto result = graph.createImageId( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT, 1u, 6u ) ); + auto inputv = graph.createViewId( test::createView( "inputv", input, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto resultv0 = graph.createViewId( test::createView( "result0v", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto resultv1 = graph.createViewId( test::createView( "result1v", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 1u, 1u ) ); + auto resultv2 = graph.createViewId( test::createView( "result2v", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 2u, 1u ) ); + auto resultv3 = graph.createViewId( test::createView( "result3v", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 3u, 1u ) ); + auto resultv4 = graph.createViewId( test::createView( "result4v", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 4u, 1u ) ); + auto resultv5 = graph.createViewId( test::createView( "result5v", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 5u, 1u ) ); auto inputa = crg::Attachment::createDefault( inputv ); auto & testPass = graph.createPass( "Pass" , [inputv]( crg::FramePass const & pass @@ -258,16 +378,16 @@ namespace { crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto input = graph.createImage( test::createImage( "input", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto result0 = graph.createImage( test::createImage( "result0", crg::PixelFormat::eR16G16B16A16_SFLOAT, 1u, 3u ) ); - auto result1 = graph.createImage( test::createImage( "result1", crg::PixelFormat::eR16G16B16A16_SFLOAT, 1u, 3u ) ); - auto inputv = graph.createView( test::createView( "inputv", input, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto result0v0 = graph.createView( test::createView( "result0v", result0, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto result0v1 = graph.createView( test::createView( "result1v", result0, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 1u, 1u ) ); - auto result0v2 = graph.createView( test::createView( "result2v", result0, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 2u, 1u ) ); - auto result1v0 = graph.createView( test::createView( "result3v", result1, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto result1v1 = graph.createView( test::createView( "result4v", result1, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 1u, 1u ) ); - auto result1v2 = graph.createView( test::createView( "result5v", result1, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 2u, 1u ) ); + auto input = graph.createImageId( test::createImage( "input", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto result0 = graph.createImageId( test::createImage( "result0", crg::PixelFormat::eR16G16B16A16_SFLOAT, 1u, 3u ) ); + auto result1 = graph.createImageId( test::createImage( "result1", crg::PixelFormat::eR16G16B16A16_SFLOAT, 1u, 3u ) ); + auto inputv = graph.createViewId( test::createView( "inputv", input, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto result0v0 = graph.createViewId( test::createView( "result0v", result0, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto result0v1 = graph.createViewId( test::createView( "result1v", result0, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 1u, 1u ) ); + auto result0v2 = graph.createViewId( test::createView( "result2v", result0, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 2u, 1u ) ); + auto result1v0 = graph.createViewId( test::createView( "result3v", result1, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto result1v1 = graph.createViewId( test::createView( "result4v", result1, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 1u, 1u ) ); + auto result1v2 = graph.createViewId( test::createView( "result5v", result1, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 2u, 1u ) ); auto inputa = crg::Attachment::createDefault( inputv ); auto & testPass = graph.createPass( "Pass" , [inputv]( crg::FramePass const & pass @@ -297,15 +417,15 @@ namespace { crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto input = graph.createImage( test::createImage( "input", crg::PixelFormat::eR16G16B16A16_SFLOAT, 1u, 6u ) ); - auto result = graph.createImage( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto inputv0 = graph.createView( test::createView( "inputv0", input, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto inputv1 = graph.createView( test::createView( "inputv1", input, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 1u, 1u ) ); - auto inputv2 = graph.createView( test::createView( "inputv2", input, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 2u, 1u ) ); - auto inputv3 = graph.createView( test::createView( "inputv3", input, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 3u, 1u ) ); - auto inputv4 = graph.createView( test::createView( "inputv4", input, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 4u, 1u ) ); - auto inputv5 = graph.createView( test::createView( "inputv5", input, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 5u, 1u ) ); - auto resultv = graph.createView( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto input = graph.createImageId( test::createImage( "input", crg::PixelFormat::eR16G16B16A16_SFLOAT, 1u, 6u ) ); + auto result = graph.createImageId( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto inputv0 = graph.createViewId( test::createView( "inputv0", input, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto inputv1 = graph.createViewId( test::createView( "inputv1", input, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 1u, 1u ) ); + auto inputv2 = graph.createViewId( test::createView( "inputv2", input, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 2u, 1u ) ); + auto inputv3 = graph.createViewId( test::createView( "inputv3", input, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 3u, 1u ) ); + auto inputv4 = graph.createViewId( test::createView( "inputv4", input, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 4u, 1u ) ); + auto inputv5 = graph.createViewId( test::createView( "inputv5", input, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 5u, 1u ) ); + auto resultv = graph.createViewId( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); auto & testPass = graph.createPass( "Pass" , [inputv0]( crg::FramePass const & pass , crg::GraphContext & context @@ -334,16 +454,16 @@ namespace { crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto input0 = graph.createImage( test::createImage( "input0", crg::PixelFormat::eR16G16B16A16_SFLOAT, 1u, 3u ) ); - auto input1 = graph.createImage( test::createImage( "input1", crg::PixelFormat::eR16G16B16A16_SFLOAT, 1u, 3u ) ); - auto result = graph.createImage( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto input0v0 = graph.createView( test::createView( "input0v0", input0, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto input0v1 = graph.createView( test::createView( "input0v1", input0, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 1u, 1u ) ); - auto input0v2 = graph.createView( test::createView( "input0v2", input0, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 2u, 1u ) ); - auto input1v0 = graph.createView( test::createView( "input1v0", input1, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto input1v1 = graph.createView( test::createView( "input1v1", input1, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 1u, 1u ) ); - auto input1v2 = graph.createView( test::createView( "input1v2", input1, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 2u, 1u ) ); - auto resultv = graph.createView( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto input0 = graph.createImageId( test::createImage( "input0", crg::PixelFormat::eR16G16B16A16_SFLOAT, 1u, 3u ) ); + auto input1 = graph.createImageId( test::createImage( "input1", crg::PixelFormat::eR16G16B16A16_SFLOAT, 1u, 3u ) ); + auto result = graph.createImageId( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto input0v0 = graph.createViewId( test::createView( "input0v0", input0, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto input0v1 = graph.createViewId( test::createView( "input0v1", input0, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 1u, 1u ) ); + auto input0v2 = graph.createViewId( test::createView( "input0v2", input0, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 2u, 1u ) ); + auto input1v0 = graph.createViewId( test::createView( "input1v0", input1, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto input1v1 = graph.createViewId( test::createView( "input1v1", input1, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 1u, 1u ) ); + auto input1v2 = graph.createViewId( test::createView( "input1v2", input1, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 2u, 1u ) ); + auto resultv = graph.createViewId( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); auto & testPass = graph.createPass( "Pass" , [result]( crg::FramePass const & pass , crg::GraphContext & context @@ -372,10 +492,10 @@ namespace { crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto input = graph.createImage( test::createImage( "input", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto result = graph.createImage( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto inputv = graph.createView( test::createView( "inputv", input, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto resultv = graph.createView( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto input = graph.createImageId( test::createImage( "input", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto result = graph.createImageId( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto inputv = graph.createViewId( test::createView( "inputv", input, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto resultv = graph.createViewId( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); auto inputa = crg::Attachment::createDefault( inputv ); auto & testPass = graph.createPass( "Pass" , [inputv]( crg::FramePass const & pass @@ -401,10 +521,10 @@ namespace { crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto input = graph.createImage( test::createImage( "input", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto result = graph.createImage( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto inputv = graph.createView( test::createView( "inputv", input, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto resultv = graph.createView( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto input = graph.createImageId( test::createImage( "input", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto result = graph.createImageId( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto inputv = graph.createViewId( test::createView( "inputv", input, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto resultv = graph.createViewId( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); auto inputa = crg::Attachment::createDefault( inputv ); auto resulta = crg::Attachment::createDefault( resultv ); auto & testPass = graph.createPass( "Pass" @@ -432,10 +552,66 @@ namespace testBegin( "testImageToBufferCopy" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto input = graph.createImage( test::createImage( "input", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto buffer = graph.createBuffer( test::createBuffer( "buffer" ) ); - auto inputv = graph.createView( test::createView( "inputv", input, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto bufferv = graph.createView( test::createView( "bufferv", buffer ) ); + auto input = graph.createImageId( test::createImage( "input", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto buffer = graph.createBufferId( test::createBuffer( "buffer" ) ); + auto inputv = graph.createViewId( test::createView( "inputv", input, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto bufferv = graph.createViewId( test::createView( "bufferv", buffer ) ); + auto inputa = crg::Attachment::createDefault( inputv ); + auto & testPass = graph.createPass( "Pass" + , [inputv]( crg::FramePass const & pass + , crg::GraphContext & context + , crg::RunnableGraph & runGraph ) + { + return std::make_unique< crg::ImageToBufferCopy >( pass, context, runGraph + , crg::Offset3D{}, getExtent( inputv ) ); + } ); + testPass.addInputTransfer( inputa ); + testPass.addOutputTransferBuffer( bufferv ); + + auto runnable = graph.compile( getContext() ); + test::checkRunnable( testCounts, runnable ); + testEnd() + } + + TEST( RunnablePass, ImageToBufferCopy_InOutMismatch ) + { + testBegin( "ImageToBufferCopy_InOutMismatch" ) + crg::ResourceHandler handler; + crg::FrameGraph graph{ handler, testCounts.testName }; + auto input0 = graph.createImageId( test::createImage( "input0", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto input1 = graph.createImageId( test::createImage( "input1", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto buffer = graph.createBufferId( test::createBuffer( "buffer" ) ); + auto input0v = graph.createViewId( test::createView( "input0v", input0, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto input1v = graph.createViewId( test::createView( "input1v", input1, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto bufferv = graph.createViewId( test::createView( "bufferv", buffer ) ); + auto input0a = crg::Attachment::createDefault( input0v ); + auto input1a = crg::Attachment::createDefault( input1v ); + auto & testPass = graph.createPass( "Pass" + , [input0v]( crg::FramePass const & pass + , crg::GraphContext & context + , crg::RunnableGraph & runGraph ) + { + return std::make_unique< crg::ImageToBufferCopy >( pass, context, runGraph + , crg::Offset3D{}, getExtent( input0v ) ); + } ); + testPass.addInputTransfer( input0a ); + testPass.addInputTransfer( input1a ); + testPass.addOutputTransferBuffer( bufferv ); + + auto runnable = graph.compile( getContext() ); + test::checkRunnable( testCounts, runnable ); + testEnd() + } + + TEST( RunnablePass, ImageToBufferCopy_PagedBuffer ) + { + testBegin( "ImageToBufferCopy_PagedBuffer" ) + crg::ResourceHandler handler; + crg::FrameGraph graph{ handler, testCounts.testName }; + auto input = graph.createImageId( test::createImage( "input", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto buffer = graph.createBufferId( test::createBuffer( "buffer", 2u ) ); + auto inputv = graph.createViewId( test::createView( "inputv", input, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto bufferv = graph.createViewId( test::createView( "bufferv", buffer ) ); auto inputa = crg::Attachment::createDefault( inputv ); auto & testPass = graph.createPass( "Pass" , [inputv]( crg::FramePass const & pass @@ -458,10 +634,10 @@ namespace testBegin( "testComputePass" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, "/" + testCounts.testName }; - auto buffer = graph.createBuffer( test::createBuffer( "buffer" ) ); - auto bufferv = graph.createView( test::createView( "bufferv", buffer ) ); - auto indirect = graph.createBuffer( test::createBuffer( "indirect" ) ); - auto indirectv = graph.createView( test::createView( "indirectv", indirect ) ); + auto buffer = graph.createBufferId( test::createBuffer( "buffer" ) ); + auto bufferv = graph.createViewId( test::createView( "bufferv", buffer ) ); + auto indirect = graph.createBufferId( test::createBuffer( "indirect", 2u ) ); + auto indirectv = graph.createViewId( test::createView( "indirectv", indirect ) ); auto & testPass1 = graph.createPass( "Pass1" , [&indirectv]( crg::FramePass const & pass , crg::GraphContext & context @@ -477,14 +653,14 @@ namespace } ); auto buffera = testPass1.addClearableOutputStorageBuffer( bufferv, 1u ); - auto result = graph.createImage( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto depth = graph.createImage( test::createImage( "depth", crg::PixelFormat::eD32_SFLOAT ) ); - auto depthStencil = graph.createImage( test::createImage( "depthStencil", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); - auto buffer1 = graph.createBuffer( test::createBuffer( "buffer1" ) ); - auto resultv = graph.createView( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto depthv = graph.createView( test::createView( "depthv", depth, crg::PixelFormat::eD32_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto depthStencilv = graph.createView( test::createView( "depthStencilv", depthStencil, crg::PixelFormat::eD32_SFLOAT_S8_UINT, 0u, 1u, 0u, 1u ) ); - auto buffer1v = graph.createView( test::createView( "buffer1v", buffer1 ) ); + auto result = graph.createImageId( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto depth = graph.createImageId( test::createImage( "depth", crg::PixelFormat::eD32_SFLOAT ) ); + auto depthStencil = graph.createImageId( test::createImage( "depthStencil", crg::PixelFormat::eD32_SFLOAT_S8_UINT ) ); + auto buffer1 = graph.createBufferId( test::createBuffer( "buffer1" ) ); + auto resultv = graph.createViewId( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto depthv = graph.createViewId( test::createView( "depthv", depth, crg::PixelFormat::eD32_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto depthStencilv = graph.createViewId( test::createView( "depthStencilv", depthStencil, crg::PixelFormat::eD32_SFLOAT_S8_UINT, 0u, 1u, 0u, 1u ) ); + auto buffer1v = graph.createViewId( test::createView( "buffer1v", buffer1 ) ); crg::ComputePass * computePass{}; auto & testPass2 = graph.createPass( "Pass2" , [&computePass]( crg::FramePass const & pass @@ -505,18 +681,18 @@ namespace auto resulta = testPass2.addClearableOutputStorageImage( resultv, 2u ); auto deptha = testPass2.addClearableOutputStorageImage( depthv, 3u ); - auto buffer2 = graph.createBuffer( test::createBuffer( "buffer2" ) ); - auto buffer3 = graph.createBuffer( test::createBuffer( "buffer3" ) ); - auto buffer4 = graph.createBuffer( test::createBuffer( "buffer4" ) ); - auto buffer5 = graph.createBuffer( test::createBuffer( "buffer5" ) ); - auto buffer6 = graph.createBuffer( test::createBuffer( "buffer6" ) ); - auto buffer7 = graph.createBuffer( test::createBuffer( "buffer7" ) ); - auto buffer2v = graph.createView( test::createView( "buffer2v", buffer2 ) ); - auto buffer3v = graph.createView( test::createView( "buffer3v", buffer3 ) ); - auto buffer4v = graph.createView( test::createView( "buffer4v", buffer4, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto buffer5v = graph.createView( test::createView( "buffer5v", buffer5, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto buffer6v = graph.createView( test::createView( "buffer6v", buffer6, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto buffer7v = graph.createView( test::createView( "buffer7v", buffer7, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto buffer2 = graph.createBufferId( test::createBuffer( "buffer2", 2u ) ); + auto buffer3 = graph.createBufferId( test::createBuffer( "buffer3" ) ); + auto buffer4 = graph.createBufferId( test::createBuffer( "buffer4" ) ); + auto buffer5 = graph.createBufferId( test::createBuffer( "buffer5" ) ); + auto buffer6 = graph.createBufferId( test::createBuffer( "buffer6" ) ); + auto buffer7 = graph.createBufferId( test::createBuffer( "buffer7" ) ); + auto buffer2v = graph.createViewId( test::createView( "buffer2v", buffer2 ) ); + auto buffer3v = graph.createViewId( test::createView( "buffer3v", buffer3 ) ); + auto buffer4v = graph.createViewId( test::createView( "buffer4v", buffer4, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto buffer5v = graph.createViewId( test::createView( "buffer5v", buffer5, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto buffer6v = graph.createViewId( test::createView( "buffer6v", buffer6, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto buffer7v = graph.createViewId( test::createView( "buffer7v", buffer7, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); auto buffer2a = crg::Attachment::createDefault( buffer2v ); auto buffer3a = crg::Attachment::createDefault( buffer3v ); auto buffer5a = crg::Attachment::createDefault( buffer5v ); @@ -562,14 +738,14 @@ namespace testBegin( "testComputePassTransitions" ) crg::ResourceHandler handler; crg::FrameGraph graph{ handler, "/" + testCounts.testName }; - auto result = graph.createImage( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto depth = graph.createImage( test::createImage( "depth", crg::PixelFormat::eD32_SFLOAT ) ); - auto buffer1 = graph.createBuffer( test::createBuffer( "buffer1" ) ); - auto buffer2 = graph.createBuffer( test::createBuffer( "buffer2" ) ); - auto resultv = graph.createView( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto depthv = graph.createView( test::createView( "depthv", depth, crg::PixelFormat::eD32_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto buffer1v = graph.createView( test::createView( "buffer1v", buffer1 ) ); - auto buffer2v = graph.createView( test::createView( "buffer2v", buffer2 ) ); + auto result = graph.createImageId( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto depth = graph.createImageId( test::createImage( "depth", crg::PixelFormat::eD32_SFLOAT ) ); + auto buffer1 = graph.createBufferId( test::createBuffer( "buffer1" ) ); + auto buffer2 = graph.createBufferId( test::createBuffer( "buffer2" ) ); + auto resultv = graph.createViewId( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto depthv = graph.createViewId( test::createView( "depthv", depth, crg::PixelFormat::eD32_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto buffer1v = graph.createViewId( test::createView( "buffer1v", buffer1 ) ); + auto buffer2v = graph.createViewId( test::createView( "buffer2v", buffer2 ) ); auto & testPass1 = graph.createPass( "Pass1" , []( crg::FramePass const & pass , crg::GraphContext & context @@ -615,18 +791,17 @@ namespace { crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto result = graph.createImage( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto resultv = graph.createView( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto sampled = graph.createImage( test::createImage( "sampled", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto sampledv = graph.createView( test::createView( "sampledv", sampled, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto result = graph.createImageId( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto resultv = graph.createViewId( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto sampled = graph.createImageId( test::createImage( "sampled", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto sampledv = graph.createViewId( test::createView( "sampledv", sampled, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); auto & testPass = graph.createPass( "Pass" , []( crg::FramePass const & pass , crg::GraphContext & context , crg::RunnableGraph & runGraph ) { return std::make_unique< crg::RenderPass >( pass, context, runGraph - , crg::RenderPass::Callbacks{ crg::defaultV< crg::RunnablePass::InitialiseCallback > - , crg::defaultV< crg::RunnablePass::RecordCallback > } ); + , crg::RenderPass::Callbacks{} ); } ); testPass.addInputSampledImage( sampledv, 0u ); testPass.addOutputColourTarget( resultv ); @@ -643,17 +818,15 @@ namespace { crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto result = graph.createImage( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto resultv = graph.createView( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto result = graph.createImageId( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto resultv = graph.createViewId( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); auto & testPass = graph.createPass( "Pass" , []( crg::FramePass const & pass , crg::GraphContext & context , crg::RunnableGraph & runGraph ) { return std::make_unique< crg::RenderPass >( pass, context, runGraph - , crg::RenderPass::Callbacks{ crg::defaultV< crg::RunnablePass::InitialiseCallback > - , crg::defaultV< crg::RunnablePass::RecordCallback > - , crg::defaultV< crg::RenderPass::GetSubpassContentsCallback > } ); + , crg::RenderPass::Callbacks{} ); } ); testPass.addOutputColourTarget( resultv ); @@ -670,9 +843,9 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; auto & group = graph.createPassGroup( "testGroup" ); - auto result = group.createImage( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT, 1u, 2u ) ); - auto result1v = group.createView( test::createView( "result1v", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto result2v = group.createView( test::createView( "result2v", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 1u, 1u ) ); + auto result = group.createImageId( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT, 1u, 2u ) ); + auto result1v = group.createViewId( test::createView( "result1v", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto result2v = group.createViewId( test::createView( "result2v", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 1u, 1u ) ); auto resultv = group.mergeViews( { result1v, result2v } ); auto & testPass = group.createPass( "Pass" , []( crg::FramePass const & pass @@ -680,9 +853,7 @@ namespace , crg::RunnableGraph & runGraph ) { return std::make_unique< crg::RenderPass >( pass, context, runGraph - , crg::RenderPass::Callbacks{ crg::defaultV< crg::RunnablePass::InitialiseCallback > - , crg::defaultV< crg::RunnablePass::RecordCallback > - , crg::defaultV< crg::RenderPass::GetSubpassContentsCallback > } ); + , crg::RenderPass::Callbacks{} ); } ); testPass.addOutputColourTarget( resultv ); @@ -700,14 +871,14 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; auto & group = graph.createPassGroup( "testGroup" ); - auto result = group.createImage( test::createImageCube( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT, 1u, 12u ) ); - auto result1v = group.createView( crg::ImageViewData{ "result1v" + auto result = group.createImageId( test::createImageCube( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT, 1u, 12u ) ); + auto result1v = group.createViewId( crg::ImageViewData{ "result1v" , result , crg::ImageViewCreateFlags::eNone , crg::ImageViewType::e2D , getFormat( result ) , { getAspectMask( getFormat( result ) ), 0u, 1u, 0u, 6u } } ); - auto result2v = group.createView( crg::ImageViewData{ "result2v" + auto result2v = group.createViewId( crg::ImageViewData{ "result2v" , result , crg::ImageViewCreateFlags::eNone , crg::ImageViewType::e2D @@ -720,9 +891,7 @@ namespace , crg::RunnableGraph & runGraph ) { return std::make_unique< crg::RenderPass >( pass, context, runGraph - , crg::RenderPass::Callbacks{ crg::defaultV< crg::RunnablePass::InitialiseCallback > - , crg::defaultV< crg::RunnablePass::RecordCallback > - , crg::defaultV< crg::RenderPass::GetSubpassContentsCallback > } ); + , crg::RenderPass::Callbacks{} ); } ); testPass.addOutputColourTarget( resultv ); @@ -740,11 +909,11 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; auto & group = graph.createPassGroup( "testGroup" ); - auto result = group.createImage( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto buffer = group.createBuffer( test::createBuffer( "buffer" ) ); - auto resultv = group.createView( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto buffer1v = group.createView( test::createView( "buffer1v", buffer, 0, 512u ) ); - auto buffer2v = group.createView( test::createView( "buffer2v", buffer, 512u, 512u ) ); + auto result = group.createImageId( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto buffer = group.createBufferId( test::createBuffer( "buffer" ) ); + auto resultv = group.createViewId( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto buffer1v = group.createViewId( test::createView( "buffer1v", buffer, 0, 512u ) ); + auto buffer2v = group.createViewId( test::createView( "buffer2v", buffer, 512u, 512u ) ); auto bufferv = group.mergeViews( { buffer1v, buffer2v } ); auto & testPass = group.createPass( "Pass" , []( crg::FramePass const & pass @@ -752,9 +921,7 @@ namespace , crg::RunnableGraph & runGraph ) { return std::make_unique< crg::RenderPass >( pass, context, runGraph - , crg::RenderPass::Callbacks{ crg::defaultV< crg::RunnablePass::InitialiseCallback > - , crg::defaultV< crg::RunnablePass::RecordCallback > - , crg::defaultV< crg::RenderPass::GetSubpassContentsCallback > } ); + , crg::RenderPass::Callbacks{} ); } ); testPass.addOutputStorageBuffer( bufferv, 0u ); testPass.addOutputColourTarget( resultv ); @@ -772,33 +939,29 @@ namespace { crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto intermediate = graph.createImage( test::createImage( "intermediate", crg::PixelFormat::eR16G16B16A16_SFLOAT, 1u, 2u ) ); - auto intermediate1v = graph.createView( test::createView( "intermediate1v", intermediate, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto intermediate2v = graph.createView( test::createView( "intermediate2v", intermediate, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 1u, 1u ) ); + auto intermediate = graph.createImageId( test::createImage( "intermediate", crg::PixelFormat::eR16G16B16A16_SFLOAT, 1u, 2u ) ); + auto intermediate1v = graph.createViewId( test::createView( "intermediate1v", intermediate, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto intermediate2v = graph.createViewId( test::createView( "intermediate2v", intermediate, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 1u, 1u ) ); auto & testPass1 = graph.createPass( "Pass1" , []( crg::FramePass const & pass , crg::GraphContext & context , crg::RunnableGraph & runGraph ) { return std::make_unique< crg::RenderPass >( pass, context, runGraph - , crg::RenderPass::Callbacks{ crg::defaultV< crg::RunnablePass::InitialiseCallback > - , crg::defaultV< crg::RunnablePass::RecordCallback > - , crg::defaultV< crg::RenderPass::GetSubpassContentsCallback > } ); + , crg::RenderPass::Callbacks{} ); } ); auto intermediate1a = testPass1.addOutputColourTarget( intermediate1v ); auto intermediate2a = testPass1.addOutputColourTarget( intermediate2v ); - auto result = graph.createImage( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto resultv = graph.createView( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto result = graph.createImageId( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto resultv = graph.createViewId( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); auto & testPass2 = graph.createPass( "Pass2" , []( crg::FramePass const & pass , crg::GraphContext & context , crg::RunnableGraph & runGraph ) { return std::make_unique< crg::RenderPass >( pass, context, runGraph - , crg::RenderPass::Callbacks{ crg::defaultV< crg::RunnablePass::InitialiseCallback > - , crg::defaultV< crg::RunnablePass::RecordCallback > - , crg::defaultV< crg::RenderPass::GetSubpassContentsCallback > } ); + , crg::RenderPass::Callbacks{} ); } ); auto intermediatea = graph.mergeAttachments( { intermediate1a, intermediate2a } ); testPass2.addInputSampled( *intermediatea, 0u ); @@ -817,9 +980,9 @@ namespace { crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto buffer = graph.createBuffer( test::createBuffer( "buffer" ) ); - auto buffer1v = graph.createView( test::createView( "buffer1v", buffer, 0u, 512u ) ); - auto buffer2v = graph.createView( test::createView( "buffer2v", buffer, 512u, 512u ) ); + auto buffer = graph.createBufferId( test::createBuffer( "buffer" ) ); + auto buffer1v = graph.createViewId( test::createView( "buffer1v", buffer, 0u, 512u ) ); + auto buffer2v = graph.createViewId( test::createView( "buffer2v", buffer, 512u, 512u ) ); auto & testPass1 = graph.createPass( "Pass1" , []( crg::FramePass const & pass , crg::GraphContext & context @@ -835,17 +998,15 @@ namespace auto buffer1a = testPass1.addOutputStorageBuffer( buffer1v, 0u ); auto buffer2a = testPass1.addOutputStorageBuffer( buffer2v, 1u ); - auto result = graph.createImage( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto resultv = graph.createView( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto result = graph.createImageId( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto resultv = graph.createViewId( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); auto & testPass2 = graph.createPass( "Pass2" , []( crg::FramePass const & pass , crg::GraphContext & context , crg::RunnableGraph & runGraph ) { return std::make_unique< crg::RenderPass >( pass, context, runGraph - , crg::RenderPass::Callbacks{ crg::defaultV< crg::RunnablePass::InitialiseCallback > - , crg::defaultV< crg::RunnablePass::RecordCallback > - , crg::defaultV< crg::RenderPass::GetSubpassContentsCallback > } ); + , crg::RenderPass::Callbacks{} ); } ); auto buffera = graph.mergeAttachments( { buffer1a, buffer2a } ); testPass2.addInputStorage( *buffera, 0u ); @@ -864,16 +1025,15 @@ namespace { crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto depth = graph.createImage( test::createImage( "depth", crg::PixelFormat::eD32_SFLOAT ) ); - auto depthv = graph.createView( test::createView( "depthv", depth, crg::PixelFormat::eD32_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto depth = graph.createImageId( test::createImage( "depth", crg::PixelFormat::eD32_SFLOAT ) ); + auto depthv = graph.createViewId( test::createView( "depthv", depth, crg::PixelFormat::eD32_SFLOAT, 0u, 1u, 0u, 1u ) ); auto & testPass = graph.createPass( "Pass" , []( crg::FramePass const & pass , crg::GraphContext & context , crg::RunnableGraph & runGraph ) { return std::make_unique< crg::RenderPass >( pass, context, runGraph - , crg::RenderPass::Callbacks{ crg::defaultV< crg::RunnablePass::InitialiseCallback > - , crg::defaultV< crg::RunnablePass::RecordCallback > } ); + , crg::RenderPass::Callbacks{} ); } ); testPass.addOutputDepthTarget ( depthv ); @@ -890,10 +1050,10 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; uint32_t passIndex{}; - auto result = graph.createImage( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto resultv = graph.createView( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto depth = graph.createImage( test::createImage( "depth", crg::PixelFormat::eD32_SFLOAT ) ); - auto depthv = graph.createView( test::createView( "depthv", depth, crg::PixelFormat::eD32_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto result = graph.createImageId( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto resultv = graph.createViewId( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto depth = graph.createImageId( test::createImage( "depth", crg::PixelFormat::eD32_SFLOAT ) ); + auto depthv = graph.createViewId( test::createView( "depthv", depth, crg::PixelFormat::eD32_SFLOAT, 0u, 1u, 0u, 1u ) ); crg::Extent2D extent{ getExtent( resultv ).width, getExtent( resultv ).height }; auto & testPass = graph.createPass( "Pass" , [&passIndex, extent]( crg::FramePass const & pass @@ -901,10 +1061,8 @@ namespace , crg::RunnableGraph & runGraph ) { return std::make_unique< crg::RenderPass >( pass, context, runGraph - , crg::RenderPass::Callbacks{ crg::defaultV< crg::RunnablePass::InitialiseCallback > - , crg::defaultV< crg::RunnablePass::RecordCallback > - , crg::defaultV< crg::RenderPass::GetSubpassContentsCallback > - , crg::RenderPass::GetPassIndexCallback( [passIndex](){ return passIndex; } ) } + , crg::RenderPass::Callbacks{} + .onGetPassIndex( crg::GetPassIndexCallback( [passIndex](){ return passIndex; } ) ) , extent , crg::ru::Config{ 2u } ); } ); @@ -926,17 +1084,16 @@ namespace { crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto result1 = graph.createImage( test::createImage( "result1", crg::PixelFormat::eR16G16B16A16_SFLOAT, 1u, 2u ) ); - auto result1v = graph.createView( test::createView( "result1v", result1, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); - auto result2v = graph.createView( test::createView( "result2v", result1, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto result1 = graph.createImageId( test::createImage( "result1", crg::PixelFormat::eR16G16B16A16_SFLOAT, 1u, 2u ) ); + auto result1v = graph.createViewId( test::createView( "result1v", result1, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto result2v = graph.createViewId( test::createView( "result2v", result1, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); auto & testPass = graph.createPass( "Pass" , []( crg::FramePass const & pass , crg::GraphContext & context , crg::RunnableGraph & runGraph ) { return std::make_unique< crg::RenderPass >( pass, context, runGraph - , crg::RenderPass::Callbacks{ crg::defaultV< crg::RunnablePass::InitialiseCallback > - , crg::defaultV< crg::RunnablePass::RecordCallback > } ); + , crg::RenderPass::Callbacks{} ); } ); testPass.addOutputColourTarget( graph.mergeViews( { result1v, result2v } ) ); testPass.addOutputColourTarget( graph.mergeViews( { result1v, result2v }, false, true ) ); @@ -996,8 +1153,46 @@ namespace { crg::FrameGraph graph{ handler, testCounts.testName }; crg::RenderQuad * renderQuad{}; - auto indirect = graph.createBuffer( test::createBuffer( "indirect" ) ); - auto indirectv = graph.createView( test::createView( "indirectv", indirect ) ); + auto indirect = graph.createBufferId( test::createBuffer( "indirect" ) ); + auto indirectv = graph.createViewId( test::createView( "indirectv", indirect ) ); + auto & testPass = graph.createPass( "Pass" + , [&renderQuad, &indirectv]( crg::FramePass const & pass + , crg::GraphContext & context + , crg::RunnableGraph & runGraph ) + { + crg::rq::Config cfg; + cfg.indirectBuffer( crg::IndirectBuffer{ indirectv, sizeof( VkDrawIndirectCommand ) } ); + cfg.baseConfig( crg::pp::Config{} + .programCreator( crg::ProgramCreator{ 1u + , []( uint32_t ){ return crg::VkPipelineShaderStageCreateInfoArray{ VkPipelineShaderStageCreateInfo{} }; } } ) ); + auto res = std::make_unique< crg::RenderQuad >( pass, context, runGraph + , crg::ru::Config{ 2u, true }, std::move( cfg ) ); + renderQuad = res.get(); + return res; + } ); + testPass.addOutputColourTarget( resultv ); + + auto runnable = graph.compile( getContext() ); + test::checkRunnable( testCounts, runnable ); + require( renderQuad ) + checkNoThrow( renderQuad->resetPipeline( crg::VkPipelineShaderStageCreateInfoArray{ VkPipelineShaderStageCreateInfo{} }, 0u ) ) + checkNoThrow( runnable->record() ) + checkNoThrow( runnable->run( VkQueue{} ) ) + } + testEnd() + } + + TEST( RunnablePass, RenderQuad_PagedIndirect ) + { + testBegin( "RenderQuad_PagedIndirect" ) + crg::ResourceHandler handler; + auto result = handler.createImageId( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto resultv = handler.createViewId( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + { + crg::FrameGraph graph{ handler, testCounts.testName }; + crg::RenderQuad * renderQuad{}; + auto indirect = graph.createBufferId( test::createBuffer( "indirect", 2u ) ); + auto indirectv = graph.createViewId( test::createView( "indirectv", indirect ) ); auto & testPass = graph.createPass( "Pass" , [&renderQuad, &indirectv]( crg::FramePass const & pass , crg::GraphContext & context @@ -1041,7 +1236,7 @@ namespace , crg::RunnableGraph & runGraph ) { crg::rm::Config cfg; - cfg.getPassIndex( crg::RunnablePass::GetPassIndexCallback( [&passIndex](){ return passIndex; } ) ); + cfg.getPassIndex( crg::GetPassIndexCallback( [&passIndex](){ return passIndex; } ) ); cfg.baseConfig( crg::pp::Config{} .programCreator( crg::ProgramCreator{ 2u , []( uint32_t ){ return crg::VkPipelineShaderStageCreateInfoArray{ VkPipelineShaderStageCreateInfo{} }; } } ) ); @@ -1072,8 +1267,45 @@ namespace { crg::FrameGraph graph{ handler, testCounts.testName }; crg::RenderMesh * renderMesh{}; - auto vertex = graph.createBuffer( test::createBuffer( "vertex" ) ); - auto vertexv = graph.createView( test::createView( "vertexv", vertex ) ); + auto vertex = graph.createBufferId( test::createBuffer( "vertex" ) ); + auto vertexv = graph.createViewId( test::createView( "vertexv", vertex ) ); + auto & testPass = graph.createPass( "Pass" + , [&renderMesh, &vertexv]( crg::FramePass const & pass + , crg::GraphContext & context + , crg::RunnableGraph & runGraph ) + { + crg::rm::Config cfg; + cfg.vertexBuffer( crg::VertexBuffer{ vertexv } ); + cfg.baseConfig( crg::pp::Config{} + .programs( { crg::VkPipelineShaderStageCreateInfoArray{ VkPipelineShaderStageCreateInfo{} } } ) ); + auto res = std::make_unique< crg::RenderMesh >( pass, context, runGraph + , crg::ru::Config{ 1u, true }, std::move( cfg ) ); + renderMesh = res.get(); + return res; + } ); + testPass.addOutputColourTarget( resultv ); + + auto runnable = graph.compile( getContext() ); + test::checkRunnable( testCounts, runnable ); + require( renderMesh ) + checkNoThrow( renderMesh->resetPipeline( crg::VkPipelineShaderStageCreateInfoArray{ VkPipelineShaderStageCreateInfo{} }, 0u ) ) + checkNoThrow( runnable->record() ) + checkNoThrow( runnable->run( VkQueue{} ) ) + } + testEnd() + } + + TEST( RunnablePass, RenderMesh_PagedVertex ) + { + testBegin( "RenderMesh_PagedVertex" ) + crg::ResourceHandler handler; + auto result = handler.createImageId( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto resultv = handler.createViewId( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + { + crg::FrameGraph graph{ handler, testCounts.testName }; + crg::RenderMesh * renderMesh{}; + auto vertex = graph.createBufferId( test::createBuffer( "vertex", 2u ) ); + auto vertexv = graph.createViewId( test::createView( "vertexv", vertex ) ); auto & testPass = graph.createPass( "Pass" , [&renderMesh, &vertexv]( crg::FramePass const & pass , crg::GraphContext & context @@ -1108,10 +1340,133 @@ namespace auto resultv = handler.createViewId( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); { crg::FrameGraph graph{ handler, testCounts.testName }; - auto vertex = graph.createBuffer( test::createBuffer( "vertex" ) ); - auto index = graph.createBuffer( test::createBuffer( "index" ) ); - auto vertexv = graph.createView( test::createView( "vertexv", vertex ) ); - auto indexv = graph.createView( test::createView( "indexv", index ) ); + auto vertex = graph.createBufferId( test::createBuffer( "vertex" ) ); + auto index = graph.createBufferId( test::createBuffer( "index" ) ); + auto vertexv = graph.createViewId( test::createView( "vertexv", vertex ) ); + auto indexv = graph.createViewId( test::createView( "indexv", index ) ); + crg::RenderMesh * renderMesh{}; + auto & testPass = graph.createPass( "Pass" + , [&renderMesh, &vertexv, &indexv]( crg::FramePass const & pass + , crg::GraphContext & context + , crg::RunnableGraph & runGraph ) + { + crg::rm::Config cfg; + cfg.vertexBuffer( crg::VertexBuffer{ vertexv } ); + cfg.indexBuffer( crg::IndexBuffer{ indexv } ); + cfg.baseConfig( crg::pp::Config{} + .programCreator( crg::ProgramCreator{ 1u + , []( uint32_t ){ return crg::VkPipelineShaderStageCreateInfoArray{ VkPipelineShaderStageCreateInfo{} }; } } ) ); + auto res = std::make_unique< crg::RenderMesh >( pass, context, runGraph + , crg::ru::Config{ 1u, true }, std::move( cfg ) ); + renderMesh = res.get(); + return res; + } ); + testPass.addOutputColourTarget( resultv ); + + auto runnable = graph.compile( getContext() ); + test::checkRunnable( testCounts, runnable ); + require( renderMesh ) + checkNoThrow( renderMesh->resetPipeline( crg::VkPipelineShaderStageCreateInfoArray{ VkPipelineShaderStageCreateInfo{} }, 0u ) ) + checkNoThrow( runnable->record() ) + checkNoThrow( runnable->run( VkQueue{} ) ) + } + testEnd() + } + + TEST( RunnablePass, RenderMesh_PagedVertex_Index ) + { + testBegin( "RenderMesh_PagedVertex_Index" ) + crg::ResourceHandler handler; + auto result = handler.createImageId( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto resultv = handler.createViewId( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + { + crg::FrameGraph graph{ handler, testCounts.testName }; + auto vertex = graph.createBufferId( test::createBuffer( "vertex", 2u ) ); + auto index = graph.createBufferId( test::createBuffer( "index" ) ); + auto vertexv = graph.createViewId( test::createView( "vertexv", vertex ) ); + auto indexv = graph.createViewId( test::createView( "indexv", index ) ); + crg::RenderMesh * renderMesh{}; + auto & testPass = graph.createPass( "Pass" + , [&renderMesh, &vertexv, &indexv]( crg::FramePass const & pass + , crg::GraphContext & context + , crg::RunnableGraph & runGraph ) + { + crg::rm::Config cfg; + cfg.vertexBuffer( crg::VertexBuffer{ vertexv } ); + cfg.indexBuffer( crg::IndexBuffer{ indexv } ); + cfg.baseConfig( crg::pp::Config{} + .programCreator( crg::ProgramCreator{ 1u + , []( uint32_t ){ return crg::VkPipelineShaderStageCreateInfoArray{ VkPipelineShaderStageCreateInfo{} }; } } ) ); + auto res = std::make_unique< crg::RenderMesh >( pass, context, runGraph + , crg::ru::Config{ 1u, true }, std::move( cfg ) ); + renderMesh = res.get(); + return res; + } ); + testPass.addOutputColourTarget( resultv ); + + auto runnable = graph.compile( getContext() ); + test::checkRunnable( testCounts, runnable ); + require( renderMesh ) + checkNoThrow( renderMesh->resetPipeline( crg::VkPipelineShaderStageCreateInfoArray{ VkPipelineShaderStageCreateInfo{} }, 0u ) ) + checkNoThrow( runnable->record() ) + checkNoThrow( runnable->run( VkQueue{} ) ) + } + testEnd() + } + + TEST( RunnablePass, RenderMesh_PagedVertex_PagedIndex ) + { + testBegin( "RenderMesh_PagedVertex_PagedIndex" ) + crg::ResourceHandler handler; + auto result = handler.createImageId( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto resultv = handler.createViewId( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + { + crg::FrameGraph graph{ handler, testCounts.testName }; + auto vertex = graph.createBufferId( test::createBuffer( "vertex", 2u ) ); + auto index = graph.createBufferId( test::createBuffer( "index", 2u ) ); + auto vertexv = graph.createViewId( test::createView( "vertexv", vertex ) ); + auto indexv = graph.createViewId( test::createView( "indexv", index ) ); + crg::RenderMesh * renderMesh{}; + auto & testPass = graph.createPass( "Pass" + , [&renderMesh, &vertexv, &indexv]( crg::FramePass const & pass + , crg::GraphContext & context + , crg::RunnableGraph & runGraph ) + { + crg::rm::Config cfg; + cfg.vertexBuffer( crg::VertexBuffer{ vertexv } ); + cfg.indexBuffer( crg::IndexBuffer{ indexv } ); + cfg.baseConfig( crg::pp::Config{} + .programCreator( crg::ProgramCreator{ 1u + , []( uint32_t ){ return crg::VkPipelineShaderStageCreateInfoArray{ VkPipelineShaderStageCreateInfo{} }; } } ) ); + auto res = std::make_unique< crg::RenderMesh >( pass, context, runGraph + , crg::ru::Config{ 1u, true }, std::move( cfg ) ); + renderMesh = res.get(); + return res; + } ); + testPass.addOutputColourTarget( resultv ); + + auto runnable = graph.compile( getContext() ); + test::checkRunnable( testCounts, runnable ); + require( renderMesh ) + checkNoThrow( renderMesh->resetPipeline( crg::VkPipelineShaderStageCreateInfoArray{ VkPipelineShaderStageCreateInfo{} }, 0u ) ) + checkNoThrow( runnable->record() ) + checkNoThrow( runnable->run( VkQueue{} ) ) + } + testEnd() + } + + TEST( RunnablePass, RenderMesh_Vertex_PagedIndex ) + { + testBegin( "RenderMesh_PagedVertex_PagedIndex" ) + crg::ResourceHandler handler; + auto result = handler.createImageId( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto resultv = handler.createViewId( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + { + crg::FrameGraph graph{ handler, testCounts.testName }; + auto vertex = graph.createBufferId( test::createBuffer( "vertex" ) ); + auto index = graph.createBufferId( test::createBuffer( "index", 2u ) ); + auto vertexv = graph.createViewId( test::createView( "vertexv", vertex ) ); + auto indexv = graph.createViewId( test::createView( "indexv", index ) ); crg::RenderMesh * renderMesh{}; auto & testPass = graph.createPass( "Pass" , [&renderMesh, &vertexv, &indexv]( crg::FramePass const & pass @@ -1150,8 +1505,46 @@ namespace auto resultv = handler.createViewId( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); { crg::FrameGraph graph{ handler, testCounts.testName }; - auto indirect = graph.createBuffer( test::createBuffer( "indirect" ) ); - auto indirectv = graph.createView( test::createView( "indirectv", indirect ) ); + auto indirect = graph.createBufferId( test::createBuffer( "indirect" ) ); + auto indirectv = graph.createViewId( test::createView( "indirectv", indirect ) ); + crg::RenderMesh * renderMesh{}; + auto & testPass = graph.createPass( "Pass" + , [&renderMesh, &indirectv]( crg::FramePass const & pass + , crg::GraphContext & context + , crg::RunnableGraph & runGraph ) + { + crg::rm::Config cfg; + cfg.indirectBuffer( crg::IndirectBuffer{ indirectv, sizeof( VkDrawIndirectCommand ) } ); + cfg.baseConfig( crg::pp::Config{} + .programCreator( crg::ProgramCreator{ 1u + , []( uint32_t ){ return crg::VkPipelineShaderStageCreateInfoArray{ VkPipelineShaderStageCreateInfo{} }; } } ) ); + auto res = std::make_unique< crg::RenderMesh >( pass, context, runGraph + , crg::ru::Config{ 1u, true }, std::move( cfg ) ); + renderMesh = res.get(); + return res; + } ); + testPass.addOutputColourTarget( resultv ); + + auto runnable = graph.compile( getContext() ); + test::checkRunnable( testCounts, runnable ); + require( renderMesh ) + checkNoThrow( renderMesh->resetPipeline( crg::VkPipelineShaderStageCreateInfoArray{ VkPipelineShaderStageCreateInfo{} }, 0u ) ) + checkNoThrow( runnable->record() ) + checkNoThrow( runnable->run( VkQueue{} ) ) + } + testEnd() + } + + TEST( RunnablePass, RenderMesh_PagedIndirect ) + { + testBegin( "testRenderMesh_Indirect" ) + crg::ResourceHandler handler; + auto result = handler.createImageId( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto resultv = handler.createViewId( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + { + crg::FrameGraph graph{ handler, testCounts.testName }; + auto indirect = graph.createBufferId( test::createBuffer( "indirect", 2u ) ); + auto indirectv = graph.createViewId( test::createView( "indirectv", indirect ) ); crg::RenderMesh * renderMesh{}; auto & testPass = graph.createPass( "Pass" , [&renderMesh, &indirectv]( crg::FramePass const & pass @@ -1188,10 +1581,133 @@ namespace auto resultv = handler.createViewId( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); { crg::FrameGraph graph{ handler, testCounts.testName }; - auto indirect = graph.createBuffer( test::createBuffer( "indirect" ) ); - auto index = graph.createBuffer( test::createBuffer( "index" ) ); - auto indirectv = graph.createView( test::createView( "indirectv", indirect ) ); - auto indexv = graph.createView( test::createView( "indexv", index ) ); + auto indirect = graph.createBufferId( test::createBuffer( "indirect" ) ); + auto index = graph.createBufferId( test::createBuffer( "index" ) ); + auto indirectv = graph.createViewId( test::createView( "indirectv", indirect ) ); + auto indexv = graph.createViewId( test::createView( "indexv", index ) ); + crg::RenderMesh * renderMesh{}; + auto & testPass = graph.createPass( "Pass" + , [&renderMesh, &indirectv, &indexv]( crg::FramePass const & pass + , crg::GraphContext & context + , crg::RunnableGraph & runGraph ) + { + crg::rm::Config cfg; + cfg.indirectBuffer( crg::IndirectBuffer{ indirectv, sizeof( VkDrawIndexedIndirectCommand ) } ); + cfg.indexBuffer( crg::IndexBuffer{ indexv } ); + cfg.baseConfig( crg::pp::Config{} + .programCreator( crg::ProgramCreator{ 1u + , []( uint32_t ){ return crg::VkPipelineShaderStageCreateInfoArray{ VkPipelineShaderStageCreateInfo{} }; } } ) ); + auto res = std::make_unique< crg::RenderMesh >( pass, context, runGraph + , crg::ru::Config{ 1u, true }, std::move( cfg ) ); + renderMesh = res.get(); + return res; + } ); + testPass.addOutputColourTarget( resultv ); + + auto runnable = graph.compile( getContext() ); + test::checkRunnable( testCounts, runnable ); + require( renderMesh ) + checkNoThrow( renderMesh->resetPipeline( crg::VkPipelineShaderStageCreateInfoArray{ VkPipelineShaderStageCreateInfo{} }, 0u ) ) + checkNoThrow( runnable->record() ) + checkNoThrow( runnable->run( VkQueue{} ) ) + } + testEnd() + } + + TEST( RunnablePass, RenderMesh_PagedIndirect_Index ) + { + testBegin( "RenderMesh_PagedIndirect_Index" ) + crg::ResourceHandler handler; + auto result = handler.createImageId( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto resultv = handler.createViewId( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + { + crg::FrameGraph graph{ handler, testCounts.testName }; + auto indirect = graph.createBufferId( test::createBuffer( "indirect", 2u ) ); + auto index = graph.createBufferId( test::createBuffer( "index" ) ); + auto indirectv = graph.createViewId( test::createView( "indirectv", indirect ) ); + auto indexv = graph.createViewId( test::createView( "indexv", index ) ); + crg::RenderMesh * renderMesh{}; + auto & testPass = graph.createPass( "Pass" + , [&renderMesh, &indirectv, &indexv]( crg::FramePass const & pass + , crg::GraphContext & context + , crg::RunnableGraph & runGraph ) + { + crg::rm::Config cfg; + cfg.indirectBuffer( crg::IndirectBuffer{ indirectv, sizeof( VkDrawIndexedIndirectCommand ) } ); + cfg.indexBuffer( crg::IndexBuffer{ indexv } ); + cfg.baseConfig( crg::pp::Config{} + .programCreator( crg::ProgramCreator{ 1u + , []( uint32_t ){ return crg::VkPipelineShaderStageCreateInfoArray{ VkPipelineShaderStageCreateInfo{} }; } } ) ); + auto res = std::make_unique< crg::RenderMesh >( pass, context, runGraph + , crg::ru::Config{ 1u, true }, std::move( cfg ) ); + renderMesh = res.get(); + return res; + } ); + testPass.addOutputColourTarget( resultv ); + + auto runnable = graph.compile( getContext() ); + test::checkRunnable( testCounts, runnable ); + require( renderMesh ) + checkNoThrow( renderMesh->resetPipeline( crg::VkPipelineShaderStageCreateInfoArray{ VkPipelineShaderStageCreateInfo{} }, 0u ) ) + checkNoThrow( runnable->record() ) + checkNoThrow( runnable->run( VkQueue{} ) ) + } + testEnd() + } + + TEST( RunnablePass, RenderMesh_PagedIndirect_PagedIndex ) + { + testBegin( "RenderMesh_PagedIndirect_PagedIndex" ) + crg::ResourceHandler handler; + auto result = handler.createImageId( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto resultv = handler.createViewId( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + { + crg::FrameGraph graph{ handler, testCounts.testName }; + auto indirect = graph.createBufferId( test::createBuffer( "indirect", 2u ) ); + auto index = graph.createBufferId( test::createBuffer( "index", 2u ) ); + auto indirectv = graph.createViewId( test::createView( "indirectv", indirect ) ); + auto indexv = graph.createViewId( test::createView( "indexv", index ) ); + crg::RenderMesh * renderMesh{}; + auto & testPass = graph.createPass( "Pass" + , [&renderMesh, &indirectv, &indexv]( crg::FramePass const & pass + , crg::GraphContext & context + , crg::RunnableGraph & runGraph ) + { + crg::rm::Config cfg; + cfg.indirectBuffer( crg::IndirectBuffer{ indirectv, sizeof( VkDrawIndexedIndirectCommand ) } ); + cfg.indexBuffer( crg::IndexBuffer{ indexv } ); + cfg.baseConfig( crg::pp::Config{} + .programCreator( crg::ProgramCreator{ 1u + , []( uint32_t ){ return crg::VkPipelineShaderStageCreateInfoArray{ VkPipelineShaderStageCreateInfo{} }; } } ) ); + auto res = std::make_unique< crg::RenderMesh >( pass, context, runGraph + , crg::ru::Config{ 1u, true }, std::move( cfg ) ); + renderMesh = res.get(); + return res; + } ); + testPass.addOutputColourTarget( resultv ); + + auto runnable = graph.compile( getContext() ); + test::checkRunnable( testCounts, runnable ); + require( renderMesh ) + checkNoThrow( renderMesh->resetPipeline( crg::VkPipelineShaderStageCreateInfoArray{ VkPipelineShaderStageCreateInfo{} }, 0u ) ) + checkNoThrow( runnable->record() ) + checkNoThrow( runnable->run( VkQueue{} ) ) + } + testEnd() + } + + TEST( RunnablePass, RenderMesh_Indirect_PagedIndex ) + { + testBegin( "RenderMesh_PagedIndirect_PagedIndex" ) + crg::ResourceHandler handler; + auto result = handler.createImageId( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto resultv = handler.createViewId( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + { + crg::FrameGraph graph{ handler, testCounts.testName }; + auto indirect = graph.createBufferId( test::createBuffer( "indirect" ) ); + auto index = graph.createBufferId( test::createBuffer( "index", 2u ) ); + auto indirectv = graph.createViewId( test::createView( "indirectv", indirect ) ); + auto indexv = graph.createViewId( test::createView( "indexv", index ) ); crg::RenderMesh * renderMesh{}; auto & testPass = graph.createPass( "Pass" , [&renderMesh, &indirectv, &indexv]( crg::FramePass const & pass @@ -1227,8 +1743,10 @@ namespace crg::ResourceHandler handler; crg::FrameGraph graph{ handler, testCounts.testName }; - auto sampled = graph.createImage( test::createImage( "sampled", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto sampledv = graph.createView( test::createView( "sampledv", sampled, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto bufferId = graph.createBufferId( test::createBuffer( "buffer", 16u ) ); + auto bufferv = graph.createViewId( test::createView( "bufferv", bufferId, crg::PixelFormat::eUNDEFINED, 16u ) ); + auto sampled = graph.createImageId( test::createImage( "sampled", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto sampledv = graph.createViewId( test::createView( "sampledv", sampled, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); crg::RenderQuad * renderQuad{}; auto & testQuad = graph.createPass( "Quad" , [&renderQuad]( crg::FramePass const & pass @@ -1248,9 +1766,10 @@ namespace return res; } ); auto sampledAttach = testQuad.addOutputColourTarget( sampledv ); + auto bufferAttach = testQuad.addOutputStorageBuffer( bufferv, 0u ); - auto result = graph.createImage( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); - auto resultv = graph.createView( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); + auto result = graph.createImageId( test::createImage( "result", crg::PixelFormat::eR16G16B16A16_SFLOAT ) ); + auto resultv = graph.createViewId( test::createView( "resultv", result, crg::PixelFormat::eR16G16B16A16_SFLOAT, 0u, 1u, 0u, 1u ) ); crg::RenderMesh * renderMesh{}; auto & testMesh = graph.createPass( "Mesh" , [&renderMesh]( crg::FramePass const & pass @@ -1271,6 +1790,7 @@ namespace } ); testMesh.addOutputColourTarget( resultv ); testMesh.addInputSampled( *sampledAttach, 0u ); + testMesh.addInputStorage( *bufferAttach, 1u ); auto runnable = graph.compile( getContext() ); test::checkRunnable( testCounts, runnable ); @@ -1284,6 +1804,9 @@ namespace checkNoThrow( runnable->run( crg::SemaphoreWait{ VkSemaphore( 1 ), crg::PipelineStageFlags::eAllGraphics }, VkQueue{} ) ) checkEqual( graph.getFinalLayoutState( sampledv, 0u ).layout, crg::ImageLayout::eShaderReadOnly ) checkEqual( graph.getDefaultGroup().getFinalLayoutState( sampledv, 0u ).layout, crg::ImageLayout::eShaderReadOnly ) + auto & buffer = runnable->createBuffer( bufferId ); + buffer.resize( buffer.getMaxSize() ); + checkNoThrow( runnable->run( crg::SemaphoreWait{ VkSemaphore( 1 ), crg::PipelineStageFlags::eAllGraphics }, VkQueue{} ) ) testEnd() } } diff --git a/vcpkg.json b/vcpkg.json index 39220a8..d3f0877 100644 --- a/vcpkg.json +++ b/vcpkg.json @@ -1,8 +1,8 @@ { "$schema": "https://raw.githubusercontent.com/microsoft/vcpkg/master/scripts/vcpkg.schema.json", "name": "rendergraph", - "version": "1.4.1", - "builtin-baseline": "e140b1fde236eb682b0d47f905e65008a191800f", + "version": "2.1.0", + "builtin-baseline": "c3867e714dd3a51c272826eea77267876517ed99", "dependencies": [ "vulkan-headers" ],