mirror of
https://github.com/izzy2lost/xemu.git
synced 2026-07-06 00:20:22 -07:00
Port hakuX Vulkan descriptor pool and framebuffer cache
This commit is contained in:
@@ -471,6 +471,26 @@ static void create_frame_buffer(PGRAPHState *pg)
|
||||
|
||||
assert(r->color_binding || r->zeta_binding);
|
||||
|
||||
SurfaceBinding *binding = r->color_binding ? : r->zeta_binding;
|
||||
VkImageView color_view = r->color_binding ? r->color_binding->image_view
|
||||
: VK_NULL_HANDLE;
|
||||
VkImageView zeta_view = r->zeta_binding ? r->zeta_binding->image_view
|
||||
: VK_NULL_HANDLE;
|
||||
uint32_t width = binding->width;
|
||||
uint32_t height = binding->height;
|
||||
pgraph_apply_scaling_factor(pg, &width, &height);
|
||||
|
||||
for (int i = 0; i < r->fb_cache_count; i++) {
|
||||
if (r->fb_cache[i].render_pass == r->render_pass &&
|
||||
r->fb_cache[i].color_view == color_view &&
|
||||
r->fb_cache[i].zeta_view == zeta_view &&
|
||||
r->fb_cache[i].width == width &&
|
||||
r->fb_cache[i].height == height) {
|
||||
r->current_framebuffer = r->fb_cache[i].framebuffer;
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
if (r->framebuffer_index >= ARRAY_SIZE(r->framebuffers)) {
|
||||
pgraph_vk_finish(pg, VK_FINISH_REASON_NEED_BUFFER_SPACE);
|
||||
}
|
||||
@@ -479,26 +499,35 @@ static void create_frame_buffer(PGRAPHState *pg)
|
||||
int attachment_count = 0;
|
||||
|
||||
if (r->color_binding) {
|
||||
attachments[attachment_count++] = r->color_binding->image_view;
|
||||
attachments[attachment_count++] = color_view;
|
||||
}
|
||||
if (r->zeta_binding) {
|
||||
attachments[attachment_count++] = r->zeta_binding->image_view;
|
||||
attachments[attachment_count++] = zeta_view;
|
||||
}
|
||||
|
||||
SurfaceBinding *binding = r->color_binding ? : r->zeta_binding;
|
||||
|
||||
VkFramebufferCreateInfo create_info = {
|
||||
.sType = VK_STRUCTURE_TYPE_FRAMEBUFFER_CREATE_INFO,
|
||||
.renderPass = r->render_pass,
|
||||
.attachmentCount = attachment_count,
|
||||
.pAttachments = attachments,
|
||||
.width = binding->width,
|
||||
.height = binding->height,
|
||||
.width = width,
|
||||
.height = height,
|
||||
.layers = 1,
|
||||
};
|
||||
pgraph_apply_scaling_factor(pg, &create_info.width, &create_info.height);
|
||||
VK_CHECK(vkCreateFramebuffer(r->device, &create_info, NULL,
|
||||
&r->framebuffers[r->framebuffer_index++]));
|
||||
r->current_framebuffer = r->framebuffers[r->framebuffer_index - 1];
|
||||
|
||||
if (r->fb_cache_count < FB_CACHE_MAX) {
|
||||
r->fb_cache[r->fb_cache_count++] = (typeof(r->fb_cache[0])) {
|
||||
.render_pass = r->render_pass,
|
||||
.color_view = color_view,
|
||||
.zeta_view = zeta_view,
|
||||
.width = width,
|
||||
.height = height,
|
||||
.framebuffer = r->current_framebuffer,
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
static void destroy_framebuffers(PGRAPHState *pg)
|
||||
@@ -511,6 +540,8 @@ static void destroy_framebuffers(PGRAPHState *pg)
|
||||
r->framebuffers[i] = VK_NULL_HANDLE;
|
||||
}
|
||||
r->framebuffer_index = 0;
|
||||
r->fb_cache_count = 0;
|
||||
r->current_framebuffer = VK_NULL_HANDLE;
|
||||
}
|
||||
|
||||
static void create_clear_pipeline(PGRAPHState *pg)
|
||||
@@ -1282,12 +1313,12 @@ static void begin_render_pass(PGRAPHState *pg)
|
||||
vp_height = pg->surface_binding_dim.height;
|
||||
pgraph_apply_scaling_factor(pg, &vp_width, &vp_height);
|
||||
|
||||
assert(r->framebuffer_index > 0);
|
||||
assert(r->current_framebuffer != VK_NULL_HANDLE);
|
||||
|
||||
VkRenderPassBeginInfo render_pass_begin_info = {
|
||||
.sType = VK_STRUCTURE_TYPE_RENDER_PASS_BEGIN_INFO,
|
||||
.renderPass = r->render_pass,
|
||||
.framebuffer = r->framebuffers[r->framebuffer_index - 1],
|
||||
.framebuffer = r->current_framebuffer,
|
||||
.renderArea.extent.width = vp_width,
|
||||
.renderArea.extent.height = vp_height,
|
||||
.clearValueCount = 0,
|
||||
|
||||
@@ -43,6 +43,9 @@
|
||||
#include "glsl.h"
|
||||
|
||||
#define HAVE_EXTERNAL_MEMORY 0
|
||||
#define NUM_GFX_DESCRIPTOR_SETS 8192
|
||||
#define MAX_FRAMEBUFFERS 256
|
||||
#define FB_CACHE_MAX 32
|
||||
|
||||
typedef struct QueueFamilyIndices {
|
||||
int queue_family;
|
||||
@@ -369,9 +372,19 @@ typedef struct PGRAPHVkState {
|
||||
VkCommandBuffer aux_command_buffer;
|
||||
bool in_aux_command_buffer;
|
||||
|
||||
VkFramebuffer framebuffers[50];
|
||||
VkFramebuffer framebuffers[MAX_FRAMEBUFFERS];
|
||||
int framebuffer_index;
|
||||
bool framebuffer_dirty;
|
||||
struct {
|
||||
VkRenderPass render_pass;
|
||||
VkImageView color_view;
|
||||
VkImageView zeta_view;
|
||||
uint32_t width;
|
||||
uint32_t height;
|
||||
VkFramebuffer framebuffer;
|
||||
} fb_cache[FB_CACHE_MAX];
|
||||
int fb_cache_count;
|
||||
VkFramebuffer current_framebuffer;
|
||||
|
||||
VkRenderPass render_pass;
|
||||
GArray *render_passes; // RenderPass
|
||||
@@ -387,7 +400,8 @@ typedef struct PGRAPHVkState {
|
||||
|
||||
VkDescriptorPool descriptor_pool;
|
||||
VkDescriptorSetLayout descriptor_set_layout;
|
||||
VkDescriptorSet descriptor_sets[1024];
|
||||
VkDescriptorSet *descriptor_sets;
|
||||
int descriptor_set_count;
|
||||
int descriptor_set_index;
|
||||
|
||||
StorageBuffer storage_buffers[BUFFER_COUNT];
|
||||
|
||||
@@ -32,7 +32,7 @@ static void create_descriptor_pool(PGRAPHState *pg)
|
||||
{
|
||||
PGRAPHVkState *r = pg->vk_renderer_state;
|
||||
|
||||
size_t num_sets = ARRAY_SIZE(r->descriptor_sets);
|
||||
size_t num_sets = r->descriptor_set_count;
|
||||
|
||||
VkDescriptorPoolSize pool_sizes[] = {
|
||||
{
|
||||
@@ -49,7 +49,7 @@ static void create_descriptor_pool(PGRAPHState *pg)
|
||||
.sType = VK_STRUCTURE_TYPE_DESCRIPTOR_POOL_CREATE_INFO,
|
||||
.poolSizeCount = ARRAY_SIZE(pool_sizes),
|
||||
.pPoolSizes = pool_sizes,
|
||||
.maxSets = ARRAY_SIZE(r->descriptor_sets),
|
||||
.maxSets = num_sets,
|
||||
.flags = VK_DESCRIPTOR_POOL_CREATE_FREE_DESCRIPTOR_SET_BIT,
|
||||
};
|
||||
VK_CHECK(vkCreateDescriptorPool(r->device, &pool_info, NULL,
|
||||
@@ -110,31 +110,39 @@ static void destroy_descriptor_set_layout(PGRAPHState *pg)
|
||||
static void create_descriptor_sets(PGRAPHState *pg)
|
||||
{
|
||||
PGRAPHVkState *r = pg->vk_renderer_state;
|
||||
int count = r->descriptor_set_count;
|
||||
|
||||
VkDescriptorSetLayout layouts[ARRAY_SIZE(r->descriptor_sets)];
|
||||
for (int i = 0; i < ARRAY_SIZE(layouts); i++) {
|
||||
r->descriptor_sets = g_malloc_n(count, sizeof(VkDescriptorSet));
|
||||
|
||||
VkDescriptorSetLayout *layouts =
|
||||
g_malloc_n(count, sizeof(VkDescriptorSetLayout));
|
||||
for (int i = 0; i < count; i++) {
|
||||
layouts[i] = r->descriptor_set_layout;
|
||||
}
|
||||
|
||||
VkDescriptorSetAllocateInfo alloc_info = {
|
||||
.sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_ALLOCATE_INFO,
|
||||
.descriptorPool = r->descriptor_pool,
|
||||
.descriptorSetCount = ARRAY_SIZE(r->descriptor_sets),
|
||||
.descriptorSetCount = count,
|
||||
.pSetLayouts = layouts,
|
||||
};
|
||||
VK_CHECK(
|
||||
vkAllocateDescriptorSets(r->device, &alloc_info, r->descriptor_sets));
|
||||
g_free(layouts);
|
||||
}
|
||||
|
||||
static void destroy_descriptor_sets(PGRAPHState *pg)
|
||||
{
|
||||
PGRAPHVkState *r = pg->vk_renderer_state;
|
||||
|
||||
vkFreeDescriptorSets(r->device, r->descriptor_pool,
|
||||
ARRAY_SIZE(r->descriptor_sets), r->descriptor_sets);
|
||||
for (int i = 0; i < ARRAY_SIZE(r->descriptor_sets); i++) {
|
||||
r->descriptor_sets[i] = VK_NULL_HANDLE;
|
||||
if (r->descriptor_sets == NULL) {
|
||||
return;
|
||||
}
|
||||
|
||||
vkFreeDescriptorSets(r->device, r->descriptor_pool,
|
||||
r->descriptor_set_count, r->descriptor_sets);
|
||||
g_free(r->descriptor_sets);
|
||||
r->descriptor_sets = NULL;
|
||||
}
|
||||
|
||||
void pgraph_vk_update_descriptor_sets(PGRAPHState *pg)
|
||||
@@ -164,7 +172,7 @@ void pgraph_vk_update_descriptor_sets(PGRAPHState *pg)
|
||||
r->device_props.limits.minUniformBufferOffsetAlignment);
|
||||
|
||||
bool need_descriptor_write_reset =
|
||||
(r->descriptor_set_index >= ARRAY_SIZE(r->descriptor_sets));
|
||||
(r->descriptor_set_index >= r->descriptor_set_count);
|
||||
|
||||
if (need_descriptor_write_reset || need_ubo_staging_buffer_reset) {
|
||||
pgraph_vk_finish(pg, VK_FINISH_REASON_NEED_BUFFER_SPACE);
|
||||
@@ -173,7 +181,7 @@ void pgraph_vk_update_descriptor_sets(PGRAPHState *pg)
|
||||
|
||||
VkWriteDescriptorSet descriptor_writes[2 + NV2A_MAX_TEXTURES];
|
||||
|
||||
assert(r->descriptor_set_index < ARRAY_SIZE(r->descriptor_sets));
|
||||
assert(r->descriptor_set_index < r->descriptor_set_count);
|
||||
|
||||
if (need_uniform_write) {
|
||||
for (int i = 0; i < ARRAY_SIZE(layouts); i++) {
|
||||
@@ -531,6 +539,7 @@ void pgraph_vk_init_shaders(PGRAPHState *pg)
|
||||
{
|
||||
PGRAPHVkState *r = pg->vk_renderer_state;
|
||||
|
||||
r->descriptor_set_count = NUM_GFX_DESCRIPTOR_SETS;
|
||||
pgraph_vk_init_glsl_compiler();
|
||||
create_descriptor_pool(pg);
|
||||
create_descriptor_set_layout(pg);
|
||||
|
||||
Reference in New Issue
Block a user