Skip to content

Commit

Permalink
[Release] Applied following fixes: (#191)
Browse files Browse the repository at this point in the history
* Applied following fixes:

  - Resolved inconsistencies with API generation of struct members (ignoring const)
  - Added offset member to the Vertex buffer binding. Default is 0.
  - Fixed DX12 Unbounded descriptor array feature not being documented and not working correctly
  - Added forgotten dynamic rendering to Vulkan pipeline creation
  - Added unbounded descriptor array feature to Vulkan
  - Vulkan now supports unused render attachments if possible
  - Added forgotten setting pipeline state call to both command list APIs
  - Removed brutal reset from DX12 command list, now it will not reset the allocator which may have lead to UB if list was executed currently

* Barrier API mentioned

---------

Co-authored-by: Restyled.io <[email protected]>

---------

Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com>
Co-authored-by: Restyled.io <[email protected]>
  • Loading branch information
3 people authored Oct 26, 2024
1 parent 9cd2d3b commit a0ad55c
Show file tree
Hide file tree
Showing 27 changed files with 284 additions and 132 deletions.
2 changes: 1 addition & 1 deletion CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@

cmake_minimum_required(VERSION 3.22)

set(WISDOM_VERSION "0.3.10")
set(WISDOM_VERSION "0.3.11")
project("Wisdom" VERSION ${WISDOM_VERSION})

set(CMAKE_DEBUG_POSTFIX d)
Expand Down
15 changes: 13 additions & 2 deletions Changelog.md
Original file line number Diff line number Diff line change
@@ -1,13 +1,24 @@
# Version History

- 0.3.7-0.3.10
- 0.3.11

- Resolved inconsistencies with API generation of struct members (ignoring const)
- Added offset member to the Vertex buffer binding. Default is 0.
- Fixed DX12 Unbounded descriptor array feature not being documented and not working correctly
- Added forgotten dynamic rendering to Vulkan pipeline creation
- Added unbounded descriptor array feature to Vulkan
- Vulkan now supports unused render attachments if possible
- Added forgotten setting pipeline state call to both command list APIs
- Removed brutal reset from DX12 command list, now it will not reset the allocator which may have lead to UB if list was executed currently
- Subresource ranges were annoying part of the TextureBarrier api. Now if left empty, it will be filled with the whole resource.

- 0.3.7-0.3.10

- Fixed annoying warning about class/struct mismatch in C++ API
- Fixed render pass for DX12 always clearing, despite of value
- Added specific function for creating depth stencil views
- Fixed missing DXGI lib dependency for DX12 under NuGet


- 0.3.6

- Fixed inconsistency with Descriptor tables (bytes vs descriptors)
Expand Down
10 changes: 10 additions & 0 deletions bindings/wisdom.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -447,6 +447,11 @@ extern "C" WisResult DX12CommandListReset(DX12CommandList self, DX12PipelineStat
;
return reinterpret_cast<WisResult&>(res);
}
extern "C" void DX12CommandListSetPipelineState(DX12CommandList self, DX12PipelineState pipeline)
{
auto* xself = reinterpret_cast<wis::DX12CommandList*>(self);
xself->SetPipelineState(*reinterpret_cast<wis::DX12PipelineState*>(pipeline));
}
extern "C" void DX12CommandListCopyBuffer(DX12CommandList self, DX12Buffer source, DX12Buffer destination, WisBufferRegion region)
{
auto* xself = reinterpret_cast<wis::DX12CommandList*>(self);
Expand Down Expand Up @@ -1183,6 +1188,11 @@ extern "C" WisResult VKCommandListReset(VKCommandList self, VKPipelineState pipe
;
return reinterpret_cast<WisResult&>(res);
}
extern "C" void VKCommandListSetPipelineState(VKCommandList self, VKPipelineState pipeline)
{
auto* xself = reinterpret_cast<wis::VKCommandList*>(self);
xself->SetPipelineState(*reinterpret_cast<wis::VKPipelineState*>(pipeline));
}
extern "C" void VKCommandListCopyBuffer(VKCommandList self, VKBuffer source, VKBuffer destination, WisBufferRegion region)
{
auto* xself = reinterpret_cast<wis::VKCommandList*>(self);
Expand Down
57 changes: 49 additions & 8 deletions bindings/wisdom.h
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@

/** \mainpage Wisdom API Documentation
<b>Version 0.3.9</b>
<b>Version 0.3.11</b>
Copyright (c) 2024 Ilya Doroshenko. All rights reserved.
License: MIT
Expand Down Expand Up @@ -1056,6 +1056,7 @@ enum WisDeviceFeature {
* Unlocks Swapchain::Present2 function. Without the extension behavior is the same as Swapchain::Present.
* */
DeviceFeatureDynamicVSync = 5,
DeviceFeatureUnusedRenderTargets = 6, ///< Supports unused render targets. Support for VK, always true for DX12.
};

/**
Expand Down Expand Up @@ -1742,7 +1743,11 @@ struct WisTextureBarrier {
WisResourceAccess access_after; ///< Resource access after the barrier.
WisTextureState state_before; ///< Texture state before the barrier.
WisTextureState state_after; ///< Texture state after the barrier.
WisSubresourceRange subresource_range; ///< Subresource range of the texture.
/**
* @brief Subresource range of the texture.
* Zero initialized range means all subresources are selected.
* */
WisSubresourceRange subresource_range;
};

/**
Expand All @@ -1752,15 +1757,15 @@ struct WisDescriptorTableEntry {
WisDescriptorType type; ///< Descriptor type.
uint32_t bind_register; ///< Bind register number in HLSL.
uint32_t binding; ///< Binding number in HLSL.
uint32_t count; ///< Descriptor count for Array descriptors.
uint32_t count; ///< Descriptor count for Array descriptors. UINT32_MAX means unbounded array.
};

/**
* @brief Descriptor table for .
* */
struct WisDescriptorTable {
WisDescriptorHeapType type; ///< Descriptor heap type. Either Descriptor or Sampler.
WisDescriptorTableEntry* entries; ///< Descriptor table entries array.
const WisDescriptorTableEntry* entries; ///< Descriptor table entries array.
uint32_t entry_count; ///< Descriptor table entries count.
WisShaderStages stage; ///< Shader stage. Defines the stage where the table is used.
};
Expand Down Expand Up @@ -1990,6 +1995,7 @@ struct VKVertexBufferBinding {
VKBufferView buffer; ///< Buffer view.
uint32_t size; ///< Size of the buffer in bytes.
uint32_t stride; ///< Stride of the buffer in bytes.
uint32_t offset; ///< Offset in buffer in bytes. Default is 0.
};

//-------------------------------------------------------------------------
Expand Down Expand Up @@ -2507,12 +2513,19 @@ WISDOM_API bool VKCommandListClosed(VKCommandList self);
WISDOM_API bool VKCommandListClose(VKCommandList self);

/**
* @brief Resets the command list for recording.
* @brief Resets the command list for recording. Can be reset while executing, but
* @param self valid handle to the CommandList
* @param pipeline The pipeline to reset the command list with. Default is empty pipeline.
* */
WISDOM_API WisResult VKCommandListReset(VKCommandList self, VKPipelineState pipeline);

/**
* @brief Switches command list to use new pipeline. All the operations will be recorded with regards to the new bound pipeline.
* @param self valid handle to the CommandList
* @param pipeline The pipeline to use with the command list with.
* */
WISDOM_API void VKCommandListSetPipelineState(VKCommandList self, VKPipelineState pipeline);

/**
* @brief Copies data from one buffer to another.
* @param self valid handle to the CommandList
Expand Down Expand Up @@ -3036,6 +3049,7 @@ struct DX12VertexBufferBinding {
DX12BufferView buffer; ///< Buffer view.
uint32_t size; ///< Size of the buffer in bytes.
uint32_t stride; ///< Stride of the buffer in bytes.
uint32_t offset; ///< Offset in buffer in bytes. Default is 0.
};

//-------------------------------------------------------------------------
Expand Down Expand Up @@ -3553,12 +3567,19 @@ WISDOM_API bool DX12CommandListClosed(DX12CommandList self);
WISDOM_API bool DX12CommandListClose(DX12CommandList self);

/**
* @brief Resets the command list for recording.
* @brief Resets the command list for recording. Can be reset while executing, but
* @param self valid handle to the CommandList
* @param pipeline The pipeline to reset the command list with. Default is empty pipeline.
* */
WISDOM_API WisResult DX12CommandListReset(DX12CommandList self, DX12PipelineState pipeline);

/**
* @brief Switches command list to use new pipeline. All the operations will be recorded with regards to the new bound pipeline.
* @param self valid handle to the CommandList
* @param pipeline The pipeline to use with the command list with.
* */
WISDOM_API void DX12CommandListSetPipelineState(DX12CommandList self, DX12PipelineState pipeline);

/**
* @brief Copies data from one buffer to another.
* @param self valid handle to the CommandList
Expand Down Expand Up @@ -4626,7 +4647,7 @@ inline bool WisCommandListClose(WisCommandList self)
}

/**
* @brief Resets the command list for recording.
* @brief Resets the command list for recording. Can be reset while executing, but
* @param self valid handle to the CommandList
* @param pipeline The pipeline to reset the command list with. Default is empty pipeline.
* */
Expand All @@ -4635,6 +4656,16 @@ inline WisResult WisCommandListReset(WisCommandList self, WisPipelineState pipel
return DX12CommandListReset(self, pipeline);
}

/**
* @brief Switches command list to use new pipeline. All the operations will be recorded with regards to the new bound pipeline.
* @param self valid handle to the CommandList
* @param pipeline The pipeline to use with the command list with.
* */
inline void WisCommandListSetPipelineState(WisCommandList self, WisPipelineState pipeline)
{
return DX12CommandListSetPipelineState(self, pipeline);
}

/**
* @brief Copies data from one buffer to another.
* @param self valid handle to the CommandList
Expand Down Expand Up @@ -5821,7 +5852,7 @@ inline bool WisCommandListClose(WisCommandList self)
}

/**
* @brief Resets the command list for recording.
* @brief Resets the command list for recording. Can be reset while executing, but
* @param self valid handle to the CommandList
* @param pipeline The pipeline to reset the command list with. Default is empty pipeline.
* */
Expand All @@ -5830,6 +5861,16 @@ inline WisResult WisCommandListReset(WisCommandList self, WisPipelineState pipel
return VKCommandListReset(self, pipeline);
}

/**
* @brief Switches command list to use new pipeline. All the operations will be recorded with regards to the new bound pipeline.
* @param self valid handle to the CommandList
* @param pipeline The pipeline to use with the command list with.
* */
inline void WisCommandListSetPipelineState(WisCommandList self, WisPipelineState pipeline)
{
return VKCommandListSetPipelineState(self, pipeline);
}

/**
* @brief Copies data from one buffer to another.
* @param self valid handle to the CommandList
Expand Down
48 changes: 25 additions & 23 deletions generator/generator.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1474,16 +1474,17 @@ std::string Generator::MakeCStruct(const WisStruct& s)
}

for (auto& m : s.members) {
auto mfullname = GetCFullTypename(m.type);

std::string res_type;

if (m.modifier == "ptr")
res_type = '*';

WisFunctionParameter wfp{
.type_info = GetTypeInfo(m.type),
.type = m.type,
.name = m.name,
.modifier = m.modifier,
.default_value = m.default_value,
.doc = m.doc,
};
auto val_str = m.array_size.empty()
? wis::format(" {} {};", mfullname + res_type, m.name)
: wis::format(" {} {}[{}];", mfullname, m.name, m.array_size);
? wis::format(" {};", GetCFullArg(wfp, ""))
: wis::format(" {} {}[{}];", GetCFullArg(wfp, "", true), m.name, m.array_size);
st_decl += MakeCValueDocumentation(val_str, m.doc, s.name);
}

Expand All @@ -1503,22 +1504,19 @@ std::string Generator::MakeCPPStruct(const WisStruct& s)

for (auto& m : s.members) {
std::string val_str;
auto mfullname = GetCPPFullTypename(m.type);

std::string mod;
if (m.modifier == "ptr")
mod = '*';
WisFunctionParameter wfp{
.type_info = GetTypeInfo(m.type),
.type = m.type,
.name = m.name,
.modifier = m.modifier,
.default_value = m.default_value,
.doc = m.doc,
};

if (m.array_size.empty()) {
std::string def = "";
if (!m.default_value.empty()) {
def = enum_map.contains(m.type) || bitmask_map.contains(m.type)
? wis::format(" = {}::{}", mfullname, m.default_value)
: wis::format(" = {}", m.default_value);
}
val_str = wis::format(" {} {}{};", mfullname + mod, m.name, def);
val_str = wis::format(" {};", GetCPPFullArg(wfp, ""));
} else {
val_str = wis::format(" std::array<{}, {}> {} {{}};", mfullname, m.array_size, m.name);
val_str = wis::format(" std::array<{}, {}> {} {{}};", GetCPPFullArg(wfp, "", true), m.array_size, m.name);
}
st_decl += MakeCPPValueDocumentation(val_str, m.doc, s.name);
}
Expand Down Expand Up @@ -2335,6 +2333,8 @@ std::string Generator::GetCPPFullArg(const WisFunctionParameter& arg, std::strin
std::string post_decl;
std::string post_name;
std::string pre_decl;
std::string mfullname = GetCPPFullTypename(arg.type, impl);

if (arg.modifier.find("ptr") != std::string_view::npos) {
post_decl = '*';
}
Expand All @@ -2348,7 +2348,9 @@ std::string Generator::GetCPPFullArg(const WisFunctionParameter& arg, std::strin
post_decl = '&';
}
if (!arg.default_value.empty()) {
post_name = wis::format(" = {}", arg.default_value);
post_name = enum_map.contains(arg.type) || bitmask_map.contains(arg.type)
? wis::format(" = {}::{}", mfullname, arg.default_value)
: wis::format(" = {}", arg.default_value);
}
return only_type
? wis::format("{} {}{}", pre_decl, GetCPPFullTypename(arg.type, impl), post_decl)
Expand Down
8 changes: 4 additions & 4 deletions wisdom/include/wisdom/dx12/dx12_allocator.h
Original file line number Diff line number Diff line change
Expand Up @@ -104,7 +104,7 @@ class DX12ResourceAllocator : public wis::ImplDX12ResourceAllocator
* @param mem_flags The flags of the memory to allocate for the buffer.
* @return wis::DX12Buffer on success (wis::Status::Ok).
* */
[[nodiscard]] inline wis::ResultValue<wis::DX12Buffer> CreateBuffer(uint64_t size, wis::BufferUsage usage, wis::MemoryType memory = MemoryType::Default, wis::MemoryFlags mem_flags = MemoryFlags::None) const noexcept
[[nodiscard]] inline wis::ResultValue<wis::DX12Buffer> CreateBuffer(uint64_t size, wis::BufferUsage usage, wis::MemoryType memory = wis::MemoryType::Default, wis::MemoryFlags mem_flags = wis::MemoryFlags::None) const noexcept
{
return wis::ImplDX12ResourceAllocator::CreateBuffer(size, usage, memory, mem_flags);
}
Expand All @@ -116,7 +116,7 @@ class DX12ResourceAllocator : public wis::ImplDX12ResourceAllocator
* @param mem_flags The flags of the memory to allocate for the texture.
* @return wis::DX12Texture on success (wis::Status::Ok).
* */
[[nodiscard]] inline wis::ResultValue<wis::DX12Texture> CreateTexture(const wis::TextureDesc& desc, wis::MemoryType memory = MemoryType::Default, wis::MemoryFlags mem_flags = MemoryFlags::None) const noexcept
[[nodiscard]] inline wis::ResultValue<wis::DX12Texture> CreateTexture(const wis::TextureDesc& desc, wis::MemoryType memory = wis::MemoryType::Default, wis::MemoryFlags mem_flags = wis::MemoryFlags::None) const noexcept
{
return wis::ImplDX12ResourceAllocator::CreateTexture(desc, memory, mem_flags);
}
Expand Down Expand Up @@ -147,7 +147,7 @@ class DX12ResourceAllocator : public wis::ImplDX12ResourceAllocator
* @param mem_flags The flags of the memory to allocate for the image.
* @return wis::DX12Memory on success (wis::Status::Ok).
* */
[[nodiscard]] inline wis::ResultValue<wis::DX12Memory> AllocateTextureMemory(uint64_t size, wis::TextureUsage usage, wis::MemoryType mem_type = MemoryType::Default, wis::MemoryFlags mem_flags = MemoryFlags::None) const noexcept
[[nodiscard]] inline wis::ResultValue<wis::DX12Memory> AllocateTextureMemory(uint64_t size, wis::TextureUsage usage, wis::MemoryType mem_type = wis::MemoryType::Default, wis::MemoryFlags mem_flags = wis::MemoryFlags::None) const noexcept
{
return wis::ImplDX12ResourceAllocator::AllocateTextureMemory(size, usage, mem_type, mem_flags);
}
Expand All @@ -159,7 +159,7 @@ class DX12ResourceAllocator : public wis::ImplDX12ResourceAllocator
* @param mem_flags The flags of the memory to allocate for the buffer.
* @return wis::DX12Memory on success (wis::Status::Ok).
* */
[[nodiscard]] inline wis::ResultValue<wis::DX12Memory> AllocateBufferMemory(uint64_t size, wis::BufferUsage usage, wis::MemoryType mem_type = MemoryType::Default, wis::MemoryFlags mem_flags = MemoryFlags::None) const noexcept
[[nodiscard]] inline wis::ResultValue<wis::DX12Memory> AllocateBufferMemory(uint64_t size, wis::BufferUsage usage, wis::MemoryType mem_type = wis::MemoryType::Default, wis::MemoryFlags mem_flags = wis::MemoryFlags::None) const noexcept
{
return wis::ImplDX12ResourceAllocator::AllocateBufferMemory(size, usage, mem_type, mem_flags);
}
Expand Down
16 changes: 13 additions & 3 deletions wisdom/include/wisdom/dx12/dx12_command_list.h
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,7 @@ class ImplDX12CommandList : public QueryInternal<DX12CommandList>
return closed;
}
WIS_INLINE bool Close() noexcept;
[[nodiscard]] WIS_INLINE wis::Result Reset(DX12PipelineHandle pipeline = nullptr) noexcept;
[[nodiscard]] WIS_INLINE wis::Result Reset(wis::DX12PipelineView pipeline = {}) noexcept;
WIS_INLINE void CopyBuffer(DX12BufferView source, DX12BufferView destination, wis::BufferRegion region) const noexcept;

