vulkan: Swapchains reimplemented

- Adds support for abstract implementations
- Adds native windowing implementations for WIN32 and X11 as fallbacks
  when present support is lacking (headless configs)
This commit is contained in:
kd-11 2018-02-17 14:45:08 +03:00
parent 1b26ec56ed
commit 77f2b521e1
6 changed files with 816 additions and 436 deletions

View File

@ -394,7 +394,7 @@ if(NOT MSVC)
endif() endif()
if(WIN32) if(WIN32)
target_link_libraries(rpcs3 ws2_32.lib Winmm.lib Psapi.lib VKstatic.1 glslang OSDependent OGLCompiler SPIRV HLSL setupapi.lib hidapi-hid Shlwapi.lib) target_link_libraries(rpcs3 ws2_32.lib Winmm.lib Psapi.lib gdi32.lib VKstatic.1 glslang OSDependent OGLCompiler SPIRV HLSL setupapi.lib hidapi-hid Shlwapi.lib)
if(NOT MSVC) if(NOT MSVC)
target_link_libraries(rpcs3 ${OPENGL_LIBRARIES} opengl32.lib glu32.lib libpthread) target_link_libraries(rpcs3 ${OPENGL_LIBRARIES} opengl32.lib glu32.lib libpthread)
else() else()

View File

