mirror of
https://github.com/RPCS3/rpcs3.git
synced 2025-07-04 14:01:25 +12:00
vulkan bringup on linux
cleanup: drop unused stuff
This commit is contained in:
parent
6cb7a17814
commit
860b76452f
21 changed files with 205 additions and 1613 deletions
|
@ -46,7 +46,6 @@ set(CMAKE_RUNTIME_OUTPUT_DIRECTORY_RELEASE "${PROJECT_BINARY_DIR}/bin")
|
||||||
set(CMAKE_RUNTIME_OUTPUT_DIRECTORY_DEBUG "${PROJECT_BINARY_DIR}/bin")
|
set(CMAKE_RUNTIME_OUTPUT_DIRECTORY_DEBUG "${PROJECT_BINARY_DIR}/bin")
|
||||||
add_subdirectory( Vulkan )
|
add_subdirectory( Vulkan )
|
||||||
add_subdirectory( rpcs3 )
|
add_subdirectory( rpcs3 )
|
||||||
add_subdirectory( rsx_program_decompiler )
|
|
||||||
|
|
||||||
include_directories(3rdparty/hidapi/hidapi)
|
include_directories(3rdparty/hidapi/hidapi)
|
||||||
if(APPLE)
|
if(APPLE)
|
||||||
|
|
|
@ -155,16 +155,13 @@ ${LLVM_INCLUDE_DIRS}
|
||||||
"${RPCS3_SRC_DIR}/../Utilities/yaml-cpp/include"
|
"${RPCS3_SRC_DIR}/../Utilities/yaml-cpp/include"
|
||||||
"${RPCS3_SRC_DIR}/../asmjit/src/asmjit"
|
"${RPCS3_SRC_DIR}/../asmjit/src/asmjit"
|
||||||
"${RPCS3_SRC_DIR}/../3rdparty/GSL/include"
|
"${RPCS3_SRC_DIR}/../3rdparty/GSL/include"
|
||||||
"${RPCS3_SRC_DIR}/../rsx_program_decompiler/rsx_decompiler"
|
|
||||||
"${RPCS3_SRC_DIR}/../rsx_program_decompiler/shader_code"
|
|
||||||
"${RPCS3_SRC_DIR}/../Vulkan/Vulkan-LoaderAndValidationLayers/include"
|
"${RPCS3_SRC_DIR}/../Vulkan/Vulkan-LoaderAndValidationLayers/include"
|
||||||
"${RPCS3_SRC_DIR}/../Vulkan/glslang/glslang/Public"
|
"${RPCS3_SRC_DIR}/../Vulkan/glslang/glslang/Public"
|
||||||
|
"${RPCS3_SRC_DIR}/../Vulkan/glslang/"
|
||||||
"${RPCS3_SRC_DIR}/../3rdparty/hidapi/hidapi"
|
"${RPCS3_SRC_DIR}/../3rdparty/hidapi/hidapi"
|
||||||
# Includes 3rdparty stuff that isn't included yet
|
# Includes 3rdparty stuff that isn't included yet
|
||||||
"${RPCS3_SRC_DIR}/../3rdparty/GL"
|
"${RPCS3_SRC_DIR}/../3rdparty/GL"
|
||||||
"${RPCS3_SRC_DIR}/../3rdparty/stblib"
|
"${RPCS3_SRC_DIR}/../3rdparty/stblib"
|
||||||
"${RPCS3_SRC_DIR}/../rsx_program_decompiler/rsx_decompiler"
|
|
||||||
"${RPCS3_SRC_DIR}/../rsx_program_decompiler/shader_code"
|
|
||||||
"${RPCS3_SRC_DIR}/../3rdparty/cereal/include"
|
"${RPCS3_SRC_DIR}/../3rdparty/cereal/include"
|
||||||
)
|
)
|
||||||
if(WIN32)
|
if(WIN32)
|
||||||
|
@ -217,20 +214,33 @@ GLOB_RECURSE
|
||||||
RPCS3_SRC
|
RPCS3_SRC
|
||||||
"${RPCS3_SRC_DIR}/*.cpp"
|
"${RPCS3_SRC_DIR}/*.cpp"
|
||||||
"${RPCS3_SRC_DIR}/../Utilities/*.cpp"
|
"${RPCS3_SRC_DIR}/../Utilities/*.cpp"
|
||||||
"${RPCS3_SRC_DIR}/../rsx_program_decompiler/rsx_decompiler/*.cpp"
|
|
||||||
"${RPCS3_SRC_DIR}/../rsx_program_decompiler/shader_code/*.cpp"
|
|
||||||
"${RPCS3_SRC_DIR}/../asmjit/src/asmjit/*.cpp"
|
"${RPCS3_SRC_DIR}/../asmjit/src/asmjit/*.cpp"
|
||||||
|
"${RPCS3_SRC_DIR}/../Vulkan/glslang/glslang/GenericCodeGen/*.cpp"
|
||||||
|
"${RPCS3_SRC_DIR}/../Vulkan/glslang/glslang/MachineIndependent/*.cpp"
|
||||||
|
"${RPCS3_SRC_DIR}/../Vulkan/glslang/glslang/OSDependent/Unix/*.cpp"
|
||||||
|
"${RPCS3_SRC_DIR}/../Vulkan/glslang/OGLCompilersDLL/*.cpp"
|
||||||
|
"${RPCS3_SRC_DIR}/../Vulkan/glslang/hlsl/*.cpp"
|
||||||
|
"${RPCS3_SRC_DIR}/../Vulkan/glslang/SPIRV/*.cpp"
|
||||||
)
|
)
|
||||||
|
|
||||||
if(NOT WIN32)
|
#File exclusion section
|
||||||
set (EXCLUDE_DIR "/RSX/VK/")
|
|
||||||
foreach (TMP_PATH ${RPCS3_SRC})
|
#Ignore vulkan if not on windows or linux
|
||||||
string (FIND ${TMP_PATH} ${EXCLUDE_DIR} EXCLUDE_DIR_FOUND)
|
if(NOT WIN32 AND NOT "${CMAKE_SYSTEM}" MATCHES "Linux")
|
||||||
if (NOT ${EXCLUDE_DIR_FOUND} EQUAL -1)
|
set (EXCLUDE_FILES "/RSX/VK/")
|
||||||
|
endif()
|
||||||
|
|
||||||
|
#Do not compile the Qt moc files, they are compiled when generating automoc
|
||||||
|
set (EXCLUDE_FILES ${EXLUDE_FILES} "moc_")
|
||||||
|
|
||||||
|
foreach (TMP_PATH ${RPCS3_SRC})
|
||||||
|
foreach (EXCLUDE_PATH ${EXCLUDE_FILES})
|
||||||
|
string (FIND ${TMP_PATH} ${EXCLUDE_PATH} EXCLUDE_FILE_FOUND)
|
||||||
|
if (NOT ${EXCLUDE_FILE_FOUND} EQUAL -1)
|
||||||
list (REMOVE_ITEM RPCS3_SRC ${TMP_PATH})
|
list (REMOVE_ITEM RPCS3_SRC ${TMP_PATH})
|
||||||
endif ()
|
endif ()
|
||||||
endforeach(TMP_PATH)
|
endforeach(EXCLUDE_PATH)
|
||||||
endif()
|
endforeach(TMP_PATH)
|
||||||
|
|
||||||
# The Gui folder contains wxWidgets stuff, which we no longer want.
|
# The Gui folder contains wxWidgets stuff, which we no longer want.
|
||||||
foreach (TMP_PATH ${RPCS3_SRC})
|
foreach (TMP_PATH ${RPCS3_SRC})
|
||||||
|
@ -261,10 +271,8 @@ if(WIN32)
|
||||||
endif()
|
endif()
|
||||||
target_link_libraries(rpcs3 avformat.lib avcodec.lib avutil.lib swresample.lib swscale.lib png16_static ${OPENAL_LIBRARY} ${ADDITIONAL_LIBS})
|
target_link_libraries(rpcs3 avformat.lib avcodec.lib avutil.lib swresample.lib swscale.lib png16_static ${OPENAL_LIBRARY} ${ADDITIONAL_LIBS})
|
||||||
else()
|
else()
|
||||||
|
|
||||||
target_link_libraries(rpcs3 ${OPENAL_LIBRARY} ${GLEW_LIBRARY} ${OPENGL_LIBRARIES} hidapi-hidraw udev)
|
target_link_libraries(rpcs3 ${OPENAL_LIBRARY} ${GLEW_LIBRARY} ${OPENGL_LIBRARIES} hidapi-hidraw udev)
|
||||||
target_link_libraries(rpcs3 -ldl -latomic -lpthread ${ZLIB_LIBRARIES} ${ADDITIONAL_LIBS})
|
target_link_libraries(rpcs3 -ldl -latomic -lpthread -lvulkan ${ZLIB_LIBRARIES} ${ADDITIONAL_LIBS})
|
||||||
|
|
||||||
if (USE_SYSTEM_FFMPEG)
|
if (USE_SYSTEM_FFMPEG)
|
||||||
link_libraries(${FFMPEG_LIBRARY_DIR})
|
link_libraries(${FFMPEG_LIBRARY_DIR})
|
||||||
target_link_libraries(rpcs3 libavformat.so libavcodec.so libavutil.so libswresample.so libswscale.so)
|
target_link_libraries(rpcs3 libavformat.so libavcodec.so libavutil.so libswresample.so libswscale.so)
|
||||||
|
@ -281,8 +289,6 @@ if(LLVM_FOUND)
|
||||||
target_link_libraries(rpcs3 ${LLVM_LIBS})
|
target_link_libraries(rpcs3 ${LLVM_LIBS})
|
||||||
endif()
|
endif()
|
||||||
|
|
||||||
target_link_libraries(rpcs3 rsx_decompiler shader_code)
|
|
||||||
|
|
||||||
set_target_properties(rpcs3 PROPERTIES COTIRE_CXX_PREFIX_HEADER_INIT "${RPCS3_SRC_DIR}/stdafx.h")
|
set_target_properties(rpcs3 PROPERTIES COTIRE_CXX_PREFIX_HEADER_INIT "${RPCS3_SRC_DIR}/stdafx.h")
|
||||||
cotire(rpcs3)
|
cotire(rpcs3)
|
||||||
|
|
||||||
|
|
|
@ -24,7 +24,8 @@ namespace
|
||||||
|
|
||||||
GLGSRender::GLGSRender() : GSRender()
|
GLGSRender::GLGSRender() : GSRender()
|
||||||
{
|
{
|
||||||
shaders_cache.load(rsx::old_shaders_cache::shader_language::glsl);
|
//TODO
|
||||||
|
//shaders_cache.load(rsx::old_shaders_cache::shader_language::glsl);
|
||||||
}
|
}
|
||||||
|
|
||||||
u32 GLGSRender::enable(u32 condition, u32 cap)
|
u32 GLGSRender::enable(u32 condition, u32 cap)
|
||||||
|
|
|
@ -27,51 +27,7 @@ namespace rsx
|
||||||
{
|
{
|
||||||
std::function<bool(u32 addr, bool is_writing)> g_access_violation_handler;
|
std::function<bool(u32 addr, bool is_writing)> g_access_violation_handler;
|
||||||
|
|
||||||
void old_shaders_cache::shaders_cache::load(const std::string &path, shader_language lang)
|
//TODO: Restore a working shaders cache
|
||||||
{
|
|
||||||
const std::string lang_name(lang == shader_language::glsl ? "glsl" : "hlsl");
|
|
||||||
|
|
||||||
auto extract_hash = [](const std::string &string)
|
|
||||||
{
|
|
||||||
return std::stoull(string.substr(0, string.find('.')).c_str(), 0, 16);
|
|
||||||
};
|
|
||||||
|
|
||||||
for (const auto& entry : fs::dir(path))
|
|
||||||
{
|
|
||||||
if (entry.name == "." || entry.name == "..")
|
|
||||||
continue;
|
|
||||||
|
|
||||||
u64 hash;
|
|
||||||
|
|
||||||
try
|
|
||||||
{
|
|
||||||
hash = extract_hash(entry.name);
|
|
||||||
}
|
|
||||||
catch (...)
|
|
||||||
{
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (fmt::match(entry.name, "*.fs." + lang_name))
|
|
||||||
{
|
|
||||||
fs::file file{ path + entry.name };
|
|
||||||
decompiled_fragment_shaders.insert(hash, { file.to_string() });
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (fmt::match(entry.name, "*.vs." + lang_name))
|
|
||||||
{
|
|
||||||
fs::file file{ path + entry.name };
|
|
||||||
decompiled_vertex_shaders.insert(hash, { file.to_string() });
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void old_shaders_cache::shaders_cache::load(shader_language lang)
|
|
||||||
{
|
|
||||||
load(Emu.GetCachePath(), lang);
|
|
||||||
}
|
|
||||||
|
|
||||||
u32 get_address(u32 offset, u32 location)
|
u32 get_address(u32 offset, u32 location)
|
||||||
{
|
{
|
||||||
|
@ -1046,102 +1002,6 @@ namespace rsx
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
raw_program thread::get_raw_program() const
|
|
||||||
{
|
|
||||||
raw_program result{};
|
|
||||||
|
|
||||||
u32 fp_info = rsx::method_registers.shader_program_address();
|
|
||||||
|
|
||||||
result.state.input_attributes = rsx::method_registers.vertex_attrib_input_mask();
|
|
||||||
result.state.output_attributes = rsx::method_registers.vertex_attrib_output_mask();
|
|
||||||
result.state.ctrl = rsx::method_registers.shader_control();
|
|
||||||
result.state.divider_op = rsx::method_registers.frequency_divider_operation_mask();
|
|
||||||
result.state.alpha_func = (u32)rsx::method_registers.alpha_func();
|
|
||||||
result.state.fog_mode = (u32)rsx::method_registers.fog_equation();
|
|
||||||
result.state.is_int = 0;
|
|
||||||
|
|
||||||
for (u8 index = 0; index < rsx::limits::vertex_count; ++index)
|
|
||||||
{
|
|
||||||
bool is_int = false;
|
|
||||||
|
|
||||||
if (rsx::method_registers.vertex_arrays_info[index].size() > 0)
|
|
||||||
{
|
|
||||||
is_int = is_int_type(rsx::method_registers.vertex_arrays_info[index].type());
|
|
||||||
result.state.frequency[index] = rsx::method_registers.vertex_arrays_info[index].frequency();
|
|
||||||
}
|
|
||||||
else if (rsx::method_registers.register_vertex_info[index].size > 0)
|
|
||||||
{
|
|
||||||
is_int = is_int_type(rsx::method_registers.register_vertex_info[index].type);
|
|
||||||
result.state.frequency[index] = rsx::method_registers.register_vertex_info[index].frequency;
|
|
||||||
result.state.divider_op |= (1 << index);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
result.state.frequency[index] = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (is_int)
|
|
||||||
{
|
|
||||||
result.state.is_int |= 1 << index;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
for (u8 index = 0; index < rsx::limits::fragment_textures_count; ++index)
|
|
||||||
{
|
|
||||||
if (!rsx::method_registers.fragment_textures[index].enabled())
|
|
||||||
{
|
|
||||||
result.state.textures_alpha_kill[index] = 0;
|
|
||||||
result.state.textures_zfunc[index] = 0;
|
|
||||||
result.state.textures[index] = rsx::texture_target::none;
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
result.state.textures_alpha_kill[index] = rsx::method_registers.fragment_textures[index].alpha_kill_enabled() ? 1 : 0;
|
|
||||||
result.state.textures_zfunc[index] = rsx::method_registers.fragment_textures[index].zfunc();
|
|
||||||
|
|
||||||
switch (rsx::method_registers.fragment_textures[index].get_extended_texture_dimension())
|
|
||||||
{
|
|
||||||
case rsx::texture_dimension_extended::texture_dimension_1d: result.state.textures[index] = rsx::texture_target::_1; break;
|
|
||||||
case rsx::texture_dimension_extended::texture_dimension_2d: result.state.textures[index] = rsx::texture_target::_2; break;
|
|
||||||
case rsx::texture_dimension_extended::texture_dimension_3d: result.state.textures[index] = rsx::texture_target::_3; break;
|
|
||||||
case rsx::texture_dimension_extended::texture_dimension_cubemap: result.state.textures[index] = rsx::texture_target::cube; break;
|
|
||||||
|
|
||||||
default:
|
|
||||||
result.state.textures[index] = rsx::texture_target::none;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
for (u8 index = 0; index < rsx::limits::vertex_textures_count; ++index)
|
|
||||||
{
|
|
||||||
if (!rsx::method_registers.fragment_textures[index].enabled())
|
|
||||||
{
|
|
||||||
result.state.vertex_textures[index] = rsx::texture_target::none;
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
switch (rsx::method_registers.fragment_textures[index].get_extended_texture_dimension())
|
|
||||||
{
|
|
||||||
case rsx::texture_dimension_extended::texture_dimension_1d: result.state.vertex_textures[index] = rsx::texture_target::_1; break;
|
|
||||||
case rsx::texture_dimension_extended::texture_dimension_2d: result.state.vertex_textures[index] = rsx::texture_target::_2; break;
|
|
||||||
case rsx::texture_dimension_extended::texture_dimension_3d: result.state.vertex_textures[index] = rsx::texture_target::_3; break;
|
|
||||||
case rsx::texture_dimension_extended::texture_dimension_cubemap: result.state.vertex_textures[index] = rsx::texture_target::cube; break;
|
|
||||||
|
|
||||||
default:
|
|
||||||
result.state.vertex_textures[index] = rsx::texture_target::none;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
result.vertex_shader.ucode_ptr = rsx::method_registers.transform_program.data();
|
|
||||||
result.vertex_shader.offset = rsx::method_registers.transform_program_start();
|
|
||||||
|
|
||||||
result.fragment_shader.ucode_ptr = vm::base(rsx::get_address(fp_info & ~0x3, (fp_info & 0x3) - 1));
|
|
||||||
result.fragment_shader.offset = 0;
|
|
||||||
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
void thread::reset()
|
void thread::reset()
|
||||||
{
|
{
|
||||||
rsx::method_registers.reset();
|
rsx::method_registers.reset();
|
||||||
|
|
|
@ -26,18 +26,6 @@ extern u64 get_system_time();
|
||||||
extern bool user_asked_for_frame_capture;
|
extern bool user_asked_for_frame_capture;
|
||||||
extern rsx::frame_capture_data frame_debug;
|
extern rsx::frame_capture_data frame_debug;
|
||||||
|
|
||||||
namespace rsx
|
|
||||||
{
|
|
||||||
namespace old_shaders_cache
|
|
||||||
{
|
|
||||||
enum class shader_language
|
|
||||||
{
|
|
||||||
glsl,
|
|
||||||
hlsl,
|
|
||||||
};
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
namespace rsx
|
namespace rsx
|
||||||
{
|
{
|
||||||
namespace limits
|
namespace limits
|
||||||
|
@ -54,54 +42,6 @@ namespace rsx
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
namespace old_shaders_cache
|
|
||||||
{
|
|
||||||
struct decompiled_shader
|
|
||||||
{
|
|
||||||
std::string code;
|
|
||||||
};
|
|
||||||
|
|
||||||
struct finalized_shader
|
|
||||||
{
|
|
||||||
u64 ucode_hash;
|
|
||||||
std::string code;
|
|
||||||
};
|
|
||||||
|
|
||||||
template<typename Type, typename KeyType = u64, typename Hasher = std::hash<KeyType>>
|
|
||||||
struct cache
|
|
||||||
{
|
|
||||||
private:
|
|
||||||
std::unordered_map<KeyType, Type, Hasher> m_entries;
|
|
||||||
|
|
||||||
public:
|
|
||||||
const Type* find(u64 key) const
|
|
||||||
{
|
|
||||||
auto found = m_entries.find(key);
|
|
||||||
|
|
||||||
if (found == m_entries.end())
|
|
||||||
return nullptr;
|
|
||||||
|
|
||||||
return &found->second;
|
|
||||||
}
|
|
||||||
|
|
||||||
void insert(KeyType key, const Type &shader)
|
|
||||||
{
|
|
||||||
m_entries.insert({ key, shader });
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
struct shaders_cache
|
|
||||||
{
|
|
||||||
cache<decompiled_shader> decompiled_fragment_shaders;
|
|
||||||
cache<decompiled_shader> decompiled_vertex_shaders;
|
|
||||||
cache<finalized_shader> finailized_fragment_shaders;
|
|
||||||
cache<finalized_shader> finailized_vertex_shaders;
|
|
||||||
|
|
||||||
void load(const std::string &path, shader_language lang);
|
|
||||||
void load(shader_language lang);
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
u32 get_vertex_type_size_on_host(vertex_base_type type, u32 size);
|
u32 get_vertex_type_size_on_host(vertex_base_type type, u32 size);
|
||||||
|
|
||||||
u32 get_address(u32 offset, u32 location);
|
u32 get_address(u32 offset, u32 location);
|
||||||
|
@ -172,9 +112,6 @@ namespace rsx
|
||||||
std::vector<u32> element_push_buffer;
|
std::vector<u32> element_push_buffer;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
old_shaders_cache::shaders_cache shaders_cache;
|
|
||||||
rsx::programs_cache programs_cache;
|
|
||||||
|
|
||||||
CellGcmControl* ctrl = nullptr;
|
CellGcmControl* ctrl = nullptr;
|
||||||
|
|
||||||
Timer timer_sync;
|
Timer timer_sync;
|
||||||
|
@ -356,7 +293,6 @@ namespace rsx
|
||||||
|
|
||||||
virtual bool scaled_image_from_memory(blit_src_info& src_info, blit_dst_info& dst_info, bool interpolate){ return false; }
|
virtual bool scaled_image_from_memory(blit_src_info& src_info, blit_dst_info& dst_info, bool interpolate){ return false; }
|
||||||
|
|
||||||
struct raw_program get_raw_program() const;
|
|
||||||
public:
|
public:
|
||||||
void reset();
|
void reset();
|
||||||
void init(const u32 ioAddress, const u32 ioSize, const u32 ctrlAddress, const u32 localAddress);
|
void init(const u32 ioAddress, const u32 ioSize, const u32 ctrlAddress, const u32 localAddress);
|
||||||
|
|
|
@ -449,10 +449,11 @@ namespace
|
||||||
|
|
||||||
VKGSRender::VKGSRender() : GSRender()
|
VKGSRender::VKGSRender() : GSRender()
|
||||||
{
|
{
|
||||||
shaders_cache.load(rsx::old_shaders_cache::shader_language::glsl);
|
//shaders_cache.load(rsx::old_shaders_cache::shader_language::glsl);
|
||||||
|
|
||||||
|
printf("Starting vulkan renderer\n");
|
||||||
u32 instance_handle = m_thread_context.createInstance("RPCS3");
|
u32 instance_handle = m_thread_context.createInstance("RPCS3");
|
||||||
|
printf("Instance created, handle=%u\n", instance_handle);
|
||||||
if (instance_handle > 0)
|
if (instance_handle > 0)
|
||||||
{
|
{
|
||||||
m_thread_context.makeCurrentInstance(instance_handle);
|
m_thread_context.makeCurrentInstance(instance_handle);
|
||||||
|
@ -498,6 +499,48 @@ VKGSRender::VKGSRender() : GSRender()
|
||||||
m_swap_chain = m_thread_context.createSwapChain(hInstance, hWnd, gpus[0]);
|
m_swap_chain = m_thread_context.createSwapChain(hInstance, hWnd, gpus[0]);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#elif __linux__
|
||||||
|
|
||||||
|
Window window = (Window)m_frame->handle();
|
||||||
|
Display *display = XOpenDisplay(0);
|
||||||
|
|
||||||
|
printf("Entering enumeration logic...\n");
|
||||||
|
|
||||||
|
std::vector<vk::physical_device>& gpus = m_thread_context.enumerateDevices();
|
||||||
|
|
||||||
|
//Actually confirm that the loader found at least one compatible device
|
||||||
|
//This should not happen unless something is wrong with the driver setup on the target system
|
||||||
|
if (gpus.size() == 0)
|
||||||
|
{
|
||||||
|
//We can't throw in Emulator::Load, so we show error and return
|
||||||
|
LOG_FATAL(RSX, "No compatible GPU devices found");
|
||||||
|
m_device = VK_NULL_HANDLE;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
printf("Post-enumerate devices, window=%llx, display=0x%p\n", window, display);
|
||||||
|
XFlush(display);
|
||||||
|
|
||||||
|
bool gpu_found = false;
|
||||||
|
std::string adapter_name = g_cfg.video.vk.adapter;
|
||||||
|
for (auto &gpu : gpus)
|
||||||
|
{
|
||||||
|
if (gpu.name() == adapter_name)
|
||||||
|
{
|
||||||
|
m_swap_chain = m_thread_context.createSwapChain(display, window, gpu);
|
||||||
|
gpu_found = true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!gpu_found || adapter_name.empty())
|
||||||
|
{
|
||||||
|
m_swap_chain = m_thread_context.createSwapChain(display, window, gpus[0]);
|
||||||
|
}
|
||||||
|
|
||||||
|
printf("Swapchain creation completed\n");
|
||||||
|
m_display_handle = display;
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
m_device = (vk::render_device *)(&m_swap_chain->get_device());
|
m_device = (vk::render_device *)(&m_swap_chain->get_device());
|
||||||
|
@ -659,6 +702,11 @@ VKGSRender::~VKGSRender()
|
||||||
m_thread_context.close();
|
m_thread_context.close();
|
||||||
|
|
||||||
delete m_swap_chain;
|
delete m_swap_chain;
|
||||||
|
|
||||||
|
#ifdef __linux__
|
||||||
|
if (m_display_handle)
|
||||||
|
XCloseDisplay(m_display_handle);
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
bool VKGSRender::on_access_violation(u32 address, bool is_writing)
|
bool VKGSRender::on_access_violation(u32 address, bool is_writing)
|
||||||
|
|
|
@ -11,6 +11,7 @@
|
||||||
#include "VKProgramBuffer.h"
|
#include "VKProgramBuffer.h"
|
||||||
#include "../GCM.h"
|
#include "../GCM.h"
|
||||||
#include "../rsx_utils.h"
|
#include "../rsx_utils.h"
|
||||||
|
#include <thread>
|
||||||
#include <atomic>
|
#include <atomic>
|
||||||
|
|
||||||
#pragma comment(lib, "VKstatic.1.lib")
|
#pragma comment(lib, "VKstatic.1.lib")
|
||||||
|
@ -165,11 +166,15 @@ private:
|
||||||
s32 m_last_flushable_cb = -1;
|
s32 m_last_flushable_cb = -1;
|
||||||
|
|
||||||
std::mutex m_flush_queue_mutex;
|
std::mutex m_flush_queue_mutex;
|
||||||
std::atomic<bool> m_flush_commands = false;
|
std::atomic<bool> m_flush_commands = { false };
|
||||||
std::atomic<int> m_queued_threads = { 0 };
|
std::atomic<int> m_queued_threads = { 0 };
|
||||||
|
|
||||||
std::thread::id rsx_thread;
|
std::thread::id rsx_thread;
|
||||||
|
|
||||||
|
#ifdef __linux__
|
||||||
|
Display *m_display_handle = nullptr;
|
||||||
|
#endif
|
||||||
|
|
||||||
public:
|
public:
|
||||||
VKGSRender();
|
VKGSRender();
|
||||||
~VKGSRender();
|
~VKGSRender();
|
||||||
|
|
|
@ -8,6 +8,10 @@
|
||||||
#include <memory>
|
#include <memory>
|
||||||
#include <unordered_map>
|
#include <unordered_map>
|
||||||
|
|
||||||
|
#ifdef __linux__
|
||||||
|
#include <X11/Xlib.h>
|
||||||
|
#endif
|
||||||
|
|
||||||
#include "Emu/System.h"
|
#include "Emu/System.h"
|
||||||
#include "VulkanAPI.h"
|
#include "VulkanAPI.h"
|
||||||
#include "../GCM.h"
|
#include "../GCM.h"
|
||||||
|
@ -799,15 +803,9 @@ namespace vk
|
||||||
void init_swapchain(u32 width, u32 height)
|
void init_swapchain(u32 width, u32 height)
|
||||||
{
|
{
|
||||||
VkSwapchainKHR old_swapchain = m_vk_swapchain;
|
VkSwapchainKHR old_swapchain = m_vk_swapchain;
|
||||||
|
|
||||||
uint32_t num_modes;
|
|
||||||
vk::physical_device& gpu = const_cast<vk::physical_device&>(dev.gpu());
|
vk::physical_device& gpu = const_cast<vk::physical_device&>(dev.gpu());
|
||||||
CHECK_RESULT(vkGetPhysicalDeviceSurfacePresentModesKHR(gpu, m_surface, &num_modes, NULL));
|
|
||||||
|
|
||||||
std::vector<VkPresentModeKHR> present_mode_descriptors(num_modes);
|
VkSurfaceCapabilitiesKHR surface_descriptors = {};
|
||||||
CHECK_RESULT(vkGetPhysicalDeviceSurfacePresentModesKHR(gpu, m_surface, &num_modes, present_mode_descriptors.data()));
|
|
||||||
|
|
||||||
VkSurfaceCapabilitiesKHR surface_descriptors;
|
|
||||||
CHECK_RESULT(vkGetPhysicalDeviceSurfaceCapabilitiesKHR(gpu, m_surface, &surface_descriptors));
|
CHECK_RESULT(vkGetPhysicalDeviceSurfaceCapabilitiesKHR(gpu, m_surface, &surface_descriptors));
|
||||||
|
|
||||||
VkExtent2D swapchainExtent;
|
VkExtent2D swapchainExtent;
|
||||||
|
@ -1058,6 +1056,8 @@ namespace vk
|
||||||
|
|
||||||
void enable_debugging()
|
void enable_debugging()
|
||||||
{
|
{
|
||||||
|
if (!g_cfg.video.debug_output) return;
|
||||||
|
|
||||||
PFN_vkDebugReportCallbackEXT callback = vk::dbgFunc;
|
PFN_vkDebugReportCallbackEXT callback = vk::dbgFunc;
|
||||||
|
|
||||||
createDebugReportCallback = (PFN_vkCreateDebugReportCallbackEXT)vkGetInstanceProcAddr(m_instance, "vkCreateDebugReportCallbackEXT");
|
createDebugReportCallback = (PFN_vkCreateDebugReportCallbackEXT)vkGetInstanceProcAddr(m_instance, "vkCreateDebugReportCallbackEXT");
|
||||||
|
@ -1089,7 +1089,11 @@ namespace vk
|
||||||
const char *requested_extensions[] =
|
const char *requested_extensions[] =
|
||||||
{
|
{
|
||||||
"VK_KHR_surface",
|
"VK_KHR_surface",
|
||||||
|
#ifdef _WIN32
|
||||||
"VK_KHR_win32_surface",
|
"VK_KHR_win32_surface",
|
||||||
|
#else
|
||||||
|
"VK_KHR_xlib_surface",
|
||||||
|
#endif
|
||||||
"VK_EXT_debug_report",
|
"VK_EXT_debug_report",
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -1166,6 +1170,7 @@ namespace vk
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef _WIN32
|
#ifdef _WIN32
|
||||||
|
|
||||||
vk::swap_chain* createSwapChain(HINSTANCE hInstance, HWND hWnd, vk::physical_device &dev)
|
vk::swap_chain* createSwapChain(HINSTANCE hInstance, HWND hWnd, vk::physical_device &dev)
|
||||||
{
|
{
|
||||||
VkWin32SurfaceCreateInfoKHR createInfo = {};
|
VkWin32SurfaceCreateInfoKHR createInfo = {};
|
||||||
|
@ -1175,6 +1180,18 @@ namespace vk
|
||||||
|
|
||||||
VkSurfaceKHR surface;
|
VkSurfaceKHR surface;
|
||||||
CHECK_RESULT(vkCreateWin32SurfaceKHR(m_instance, &createInfo, NULL, &surface));
|
CHECK_RESULT(vkCreateWin32SurfaceKHR(m_instance, &createInfo, NULL, &surface));
|
||||||
|
#elif __linux__
|
||||||
|
|
||||||
|
vk::swap_chain* createSwapChain(Display *display, Window window, vk::physical_device &dev)
|
||||||
|
{
|
||||||
|
VkXlibSurfaceCreateInfoKHR createInfo = {};
|
||||||
|
createInfo.sType = VK_STRUCTURE_TYPE_XLIB_SURFACE_CREATE_INFO_KHR;
|
||||||
|
createInfo.dpy = display;
|
||||||
|
createInfo.window = window;
|
||||||
|
|
||||||
|
VkSurfaceKHR surface;
|
||||||
|
CHECK_RESULT(vkCreateXlibSurfaceKHR(m_instance, &createInfo, nullptr, &surface));
|
||||||
|
#endif
|
||||||
|
|
||||||
uint32_t device_queues = dev.get_queue_count();
|
uint32_t device_queues = dev.get_queue_count();
|
||||||
std::vector<VkBool32> supportsPresent(device_queues);
|
std::vector<VkBool32> supportsPresent(device_queues);
|
||||||
|
@ -1251,8 +1268,6 @@ namespace vk
|
||||||
|
|
||||||
return new swap_chain(dev, presentQueueNodeIndex, graphicsQueueNodeIndex, format, surface, color_space);
|
return new swap_chain(dev, presentQueueNodeIndex, graphicsQueueNodeIndex, format, surface, color_space);
|
||||||
}
|
}
|
||||||
#endif //if _WIN32
|
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
class descriptor_pool
|
class descriptor_pool
|
||||||
|
|
|
@ -205,7 +205,7 @@ namespace vk
|
||||||
template<typename T>
|
template<typename T>
|
||||||
void do_memory_transfer(void *pixels_dst, const void *pixels_src)
|
void do_memory_transfer(void *pixels_dst, const void *pixels_src)
|
||||||
{
|
{
|
||||||
if (sizeof T == 1)
|
if (sizeof(T) == 1)
|
||||||
memcpy(pixels_dst, pixels_src, cpu_address_range);
|
memcpy(pixels_dst, pixels_src, cpu_address_range);
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
|
|
@ -551,6 +551,6 @@ VKGSRender::upload_vertex_data()
|
||||||
{
|
{
|
||||||
draw_command_visitor visitor(*m_device, m_index_buffer_ring_info, m_attrib_ring_info, m_program,
|
draw_command_visitor visitor(*m_device, m_index_buffer_ring_info, m_attrib_ring_info, m_program,
|
||||||
descriptor_sets, m_buffer_view_to_clean,
|
descriptor_sets, m_buffer_view_to_clean,
|
||||||
[this](const auto& state, const auto& range) { return get_vertex_buffers(state, range); });
|
[this](const auto& state, const auto& range) { return this->get_vertex_buffers(state, range); });
|
||||||
return std::apply_visitor(visitor, get_draw_command(rsx::method_registers));
|
return std::apply_visitor(visitor, get_draw_command(rsx::method_registers));
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,139 +0,0 @@
|
||||||
#include "stdafx.h"
|
|
||||||
#include "rsx_cache.h"
|
|
||||||
#include "Emu/System.h"
|
|
||||||
|
|
||||||
namespace rsx
|
|
||||||
{
|
|
||||||
void shaders_cache::path(const std::string &path_)
|
|
||||||
{
|
|
||||||
m_path = path_;
|
|
||||||
}
|
|
||||||
|
|
||||||
shader_info shaders_cache::get(const program_cache_context &ctxt, raw_shader &raw_shader, const program_state& state)
|
|
||||||
{
|
|
||||||
auto found_entry = m_entries.find(raw_shader);
|
|
||||||
|
|
||||||
shader_info info;
|
|
||||||
entry_t *entry;
|
|
||||||
|
|
||||||
if (found_entry != m_entries.end())
|
|
||||||
{
|
|
||||||
entry = &found_entry->second;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
//analyze_raw_shader(raw_shader);
|
|
||||||
|
|
||||||
std::string shader_name_base =
|
|
||||||
fmt::format("%lld.%016llx", ++m_index, raw_shader.hash()) +
|
|
||||||
(raw_shader.type == rsx::program_type::fragment ? ".fp" : ".vp");
|
|
||||||
|
|
||||||
fs::file{ m_path + shader_name_base + ".ucode", fs::rewrite }
|
|
||||||
.write(raw_shader.ucode.data(), raw_shader.ucode.size());
|
|
||||||
|
|
||||||
rsx::decompiled_shader decompiled_shader = decompile(raw_shader, ctxt.lang);
|
|
||||||
|
|
||||||
fs::file{ m_path + shader_name_base + (ctxt.lang == rsx::decompile_language::glsl ? ".glsl" : ".hlsl"), fs::rewrite }
|
|
||||||
.write(decompiled_shader.code);
|
|
||||||
|
|
||||||
auto inserted = m_entries.insert({ raw_shader, entry_t{ m_index, decompiled_shader } }).first;
|
|
||||||
inserted->second.decompiled.raw = &inserted->first;
|
|
||||||
entry = &inserted->second;
|
|
||||||
}
|
|
||||||
|
|
||||||
info.decompiled = &entry->decompiled;
|
|
||||||
|
|
||||||
auto found_complete = entry->complete.find(state);
|
|
||||||
|
|
||||||
if (found_complete != entry->complete.end())
|
|
||||||
{
|
|
||||||
info.complete = &found_complete->second;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
rsx::complete_shader complete_shader = ctxt.complete_shader(entry->decompiled, state);
|
|
||||||
complete_shader.decompiled = info.decompiled;
|
|
||||||
info.complete = &entry->complete.insert({ state, complete_shader }).first->second;
|
|
||||||
info.complete->user_data = nullptr;
|
|
||||||
|
|
||||||
const std::string hash_combination = fmt::format("%lld.%016llx.%016llx", entry->index, raw_shader.hash(), state.hash());
|
|
||||||
|
|
||||||
std::string shader_name =
|
|
||||||
hash_combination +
|
|
||||||
(raw_shader.type == rsx::program_type::fragment ? ".fp" : ".vp") +
|
|
||||||
(ctxt.lang == rsx::decompile_language::glsl ? ".glsl" : ".hlsl");
|
|
||||||
|
|
||||||
fs::file{ m_path + shader_name, fs::rewrite }.write(info.complete->code);
|
|
||||||
fs::file{ m_path + hash_combination + ".state", fs::rewrite }.write(state);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (info.complete->user_data == nullptr)
|
|
||||||
{
|
|
||||||
info.complete->user_data = ctxt.compile_shader(raw_shader.type, info.complete->code);
|
|
||||||
}
|
|
||||||
|
|
||||||
return info;
|
|
||||||
}
|
|
||||||
|
|
||||||
void shaders_cache::clear(const program_cache_context& context)
|
|
||||||
{
|
|
||||||
for (auto &entry : m_entries)
|
|
||||||
{
|
|
||||||
for (auto &shader : entry.second.complete)
|
|
||||||
{
|
|
||||||
context.remove_shader(shader.second.user_data);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
m_entries.clear();
|
|
||||||
}
|
|
||||||
|
|
||||||
programs_cache::programs_cache()
|
|
||||||
{
|
|
||||||
m_vertex_shaders_cache.path(Emu.GetCachePath());
|
|
||||||
m_fragment_shader_cache.path(Emu.GetCachePath());
|
|
||||||
}
|
|
||||||
|
|
||||||
programs_cache::~programs_cache()
|
|
||||||
{
|
|
||||||
clear();
|
|
||||||
}
|
|
||||||
|
|
||||||
program_info programs_cache::get(raw_program raw_program_, decompile_language lang)
|
|
||||||
{
|
|
||||||
raw_program_.vertex_shader.type = program_type::vertex;
|
|
||||||
raw_program_.fragment_shader.type = program_type::fragment;
|
|
||||||
|
|
||||||
analyze_raw_shader(raw_program_.vertex_shader);
|
|
||||||
analyze_raw_shader(raw_program_.fragment_shader);
|
|
||||||
|
|
||||||
auto found = m_program_cache.find(raw_program_);
|
|
||||||
|
|
||||||
if (found != m_program_cache.end())
|
|
||||||
{
|
|
||||||
return found->second;
|
|
||||||
}
|
|
||||||
|
|
||||||
program_info result;
|
|
||||||
|
|
||||||
result.vertex_shader = m_vertex_shaders_cache.get(context, raw_program_.vertex_shader, raw_program_.state);
|
|
||||||
result.fragment_shader = m_fragment_shader_cache.get(context, raw_program_.fragment_shader, raw_program_.state);
|
|
||||||
result.program = context.make_program(result.vertex_shader.complete->user_data, result.fragment_shader.complete->user_data);
|
|
||||||
m_program_cache.insert({ raw_program_, result });
|
|
||||||
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
void programs_cache::clear()
|
|
||||||
{
|
|
||||||
for (auto &entry : m_program_cache)
|
|
||||||
{
|
|
||||||
context.remove_program(entry.second.program);
|
|
||||||
}
|
|
||||||
|
|
||||||
m_program_cache.clear();
|
|
||||||
|
|
||||||
m_vertex_shaders_cache.clear(context);
|
|
||||||
m_fragment_shader_cache.clear(context);
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -1,36 +1,10 @@
|
||||||
#pragma once
|
#pragma once
|
||||||
#include <rsx_decompiler.h>
|
|
||||||
#include "Utilities/VirtualMemory.h"
|
#include "Utilities/VirtualMemory.h"
|
||||||
#include "Emu/Memory/vm.h"
|
#include "Emu/Memory/vm.h"
|
||||||
#include "gcm_enums.h"
|
#include "gcm_enums.h"
|
||||||
|
|
||||||
namespace rsx
|
namespace rsx
|
||||||
{
|
{
|
||||||
struct shader_info
|
|
||||||
{
|
|
||||||
decompiled_shader *decompiled;
|
|
||||||
complete_shader *complete;
|
|
||||||
};
|
|
||||||
|
|
||||||
struct program_info
|
|
||||||
{
|
|
||||||
shader_info vertex_shader;
|
|
||||||
shader_info fragment_shader;
|
|
||||||
|
|
||||||
void *program;
|
|
||||||
};
|
|
||||||
|
|
||||||
struct program_cache_context
|
|
||||||
{
|
|
||||||
decompile_language lang;
|
|
||||||
|
|
||||||
void*(*compile_shader)(program_type type, const std::string &code);
|
|
||||||
rsx::complete_shader(*complete_shader)(const decompiled_shader &shader, program_state state);
|
|
||||||
void*(*make_program)(const void *vertex_shader, const void *fragment_shader);
|
|
||||||
void(*remove_program)(void *ptr);
|
|
||||||
void(*remove_shader)(void *ptr);
|
|
||||||
};
|
|
||||||
|
|
||||||
struct blit_src_info
|
struct blit_src_info
|
||||||
{
|
{
|
||||||
blit_engine::transfer_source_format format;
|
blit_engine::transfer_source_format format;
|
||||||
|
@ -64,43 +38,6 @@ namespace rsx
|
||||||
u32 rsx_address;
|
u32 rsx_address;
|
||||||
};
|
};
|
||||||
|
|
||||||
class shaders_cache
|
|
||||||
{
|
|
||||||
struct entry_t
|
|
||||||
{
|
|
||||||
std::int64_t index;
|
|
||||||
decompiled_shader decompiled;
|
|
||||||
std::unordered_map<program_state, complete_shader, hasher> complete;
|
|
||||||
};
|
|
||||||
|
|
||||||
std::unordered_map<raw_shader, entry_t, hasher> m_entries;
|
|
||||||
std::string m_path;
|
|
||||||
std::int64_t m_index = -1;
|
|
||||||
|
|
||||||
public:
|
|
||||||
void path(const std::string &path_);
|
|
||||||
|
|
||||||
shader_info get(const program_cache_context &ctxt, raw_shader &raw_shader, const program_state& state);
|
|
||||||
void clear(const program_cache_context& context);
|
|
||||||
};
|
|
||||||
|
|
||||||
class programs_cache
|
|
||||||
{
|
|
||||||
std::unordered_map<raw_program, program_info, hasher> m_program_cache;
|
|
||||||
|
|
||||||
shaders_cache m_vertex_shaders_cache;
|
|
||||||
shaders_cache m_fragment_shader_cache;
|
|
||||||
|
|
||||||
public:
|
|
||||||
program_cache_context context;
|
|
||||||
|
|
||||||
programs_cache();
|
|
||||||
~programs_cache();
|
|
||||||
|
|
||||||
program_info get(raw_program raw_program_, decompile_language lang);
|
|
||||||
void clear();
|
|
||||||
};
|
|
||||||
|
|
||||||
class buffered_section
|
class buffered_section
|
||||||
{
|
{
|
||||||
protected:
|
protected:
|
||||||
|
|
|
@ -89,9 +89,7 @@ void fmt_class_string<video_renderer>::format(std::string& out, u64 arg)
|
||||||
{
|
{
|
||||||
case video_renderer::null: return "Null";
|
case video_renderer::null: return "Null";
|
||||||
case video_renderer::opengl: return "OpenGL";
|
case video_renderer::opengl: return "OpenGL";
|
||||||
#ifdef _WIN32
|
|
||||||
case video_renderer::vulkan: return "Vulkan";
|
case video_renderer::vulkan: return "Vulkan";
|
||||||
#endif
|
|
||||||
#ifdef _MSC_VER
|
#ifdef _MSC_VER
|
||||||
case video_renderer::dx12: return "D3D12";
|
case video_renderer::dx12: return "D3D12";
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -74,9 +74,7 @@ enum class video_renderer
|
||||||
{
|
{
|
||||||
null,
|
null,
|
||||||
opengl,
|
opengl,
|
||||||
#ifdef _WIN32
|
|
||||||
vulkan,
|
vulkan,
|
||||||
#endif
|
|
||||||
#ifdef _MSC_VER
|
#ifdef _MSC_VER
|
||||||
dx12,
|
dx12,
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -13,10 +13,7 @@
|
||||||
#include <dxgi1_4.h>
|
#include <dxgi1_4.h>
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef _WIN32
|
|
||||||
#include "Emu/RSX/VK/VKHelpers.h"
|
#include "Emu/RSX/VK/VKHelpers.h"
|
||||||
#endif
|
|
||||||
|
|
||||||
#include "SettingsDialog.h"
|
#include "SettingsDialog.h"
|
||||||
|
|
||||||
#include <set>
|
#include <set>
|
||||||
|
@ -480,7 +477,6 @@ SettingsDialog::SettingsDialog(wxWindow* parent, const std::string& path)
|
||||||
cbox_gs_d3d_adapter->Enable(false);
|
cbox_gs_d3d_adapter->Enable(false);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef _WIN32
|
|
||||||
//TODO: This is very slow. Only init once
|
//TODO: This is very slow. Only init once
|
||||||
bool vulkan_supported = false;
|
bool vulkan_supported = false;
|
||||||
|
|
||||||
|
@ -514,9 +510,6 @@ SettingsDialog::SettingsDialog(wxWindow* parent, const std::string& path)
|
||||||
}
|
}
|
||||||
|
|
||||||
device_enum_context.close();
|
device_enum_context.close();
|
||||||
#else
|
|
||||||
cbox_gs_vk_adapter->Enable(false);
|
|
||||||
#endif
|
|
||||||
|
|
||||||
// Rendering
|
// Rendering
|
||||||
s_round_gs_render->Add(cbox_gs_render, wxSizerFlags().Border(wxALL, 5).Expand());
|
s_round_gs_render->Add(cbox_gs_render, wxSizerFlags().Border(wxALL, 5).Expand());
|
||||||
|
|
File diff suppressed because it is too large
Load diff
|
@ -37,8 +37,8 @@
|
||||||
#ifdef _MSC_VER
|
#ifdef _MSC_VER
|
||||||
#include "Emu/RSX/D3D12/D3D12GSRender.h"
|
#include "Emu/RSX/D3D12/D3D12GSRender.h"
|
||||||
#endif
|
#endif
|
||||||
#ifdef _WIN32
|
|
||||||
#include "Emu/RSX/VK/VKGSRender.h"
|
#include "Emu/RSX/VK/VKGSRender.h"
|
||||||
|
#ifdef _WIN32
|
||||||
#include "Emu/Audio/XAudio2/XAudio2Thread.h"
|
#include "Emu/Audio/XAudio2/XAudio2Thread.h"
|
||||||
#endif
|
#endif
|
||||||
#ifdef __linux__
|
#ifdef __linux__
|
||||||
|
@ -149,9 +149,7 @@ void rpcs3_app::InitializeCallbacks()
|
||||||
{
|
{
|
||||||
case video_renderer::null: return std::make_unique<gs_frame>("Null", size.first, size.second, RPCS3MainWin->GetAppIcon());
|
case video_renderer::null: return std::make_unique<gs_frame>("Null", size.first, size.second, RPCS3MainWin->GetAppIcon());
|
||||||
case video_renderer::opengl: return std::make_unique<gl_gs_frame>(size.first, size.second, RPCS3MainWin->GetAppIcon());
|
case video_renderer::opengl: return std::make_unique<gl_gs_frame>(size.first, size.second, RPCS3MainWin->GetAppIcon());
|
||||||
#ifdef _WIN32
|
|
||||||
case video_renderer::vulkan: return std::make_unique<gs_frame>("Vulkan", size.first, size.second, RPCS3MainWin->GetAppIcon());
|
case video_renderer::vulkan: return std::make_unique<gs_frame>("Vulkan", size.first, size.second, RPCS3MainWin->GetAppIcon());
|
||||||
#endif
|
|
||||||
#ifdef _MSC_VER
|
#ifdef _MSC_VER
|
||||||
case video_renderer::dx12: return std::make_unique<gs_frame>("DirectX 12", size.first, size.second, RPCS3MainWin->GetAppIcon());
|
case video_renderer::dx12: return std::make_unique<gs_frame>("DirectX 12", size.first, size.second, RPCS3MainWin->GetAppIcon());
|
||||||
#endif
|
#endif
|
||||||
|
@ -165,9 +163,7 @@ void rpcs3_app::InitializeCallbacks()
|
||||||
{
|
{
|
||||||
case video_renderer::null: return std::make_shared<NullGSRender>();
|
case video_renderer::null: return std::make_shared<NullGSRender>();
|
||||||
case video_renderer::opengl: return std::make_shared<GLGSRender>();
|
case video_renderer::opengl: return std::make_shared<GLGSRender>();
|
||||||
#ifdef _WIN32
|
|
||||||
case video_renderer::vulkan: return std::make_shared<VKGSRender>();
|
case video_renderer::vulkan: return std::make_shared<VKGSRender>();
|
||||||
#endif
|
|
||||||
#ifdef _MSC_VER
|
#ifdef _MSC_VER
|
||||||
case video_renderer::dx12: return std::make_shared<D3D12GSRender>();
|
case video_renderer::dx12: return std::make_shared<D3D12GSRender>();
|
||||||
#endif
|
#endif
|
||||||
|
|
29
rpcs3/rpcs3_automoc.cpp
Normal file
29
rpcs3/rpcs3_automoc.cpp
Normal file
|
@ -0,0 +1,29 @@
|
||||||
|
/* This file is autogenerated, do not edit*/
|
||||||
|
#include "moc_basic_keyboard_handler.cpp"
|
||||||
|
#include "moc_basic_mouse_handler.cpp"
|
||||||
|
#include "moc_rpcs3_app.cpp"
|
||||||
|
#include "moc_audio_tab.cpp"
|
||||||
|
#include "moc_auto_pause_settings_dialog.cpp"
|
||||||
|
#include "moc_cg_disasm_window.cpp"
|
||||||
|
#include "moc_core_tab.cpp"
|
||||||
|
#include "moc_debugger_frame.cpp"
|
||||||
|
#include "moc_emu_settings.cpp"
|
||||||
|
#include "moc_game_list_frame.cpp"
|
||||||
|
#include "moc_graphics_tab.cpp"
|
||||||
|
#include "moc_gs_frame.cpp"
|
||||||
|
#include "moc_gui_settings.cpp"
|
||||||
|
#include "moc_gui_tab.cpp"
|
||||||
|
#include "moc_input_tab.cpp"
|
||||||
|
#include "moc_kernel_explorer.cpp"
|
||||||
|
#include "moc_log_frame.cpp"
|
||||||
|
#include "moc_main_window.cpp"
|
||||||
|
#include "moc_memory_string_searcher.cpp"
|
||||||
|
#include "moc_misc_tab.cpp"
|
||||||
|
#include "moc_msg_dialog_frame.cpp"
|
||||||
|
#include "moc_networking_tab.cpp"
|
||||||
|
#include "moc_pad_settings_dialog.cpp"
|
||||||
|
#include "moc_rsx_debugger.cpp"
|
||||||
|
#include "moc_save_data_utility.cpp"
|
||||||
|
#include "moc_settings_dialog.cpp"
|
||||||
|
#include "moc_system_tab.cpp"
|
||||||
|
#include "moc_welcome_dialog.cpp"
|
|
@ -4,6 +4,18 @@
|
||||||
#include "Emu/System.h"
|
#include "Emu/System.h"
|
||||||
#include "Utilities/Config.h"
|
#include "Utilities/Config.h"
|
||||||
|
|
||||||
|
#ifdef _MSC_VER
|
||||||
|
#include <Windows.h>
|
||||||
|
#undef GetHwnd
|
||||||
|
#include <d3d12.h>
|
||||||
|
#include <wrl/client.h>
|
||||||
|
#include <dxgi1_4.h>
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#if defined(_WIN32) || defined(__linux__)
|
||||||
|
#include "Emu/RSX/VK/VKHelpers.h"
|
||||||
|
#endif
|
||||||
|
|
||||||
extern std::string g_cfg_defaults; //! Default settings grabbed from Utilities/Config.h
|
extern std::string g_cfg_defaults; //! Default settings grabbed from Utilities/Config.h
|
||||||
|
|
||||||
inline std::string sstr(const QString& _in) { return _in.toUtf8().toStdString(); }
|
inline std::string sstr(const QString& _in) { return _in.toUtf8().toStdString(); }
|
||||||
|
@ -103,6 +115,58 @@ static QStringList getOptions(cfg_location location)
|
||||||
return values;
|
return values;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Render_Creator::Render_Creator()
|
||||||
|
{
|
||||||
|
// check for dx12 adapters
|
||||||
|
#ifdef _MSC_VER
|
||||||
|
Microsoft::WRL::ComPtr<IDXGIFactory4> dxgi_factory;
|
||||||
|
supportsD3D12 = SUCCEEDED(CreateDXGIFactory(IID_PPV_ARGS(&dxgi_factory)));
|
||||||
|
|
||||||
|
if (supportsD3D12)
|
||||||
|
{
|
||||||
|
supportsD3D12 = false;
|
||||||
|
IDXGIAdapter1* pAdapter = nullptr;
|
||||||
|
|
||||||
|
for (UINT adapterIndex = 0; DXGI_ERROR_NOT_FOUND != dxgi_factory->EnumAdapters1(adapterIndex, &pAdapter); ++adapterIndex)
|
||||||
|
{
|
||||||
|
HMODULE D3D12Module = verify("d3d12.dll", LoadLibrary(L"d3d12.dll"));
|
||||||
|
PFN_D3D12_CREATE_DEVICE wrapD3D12CreateDevice = (PFN_D3D12_CREATE_DEVICE)GetProcAddress(D3D12Module, "D3D12CreateDevice");
|
||||||
|
|
||||||
|
if (SUCCEEDED(wrapD3D12CreateDevice(pAdapter, D3D_FEATURE_LEVEL_11_0, _uuidof(ID3D12Device), nullptr)))
|
||||||
|
{
|
||||||
|
//A device with D3D12 support found. Init data
|
||||||
|
supportsD3D12 = true;
|
||||||
|
|
||||||
|
DXGI_ADAPTER_DESC desc;
|
||||||
|
pAdapter->GetDesc(&desc);
|
||||||
|
D3D12Adapters.append(QString::fromWCharArray(desc.Description));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// check for vulkan adapters
|
||||||
|
vk::context device_enum_context;
|
||||||
|
u32 instance_handle = device_enum_context.createInstance("RPCS3", true);
|
||||||
|
|
||||||
|
if (instance_handle > 0)
|
||||||
|
{
|
||||||
|
device_enum_context.makeCurrentInstance(instance_handle);
|
||||||
|
std::vector<vk::physical_device>& gpus = device_enum_context.enumerateDevices();
|
||||||
|
|
||||||
|
if (gpus.size() > 0)
|
||||||
|
{
|
||||||
|
//A device with vulkan support found. Init data
|
||||||
|
supportsVulkan = true;
|
||||||
|
|
||||||
|
for (auto& gpu : gpus)
|
||||||
|
{
|
||||||
|
vulkanAdapters.append(qstr(gpu.name()));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
emu_settings::emu_settings(const std::string& path) : QObject()
|
emu_settings::emu_settings(const std::string& path) : QObject()
|
||||||
{
|
{
|
||||||
// Create config path if necessary
|
// Create config path if necessary
|
||||||
|
|
|
@ -12,18 +12,6 @@
|
||||||
#include <QObject>
|
#include <QObject>
|
||||||
#include <QComboBox>
|
#include <QComboBox>
|
||||||
|
|
||||||
#ifdef _MSC_VER
|
|
||||||
#include <Windows.h>
|
|
||||||
#undef GetHwnd
|
|
||||||
#include <d3d12.h>
|
|
||||||
#include <wrl/client.h>
|
|
||||||
#include <dxgi1_4.h>
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifdef _WIN32
|
|
||||||
#include "Emu/RSX/VK/VKHelpers.h"
|
|
||||||
#endif
|
|
||||||
|
|
||||||
inline QString qstr(const std::string& _in) { return QString::fromUtf8(_in.data(), _in.size()); }
|
inline QString qstr(const std::string& _in) { return QString::fromUtf8(_in.data(), _in.size()); }
|
||||||
|
|
||||||
struct Render_Creator
|
struct Render_Creator
|
||||||
|
@ -36,60 +24,7 @@ struct Render_Creator
|
||||||
QString render_D3D12 = QObject::tr("D3D12");
|
QString render_D3D12 = QObject::tr("D3D12");
|
||||||
QString render_OpenGL = QObject::tr("OpenGL");
|
QString render_OpenGL = QObject::tr("OpenGL");
|
||||||
|
|
||||||
Render_Creator()
|
Render_Creator();
|
||||||
{
|
|
||||||
// check for dx12 adapters
|
|
||||||
#ifdef _MSC_VER
|
|
||||||
Microsoft::WRL::ComPtr<IDXGIFactory4> dxgi_factory;
|
|
||||||
supportsD3D12 = SUCCEEDED(CreateDXGIFactory(IID_PPV_ARGS(&dxgi_factory)));
|
|
||||||
|
|
||||||
if (supportsD3D12)
|
|
||||||
{
|
|
||||||
supportsD3D12 = false;
|
|
||||||
IDXGIAdapter1* pAdapter = nullptr;
|
|
||||||
|
|
||||||
for (UINT adapterIndex = 0; DXGI_ERROR_NOT_FOUND != dxgi_factory->EnumAdapters1(adapterIndex, &pAdapter); ++adapterIndex)
|
|
||||||
{
|
|
||||||
HMODULE D3D12Module = verify("d3d12.dll", LoadLibrary(L"d3d12.dll"));
|
|
||||||
PFN_D3D12_CREATE_DEVICE wrapD3D12CreateDevice = (PFN_D3D12_CREATE_DEVICE)GetProcAddress(D3D12Module, "D3D12CreateDevice");
|
|
||||||
|
|
||||||
if (SUCCEEDED(wrapD3D12CreateDevice(pAdapter, D3D_FEATURE_LEVEL_11_0, _uuidof(ID3D12Device), nullptr)))
|
|
||||||
{
|
|
||||||
//A device with D3D12 support found. Init data
|
|
||||||
supportsD3D12 = true;
|
|
||||||
|
|
||||||
DXGI_ADAPTER_DESC desc;
|
|
||||||
pAdapter->GetDesc(&desc);
|
|
||||||
D3D12Adapters.append(QString::fromWCharArray(desc.Description));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
|
|
||||||
// check for vulkan adapters
|
|
||||||
#ifdef _WIN32
|
|
||||||
vk::context device_enum_context;
|
|
||||||
u32 instance_handle = device_enum_context.createInstance("RPCS3", true);
|
|
||||||
|
|
||||||
if (instance_handle > 0)
|
|
||||||
{
|
|
||||||
device_enum_context.makeCurrentInstance(instance_handle);
|
|
||||||
std::vector<vk::physical_device>& gpus = device_enum_context.enumerateDevices();
|
|
||||||
|
|
||||||
if (gpus.size() > 0)
|
|
||||||
{
|
|
||||||
//A device with vulkan support found. Init data
|
|
||||||
supportsVulkan = true;
|
|
||||||
|
|
||||||
for (auto& gpu : gpus)
|
|
||||||
{
|
|
||||||
vulkanAdapters.append(qstr(gpu.name()));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
|
|
||||||
}
|
|
||||||
};
|
};
|
||||||
|
|
||||||
// Node location
|
// Node location
|
||||||
|
|
|
@ -1 +0,0 @@
|
||||||
Subproject commit de3b2056edb91a439d856f1a84817c433ac1293c
|
|
Loading…
Add table
Add a link
Reference in a new issue