WIS_INLINE void CopyBufferToTexture(DX12BufferView src_buffer, DX12TextureView dest_texture, const wis::BufferTextureCopyRegion* regions, uint32_t region_count) const noexcept;
Expand All @@ -65,6 +65,8 @@ class ImplDX12CommandList : public QueryInternal<DX12CommandList>

WIS_INLINE void SetRootSignature(wis::DX12RootSignatureView root_signature) noexcept;

WIS_INLINE void SetPipelineState(wis::DX12PipelineView pipeline_state) noexcept;

WIS_INLINE void IASetPrimitiveTopology(wis::PrimitiveTopology vp) noexcept;

WIS_INLINE void IASetVertexBuffers(const wis::DX12VertexBufferBinding* resources, uint32_t count, uint32_t start_slot = 0) noexcept;
Expand Down Expand Up @@ -128,13 +130,21 @@ class DX12CommandList : public wis::ImplDX12CommandList
return wis::ImplDX12CommandList::Close();
}
/**
* @brief Resets the command list for recording.
* @brief Resets the command list for recording. Can be reset while executing, but
* @param pipeline The pipeline to reset the command list with. Default is empty pipeline.
* */
[[nodiscard]] inline wis::Result Reset(wis::DX12PipelineHandle pipeline = {}) noexcept
[[nodiscard]] inline wis::Result Reset(wis::DX12PipelineView pipeline = {}) noexcept
{
return wis::ImplDX12CommandList::Reset(std::move(pipeline));
}
/**
* @brief Switches command list to use new pipeline. All the operations will be recorded with regards to the new bound pipeline.
* @param pipeline The pipeline to use with the command list with.
* */
inline void SetPipelineState(wis::DX12PipelineView pipeline) noexcept
{
return wis::ImplDX12CommandList::SetPipelineState(std::move(pipeline));
}
/**
* @brief Copies data from one buffer to another.
* @param source The source buffer to copy from.
Expand Down
4 changes: 2 additions & 2 deletions wisdom/include/wisdom/dx12/dx12_device.h
Original file line number Diff line number Diff line change
Expand Up @@ -124,7 +124,7 @@ class DX12Device : public wis::ImplDX12Device
* Default is wis::MutiWaitFlags::All
* @param timeout The timeout in nanoseconds. If UINT64_MAX, waits indefinitely.
* */
[[nodiscard]] inline wis::Result WaitForMultipleFences(const wis::DX12FenceView* fences, const uint64_t* fence_values, uint32_t fence_count, wis::MutiWaitFlags wait_all = MutiWaitFlags::All, uint64_t timeout = UINT64_MAX) const noexcept
[[nodiscard]] inline wis::Result WaitForMultipleFences(const wis::DX12FenceView* fences, const uint64_t* fence_values, uint32_t fence_count, wis::MutiWaitFlags wait_all = wis::MutiWaitFlags::All, uint64_t timeout = UINT64_MAX) const noexcept
{
return wis::ImplDX12Device::WaitForMultipleFences(fences, fence_values, fence_count, wait_all, timeout);
}
Expand All @@ -134,7 +134,7 @@ class DX12Device : public wis::ImplDX12Device
* @param flags The flags of the fence.
* @return wis::DX12Fence on success (wis::Status::Ok).
* */
[[nodiscard]] inline wis::ResultValue<wis::DX12Fence> CreateFence(uint64_t initial_value = 0, wis::FenceFlags flags = FenceFlags::None) const noexcept
[[nodiscard]] inline wis::ResultValue<wis::DX12Fence> CreateFence(uint64_t initial_value = 0, wis::FenceFlags flags = wis::FenceFlags::None) const noexcept
{
return wis::ImplDX12Device::CreateFence(initial_value, flags);
}
Expand Down
Loading

0 comments on commit a0ad55c

Please sign in to comment.