@ -472,8 +472,6 @@ namespace
VKGSRender::VKGSRender() : GSRender() VKGSRender::VKGSRender() : GSRender()
{ {
//shaders_cache.load(rsx::old_shaders_cache::shader_language::glsl);
u32 instance_handle = m_thread_context.createInstance("RPCS3"); u32 instance_handle = m_thread_context.createInstance("RPCS3");
if (instance_handle > 0) if (instance_handle > 0)
@ -505,60 +503,44 @@ VKGSRender::VKGSRender() : GSRender()
display_handle_t display = m_frame->handle(); display_handle_t display = m_frame->handle();
#ifdef _WIN32 #ifndef _WIN32
display.match([this](std::pair<Display*, Window> p) { m_display_handle = p.first; XFlush(m_display_handle); }, [](auto _) {});
HINSTANCE hInstance = NULL;
for (auto &gpu : gpus)
{
if (gpu.name() == adapter_name)
{
m_swap_chain = m_thread_context.createSwapChain(hInstance, display, gpu);
gpu_found = true;
break;
}
}
if (!gpu_found || adapter_name.empty())
{
m_swap_chain = m_thread_context.createSwapChain(hInstance, display, gpus[0]);
}
#elif HAVE_VULKAN
display.match([](std::pair<Display*, Window> p) { XFlush(p.first); }, [](auto _) {});
for (auto &gpu : gpus)
{
if (gpu.name() == adapter_name)
{
m_swap_chain = m_thread_context.createSwapChain(display, gpu);
gpu_found = true;
break;
}
}
if (!gpu_found || adapter_name.empty())
{
m_swap_chain = m_thread_context.createSwapChain(display, gpus[0]);
}
display.match([&](std::pair<Display*, Window> p) { m_display_handle = p.first; }, [](auto _) {});
#endif #endif
m_device = (vk::render_device *)(&m_swap_chain->get_device()); for (auto &gpu : gpus)
{
if (gpu.name() == adapter_name)
{
m_swapchain.reset(m_thread_context.createSwapChain(display, gpu));
gpu_found = true;
break;
}
}
m_memory_type_mapping = get_memory_mapping(m_device->gpu()); if (!gpu_found || adapter_name.empty())
{
m_swapchain.reset(m_thread_context.createSwapChain(display, gpus[0]));
}
if (!m_swapchain)
{
m_device = VK_NULL_HANDLE;
LOG_FATAL(RSX, "Could not successfully initialize a swapchain");
return;
}
m_device = (vk::render_device*)(&m_swapchain->get_device());
m_memory_type_mapping = m_device->get_memory_mapping();
m_optimal_tiling_supported_formats = vk::get_optimal_tiling_supported_formats(m_device->gpu()); m_optimal_tiling_supported_formats = vk::get_optimal_tiling_supported_formats(m_device->gpu());
vk::set_current_thread_ctx(m_thread_context); vk::set_current_thread_ctx(m_thread_context);
vk::set_current_renderer(m_swap_chain->get_device()); vk::set_current_renderer(m_swapchain->get_device());
m_client_width = m_frame->client_width(); m_client_width = m_frame->client_width();
m_client_height = m_frame->client_height(); m_client_height = m_frame->client_height();
if (!m_swap_chain->init_swapchain(m_client_width, m_client_height)) if (!m_swapchain->init(m_client_width, m_client_height))
present_surface_dirty_flag = true; present_surface_dirty_flag = true;
//create command buffer... //create command buffer...
@ -619,7 +601,7 @@ VKGSRender::VKGSRender() : GSRender()
if (g_cfg.video.overlay) if (g_cfg.video.overlay)
{ {
size_t idx = vk::get_render_pass_location( m_swap_chain->get_surface_format(), VK_FORMAT_UNDEFINED, 1); size_t idx = vk::get_render_pass_location( m_swapchain->get_surface_format(), VK_FORMAT_UNDEFINED, 1);
m_text_writer.reset(new vk::text_writer()); m_text_writer.reset(new vk::text_writer());
m_text_writer->init(*m_device, m_memory_type_mapping, m_render_passes[idx]); m_text_writer->init(*m_device, m_memory_type_mapping, m_render_passes[idx]);
} }
@ -641,25 +623,22 @@ VKGSRender::VKGSRender() : GSRender()
open_command_buffer(); open_command_buffer();
for (u32 i = 0; i < m_swap_chain->get_swap_image_count(); ++i) for (u32 i = 0; i < m_swapchain->get_swap_image_count(); ++i)
{ {
const auto target_layout = m_swapchain->get_optimal_present_layout();
const auto target_image = m_swapchain->get_image(i);
VkClearColorValue clear_color{}; VkClearColorValue clear_color{};
VkImageSubresourceRange range = { VK_IMAGE_ASPECT_COLOR_BIT, 0, 1, 0, 1 }; VkImageSubresourceRange range = { VK_IMAGE_ASPECT_COLOR_BIT, 0, 1, 0, 1 };
vk::change_image_layout(*m_current_command_buffer, m_swap_chain->get_swap_chain_image(i), vk::change_image_layout(*m_current_command_buffer, target_image, VK_IMAGE_LAYOUT_UNDEFINED, VK_IMAGE_LAYOUT_GENERAL, range);
VK_IMAGE_LAYOUT_UNDEFINED, VK_IMAGE_LAYOUT_GENERAL, vkCmdClearColorImage(*m_current_command_buffer, target_image, VK_IMAGE_LAYOUT_GENERAL, &clear_color, 1, &range);
range); vk::change_image_layout(*m_current_command_buffer, target_image, VK_IMAGE_LAYOUT_GENERAL, target_layout, range);
vkCmdClearColorImage(*m_current_command_buffer, m_swap_chain->get_swap_chain_image(i), VK_IMAGE_LAYOUT_GENERAL, &clear_color, 1, &range);
vk::change_image_layout(*m_current_command_buffer, m_swap_chain->get_swap_chain_image(i),
VK_IMAGE_LAYOUT_GENERAL, VK_IMAGE_LAYOUT_PRESENT_SRC_KHR,
range);
} }
m_current_frame = &frame_context_storage[0]; m_current_frame = &frame_context_storage[0];
m_texture_cache.initialize((*m_device), m_memory_type_mapping, m_optimal_tiling_supported_formats, m_swap_chain->get_present_queue(), m_texture_cache.initialize((*m_device), m_memory_type_mapping, m_optimal_tiling_supported_formats, m_swapchain->get_graphics_queue(),
m_texture_upload_buffer_ring_info); m_texture_upload_buffer_ring_info);
m_ui_renderer.reset(new vk::ui_overlay_renderer()); m_ui_renderer.reset(new vk::ui_overlay_renderer());
@ -774,10 +753,8 @@ VKGSRender::~VKGSRender()
m_secondary_command_buffer_pool.destroy(); m_secondary_command_buffer_pool.destroy();
//Device handles/contexts //Device handles/contexts
m_swap_chain->destroy(); m_swapchain->destroy();
m_thread_context.close(); m_thread_context.close();
delete m_swap_chain;
#if !defined(_WIN32) && defined(HAVE_VULKAN) #if !defined(_WIN32) && defined(HAVE_VULKAN)
if (m_display_handle) if (m_display_handle)
@ -790,7 +767,7 @@ bool VKGSRender::on_access_violation(u32 address, bool is_writing)
vk::texture_cache::thrashed_set result; vk::texture_cache::thrashed_set result;
{ {
std::lock_guard<std::mutex> lock(m_secondary_cb_guard); std::lock_guard<std::mutex> lock(m_secondary_cb_guard);
result = std::move(m_texture_cache.invalidate_address(address, is_writing, false, m_secondary_command_buffer, m_memory_type_mapping, m_swap_chain->get_present_queue())); result = std::move(m_texture_cache.invalidate_address(address, is_writing, false, m_secondary_command_buffer, m_memory_type_mapping, m_swapchain->get_graphics_queue()));
} }
if (!result.violation_handled) if (!result.violation_handled)
@ -852,7 +829,7 @@ bool VKGSRender::on_access_violation(u32 address, bool is_writing)
m_flush_requests.producer_wait(); m_flush_requests.producer_wait();
} }
m_texture_cache.flush_all(result, m_secondary_command_buffer, m_memory_type_mapping, m_swap_chain->get_present_queue()); m_texture_cache.flush_all(result, m_secondary_command_buffer, m_memory_type_mapping, m_swapchain->get_graphics_queue());
if (has_queue_ref) if (has_queue_ref)
{ {
@ -868,7 +845,7 @@ void VKGSRender::on_notify_memory_unmapped(u32 address_base, u32 size)
{ {
std::lock_guard<std::mutex> lock(m_secondary_cb_guard); std::lock_guard<std::mutex> lock(m_secondary_cb_guard);
if (m_texture_cache.invalidate_range(address_base, size, true, true, false, if (m_texture_cache.invalidate_range(address_base, size, true, true, false,
m_secondary_command_buffer, m_memory_type_mapping, m_swap_chain->get_present_queue()).violation_handled) m_secondary_command_buffer, m_memory_type_mapping, m_swapchain->get_graphics_queue()).violation_handled)
{ {
m_texture_cache.purge_dirty(); m_texture_cache.purge_dirty();
{ {
@ -1809,7 +1786,7 @@ void VKGSRender::copy_render_targets_to_dma_location()
continue; continue;
m_texture_cache.flush_memory_to_cache(m_surface_info[index].address, m_surface_info[index].pitch * m_surface_info[index].height, true, m_texture_cache.flush_memory_to_cache(m_surface_info[index].address, m_surface_info[index].pitch * m_surface_info[index].height, true,
*m_current_command_buffer, m_memory_type_mapping, m_swap_chain->get_present_queue()); *m_current_command_buffer, m_memory_type_mapping, m_swapchain->get_graphics_queue());
} }
} }
@ -1818,7 +1795,7 @@ void VKGSRender::copy_render_targets_to_dma_location()
if (m_depth_surface_info.pitch) if (m_depth_surface_info.pitch)
{ {
m_texture_cache.flush_memory_to_cache(m_depth_surface_info.address, m_depth_surface_info.pitch * m_depth_surface_info.height, true, m_texture_cache.flush_memory_to_cache(m_depth_surface_info.address, m_depth_surface_info.pitch * m_depth_surface_info.height, true,
*m_current_command_buffer, m_memory_type_mapping, m_swap_chain->get_present_queue()); *m_current_command_buffer, m_memory_type_mapping, m_swapchain->get_graphics_queue());
} }
} }
@ -1927,18 +1904,10 @@ void VKGSRender::advance_queued_frames()
void VKGSRender::present(frame_context_t *ctx) void VKGSRender::present(frame_context_t *ctx)
{ {
verify(HERE), ctx->present_image != UINT32_MAX; verify(HERE), ctx->present_image != UINT32_MAX;
VkSwapchainKHR swap_chain = (VkSwapchainKHR)(*m_swap_chain);
if (!present_surface_dirty_flag) if (!present_surface_dirty_flag)
{ {
VkPresentInfoKHR present = {}; switch (VkResult error = m_swapchain->present(ctx->present_image))
present.sType = VK_STRUCTURE_TYPE_PRESENT_INFO_KHR;
present.pNext = nullptr;
present.swapchainCount = 1;
present.pSwapchains = &swap_chain;
present.pImageIndices = &ctx->present_image;
switch (VkResult error = m_swap_chain->queuePresentKHR(m_swap_chain->get_present_queue(), &present))
{ {
case VK_SUCCESS: case VK_SUCCESS:
case VK_SUBOPTIMAL_KHR: case VK_SUBOPTIMAL_KHR:
@ -1968,7 +1937,17 @@ void VKGSRender::queue_swap_request()
} }
m_current_frame->swap_command_buffer = m_current_command_buffer; m_current_frame->swap_command_buffer = m_current_command_buffer;
close_and_submit_command_buffer({ m_current_frame->present_semaphore }, m_current_command_buffer->submit_fence);
if (m_swapchain->is_headless())
{
m_swapchain->end_frame(*m_current_command_buffer, m_current_frame->present_image);
close_and_submit_command_buffer({}, m_current_command_buffer->submit_fence);
}
else
{
close_and_submit_command_buffer({ m_current_frame->present_semaphore }, m_current_command_buffer->submit_fence);
}
m_current_frame->swap_command_buffer->pending = true; m_current_frame->swap_command_buffer->pending = true;
//Grab next cb in line and make it usable //Grab next cb in line and make it usable
@ -2462,7 +2441,7 @@ void VKGSRender::close_and_submit_command_buffer(const std::vector<VkSemaphore>
{ {
m_current_command_buffer->end(); m_current_command_buffer->end();
m_current_command_buffer->tag(); m_current_command_buffer->tag();
m_current_command_buffer->submit(m_swap_chain->get_present_queue(), semaphores, fence, pipeline_stage_flags); m_current_command_buffer->submit(m_swapchain->get_graphics_queue(), semaphores, fence, pipeline_stage_flags);
} }
void VKGSRender::open_command_buffer() void VKGSRender::open_command_buffer()
@ -2654,7 +2633,7 @@ void VKGSRender::prepare_rtts(rsx::framebuffer_creation_context context)
m_texture_cache.set_memory_read_flags(m_surface_info[i].address, m_surface_info[i].pitch * m_surface_info[i].height, rsx::memory_read_flags::flush_once); m_texture_cache.set_memory_read_flags(m_surface_info[i].address, m_surface_info[i].pitch * m_surface_info[i].height, rsx::memory_read_flags::flush_once);
m_texture_cache.flush_if_cache_miss_likely(old_format, m_surface_info[i].address, m_surface_info[i].pitch * m_surface_info[i].height, m_texture_cache.flush_if_cache_miss_likely(old_format, m_surface_info[i].address, m_surface_info[i].pitch * m_surface_info[i].height,
*m_current_command_buffer, m_memory_type_mapping, m_swap_chain->get_present_queue()); *m_current_command_buffer, m_memory_type_mapping, m_swapchain->get_graphics_queue());
} }
m_surface_info[i].address = m_surface_info[i].pitch = 0; m_surface_info[i].address = m_surface_info[i].pitch = 0;
@ -2670,7 +2649,7 @@ void VKGSRender::prepare_rtts(rsx::framebuffer_creation_context context)
auto old_format = vk::get_compatible_depth_surface_format(m_optimal_tiling_supported_formats, m_depth_surface_info.depth_format); auto old_format = vk::get_compatible_depth_surface_format(m_optimal_tiling_supported_formats, m_depth_surface_info.depth_format);
m_texture_cache.set_memory_read_flags(m_depth_surface_info.address, m_depth_surface_info.pitch * m_depth_surface_info.height, rsx::memory_read_flags::flush_once); m_texture_cache.set_memory_read_flags(m_depth_surface_info.address, m_depth_surface_info.pitch * m_depth_surface_info.height, rsx::memory_read_flags::flush_once);
m_texture_cache.flush_if_cache_miss_likely(old_format, m_depth_surface_info.address, m_depth_surface_info.pitch * m_depth_surface_info.height, m_texture_cache.flush_if_cache_miss_likely(old_format, m_depth_surface_info.address, m_depth_surface_info.pitch * m_depth_surface_info.height,
*m_current_command_buffer, m_memory_type_mapping, m_swap_chain->get_present_queue()); *m_current_command_buffer, m_memory_type_mapping, m_swapchain->get_graphics_queue());
} }
m_depth_surface_info.address = m_depth_surface_info.pitch = 0; m_depth_surface_info.address = m_depth_surface_info.pitch = 0;
@ -2847,14 +2826,14 @@ void VKGSRender::reinitialize_swapchain()
present(&ctx); present(&ctx);
} }
vkQueueWaitIdle(m_swap_chain->get_present_queue()); //Wait for completion
vkDeviceWaitIdle(*m_device); vkDeviceWaitIdle(*m_device);
//Remove any old refs to the old images as they are about to be destroyed //Remove any old refs to the old images as they are about to be destroyed
m_framebuffers_to_clean.clear(); m_framebuffers_to_clean.clear();
//Rebuild swapchain. Old swapchain destruction is handled by the init_swapchain call //Rebuild swapchain. Old swapchain destruction is handled by the init_swapchain call
if (!m_swap_chain->init_swapchain(new_width, new_height)) if (!m_swapchain->init(new_width, new_height))
{ {
LOG_WARNING(RSX, "Swapchain initialization failed. Request ignored [%dx%d]", new_width, new_height); LOG_WARNING(RSX, "Swapchain initialization failed. Request ignored [%dx%d]", new_width, new_height);
present_surface_dirty_flag = true; present_surface_dirty_flag = true;
@ -2869,18 +2848,16 @@ void VKGSRender::reinitialize_swapchain()
//Prepare new swapchain images for use //Prepare new swapchain images for use
open_command_buffer(); open_command_buffer();
for (u32 i = 0; i < m_swap_chain->get_swap_image_count(); ++i) for (u32 i = 0; i < m_swapchain->get_swap_image_count(); ++i)
{ {
vk::change_image_layout(*m_current_command_buffer, m_swap_chain->get_swap_chain_image(i), const auto target_layout = m_swapchain->get_optimal_present_layout();
VK_IMAGE_LAYOUT_UNDEFINED, VK_IMAGE_LAYOUT_GENERAL, const auto target_image = m_swapchain->get_image(i);
{ VK_IMAGE_ASPECT_COLOR_BIT, 0, 1, 0, 1 });
VkClearColorValue clear_color{}; VkClearColorValue clear_color{};
auto range = vk::get_image_subresource_range(0, 0, 1, 1, VK_IMAGE_ASPECT_COLOR_BIT); VkImageSubresourceRange range = {VK_IMAGE_ASPECT_COLOR_BIT, 0, 1, 0, 1};
vkCmdClearColorImage(*m_current_command_buffer, m_swap_chain->get_swap_chain_image(i), VK_IMAGE_LAYOUT_GENERAL, &clear_color, 1, &range);
vk::change_image_layout(*m_current_command_buffer, m_swap_chain->get_swap_chain_image(i), vk::change_image_layout(*m_current_command_buffer, target_image, VK_IMAGE_LAYOUT_UNDEFINED, VK_IMAGE_LAYOUT_GENERAL, range);
VK_IMAGE_LAYOUT_GENERAL, VK_IMAGE_LAYOUT_PRESENT_SRC_KHR, vkCmdClearColorImage(*m_current_command_buffer, target_image, VK_IMAGE_LAYOUT_GENERAL, &clear_color, 1, &range);
{ VK_IMAGE_ASPECT_COLOR_BIT, 0, 1, 0, 1 }); vk::change_image_layout(*m_current_command_buffer, target_image, VK_IMAGE_LAYOUT_GENERAL, target_layout, range);
} }
//Will have to block until rendering is completed //Will have to block until rendering is completed
@ -2989,8 +2966,9 @@ void VKGSRender::flip(int buffer)
//Prepare surface for new frame. Set no timeout here so that we wait for the next image if need be //Prepare surface for new frame. Set no timeout here so that we wait for the next image if need be
verify(HERE), m_current_frame->present_image == UINT32_MAX; verify(HERE), m_current_frame->present_image == UINT32_MAX;
u64 timeout = m_swap_chain->get_swap_image_count() <= VK_MAX_ASYNC_FRAMES? 0ull: 100000000ull;
while (VkResult status = vkAcquireNextImageKHR((*m_device), (*m_swap_chain), timeout, m_current_frame->present_semaphore, VK_NULL_HANDLE, &m_current_frame->present_image)) u64 timeout = m_swapchain->get_swap_image_count() <= VK_MAX_ASYNC_FRAMES? 0ull: 100000000ull;
while (VkResult status = m_swapchain->acquire_next_swapchain_image(m_current_frame->present_semaphore, timeout, &m_current_frame->present_image))
{ {
switch (status) switch (status)
{ {
@ -3053,16 +3031,18 @@ void VKGSRender::flip(int buffer)
} }
} }
VkImage target_image = m_swap_chain->get_swap_chain_image(m_current_frame->present_image); VkImage target_image = m_swapchain->get_image(m_current_frame->present_image);
const auto present_layout = m_swapchain->get_optimal_present_layout();
if (image_to_flip) if (image_to_flip)
{ {
VkImageLayout target_layout = VK_IMAGE_LAYOUT_PRESENT_SRC_KHR; VkImageLayout target_layout = present_layout;
VkImageSubresourceRange range = { VK_IMAGE_ASPECT_COLOR_BIT, 0, 1, 0, 1 }; VkImageSubresourceRange range = { VK_IMAGE_ASPECT_COLOR_BIT, 0, 1, 0, 1 };
if (aspect_ratio.x || aspect_ratio.y) if (aspect_ratio.x || aspect_ratio.y)
{ {
VkClearColorValue clear_black {}; VkClearColorValue clear_black {};
vk::change_image_layout(*m_current_command_buffer, target_image, VK_IMAGE_LAYOUT_PRESENT_SRC_KHR, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, range); vk::change_image_layout(*m_current_command_buffer, target_image, present_layout, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, range);
vkCmdClearColorImage(*m_current_command_buffer, target_image, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, &clear_black, 1, &range); vkCmdClearColorImage(*m_current_command_buffer, target_image, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, &clear_black, 1, &range);
target_layout = VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL; target_layout = VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL;
@ -3071,9 +3051,9 @@ void VKGSRender::flip(int buffer)
vk::copy_scaled_image(*m_current_command_buffer, image_to_flip->value, target_image, image_to_flip->current_layout, target_layout, vk::copy_scaled_image(*m_current_command_buffer, image_to_flip->value, target_image, image_to_flip->current_layout, target_layout,
0, 0, image_to_flip->width(), image_to_flip->height(), aspect_ratio.x, aspect_ratio.y, aspect_ratio.width, aspect_ratio.height, 1, VK_IMAGE_ASPECT_COLOR_BIT, false); 0, 0, image_to_flip->width(), image_to_flip->height(), aspect_ratio.x, aspect_ratio.y, aspect_ratio.width, aspect_ratio.height, 1, VK_IMAGE_ASPECT_COLOR_BIT, false);
if (target_layout != VK_IMAGE_LAYOUT_PRESENT_SRC_KHR) if (target_layout != present_layout)
{ {
vk::change_image_layout(*m_current_command_buffer, target_image, target_layout, VK_IMAGE_LAYOUT_PRESENT_SRC_KHR, range); vk::change_image_layout(*m_current_command_buffer, target_image, target_layout, present_layout, range);
} }
} }
else else
@ -3082,9 +3062,9 @@ void VKGSRender::flip(int buffer)
//TODO: Upload raw bytes from cpu for rendering //TODO: Upload raw bytes from cpu for rendering
VkImageSubresourceRange range = { VK_IMAGE_ASPECT_COLOR_BIT, 0, 1, 0, 1 }; VkImageSubresourceRange range = { VK_IMAGE_ASPECT_COLOR_BIT, 0, 1, 0, 1 };
VkClearColorValue clear_black {}; VkClearColorValue clear_black {};
vk::change_image_layout(*m_current_command_buffer, m_swap_chain->get_swap_chain_image(m_current_frame->present_image), VK_IMAGE_LAYOUT_PRESENT_SRC_KHR, VK_IMAGE_LAYOUT_GENERAL, range); vk::change_image_layout(*m_current_command_buffer, m_swapchain->get_image(m_current_frame->present_image), present_layout, VK_IMAGE_LAYOUT_GENERAL, range);
vkCmdClearColorImage(*m_current_command_buffer, m_swap_chain->get_swap_chain_image(m_current_frame->present_image), VK_IMAGE_LAYOUT_GENERAL, &clear_black, 1, &range); vkCmdClearColorImage(*m_current_command_buffer, m_swapchain->get_image(m_current_frame->present_image), VK_IMAGE_LAYOUT_GENERAL, &clear_black, 1, &range);
vk::change_image_layout(*m_current_command_buffer, m_swap_chain->get_swap_chain_image(m_current_frame->present_image), VK_IMAGE_LAYOUT_GENERAL, VK_IMAGE_LAYOUT_PRESENT_SRC_KHR, range); vk::change_image_layout(*m_current_command_buffer, m_swapchain->get_image(m_current_frame->present_image), VK_IMAGE_LAYOUT_GENERAL, present_layout, range);
} }
std::unique_ptr<vk::framebuffer_holder> direct_fbo; std::unique_ptr<vk::framebuffer_holder> direct_fbo;
@ -3096,7 +3076,7 @@ void VKGSRender::flip(int buffer)
VkImageMemoryBarrier barrier = {}; VkImageMemoryBarrier barrier = {};
barrier.sType = VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER; barrier.sType = VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER;
barrier.newLayout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL; barrier.newLayout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL;
barrier.oldLayout = VK_IMAGE_LAYOUT_PRESENT_SRC_KHR; barrier.oldLayout = present_layout;
barrier.image = target_image; barrier.image = target_image;
barrier.srcAccessMask = VK_ACCESS_TRANSFER_WRITE_BIT; barrier.srcAccessMask = VK_ACCESS_TRANSFER_WRITE_BIT;
barrier.dstAccessMask = VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT; barrier.dstAccessMask = VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT;
@ -3106,7 +3086,7 @@ void VKGSRender::flip(int buffer)
vkCmdPipelineBarrier(*m_current_command_buffer, VK_PIPELINE_STAGE_TRANSFER_BIT, VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT, VK_DEPENDENCY_BY_REGION_BIT, 0, nullptr, 0, nullptr, 1, &barrier); vkCmdPipelineBarrier(*m_current_command_buffer, VK_PIPELINE_STAGE_TRANSFER_BIT, VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT, VK_DEPENDENCY_BY_REGION_BIT, 0, nullptr, 0, nullptr, 1, &barrier);
size_t idx = vk::get_render_pass_location(m_swap_chain->get_surface_format(), VK_FORMAT_UNDEFINED, 1); size_t idx = vk::get_render_pass_location(m_swapchain->get_surface_format(), VK_FORMAT_UNDEFINED, 1);
VkRenderPass single_target_pass = m_render_passes[idx]; VkRenderPass single_target_pass = m_render_passes[idx];
for (auto It = m_framebuffers_to_clean.begin(); It != m_framebuffers_to_clean.end(); It++) for (auto It = m_framebuffers_to_clean.begin(); It != m_framebuffers_to_clean.end(); It++)
@ -3123,7 +3103,7 @@ void VKGSRender::flip(int buffer)
if (!direct_fbo) if (!direct_fbo)
{ {
swap_image_view.push_back(std::make_unique<vk::image_view>(*m_device, target_image, VK_IMAGE_VIEW_TYPE_2D, m_swap_chain->get_surface_format(), vk::default_component_map(), subres)); swap_image_view.push_back(std::make_unique<vk::image_view>(*m_device, target_image, VK_IMAGE_VIEW_TYPE_2D, m_swapchain->get_surface_format(), vk::default_component_map(), subres));
direct_fbo.reset(new vk::framebuffer_holder(*m_device, single_target_pass, m_client_width, m_client_height, std::move(swap_image_view))); direct_fbo.reset(new vk::framebuffer_holder(*m_device, single_target_pass, m_client_width, m_client_height, std::move(swap_image_view)));
} }
@ -3152,7 +3132,7 @@ void VKGSRender::flip(int buffer)
m_text_writer->print_text(*m_current_command_buffer, *direct_fbo, 0, 180, direct_fbo->width(), direct_fbo->height(), "Flush requests: " + std::to_string(num_flushes) + " (" + std::to_string(cache_miss_ratio) + "% hard faults)"); m_text_writer->print_text(*m_current_command_buffer, *direct_fbo, 0, 180, direct_fbo->width(), direct_fbo->height(), "Flush requests: " + std::to_string(num_flushes) + " (" + std::to_string(cache_miss_ratio) + "% hard faults)");
} }
vk::change_image_layout(*m_current_command_buffer, target_image, VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL, VK_IMAGE_LAYOUT_PRESENT_SRC_KHR, subres); vk::change_image_layout(*m_current_command_buffer, target_image, VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL, present_layout, subres);
m_framebuffers_to_clean.push_back(std::move(direct_fbo)); m_framebuffers_to_clean.push_back(std::move(direct_fbo));
} }
@ -3217,7 +3197,7 @@ bool VKGSRender::scaled_image_from_memory(rsx::blit_src_info& src, rsx::blit_dst
if (result.dst_image) if (result.dst_image)
{ {
if (m_texture_cache.flush_if_cache_miss_likely(result.dst_image->info.format, result.real_dst_address, result.real_dst_size, if (m_texture_cache.flush_if_cache_miss_likely(result.dst_image->info.format, result.real_dst_address, result.real_dst_size,
*m_current_command_buffer, m_memory_type_mapping, m_swap_chain->get_present_queue())) *m_current_command_buffer, m_memory_type_mapping, m_swapchain->get_graphics_queue()))
require_flush = true; require_flush = true;
} }

View File

@ -238,9 +238,7 @@ class VKGSRender : public GSRender
private: private:
VKFragmentProgram m_fragment_prog; VKFragmentProgram m_fragment_prog;
VKVertexProgram m_vertex_prog; VKVertexProgram m_vertex_prog;
vk::glsl::program *m_program; vk::glsl::program *m_program;
vk::context m_thread_context;
vk::texture_cache m_texture_cache; vk::texture_cache m_texture_cache;
rsx::vk_render_targets m_rtts; rsx::vk_render_targets m_rtts;
@ -275,8 +273,9 @@ public:
private: private:
std::unique_ptr<VKProgramBuffer> m_prog_buffer; std::unique_ptr<VKProgramBuffer> m_prog_buffer;
std::unique_ptr<vk::swapchain_base> m_swapchain;
vk::context m_thread_context;
vk::render_device *m_device; vk::render_device *m_device;
vk::swap_chain* m_swap_chain;
//Vulkan internals //Vulkan internals
vk::command_pool m_command_buffer_pool; vk::command_pool m_command_buffer_pool;

View File

@ -56,10 +56,10 @@ namespace vk
#endif #endif
} }
memory_type_mapping get_memory_mapping(VkPhysicalDevice pdev) memory_type_mapping get_memory_mapping(const vk::physical_device& dev)
{ {
VkPhysicalDeviceMemoryProperties memory_properties; VkPhysicalDeviceMemoryProperties memory_properties;
vkGetPhysicalDeviceMemoryProperties(pdev, &memory_properties); vkGetPhysicalDeviceMemoryProperties((VkPhysicalDevice&)dev, &memory_properties);
memory_type_mapping result; memory_type_mapping result;
result.device_local = VK_MAX_MEMORY_TYPES; result.device_local = VK_MAX_MEMORY_TYPES;

File diff suppressed because it is too large Load Diff

View File

@ -195,7 +195,7 @@
<WarningLevel>Level3</WarningLevel> <WarningLevel>Level3</WarningLevel>
</ClCompile> </ClCompile>
<Link> <Link>
<AdditionalDependencies>..\hidapi.lib;winmm.lib;OpenAL.lib;XAudio.lib;D3D12GSRender.lib;GLGSRender.lib;shlwapi.lib;VKGSRender.lib;VKstatic.1.lib;glslang.lib;OSDependent.lib;OGLCompiler.lib;SPIRV.lib;HLSL.lib;Advapi32.lib;user32.lib;zlib.lib;..\libpng.lib;asmjit.lib;yaml-cpp.lib;emucore.lib;dxgi.lib;$(QTDIR)\lib\qtmain.lib;shell32.lib;opengl32.lib;$(QTDIR)\lib\Qt5OpenGL.lib;$(QTDIR)\lib\Qt5Widgets.lib;$(QTDIR)\lib\Qt5Quick.lib;$(QTDIR)\lib\Qt5Gui.lib;$(QTDIR)\lib\Qt5Qml.lib;$(QTDIR)\lib\Qt5Network.lib;$(QTDIR)\lib\Qt5Core.lib;Qt5Core.lib;Qt5Gui.lib;Qt5Widgets.lib;Qt5WinExtras.lib;%(AdditionalDependencies)</AdditionalDependencies> <AdditionalDependencies>gdi32.lib;..\hidapi.lib;winmm.lib;OpenAL.lib;XAudio.lib;D3D12GSRender.lib;GLGSRender.lib;shlwapi.lib;VKGSRender.lib;VKstatic.1.lib;glslang.lib;OSDependent.lib;OGLCompiler.lib;SPIRV.lib;HLSL.lib;Advapi32.lib;user32.lib;zlib.lib;..\libpng.lib;asmjit.lib;yaml-cpp.lib;emucore.lib;dxgi.lib;$(QTDIR)\lib\qtmain.lib;shell32.lib;opengl32.lib;$(QTDIR)\lib\Qt5OpenGL.lib;$(QTDIR)\lib\Qt5Widgets.lib;$(QTDIR)\lib\Qt5Quick.lib;$(QTDIR)\lib\Qt5Gui.lib;$(QTDIR)\lib\Qt5Qml.lib;$(QTDIR)\lib\Qt5Network.lib;$(QTDIR)\lib\Qt5Core.lib;Qt5Core.lib;Qt5Gui.lib;Qt5Widgets.lib;Qt5WinExtras.lib;%(AdditionalDependencies)</AdditionalDependencies>
<AdditionalLibraryDirectories>..\3rdparty\OpenAL\libs\Win64;..\Vulkan\glslang-build\hlsl\Release;..\Vulkan\glslang-build\SPIRV\Release;..\Vulkan\glslang-build\OGLCompilersDLL\Release;..\Vulkan\glslang-build\glslang\OSDependent\Windows\Release;..\Vulkan\Vulkan-build\loader\Release;..\Vulkan\glslang-build\glslang\Release;..\lib\$(CONFIGURATION)-$(PLATFORM);..\3rdparty\minidx12\Lib;$(QTDIR)\lib;%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories> <AdditionalLibraryDirectories>..\3rdparty\OpenAL\libs\Win64;..\Vulkan\glslang-build\hlsl\Release;..\Vulkan\glslang-build\SPIRV\Release;..\Vulkan\glslang-build\OGLCompilersDLL\Release;..\Vulkan\glslang-build\glslang\OSDependent\Windows\Release;..\Vulkan\Vulkan-build\loader\Release;..\Vulkan\glslang-build\glslang\Release;..\lib\$(CONFIGURATION)-$(PLATFORM);..\3rdparty\minidx12\Lib;$(QTDIR)\lib;%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
<AdditionalOptions>"/MANIFESTDEPENDENCY:type='win32' name='Microsoft.Windows.Common-Controls' version='6.0.0.0' publicKeyToken='6595b64144ccf1df' language='*' processorArchitecture='*'" %(AdditionalOptions)</AdditionalOptions> <AdditionalOptions>"/MANIFESTDEPENDENCY:type='win32' name='Microsoft.Windows.Common-Controls' version='6.0.0.0' publicKeyToken='6595b64144ccf1df' language='*' processorArchitecture='*'" %(AdditionalOptions)</AdditionalOptions>
<DataExecutionPrevention>true</DataExecutionPrevention> <DataExecutionPrevention>true</DataExecutionPrevention>