[GPU] Non-ROV f24 trunc/round, host shader modifications, cache dir
This commit is contained in:
parent
a86609e93a
commit
9a4643d0f2
|
@ -65,6 +65,14 @@ DEFINE_path(
|
||||||
"Root path for guest content storage (saves, etc.), or empty to use the "
|
"Root path for guest content storage (saves, etc.), or empty to use the "
|
||||||
"content folder under the storage root.",
|
"content folder under the storage root.",
|
||||||
"Storage");
|
"Storage");
|
||||||
|
DEFINE_path(
|
||||||
|
cache_root, "",
|
||||||
|
"Root path for files used to speed up certain parts of the emulator or the "
|
||||||
|
"game. These files may be persistent, but they can be deleted without "
|
||||||
|
"major side effects such as progress loss. If empty, the cache folder "
|
||||||
|
"under the storage root, or, if available, the cache directory preferred "
|
||||||
|
"for the OS, will be used.",
|
||||||
|
"Storage");
|
||||||
|
|
||||||
DEFINE_bool(mount_scratch, false, "Enable scratch mount", "Storage");
|
DEFINE_bool(mount_scratch, false, "Enable scratch mount", "Storage");
|
||||||
DEFINE_bool(mount_cache, false, "Enable cache mount", "Storage");
|
DEFINE_bool(mount_cache, false, "Enable cache mount", "Storage");
|
||||||
|
@ -221,6 +229,8 @@ int xenia_main(const std::vector<std::string>& args) {
|
||||||
#if defined(XE_PLATFORM_WIN32) || defined(XE_PLATFORM_GNU_LINUX)
|
#if defined(XE_PLATFORM_WIN32) || defined(XE_PLATFORM_GNU_LINUX)
|
||||||
storage_root = storage_root / "Xenia";
|
storage_root = storage_root / "Xenia";
|
||||||
#else
|
#else
|
||||||
|
// TODO(Triang3l): Point to the app's external storage "files" directory
|
||||||
|
// on Android.
|
||||||
#warning Unhandled platform for the data root.
|
#warning Unhandled platform for the data root.
|
||||||
storage_root = storage_root / "Xenia";
|
storage_root = storage_root / "Xenia";
|
||||||
#endif
|
#endif
|
||||||
|
@ -244,13 +254,29 @@ int xenia_main(const std::vector<std::string>& args) {
|
||||||
content_root = std::filesystem::absolute(content_root);
|
content_root = std::filesystem::absolute(content_root);
|
||||||
XELOGI("Content root: {}", xe::path_to_utf8(content_root));
|
XELOGI("Content root: {}", xe::path_to_utf8(content_root));
|
||||||
|
|
||||||
|
std::filesystem::path cache_root = cvars::cache_root;
|
||||||
|
if (cache_root.empty()) {
|
||||||
|
cache_root = storage_root / "cache";
|
||||||
|
// TODO(Triang3l): Point to the app's external storage "cache" directory on
|
||||||
|
// Android.
|
||||||
|
} else {
|
||||||
|
// If content root isn't an absolute path, then it should be relative to the
|
||||||
|
// storage root.
|
||||||
|
if (!cache_root.is_absolute()) {
|
||||||
|
cache_root = storage_root / cache_root;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
cache_root = std::filesystem::absolute(cache_root);
|
||||||
|
XELOGI("Cache root: {}", xe::path_to_utf8(cache_root));
|
||||||
|
|
||||||
if (cvars::discord) {
|
if (cvars::discord) {
|
||||||
discord::DiscordPresence::Initialize();
|
discord::DiscordPresence::Initialize();
|
||||||
discord::DiscordPresence::NotPlaying();
|
discord::DiscordPresence::NotPlaying();
|
||||||
}
|
}
|
||||||
|
|
||||||
// Create the emulator but don't initialize so we can setup the window.
|
// Create the emulator but don't initialize so we can setup the window.
|
||||||
auto emulator = std::make_unique<Emulator>("", storage_root, content_root);
|
auto emulator =
|
||||||
|
std::make_unique<Emulator>("", storage_root, content_root, cache_root);
|
||||||
|
|
||||||
// Main emulator display window.
|
// Main emulator display window.
|
||||||
auto emulator_window = EmulatorWindow::Create(emulator.get());
|
auto emulator_window = EmulatorWindow::Create(emulator.get());
|
||||||
|
|
|
@ -59,13 +59,15 @@ namespace xe {
|
||||||
|
|
||||||
Emulator::Emulator(const std::filesystem::path& command_line,
|
Emulator::Emulator(const std::filesystem::path& command_line,
|
||||||
const std::filesystem::path& storage_root,
|
const std::filesystem::path& storage_root,
|
||||||
const std::filesystem::path& content_root)
|
const std::filesystem::path& content_root,
|
||||||
|
const std::filesystem::path& cache_root)
|
||||||
: on_launch(),
|
: on_launch(),
|
||||||
on_terminate(),
|
on_terminate(),
|
||||||
on_exit(),
|
on_exit(),
|
||||||
command_line_(command_line),
|
command_line_(command_line),
|
||||||
storage_root_(storage_root),
|
storage_root_(storage_root),
|
||||||
content_root_(content_root),
|
content_root_(content_root),
|
||||||
|
cache_root_(cache_root),
|
||||||
game_title_(),
|
game_title_(),
|
||||||
display_window_(nullptr),
|
display_window_(nullptr),
|
||||||
memory_(),
|
memory_(),
|
||||||
|
@ -689,7 +691,7 @@ X_STATUS Emulator::CompleteLaunch(const std::filesystem::path& path,
|
||||||
// playing before the video can be seen if doing this in parallel with the
|
// playing before the video can be seen if doing this in parallel with the
|
||||||
// main thread.
|
// main thread.
|
||||||
on_shader_storage_initialization(true);
|
on_shader_storage_initialization(true);
|
||||||
graphics_system_->InitializeShaderStorage(storage_root_, title_id_, true);
|
graphics_system_->InitializeShaderStorage(cache_root_, title_id_, true);
|
||||||
on_shader_storage_initialization(false);
|
on_shader_storage_initialization(false);
|
||||||
|
|
||||||
auto main_thread = kernel_state_->LaunchModule(module);
|
auto main_thread = kernel_state_->LaunchModule(module);
|
||||||
|
|
|
@ -49,7 +49,8 @@ class Emulator {
|
||||||
public:
|
public:
|
||||||
explicit Emulator(const std::filesystem::path& command_line,
|
explicit Emulator(const std::filesystem::path& command_line,
|
||||||
const std::filesystem::path& storage_root,
|
const std::filesystem::path& storage_root,
|
||||||
const std::filesystem::path& content_root);
|
const std::filesystem::path& content_root,
|
||||||
|
const std::filesystem::path& cache_root);
|
||||||
~Emulator();
|
~Emulator();
|
||||||
|
|
||||||
// Full command line used when launching the process.
|
// Full command line used when launching the process.
|
||||||
|
@ -61,6 +62,9 @@ class Emulator {
|
||||||
// Folder guest content is stored in.
|
// Folder guest content is stored in.
|
||||||
const std::filesystem::path& content_root() const { return content_root_; }
|
const std::filesystem::path& content_root() const { return content_root_; }
|
||||||
|
|
||||||
|
// Folder files safe to remove without significant side effects are stored in.
|
||||||
|
const std::filesystem::path& cache_root() const { return cache_root_; }
|
||||||
|
|
||||||
// Title of the game in the default language.
|
// Title of the game in the default language.
|
||||||
const std::string& game_title() const { return game_title_; }
|
const std::string& game_title() const { return game_title_; }
|
||||||
|
|
||||||
|
@ -166,6 +170,7 @@ class Emulator {
|
||||||
std::filesystem::path command_line_;
|
std::filesystem::path command_line_;
|
||||||
std::filesystem::path storage_root_;
|
std::filesystem::path storage_root_;
|
||||||
std::filesystem::path content_root_;
|
std::filesystem::path content_root_;
|
||||||
|
std::filesystem::path cache_root_;
|
||||||
|
|
||||||
std::string game_title_;
|
std::string game_title_;
|
||||||
|
|
||||||
|
|
|
@ -89,8 +89,8 @@ void CommandProcessor::Shutdown() {
|
||||||
}
|
}
|
||||||
|
|
||||||
void CommandProcessor::InitializeShaderStorage(
|
void CommandProcessor::InitializeShaderStorage(
|
||||||
const std::filesystem::path& storage_root, uint32_t title_id,
|
const std::filesystem::path& cache_root, uint32_t title_id, bool blocking) {
|
||||||
bool blocking) {}
|
}
|
||||||
|
|
||||||
void CommandProcessor::RequestFrameTrace(
|
void CommandProcessor::RequestFrameTrace(
|
||||||
const std::filesystem::path& root_path) {
|
const std::filesystem::path& root_path) {
|
||||||
|
|
|
@ -133,9 +133,8 @@ class CommandProcessor {
|
||||||
// May be called not only from the command processor thread when the command
|
// May be called not only from the command processor thread when the command
|
||||||
// processor is paused, and the termination of this function may be explicitly
|
// processor is paused, and the termination of this function may be explicitly
|
||||||
// awaited.
|
// awaited.
|
||||||
virtual void InitializeShaderStorage(
|
virtual void InitializeShaderStorage(const std::filesystem::path& cache_root,
|
||||||
const std::filesystem::path& storage_root, uint32_t title_id,
|
uint32_t title_id, bool blocking);
|
||||||
bool blocking);
|
|
||||||
|
|
||||||
virtual void RequestFrameTrace(const std::filesystem::path& root_path);
|
virtual void RequestFrameTrace(const std::filesystem::path& root_path);
|
||||||
virtual void BeginTracing(const std::filesystem::path& root_path);
|
virtual void BeginTracing(const std::filesystem::path& root_path);
|
||||||
|
|
|
@ -73,10 +73,9 @@ void D3D12CommandProcessor::ClearCaches() {
|
||||||
}
|
}
|
||||||
|
|
||||||
void D3D12CommandProcessor::InitializeShaderStorage(
|
void D3D12CommandProcessor::InitializeShaderStorage(
|
||||||
const std::filesystem::path& storage_root, uint32_t title_id,
|
const std::filesystem::path& cache_root, uint32_t title_id, bool blocking) {
|
||||||
bool blocking) {
|
CommandProcessor::InitializeShaderStorage(cache_root, title_id, blocking);
|
||||||
CommandProcessor::InitializeShaderStorage(storage_root, title_id, blocking);
|
pipeline_cache_->InitializeShaderStorage(cache_root, title_id, blocking);
|
||||||
pipeline_cache_->InitializeShaderStorage(storage_root, title_id, blocking);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void D3D12CommandProcessor::RequestFrameTrace(
|
void D3D12CommandProcessor::RequestFrameTrace(
|
||||||
|
@ -102,7 +101,7 @@ void D3D12CommandProcessor::RestoreEdramSnapshot(const void* snapshot) {
|
||||||
}
|
}
|
||||||
|
|
||||||
uint32_t D3D12CommandProcessor::GetCurrentColorMask(
|
uint32_t D3D12CommandProcessor::GetCurrentColorMask(
|
||||||
const D3D12Shader* pixel_shader) const {
|
const Shader* pixel_shader) const {
|
||||||
if (pixel_shader == nullptr) {
|
if (pixel_shader == nullptr) {
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
@ -159,25 +158,16 @@ void D3D12CommandProcessor::SubmitBarriers() {
|
||||||
}
|
}
|
||||||
|
|
||||||
ID3D12RootSignature* D3D12CommandProcessor::GetRootSignature(
|
ID3D12RootSignature* D3D12CommandProcessor::GetRootSignature(
|
||||||
const D3D12Shader* vertex_shader, const D3D12Shader* pixel_shader) {
|
const DxbcShader* vertex_shader, const DxbcShader* pixel_shader,
|
||||||
assert_true(vertex_shader->is_translated());
|
bool tessellated) {
|
||||||
|
|
||||||
if (bindless_resources_used_) {
|
if (bindless_resources_used_) {
|
||||||
return vertex_shader->host_vertex_shader_type() !=
|
return tessellated ? root_signature_bindless_ds_
|
||||||
Shader::HostVertexShaderType::kVertex
|
: root_signature_bindless_vs_;
|
||||||
? root_signature_bindless_ds_
|
|
||||||
: root_signature_bindless_vs_;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
assert_true(pixel_shader == nullptr || pixel_shader->is_translated());
|
D3D12_SHADER_VISIBILITY vertex_visibility =
|
||||||
|
tessellated ? D3D12_SHADER_VISIBILITY_DOMAIN
|
||||||
D3D12_SHADER_VISIBILITY vertex_visibility;
|
: D3D12_SHADER_VISIBILITY_VERTEX;
|
||||||
if (vertex_shader->host_vertex_shader_type() !=
|
|
||||||
Shader::HostVertexShaderType::kVertex) {
|
|
||||||
vertex_visibility = D3D12_SHADER_VISIBILITY_DOMAIN;
|
|
||||||
} else {
|
|
||||||
vertex_visibility = D3D12_SHADER_VISIBILITY_VERTEX;
|
|
||||||
}
|
|
||||||
|
|
||||||
uint32_t texture_count_vertex, sampler_count_vertex;
|
uint32_t texture_count_vertex, sampler_count_vertex;
|
||||||
vertex_shader->GetTextureBindings(texture_count_vertex);
|
vertex_shader->GetTextureBindings(texture_count_vertex);
|
||||||
|
@ -393,7 +383,7 @@ ID3D12RootSignature* D3D12CommandProcessor::GetRootSignature(
|
||||||
}
|
}
|
||||||
|
|
||||||
uint32_t D3D12CommandProcessor::GetRootBindfulExtraParameterIndices(
|
uint32_t D3D12CommandProcessor::GetRootBindfulExtraParameterIndices(
|
||||||
const D3D12Shader* vertex_shader, const D3D12Shader* pixel_shader,
|
const DxbcShader* vertex_shader, const DxbcShader* pixel_shader,
|
||||||
RootBindfulExtraParameterIndices& indices_out) {
|
RootBindfulExtraParameterIndices& indices_out) {
|
||||||
uint32_t texture_count_pixel = 0, sampler_count_pixel = 0;
|
uint32_t texture_count_pixel = 0, sampler_count_pixel = 0;
|
||||||
if (pixel_shader != nullptr) {
|
if (pixel_shader != nullptr) {
|
||||||
|
@ -1202,6 +1192,7 @@ bool D3D12CommandProcessor::SetupContext() {
|
||||||
|
|
||||||
pipeline_cache_ = std::make_unique<PipelineCache>(
|
pipeline_cache_ = std::make_unique<PipelineCache>(
|
||||||
*this, *register_file_, bindless_resources_used_, edram_rov_used_,
|
*this, *register_file_, bindless_resources_used_, edram_rov_used_,
|
||||||
|
render_target_cache_->depth_float24_conversion(),
|
||||||
texture_cache_->IsResolutionScale2X() ? 2 : 1);
|
texture_cache_->IsResolutionScale2X() ? 2 : 1);
|
||||||
if (!pipeline_cache_->Initialize()) {
|
if (!pipeline_cache_->Initialize()) {
|
||||||
XELOGE("Failed to initialize the graphics pipeline cache");
|
XELOGE("Failed to initialize the graphics pipeline cache");
|
||||||
|
@ -1804,8 +1795,7 @@ Shader* D3D12CommandProcessor::LoadShader(xenos::ShaderType shader_type,
|
||||||
uint32_t guest_address,
|
uint32_t guest_address,
|
||||||
const uint32_t* host_address,
|
const uint32_t* host_address,
|
||||||
uint32_t dword_count) {
|
uint32_t dword_count) {
|
||||||
return pipeline_cache_->LoadShader(shader_type, guest_address, host_address,
|
return pipeline_cache_->LoadShader(shader_type, host_address, dword_count);
|
||||||
dword_count);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
bool D3D12CommandProcessor::IssueDraw(xenos::PrimitiveType primitive_type,
|
bool D3D12CommandProcessor::IssueDraw(xenos::PrimitiveType primitive_type,
|
||||||
|
@ -1851,21 +1841,30 @@ bool D3D12CommandProcessor::IssueDraw(xenos::PrimitiveType primitive_type,
|
||||||
// Need a pixel shader in normal color mode.
|
// Need a pixel shader in normal color mode.
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
// Get tessellation info for the current draw for vertex shader translation.
|
DxbcShaderTranslator::Modification vertex_shader_modification;
|
||||||
Shader::HostVertexShaderType host_vertex_shader_type =
|
DxbcShaderTranslator::Modification pixel_shader_modification;
|
||||||
pipeline_cache_->GetHostVertexShaderTypeIfValid();
|
if (!pipeline_cache_->GetCurrentShaderModifications(
|
||||||
if (host_vertex_shader_type == Shader::HostVertexShaderType(-1)) {
|
vertex_shader_modification, pixel_shader_modification)) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
D3D12Shader::D3D12Translation* vertex_shader_translation =
|
||||||
|
static_cast<D3D12Shader::D3D12Translation*>(
|
||||||
|
vertex_shader->GetOrCreateTranslation(
|
||||||
|
vertex_shader_modification.value));
|
||||||
|
D3D12Shader::D3D12Translation* pixel_shader_translation =
|
||||||
|
pixel_shader ? static_cast<D3D12Shader::D3D12Translation*>(
|
||||||
|
pixel_shader->GetOrCreateTranslation(
|
||||||
|
pixel_shader_modification.value))
|
||||||
|
: nullptr;
|
||||||
// Translate the shaders now to get memexport configuration and color mask,
|
// Translate the shaders now to get memexport configuration and color mask,
|
||||||
// which is needed by the render target cache, to check the possibility of
|
// which is needed by the render target cache, and also to get used textures
|
||||||
// doing early depth/stencil, and also to get used textures and samplers.
|
// and samplers.
|
||||||
if (!pipeline_cache_->EnsureShadersTranslated(vertex_shader, pixel_shader,
|
if (!pipeline_cache_->EnsureShadersTranslated(vertex_shader_translation,
|
||||||
host_vertex_shader_type)) {
|
pixel_shader_translation)) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
bool tessellated =
|
bool tessellated = vertex_shader_modification.host_vertex_shader_type !=
|
||||||
host_vertex_shader_type != Shader::HostVertexShaderType::kVertex;
|
Shader::HostVertexShaderType::kVertex;
|
||||||
|
|
||||||
// Check if memexport is used. If it is, we can't skip draw calls that have no
|
// Check if memexport is used. If it is, we can't skip draw calls that have no
|
||||||
// visual effect.
|
// visual effect.
|
||||||
|
@ -1967,26 +1966,14 @@ bool D3D12CommandProcessor::IssueDraw(xenos::PrimitiveType primitive_type,
|
||||||
(pixel_shader != nullptr ? pixel_shader->GetUsedTextureMask() : 0);
|
(pixel_shader != nullptr ? pixel_shader->GetUsedTextureMask() : 0);
|
||||||
texture_cache_->RequestTextures(used_texture_mask);
|
texture_cache_->RequestTextures(used_texture_mask);
|
||||||
|
|
||||||
// Check if early depth/stencil can be enabled.
|
|
||||||
bool early_z;
|
|
||||||
if (pixel_shader) {
|
|
||||||
auto rb_colorcontrol = regs.Get<reg::RB_COLORCONTROL>();
|
|
||||||
early_z = pixel_shader->implicit_early_z_allowed() &&
|
|
||||||
(!rb_colorcontrol.alpha_test_enable ||
|
|
||||||
rb_colorcontrol.alpha_func == xenos::CompareFunction::kAlways) &&
|
|
||||||
!rb_colorcontrol.alpha_to_mask_enable;
|
|
||||||
} else {
|
|
||||||
early_z = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Create the pipeline if needed and bind it.
|
// Create the pipeline if needed and bind it.
|
||||||
void* pipeline_handle;
|
void* pipeline_handle;
|
||||||
ID3D12RootSignature* root_signature;
|
ID3D12RootSignature* root_signature;
|
||||||
if (!pipeline_cache_->ConfigurePipeline(
|
if (!pipeline_cache_->ConfigurePipeline(
|
||||||
vertex_shader, pixel_shader, primitive_type_converted,
|
vertex_shader_translation, pixel_shader_translation,
|
||||||
|
primitive_type_converted,
|
||||||
indexed ? index_buffer_info->format : xenos::IndexFormat::kInt16,
|
indexed ? index_buffer_info->format : xenos::IndexFormat::kInt16,
|
||||||
early_z, pipeline_render_targets, &pipeline_handle,
|
pipeline_render_targets, &pipeline_handle, &root_signature)) {
|
||||||
&root_signature)) {
|
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
if (current_cached_pipeline_ != pipeline_handle) {
|
if (current_cached_pipeline_ != pipeline_handle) {
|
||||||
|
@ -2014,11 +2001,18 @@ bool D3D12CommandProcessor::IssueDraw(xenos::PrimitiveType primitive_type,
|
||||||
pixel_size_x *= 2;
|
pixel_size_x *= 2;
|
||||||
pixel_size_y *= 2;
|
pixel_size_y *= 2;
|
||||||
}
|
}
|
||||||
|
flags::DepthFloat24Conversion depth_float24_conversion =
|
||||||
|
render_target_cache_->depth_float24_conversion();
|
||||||
draw_util::ViewportInfo viewport_info;
|
draw_util::ViewportInfo viewport_info;
|
||||||
draw_util::GetHostViewportInfo(regs, float(pixel_size_x), float(pixel_size_y),
|
draw_util::GetHostViewportInfo(
|
||||||
true, float(D3D12_VIEWPORT_BOUNDS_MAX),
|
regs, float(pixel_size_x), float(pixel_size_y), true,
|
||||||
float(D3D12_VIEWPORT_BOUNDS_MAX), false,
|
float(D3D12_VIEWPORT_BOUNDS_MAX), float(D3D12_VIEWPORT_BOUNDS_MAX), false,
|
||||||
viewport_info);
|
!edram_rov_used_ &&
|
||||||
|
(depth_float24_conversion ==
|
||||||
|
flags::DepthFloat24Conversion::kOnOutputTruncating ||
|
||||||
|
depth_float24_conversion ==
|
||||||
|
flags::DepthFloat24Conversion::kOnOutputRounding),
|
||||||
|
viewport_info);
|
||||||
draw_util::Scissor scissor;
|
draw_util::Scissor scissor;
|
||||||
draw_util::GetScissor(regs, scissor);
|
draw_util::GetScissor(regs, scissor);
|
||||||
scissor.left *= pixel_size_x;
|
scissor.left *= pixel_size_x;
|
||||||
|
@ -2033,7 +2027,7 @@ bool D3D12CommandProcessor::IssueDraw(xenos::PrimitiveType primitive_type,
|
||||||
UpdateSystemConstantValues(
|
UpdateSystemConstantValues(
|
||||||
memexport_used, primitive_polygonal, line_loop_closing_index,
|
memexport_used, primitive_polygonal, line_loop_closing_index,
|
||||||
indexed ? index_buffer_info->endianness : xenos::Endian::kNone,
|
indexed ? index_buffer_info->endianness : xenos::Endian::kNone,
|
||||||
viewport_info, pixel_size_x, pixel_size_y, used_texture_mask, early_z,
|
viewport_info, pixel_size_x, pixel_size_y, used_texture_mask,
|
||||||
GetCurrentColorMask(pixel_shader), pipeline_render_targets);
|
GetCurrentColorMask(pixel_shader), pipeline_render_targets);
|
||||||
|
|
||||||
// Update constant buffers, descriptors and root parameters.
|
// Update constant buffers, descriptors and root parameters.
|
||||||
|
@ -2873,8 +2867,7 @@ void D3D12CommandProcessor::UpdateSystemConstantValues(
|
||||||
bool shared_memory_is_uav, bool primitive_polygonal,
|
bool shared_memory_is_uav, bool primitive_polygonal,
|
||||||
uint32_t line_loop_closing_index, xenos::Endian index_endian,
|
uint32_t line_loop_closing_index, xenos::Endian index_endian,
|
||||||
const draw_util::ViewportInfo& viewport_info, uint32_t pixel_size_x,
|
const draw_util::ViewportInfo& viewport_info, uint32_t pixel_size_x,
|
||||||
uint32_t pixel_size_y, uint32_t used_texture_mask, bool early_z,
|
uint32_t pixel_size_y, uint32_t used_texture_mask, uint32_t color_mask,
|
||||||
uint32_t color_mask,
|
|
||||||
const RenderTargetCache::PipelineRenderTarget render_targets[4]) {
|
const RenderTargetCache::PipelineRenderTarget render_targets[4]) {
|
||||||
#if XE_UI_D3D12_FINE_GRAINED_DRAW_SCOPES
|
#if XE_UI_D3D12_FINE_GRAINED_DRAW_SCOPES
|
||||||
SCOPE_profile_cpu_f("gpu");
|
SCOPE_profile_cpu_f("gpu");
|
||||||
|
@ -2992,14 +2985,11 @@ void D3D12CommandProcessor::UpdateSystemConstantValues(
|
||||||
flags |= DxbcShaderTranslator::kSysFlag_KillIfAnyVertexKilled;
|
flags |= DxbcShaderTranslator::kSysFlag_KillIfAnyVertexKilled;
|
||||||
}
|
}
|
||||||
// Alpha test.
|
// Alpha test.
|
||||||
if (rb_colorcontrol.alpha_test_enable) {
|
xenos::CompareFunction alpha_test_function =
|
||||||
flags |= uint32_t(rb_colorcontrol.alpha_func)
|
rb_colorcontrol.alpha_test_enable ? rb_colorcontrol.alpha_func
|
||||||
<< DxbcShaderTranslator::kSysFlag_AlphaPassIfLess_Shift;
|
: xenos::CompareFunction::kAlways;
|
||||||
} else {
|
flags |= uint32_t(alpha_test_function)
|
||||||
flags |= DxbcShaderTranslator::kSysFlag_AlphaPassIfLess |
|
<< DxbcShaderTranslator::kSysFlag_AlphaPassIfLess_Shift;
|
||||||
DxbcShaderTranslator::kSysFlag_AlphaPassIfEqual |
|
|
||||||
DxbcShaderTranslator::kSysFlag_AlphaPassIfGreater;
|
|
||||||
}
|
|
||||||
// Gamma writing.
|
// Gamma writing.
|
||||||
for (uint32_t i = 0; i < 4; ++i) {
|
for (uint32_t i = 0; i < 4; ++i) {
|
||||||
if (color_infos[i].color_format ==
|
if (color_infos[i].color_format ==
|
||||||
|
@ -3028,7 +3018,9 @@ void D3D12CommandProcessor::UpdateSystemConstantValues(
|
||||||
if (rb_depthcontrol.stencil_enable) {
|
if (rb_depthcontrol.stencil_enable) {
|
||||||
flags |= DxbcShaderTranslator::kSysFlag_ROVStencilTest;
|
flags |= DxbcShaderTranslator::kSysFlag_ROVStencilTest;
|
||||||
}
|
}
|
||||||
if (early_z) {
|
// Hint - if not applicable to the shader, will not have effect.
|
||||||
|
if (alpha_test_function == xenos::CompareFunction::kAlways &&
|
||||||
|
!rb_colorcontrol.alpha_to_mask_enable) {
|
||||||
flags |= DxbcShaderTranslator::kSysFlag_ROVDepthStencilEarlyWrite;
|
flags |= DxbcShaderTranslator::kSysFlag_ROVDepthStencilEarlyWrite;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -27,6 +27,7 @@
|
||||||
#include "xenia/gpu/d3d12/render_target_cache.h"
|
#include "xenia/gpu/d3d12/render_target_cache.h"
|
||||||
#include "xenia/gpu/d3d12/texture_cache.h"
|
#include "xenia/gpu/d3d12/texture_cache.h"
|
||||||
#include "xenia/gpu/draw_util.h"
|
#include "xenia/gpu/draw_util.h"
|
||||||
|
#include "xenia/gpu/dxbc_shader.h"
|
||||||
#include "xenia/gpu/dxbc_shader_translator.h"
|
#include "xenia/gpu/dxbc_shader_translator.h"
|
||||||
#include "xenia/gpu/xenos.h"
|
#include "xenia/gpu/xenos.h"
|
||||||
#include "xenia/kernel/kernel_state.h"
|
#include "xenia/kernel/kernel_state.h"
|
||||||
|
@ -47,7 +48,7 @@ class D3D12CommandProcessor : public CommandProcessor {
|
||||||
|
|
||||||
void ClearCaches() override;
|
void ClearCaches() override;
|
||||||
|
|
||||||
void InitializeShaderStorage(const std::filesystem::path& storage_root,
|
void InitializeShaderStorage(const std::filesystem::path& cache_root,
|
||||||
uint32_t title_id, bool blocking) override;
|
uint32_t title_id, bool blocking) override;
|
||||||
|
|
||||||
void RequestFrameTrace(const std::filesystem::path& root_path) override;
|
void RequestFrameTrace(const std::filesystem::path& root_path) override;
|
||||||
|
@ -88,7 +89,7 @@ class D3D12CommandProcessor : public CommandProcessor {
|
||||||
// there are 4 render targets bound with the same EDRAM base (clearly not
|
// there are 4 render targets bound with the same EDRAM base (clearly not
|
||||||
// correct usage), but the shader only clears 1, and then EDRAM buffer stores
|
// correct usage), but the shader only clears 1, and then EDRAM buffer stores
|
||||||
// conflict with each other.
|
// conflict with each other.
|
||||||
uint32_t GetCurrentColorMask(const D3D12Shader* pixel_shader) const;
|
uint32_t GetCurrentColorMask(const Shader* pixel_shader) const;
|
||||||
|
|
||||||
void PushTransitionBarrier(
|
void PushTransitionBarrier(
|
||||||
ID3D12Resource* resource, D3D12_RESOURCE_STATES old_state,
|
ID3D12Resource* resource, D3D12_RESOURCE_STATES old_state,
|
||||||
|
@ -100,8 +101,9 @@ class D3D12CommandProcessor : public CommandProcessor {
|
||||||
void SubmitBarriers();
|
void SubmitBarriers();
|
||||||
|
|
||||||
// Finds or creates root signature for a pipeline.
|
// Finds or creates root signature for a pipeline.
|
||||||
ID3D12RootSignature* GetRootSignature(const D3D12Shader* vertex_shader,
|
ID3D12RootSignature* GetRootSignature(const DxbcShader* vertex_shader,
|
||||||
const D3D12Shader* pixel_shader);
|
const DxbcShader* pixel_shader,
|
||||||
|
bool tessellated);
|
||||||
|
|
||||||
ui::d3d12::D3D12UploadBufferPool& GetConstantBufferPool() const {
|
ui::d3d12::D3D12UploadBufferPool& GetConstantBufferPool() const {
|
||||||
return *constant_buffer_pool_;
|
return *constant_buffer_pool_;
|
||||||
|
@ -300,7 +302,7 @@ class D3D12CommandProcessor : public CommandProcessor {
|
||||||
// Gets the indices of optional root parameters. Returns the total parameter
|
// Gets the indices of optional root parameters. Returns the total parameter
|
||||||
// count.
|
// count.
|
||||||
static uint32_t GetRootBindfulExtraParameterIndices(
|
static uint32_t GetRootBindfulExtraParameterIndices(
|
||||||
const D3D12Shader* vertex_shader, const D3D12Shader* pixel_shader,
|
const DxbcShader* vertex_shader, const DxbcShader* pixel_shader,
|
||||||
RootBindfulExtraParameterIndices& indices_out);
|
RootBindfulExtraParameterIndices& indices_out);
|
||||||
|
|
||||||
// BeginSubmission and EndSubmission may be called at any time. If there's an
|
// BeginSubmission and EndSubmission may be called at any time. If there's an
|
||||||
|
@ -353,8 +355,7 @@ class D3D12CommandProcessor : public CommandProcessor {
|
||||||
bool shared_memory_is_uav, bool primitive_polygonal,
|
bool shared_memory_is_uav, bool primitive_polygonal,
|
||||||
uint32_t line_loop_closing_index, xenos::Endian index_endian,
|
uint32_t line_loop_closing_index, xenos::Endian index_endian,
|
||||||
const draw_util::ViewportInfo& viewport_info, uint32_t pixel_size_x,
|
const draw_util::ViewportInfo& viewport_info, uint32_t pixel_size_x,
|
||||||
uint32_t pixel_size_y, uint32_t used_texture_mask, bool early_z,
|
uint32_t pixel_size_y, uint32_t used_texture_mask, uint32_t color_mask,
|
||||||
uint32_t color_mask,
|
|
||||||
const RenderTargetCache::PipelineRenderTarget render_targets[4]);
|
const RenderTargetCache::PipelineRenderTarget render_targets[4]);
|
||||||
bool UpdateBindings(const D3D12Shader* vertex_shader,
|
bool UpdateBindings(const D3D12Shader* vertex_shader,
|
||||||
const D3D12Shader* pixel_shader,
|
const D3D12Shader* pixel_shader,
|
||||||
|
|
|
@ -10,9 +10,11 @@
|
||||||
#include "xenia/gpu/d3d12/d3d12_shader.h"
|
#include "xenia/gpu/d3d12/d3d12_shader.h"
|
||||||
|
|
||||||
#include <cstring>
|
#include <cstring>
|
||||||
|
#include <utility>
|
||||||
|
|
||||||
#include "xenia/base/assert.h"
|
#include "xenia/base/assert.h"
|
||||||
#include "xenia/base/logging.h"
|
#include "xenia/base/logging.h"
|
||||||
|
#include "xenia/gpu/dxbc_shader.h"
|
||||||
#include "xenia/gpu/gpu_flags.h"
|
#include "xenia/gpu/gpu_flags.h"
|
||||||
#include "xenia/ui/d3d12/d3d12_api.h"
|
#include "xenia/ui/d3d12/d3d12_api.h"
|
||||||
|
|
||||||
|
@ -22,51 +24,13 @@ namespace d3d12 {
|
||||||
|
|
||||||
D3D12Shader::D3D12Shader(xenos::ShaderType shader_type, uint64_t data_hash,
|
D3D12Shader::D3D12Shader(xenos::ShaderType shader_type, uint64_t data_hash,
|
||||||
const uint32_t* dword_ptr, uint32_t dword_count)
|
const uint32_t* dword_ptr, uint32_t dword_count)
|
||||||
: Shader(shader_type, data_hash, dword_ptr, dword_count) {}
|
: DxbcShader(shader_type, data_hash, dword_ptr, dword_count) {}
|
||||||
|
|
||||||
void D3D12Shader::SetTexturesAndSamplers(
|
void D3D12Shader::D3D12Translation::DisassembleDxbcAndDxil(
|
||||||
const DxbcShaderTranslator::TextureBinding* texture_bindings,
|
const ui::d3d12::D3D12Provider& provider, bool disassemble_dxbc,
|
||||||
uint32_t texture_binding_count,
|
IDxbcConverter* dxbc_converter, IDxcUtils* dxc_utils,
|
||||||
const DxbcShaderTranslator::SamplerBinding* sampler_bindings,
|
IDxcCompiler* dxc_compiler) {
|
||||||
uint32_t sampler_binding_count) {
|
std::string disassembly;
|
||||||
texture_bindings_.clear();
|
|
||||||
texture_bindings_.reserve(texture_binding_count);
|
|
||||||
used_texture_mask_ = 0;
|
|
||||||
for (uint32_t i = 0; i < texture_binding_count; ++i) {
|
|
||||||
TextureBinding& binding = texture_bindings_.emplace_back();
|
|
||||||
// For a stable hash.
|
|
||||||
std::memset(&binding, 0, sizeof(binding));
|
|
||||||
const DxbcShaderTranslator::TextureBinding& translator_binding =
|
|
||||||
texture_bindings[i];
|
|
||||||
binding.bindless_descriptor_index =
|
|
||||||
translator_binding.bindless_descriptor_index;
|
|
||||||
binding.fetch_constant = translator_binding.fetch_constant;
|
|
||||||
binding.dimension = translator_binding.dimension;
|
|
||||||
binding.is_signed = translator_binding.is_signed;
|
|
||||||
used_texture_mask_ |= 1u << translator_binding.fetch_constant;
|
|
||||||
}
|
|
||||||
sampler_bindings_.clear();
|
|
||||||
sampler_bindings_.reserve(sampler_binding_count);
|
|
||||||
for (uint32_t i = 0; i < sampler_binding_count; ++i) {
|
|
||||||
SamplerBinding binding;
|
|
||||||
const DxbcShaderTranslator::SamplerBinding& translator_binding =
|
|
||||||
sampler_bindings[i];
|
|
||||||
binding.bindless_descriptor_index =
|
|
||||||
translator_binding.bindless_descriptor_index;
|
|
||||||
binding.fetch_constant = translator_binding.fetch_constant;
|
|
||||||
binding.mag_filter = translator_binding.mag_filter;
|
|
||||||
binding.min_filter = translator_binding.min_filter;
|
|
||||||
binding.mip_filter = translator_binding.mip_filter;
|
|
||||||
binding.aniso_filter = translator_binding.aniso_filter;
|
|
||||||
sampler_bindings_.push_back(binding);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void D3D12Shader::DisassembleDxbc(const ui::d3d12::D3D12Provider& provider,
|
|
||||||
bool disassemble_dxbc,
|
|
||||||
IDxbcConverter* dxbc_converter,
|
|
||||||
IDxcUtils* dxc_utils,
|
|
||||||
IDxcCompiler* dxc_compiler) {
|
|
||||||
bool is_first_disassembly = true;
|
bool is_first_disassembly = true;
|
||||||
if (disassemble_dxbc) {
|
if (disassemble_dxbc) {
|
||||||
ID3DBlob* dxbc_disassembly;
|
ID3DBlob* dxbc_disassembly;
|
||||||
|
@ -77,11 +41,12 @@ void D3D12Shader::DisassembleDxbc(const ui::d3d12::D3D12Provider& provider,
|
||||||
nullptr, &dxbc_disassembly))) {
|
nullptr, &dxbc_disassembly))) {
|
||||||
assert_true(is_first_disassembly);
|
assert_true(is_first_disassembly);
|
||||||
is_first_disassembly = false;
|
is_first_disassembly = false;
|
||||||
host_disassembly_.append(
|
disassembly.append(
|
||||||
reinterpret_cast<const char*>(dxbc_disassembly->GetBufferPointer()));
|
reinterpret_cast<const char*>(dxbc_disassembly->GetBufferPointer()));
|
||||||
dxbc_disassembly->Release();
|
dxbc_disassembly->Release();
|
||||||
} else {
|
} else {
|
||||||
XELOGE("Failed to disassemble DXBC shader {:016X}", ucode_data_hash());
|
XELOGE("Failed to disassemble DXBC shader {:016X}",
|
||||||
|
shader().ucode_data_hash());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (dxbc_converter && dxc_utils && dxc_compiler) {
|
if (dxbc_converter && dxc_utils && dxc_compiler) {
|
||||||
|
@ -106,29 +71,36 @@ void D3D12Shader::DisassembleDxbc(const ui::d3d12::D3D12Provider& provider,
|
||||||
dxil_disassembly->Release();
|
dxil_disassembly->Release();
|
||||||
if (dxil_disassembly_got_utf8) {
|
if (dxil_disassembly_got_utf8) {
|
||||||
if (!is_first_disassembly) {
|
if (!is_first_disassembly) {
|
||||||
host_disassembly_.append("\n\n");
|
disassembly.append("\n\n");
|
||||||
}
|
}
|
||||||
is_first_disassembly = false;
|
is_first_disassembly = false;
|
||||||
host_disassembly_.append(reinterpret_cast<const char*>(
|
disassembly.append(reinterpret_cast<const char*>(
|
||||||
dxil_disassembly_utf8->GetStringPointer()));
|
dxil_disassembly_utf8->GetStringPointer()));
|
||||||
dxil_disassembly_utf8->Release();
|
dxil_disassembly_utf8->Release();
|
||||||
} else {
|
} else {
|
||||||
XELOGE("Failed to get DXIL shader {:016X} disassembly as UTF-8",
|
XELOGE("Failed to get DXIL shader {:016X} disassembly as UTF-8",
|
||||||
ucode_data_hash());
|
shader().ucode_data_hash());
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
XELOGE("Failed to disassemble DXIL shader {:016X}",
|
XELOGE("Failed to disassemble DXIL shader {:016X}",
|
||||||
ucode_data_hash());
|
shader().ucode_data_hash());
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
XELOGE("Failed to create a blob with DXIL shader {:016X}",
|
XELOGE("Failed to create a blob with DXIL shader {:016X}",
|
||||||
ucode_data_hash());
|
shader().ucode_data_hash());
|
||||||
CoTaskMemFree(dxil);
|
CoTaskMemFree(dxil);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
XELOGE("Failed to convert shader {:016X} to DXIL", ucode_data_hash());
|
XELOGE("Failed to convert shader {:016X} to DXIL",
|
||||||
|
shader().ucode_data_hash());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
set_host_disassembly(std::move(disassembly));
|
||||||
|
}
|
||||||
|
|
||||||
|
Shader::Translation* D3D12Shader::CreateTranslationInstance(
|
||||||
|
uint32_t modification) {
|
||||||
|
return new D3D12Translation(*this, modification);
|
||||||
}
|
}
|
||||||
|
|
||||||
} // namespace d3d12
|
} // namespace d3d12
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
******************************************************************************
|
******************************************************************************
|
||||||
* Xenia : Xbox 360 Emulator Research Project *
|
* Xenia : Xbox 360 Emulator Research Project *
|
||||||
******************************************************************************
|
******************************************************************************
|
||||||
* Copyright 2018 Ben Vanik. All rights reserved. *
|
* Copyright 2020 Ben Vanik. All rights reserved. *
|
||||||
* Released under the BSD license - see LICENSE in the root for more details. *
|
* Released under the BSD license - see LICENSE in the root for more details. *
|
||||||
******************************************************************************
|
******************************************************************************
|
||||||
*/
|
*/
|
||||||
|
@ -10,106 +10,62 @@
|
||||||
#ifndef XENIA_GPU_D3D12_D3D12_SHADER_H_
|
#ifndef XENIA_GPU_D3D12_D3D12_SHADER_H_
|
||||||
#define XENIA_GPU_D3D12_D3D12_SHADER_H_
|
#define XENIA_GPU_D3D12_D3D12_SHADER_H_
|
||||||
|
|
||||||
#include <vector>
|
#include <atomic>
|
||||||
|
|
||||||
#include "xenia/gpu/dxbc_shader_translator.h"
|
#include "xenia/gpu/dxbc_shader.h"
|
||||||
#include "xenia/gpu/shader.h"
|
|
||||||
#include "xenia/gpu/xenos.h"
|
|
||||||
#include "xenia/ui/d3d12/d3d12_provider.h"
|
#include "xenia/ui/d3d12/d3d12_provider.h"
|
||||||
|
|
||||||
namespace xe {
|
namespace xe {
|
||||||
namespace gpu {
|
namespace gpu {
|
||||||
namespace d3d12 {
|
namespace d3d12 {
|
||||||
|
|
||||||
class D3D12Shader : public Shader {
|
class D3D12Shader : public DxbcShader {
|
||||||
public:
|
public:
|
||||||
|
class D3D12Translation : public DxbcTranslation {
|
||||||
|
public:
|
||||||
|
D3D12Translation(D3D12Shader& shader, uint32_t modification)
|
||||||
|
: DxbcTranslation(shader, modification) {}
|
||||||
|
|
||||||
|
void DisassembleDxbcAndDxil(const ui::d3d12::D3D12Provider& provider,
|
||||||
|
bool disassemble_dxbc,
|
||||||
|
IDxbcConverter* dxbc_converter = nullptr,
|
||||||
|
IDxcUtils* dxc_utils = nullptr,
|
||||||
|
IDxcCompiler* dxc_compiler = nullptr);
|
||||||
|
};
|
||||||
|
|
||||||
D3D12Shader(xenos::ShaderType shader_type, uint64_t data_hash,
|
D3D12Shader(xenos::ShaderType shader_type, uint64_t data_hash,
|
||||||
const uint32_t* dword_ptr, uint32_t dword_count);
|
const uint32_t* dword_ptr, uint32_t dword_count);
|
||||||
|
|
||||||
void SetTexturesAndSamplers(
|
// For owning subsystem like the pipeline cache, accessors for unique
|
||||||
const DxbcShaderTranslator::TextureBinding* texture_bindings,
|
|
||||||
uint32_t texture_binding_count,
|
|
||||||
const DxbcShaderTranslator::SamplerBinding* sampler_bindings,
|
|
||||||
uint32_t sampler_binding_count);
|
|
||||||
|
|
||||||
void SetForcedEarlyZShaderObject(const std::vector<uint8_t>& shader_object) {
|
|
||||||
forced_early_z_shader_ = shader_object;
|
|
||||||
}
|
|
||||||
// Returns the shader with forced early depth/stencil set with
|
|
||||||
// SetForcedEarlyZShader after translation. If there's none (for example,
|
|
||||||
// if the shader discards pixels or writes to the depth buffer), an empty
|
|
||||||
// vector is returned.
|
|
||||||
const std::vector<uint8_t>& GetForcedEarlyZShaderObject() const {
|
|
||||||
return forced_early_z_shader_;
|
|
||||||
}
|
|
||||||
|
|
||||||
void DisassembleDxbc(const ui::d3d12::D3D12Provider& provider,
|
|
||||||
bool disassemble_dxbc,
|
|
||||||
IDxbcConverter* dxbc_converter = nullptr,
|
|
||||||
IDxcUtils* dxc_utils = nullptr,
|
|
||||||
IDxcCompiler* dxc_compiler = nullptr);
|
|
||||||
|
|
||||||
static constexpr uint32_t kMaxTextureBindingIndexBits =
|
|
||||||
DxbcShaderTranslator::kMaxTextureBindingIndexBits;
|
|
||||||
static constexpr uint32_t kMaxTextureBindings =
|
|
||||||
DxbcShaderTranslator::kMaxTextureBindings;
|
|
||||||
struct TextureBinding {
|
|
||||||
uint32_t bindless_descriptor_index;
|
|
||||||
uint32_t fetch_constant;
|
|
||||||
// Stacked and 3D are separate TextureBindings, even for bindless for null
|
|
||||||
// descriptor handling simplicity.
|
|
||||||
xenos::FetchOpDimension dimension;
|
|
||||||
bool is_signed;
|
|
||||||
};
|
|
||||||
// Safe to hash and compare with memcmp for layout hashing.
|
|
||||||
const TextureBinding* GetTextureBindings(uint32_t& count_out) const {
|
|
||||||
count_out = uint32_t(texture_bindings_.size());
|
|
||||||
return texture_bindings_.data();
|
|
||||||
}
|
|
||||||
const uint32_t GetUsedTextureMask() const { return used_texture_mask_; }
|
|
||||||
|
|
||||||
static constexpr uint32_t kMaxSamplerBindingIndexBits =
|
|
||||||
DxbcShaderTranslator::kMaxSamplerBindingIndexBits;
|
|
||||||
static constexpr uint32_t kMaxSamplerBindings =
|
|
||||||
DxbcShaderTranslator::kMaxSamplerBindings;
|
|
||||||
struct SamplerBinding {
|
|
||||||
uint32_t bindless_descriptor_index;
|
|
||||||
uint32_t fetch_constant;
|
|
||||||
xenos::TextureFilter mag_filter;
|
|
||||||
xenos::TextureFilter min_filter;
|
|
||||||
xenos::TextureFilter mip_filter;
|
|
||||||
xenos::AnisoFilter aniso_filter;
|
|
||||||
};
|
|
||||||
const SamplerBinding* GetSamplerBindings(uint32_t& count_out) const {
|
|
||||||
count_out = uint32_t(sampler_bindings_.size());
|
|
||||||
return sampler_bindings_.data();
|
|
||||||
}
|
|
||||||
|
|
||||||
// For owning subsystems like the pipeline cache, accessors for unique
|
|
||||||
// identifiers (used instead of hashes to make sure collisions can't happen)
|
// identifiers (used instead of hashes to make sure collisions can't happen)
|
||||||
// of binding layouts used by the shader, for invalidation if a shader with an
|
// of binding layouts used by the shader, for invalidation if a shader with an
|
||||||
// incompatible layout was bound.
|
// incompatible layout was bound.
|
||||||
size_t GetTextureBindingLayoutUserUID() const {
|
size_t GetTextureBindingLayoutUserUID() const {
|
||||||
return texture_binding_layout_user_uid_;
|
return texture_binding_layout_user_uid_;
|
||||||
}
|
}
|
||||||
void SetTextureBindingLayoutUserUID(size_t uid) {
|
|
||||||
texture_binding_layout_user_uid_ = uid;
|
|
||||||
}
|
|
||||||
size_t GetSamplerBindingLayoutUserUID() const {
|
size_t GetSamplerBindingLayoutUserUID() const {
|
||||||
return sampler_binding_layout_user_uid_;
|
return sampler_binding_layout_user_uid_;
|
||||||
}
|
}
|
||||||
|
// Modifications of the same shader can be translated on different threads.
|
||||||
|
// The "set" function must only be called if "enter" returned true - these are
|
||||||
|
// set up only once.
|
||||||
|
bool EnterBindingLayoutUserUIDSetup() {
|
||||||
|
return !binding_layout_user_uids_set_up_.test_and_set();
|
||||||
|
}
|
||||||
|
void SetTextureBindingLayoutUserUID(size_t uid) {
|
||||||
|
texture_binding_layout_user_uid_ = uid;
|
||||||
|
}
|
||||||
void SetSamplerBindingLayoutUserUID(size_t uid) {
|
void SetSamplerBindingLayoutUserUID(size_t uid) {
|
||||||
sampler_binding_layout_user_uid_ = uid;
|
sampler_binding_layout_user_uid_ = uid;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
protected:
|
||||||
|
Translation* CreateTranslationInstance(uint32_t modification) override;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
std::vector<TextureBinding> texture_bindings_;
|
std::atomic_flag binding_layout_user_uids_set_up_ = ATOMIC_FLAG_INIT;
|
||||||
std::vector<SamplerBinding> sampler_bindings_;
|
|
||||||
size_t texture_binding_layout_user_uid_ = 0;
|
size_t texture_binding_layout_user_uid_ = 0;
|
||||||
size_t sampler_binding_layout_user_uid_ = 0;
|
size_t sampler_binding_layout_user_uid_ = 0;
|
||||||
uint32_t used_texture_mask_ = 0;
|
|
||||||
|
|
||||||
std::vector<uint8_t> forced_early_z_shader_;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
} // namespace d3d12
|
} // namespace d3d12
|
||||||
|
|
File diff suppressed because it is too large
Load Diff
|
@ -27,6 +27,7 @@
|
||||||
#include "xenia/gpu/d3d12/d3d12_shader.h"
|
#include "xenia/gpu/d3d12/d3d12_shader.h"
|
||||||
#include "xenia/gpu/d3d12/render_target_cache.h"
|
#include "xenia/gpu/d3d12/render_target_cache.h"
|
||||||
#include "xenia/gpu/dxbc_shader_translator.h"
|
#include "xenia/gpu/dxbc_shader_translator.h"
|
||||||
|
#include "xenia/gpu/gpu_flags.h"
|
||||||
#include "xenia/gpu/register_file.h"
|
#include "xenia/gpu/register_file.h"
|
||||||
#include "xenia/gpu/xenos.h"
|
#include "xenia/gpu/xenos.h"
|
||||||
#include "xenia/ui/d3d12/d3d12_api.h"
|
#include "xenia/ui/d3d12/d3d12_api.h"
|
||||||
|
@ -43,36 +44,39 @@ class PipelineCache {
|
||||||
|
|
||||||
PipelineCache(D3D12CommandProcessor& command_processor,
|
PipelineCache(D3D12CommandProcessor& command_processor,
|
||||||
const RegisterFile& register_file, bool bindless_resources_used,
|
const RegisterFile& register_file, bool bindless_resources_used,
|
||||||
bool edram_rov_used, uint32_t resolution_scale);
|
bool edram_rov_used,
|
||||||
|
flags::DepthFloat24Conversion depth_float24_conversion,
|
||||||
|
uint32_t resolution_scale);
|
||||||
~PipelineCache();
|
~PipelineCache();
|
||||||
|
|
||||||
bool Initialize();
|
bool Initialize();
|
||||||
void Shutdown();
|
void Shutdown();
|
||||||
void ClearCache(bool shutting_down = false);
|
void ClearCache(bool shutting_down = false);
|
||||||
|
|
||||||
void InitializeShaderStorage(const std::filesystem::path& storage_root,
|
void InitializeShaderStorage(const std::filesystem::path& cache_root,
|
||||||
uint32_t title_id, bool blocking);
|
uint32_t title_id, bool blocking);
|
||||||
void ShutdownShaderStorage();
|
void ShutdownShaderStorage();
|
||||||
|
|
||||||
void EndSubmission();
|
void EndSubmission();
|
||||||
bool IsCreatingPipelines();
|
bool IsCreatingPipelines();
|
||||||
|
|
||||||
D3D12Shader* LoadShader(xenos::ShaderType shader_type, uint32_t guest_address,
|
D3D12Shader* LoadShader(xenos::ShaderType shader_type,
|
||||||
const uint32_t* host_address, uint32_t dword_count);
|
const uint32_t* host_address, uint32_t dword_count);
|
||||||
|
|
||||||
// Returns the host vertex shader type for the current draw if it's valid and
|
// Retrieves the shader modifications for the current state, and returns
|
||||||
// supported, or Shader::HostVertexShaderType(-1) if not.
|
// whether they are valid.
|
||||||
Shader::HostVertexShaderType GetHostVertexShaderTypeIfValid() const;
|
bool GetCurrentShaderModifications(
|
||||||
|
DxbcShaderTranslator::Modification& vertex_shader_modification_out,
|
||||||
|
DxbcShaderTranslator::Modification& pixel_shader_modification_out) const;
|
||||||
|
|
||||||
// Translates shaders if needed, also making shader info up to date.
|
// Translates shaders if needed, also making shader info up to date.
|
||||||
bool EnsureShadersTranslated(
|
bool EnsureShadersTranslated(D3D12Shader::D3D12Translation* vertex_shader,
|
||||||
D3D12Shader* vertex_shader, D3D12Shader* pixel_shader,
|
D3D12Shader::D3D12Translation* pixel_shader);
|
||||||
Shader::HostVertexShaderType host_vertex_shader_type);
|
|
||||||
|
|
||||||
bool ConfigurePipeline(
|
bool ConfigurePipeline(
|
||||||
D3D12Shader* vertex_shader, D3D12Shader* pixel_shader,
|
D3D12Shader::D3D12Translation* vertex_shader,
|
||||||
|
D3D12Shader::D3D12Translation* pixel_shader,
|
||||||
xenos::PrimitiveType primitive_type, xenos::IndexFormat index_format,
|
xenos::PrimitiveType primitive_type, xenos::IndexFormat index_format,
|
||||||
bool early_z,
|
|
||||||
const RenderTargetCache::PipelineRenderTarget render_targets[5],
|
const RenderTargetCache::PipelineRenderTarget render_targets[5],
|
||||||
void** pipeline_handle_out, ID3D12RootSignature** root_signature_out);
|
void** pipeline_handle_out, ID3D12RootSignature** root_signature_out);
|
||||||
|
|
||||||
|
@ -86,13 +90,12 @@ class PipelineCache {
|
||||||
XEPACKEDSTRUCT(ShaderStoredHeader, {
|
XEPACKEDSTRUCT(ShaderStoredHeader, {
|
||||||
uint64_t ucode_data_hash;
|
uint64_t ucode_data_hash;
|
||||||
|
|
||||||
uint32_t ucode_dword_count : 16;
|
uint32_t ucode_dword_count : 31;
|
||||||
xenos::ShaderType type : 1;
|
xenos::ShaderType type : 1;
|
||||||
Shader::HostVertexShaderType host_vertex_shader_type : 3;
|
|
||||||
|
|
||||||
reg::SQ_PROGRAM_CNTL sq_program_cntl;
|
reg::SQ_PROGRAM_CNTL sq_program_cntl;
|
||||||
|
|
||||||
static constexpr uint32_t kVersion = 0x20200405;
|
static constexpr uint32_t kVersion = 0x20201129;
|
||||||
});
|
});
|
||||||
|
|
||||||
// Update PipelineDescription::kVersion if any of the Pipeline* enums are
|
// Update PipelineDescription::kVersion if any of the Pipeline* enums are
|
||||||
|
@ -170,28 +173,28 @@ class PipelineCache {
|
||||||
uint64_t vertex_shader_hash;
|
uint64_t vertex_shader_hash;
|
||||||
// 0 if drawing without a pixel shader.
|
// 0 if drawing without a pixel shader.
|
||||||
uint64_t pixel_shader_hash;
|
uint64_t pixel_shader_hash;
|
||||||
|
uint32_t vertex_shader_modification;
|
||||||
|
uint32_t pixel_shader_modification;
|
||||||
|
|
||||||
int32_t depth_bias;
|
int32_t depth_bias;
|
||||||
float depth_bias_slope_scaled;
|
float depth_bias_slope_scaled;
|
||||||
|
|
||||||
PipelineStripCutIndex strip_cut_index : 2; // 2
|
PipelineStripCutIndex strip_cut_index : 2; // 2
|
||||||
Shader::HostVertexShaderType host_vertex_shader_type : 3; // 5
|
|
||||||
// PipelinePrimitiveTopologyType for a vertex shader.
|
// PipelinePrimitiveTopologyType for a vertex shader.
|
||||||
// xenos::TessellationMode for a domain shader.
|
// xenos::TessellationMode for a domain shader.
|
||||||
uint32_t primitive_topology_type_or_tessellation_mode : 2; // 7
|
uint32_t primitive_topology_type_or_tessellation_mode : 2; // 4
|
||||||
// Zero for non-kVertex host_vertex_shader_type.
|
// Zero for non-kVertex host_vertex_shader_type.
|
||||||
PipelineGeometryShader geometry_shader : 2; // 9
|
PipelineGeometryShader geometry_shader : 2; // 6
|
||||||
uint32_t fill_mode_wireframe : 1; // 10
|
uint32_t fill_mode_wireframe : 1; // 7
|
||||||
PipelineCullMode cull_mode : 2; // 12
|
PipelineCullMode cull_mode : 2; // 9
|
||||||
uint32_t front_counter_clockwise : 1; // 13
|
uint32_t front_counter_clockwise : 1; // 10
|
||||||
uint32_t depth_clip : 1; // 14
|
uint32_t depth_clip : 1; // 11
|
||||||
uint32_t rov_msaa : 1; // 15
|
uint32_t rov_msaa : 1; // 12
|
||||||
xenos::DepthRenderTargetFormat depth_format : 1; // 16
|
xenos::DepthRenderTargetFormat depth_format : 1; // 13
|
||||||
xenos::CompareFunction depth_func : 3; // 19
|
xenos::CompareFunction depth_func : 3; // 16
|
||||||
uint32_t depth_write : 1; // 20
|
uint32_t depth_write : 1; // 17
|
||||||
uint32_t stencil_enable : 1; // 21
|
uint32_t stencil_enable : 1; // 18
|
||||||
uint32_t stencil_read_mask : 8; // 29
|
uint32_t stencil_read_mask : 8; // 26
|
||||||
uint32_t force_early_z : 1; // 30
|
|
||||||
|
|
||||||
uint32_t stencil_write_mask : 8; // 8
|
uint32_t stencil_write_mask : 8; // 8
|
||||||
xenos::StencilOp stencil_front_fail_op : 3; // 11
|
xenos::StencilOp stencil_front_fail_op : 3; // 11
|
||||||
|
@ -205,7 +208,7 @@ class PipelineCache {
|
||||||
|
|
||||||
PipelineRenderTarget render_targets[4];
|
PipelineRenderTarget render_targets[4];
|
||||||
|
|
||||||
static constexpr uint32_t kVersion = 0x20200405;
|
static constexpr uint32_t kVersion = 0x20201202;
|
||||||
});
|
});
|
||||||
|
|
||||||
XEPACKEDSTRUCT(PipelineStoredDescription, {
|
XEPACKEDSTRUCT(PipelineStoredDescription, {
|
||||||
|
@ -215,24 +218,31 @@ class PipelineCache {
|
||||||
|
|
||||||
struct PipelineRuntimeDescription {
|
struct PipelineRuntimeDescription {
|
||||||
ID3D12RootSignature* root_signature;
|
ID3D12RootSignature* root_signature;
|
||||||
D3D12Shader* vertex_shader;
|
D3D12Shader::D3D12Translation* vertex_shader;
|
||||||
D3D12Shader* pixel_shader;
|
D3D12Shader::D3D12Translation* pixel_shader;
|
||||||
PipelineDescription description;
|
PipelineDescription description;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
// Returns the host vertex shader type for the current draw if it's valid and
|
||||||
|
// supported, or Shader::HostVertexShaderType(-1) if not.
|
||||||
|
Shader::HostVertexShaderType GetCurrentHostVertexShaderTypeIfValid() const;
|
||||||
|
|
||||||
|
D3D12Shader* LoadShader(xenos::ShaderType shader_type,
|
||||||
|
const uint32_t* host_address, uint32_t dword_count,
|
||||||
|
uint64_t data_hash);
|
||||||
|
|
||||||
// Can be called from multiple threads.
|
// Can be called from multiple threads.
|
||||||
bool TranslateShader(DxbcShaderTranslator& translator, D3D12Shader& shader,
|
bool TranslateShader(DxbcShaderTranslator& translator,
|
||||||
|
D3D12Shader::D3D12Translation& translation,
|
||||||
reg::SQ_PROGRAM_CNTL cntl,
|
reg::SQ_PROGRAM_CNTL cntl,
|
||||||
IDxbcConverter* dxbc_converter = nullptr,
|
IDxbcConverter* dxbc_converter = nullptr,
|
||||||
IDxcUtils* dxc_utils = nullptr,
|
IDxcUtils* dxc_utils = nullptr,
|
||||||
IDxcCompiler* dxc_compiler = nullptr,
|
IDxcCompiler* dxc_compiler = nullptr);
|
||||||
Shader::HostVertexShaderType host_vertex_shader_type =
|
|
||||||
Shader::HostVertexShaderType::kVertex);
|
|
||||||
|
|
||||||
bool GetCurrentStateDescription(
|
bool GetCurrentStateDescription(
|
||||||
D3D12Shader* vertex_shader, D3D12Shader* pixel_shader,
|
D3D12Shader::D3D12Translation* vertex_shader,
|
||||||
|
D3D12Shader::D3D12Translation* pixel_shader,
|
||||||
xenos::PrimitiveType primitive_type, xenos::IndexFormat index_format,
|
xenos::PrimitiveType primitive_type, xenos::IndexFormat index_format,
|
||||||
bool early_z,
|
|
||||||
const RenderTargetCache::PipelineRenderTarget render_targets[5],
|
const RenderTargetCache::PipelineRenderTarget render_targets[5],
|
||||||
PipelineRuntimeDescription& runtime_description_out);
|
PipelineRuntimeDescription& runtime_description_out);
|
||||||
|
|
||||||
|
@ -243,6 +253,8 @@ class PipelineCache {
|
||||||
const RegisterFile& register_file_;
|
const RegisterFile& register_file_;
|
||||||
bool bindless_resources_used_;
|
bool bindless_resources_used_;
|
||||||
bool edram_rov_used_;
|
bool edram_rov_used_;
|
||||||
|
// 20e4 depth conversion mode to use for non-ROV output.
|
||||||
|
flags::DepthFloat24Conversion depth_float24_conversion_;
|
||||||
uint32_t resolution_scale_;
|
uint32_t resolution_scale_;
|
||||||
|
|
||||||
// Reusable shader translator.
|
// Reusable shader translator.
|
||||||
|
@ -300,11 +312,14 @@ class PipelineCache {
|
||||||
Pipeline* current_pipeline_ = nullptr;
|
Pipeline* current_pipeline_ = nullptr;
|
||||||
|
|
||||||
// Currently open shader storage path.
|
// Currently open shader storage path.
|
||||||
std::filesystem::path shader_storage_root_;
|
std::filesystem::path shader_storage_cache_root_;
|
||||||
uint32_t shader_storage_title_id_ = 0;
|
uint32_t shader_storage_title_id_ = 0;
|
||||||
|
|
||||||
// Shader storage output stream, for preload in the next emulator runs.
|
// Shader storage output stream, for preload in the next emulator runs.
|
||||||
FILE* shader_storage_file_ = nullptr;
|
FILE* shader_storage_file_ = nullptr;
|
||||||
|
// For only writing shaders to the currently open storage once, incremented
|
||||||
|
// when switching the storage.
|
||||||
|
uint32_t shader_storage_index_ = 0;
|
||||||
bool shader_storage_file_flush_needed_ = false;
|
bool shader_storage_file_flush_needed_ = false;
|
||||||
|
|
||||||
// Pipeline storage output stream, for preload in the next emulator runs.
|
// Pipeline storage output stream, for preload in the next emulator runs.
|
||||||
|
|
|
@ -40,11 +40,13 @@ namespace d3d12 {
|
||||||
#include "xenia/gpu/d3d12/shaders/dxbc/edram_load_color_32bpp_cs.h"
|
#include "xenia/gpu/d3d12/shaders/dxbc/edram_load_color_32bpp_cs.h"
|
||||||
#include "xenia/gpu/d3d12/shaders/dxbc/edram_load_color_64bpp_cs.h"
|
#include "xenia/gpu/d3d12/shaders/dxbc/edram_load_color_64bpp_cs.h"
|
||||||
#include "xenia/gpu/d3d12/shaders/dxbc/edram_load_color_7e3_cs.h"
|
#include "xenia/gpu/d3d12/shaders/dxbc/edram_load_color_7e3_cs.h"
|
||||||
|
#include "xenia/gpu/d3d12/shaders/dxbc/edram_load_depth_float24and32_cs.h"
|
||||||
#include "xenia/gpu/d3d12/shaders/dxbc/edram_load_depth_float_cs.h"
|
#include "xenia/gpu/d3d12/shaders/dxbc/edram_load_depth_float_cs.h"
|
||||||
#include "xenia/gpu/d3d12/shaders/dxbc/edram_load_depth_unorm_cs.h"
|
#include "xenia/gpu/d3d12/shaders/dxbc/edram_load_depth_unorm_cs.h"
|
||||||
#include "xenia/gpu/d3d12/shaders/dxbc/edram_store_color_32bpp_cs.h"
|
#include "xenia/gpu/d3d12/shaders/dxbc/edram_store_color_32bpp_cs.h"
|
||||||
#include "xenia/gpu/d3d12/shaders/dxbc/edram_store_color_64bpp_cs.h"
|
#include "xenia/gpu/d3d12/shaders/dxbc/edram_store_color_64bpp_cs.h"
|
||||||
#include "xenia/gpu/d3d12/shaders/dxbc/edram_store_color_7e3_cs.h"
|
#include "xenia/gpu/d3d12/shaders/dxbc/edram_store_color_7e3_cs.h"
|
||||||
|
#include "xenia/gpu/d3d12/shaders/dxbc/edram_store_depth_float24and32_cs.h"
|
||||||
#include "xenia/gpu/d3d12/shaders/dxbc/edram_store_depth_float_cs.h"
|
#include "xenia/gpu/d3d12/shaders/dxbc/edram_store_depth_float_cs.h"
|
||||||
#include "xenia/gpu/d3d12/shaders/dxbc/edram_store_depth_unorm_cs.h"
|
#include "xenia/gpu/d3d12/shaders/dxbc/edram_store_depth_unorm_cs.h"
|
||||||
#include "xenia/gpu/d3d12/shaders/dxbc/resolve_clear_32bpp_2xres_cs.h"
|
#include "xenia/gpu/d3d12/shaders/dxbc/resolve_clear_32bpp_2xres_cs.h"
|
||||||
|
@ -87,6 +89,12 @@ const RenderTargetCache::EdramLoadStoreModeInfo
|
||||||
{edram_load_depth_float_cs, sizeof(edram_load_depth_float_cs),
|
{edram_load_depth_float_cs, sizeof(edram_load_depth_float_cs),
|
||||||
L"EDRAM Load Float Depth", edram_store_depth_float_cs,
|
L"EDRAM Load Float Depth", edram_store_depth_float_cs,
|
||||||
sizeof(edram_store_depth_float_cs), L"EDRAM Store Float Depth"},
|
sizeof(edram_store_depth_float_cs), L"EDRAM Store Float Depth"},
|
||||||
|
{edram_load_depth_float24and32_cs,
|
||||||
|
sizeof(edram_load_depth_float24and32_cs),
|
||||||
|
L"EDRAM Load 24-bit & 32-bit Float Depth",
|
||||||
|
edram_store_depth_float24and32_cs,
|
||||||
|
sizeof(edram_store_depth_float24and32_cs),
|
||||||
|
L"EDRAM Store 24-bit & 32-bit Float Depth"},
|
||||||
};
|
};
|
||||||
|
|
||||||
const std::pair<const uint8_t*, size_t>
|
const std::pair<const uint8_t*, size_t>
|
||||||
|
@ -126,6 +134,8 @@ RenderTargetCache::RenderTargetCache(D3D12CommandProcessor& command_processor,
|
||||||
RenderTargetCache::~RenderTargetCache() { Shutdown(); }
|
RenderTargetCache::~RenderTargetCache() { Shutdown(); }
|
||||||
|
|
||||||
bool RenderTargetCache::Initialize(const TextureCache& texture_cache) {
|
bool RenderTargetCache::Initialize(const TextureCache& texture_cache) {
|
||||||
|
depth_float24_conversion_ = flags::GetDepthFloat24Conversion();
|
||||||
|
|
||||||
// EDRAM buffer size depends on this.
|
// EDRAM buffer size depends on this.
|
||||||
resolution_scale_2x_ = texture_cache.IsResolutionScale2X();
|
resolution_scale_2x_ = texture_cache.IsResolutionScale2X();
|
||||||
assert_false(resolution_scale_2x_ && !edram_rov_used_);
|
assert_false(resolution_scale_2x_ && !edram_rov_used_);
|
||||||
|
@ -420,7 +430,8 @@ bool RenderTargetCache::Initialize(const TextureCache& texture_cache) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
resolve_clear_64bpp_pipeline_->SetName(L"Resolve Clear 64bpp");
|
resolve_clear_64bpp_pipeline_->SetName(L"Resolve Clear 64bpp");
|
||||||
if (!edram_rov_used_) {
|
if (!edram_rov_used_ &&
|
||||||
|
depth_float24_conversion_ == flags::DepthFloat24Conversion::kOnCopy) {
|
||||||
assert_false(resolution_scale_2x_);
|
assert_false(resolution_scale_2x_);
|
||||||
resolve_clear_depth_24_32_pipeline_ =
|
resolve_clear_depth_24_32_pipeline_ =
|
||||||
ui::d3d12::util::CreateComputePipeline(
|
ui::d3d12::util::CreateComputePipeline(
|
||||||
|
@ -434,7 +445,7 @@ bool RenderTargetCache::Initialize(const TextureCache& texture_cache) {
|
||||||
Shutdown();
|
Shutdown();
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
resolve_clear_64bpp_pipeline_->SetName(
|
resolve_clear_depth_24_32_pipeline_->SetName(
|
||||||
L"Resolve Clear 24-bit & 32-bit Depth");
|
L"Resolve Clear 24-bit & 32-bit Depth");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1266,10 +1277,12 @@ bool RenderTargetCache::Resolve(const Memory& memory,
|
||||||
if (clear_depth) {
|
if (clear_depth) {
|
||||||
// Also clear the host 32-bit floating-point depth used for loaing and
|
// Also clear the host 32-bit floating-point depth used for loaing and
|
||||||
// storing 24-bit floating-point depth at full precision.
|
// storing 24-bit floating-point depth at full precision.
|
||||||
bool clear_float32_depth =
|
bool clear_float32_depth = !edram_rov_used_ &&
|
||||||
!edram_rov_used_ && xenos::DepthRenderTargetFormat(
|
depth_float24_conversion_ ==
|
||||||
resolve_info.depth_edram_info.format) ==
|
flags::DepthFloat24Conversion::kOnCopy &&
|
||||||
xenos::DepthRenderTargetFormat::kD24FS8;
|
xenos::DepthRenderTargetFormat(
|
||||||
|
resolve_info.depth_edram_info.format) ==
|
||||||
|
xenos::DepthRenderTargetFormat::kD24FS8;
|
||||||
draw_util::ResolveClearShaderConstants depth_clear_constants;
|
draw_util::ResolveClearShaderConstants depth_clear_constants;
|
||||||
resolve_info.GetDepthClearShaderConstants(clear_float32_depth,
|
resolve_info.GetDepthClearShaderConstants(clear_float32_depth,
|
||||||
depth_clear_constants);
|
depth_clear_constants);
|
||||||
|
@ -1558,7 +1571,8 @@ void RenderTargetCache::RestoreEdramSnapshot(const void* snapshot) {
|
||||||
|
|
||||||
uint32_t RenderTargetCache::GetEdramBufferSize() const {
|
uint32_t RenderTargetCache::GetEdramBufferSize() const {
|
||||||
uint32_t size = xenos::kEdramSizeBytes;
|
uint32_t size = xenos::kEdramSizeBytes;
|
||||||
if (!edram_rov_used_) {
|
if (!edram_rov_used_ &&
|
||||||
|
depth_float24_conversion_ == flags::DepthFloat24Conversion::kOnCopy) {
|
||||||
// Two 10 MB pages, one containing color and integer depth data, another
|
// Two 10 MB pages, one containing color and integer depth data, another
|
||||||
// with 32-bit float depth when 20e4 depth is used to allow for multipass
|
// with 32-bit float depth when 20e4 depth is used to allow for multipass
|
||||||
// drawing without precision loss in case of EDRAM store/load.
|
// drawing without precision loss in case of EDRAM store/load.
|
||||||
|
@ -1831,12 +1845,15 @@ RenderTargetCache::RenderTarget* RenderTargetCache::FindOrCreateRenderTarget(
|
||||||
}
|
}
|
||||||
|
|
||||||
RenderTargetCache::EdramLoadStoreMode RenderTargetCache::GetLoadStoreMode(
|
RenderTargetCache::EdramLoadStoreMode RenderTargetCache::GetLoadStoreMode(
|
||||||
bool is_depth, uint32_t format) {
|
bool is_depth, uint32_t format) const {
|
||||||
if (is_depth) {
|
if (is_depth) {
|
||||||
return xenos::DepthRenderTargetFormat(format) ==
|
if (xenos::DepthRenderTargetFormat(format) ==
|
||||||
xenos::DepthRenderTargetFormat::kD24FS8
|
xenos::DepthRenderTargetFormat::kD24FS8) {
|
||||||
? EdramLoadStoreMode::kDepthFloat
|
return depth_float24_conversion_ == flags::DepthFloat24Conversion::kOnCopy
|
||||||
: EdramLoadStoreMode::kDepthUnorm;
|
? EdramLoadStoreMode::kDepthFloat24And32
|
||||||
|
: EdramLoadStoreMode::kDepthFloat;
|
||||||
|
}
|
||||||
|
return EdramLoadStoreMode::kDepthUnorm;
|
||||||
}
|
}
|
||||||
xenos::ColorRenderTargetFormat color_format =
|
xenos::ColorRenderTargetFormat color_format =
|
||||||
xenos::ColorRenderTargetFormat(format);
|
xenos::ColorRenderTargetFormat(format);
|
||||||
|
|
|
@ -18,6 +18,7 @@
|
||||||
#include "xenia/gpu/d3d12/d3d12_shared_memory.h"
|
#include "xenia/gpu/d3d12/d3d12_shared_memory.h"
|
||||||
#include "xenia/gpu/d3d12/texture_cache.h"
|
#include "xenia/gpu/d3d12/texture_cache.h"
|
||||||
#include "xenia/gpu/draw_util.h"
|
#include "xenia/gpu/draw_util.h"
|
||||||
|
#include "xenia/gpu/gpu_flags.h"
|
||||||
#include "xenia/gpu/register_file.h"
|
#include "xenia/gpu/register_file.h"
|
||||||
#include "xenia/gpu/trace_writer.h"
|
#include "xenia/gpu/trace_writer.h"
|
||||||
#include "xenia/gpu/xenos.h"
|
#include "xenia/gpu/xenos.h"
|
||||||
|
@ -259,6 +260,10 @@ class RenderTargetCache {
|
||||||
void Shutdown();
|
void Shutdown();
|
||||||
void ClearCache();
|
void ClearCache();
|
||||||
|
|
||||||
|
flags::DepthFloat24Conversion depth_float24_conversion() const {
|
||||||
|
return depth_float24_conversion_;
|
||||||
|
}
|
||||||
|
|
||||||
void CompletedSubmissionUpdated();
|
void CompletedSubmissionUpdated();
|
||||||
void BeginSubmission();
|
void BeginSubmission();
|
||||||
void EndFrame();
|
void EndFrame();
|
||||||
|
@ -318,6 +323,7 @@ class RenderTargetCache {
|
||||||
kColor7e3,
|
kColor7e3,
|
||||||
kDepthUnorm,
|
kDepthUnorm,
|
||||||
kDepthFloat,
|
kDepthFloat,
|
||||||
|
kDepthFloat24And32,
|
||||||
|
|
||||||
kCount
|
kCount
|
||||||
};
|
};
|
||||||
|
@ -424,7 +430,7 @@ class RenderTargetCache {
|
||||||
uint32_t instance);
|
uint32_t instance);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
static EdramLoadStoreMode GetLoadStoreMode(bool is_depth, uint32_t format);
|
EdramLoadStoreMode GetLoadStoreMode(bool is_depth, uint32_t format) const;
|
||||||
|
|
||||||
// Must be in a frame to call. Stores the dirty areas of the currently bound
|
// Must be in a frame to call. Stores the dirty areas of the currently bound
|
||||||
// render targets and marks them as clean.
|
// render targets and marks them as clean.
|
||||||
|
@ -442,6 +448,9 @@ class RenderTargetCache {
|
||||||
bool bindless_resources_used_;
|
bool bindless_resources_used_;
|
||||||
bool edram_rov_used_;
|
bool edram_rov_used_;
|
||||||
|
|
||||||
|
// 20e4 depth conversion mode to use for non-ROV output.
|
||||||
|
flags::DepthFloat24Conversion depth_float24_conversion_;
|
||||||
|
|
||||||
// Whether 1 guest pixel is rendered as 2x2 host pixels (currently only
|
// Whether 1 guest pixel is rendered as 2x2 host pixels (currently only
|
||||||
// supported with ROV).
|
// supported with ROV).
|
||||||
bool resolution_scale_2x_ = false;
|
bool resolution_scale_2x_ = false;
|
||||||
|
|
Binary file not shown.
|
@ -0,0 +1,296 @@
|
||||||
|
// generated from `xb buildhlsl`
|
||||||
|
// source: edram_load_depth_float24and32.cs.hlsl
|
||||||
|
const uint8_t edram_load_depth_float24and32_cs[] = {
|
||||||
|
0x44, 0x58, 0x42, 0x43, 0xF3, 0xA3, 0xA4, 0x14, 0x0A, 0x50, 0x56, 0x49,
|
||||||
|
0x5D, 0x09, 0x6C, 0xBF, 0x33, 0xC9, 0xC1, 0x9A, 0x01, 0x00, 0x00, 0x00,
|
||||||
|
0xAC, 0x0D, 0x00, 0x00, 0x05, 0x00, 0x00, 0x00, 0x34, 0x00, 0x00, 0x00,
|
||||||
|
0x0C, 0x03, 0x00, 0x00, 0x1C, 0x03, 0x00, 0x00, 0x2C, 0x03, 0x00, 0x00,
|
||||||
|
0x10, 0x0D, 0x00, 0x00, 0x52, 0x44, 0x45, 0x46, 0xD0, 0x02, 0x00, 0x00,
|
||||||
|
0x01, 0x00, 0x00, 0x00, 0x04, 0x01, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x3C, 0x00, 0x00, 0x00, 0x01, 0x05, 0x53, 0x43, 0x00, 0x05, 0x00, 0x00,
|
||||||
|
0xA8, 0x02, 0x00, 0x00, 0x13, 0x13, 0x44, 0x25, 0x3C, 0x00, 0x00, 0x00,
|
||||||
|
0x18, 0x00, 0x00, 0x00, 0x28, 0x00, 0x00, 0x00, 0x28, 0x00, 0x00, 0x00,
|
||||||
|
0x24, 0x00, 0x00, 0x00, 0x0C, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0xB4, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0xCF, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00,
|
||||||
|
0x06, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xE8, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x78, 0x65, 0x5F, 0x65, 0x64, 0x72, 0x61, 0x6D, 0x5F, 0x6C, 0x6F, 0x61,
|
||||||
|
0x64, 0x5F, 0x73, 0x74, 0x6F, 0x72, 0x65, 0x5F, 0x73, 0x6F, 0x75, 0x72,
|
||||||
|
0x63, 0x65, 0x00, 0x78, 0x65, 0x5F, 0x65, 0x64, 0x72, 0x61, 0x6D, 0x5F,
|
||||||
|
0x6C, 0x6F, 0x61, 0x64, 0x5F, 0x73, 0x74, 0x6F, 0x72, 0x65, 0x5F, 0x64,
|
||||||
|
0x65, 0x73, 0x74, 0x00, 0x58, 0x65, 0x45, 0x64, 0x72, 0x61, 0x6D, 0x4C,
|
||||||
|
0x6F, 0x61, 0x64, 0x53, 0x74, 0x6F, 0x72, 0x65, 0x43, 0x6F, 0x6E, 0x73,
|
||||||
|
0x74, 0x61, 0x6E, 0x74, 0x73, 0x00, 0xAB, 0xAB, 0xE8, 0x00, 0x00, 0x00,
|
||||||
|
0x05, 0x00, 0x00, 0x00, 0x1C, 0x01, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xE4, 0x01, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
|
0x0C, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x30, 0x02, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x0C, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x4E, 0x02, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00,
|
||||||
|
0x04, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x0C, 0x02, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00, 0x69, 0x02, 0x00, 0x00,
|
||||||
|
0x0C, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
|
0x0C, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x83, 0x02, 0x00, 0x00, 0x10, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x0C, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x78, 0x65, 0x5F, 0x65, 0x64, 0x72, 0x61, 0x6D,
|
||||||
|
0x5F, 0x72, 0x74, 0x5F, 0x63, 0x6F, 0x6C, 0x6F, 0x72, 0x5F, 0x64, 0x65,
|
||||||
|
0x70, 0x74, 0x68, 0x5F, 0x6F, 0x66, 0x66, 0x73, 0x65, 0x74, 0x00, 0x64,
|
||||||
|
0x77, 0x6F, 0x72, 0x64, 0x00, 0xAB, 0xAB, 0xAB, 0x00, 0x00, 0x13, 0x00,
|
||||||
|
0x01, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x03, 0x02, 0x00, 0x00, 0x78, 0x65, 0x5F, 0x65,
|
||||||
|
0x64, 0x72, 0x61, 0x6D, 0x5F, 0x72, 0x74, 0x5F, 0x63, 0x6F, 0x6C, 0x6F,
|
||||||
|
0x72, 0x5F, 0x64, 0x65, 0x70, 0x74, 0x68, 0x5F, 0x70, 0x69, 0x74, 0x63,
|
||||||
|
0x68, 0x00, 0x78, 0x65, 0x5F, 0x65, 0x64, 0x72, 0x61, 0x6D, 0x5F, 0x72,
|
||||||
|
0x74, 0x5F, 0x73, 0x74, 0x65, 0x6E, 0x63, 0x69, 0x6C, 0x5F, 0x6F, 0x66,
|
||||||
|
0x66, 0x73, 0x65, 0x74, 0x00, 0x78, 0x65, 0x5F, 0x65, 0x64, 0x72, 0x61,
|
||||||
|
0x6D, 0x5F, 0x72, 0x74, 0x5F, 0x73, 0x74, 0x65, 0x6E, 0x63, 0x69, 0x6C,
|
||||||
|
0x5F, 0x70, 0x69, 0x74, 0x63, 0x68, 0x00, 0x78, 0x65, 0x5F, 0x65, 0x64,
|
||||||
|
0x72, 0x61, 0x6D, 0x5F, 0x62, 0x61, 0x73, 0x65, 0x5F, 0x73, 0x61, 0x6D,
|
||||||
|
0x70, 0x6C, 0x65, 0x73, 0x5F, 0x32, 0x78, 0x5F, 0x64, 0x65, 0x70, 0x74,
|
||||||
|
0x68, 0x5F, 0x70, 0x69, 0x74, 0x63, 0x68, 0x00, 0x4D, 0x69, 0x63, 0x72,
|
||||||
|
0x6F, 0x73, 0x6F, 0x66, 0x74, 0x20, 0x28, 0x52, 0x29, 0x20, 0x48, 0x4C,
|
||||||
|
0x53, 0x4C, 0x20, 0x53, 0x68, 0x61, 0x64, 0x65, 0x72, 0x20, 0x43, 0x6F,
|
||||||
|
0x6D, 0x70, 0x69, 0x6C, 0x65, 0x72, 0x20, 0x31, 0x30, 0x2E, 0x31, 0x00,
|
||||||
|
0x49, 0x53, 0x47, 0x4E, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x08, 0x00, 0x00, 0x00, 0x4F, 0x53, 0x47, 0x4E, 0x08, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x53, 0x48, 0x45, 0x58,
|
||||||
|
0xDC, 0x09, 0x00, 0x00, 0x51, 0x00, 0x05, 0x00, 0x77, 0x02, 0x00, 0x00,
|
||||||
|
0x6A, 0x08, 0x00, 0x01, 0x59, 0x00, 0x00, 0x07, 0x46, 0x8E, 0x30, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xA1, 0x00, 0x00, 0x06,
|
||||||
|
0x46, 0x7E, 0x30, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x9D, 0x00, 0x00, 0x06,
|
||||||
|
0x46, 0xEE, 0x31, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x5F, 0x00, 0x00, 0x02,
|
||||||
|
0x32, 0x10, 0x02, 0x00, 0x5F, 0x00, 0x00, 0x02, 0x32, 0x20, 0x02, 0x00,
|
||||||
|
0x5F, 0x00, 0x00, 0x02, 0x32, 0x00, 0x02, 0x00, 0x68, 0x00, 0x00, 0x02,
|
||||||
|
0x07, 0x00, 0x00, 0x00, 0x9B, 0x00, 0x00, 0x04, 0x14, 0x00, 0x00, 0x00,
|
||||||
|
0x10, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x29, 0x00, 0x00, 0x06,
|
||||||
|
0x12, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0A, 0x20, 0x02, 0x00,
|
||||||
|
0x01, 0x40, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x0C,
|
||||||
|
0x62, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x06, 0x80, 0x30, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
|
0x02, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x80, 0x00, 0x00,
|
||||||
|
0xFF, 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1F, 0x00, 0x04, 0x03,
|
||||||
|
0x1A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x4F, 0x00, 0x00, 0x06,
|
||||||
|
0x22, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0A, 0x20, 0x02, 0x00,
|
||||||
|
0x01, 0x40, 0x00, 0x00, 0x0A, 0x00, 0x00, 0x00, 0x50, 0x00, 0x00, 0x06,
|
||||||
|
0x82, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0A, 0x20, 0x02, 0x00,
|
||||||
|
0x01, 0x40, 0x00, 0x00, 0x0A, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x0A,
|
||||||
|
0xA2, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x56, 0x0D, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x28, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xD8, 0xFF, 0xFF, 0xFF,
|
||||||
|
0x1E, 0x00, 0x00, 0x07, 0x22, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x3A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x07, 0x12, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x0A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x15, 0x00, 0x00, 0x01,
|
||||||
|
0x55, 0x00, 0x00, 0x09, 0x22, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x0A, 0x80, 0x30, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00, 0x10, 0x00, 0x00, 0x00,
|
||||||
|
0x23, 0x00, 0x00, 0x08, 0x22, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x1A, 0x10, 0x02, 0x00, 0x1A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x2A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x06,
|
||||||
|
0x22, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x0A, 0x10, 0x02, 0x00, 0x26, 0x00, 0x00, 0x07,
|
||||||
|
0x00, 0xD0, 0x00, 0x00, 0x42, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x1A, 0x20, 0x02, 0x00, 0x01, 0x40, 0x00, 0x00, 0x40, 0x01, 0x00, 0x00,
|
||||||
|
0x23, 0x00, 0x00, 0x09, 0x22, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x1A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00,
|
||||||
|
0x00, 0x14, 0x00, 0x00, 0x2A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x29, 0x00, 0x00, 0x07, 0x12, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x0A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x07, 0x12, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x1A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x8A, 0x00, 0x00, 0x0B,
|
||||||
|
0x22, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00,
|
||||||
|
0x01, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00, 0x0D, 0x00, 0x00, 0x00,
|
||||||
|
0x0A, 0x80, 0x30, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x00, 0x00, 0x00, 0x29, 0x00, 0x00, 0x07, 0x22, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x40, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x29, 0x00, 0x00, 0x07,
|
||||||
|
0x12, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0xA5, 0x00, 0x00, 0x08, 0xF2, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
|
0x0A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x46, 0x7E, 0x20, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x55, 0x00, 0x00, 0x0A,
|
||||||
|
0xF2, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
|
0x01, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00,
|
||||||
|
0x08, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00,
|
||||||
|
0x1E, 0x00, 0x00, 0x07, 0x12, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x0A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0xA0, 0x00, 0xA5, 0x00, 0x00, 0x08, 0xF2, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x46, 0x7E, 0x20, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x8A, 0x00, 0x00, 0x0F, 0xF2, 0x00, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x02, 0x40, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00,
|
||||||
|
0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
||||||
|
0x08, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00,
|
||||||
|
0x08, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
|
0x55, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00, 0x04, 0x00, 0x00, 0x00,
|
||||||
|
0x46, 0x0E, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
||||||
|
0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00,
|
||||||
|
0x14, 0x00, 0x00, 0x00, 0x87, 0x00, 0x00, 0x05, 0xF2, 0x00, 0x10, 0x00,
|
||||||
|
0x05, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x1E, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00, 0x05, 0x00, 0x00, 0x00,
|
||||||
|
0x46, 0x0E, 0x10, 0x00, 0x05, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
||||||
|
0xF5, 0xFF, 0xFF, 0xFF, 0xF5, 0xFF, 0xFF, 0xFF, 0xF5, 0xFF, 0xFF, 0xFF,
|
||||||
|
0xF5, 0xFF, 0xFF, 0xFF, 0x37, 0x00, 0x00, 0x0C, 0xF2, 0x00, 0x10, 0x00,
|
||||||
|
0x05, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x46, 0x0E, 0x10, 0x00, 0x05, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
||||||
|
0x15, 0x00, 0x00, 0x00, 0x15, 0x00, 0x00, 0x00, 0x15, 0x00, 0x00, 0x00,
|
||||||
|
0x15, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x0B, 0xF2, 0x00, 0x10, 0x00,
|
||||||
|
0x06, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x80, 0x41, 0x00, 0x00, 0x00,
|
||||||
|
0x05, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
|
0x37, 0x00, 0x00, 0x09, 0xF2, 0x00, 0x10, 0x00, 0x06, 0x00, 0x00, 0x00,
|
||||||
|
0x46, 0x0E, 0x10, 0x00, 0x04, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
|
0x04, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x06, 0x00, 0x00, 0x00,
|
||||||
|
0x29, 0x00, 0x00, 0x07, 0xF2, 0x00, 0x10, 0x00, 0x05, 0x00, 0x00, 0x00,
|
||||||
|
0x46, 0x0E, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
|
0x05, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00,
|
||||||
|
0x05, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x05, 0x00, 0x00, 0x00,
|
||||||
|
0x02, 0x40, 0x00, 0x00, 0xFF, 0xFF, 0x0F, 0x00, 0xFF, 0xFF, 0x0F, 0x00,
|
||||||
|
0xFF, 0xFF, 0x0F, 0x00, 0xFF, 0xFF, 0x0F, 0x00, 0x37, 0x00, 0x00, 0x09,
|
||||||
|
0xF2, 0x00, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
|
0x04, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x46, 0x0E, 0x10, 0x00, 0x05, 0x00, 0x00, 0x00, 0x29, 0x00, 0x00, 0x0A,
|
||||||
|
0xF2, 0x00, 0x10, 0x00, 0x04, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
|
0x06, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00,
|
||||||
|
0x17, 0x00, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00,
|
||||||
|
0x1E, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00, 0x04, 0x00, 0x00, 0x00,
|
||||||
|
0x46, 0x0E, 0x10, 0x00, 0x04, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x38, 0x00, 0x00, 0x00, 0x38, 0x00, 0x00, 0x00, 0x38,
|
||||||
|
0x00, 0x00, 0x00, 0x38, 0x29, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00,
|
||||||
|
0x03, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x02, 0x40, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x07,
|
||||||
|
0xF2, 0x00, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
|
0x04, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x37, 0x00, 0x00, 0x0C, 0xF2, 0x00, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x46, 0x0E, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
|
0x03, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x1E, 0x00, 0x00, 0x08, 0xF2, 0x00, 0x10, 0x00, 0x04, 0x00, 0x00, 0x00,
|
||||||
|
0x46, 0x0E, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x80,
|
||||||
|
0x41, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x50, 0x00, 0x00, 0x0A,
|
||||||
|
0xF2, 0x00, 0x10, 0x00, 0x05, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
||||||
|
0xFF, 0xFF, 0xFF, 0x7F, 0xFF, 0xFF, 0xFF, 0x7F, 0xFF, 0xFF, 0xFF, 0x7F,
|
||||||
|
0xFF, 0xFF, 0xFF, 0x7F, 0x46, 0x0E, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x00, 0x00, 0x07, 0xF2, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x46, 0x0E, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
|
0x05, 0x00, 0x00, 0x00, 0x54, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x02, 0x40, 0x00, 0x00, 0xF8, 0xFF, 0xFF, 0x3F, 0xF8, 0xFF, 0xFF, 0x3F,
|
||||||
|
0xF8, 0xFF, 0xFF, 0x3F, 0xF8, 0xFF, 0xFF, 0x3F, 0x8C, 0x00, 0x00, 0x14,
|
||||||
|
0xF2, 0x00, 0x10, 0x00, 0x05, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
||||||
|
0x17, 0x00, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00,
|
||||||
|
0x17, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x46, 0x0E, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x80, 0x00, 0x00, 0x00, 0x80, 0x00, 0x00, 0x00, 0x80, 0x00,
|
||||||
|
0x00, 0x00, 0x80, 0x00, 0x55, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00,
|
||||||
|
0x06, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x02, 0x40, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00,
|
||||||
|
0x17, 0x00, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x0B,
|
||||||
|
0xF2, 0x00, 0x10, 0x00, 0x06, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x80,
|
||||||
|
0x41, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
||||||
|
0x71, 0x00, 0x00, 0x00, 0x71, 0x00, 0x00, 0x00, 0x71, 0x00, 0x00, 0x00,
|
||||||
|
0x71, 0x00, 0x00, 0x00, 0x54, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00,
|
||||||
|
0x06, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x06, 0x00, 0x00, 0x00,
|
||||||
|
0x02, 0x40, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00,
|
||||||
|
0x18, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x55, 0x00, 0x00, 0x07,
|
||||||
|
0xF2, 0x00, 0x10, 0x00, 0x05, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
|
0x05, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x06, 0x00, 0x00, 0x00,
|
||||||
|
0x4F, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00, 0x06, 0x00, 0x00, 0x00,
|
||||||
|
0x46, 0x0E, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x80, 0x38, 0x00, 0x00, 0x80, 0x38, 0x00, 0x00, 0x80, 0x38,
|
||||||
|
0x00, 0x00, 0x80, 0x38, 0x1E, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x02, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0xC8, 0x00, 0x00, 0x00, 0xC8,
|
||||||
|
0x00, 0x00, 0x00, 0xC8, 0x00, 0x00, 0x00, 0xC8, 0x37, 0x00, 0x00, 0x09,
|
||||||
|
0xF2, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
|
0x06, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x05, 0x00, 0x00, 0x00,
|
||||||
|
0x46, 0x0E, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x0A,
|
||||||
|
0xF2, 0x00, 0x10, 0x00, 0x05, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x8A, 0x00, 0x00, 0x0F, 0xF2, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x02, 0x40, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
||||||
|
0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x03, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x1E, 0x00, 0x00, 0x07, 0xF2, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x46, 0x0E, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
|
0x05, 0x00, 0x00, 0x00, 0x8A, 0x00, 0x00, 0x0F, 0xF2, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00,
|
||||||
|
0x18, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00,
|
||||||
|
0x02, 0x40, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x07, 0xF2, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
|
0x46, 0x0E, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x0A,
|
||||||
|
0xF2, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
|
0x23, 0x00, 0x00, 0x09, 0xF2, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x46, 0x0E, 0x10, 0x00, 0x04, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x29, 0x00, 0x00, 0x09, 0x32, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
|
0x06, 0x00, 0x02, 0x00, 0x02, 0x40, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x23, 0x00, 0x00, 0x0A, 0x32, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
|
0x56, 0x05, 0x02, 0x00, 0xD6, 0x85, 0x30, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x46, 0x00, 0x10, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x09, 0x32, 0x00, 0x10, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x46, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
|
0x86, 0x80, 0x30, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0xA6, 0x00, 0x00, 0x08, 0xF2, 0xE0, 0x21, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x00, 0x00, 0x07, 0x12, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x0A, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00,
|
||||||
|
0xFF, 0x00, 0x00, 0x00, 0x8C, 0x00, 0x00, 0x14, 0xE2, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x08, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00,
|
||||||
|
0x02, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00,
|
||||||
|
0x10, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x56, 0x0E, 0x10, 0x00,
|
||||||
|
0x01, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x1E, 0x00, 0x00, 0x07, 0x32, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0xE6, 0x0A, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x46, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x07, 0x12, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x0A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0xA6, 0x00, 0x00, 0x08,
|
||||||
|
0x12, 0xE0, 0x21, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x1A, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x3E, 0x00, 0x00, 0x01, 0x53, 0x54, 0x41, 0x54,
|
||||||
|
0x94, 0x00, 0x00, 0x00, 0x43, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x1F, 0x00, 0x00, 0x00, 0x11, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x05, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
|
};
|
|
@ -0,0 +1,117 @@
|
||||||
|
//
|
||||||
|
// Generated by Microsoft (R) HLSL Shader Compiler 10.1
|
||||||
|
//
|
||||||
|
//
|
||||||
|
// Buffer Definitions:
|
||||||
|
//
|
||||||
|
// cbuffer XeEdramLoadStoreConstants
|
||||||
|
// {
|
||||||
|
//
|
||||||
|
// uint xe_edram_rt_color_depth_offset;// Offset: 0 Size: 4
|
||||||
|
// uint xe_edram_rt_color_depth_pitch;// Offset: 4 Size: 4
|
||||||
|
// uint xe_edram_rt_stencil_offset; // Offset: 8 Size: 4
|
||||||
|
// uint xe_edram_rt_stencil_pitch; // Offset: 12 Size: 4
|
||||||
|
// uint xe_edram_base_samples_2x_depth_pitch;// Offset: 16 Size: 4
|
||||||
|
//
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
//
|
||||||
|
// Resource Bindings:
|
||||||
|
//
|
||||||
|
// Name Type Format Dim ID HLSL Bind Count
|
||||||
|
// ------------------------------ ---------- ------- ----------- ------- -------------- ------
|
||||||
|
// xe_edram_load_store_source texture byte r/o T0 t0 1
|
||||||
|
// xe_edram_load_store_dest UAV byte r/w U0 u0 1
|
||||||
|
// XeEdramLoadStoreConstants cbuffer NA NA CB0 cb0 1
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
// Input signature:
|
||||||
|
//
|
||||||
|
// Name Index Mask Register SysValue Format Used
|
||||||
|
// -------------------- ----- ------ -------- -------- ------- ------
|
||||||
|
// no Input
|
||||||
|
//
|
||||||
|
// Output signature:
|
||||||
|
//
|
||||||
|
// Name Index Mask Register SysValue Format Used
|
||||||
|
// -------------------- ----- ------ -------- -------- ------- ------
|
||||||
|
// no Output
|
||||||
|
cs_5_1
|
||||||
|
dcl_globalFlags refactoringAllowed
|
||||||
|
dcl_constantbuffer CB0[0:0][2], immediateIndexed, space=0
|
||||||
|
dcl_resource_raw T0[0:0], space=0
|
||||||
|
dcl_uav_raw U0[0:0], space=0
|
||||||
|
dcl_input vThreadGroupID.xy
|
||||||
|
dcl_input vThreadIDInGroup.xy
|
||||||
|
dcl_input vThreadID.xy
|
||||||
|
dcl_temps 7
|
||||||
|
dcl_thread_group 20, 16, 1
|
||||||
|
ishl r0.x, vThreadIDInGroup.x, l(2)
|
||||||
|
and r0.yz, CB0[0][1].xxxx, l(0, 0x00008000, 2047, 0)
|
||||||
|
if_nz r0.y
|
||||||
|
ult r0.y, vThreadIDInGroup.x, l(10)
|
||||||
|
uge r0.w, vThreadIDInGroup.x, l(10)
|
||||||
|
and r0.yw, r0.yyyw, l(0, 40, 0, -40)
|
||||||
|
iadd r0.y, r0.w, r0.y
|
||||||
|
iadd r0.x, r0.y, r0.x
|
||||||
|
endif
|
||||||
|
ushr r0.y, CB0[0][1].x, l(16)
|
||||||
|
imad r0.y, vThreadGroupID.y, r0.y, r0.z
|
||||||
|
iadd r0.y, r0.y, vThreadGroupID.x
|
||||||
|
imul null, r0.z, vThreadIDInGroup.y, l(320)
|
||||||
|
imad r0.y, r0.y, l(5120), r0.z
|
||||||
|
ishl r0.x, r0.x, l(2)
|
||||||
|
iadd r0.x, r0.x, r0.y
|
||||||
|
ubfe r0.y, l(1), l(13), CB0[0][1].x
|
||||||
|
ishl r0.y, r0.y, l(1)
|
||||||
|
ishl r0.x, r0.x, r0.y
|
||||||
|
ld_raw r1.xyzw, r0.x, T0[0].xyzw
|
||||||
|
ushr r2.xyzw, r1.xyzw, l(8, 8, 8, 8)
|
||||||
|
iadd r0.x, r0.x, l(0x00a00000)
|
||||||
|
ld_raw r0.xyzw, r0.x, T0[0].xyzw
|
||||||
|
ubfe r3.xyzw, l(20, 20, 20, 20), l(8, 8, 8, 8), r1.xyzw
|
||||||
|
ushr r4.xyzw, r2.xyzw, l(20, 20, 20, 20)
|
||||||
|
firstbit_hi r5.xyzw, r3.xyzw
|
||||||
|
iadd r5.xyzw, r5.xyzw, l(-11, -11, -11, -11)
|
||||||
|
movc r5.xyzw, r3.xyzw, r5.xyzw, l(21,21,21,21)
|
||||||
|
iadd r6.xyzw, -r5.xyzw, l(1, 1, 1, 1)
|
||||||
|
movc r6.xyzw, r4.xyzw, r4.xyzw, r6.xyzw
|
||||||
|
ishl r5.xyzw, r3.xyzw, r5.xyzw
|
||||||
|
and r5.xyzw, r5.xyzw, l(0x000fffff, 0x000fffff, 0x000fffff, 0x000fffff)
|
||||||
|
movc r3.xyzw, r4.xyzw, r3.xyzw, r5.xyzw
|
||||||
|
ishl r4.xyzw, r6.xyzw, l(23, 23, 23, 23)
|
||||||
|
iadd r4.xyzw, r4.xyzw, l(0x38000000, 0x38000000, 0x38000000, 0x38000000)
|
||||||
|
ishl r3.xyzw, r3.xyzw, l(3, 3, 3, 3)
|
||||||
|
iadd r3.xyzw, r4.xyzw, r3.xyzw
|
||||||
|
movc r3.xyzw, r2.xyzw, r3.xyzw, l(0,0,0,0)
|
||||||
|
iadd r4.xyzw, r0.xyzw, -r3.xyzw
|
||||||
|
uge r5.xyzw, l(0x7fffffff, 0x7fffffff, 0x7fffffff, 0x7fffffff), r0.xyzw
|
||||||
|
and r0.xyzw, r0.xyzw, r5.xyzw
|
||||||
|
umin r0.xyzw, r0.xyzw, l(0x3ffffff8, 0x3ffffff8, 0x3ffffff8, 0x3ffffff8)
|
||||||
|
bfi r5.xyzw, l(23, 23, 23, 23), l(0, 0, 0, 0), r0.xyzw, l(0x00800000, 0x00800000, 0x00800000, 0x00800000)
|
||||||
|
ushr r6.xyzw, r0.xyzw, l(23, 23, 23, 23)
|
||||||
|
iadd r6.xyzw, -r6.xyzw, l(113, 113, 113, 113)
|
||||||
|
umin r6.xyzw, r6.xyzw, l(24, 24, 24, 24)
|
||||||
|
ushr r5.xyzw, r5.xyzw, r6.xyzw
|
||||||
|
ult r6.xyzw, r0.xyzw, l(0x38800000, 0x38800000, 0x38800000, 0x38800000)
|
||||||
|
iadd r0.xyzw, r0.xyzw, l(0xc8000000, 0xc8000000, 0xc8000000, 0xc8000000)
|
||||||
|
movc r0.xyzw, r6.xyzw, r5.xyzw, r0.xyzw
|
||||||
|
iadd r5.xyzw, r0.xyzw, l(3, 3, 3, 3)
|
||||||
|
ubfe r0.xyzw, l(1, 1, 1, 1), l(3, 3, 3, 3), r0.xyzw
|
||||||
|
iadd r0.xyzw, r0.xyzw, r5.xyzw
|
||||||
|
ubfe r0.xyzw, l(24, 24, 24, 24), l(3, 3, 3, 3), r0.xyzw
|
||||||
|
ieq r0.xyzw, r2.xyzw, r0.xyzw
|
||||||
|
and r0.xyzw, r0.xyzw, l(1, 1, 1, 1)
|
||||||
|
imad r0.xyzw, r4.xyzw, r0.xyzw, r3.xyzw
|
||||||
|
ishl r2.xy, vThreadID.xxxx, l(4, 2, 0, 0)
|
||||||
|
imad r2.xy, vThreadID.yyyy, CB0[0][0].ywyy, r2.xyxx
|
||||||
|
iadd r2.xy, r2.xyxx, CB0[0][0].xzxx
|
||||||
|
store_raw U0[0].xyzw, r2.x, r0.xyzw
|
||||||
|
and r0.x, r1.x, l(255)
|
||||||
|
bfi r0.yzw, l(0, 8, 8, 8), l(0, 8, 16, 24), r1.yyzw, l(0, 0, 0, 0)
|
||||||
|
iadd r0.xy, r0.zwzz, r0.xyxx
|
||||||
|
iadd r0.x, r0.y, r0.x
|
||||||
|
store_raw U0[0].x, r2.y, r0.x
|
||||||
|
ret
|
||||||
|
// Approximately 67 instruction slots used
|
Binary file not shown.
|
@ -1,11 +1,11 @@
|
||||||
// generated from `xb buildhlsl`
|
// generated from `xb buildhlsl`
|
||||||
// source: edram_load_depth_float.cs.hlsl
|
// source: edram_load_depth_float.cs.hlsl
|
||||||
const uint8_t edram_load_depth_float_cs[] = {
|
const uint8_t edram_load_depth_float_cs[] = {
|
||||||
0x44, 0x58, 0x42, 0x43, 0xF3, 0xA3, 0xA4, 0x14, 0x0A, 0x50, 0x56, 0x49,
|
0x44, 0x58, 0x42, 0x43, 0x17, 0xEE, 0x03, 0x06, 0xD3, 0x6E, 0x58, 0x75,
|
||||||
0x5D, 0x09, 0x6C, 0xBF, 0x33, 0xC9, 0xC1, 0x9A, 0x01, 0x00, 0x00, 0x00,
|
0x66, 0x3B, 0x5B, 0x87, 0x2F, 0xF9, 0x44, 0x9E, 0x01, 0x00, 0x00, 0x00,
|
||||||
0xAC, 0x0D, 0x00, 0x00, 0x05, 0x00, 0x00, 0x00, 0x34, 0x00, 0x00, 0x00,
|
0x64, 0x0A, 0x00, 0x00, 0x05, 0x00, 0x00, 0x00, 0x34, 0x00, 0x00, 0x00,
|
||||||
0x0C, 0x03, 0x00, 0x00, 0x1C, 0x03, 0x00, 0x00, 0x2C, 0x03, 0x00, 0x00,
|
0x0C, 0x03, 0x00, 0x00, 0x1C, 0x03, 0x00, 0x00, 0x2C, 0x03, 0x00, 0x00,
|
||||||
0x10, 0x0D, 0x00, 0x00, 0x52, 0x44, 0x45, 0x46, 0xD0, 0x02, 0x00, 0x00,
|
0xC8, 0x09, 0x00, 0x00, 0x52, 0x44, 0x45, 0x46, 0xD0, 0x02, 0x00, 0x00,
|
||||||
0x01, 0x00, 0x00, 0x00, 0x04, 0x01, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
0x01, 0x00, 0x00, 0x00, 0x04, 0x01, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
0x3C, 0x00, 0x00, 0x00, 0x01, 0x05, 0x53, 0x43, 0x00, 0x05, 0x00, 0x00,
|
0x3C, 0x00, 0x00, 0x00, 0x01, 0x05, 0x53, 0x43, 0x00, 0x05, 0x00, 0x00,
|
||||||
0xA8, 0x02, 0x00, 0x00, 0x13, 0x13, 0x44, 0x25, 0x3C, 0x00, 0x00, 0x00,
|
0xA8, 0x02, 0x00, 0x00, 0x13, 0x13, 0x44, 0x25, 0x3C, 0x00, 0x00, 0x00,
|
||||||
|
@ -69,7 +69,7 @@ const uint8_t edram_load_depth_float_cs[] = {
|
||||||
0x49, 0x53, 0x47, 0x4E, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0x49, 0x53, 0x47, 0x4E, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
0x08, 0x00, 0x00, 0x00, 0x4F, 0x53, 0x47, 0x4E, 0x08, 0x00, 0x00, 0x00,
|
0x08, 0x00, 0x00, 0x00, 0x4F, 0x53, 0x47, 0x4E, 0x08, 0x00, 0x00, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x53, 0x48, 0x45, 0x58,
|
0x00, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x53, 0x48, 0x45, 0x58,
|
||||||
0xDC, 0x09, 0x00, 0x00, 0x51, 0x00, 0x05, 0x00, 0x77, 0x02, 0x00, 0x00,
|
0x94, 0x06, 0x00, 0x00, 0x51, 0x00, 0x05, 0x00, 0xA5, 0x01, 0x00, 0x00,
|
||||||
0x6A, 0x08, 0x00, 0x01, 0x59, 0x00, 0x00, 0x07, 0x46, 0x8E, 0x30, 0x00,
|
0x6A, 0x08, 0x00, 0x01, 0x59, 0x00, 0x00, 0x07, 0x46, 0x8E, 0x30, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xA1, 0x00, 0x00, 0x06,
|
0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xA1, 0x00, 0x00, 0x06,
|
||||||
|
@ -126,168 +126,98 @@ const uint8_t edram_load_depth_float_cs[] = {
|
||||||
0x01, 0x40, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x29, 0x00, 0x00, 0x07,
|
0x01, 0x40, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x29, 0x00, 0x00, 0x07,
|
||||||
0x12, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00,
|
0x12, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0x00, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
0xA5, 0x00, 0x00, 0x08, 0xF2, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00,
|
0xA5, 0x00, 0x00, 0x08, 0xF2, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
0x0A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x46, 0x7E, 0x20, 0x00,
|
0x0A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x46, 0x7E, 0x20, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x55, 0x00, 0x00, 0x0A,
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x29, 0x00, 0x00, 0x09,
|
||||||
0xF2, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
0x32, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00, 0x06, 0x00, 0x02, 0x00,
|
||||||
0x01, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00,
|
0x02, 0x40, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x23, 0x00, 0x00, 0x0A,
|
||||||
|
0x32, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00, 0x56, 0x05, 0x02, 0x00,
|
||||||
|
0xD6, 0x85, 0x30, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x46, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
|
0x1E, 0x00, 0x00, 0x09, 0x32, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
|
0x46, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00, 0x86, 0x80, 0x30, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x55, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
|
0x46, 0x0E, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
||||||
0x08, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00,
|
0x08, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00,
|
||||||
0x1E, 0x00, 0x00, 0x07, 0x12, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0x08, 0x00, 0x00, 0x00, 0x8A, 0x00, 0x00, 0x0F, 0xF2, 0x00, 0x10, 0x00,
|
||||||
0x0A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00,
|
0x03, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00,
|
||||||
0x00, 0x00, 0xA0, 0x00, 0xA5, 0x00, 0x00, 0x08, 0xF2, 0x00, 0x10, 0x00,
|
|
||||||
0x00, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
|
||||||
0x46, 0x7E, 0x20, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
|
||||||
0x8A, 0x00, 0x00, 0x0F, 0xF2, 0x00, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00,
|
|
||||||
0x02, 0x40, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00,
|
|
||||||
0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
|
||||||
0x08, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00,
|
|
||||||
0x08, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00,
|
|
||||||
0x55, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00, 0x04, 0x00, 0x00, 0x00,
|
|
||||||
0x46, 0x0E, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
|
||||||
0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00,
|
0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00,
|
||||||
0x14, 0x00, 0x00, 0x00, 0x87, 0x00, 0x00, 0x05, 0xF2, 0x00, 0x10, 0x00,
|
0x02, 0x40, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00,
|
||||||
0x05, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00,
|
0x08, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
0x1E, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00, 0x05, 0x00, 0x00, 0x00,
|
0x00, 0x00, 0x00, 0x00, 0x55, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00,
|
||||||
0x46, 0x0E, 0x10, 0x00, 0x05, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
0x04, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
0xF5, 0xFF, 0xFF, 0xFF, 0xF5, 0xFF, 0xFF, 0xFF, 0xF5, 0xFF, 0xFF, 0xFF,
|
0x02, 0x40, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00,
|
||||||
0xF5, 0xFF, 0xFF, 0xFF, 0x37, 0x00, 0x00, 0x0C, 0xF2, 0x00, 0x10, 0x00,
|
0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x87, 0x00, 0x00, 0x05,
|
||||||
0x05, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00,
|
0xF2, 0x00, 0x10, 0x00, 0x05, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
0x46, 0x0E, 0x10, 0x00, 0x05, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
0x03, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00,
|
||||||
0x15, 0x00, 0x00, 0x00, 0x15, 0x00, 0x00, 0x00, 0x15, 0x00, 0x00, 0x00,
|
|
||||||
0x15, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x0B, 0xF2, 0x00, 0x10, 0x00,
|
|
||||||
0x06, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x80, 0x41, 0x00, 0x00, 0x00,
|
|
||||||
0x05, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
|
||||||
0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
|
||||||
0x37, 0x00, 0x00, 0x09, 0xF2, 0x00, 0x10, 0x00, 0x06, 0x00, 0x00, 0x00,
|
|
||||||
0x46, 0x0E, 0x10, 0x00, 0x04, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
|
||||||
0x04, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x06, 0x00, 0x00, 0x00,
|
|
||||||
0x29, 0x00, 0x00, 0x07, 0xF2, 0x00, 0x10, 0x00, 0x05, 0x00, 0x00, 0x00,
|
|
||||||
0x46, 0x0E, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
|
||||||
0x05, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00,
|
|
||||||
0x05, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x05, 0x00, 0x00, 0x00,
|
0x05, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x05, 0x00, 0x00, 0x00,
|
||||||
0x02, 0x40, 0x00, 0x00, 0xFF, 0xFF, 0x0F, 0x00, 0xFF, 0xFF, 0x0F, 0x00,
|
0x02, 0x40, 0x00, 0x00, 0xF5, 0xFF, 0xFF, 0xFF, 0xF5, 0xFF, 0xFF, 0xFF,
|
||||||
0xFF, 0xFF, 0x0F, 0x00, 0xFF, 0xFF, 0x0F, 0x00, 0x37, 0x00, 0x00, 0x09,
|
0xF5, 0xFF, 0xFF, 0xFF, 0xF5, 0xFF, 0xFF, 0xFF, 0x37, 0x00, 0x00, 0x0C,
|
||||||
0xF2, 0x00, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
0xF2, 0x00, 0x10, 0x00, 0x05, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
0x04, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00,
|
0x03, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x05, 0x00, 0x00, 0x00,
|
||||||
0x46, 0x0E, 0x10, 0x00, 0x05, 0x00, 0x00, 0x00, 0x29, 0x00, 0x00, 0x0A,
|
0x02, 0x40, 0x00, 0x00, 0x15, 0x00, 0x00, 0x00, 0x15, 0x00, 0x00, 0x00,
|
||||||
0xF2, 0x00, 0x10, 0x00, 0x04, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
0x15, 0x00, 0x00, 0x00, 0x15, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x0B,
|
||||||
0x06, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00,
|
|
||||||
0x17, 0x00, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00,
|
|
||||||
0x1E, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00, 0x04, 0x00, 0x00, 0x00,
|
|
||||||
0x46, 0x0E, 0x10, 0x00, 0x04, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
|
||||||
0x00, 0x00, 0x00, 0x38, 0x00, 0x00, 0x00, 0x38, 0x00, 0x00, 0x00, 0x38,
|
|
||||||
0x00, 0x00, 0x00, 0x38, 0x29, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00,
|
|
||||||
0x03, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00,
|
|
||||||
0x02, 0x40, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
|
||||||
0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x07,
|
|
||||||
0xF2, 0x00, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
|
||||||
0x04, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00,
|
|
||||||
0x37, 0x00, 0x00, 0x0C, 0xF2, 0x00, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00,
|
|
||||||
0x46, 0x0E, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
|
||||||
0x03, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
|
||||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
|
||||||
0x1E, 0x00, 0x00, 0x08, 0xF2, 0x00, 0x10, 0x00, 0x04, 0x00, 0x00, 0x00,
|
|
||||||
0x46, 0x0E, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x80,
|
|
||||||
0x41, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x50, 0x00, 0x00, 0x0A,
|
|
||||||
0xF2, 0x00, 0x10, 0x00, 0x05, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
|
||||||
0xFF, 0xFF, 0xFF, 0x7F, 0xFF, 0xFF, 0xFF, 0x7F, 0xFF, 0xFF, 0xFF, 0x7F,
|
|
||||||
0xFF, 0xFF, 0xFF, 0x7F, 0x46, 0x0E, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
|
||||||
0x01, 0x00, 0x00, 0x07, 0xF2, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
|
||||||
0x46, 0x0E, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
|
||||||
0x05, 0x00, 0x00, 0x00, 0x54, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00,
|
|
||||||
0x00, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
|
||||||
0x02, 0x40, 0x00, 0x00, 0xF8, 0xFF, 0xFF, 0x3F, 0xF8, 0xFF, 0xFF, 0x3F,
|
|
||||||
0xF8, 0xFF, 0xFF, 0x3F, 0xF8, 0xFF, 0xFF, 0x3F, 0x8C, 0x00, 0x00, 0x14,
|
|
||||||
0xF2, 0x00, 0x10, 0x00, 0x05, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
|
||||||
0x17, 0x00, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00,
|
|
||||||
0x17, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
|
||||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
|
||||||
0x46, 0x0E, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
|
||||||
0x00, 0x00, 0x80, 0x00, 0x00, 0x00, 0x80, 0x00, 0x00, 0x00, 0x80, 0x00,
|
|
||||||
0x00, 0x00, 0x80, 0x00, 0x55, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00,
|
|
||||||
0x06, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
|
||||||
0x02, 0x40, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00,
|
|
||||||
0x17, 0x00, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x0B,
|
|
||||||
0xF2, 0x00, 0x10, 0x00, 0x06, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x80,
|
0xF2, 0x00, 0x10, 0x00, 0x06, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x80,
|
||||||
0x41, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
0x41, 0x00, 0x00, 0x00, 0x05, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
||||||
0x71, 0x00, 0x00, 0x00, 0x71, 0x00, 0x00, 0x00, 0x71, 0x00, 0x00, 0x00,
|
|
||||||
0x71, 0x00, 0x00, 0x00, 0x54, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00,
|
|
||||||
0x06, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x06, 0x00, 0x00, 0x00,
|
|
||||||
0x02, 0x40, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00,
|
|
||||||
0x18, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x55, 0x00, 0x00, 0x07,
|
|
||||||
0xF2, 0x00, 0x10, 0x00, 0x05, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
|
||||||
0x05, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x06, 0x00, 0x00, 0x00,
|
|
||||||
0x4F, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00, 0x06, 0x00, 0x00, 0x00,
|
|
||||||
0x46, 0x0E, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
|
||||||
0x00, 0x00, 0x80, 0x38, 0x00, 0x00, 0x80, 0x38, 0x00, 0x00, 0x80, 0x38,
|
|
||||||
0x00, 0x00, 0x80, 0x38, 0x1E, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00,
|
|
||||||
0x00, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
|
||||||
0x02, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0xC8, 0x00, 0x00, 0x00, 0xC8,
|
|
||||||
0x00, 0x00, 0x00, 0xC8, 0x00, 0x00, 0x00, 0xC8, 0x37, 0x00, 0x00, 0x09,
|
|
||||||
0xF2, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
|
||||||
0x06, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x05, 0x00, 0x00, 0x00,
|
|
||||||
0x46, 0x0E, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x0A,
|
|
||||||
0xF2, 0x00, 0x10, 0x00, 0x05, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
|
||||||
0x00, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
|
||||||
0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
|
||||||
0x8A, 0x00, 0x00, 0x0F, 0xF2, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
|
||||||
0x02, 0x40, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
|
||||||
0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
|
||||||
0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
|
||||||
0x03, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
|
||||||
0x1E, 0x00, 0x00, 0x07, 0xF2, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
|
||||||
0x46, 0x0E, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
|
||||||
0x05, 0x00, 0x00, 0x00, 0x8A, 0x00, 0x00, 0x0F, 0xF2, 0x00, 0x10, 0x00,
|
|
||||||
0x00, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00,
|
|
||||||
0x18, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00,
|
|
||||||
0x02, 0x40, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
|
||||||
0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
|
||||||
0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x07, 0xF2, 0x00, 0x10, 0x00,
|
|
||||||
0x00, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
|
||||||
0x46, 0x0E, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x0A,
|
|
||||||
0xF2, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
|
||||||
0x00, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
|
||||||
0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
0x23, 0x00, 0x00, 0x09, 0xF2, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0x01, 0x00, 0x00, 0x00, 0x37, 0x00, 0x00, 0x09, 0xF2, 0x00, 0x10, 0x00,
|
||||||
|
0x06, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x04, 0x00, 0x00, 0x00,
|
||||||
0x46, 0x0E, 0x10, 0x00, 0x04, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
0x46, 0x0E, 0x10, 0x00, 0x04, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00,
|
0x06, 0x00, 0x00, 0x00, 0x29, 0x00, 0x00, 0x07, 0xF2, 0x00, 0x10, 0x00,
|
||||||
0x29, 0x00, 0x00, 0x09, 0x32, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
0x05, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
0x06, 0x00, 0x02, 0x00, 0x02, 0x40, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00,
|
0x46, 0x0E, 0x10, 0x00, 0x05, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x0A,
|
||||||
0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0xF2, 0x00, 0x10, 0x00, 0x05, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
0x23, 0x00, 0x00, 0x0A, 0x32, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
0x05, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0xFF, 0xFF, 0x0F, 0x00,
|
||||||
0x56, 0x05, 0x02, 0x00, 0xD6, 0x85, 0x30, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0xFF, 0xFF, 0x0F, 0x00, 0xFF, 0xFF, 0x0F, 0x00, 0xFF, 0xFF, 0x0F, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x46, 0x00, 0x10, 0x00,
|
0x37, 0x00, 0x00, 0x09, 0xF2, 0x00, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
0x02, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x09, 0x32, 0x00, 0x10, 0x00,
|
0x46, 0x0E, 0x10, 0x00, 0x04, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
0x02, 0x00, 0x00, 0x00, 0x46, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
0x03, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x05, 0x00, 0x00, 0x00,
|
||||||
0x86, 0x80, 0x30, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0x29, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00, 0x04, 0x00, 0x00, 0x00,
|
||||||
|
0x46, 0x0E, 0x10, 0x00, 0x06, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
||||||
|
0x17, 0x00, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00,
|
||||||
|
0x17, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00,
|
||||||
|
0x04, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x04, 0x00, 0x00, 0x00,
|
||||||
|
0x02, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x38, 0x00, 0x00, 0x00, 0x38,
|
||||||
|
0x00, 0x00, 0x00, 0x38, 0x00, 0x00, 0x00, 0x38, 0x29, 0x00, 0x00, 0x0A,
|
||||||
|
0xF2, 0x00, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
|
0x03, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x1E, 0x00, 0x00, 0x07, 0xF2, 0x00, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x46, 0x0E, 0x10, 0x00, 0x04, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
|
0x03, 0x00, 0x00, 0x00, 0x37, 0x00, 0x00, 0x0C, 0xF2, 0x00, 0x10, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
|
0x46, 0x0E, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0xA6, 0x00, 0x00, 0x08, 0xF2, 0xE0, 0x21, 0x00,
|
0x00, 0x00, 0x00, 0x00, 0xA6, 0x00, 0x00, 0x08, 0xF2, 0xE0, 0x21, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00,
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00,
|
||||||
0x02, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0x01, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
0x01, 0x00, 0x00, 0x07, 0x12, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0x01, 0x00, 0x00, 0x07, 0x12, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
0x0A, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00,
|
0x0A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00,
|
||||||
0xFF, 0x00, 0x00, 0x00, 0x8C, 0x00, 0x00, 0x14, 0xE2, 0x00, 0x10, 0x00,
|
0xFF, 0x00, 0x00, 0x00, 0x8C, 0x00, 0x00, 0x14, 0xE2, 0x00, 0x10, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0x02, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
0x08, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00,
|
0x08, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00,
|
||||||
0x02, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00,
|
0x02, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00,
|
||||||
0x10, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x56, 0x0E, 0x10, 0x00,
|
0x10, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x56, 0x0E, 0x10, 0x00,
|
||||||
0x01, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0x00, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
0x1E, 0x00, 0x00, 0x07, 0x32, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0x1E, 0x00, 0x00, 0x07, 0x32, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
0xE6, 0x0A, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x46, 0x00, 0x10, 0x00,
|
0xE6, 0x0A, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x46, 0x00, 0x10, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x07, 0x12, 0x00, 0x10, 0x00,
|
0x02, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x07, 0x12, 0x00, 0x10, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0x00, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
0x0A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0xA6, 0x00, 0x00, 0x08,
|
0x0A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0xA6, 0x00, 0x00, 0x08,
|
||||||
0x12, 0xE0, 0x21, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0x12, 0xE0, 0x21, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
0x1A, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00,
|
0x1A, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0x3E, 0x00, 0x00, 0x01, 0x53, 0x54, 0x41, 0x54,
|
0x00, 0x00, 0x00, 0x00, 0x3E, 0x00, 0x00, 0x01, 0x53, 0x54, 0x41, 0x54,
|
||||||
0x94, 0x00, 0x00, 0x00, 0x43, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00,
|
0x94, 0x00, 0x00, 0x00, 0x2E, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
0x1F, 0x00, 0x00, 0x00, 0x11, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
0x17, 0x00, 0x00, 0x00, 0x09, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
0x05, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
|
|
@ -66,11 +66,12 @@ iadd r0.x, r0.x, r0.y
|
||||||
ubfe r0.y, l(1), l(13), CB0[0][1].x
|
ubfe r0.y, l(1), l(13), CB0[0][1].x
|
||||||
ishl r0.y, r0.y, l(1)
|
ishl r0.y, r0.y, l(1)
|
||||||
ishl r0.x, r0.x, r0.y
|
ishl r0.x, r0.x, r0.y
|
||||||
ld_raw r1.xyzw, r0.x, T0[0].xyzw
|
|
||||||
ushr r2.xyzw, r1.xyzw, l(8, 8, 8, 8)
|
|
||||||
iadd r0.x, r0.x, l(0x00a00000)
|
|
||||||
ld_raw r0.xyzw, r0.x, T0[0].xyzw
|
ld_raw r0.xyzw, r0.x, T0[0].xyzw
|
||||||
ubfe r3.xyzw, l(20, 20, 20, 20), l(8, 8, 8, 8), r1.xyzw
|
ishl r1.xy, vThreadID.xxxx, l(4, 2, 0, 0)
|
||||||
|
imad r1.xy, vThreadID.yyyy, CB0[0][0].ywyy, r1.xyxx
|
||||||
|
iadd r1.xy, r1.xyxx, CB0[0][0].xzxx
|
||||||
|
ushr r2.xyzw, r0.xyzw, l(8, 8, 8, 8)
|
||||||
|
ubfe r3.xyzw, l(20, 20, 20, 20), l(8, 8, 8, 8), r0.xyzw
|
||||||
ushr r4.xyzw, r2.xyzw, l(20, 20, 20, 20)
|
ushr r4.xyzw, r2.xyzw, l(20, 20, 20, 20)
|
||||||
firstbit_hi r5.xyzw, r3.xyzw
|
firstbit_hi r5.xyzw, r3.xyzw
|
||||||
iadd r5.xyzw, r5.xyzw, l(-11, -11, -11, -11)
|
iadd r5.xyzw, r5.xyzw, l(-11, -11, -11, -11)
|
||||||
|
@ -84,34 +85,12 @@ ishl r4.xyzw, r6.xyzw, l(23, 23, 23, 23)
|
||||||
iadd r4.xyzw, r4.xyzw, l(0x38000000, 0x38000000, 0x38000000, 0x38000000)
|
iadd r4.xyzw, r4.xyzw, l(0x38000000, 0x38000000, 0x38000000, 0x38000000)
|
||||||
ishl r3.xyzw, r3.xyzw, l(3, 3, 3, 3)
|
ishl r3.xyzw, r3.xyzw, l(3, 3, 3, 3)
|
||||||
iadd r3.xyzw, r4.xyzw, r3.xyzw
|
iadd r3.xyzw, r4.xyzw, r3.xyzw
|
||||||
movc r3.xyzw, r2.xyzw, r3.xyzw, l(0,0,0,0)
|
movc r2.xyzw, r2.xyzw, r3.xyzw, l(0,0,0,0)
|
||||||
iadd r4.xyzw, r0.xyzw, -r3.xyzw
|
store_raw U0[0].xyzw, r1.x, r2.xyzw
|
||||||
uge r5.xyzw, l(0x7fffffff, 0x7fffffff, 0x7fffffff, 0x7fffffff), r0.xyzw
|
and r2.x, r0.x, l(255)
|
||||||
and r0.xyzw, r0.xyzw, r5.xyzw
|
bfi r2.yzw, l(0, 8, 8, 8), l(0, 8, 16, 24), r0.yyzw, l(0, 0, 0, 0)
|
||||||
umin r0.xyzw, r0.xyzw, l(0x3ffffff8, 0x3ffffff8, 0x3ffffff8, 0x3ffffff8)
|
iadd r0.xy, r2.zwzz, r2.xyxx
|
||||||
bfi r5.xyzw, l(23, 23, 23, 23), l(0, 0, 0, 0), r0.xyzw, l(0x00800000, 0x00800000, 0x00800000, 0x00800000)
|
|
||||||
ushr r6.xyzw, r0.xyzw, l(23, 23, 23, 23)
|
|
||||||
iadd r6.xyzw, -r6.xyzw, l(113, 113, 113, 113)
|
|
||||||
umin r6.xyzw, r6.xyzw, l(24, 24, 24, 24)
|
|
||||||
ushr r5.xyzw, r5.xyzw, r6.xyzw
|
|
||||||
ult r6.xyzw, r0.xyzw, l(0x38800000, 0x38800000, 0x38800000, 0x38800000)
|
|
||||||
iadd r0.xyzw, r0.xyzw, l(0xc8000000, 0xc8000000, 0xc8000000, 0xc8000000)
|
|
||||||
movc r0.xyzw, r6.xyzw, r5.xyzw, r0.xyzw
|
|
||||||
iadd r5.xyzw, r0.xyzw, l(3, 3, 3, 3)
|
|
||||||
ubfe r0.xyzw, l(1, 1, 1, 1), l(3, 3, 3, 3), r0.xyzw
|
|
||||||
iadd r0.xyzw, r0.xyzw, r5.xyzw
|
|
||||||
ubfe r0.xyzw, l(24, 24, 24, 24), l(3, 3, 3, 3), r0.xyzw
|
|
||||||
ieq r0.xyzw, r2.xyzw, r0.xyzw
|
|
||||||
and r0.xyzw, r0.xyzw, l(1, 1, 1, 1)
|
|
||||||
imad r0.xyzw, r4.xyzw, r0.xyzw, r3.xyzw
|
|
||||||
ishl r2.xy, vThreadID.xxxx, l(4, 2, 0, 0)
|
|
||||||
imad r2.xy, vThreadID.yyyy, CB0[0][0].ywyy, r2.xyxx
|
|
||||||
iadd r2.xy, r2.xyxx, CB0[0][0].xzxx
|
|
||||||
store_raw U0[0].xyzw, r2.x, r0.xyzw
|
|
||||||
and r0.x, r1.x, l(255)
|
|
||||||
bfi r0.yzw, l(0, 8, 8, 8), l(0, 8, 16, 24), r1.yyzw, l(0, 0, 0, 0)
|
|
||||||
iadd r0.xy, r0.zwzz, r0.xyxx
|
|
||||||
iadd r0.x, r0.y, r0.x
|
iadd r0.x, r0.y, r0.x
|
||||||
store_raw U0[0].x, r2.y, r0.x
|
store_raw U0[0].x, r1.y, r0.x
|
||||||
ret
|
ret
|
||||||
// Approximately 67 instruction slots used
|
// Approximately 46 instruction slots used
|
||||||
|
|
Binary file not shown.
|
@ -0,0 +1,226 @@
|
||||||
|
// generated from `xb buildhlsl`
|
||||||
|
// source: edram_store_depth_float24and32.cs.hlsl
|
||||||
|
const uint8_t edram_store_depth_float24and32_cs[] = {
|
||||||
|
0x44, 0x58, 0x42, 0x43, 0xC6, 0x10, 0x80, 0x14, 0x97, 0x01, 0xE4, 0x46,
|
||||||
|
0x76, 0xF1, 0x67, 0xD3, 0xDF, 0x50, 0x25, 0xF7, 0x01, 0x00, 0x00, 0x00,
|
||||||
|
0x64, 0x0A, 0x00, 0x00, 0x05, 0x00, 0x00, 0x00, 0x34, 0x00, 0x00, 0x00,
|
||||||
|
0x0C, 0x03, 0x00, 0x00, 0x1C, 0x03, 0x00, 0x00, 0x2C, 0x03, 0x00, 0x00,
|
||||||
|
0xC8, 0x09, 0x00, 0x00, 0x52, 0x44, 0x45, 0x46, 0xD0, 0x02, 0x00, 0x00,
|
||||||
|
0x01, 0x00, 0x00, 0x00, 0x04, 0x01, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x3C, 0x00, 0x00, 0x00, 0x01, 0x05, 0x53, 0x43, 0x00, 0x05, 0x00, 0x00,
|
||||||
|
0xA8, 0x02, 0x00, 0x00, 0x13, 0x13, 0x44, 0x25, 0x3C, 0x00, 0x00, 0x00,
|
||||||
|
0x18, 0x00, 0x00, 0x00, 0x28, 0x00, 0x00, 0x00, 0x28, 0x00, 0x00, 0x00,
|
||||||
|
0x24, 0x00, 0x00, 0x00, 0x0C, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0xB4, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0xCF, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00,
|
||||||
|
0x06, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xE8, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x78, 0x65, 0x5F, 0x65, 0x64, 0x72, 0x61, 0x6D, 0x5F, 0x6C, 0x6F, 0x61,
|
||||||
|
0x64, 0x5F, 0x73, 0x74, 0x6F, 0x72, 0x65, 0x5F, 0x73, 0x6F, 0x75, 0x72,
|
||||||
|
0x63, 0x65, 0x00, 0x78, 0x65, 0x5F, 0x65, 0x64, 0x72, 0x61, 0x6D, 0x5F,
|
||||||
|
0x6C, 0x6F, 0x61, 0x64, 0x5F, 0x73, 0x74, 0x6F, 0x72, 0x65, 0x5F, 0x64,
|
||||||
|
0x65, 0x73, 0x74, 0x00, 0x58, 0x65, 0x45, 0x64, 0x72, 0x61, 0x6D, 0x4C,
|
||||||
|
0x6F, 0x61, 0x64, 0x53, 0x74, 0x6F, 0x72, 0x65, 0x43, 0x6F, 0x6E, 0x73,
|
||||||
|
0x74, 0x61, 0x6E, 0x74, 0x73, 0x00, 0xAB, 0xAB, 0xE8, 0x00, 0x00, 0x00,
|
||||||
|
0x05, 0x00, 0x00, 0x00, 0x1C, 0x01, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xE4, 0x01, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
|
0x0C, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x30, 0x02, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x0C, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x4E, 0x02, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00,
|
||||||
|
0x04, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x0C, 0x02, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00, 0x69, 0x02, 0x00, 0x00,
|
||||||
|
0x0C, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
|
0x0C, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x83, 0x02, 0x00, 0x00, 0x10, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x0C, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x78, 0x65, 0x5F, 0x65, 0x64, 0x72, 0x61, 0x6D,
|
||||||
|
0x5F, 0x72, 0x74, 0x5F, 0x63, 0x6F, 0x6C, 0x6F, 0x72, 0x5F, 0x64, 0x65,
|
||||||
|
0x70, 0x74, 0x68, 0x5F, 0x6F, 0x66, 0x66, 0x73, 0x65, 0x74, 0x00, 0x64,
|
||||||
|
0x77, 0x6F, 0x72, 0x64, 0x00, 0xAB, 0xAB, 0xAB, 0x00, 0x00, 0x13, 0x00,
|
||||||
|
0x01, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x03, 0x02, 0x00, 0x00, 0x78, 0x65, 0x5F, 0x65,
|
||||||
|
0x64, 0x72, 0x61, 0x6D, 0x5F, 0x72, 0x74, 0x5F, 0x63, 0x6F, 0x6C, 0x6F,
|
||||||
|
0x72, 0x5F, 0x64, 0x65, 0x70, 0x74, 0x68, 0x5F, 0x70, 0x69, 0x74, 0x63,
|
||||||
|
0x68, 0x00, 0x78, 0x65, 0x5F, 0x65, 0x64, 0x72, 0x61, 0x6D, 0x5F, 0x72,
|
||||||
|
0x74, 0x5F, 0x73, 0x74, 0x65, 0x6E, 0x63, 0x69, 0x6C, 0x5F, 0x6F, 0x66,
|
||||||
|
0x66, 0x73, 0x65, 0x74, 0x00, 0x78, 0x65, 0x5F, 0x65, 0x64, 0x72, 0x61,
|
||||||
|
0x6D, 0x5F, 0x72, 0x74, 0x5F, 0x73, 0x74, 0x65, 0x6E, 0x63, 0x69, 0x6C,
|
||||||
|
0x5F, 0x70, 0x69, 0x74, 0x63, 0x68, 0x00, 0x78, 0x65, 0x5F, 0x65, 0x64,
|
||||||
|
0x72, 0x61, 0x6D, 0x5F, 0x62, 0x61, 0x73, 0x65, 0x5F, 0x73, 0x61, 0x6D,
|
||||||
|
0x70, 0x6C, 0x65, 0x73, 0x5F, 0x32, 0x78, 0x5F, 0x64, 0x65, 0x70, 0x74,
|
||||||
|
0x68, 0x5F, 0x70, 0x69, 0x74, 0x63, 0x68, 0x00, 0x4D, 0x69, 0x63, 0x72,
|
||||||
|
0x6F, 0x73, 0x6F, 0x66, 0x74, 0x20, 0x28, 0x52, 0x29, 0x20, 0x48, 0x4C,
|
||||||
|
0x53, 0x4C, 0x20, 0x53, 0x68, 0x61, 0x64, 0x65, 0x72, 0x20, 0x43, 0x6F,
|
||||||
|
0x6D, 0x70, 0x69, 0x6C, 0x65, 0x72, 0x20, 0x31, 0x30, 0x2E, 0x31, 0x00,
|
||||||
|
0x49, 0x53, 0x47, 0x4E, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x08, 0x00, 0x00, 0x00, 0x4F, 0x53, 0x47, 0x4E, 0x08, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x53, 0x48, 0x45, 0x58,
|
||||||
|
0x94, 0x06, 0x00, 0x00, 0x51, 0x00, 0x05, 0x00, 0xA5, 0x01, 0x00, 0x00,
|
||||||
|
0x6A, 0x08, 0x00, 0x01, 0x59, 0x00, 0x00, 0x07, 0x46, 0x8E, 0x30, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xA1, 0x00, 0x00, 0x06,
|
||||||
|
0x46, 0x7E, 0x30, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x9D, 0x00, 0x00, 0x06,
|
||||||
|
0x46, 0xEE, 0x31, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x5F, 0x00, 0x00, 0x02,
|
||||||
|
0x32, 0x10, 0x02, 0x00, 0x5F, 0x00, 0x00, 0x02, 0x32, 0x20, 0x02, 0x00,
|
||||||
|
0x5F, 0x00, 0x00, 0x02, 0x32, 0x00, 0x02, 0x00, 0x68, 0x00, 0x00, 0x02,
|
||||||
|
0x05, 0x00, 0x00, 0x00, 0x9B, 0x00, 0x00, 0x04, 0x14, 0x00, 0x00, 0x00,
|
||||||
|
0x10, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x29, 0x00, 0x00, 0x09,
|
||||||
|
0x32, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x06, 0x00, 0x02, 0x00,
|
||||||
|
0x02, 0x40, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x23, 0x00, 0x00, 0x0A,
|
||||||
|
0x32, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x56, 0x05, 0x02, 0x00,
|
||||||
|
0xD6, 0x85, 0x30, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x46, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x1E, 0x00, 0x00, 0x09, 0x32, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x46, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x86, 0x80, 0x30, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0xA5, 0x00, 0x00, 0x08, 0xF2, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
|
0x0A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x46, 0x7E, 0x20, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x50, 0x00, 0x00, 0x0A,
|
||||||
|
0xF2, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
||||||
|
0xFF, 0xFF, 0xFF, 0x7F, 0xFF, 0xFF, 0xFF, 0x7F, 0xFF, 0xFF, 0xFF, 0x7F,
|
||||||
|
0xFF, 0xFF, 0xFF, 0x7F, 0x46, 0x0E, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x00, 0x00, 0x07, 0xF2, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
|
0x46, 0x0E, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x54, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
|
0x02, 0x40, 0x00, 0x00, 0xF8, 0xFF, 0xFF, 0x3F, 0xF8, 0xFF, 0xFF, 0x3F,
|
||||||
|
0xF8, 0xFF, 0xFF, 0x3F, 0xF8, 0xFF, 0xFF, 0x3F, 0x8C, 0x00, 0x00, 0x14,
|
||||||
|
0xF2, 0x00, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
||||||
|
0x17, 0x00, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00,
|
||||||
|
0x17, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x46, 0x0E, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x80, 0x00, 0x00, 0x00, 0x80, 0x00, 0x00, 0x00, 0x80, 0x00,
|
||||||
|
0x00, 0x00, 0x80, 0x00, 0x55, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00,
|
||||||
|
0x04, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
|
0x02, 0x40, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00,
|
||||||
|
0x17, 0x00, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x0B,
|
||||||
|
0xF2, 0x00, 0x10, 0x00, 0x04, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x80,
|
||||||
|
0x41, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
||||||
|
0x71, 0x00, 0x00, 0x00, 0x71, 0x00, 0x00, 0x00, 0x71, 0x00, 0x00, 0x00,
|
||||||
|
0x71, 0x00, 0x00, 0x00, 0x54, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00,
|
||||||
|
0x04, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x04, 0x00, 0x00, 0x00,
|
||||||
|
0x02, 0x40, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00,
|
||||||
|
0x18, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x55, 0x00, 0x00, 0x07,
|
||||||
|
0xF2, 0x00, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
|
0x03, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x04, 0x00, 0x00, 0x00,
|
||||||
|
0x4F, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00, 0x04, 0x00, 0x00, 0x00,
|
||||||
|
0x46, 0x0E, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x80, 0x38, 0x00, 0x00, 0x80, 0x38, 0x00, 0x00, 0x80, 0x38,
|
||||||
|
0x00, 0x00, 0x80, 0x38, 0x1E, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
|
0x02, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0xC8, 0x00, 0x00, 0x00, 0xC8,
|
||||||
|
0x00, 0x00, 0x00, 0xC8, 0x00, 0x00, 0x00, 0xC8, 0x37, 0x00, 0x00, 0x09,
|
||||||
|
0xF2, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
|
0x04, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x46, 0x0E, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x0A,
|
||||||
|
0xF2, 0x00, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x8A, 0x00, 0x00, 0x0F, 0xF2, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
|
0x02, 0x40, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
||||||
|
0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x03, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
|
0x1E, 0x00, 0x00, 0x07, 0xF2, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
|
0x46, 0x0E, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
|
0x03, 0x00, 0x00, 0x00, 0x55, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
|
0x02, 0x40, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0xA5, 0x00, 0x00, 0x08,
|
||||||
|
0x12, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x06, 0x70, 0x20, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x55, 0x00, 0x00, 0x0A, 0xE2, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x06, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x02, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00,
|
||||||
|
0x10, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x8C, 0x00, 0x00, 0x11,
|
||||||
|
0xF2, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
||||||
|
0x18, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00,
|
||||||
|
0x18, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00,
|
||||||
|
0x08, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00,
|
||||||
|
0x46, 0x0E, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x29, 0x00, 0x00, 0x06, 0x12, 0x00, 0x10, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x0A, 0x20, 0x02, 0x00, 0x01, 0x40, 0x00, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x0C, 0x62, 0x00, 0x10, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x06, 0x80, 0x30, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x80, 0x00, 0x00, 0xFF, 0x07, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x1F, 0x00, 0x04, 0x03, 0x1A, 0x00, 0x10, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x4F, 0x00, 0x00, 0x06, 0x22, 0x00, 0x10, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x0A, 0x20, 0x02, 0x00, 0x01, 0x40, 0x00, 0x00,
|
||||||
|
0x0A, 0x00, 0x00, 0x00, 0x50, 0x00, 0x00, 0x06, 0x82, 0x00, 0x10, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x0A, 0x20, 0x02, 0x00, 0x01, 0x40, 0x00, 0x00,
|
||||||
|
0x0A, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x0A, 0xA2, 0x00, 0x10, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x56, 0x0D, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
|
0x02, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x28, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0xD8, 0xFF, 0xFF, 0xFF, 0x1E, 0x00, 0x00, 0x07,
|
||||||
|
0x22, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x3A, 0x00, 0x10, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
|
0x1E, 0x00, 0x00, 0x07, 0x12, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
|
0x1A, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x15, 0x00, 0x00, 0x01, 0x55, 0x00, 0x00, 0x09,
|
||||||
|
0x22, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x0A, 0x80, 0x30, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x40, 0x00, 0x00, 0x10, 0x00, 0x00, 0x00, 0x23, 0x00, 0x00, 0x08,
|
||||||
|
0x22, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x1A, 0x10, 0x02, 0x00,
|
||||||
|
0x1A, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x2A, 0x00, 0x10, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x06, 0x22, 0x00, 0x10, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
|
0x0A, 0x10, 0x02, 0x00, 0x26, 0x00, 0x00, 0x07, 0x00, 0xD0, 0x00, 0x00,
|
||||||
|
0x42, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x1A, 0x20, 0x02, 0x00,
|
||||||
|
0x01, 0x40, 0x00, 0x00, 0x40, 0x01, 0x00, 0x00, 0x23, 0x00, 0x00, 0x09,
|
||||||
|
0x22, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x10, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00,
|
||||||
|
0x2A, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x29, 0x00, 0x00, 0x07,
|
||||||
|
0x12, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
|
0x1E, 0x00, 0x00, 0x07, 0x12, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
|
0x0A, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x10, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x8A, 0x00, 0x00, 0x0B, 0x22, 0x00, 0x10, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x40, 0x00, 0x00, 0x0D, 0x00, 0x00, 0x00, 0x0A, 0x80, 0x30, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
|
0x29, 0x00, 0x00, 0x07, 0x22, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
|
0x1A, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00,
|
||||||
|
0x01, 0x00, 0x00, 0x00, 0x29, 0x00, 0x00, 0x07, 0x12, 0x00, 0x10, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
|
0x1A, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0xA6, 0x00, 0x00, 0x08,
|
||||||
|
0xF2, 0xE0, 0x21, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x0A, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x07, 0x12, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x40, 0x00, 0x00, 0x00, 0x00, 0xA0, 0x00, 0xA6, 0x00, 0x00, 0x08,
|
||||||
|
0xF2, 0xE0, 0x21, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x0A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
|
0x01, 0x00, 0x00, 0x00, 0x3E, 0x00, 0x00, 0x01, 0x53, 0x54, 0x41, 0x54,
|
||||||
|
0x94, 0x00, 0x00, 0x00, 0x2D, 0x00, 0x00, 0x00, 0x05, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x13, 0x00, 0x00, 0x00, 0x0E, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
|
};
|
|
@ -0,0 +1,95 @@
|
||||||
|
//
|
||||||
|
// Generated by Microsoft (R) HLSL Shader Compiler 10.1
|
||||||
|
//
|
||||||
|
//
|
||||||
|
// Buffer Definitions:
|
||||||
|
//
|
||||||
|
// cbuffer XeEdramLoadStoreConstants
|
||||||
|
// {
|
||||||
|
//
|
||||||
|
// uint xe_edram_rt_color_depth_offset;// Offset: 0 Size: 4
|
||||||
|
// uint xe_edram_rt_color_depth_pitch;// Offset: 4 Size: 4
|
||||||
|
// uint xe_edram_rt_stencil_offset; // Offset: 8 Size: 4
|
||||||
|
// uint xe_edram_rt_stencil_pitch; // Offset: 12 Size: 4
|
||||||
|
// uint xe_edram_base_samples_2x_depth_pitch;// Offset: 16 Size: 4
|
||||||
|
//
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
//
|
||||||
|
// Resource Bindings:
|
||||||
|
//
|
||||||
|
// Name Type Format Dim ID HLSL Bind Count
|
||||||
|
// ------------------------------ ---------- ------- ----------- ------- -------------- ------
|
||||||
|
// xe_edram_load_store_source texture byte r/o T0 t0 1
|
||||||
|
// xe_edram_load_store_dest UAV byte r/w U0 u0 1
|
||||||
|
// XeEdramLoadStoreConstants cbuffer NA NA CB0 cb0 1
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
// Input signature:
|
||||||
|
//
|
||||||
|
// Name Index Mask Register SysValue Format Used
|
||||||
|
// -------------------- ----- ------ -------- -------- ------- ------
|
||||||
|
// no Input
|
||||||
|
//
|
||||||
|
// Output signature:
|
||||||
|
//
|
||||||
|
// Name Index Mask Register SysValue Format Used
|
||||||
|
// -------------------- ----- ------ -------- -------- ------- ------
|
||||||
|
// no Output
|
||||||
|
cs_5_1
|
||||||
|
dcl_globalFlags refactoringAllowed
|
||||||
|
dcl_constantbuffer CB0[0:0][2], immediateIndexed, space=0
|
||||||
|
dcl_resource_raw T0[0:0], space=0
|
||||||
|
dcl_uav_raw U0[0:0], space=0
|
||||||
|
dcl_input vThreadGroupID.xy
|
||||||
|
dcl_input vThreadIDInGroup.xy
|
||||||
|
dcl_input vThreadID.xy
|
||||||
|
dcl_temps 5
|
||||||
|
dcl_thread_group 20, 16, 1
|
||||||
|
ishl r0.xy, vThreadID.xxxx, l(4, 2, 0, 0)
|
||||||
|
imad r0.xy, vThreadID.yyyy, CB0[0][0].ywyy, r0.xyxx
|
||||||
|
iadd r0.xy, r0.xyxx, CB0[0][0].xzxx
|
||||||
|
ld_raw r1.xyzw, r0.x, T0[0].xyzw
|
||||||
|
uge r2.xyzw, l(0x7fffffff, 0x7fffffff, 0x7fffffff, 0x7fffffff), r1.xyzw
|
||||||
|
and r2.xyzw, r1.xyzw, r2.xyzw
|
||||||
|
umin r2.xyzw, r2.xyzw, l(0x3ffffff8, 0x3ffffff8, 0x3ffffff8, 0x3ffffff8)
|
||||||
|
bfi r3.xyzw, l(23, 23, 23, 23), l(0, 0, 0, 0), r2.xyzw, l(0x00800000, 0x00800000, 0x00800000, 0x00800000)
|
||||||
|
ushr r4.xyzw, r2.xyzw, l(23, 23, 23, 23)
|
||||||
|
iadd r4.xyzw, -r4.xyzw, l(113, 113, 113, 113)
|
||||||
|
umin r4.xyzw, r4.xyzw, l(24, 24, 24, 24)
|
||||||
|
ushr r3.xyzw, r3.xyzw, r4.xyzw
|
||||||
|
ult r4.xyzw, r2.xyzw, l(0x38800000, 0x38800000, 0x38800000, 0x38800000)
|
||||||
|
iadd r2.xyzw, r2.xyzw, l(0xc8000000, 0xc8000000, 0xc8000000, 0xc8000000)
|
||||||
|
movc r2.xyzw, r4.xyzw, r3.xyzw, r2.xyzw
|
||||||
|
iadd r3.xyzw, r2.xyzw, l(3, 3, 3, 3)
|
||||||
|
ubfe r2.xyzw, l(1, 1, 1, 1), l(3, 3, 3, 3), r2.xyzw
|
||||||
|
iadd r2.xyzw, r2.xyzw, r3.xyzw
|
||||||
|
ushr r2.xyzw, r2.xyzw, l(3, 3, 3, 3)
|
||||||
|
ld_raw r0.x, r0.y, T0[0].xxxx
|
||||||
|
ushr r0.yzw, r0.xxxx, l(0, 8, 16, 24)
|
||||||
|
bfi r0.xyzw, l(24, 24, 24, 24), l(8, 8, 8, 8), r2.xyzw, r0.xyzw
|
||||||
|
ishl r2.x, vThreadIDInGroup.x, l(2)
|
||||||
|
and r2.yz, CB0[0][1].xxxx, l(0, 0x00008000, 2047, 0)
|
||||||
|
if_nz r2.y
|
||||||
|
ult r2.y, vThreadIDInGroup.x, l(10)
|
||||||
|
uge r2.w, vThreadIDInGroup.x, l(10)
|
||||||
|
and r2.yw, r2.yyyw, l(0, 40, 0, -40)
|
||||||
|
iadd r2.y, r2.w, r2.y
|
||||||
|
iadd r2.x, r2.y, r2.x
|
||||||
|
endif
|
||||||
|
ushr r2.y, CB0[0][1].x, l(16)
|
||||||
|
imad r2.y, vThreadGroupID.y, r2.y, r2.z
|
||||||
|
iadd r2.y, r2.y, vThreadGroupID.x
|
||||||
|
imul null, r2.z, vThreadIDInGroup.y, l(320)
|
||||||
|
imad r2.y, r2.y, l(5120), r2.z
|
||||||
|
ishl r2.x, r2.x, l(2)
|
||||||
|
iadd r2.x, r2.x, r2.y
|
||||||
|
ubfe r2.y, l(1), l(13), CB0[0][1].x
|
||||||
|
ishl r2.y, r2.y, l(1)
|
||||||
|
ishl r2.x, r2.x, r2.y
|
||||||
|
store_raw U0[0].xyzw, r2.x, r0.xyzw
|
||||||
|
iadd r0.x, r2.x, l(0x00a00000)
|
||||||
|
store_raw U0[0].xyzw, r0.x, r1.xyzw
|
||||||
|
ret
|
||||||
|
// Approximately 45 instruction slots used
|
Binary file not shown.
|
@ -1,11 +1,11 @@
|
||||||
// generated from `xb buildhlsl`
|
// generated from `xb buildhlsl`
|
||||||
// source: edram_store_depth_float.cs.hlsl
|
// source: edram_store_depth_float.cs.hlsl
|
||||||
const uint8_t edram_store_depth_float_cs[] = {
|
const uint8_t edram_store_depth_float_cs[] = {
|
||||||
0x44, 0x58, 0x42, 0x43, 0xC6, 0x10, 0x80, 0x14, 0x97, 0x01, 0xE4, 0x46,
|
0x44, 0x58, 0x42, 0x43, 0xF1, 0x72, 0x64, 0x54, 0x9D, 0xF6, 0x79, 0x48,
|
||||||
0x76, 0xF1, 0x67, 0xD3, 0xDF, 0x50, 0x25, 0xF7, 0x01, 0x00, 0x00, 0x00,
|
0x2F, 0x8C, 0xD1, 0x59, 0x56, 0x1C, 0x90, 0x9A, 0x01, 0x00, 0x00, 0x00,
|
||||||
0x64, 0x0A, 0x00, 0x00, 0x05, 0x00, 0x00, 0x00, 0x34, 0x00, 0x00, 0x00,
|
0x28, 0x0A, 0x00, 0x00, 0x05, 0x00, 0x00, 0x00, 0x34, 0x00, 0x00, 0x00,
|
||||||
0x0C, 0x03, 0x00, 0x00, 0x1C, 0x03, 0x00, 0x00, 0x2C, 0x03, 0x00, 0x00,
|
0x0C, 0x03, 0x00, 0x00, 0x1C, 0x03, 0x00, 0x00, 0x2C, 0x03, 0x00, 0x00,
|
||||||
0xC8, 0x09, 0x00, 0x00, 0x52, 0x44, 0x45, 0x46, 0xD0, 0x02, 0x00, 0x00,
|
0x8C, 0x09, 0x00, 0x00, 0x52, 0x44, 0x45, 0x46, 0xD0, 0x02, 0x00, 0x00,
|
||||||
0x01, 0x00, 0x00, 0x00, 0x04, 0x01, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
0x01, 0x00, 0x00, 0x00, 0x04, 0x01, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
0x3C, 0x00, 0x00, 0x00, 0x01, 0x05, 0x53, 0x43, 0x00, 0x05, 0x00, 0x00,
|
0x3C, 0x00, 0x00, 0x00, 0x01, 0x05, 0x53, 0x43, 0x00, 0x05, 0x00, 0x00,
|
||||||
0xA8, 0x02, 0x00, 0x00, 0x13, 0x13, 0x44, 0x25, 0x3C, 0x00, 0x00, 0x00,
|
0xA8, 0x02, 0x00, 0x00, 0x13, 0x13, 0x44, 0x25, 0x3C, 0x00, 0x00, 0x00,
|
||||||
|
@ -69,7 +69,7 @@ const uint8_t edram_store_depth_float_cs[] = {
|
||||||
0x49, 0x53, 0x47, 0x4E, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0x49, 0x53, 0x47, 0x4E, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
0x08, 0x00, 0x00, 0x00, 0x4F, 0x53, 0x47, 0x4E, 0x08, 0x00, 0x00, 0x00,
|
0x08, 0x00, 0x00, 0x00, 0x4F, 0x53, 0x47, 0x4E, 0x08, 0x00, 0x00, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x53, 0x48, 0x45, 0x58,
|
0x00, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x53, 0x48, 0x45, 0x58,
|
||||||
0x94, 0x06, 0x00, 0x00, 0x51, 0x00, 0x05, 0x00, 0xA5, 0x01, 0x00, 0x00,
|
0x58, 0x06, 0x00, 0x00, 0x51, 0x00, 0x05, 0x00, 0x96, 0x01, 0x00, 0x00,
|
||||||
0x6A, 0x08, 0x00, 0x01, 0x59, 0x00, 0x00, 0x07, 0x46, 0x8E, 0x30, 0x00,
|
0x6A, 0x08, 0x00, 0x01, 0x59, 0x00, 0x00, 0x07, 0x46, 0x8E, 0x30, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xA1, 0x00, 0x00, 0x06,
|
0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xA1, 0x00, 0x00, 0x06,
|
||||||
|
@ -79,7 +79,7 @@ const uint8_t edram_store_depth_float_cs[] = {
|
||||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x5F, 0x00, 0x00, 0x02,
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x5F, 0x00, 0x00, 0x02,
|
||||||
0x32, 0x10, 0x02, 0x00, 0x5F, 0x00, 0x00, 0x02, 0x32, 0x20, 0x02, 0x00,
|
0x32, 0x10, 0x02, 0x00, 0x5F, 0x00, 0x00, 0x02, 0x32, 0x20, 0x02, 0x00,
|
||||||
0x5F, 0x00, 0x00, 0x02, 0x32, 0x00, 0x02, 0x00, 0x68, 0x00, 0x00, 0x02,
|
0x5F, 0x00, 0x00, 0x02, 0x32, 0x00, 0x02, 0x00, 0x68, 0x00, 0x00, 0x02,
|
||||||
0x05, 0x00, 0x00, 0x00, 0x9B, 0x00, 0x00, 0x04, 0x14, 0x00, 0x00, 0x00,
|
0x04, 0x00, 0x00, 0x00, 0x9B, 0x00, 0x00, 0x04, 0x14, 0x00, 0x00, 0x00,
|
||||||
0x10, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x29, 0x00, 0x00, 0x09,
|
0x10, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x29, 0x00, 0x00, 0x09,
|
||||||
0x32, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x06, 0x00, 0x02, 0x00,
|
0x32, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x06, 0x00, 0x02, 0x00,
|
||||||
0x02, 0x40, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00,
|
0x02, 0x40, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
|
@ -96,53 +96,53 @@ const uint8_t edram_store_depth_float_cs[] = {
|
||||||
0xF2, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
0xF2, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
||||||
0xFF, 0xFF, 0xFF, 0x7F, 0xFF, 0xFF, 0xFF, 0x7F, 0xFF, 0xFF, 0xFF, 0x7F,
|
0xFF, 0xFF, 0xFF, 0x7F, 0xFF, 0xFF, 0xFF, 0x7F, 0xFF, 0xFF, 0xFF, 0x7F,
|
||||||
0xFF, 0xFF, 0xFF, 0x7F, 0x46, 0x0E, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00,
|
0xFF, 0xFF, 0xFF, 0x7F, 0x46, 0x0E, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
0x01, 0x00, 0x00, 0x07, 0xF2, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
0x01, 0x00, 0x00, 0x07, 0xF2, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
0x46, 0x0E, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
0x46, 0x0E, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
0x02, 0x00, 0x00, 0x00, 0x54, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00,
|
0x02, 0x00, 0x00, 0x00, 0x54, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00,
|
||||||
0x02, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
0x01, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
0x02, 0x40, 0x00, 0x00, 0xF8, 0xFF, 0xFF, 0x3F, 0xF8, 0xFF, 0xFF, 0x3F,
|
0x02, 0x40, 0x00, 0x00, 0xF8, 0xFF, 0xFF, 0x3F, 0xF8, 0xFF, 0xFF, 0x3F,
|
||||||
0xF8, 0xFF, 0xFF, 0x3F, 0xF8, 0xFF, 0xFF, 0x3F, 0x8C, 0x00, 0x00, 0x14,
|
0xF8, 0xFF, 0xFF, 0x3F, 0xF8, 0xFF, 0xFF, 0x3F, 0x8C, 0x00, 0x00, 0x14,
|
||||||
0xF2, 0x00, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
0xF2, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
||||||
0x17, 0x00, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00,
|
0x17, 0x00, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00,
|
||||||
0x17, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0x17, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
0x46, 0x0E, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
0x46, 0x0E, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
||||||
0x00, 0x00, 0x80, 0x00, 0x00, 0x00, 0x80, 0x00, 0x00, 0x00, 0x80, 0x00,
|
0x00, 0x00, 0x80, 0x00, 0x00, 0x00, 0x80, 0x00, 0x00, 0x00, 0x80, 0x00,
|
||||||
0x00, 0x00, 0x80, 0x00, 0x55, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00,
|
0x00, 0x00, 0x80, 0x00, 0x55, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00,
|
||||||
0x04, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
0x03, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
0x02, 0x40, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00,
|
0x02, 0x40, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00,
|
||||||
0x17, 0x00, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x0B,
|
0x17, 0x00, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x0B,
|
||||||
0xF2, 0x00, 0x10, 0x00, 0x04, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x80,
|
0xF2, 0x00, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x80,
|
||||||
0x41, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
0x41, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
||||||
0x71, 0x00, 0x00, 0x00, 0x71, 0x00, 0x00, 0x00, 0x71, 0x00, 0x00, 0x00,
|
0x71, 0x00, 0x00, 0x00, 0x71, 0x00, 0x00, 0x00, 0x71, 0x00, 0x00, 0x00,
|
||||||
0x71, 0x00, 0x00, 0x00, 0x54, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00,
|
0x71, 0x00, 0x00, 0x00, 0x54, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00,
|
||||||
0x04, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x04, 0x00, 0x00, 0x00,
|
0x03, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
0x02, 0x40, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00,
|
0x02, 0x40, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00,
|
||||||
0x18, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x55, 0x00, 0x00, 0x07,
|
0x18, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x55, 0x00, 0x00, 0x07,
|
||||||
0xF2, 0x00, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
0xF2, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
0x03, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x04, 0x00, 0x00, 0x00,
|
0x02, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
0x4F, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00, 0x04, 0x00, 0x00, 0x00,
|
0x4F, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
0x46, 0x0E, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
0x46, 0x0E, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
||||||
0x00, 0x00, 0x80, 0x38, 0x00, 0x00, 0x80, 0x38, 0x00, 0x00, 0x80, 0x38,
|
0x00, 0x00, 0x80, 0x38, 0x00, 0x00, 0x80, 0x38, 0x00, 0x00, 0x80, 0x38,
|
||||||
0x00, 0x00, 0x80, 0x38, 0x1E, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00,
|
0x00, 0x00, 0x80, 0x38, 0x1E, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00,
|
||||||
0x02, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
0x01, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
0x02, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0xC8, 0x00, 0x00, 0x00, 0xC8,
|
0x02, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0xC8, 0x00, 0x00, 0x00, 0xC8,
|
||||||
0x00, 0x00, 0x00, 0xC8, 0x00, 0x00, 0x00, 0xC8, 0x37, 0x00, 0x00, 0x09,
|
0x00, 0x00, 0x00, 0xC8, 0x00, 0x00, 0x00, 0xC8, 0x37, 0x00, 0x00, 0x09,
|
||||||
|
0xF2, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
|
0x03, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
|
0x46, 0x0E, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x0A,
|
||||||
0xF2, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
0xF2, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
0x04, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00,
|
0x01, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
0x46, 0x0E, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x0A,
|
|
||||||
0xF2, 0x00, 0x10, 0x00, 0x03, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
|
||||||
0x02, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
|
||||||
0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
0x8A, 0x00, 0x00, 0x0F, 0xF2, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
0x8A, 0x00, 0x00, 0x0F, 0xF2, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
0x02, 0x40, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
0x02, 0x40, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
||||||
0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
0x03, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
0x03, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
0x1E, 0x00, 0x00, 0x07, 0xF2, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
0x1E, 0x00, 0x00, 0x07, 0xF2, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
0x46, 0x0E, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
0x46, 0x0E, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
0x03, 0x00, 0x00, 0x00, 0x55, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00,
|
0x02, 0x00, 0x00, 0x00, 0x55, 0x00, 0x00, 0x0A, 0xF2, 0x00, 0x10, 0x00,
|
||||||
0x02, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
0x01, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
0x02, 0x40, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
0x02, 0x40, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0xA5, 0x00, 0x00, 0x08,
|
0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0xA5, 0x00, 0x00, 0x08,
|
||||||
0x12, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x10, 0x00,
|
0x12, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x10, 0x00,
|
||||||
|
@ -155,64 +155,59 @@ const uint8_t edram_store_depth_float_cs[] = {
|
||||||
0x18, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00,
|
0x18, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00,
|
||||||
0x18, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00,
|
0x18, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00,
|
||||||
0x08, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00,
|
0x08, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00,
|
||||||
0x46, 0x0E, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
0x46, 0x0E, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0x29, 0x00, 0x00, 0x06, 0x12, 0x00, 0x10, 0x00,
|
0x00, 0x00, 0x00, 0x00, 0x29, 0x00, 0x00, 0x06, 0x12, 0x00, 0x10, 0x00,
|
||||||
0x02, 0x00, 0x00, 0x00, 0x0A, 0x20, 0x02, 0x00, 0x01, 0x40, 0x00, 0x00,
|
0x01, 0x00, 0x00, 0x00, 0x0A, 0x20, 0x02, 0x00, 0x01, 0x40, 0x00, 0x00,
|
||||||
0x02, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x0C, 0x62, 0x00, 0x10, 0x00,
|
0x02, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x0C, 0x62, 0x00, 0x10, 0x00,
|
||||||
0x02, 0x00, 0x00, 0x00, 0x06, 0x80, 0x30, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0x01, 0x00, 0x00, 0x00, 0x06, 0x80, 0x30, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x80, 0x00, 0x00, 0xFF, 0x07, 0x00, 0x00,
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x80, 0x00, 0x00, 0xFF, 0x07, 0x00, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0x1F, 0x00, 0x04, 0x03, 0x1A, 0x00, 0x10, 0x00,
|
0x00, 0x00, 0x00, 0x00, 0x1F, 0x00, 0x04, 0x03, 0x1A, 0x00, 0x10, 0x00,
|
||||||
0x02, 0x00, 0x00, 0x00, 0x4F, 0x00, 0x00, 0x06, 0x22, 0x00, 0x10, 0x00,
|
0x01, 0x00, 0x00, 0x00, 0x4F, 0x00, 0x00, 0x06, 0x22, 0x00, 0x10, 0x00,
|
||||||
0x02, 0x00, 0x00, 0x00, 0x0A, 0x20, 0x02, 0x00, 0x01, 0x40, 0x00, 0x00,
|
0x01, 0x00, 0x00, 0x00, 0x0A, 0x20, 0x02, 0x00, 0x01, 0x40, 0x00, 0x00,
|
||||||
0x0A, 0x00, 0x00, 0x00, 0x50, 0x00, 0x00, 0x06, 0x82, 0x00, 0x10, 0x00,
|
0x0A, 0x00, 0x00, 0x00, 0x50, 0x00, 0x00, 0x06, 0x82, 0x00, 0x10, 0x00,
|
||||||
0x02, 0x00, 0x00, 0x00, 0x0A, 0x20, 0x02, 0x00, 0x01, 0x40, 0x00, 0x00,
|
0x01, 0x00, 0x00, 0x00, 0x0A, 0x20, 0x02, 0x00, 0x01, 0x40, 0x00, 0x00,
|
||||||
0x0A, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x0A, 0xA2, 0x00, 0x10, 0x00,
|
0x0A, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x0A, 0xA2, 0x00, 0x10, 0x00,
|
||||||
0x02, 0x00, 0x00, 0x00, 0x56, 0x0D, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
0x01, 0x00, 0x00, 0x00, 0x56, 0x0D, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
0x02, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x28, 0x00, 0x00, 0x00,
|
0x02, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x28, 0x00, 0x00, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0xD8, 0xFF, 0xFF, 0xFF, 0x1E, 0x00, 0x00, 0x07,
|
0x00, 0x00, 0x00, 0x00, 0xD8, 0xFF, 0xFF, 0xFF, 0x1E, 0x00, 0x00, 0x07,
|
||||||
0x22, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x3A, 0x00, 0x10, 0x00,
|
0x22, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00, 0x3A, 0x00, 0x10, 0x00,
|
||||||
0x02, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
0x01, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
0x1E, 0x00, 0x00, 0x07, 0x12, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
0x1E, 0x00, 0x00, 0x07, 0x12, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
0x1A, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00,
|
0x1A, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00,
|
||||||
0x02, 0x00, 0x00, 0x00, 0x15, 0x00, 0x00, 0x01, 0x55, 0x00, 0x00, 0x09,
|
0x01, 0x00, 0x00, 0x00, 0x15, 0x00, 0x00, 0x01, 0x55, 0x00, 0x00, 0x09,
|
||||||
0x22, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x0A, 0x80, 0x30, 0x00,
|
0x22, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00, 0x0A, 0x80, 0x30, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
0x01, 0x40, 0x00, 0x00, 0x10, 0x00, 0x00, 0x00, 0x23, 0x00, 0x00, 0x08,
|
0x01, 0x40, 0x00, 0x00, 0x10, 0x00, 0x00, 0x00, 0x23, 0x00, 0x00, 0x08,
|
||||||
0x22, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x1A, 0x10, 0x02, 0x00,
|
0x22, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00, 0x1A, 0x10, 0x02, 0x00,
|
||||||
0x1A, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x2A, 0x00, 0x10, 0x00,
|
0x1A, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00, 0x2A, 0x00, 0x10, 0x00,
|
||||||
0x02, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x06, 0x22, 0x00, 0x10, 0x00,
|
0x01, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x06, 0x22, 0x00, 0x10, 0x00,
|
||||||
0x02, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
0x01, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
0x0A, 0x10, 0x02, 0x00, 0x26, 0x00, 0x00, 0x07, 0x00, 0xD0, 0x00, 0x00,
|
0x0A, 0x10, 0x02, 0x00, 0x26, 0x00, 0x00, 0x07, 0x00, 0xD0, 0x00, 0x00,
|
||||||
0x42, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x1A, 0x20, 0x02, 0x00,
|
0x42, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00, 0x1A, 0x20, 0x02, 0x00,
|
||||||
0x01, 0x40, 0x00, 0x00, 0x40, 0x01, 0x00, 0x00, 0x23, 0x00, 0x00, 0x09,
|
0x01, 0x40, 0x00, 0x00, 0x40, 0x01, 0x00, 0x00, 0x23, 0x00, 0x00, 0x09,
|
||||||
0x22, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x10, 0x00,
|
0x22, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x10, 0x00,
|
||||||
0x02, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00,
|
0x01, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00,
|
||||||
0x2A, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x29, 0x00, 0x00, 0x07,
|
0x2A, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00, 0x29, 0x00, 0x00, 0x07,
|
||||||
0x12, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00,
|
0x12, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00,
|
||||||
0x02, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00,
|
0x01, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
0x1E, 0x00, 0x00, 0x07, 0x12, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
0x1E, 0x00, 0x00, 0x07, 0x12, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
0x0A, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x10, 0x00,
|
0x0A, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x10, 0x00,
|
||||||
0x02, 0x00, 0x00, 0x00, 0x8A, 0x00, 0x00, 0x0B, 0x22, 0x00, 0x10, 0x00,
|
0x01, 0x00, 0x00, 0x00, 0x8A, 0x00, 0x00, 0x0B, 0x22, 0x00, 0x10, 0x00,
|
||||||
0x02, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
0x01, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
0x01, 0x40, 0x00, 0x00, 0x0D, 0x00, 0x00, 0x00, 0x0A, 0x80, 0x30, 0x00,
|
0x01, 0x40, 0x00, 0x00, 0x0D, 0x00, 0x00, 0x00, 0x0A, 0x80, 0x30, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
0x29, 0x00, 0x00, 0x07, 0x22, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
0x29, 0x00, 0x00, 0x07, 0x22, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
0x1A, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00,
|
0x1A, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00,
|
||||||
0x01, 0x00, 0x00, 0x00, 0x29, 0x00, 0x00, 0x07, 0x12, 0x00, 0x10, 0x00,
|
0x01, 0x00, 0x00, 0x00, 0x29, 0x00, 0x00, 0x07, 0x12, 0x00, 0x10, 0x00,
|
||||||
0x02, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
0x01, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
0x1A, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0xA6, 0x00, 0x00, 0x08,
|
0x1A, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00, 0xA6, 0x00, 0x00, 0x08,
|
||||||
0xF2, 0xE0, 0x21, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0xF2, 0xE0, 0x21, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
0x0A, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
0x0A, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x07, 0x12, 0x00, 0x10, 0x00,
|
0x00, 0x00, 0x00, 0x00, 0x3E, 0x00, 0x00, 0x01, 0x53, 0x54, 0x41, 0x54,
|
||||||
0x00, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00, 0x02, 0x00, 0x00, 0x00,
|
0x94, 0x00, 0x00, 0x00, 0x2B, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00,
|
||||||
0x01, 0x40, 0x00, 0x00, 0x00, 0x00, 0xA0, 0x00, 0xA6, 0x00, 0x00, 0x08,
|
|
||||||
0xF2, 0xE0, 0x21, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
|
||||||
0x0A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x46, 0x0E, 0x10, 0x00,
|
|
||||||
0x01, 0x00, 0x00, 0x00, 0x3E, 0x00, 0x00, 0x01, 0x53, 0x54, 0x41, 0x54,
|
|
||||||
0x94, 0x00, 0x00, 0x00, 0x2D, 0x00, 0x00, 0x00, 0x05, 0x00, 0x00, 0x00,
|
|
||||||
0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
0x13, 0x00, 0x00, 0x00, 0x0E, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
0x12, 0x00, 0x00, 0x00, 0x0E, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0x00, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
@ -222,5 +217,5 @@ const uint8_t edram_store_depth_float_cs[] = {
|
||||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
0x00, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00,
|
0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
};
|
};
|
||||||
|
|
|
@ -45,51 +45,49 @@ dcl_uav_raw U0[0:0], space=0
|
||||||
dcl_input vThreadGroupID.xy
|
dcl_input vThreadGroupID.xy
|
||||||
dcl_input vThreadIDInGroup.xy
|
dcl_input vThreadIDInGroup.xy
|
||||||
dcl_input vThreadID.xy
|
dcl_input vThreadID.xy
|
||||||
dcl_temps 5
|
dcl_temps 4
|
||||||
dcl_thread_group 20, 16, 1
|
dcl_thread_group 20, 16, 1
|
||||||
ishl r0.xy, vThreadID.xxxx, l(4, 2, 0, 0)
|
ishl r0.xy, vThreadID.xxxx, l(4, 2, 0, 0)
|
||||||
imad r0.xy, vThreadID.yyyy, CB0[0][0].ywyy, r0.xyxx
|
imad r0.xy, vThreadID.yyyy, CB0[0][0].ywyy, r0.xyxx
|
||||||
iadd r0.xy, r0.xyxx, CB0[0][0].xzxx
|
iadd r0.xy, r0.xyxx, CB0[0][0].xzxx
|
||||||
ld_raw r1.xyzw, r0.x, T0[0].xyzw
|
ld_raw r1.xyzw, r0.x, T0[0].xyzw
|
||||||
uge r2.xyzw, l(0x7fffffff, 0x7fffffff, 0x7fffffff, 0x7fffffff), r1.xyzw
|
uge r2.xyzw, l(0x7fffffff, 0x7fffffff, 0x7fffffff, 0x7fffffff), r1.xyzw
|
||||||
and r2.xyzw, r1.xyzw, r2.xyzw
|
and r1.xyzw, r1.xyzw, r2.xyzw
|
||||||
umin r2.xyzw, r2.xyzw, l(0x3ffffff8, 0x3ffffff8, 0x3ffffff8, 0x3ffffff8)
|
umin r1.xyzw, r1.xyzw, l(0x3ffffff8, 0x3ffffff8, 0x3ffffff8, 0x3ffffff8)
|
||||||
bfi r3.xyzw, l(23, 23, 23, 23), l(0, 0, 0, 0), r2.xyzw, l(0x00800000, 0x00800000, 0x00800000, 0x00800000)
|
bfi r2.xyzw, l(23, 23, 23, 23), l(0, 0, 0, 0), r1.xyzw, l(0x00800000, 0x00800000, 0x00800000, 0x00800000)
|
||||||
ushr r4.xyzw, r2.xyzw, l(23, 23, 23, 23)
|
ushr r3.xyzw, r1.xyzw, l(23, 23, 23, 23)
|
||||||
iadd r4.xyzw, -r4.xyzw, l(113, 113, 113, 113)
|
iadd r3.xyzw, -r3.xyzw, l(113, 113, 113, 113)
|
||||||
umin r4.xyzw, r4.xyzw, l(24, 24, 24, 24)
|
umin r3.xyzw, r3.xyzw, l(24, 24, 24, 24)
|
||||||
ushr r3.xyzw, r3.xyzw, r4.xyzw
|
ushr r2.xyzw, r2.xyzw, r3.xyzw
|
||||||
ult r4.xyzw, r2.xyzw, l(0x38800000, 0x38800000, 0x38800000, 0x38800000)
|
ult r3.xyzw, r1.xyzw, l(0x38800000, 0x38800000, 0x38800000, 0x38800000)
|
||||||
iadd r2.xyzw, r2.xyzw, l(0xc8000000, 0xc8000000, 0xc8000000, 0xc8000000)
|
iadd r1.xyzw, r1.xyzw, l(0xc8000000, 0xc8000000, 0xc8000000, 0xc8000000)
|
||||||
movc r2.xyzw, r4.xyzw, r3.xyzw, r2.xyzw
|
movc r1.xyzw, r3.xyzw, r2.xyzw, r1.xyzw
|
||||||
iadd r3.xyzw, r2.xyzw, l(3, 3, 3, 3)
|
iadd r2.xyzw, r1.xyzw, l(3, 3, 3, 3)
|
||||||
ubfe r2.xyzw, l(1, 1, 1, 1), l(3, 3, 3, 3), r2.xyzw
|
ubfe r1.xyzw, l(1, 1, 1, 1), l(3, 3, 3, 3), r1.xyzw
|
||||||
iadd r2.xyzw, r2.xyzw, r3.xyzw
|
iadd r1.xyzw, r1.xyzw, r2.xyzw
|
||||||
ushr r2.xyzw, r2.xyzw, l(3, 3, 3, 3)
|
ushr r1.xyzw, r1.xyzw, l(3, 3, 3, 3)
|
||||||
ld_raw r0.x, r0.y, T0[0].xxxx
|
ld_raw r0.x, r0.y, T0[0].xxxx
|
||||||
ushr r0.yzw, r0.xxxx, l(0, 8, 16, 24)
|
ushr r0.yzw, r0.xxxx, l(0, 8, 16, 24)
|
||||||
bfi r0.xyzw, l(24, 24, 24, 24), l(8, 8, 8, 8), r2.xyzw, r0.xyzw
|
bfi r0.xyzw, l(24, 24, 24, 24), l(8, 8, 8, 8), r1.xyzw, r0.xyzw
|
||||||
ishl r2.x, vThreadIDInGroup.x, l(2)
|
ishl r1.x, vThreadIDInGroup.x, l(2)
|
||||||
and r2.yz, CB0[0][1].xxxx, l(0, 0x00008000, 2047, 0)
|
and r1.yz, CB0[0][1].xxxx, l(0, 0x00008000, 2047, 0)
|
||||||
if_nz r2.y
|
if_nz r1.y
|
||||||
ult r2.y, vThreadIDInGroup.x, l(10)
|
ult r1.y, vThreadIDInGroup.x, l(10)
|
||||||
uge r2.w, vThreadIDInGroup.x, l(10)
|
uge r1.w, vThreadIDInGroup.x, l(10)
|
||||||
and r2.yw, r2.yyyw, l(0, 40, 0, -40)
|
and r1.yw, r1.yyyw, l(0, 40, 0, -40)
|
||||||
iadd r2.y, r2.w, r2.y
|
iadd r1.y, r1.w, r1.y
|
||||||
iadd r2.x, r2.y, r2.x
|
iadd r1.x, r1.y, r1.x
|
||||||
endif
|
endif
|
||||||
ushr r2.y, CB0[0][1].x, l(16)
|
ushr r1.y, CB0[0][1].x, l(16)
|
||||||
imad r2.y, vThreadGroupID.y, r2.y, r2.z
|
imad r1.y, vThreadGroupID.y, r1.y, r1.z
|
||||||
iadd r2.y, r2.y, vThreadGroupID.x
|
iadd r1.y, r1.y, vThreadGroupID.x
|
||||||
imul null, r2.z, vThreadIDInGroup.y, l(320)
|
imul null, r1.z, vThreadIDInGroup.y, l(320)
|
||||||
imad r2.y, r2.y, l(5120), r2.z
|
imad r1.y, r1.y, l(5120), r1.z
|
||||||
ishl r2.x, r2.x, l(2)
|
ishl r1.x, r1.x, l(2)
|
||||||
iadd r2.x, r2.x, r2.y
|
iadd r1.x, r1.x, r1.y
|
||||||
ubfe r2.y, l(1), l(13), CB0[0][1].x
|
ubfe r1.y, l(1), l(13), CB0[0][1].x
|
||||||
ishl r2.y, r2.y, l(1)
|
ishl r1.y, r1.y, l(1)
|
||||||
ishl r2.x, r2.x, r2.y
|
ishl r1.x, r1.x, r1.y
|
||||||
store_raw U0[0].xyzw, r2.x, r0.xyzw
|
store_raw U0[0].xyzw, r1.x, r0.xyzw
|
||||||
iadd r0.x, r2.x, l(0x00a00000)
|
|
||||||
store_raw U0[0].xyzw, r0.x, r1.xyzw
|
|
||||||
ret
|
ret
|
||||||
// Approximately 45 instruction slots used
|
// Approximately 43 instruction slots used
|
||||||
|
|
Binary file not shown.
|
@ -0,0 +1,156 @@
|
||||||
|
// generated from `xb buildhlsl`
|
||||||
|
// source: float24_round.ps.hlsl
|
||||||
|
const uint8_t float24_round_ps[] = {
|
||||||
|
0x44, 0x58, 0x42, 0x43, 0xDF, 0x71, 0xF3, 0x0A, 0x4A, 0xDB, 0xC3, 0x80,
|
||||||
|
0x1E, 0xE4, 0x39, 0x21, 0x59, 0x07, 0x78, 0x97, 0x01, 0x00, 0x00, 0x00,
|
||||||
|
0x18, 0x07, 0x00, 0x00, 0x05, 0x00, 0x00, 0x00, 0x34, 0x00, 0x00, 0x00,
|
||||||
|
0xA0, 0x00, 0x00, 0x00, 0x90, 0x02, 0x00, 0x00, 0xC4, 0x02, 0x00, 0x00,
|
||||||
|
0x7C, 0x06, 0x00, 0x00, 0x52, 0x44, 0x45, 0x46, 0x64, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x3C, 0x00, 0x00, 0x00, 0x01, 0x05, 0xFF, 0xFF, 0x00, 0x05, 0x00, 0x00,
|
||||||
|
0x3C, 0x00, 0x00, 0x00, 0x13, 0x13, 0x44, 0x25, 0x3C, 0x00, 0x00, 0x00,
|
||||||
|
0x18, 0x00, 0x00, 0x00, 0x28, 0x00, 0x00, 0x00, 0x28, 0x00, 0x00, 0x00,
|
||||||
|
0x24, 0x00, 0x00, 0x00, 0x0C, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x4D, 0x69, 0x63, 0x72, 0x6F, 0x73, 0x6F, 0x66, 0x74, 0x20, 0x28, 0x52,
|
||||||
|
0x29, 0x20, 0x48, 0x4C, 0x53, 0x4C, 0x20, 0x53, 0x68, 0x61, 0x64, 0x65,
|
||||||
|
0x72, 0x20, 0x43, 0x6F, 0x6D, 0x70, 0x69, 0x6C, 0x65, 0x72, 0x20, 0x31,
|
||||||
|
0x30, 0x2E, 0x31, 0x00, 0x49, 0x53, 0x47, 0x4E, 0xE8, 0x01, 0x00, 0x00,
|
||||||
|
0x13, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x03, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x04, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x05, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x05, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x06, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x07, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x08, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x09, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x09, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x0A, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x0A, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x0B, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x0B, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x0C, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x0C, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x0D, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x0D, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x0E, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x0E, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x0F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x0F, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x10, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x11, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x11, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0xD9, 0x01, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x12, 0x00, 0x00, 0x00, 0x0F, 0x04, 0x00, 0x00, 0x54, 0x45, 0x58, 0x43,
|
||||||
|
0x4F, 0x4F, 0x52, 0x44, 0x00, 0x53, 0x56, 0x5F, 0x50, 0x6F, 0x73, 0x69,
|
||||||
|
0x74, 0x69, 0x6F, 0x6E, 0x00, 0xAB, 0xAB, 0xAB, 0x4F, 0x53, 0x47, 0x4E,
|
||||||
|
0x2C, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00,
|
||||||
|
0x20, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x03, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0x01, 0x0E, 0x00, 0x00,
|
||||||
|
0x53, 0x56, 0x5F, 0x44, 0x65, 0x70, 0x74, 0x68, 0x00, 0xAB, 0xAB, 0xAB,
|
||||||
|
0x53, 0x48, 0x45, 0x58, 0xB0, 0x03, 0x00, 0x00, 0x51, 0x00, 0x00, 0x00,
|
||||||
|
0xEC, 0x00, 0x00, 0x00, 0x6A, 0x08, 0x00, 0x01, 0x64, 0x38, 0x00, 0x04,
|
||||||
|
0x42, 0x10, 0x10, 0x00, 0x12, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
|
0x65, 0x00, 0x00, 0x02, 0x01, 0xC0, 0x00, 0x00, 0x68, 0x00, 0x00, 0x02,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x36, 0x20, 0x08, 0x05, 0x12, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x2A, 0x10, 0x10, 0x00, 0x12, 0x00, 0x00, 0x00,
|
||||||
|
0x50, 0x00, 0x10, 0x07, 0x22, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x40, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0x7F, 0x0A, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x08, 0x07, 0x12, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x1A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x54, 0x00, 0x08, 0x07,
|
||||||
|
0x12, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00, 0xF8, 0xFF, 0xFF, 0x3F,
|
||||||
|
0x8C, 0x00, 0x10, 0x0B, 0x22, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x40, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x40, 0x00, 0x00, 0x00, 0x00, 0x80, 0x00, 0x55, 0x00, 0x20, 0x07,
|
||||||
|
0x42, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00,
|
||||||
|
0x1E, 0x00, 0x20, 0x08, 0x42, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x2A, 0x00, 0x10, 0x80, 0x41, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x40, 0x00, 0x00, 0x71, 0x00, 0x00, 0x00, 0x54, 0x00, 0x20, 0x07,
|
||||||
|
0x42, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x2A, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00,
|
||||||
|
0x55, 0x00, 0x10, 0x07, 0x22, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x1A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x2A, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x4F, 0x00, 0x20, 0x07, 0x42, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x40, 0x00, 0x00, 0x00, 0x00, 0x80, 0x38, 0x1E, 0x00, 0x08, 0x07,
|
||||||
|
0x12, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0xC8,
|
||||||
|
0x37, 0x00, 0x08, 0x09, 0x12, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x2A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x1E, 0x00, 0x10, 0x07, 0x22, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x0A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00,
|
||||||
|
0x03, 0x00, 0x00, 0x00, 0x8A, 0x00, 0x08, 0x09, 0x12, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x40, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x08, 0x07, 0x12, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x1A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x8A, 0x00, 0x38, 0x0F,
|
||||||
|
0x72, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00,
|
||||||
|
0x18, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x02, 0x40, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x03, 0x00, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x06, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x87, 0x00, 0x40, 0x05,
|
||||||
|
0x82, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x40, 0x07, 0x82, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x3A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x40, 0x00, 0x00, 0xF5, 0xFF, 0xFF, 0xFF, 0x37, 0x00, 0x40, 0x09,
|
||||||
|
0x82, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x3A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x40, 0x00, 0x00, 0x15, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x08, 0x08,
|
||||||
|
0x12, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00, 0x3A, 0x00, 0x10, 0x80,
|
||||||
|
0x41, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00,
|
||||||
|
0x01, 0x00, 0x00, 0x00, 0x37, 0x00, 0x08, 0x09, 0x12, 0x00, 0x10, 0x00,
|
||||||
|
0x01, 0x00, 0x00, 0x00, 0x2A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x2A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00,
|
||||||
|
0x01, 0x00, 0x00, 0x00, 0x29, 0x00, 0x40, 0x07, 0x82, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x3A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x40, 0x07,
|
||||||
|
0x82, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x3A, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00, 0xFF, 0xFF, 0x0F, 0x00,
|
||||||
|
0x37, 0x00, 0x10, 0x09, 0x22, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x2A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x3A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x29, 0x00, 0x20, 0x07, 0x42, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x0A, 0x00, 0x10, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00,
|
||||||
|
0x17, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x20, 0x07, 0x42, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x2A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x38, 0x29, 0x00, 0x10, 0x07,
|
||||||
|
0x22, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x1E, 0x00, 0x10, 0x07, 0x22, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x2A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x37, 0x00, 0x08, 0x08, 0x01, 0xC0, 0x00, 0x00,
|
||||||
|
0x0A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x3E, 0x00, 0x00, 0x01, 0x53, 0x54, 0x41, 0x54, 0x94, 0x00, 0x00, 0x00,
|
||||||
|
0x1E, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0B, 0x00, 0x00, 0x00,
|
||||||
|
0x08, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x05, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00,
|
||||||
|
};
|
|
@ -0,0 +1,74 @@
|
||||||
|
//
|
||||||
|
// Generated by Microsoft (R) HLSL Shader Compiler 10.1
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
// Input signature:
|
||||||
|
//
|
||||||
|
// Name Index Mask Register SysValue Format Used
|
||||||
|
// -------------------- ----- ------ -------- -------- ------- ------
|
||||||
|
// TEXCOORD 0 xyzw 0 NONE float
|
||||||
|
// TEXCOORD 1 xyzw 1 NONE float
|
||||||
|
// TEXCOORD 2 xyzw 2 NONE float
|
||||||
|
// TEXCOORD 3 xyzw 3 NONE float
|
||||||
|
// TEXCOORD 4 xyzw 4 NONE float
|
||||||
|
// TEXCOORD 5 xyzw 5 NONE float
|
||||||
|
// TEXCOORD 6 xyzw 6 NONE float
|
||||||
|
// TEXCOORD 7 xyzw 7 NONE float
|
||||||
|
// TEXCOORD 8 xyzw 8 NONE float
|
||||||
|
// TEXCOORD 9 xyzw 9 NONE float
|
||||||
|
// TEXCOORD 10 xyzw 10 NONE float
|
||||||
|
// TEXCOORD 11 xyzw 11 NONE float
|
||||||
|
// TEXCOORD 12 xyzw 12 NONE float
|
||||||
|
// TEXCOORD 13 xyzw 13 NONE float
|
||||||
|
// TEXCOORD 14 xyzw 14 NONE float
|
||||||
|
// TEXCOORD 15 xyzw 15 NONE float
|
||||||
|
// TEXCOORD 16 xyz 16 NONE float
|
||||||
|
// TEXCOORD 17 xy 17 NONE float
|
||||||
|
// SV_Position 0 xyzw 18 POS float z
|
||||||
|
//
|
||||||
|
//
|
||||||
|
// Output signature:
|
||||||
|
//
|
||||||
|
// Name Index Mask Register SysValue Format Used
|
||||||
|
// -------------------- ----- ------ -------- -------- ------- ------
|
||||||
|
// SV_Depth 0 N/A oDepth DEPTH float YES
|
||||||
|
//
|
||||||
|
// Pixel Shader runs at sample frequency
|
||||||
|
//
|
||||||
|
ps_5_1
|
||||||
|
dcl_globalFlags refactoringAllowed
|
||||||
|
dcl_input_ps_siv linear noperspective sample v18.z, position
|
||||||
|
dcl_output oDepth
|
||||||
|
dcl_temps 2
|
||||||
|
mov_sat [precise(x)] r0.x, v18.z
|
||||||
|
uge [precise(y)] r0.y, l(0x7fffffff), r0.x
|
||||||
|
and [precise(x)] r0.x, r0.x, r0.y
|
||||||
|
umin [precise(x)] r0.x, r0.x, l(0x3ffffff8)
|
||||||
|
bfi [precise(y)] r0.y, l(23), l(0), r0.x, l(0x00800000)
|
||||||
|
ushr [precise(z)] r0.z, r0.x, l(23)
|
||||||
|
iadd [precise(z)] r0.z, -r0.z, l(113)
|
||||||
|
umin [precise(z)] r0.z, r0.z, l(24)
|
||||||
|
ushr [precise(y)] r0.y, r0.y, r0.z
|
||||||
|
ult [precise(z)] r0.z, r0.x, l(0x38800000)
|
||||||
|
iadd [precise(x)] r0.x, r0.x, l(0xc8000000)
|
||||||
|
movc [precise(x)] r0.x, r0.z, r0.y, r0.x
|
||||||
|
iadd [precise(y)] r0.y, r0.x, l(3)
|
||||||
|
ubfe [precise(x)] r0.x, l(1), l(3), r0.x
|
||||||
|
iadd [precise(x)] r0.x, r0.x, r0.y
|
||||||
|
ubfe [precise(xyz)] r0.xyz, l(24, 20, 4, 0), l(3, 3, 23, 0), r0.xxxx
|
||||||
|
firstbit_hi [precise(w)] r0.w, r0.y
|
||||||
|
iadd [precise(w)] r0.w, r0.w, l(-11)
|
||||||
|
movc [precise(w)] r0.w, r0.y, r0.w, l(21)
|
||||||
|
iadd [precise(x)] r1.x, -r0.w, l(1)
|
||||||
|
movc [precise(x)] r1.x, r0.z, r0.z, r1.x
|
||||||
|
ishl [precise(w)] r0.w, r0.y, r0.w
|
||||||
|
and [precise(w)] r0.w, r0.w, l(0x000fffff)
|
||||||
|
movc [precise(y)] r0.y, r0.z, r0.y, r0.w
|
||||||
|
ishl [precise(z)] r0.z, r1.x, l(23)
|
||||||
|
iadd [precise(z)] r0.z, r0.z, l(0x38000000)
|
||||||
|
ishl [precise(y)] r0.y, r0.y, l(3)
|
||||||
|
iadd [precise(y)] r0.y, r0.z, r0.y
|
||||||
|
movc [precise(x)] oDepth, r0.x, r0.y, l(0)
|
||||||
|
ret
|
||||||
|
// Approximately 30 instruction slots used
|
Binary file not shown.
|
@ -0,0 +1,100 @@
|
||||||
|
// generated from `xb buildhlsl`
|
||||||
|
// source: float24_truncate.ps.hlsl
|
||||||
|
const uint8_t float24_truncate_ps[] = {
|
||||||
|
0x44, 0x58, 0x42, 0x43, 0xB8, 0x51, 0x55, 0x1D, 0xF4, 0xF1, 0xC9, 0xC0,
|
||||||
|
0x0C, 0x22, 0xD3, 0x43, 0x94, 0xDF, 0x83, 0x9D, 0x01, 0x00, 0x00, 0x00,
|
||||||
|
0x7C, 0x04, 0x00, 0x00, 0x05, 0x00, 0x00, 0x00, 0x34, 0x00, 0x00, 0x00,
|
||||||
|
0xA0, 0x00, 0x00, 0x00, 0x90, 0x02, 0x00, 0x00, 0xCC, 0x02, 0x00, 0x00,
|
||||||
|
0xE0, 0x03, 0x00, 0x00, 0x52, 0x44, 0x45, 0x46, 0x64, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x3C, 0x00, 0x00, 0x00, 0x01, 0x05, 0xFF, 0xFF, 0x00, 0x05, 0x00, 0x00,
|
||||||
|
0x3C, 0x00, 0x00, 0x00, 0x13, 0x13, 0x44, 0x25, 0x3C, 0x00, 0x00, 0x00,
|
||||||
|
0x18, 0x00, 0x00, 0x00, 0x28, 0x00, 0x00, 0x00, 0x28, 0x00, 0x00, 0x00,
|
||||||
|
0x24, 0x00, 0x00, 0x00, 0x0C, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x4D, 0x69, 0x63, 0x72, 0x6F, 0x73, 0x6F, 0x66, 0x74, 0x20, 0x28, 0x52,
|
||||||
|
0x29, 0x20, 0x48, 0x4C, 0x53, 0x4C, 0x20, 0x53, 0x68, 0x61, 0x64, 0x65,
|
||||||
|
0x72, 0x20, 0x43, 0x6F, 0x6D, 0x70, 0x69, 0x6C, 0x65, 0x72, 0x20, 0x31,
|
||||||
|
0x30, 0x2E, 0x31, 0x00, 0x49, 0x53, 0x47, 0x4E, 0xE8, 0x01, 0x00, 0x00,
|
||||||
|
0x13, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x03, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x04, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x05, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x05, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x06, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x07, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x08, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x09, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x09, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x0A, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x0A, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x0B, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x0B, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x0C, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x0C, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x0D, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x0D, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x0E, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x0E, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x0F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x0F, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x10, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0xD0, 0x01, 0x00, 0x00,
|
||||||
|
0x11, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x11, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0xD9, 0x01, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x12, 0x00, 0x00, 0x00, 0x0F, 0x04, 0x00, 0x00, 0x54, 0x45, 0x58, 0x43,
|
||||||
|
0x4F, 0x4F, 0x52, 0x44, 0x00, 0x53, 0x56, 0x5F, 0x50, 0x6F, 0x73, 0x69,
|
||||||
|
0x74, 0x69, 0x6F, 0x6E, 0x00, 0xAB, 0xAB, 0xAB, 0x4F, 0x53, 0x47, 0x4E,
|
||||||
|
0x34, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00,
|
||||||
|
0x20, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x03, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0x01, 0x0E, 0x00, 0x00,
|
||||||
|
0x53, 0x56, 0x5F, 0x44, 0x65, 0x70, 0x74, 0x68, 0x4C, 0x65, 0x73, 0x73,
|
||||||
|
0x45, 0x71, 0x75, 0x61, 0x6C, 0x00, 0xAB, 0xAB, 0x53, 0x48, 0x45, 0x58,
|
||||||
|
0x0C, 0x01, 0x00, 0x00, 0x51, 0x00, 0x00, 0x00, 0x43, 0x00, 0x00, 0x00,
|
||||||
|
0x6A, 0x08, 0x00, 0x01, 0x64, 0x38, 0x00, 0x04, 0x42, 0x10, 0x10, 0x00,
|
||||||
|
0x12, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x65, 0x00, 0x00, 0x02,
|
||||||
|
0x01, 0x70, 0x02, 0x00, 0x68, 0x00, 0x00, 0x02, 0x01, 0x00, 0x00, 0x00,
|
||||||
|
0x36, 0x20, 0x08, 0x05, 0x12, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x2A, 0x10, 0x10, 0x00, 0x12, 0x00, 0x00, 0x00, 0x50, 0x00, 0x10, 0x07,
|
||||||
|
0x22, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00, 0x00, 0x00, 0x80, 0x2E,
|
||||||
|
0x1F, 0x00, 0x04, 0x03, 0x1A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x8A, 0x00, 0x10, 0x09, 0x22, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x40, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00,
|
||||||
|
0x17, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x1E, 0x00, 0x10, 0x08, 0x22, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x1A, 0x00, 0x10, 0x80, 0x41, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x40, 0x00, 0x00, 0x74, 0x00, 0x00, 0x00, 0x24, 0x00, 0x10, 0x07,
|
||||||
|
0x22, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||||
|
0x8C, 0x00, 0x08, 0x0A, 0x01, 0x70, 0x02, 0x00, 0x1A, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x01, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x10, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x12, 0x00, 0x00, 0x01, 0x36, 0x00, 0x08, 0x04,
|
||||||
|
0x01, 0x70, 0x02, 0x00, 0x01, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x15, 0x00, 0x00, 0x01, 0x3E, 0x00, 0x00, 0x01, 0x53, 0x54, 0x41, 0x54,
|
||||||
|
0x94, 0x00, 0x00, 0x00, 0x0B, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x02, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
|
0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||||
|
};
|
|
@ -0,0 +1,55 @@
|
||||||
|
//
|
||||||
|
// Generated by Microsoft (R) HLSL Shader Compiler 10.1
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
// Input signature:
|
||||||
|
//
|
||||||
|
// Name Index Mask Register SysValue Format Used
|
||||||
|
// -------------------- ----- ------ -------- -------- ------- ------
|
||||||
|
// TEXCOORD 0 xyzw 0 NONE float
|
||||||
|
// TEXCOORD 1 xyzw 1 NONE float
|
||||||
|
// TEXCOORD 2 xyzw 2 NONE float
|
||||||
|
// TEXCOORD 3 xyzw 3 NONE float
|
||||||
|
// TEXCOORD 4 xyzw 4 NONE float
|
||||||
|
// TEXCOORD 5 xyzw 5 NONE float
|
||||||
|
// TEXCOORD 6 xyzw 6 NONE float
|
||||||
|
// TEXCOORD 7 xyzw 7 NONE float
|
||||||
|
// TEXCOORD 8 xyzw 8 NONE float
|
||||||
|
// TEXCOORD 9 xyzw 9 NONE float
|
||||||
|
// TEXCOORD 10 xyzw 10 NONE float
|
||||||
|
// TEXCOORD 11 xyzw 11 NONE float
|
||||||
|
// TEXCOORD 12 xyzw 12 NONE float
|
||||||
|
// TEXCOORD 13 xyzw 13 NONE float
|
||||||
|
// TEXCOORD 14 xyzw 14 NONE float
|
||||||
|
// TEXCOORD 15 xyzw 15 NONE float
|
||||||
|
// TEXCOORD 16 xyz 16 NONE float
|
||||||
|
// TEXCOORD 17 xy 17 NONE float
|
||||||
|
// SV_Position 0 xyzw 18 POS float z
|
||||||
|
//
|
||||||
|
//
|
||||||
|
// Output signature:
|
||||||
|
//
|
||||||
|
// Name Index Mask Register SysValue Format Used
|
||||||
|
// -------------------- ----- ------ -------- -------- ------- ------
|
||||||
|
// SV_DepthLessEqual 0 N/A oDepthLE DEPTHLE float YES
|
||||||
|
//
|
||||||
|
// Pixel Shader runs at sample frequency
|
||||||
|
//
|
||||||
|
ps_5_1
|
||||||
|
dcl_globalFlags refactoringAllowed
|
||||||
|
dcl_input_ps_siv linear noperspective sample v18.z, position
|
||||||
|
dcl_output oDepthLE
|
||||||
|
dcl_temps 1
|
||||||
|
mov_sat [precise(x)] r0.x, v18.z
|
||||||
|
uge [precise(y)] r0.y, r0.x, l(0x2e800000)
|
||||||
|
if_nz r0.y
|
||||||
|
ubfe [precise(y)] r0.y, l(8), l(23), r0.x
|
||||||
|
iadd [precise(y)] r0.y, -r0.y, l(116)
|
||||||
|
imax [precise(y)] r0.y, r0.y, l(3)
|
||||||
|
bfi [precise(x)] oDepthLE, r0.y, l(0), l(0), r0.x
|
||||||
|
else
|
||||||
|
mov [precise(x)] oDepthLE, l(0)
|
||||||
|
endif
|
||||||
|
ret
|
||||||
|
// Approximately 11 instruction slots used
|
|
@ -7,22 +7,14 @@ void main(uint3 xe_group_id : SV_GroupID,
|
||||||
uint3 xe_thread_id : SV_DispatchThreadID) {
|
uint3 xe_thread_id : SV_DispatchThreadID) {
|
||||||
uint2 tile_sample_index = xe_group_thread_id.xy;
|
uint2 tile_sample_index = xe_group_thread_id.xy;
|
||||||
tile_sample_index.x *= 4u;
|
tile_sample_index.x *= 4u;
|
||||||
uint edram_offset = XeEdramOffset32bpp(xe_group_id.xy, tile_sample_index);
|
uint4 samples = xe_edram_load_store_source.Load4(
|
||||||
uint4 depth24_stencil = xe_edram_load_store_source.Load4(edram_offset);
|
XeEdramOffset32bpp(xe_group_id.xy, tile_sample_index));
|
||||||
uint4 depth24 = depth24_stencil >> 8u;
|
// Depth (exact conversion ensured during drawing).
|
||||||
uint4 depth32 = xe_edram_load_store_source.Load4(10485760u + edram_offset);
|
|
||||||
// Depth. If the stored 32-bit depth converted to 24-bit is the same as the
|
|
||||||
// stored 24-bit depth, load the 32-bit value because it has more precision
|
|
||||||
// (and multipass rendering is possible), if it's not, convert the 24-bit
|
|
||||||
// depth because it was overwritten by aliasing.
|
|
||||||
uint4 depth24to32 = XeFloat20e4To32(depth24);
|
|
||||||
uint4 depth = depth24to32 + (depth32 - depth24to32) *
|
|
||||||
uint4(XeFloat32To20e4(depth32) == depth24);
|
|
||||||
uint rt_offset = xe_thread_id.y * xe_edram_rt_color_depth_pitch +
|
uint rt_offset = xe_thread_id.y * xe_edram_rt_color_depth_pitch +
|
||||||
xe_thread_id.x * 16u + xe_edram_rt_color_depth_offset;
|
xe_thread_id.x * 16u + xe_edram_rt_color_depth_offset;
|
||||||
xe_edram_load_store_dest.Store4(rt_offset, depth);
|
xe_edram_load_store_dest.Store4(rt_offset, XeFloat20e4To32(samples >> 8u));
|
||||||
// Stencil.
|
// Stencil.
|
||||||
uint4 stencil = (depth24_stencil & 0xFFu) << uint4(0u, 8u, 16u, 24u);
|
uint4 stencil = (samples & 0xFFu) << uint4(0u, 8u, 16u, 24u);
|
||||||
stencil.xy |= stencil.zw;
|
stencil.xy |= stencil.zw;
|
||||||
stencil.x |= stencil.y;
|
stencil.x |= stencil.y;
|
||||||
rt_offset = xe_thread_id.y * xe_edram_rt_stencil_pitch + xe_thread_id.x * 4u +
|
rt_offset = xe_thread_id.y * xe_edram_rt_stencil_pitch + xe_thread_id.x * 4u +
|
||||||
|
|
|
@ -0,0 +1,31 @@
|
||||||
|
#include "edram_load_store.hlsli"
|
||||||
|
#include "pixel_formats.hlsli"
|
||||||
|
|
||||||
|
[numthreads(20, 16, 1)]
|
||||||
|
void main(uint3 xe_group_id : SV_GroupID,
|
||||||
|
uint3 xe_group_thread_id : SV_GroupThreadID,
|
||||||
|
uint3 xe_thread_id : SV_DispatchThreadID) {
|
||||||
|
uint2 tile_sample_index = xe_group_thread_id.xy;
|
||||||
|
tile_sample_index.x *= 4u;
|
||||||
|
uint edram_offset = XeEdramOffset32bpp(xe_group_id.xy, tile_sample_index);
|
||||||
|
uint4 depth24_stencil = xe_edram_load_store_source.Load4(edram_offset);
|
||||||
|
uint4 depth24 = depth24_stencil >> 8u;
|
||||||
|
uint4 depth32 = xe_edram_load_store_source.Load4(10485760u + edram_offset);
|
||||||
|
// Depth. If the stored 32-bit depth converted to 24-bit is the same as the
|
||||||
|
// stored 24-bit depth, load the 32-bit value because it has more precision
|
||||||
|
// (and multipass rendering is possible), if it's not, convert the 24-bit
|
||||||
|
// depth because it was overwritten by aliasing.
|
||||||
|
uint4 depth24to32 = XeFloat20e4To32(depth24);
|
||||||
|
uint4 depth = depth24to32 + (depth32 - depth24to32) *
|
||||||
|
uint4(XeFloat32To20e4(depth32) == depth24);
|
||||||
|
uint rt_offset = xe_thread_id.y * xe_edram_rt_color_depth_pitch +
|
||||||
|
xe_thread_id.x * 16u + xe_edram_rt_color_depth_offset;
|
||||||
|
xe_edram_load_store_dest.Store4(rt_offset, depth);
|
||||||
|
// Stencil.
|
||||||
|
uint4 stencil = (depth24_stencil & 0xFFu) << uint4(0u, 8u, 16u, 24u);
|
||||||
|
stencil.xy |= stencil.zw;
|
||||||
|
stencil.x |= stencil.y;
|
||||||
|
rt_offset = xe_thread_id.y * xe_edram_rt_stencil_pitch + xe_thread_id.x * 4u +
|
||||||
|
xe_edram_rt_stencil_offset;
|
||||||
|
xe_edram_load_store_dest.Store(rt_offset, stencil.x);
|
||||||
|
}
|
|
@ -5,21 +5,18 @@
|
||||||
void main(uint3 xe_group_id : SV_GroupID,
|
void main(uint3 xe_group_id : SV_GroupID,
|
||||||
uint3 xe_group_thread_id : SV_GroupThreadID,
|
uint3 xe_group_thread_id : SV_GroupThreadID,
|
||||||
uint3 xe_thread_id : SV_DispatchThreadID) {
|
uint3 xe_thread_id : SV_DispatchThreadID) {
|
||||||
// Depth.
|
// Depth (exact conversion ensured during drawing).
|
||||||
uint rt_offset = xe_thread_id.y * xe_edram_rt_color_depth_pitch +
|
uint rt_offset = xe_thread_id.y * xe_edram_rt_color_depth_pitch +
|
||||||
xe_thread_id.x * 16u + xe_edram_rt_color_depth_offset;
|
xe_thread_id.x * 16u + xe_edram_rt_color_depth_offset;
|
||||||
uint4 depth32 = xe_edram_load_store_source.Load4(rt_offset);
|
uint4 samples =
|
||||||
uint4 depth24_stencil = XeFloat32To20e4(depth32) << 8u;
|
XeFloat32To20e4(xe_edram_load_store_source.Load4(rt_offset)) << 8u;
|
||||||
// Stencil.
|
// Stencil.
|
||||||
rt_offset = xe_thread_id.y * xe_edram_rt_stencil_pitch + xe_thread_id.x * 4u +
|
rt_offset = xe_thread_id.y * xe_edram_rt_stencil_pitch + xe_thread_id.x * 4u +
|
||||||
xe_edram_rt_stencil_offset;
|
xe_edram_rt_stencil_offset;
|
||||||
depth24_stencil |= (xe_edram_load_store_source.Load(rt_offset).xxxx >>
|
samples |= (xe_edram_load_store_source.Load(rt_offset).xxxx >>
|
||||||
uint4(0u, 8u, 16u, 24u)) & 0xFFu;
|
uint4(0u, 8u, 16u, 24u)) & 0xFFu;
|
||||||
uint2 tile_sample_index = xe_group_thread_id.xy;
|
uint2 tile_sample_index = xe_group_thread_id.xy;
|
||||||
tile_sample_index.x *= 4u;
|
tile_sample_index.x *= 4u;
|
||||||
uint edram_offset = XeEdramOffset32bpp(xe_group_id.xy, tile_sample_index);
|
xe_edram_load_store_dest.Store4(
|
||||||
// Store 24-bit depth for aliasing and checking if 32-bit depth is up to date.
|
XeEdramOffset32bpp(xe_group_id.xy, tile_sample_index), samples);
|
||||||
xe_edram_load_store_dest.Store4(edram_offset, depth24_stencil);
|
|
||||||
// Store 32-bit depth so precision isn't lost when doing multipass rendering.
|
|
||||||
xe_edram_load_store_dest.Store4(10485760u + edram_offset, depth32);
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -0,0 +1,25 @@
|
||||||
|
#include "edram_load_store.hlsli"
|
||||||
|
#include "pixel_formats.hlsli"
|
||||||
|
|
||||||
|
[numthreads(20, 16, 1)]
|
||||||
|
void main(uint3 xe_group_id : SV_GroupID,
|
||||||
|
uint3 xe_group_thread_id : SV_GroupThreadID,
|
||||||
|
uint3 xe_thread_id : SV_DispatchThreadID) {
|
||||||
|
// Depth.
|
||||||
|
uint rt_offset = xe_thread_id.y * xe_edram_rt_color_depth_pitch +
|
||||||
|
xe_thread_id.x * 16u + xe_edram_rt_color_depth_offset;
|
||||||
|
uint4 depth32 = xe_edram_load_store_source.Load4(rt_offset);
|
||||||
|
uint4 depth24_stencil = XeFloat32To20e4(depth32) << 8u;
|
||||||
|
// Stencil.
|
||||||
|
rt_offset = xe_thread_id.y * xe_edram_rt_stencil_pitch + xe_thread_id.x * 4u +
|
||||||
|
xe_edram_rt_stencil_offset;
|
||||||
|
depth24_stencil |= (xe_edram_load_store_source.Load(rt_offset).xxxx >>
|
||||||
|
uint4(0u, 8u, 16u, 24u)) & 0xFFu;
|
||||||
|
uint2 tile_sample_index = xe_group_thread_id.xy;
|
||||||
|
tile_sample_index.x *= 4u;
|
||||||
|
uint edram_offset = XeEdramOffset32bpp(xe_group_id.xy, tile_sample_index);
|
||||||
|
// Store 24-bit depth for aliasing and checking if 32-bit depth is up to date.
|
||||||
|
xe_edram_load_store_dest.Store4(edram_offset, depth24_stencil);
|
||||||
|
// Store 32-bit depth so precision isn't lost when doing multipass rendering.
|
||||||
|
xe_edram_load_store_dest.Store4(10485760u + edram_offset, depth32);
|
||||||
|
}
|
|
@ -7,8 +7,7 @@ void main(uint3 xe_group_id : SV_GroupID,
|
||||||
// Depth.
|
// Depth.
|
||||||
uint rt_offset = xe_thread_id.y * xe_edram_rt_color_depth_pitch +
|
uint rt_offset = xe_thread_id.y * xe_edram_rt_color_depth_pitch +
|
||||||
xe_thread_id.x * 16u + xe_edram_rt_color_depth_offset;
|
xe_thread_id.x * 16u + xe_edram_rt_color_depth_offset;
|
||||||
uint4 samples =
|
uint4 samples = xe_edram_load_store_source.Load4(rt_offset) << 8u;
|
||||||
(xe_edram_load_store_source.Load4(rt_offset) & 0xFFFFFFu) << 8u;
|
|
||||||
// Stencil.
|
// Stencil.
|
||||||
rt_offset = xe_thread_id.y * xe_edram_rt_stencil_pitch + xe_thread_id.x * 4u +
|
rt_offset = xe_thread_id.y * xe_edram_rt_stencil_pitch + xe_thread_id.x * 4u +
|
||||||
xe_edram_rt_stencil_offset;
|
xe_edram_rt_stencil_offset;
|
||||||
|
|
|
@ -0,0 +1,13 @@
|
||||||
|
#include "pixel_formats.hlsli"
|
||||||
|
#include "xenos_draw.hlsli"
|
||||||
|
|
||||||
|
struct XePSInput {
|
||||||
|
XeVertexPrePS pre_ps;
|
||||||
|
sample float4 position : SV_Position;
|
||||||
|
};
|
||||||
|
|
||||||
|
precise float main(XePSInput xe_input) : SV_Depth {
|
||||||
|
// Input Z may be outside the viewport range (it's clamped after the shader).
|
||||||
|
return asfloat(
|
||||||
|
XeFloat20e4To32(XeFloat32To20e4(asuint(saturate(xe_input.position.z)))));
|
||||||
|
}
|
|
@ -0,0 +1,38 @@
|
||||||
|
#include "pixel_formats.hlsli"
|
||||||
|
#include "xenos_draw.hlsli"
|
||||||
|
|
||||||
|
struct XePSInput {
|
||||||
|
XeVertexPrePS pre_ps;
|
||||||
|
sample float4 position : SV_Position;
|
||||||
|
};
|
||||||
|
|
||||||
|
precise float main(XePSInput xe_input) : SV_DepthLessEqual {
|
||||||
|
// Simplified conversion, always less than or equal to the original value -
|
||||||
|
// just drop the lower bits.
|
||||||
|
// The float32 exponent bias is 127.
|
||||||
|
// After saturating, the exponent range is -127...0.
|
||||||
|
// The smallest normalized 20e4 exponent is -14 - should drop 3 mantissa bits
|
||||||
|
// at -14 or above.
|
||||||
|
// The smallest denormalized 20e4 number is -34 - should drop 23 mantissa bits
|
||||||
|
// at -34.
|
||||||
|
// Anything smaller than 2^-34 becomes 0.
|
||||||
|
// Input Z may be outside the viewport range (it's clamped after the shader).
|
||||||
|
precise uint depth = asuint(saturate(xe_input.position.z));
|
||||||
|
// Check if the number is representable as a float24 after truncation - the
|
||||||
|
// exponent is at least -34.
|
||||||
|
if (depth >= 0x2E800000u) {
|
||||||
|
// Extract the biased float32 exponent:
|
||||||
|
// 113+ at exponent -14+.
|
||||||
|
// 93 at exponent -34.
|
||||||
|
uint exponent = (depth >> 23u) & 0xFFu;
|
||||||
|
// Convert exponent to the shift amount.
|
||||||
|
// 116 - 113 = 3.
|
||||||
|
// 116 - 93 = 23.
|
||||||
|
uint shift = asuint(max(116 - asint(exponent), 3));
|
||||||
|
depth = depth >> shift << shift;
|
||||||
|
} else {
|
||||||
|
// The number is not representable as float24 after truncation - zero.
|
||||||
|
depth = 0u;
|
||||||
|
}
|
||||||
|
return asfloat(depth);
|
||||||
|
}
|
|
@ -495,6 +495,16 @@ void XeR11G11B10SNormToRGBA16(uint4 packed_texels, out uint4 out_01,
|
||||||
// 6e4 has a different exponent bias allowing [0,512) values, 20e4 allows [0,2).
|
// 6e4 has a different exponent bias allowing [0,512) values, 20e4 allows [0,2).
|
||||||
// We also can't clamp the stored value to 1 as load->store->load must be exact.
|
// We also can't clamp the stored value to 1 as load->store->load must be exact.
|
||||||
|
|
||||||
|
uint XeFloat32To20e4(uint f32u32) {
|
||||||
|
// Keep only positive (high bit set means negative for both float and int) and
|
||||||
|
// saturate to the maximum representable value near 2 (also dropping NaNs).
|
||||||
|
f32u32 = min((f32u32 <= 0x7FFFFFFFu) ? f32u32 : 0u, 0x3FFFFFF8u);
|
||||||
|
uint denormalized =
|
||||||
|
((f32u32 & 0x7FFFFFu) | 0x800000u) >> min(113u - (f32u32 >> 23u), 24u);
|
||||||
|
uint f24u32 = (f32u32 < 0x38800000u) ? denormalized : (f32u32 + 0xC8000000u);
|
||||||
|
return ((f24u32 + 3u + ((f24u32 >> 3u) & 1u)) >> 3u) & 0xFFFFFFu;
|
||||||
|
}
|
||||||
|
|
||||||
uint4 XeFloat32To20e4(uint4 f32u32) {
|
uint4 XeFloat32To20e4(uint4 f32u32) {
|
||||||
// Keep only positive (high bit set means negative for both float and int) and
|
// Keep only positive (high bit set means negative for both float and int) and
|
||||||
// saturate to the maximum representable value near 2 (also dropping NaNs).
|
// saturate to the maximum representable value near 2 (also dropping NaNs).
|
||||||
|
@ -505,6 +515,21 @@ uint4 XeFloat32To20e4(uint4 f32u32) {
|
||||||
return ((f24u32 + 3u + ((f24u32 >> 3u) & 1u)) >> 3u) & 0xFFFFFFu;
|
return ((f24u32 + 3u + ((f24u32 >> 3u) & 1u)) >> 3u) & 0xFFFFFFu;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
uint XeFloat20e4To32(uint f24u32) {
|
||||||
|
uint mantissa = f24u32 & 0xFFFFFu;
|
||||||
|
uint exponent = f24u32 >> 20u;
|
||||||
|
// Normalize the values for the denormalized components.
|
||||||
|
// Exponent = 1;
|
||||||
|
// do { Exponent--; Mantissa <<= 1; } while ((Mantissa & 0x100000) == 0);
|
||||||
|
bool is_denormalized = exponent == 0u;
|
||||||
|
uint mantissa_lzcnt = 20u - firstbithigh(mantissa);
|
||||||
|
exponent = is_denormalized ? (1u - mantissa_lzcnt) : exponent;
|
||||||
|
mantissa =
|
||||||
|
is_denormalized ? ((mantissa << mantissa_lzcnt) & 0xFFFFFu) : mantissa;
|
||||||
|
// Combine into 32-bit float bits and clear zeros.
|
||||||
|
return (f24u32 != 0u) ? (((exponent + 112u) << 23u) | (mantissa << 3u)) : 0u;
|
||||||
|
}
|
||||||
|
|
||||||
uint4 XeFloat20e4To32(uint4 f24u32) {
|
uint4 XeFloat20e4To32(uint4 f24u32) {
|
||||||
uint4 mantissa = f24u32 & 0xFFFFFu;
|
uint4 mantissa = f24u32 & 0xFFFFFu;
|
||||||
uint4 exponent = f24u32 >> 20u;
|
uint4 exponent = f24u32 >> 20u;
|
||||||
|
|
|
@ -10,9 +10,9 @@ void main(point XeVertexPreGS xe_in[1],
|
||||||
}
|
}
|
||||||
|
|
||||||
XeVertexPostGS xe_out;
|
XeVertexPostGS xe_out;
|
||||||
xe_out.interpolators = xe_in[0].post_gs.interpolators;
|
xe_out.pre_ps.interpolators = xe_in[0].post_gs.pre_ps.interpolators;
|
||||||
xe_out.point_params.z = xe_in[0].post_gs.point_params.z;
|
xe_out.pre_ps.point_params.z = xe_in[0].post_gs.pre_ps.point_params.z;
|
||||||
xe_out.clip_space_zw = xe_in[0].post_gs.clip_space_zw;
|
xe_out.pre_ps.clip_space_zw = xe_in[0].post_gs.pre_ps.clip_space_zw;
|
||||||
xe_out.position.zw = xe_in[0].post_gs.position.zw;
|
xe_out.position.zw = xe_in[0].post_gs.position.zw;
|
||||||
xe_out.clip_distance_0123 = xe_in[0].post_gs.clip_distance_0123;
|
xe_out.clip_distance_0123 = xe_in[0].post_gs.clip_distance_0123;
|
||||||
xe_out.clip_distance_45 = xe_in[0].post_gs.clip_distance_45;
|
xe_out.clip_distance_45 = xe_in[0].post_gs.clip_distance_45;
|
||||||
|
@ -20,26 +20,27 @@ void main(point XeVertexPreGS xe_in[1],
|
||||||
// Shader header writes -1.0f to point_size by default, so any positive value
|
// Shader header writes -1.0f to point_size by default, so any positive value
|
||||||
// means that it was overwritten by the translated vertex shader.
|
// means that it was overwritten by the translated vertex shader.
|
||||||
float2 point_size =
|
float2 point_size =
|
||||||
(xe_in[0].post_gs.point_params.z > 0.0f ? xe_in[0].post_gs.point_params.zz
|
xe_in[0].post_gs.pre_ps.point_params.z > 0.0f
|
||||||
: xe_point_size);
|
? xe_in[0].post_gs.pre_ps.point_params.zz
|
||||||
|
: xe_point_size;
|
||||||
point_size =
|
point_size =
|
||||||
clamp(point_size, xe_point_size_min_max.xx, xe_point_size_min_max.yy) *
|
clamp(point_size, xe_point_size_min_max.xx, xe_point_size_min_max.yy) *
|
||||||
xe_point_screen_to_ndc * xe_in[0].post_gs.position.w;
|
xe_point_screen_to_ndc * xe_in[0].post_gs.position.w;
|
||||||
|
|
||||||
xe_out.point_params.xy = float2(0.0, 0.0);
|
xe_out.pre_ps.point_params.xy = float2(0.0, 0.0);
|
||||||
// TODO(Triang3l): On Vulkan, sign of Y needs to inverted because of
|
// TODO(Triang3l): On Vulkan, sign of Y needs to inverted because of
|
||||||
// upper-left origin.
|
// upper-left origin.
|
||||||
// TODO(Triang3l): Investigate the true signs of point sprites.
|
// TODO(Triang3l): Investigate the true signs of point sprites.
|
||||||
xe_out.position.xy =
|
xe_out.position.xy =
|
||||||
xe_in[0].post_gs.position.xy + float2(-point_size.x, point_size.y);
|
xe_in[0].post_gs.position.xy + float2(-point_size.x, point_size.y);
|
||||||
xe_stream.Append(xe_out);
|
xe_stream.Append(xe_out);
|
||||||
xe_out.point_params.xy = float2(0.0, 1.0);
|
xe_out.pre_ps.point_params.xy = float2(0.0, 1.0);
|
||||||
xe_out.position.xy = xe_in[0].post_gs.position.xy - point_size;
|
xe_out.position.xy = xe_in[0].post_gs.position.xy - point_size;
|
||||||
xe_stream.Append(xe_out);
|
xe_stream.Append(xe_out);
|
||||||
xe_out.point_params.xy = float2(1.0, 0.0);
|
xe_out.pre_ps.point_params.xy = float2(1.0, 0.0);
|
||||||
xe_out.position.xy = xe_in[0].post_gs.position.xy + point_size;
|
xe_out.position.xy = xe_in[0].post_gs.position.xy + point_size;
|
||||||
xe_stream.Append(xe_out);
|
xe_stream.Append(xe_out);
|
||||||
xe_out.point_params.xy = float2(1.0, 1.0);
|
xe_out.pre_ps.point_params.xy = float2(1.0, 1.0);
|
||||||
xe_out.position.xy =
|
xe_out.position.xy =
|
||||||
xe_in[0].post_gs.position.xy + float2(point_size.x, -point_size.y);
|
xe_in[0].post_gs.position.xy + float2(point_size.x, -point_size.y);
|
||||||
xe_stream.Append(xe_out);
|
xe_stream.Append(xe_out);
|
||||||
|
|
|
@ -80,16 +80,19 @@ void main(triangle XeVertexPreGS xe_in[3],
|
||||||
v3_signs = float3(1.0f, 1.0f, -1.0f);
|
v3_signs = float3(1.0f, 1.0f, -1.0f);
|
||||||
}
|
}
|
||||||
[unroll] for (int i = 0; i < 16; ++i) {
|
[unroll] for (int i = 0; i < 16; ++i) {
|
||||||
xe_out.interpolators[i] = v3_signs.x * xe_in[0].post_gs.interpolators[i] +
|
xe_out.pre_ps.interpolators[i] =
|
||||||
v3_signs.y * xe_in[1].post_gs.interpolators[i] +
|
v3_signs.x * xe_in[0].post_gs.pre_ps.interpolators[i] +
|
||||||
v3_signs.z * xe_in[2].post_gs.interpolators[i];
|
v3_signs.y * xe_in[1].post_gs.pre_ps.interpolators[i] +
|
||||||
|
v3_signs.z * xe_in[2].post_gs.pre_ps.interpolators[i];
|
||||||
}
|
}
|
||||||
xe_out.point_params = v3_signs.x * xe_in[0].post_gs.point_params +
|
xe_out.pre_ps.point_params =
|
||||||
v3_signs.y * xe_in[1].post_gs.point_params +
|
v3_signs.x * xe_in[0].post_gs.pre_ps.point_params +
|
||||||
v3_signs.z * xe_in[2].post_gs.point_params;
|
v3_signs.y * xe_in[1].post_gs.pre_ps.point_params +
|
||||||
xe_out.clip_space_zw = v3_signs.x * xe_in[0].post_gs.clip_space_zw +
|
v3_signs.z * xe_in[2].post_gs.pre_ps.point_params;
|
||||||
v3_signs.y * xe_in[1].post_gs.clip_space_zw +
|
xe_out.pre_ps.clip_space_zw =
|
||||||
v3_signs.z * xe_in[2].post_gs.clip_space_zw;
|
v3_signs.x * xe_in[0].post_gs.pre_ps.clip_space_zw +
|
||||||
|
v3_signs.y * xe_in[1].post_gs.pre_ps.clip_space_zw +
|
||||||
|
v3_signs.z * xe_in[2].post_gs.pre_ps.clip_space_zw;
|
||||||
xe_out.position = v3_signs.x * xe_in[0].post_gs.position +
|
xe_out.position = v3_signs.x * xe_in[0].post_gs.position +
|
||||||
v3_signs.y * xe_in[1].post_gs.position +
|
v3_signs.y * xe_in[1].post_gs.position +
|
||||||
v3_signs.z * xe_in[2].post_gs.position;
|
v3_signs.z * xe_in[2].post_gs.position;
|
||||||
|
|
|
@ -63,10 +63,14 @@ struct XeHSControlPointOutput {
|
||||||
float index : XEVERTEXID;
|
float index : XEVERTEXID;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct XeVertexPostGS {
|
struct XeVertexPrePS {
|
||||||
float4 interpolators[16] : TEXCOORD0;
|
float4 interpolators[16] : TEXCOORD0;
|
||||||
float3 point_params : TEXCOORD16;
|
float3 point_params : TEXCOORD16;
|
||||||
float2 clip_space_zw : TEXCOORD17;
|
float2 clip_space_zw : TEXCOORD17;
|
||||||
|
};
|
||||||
|
|
||||||
|
struct XeVertexPostGS {
|
||||||
|
XeVertexPrePS pre_ps;
|
||||||
// Precise needed to preserve NaN - guest primitives may be converted to more
|
// Precise needed to preserve NaN - guest primitives may be converted to more
|
||||||
// than 1 triangle, so need to kill them entirely manually in GS if any vertex
|
// than 1 triangle, so need to kill them entirely manually in GS if any vertex
|
||||||
// is NaN.
|
// is NaN.
|
||||||
|
|
|
@ -114,6 +114,7 @@ int32_t FloatToD3D11Fixed16p8(float f32) {
|
||||||
void GetHostViewportInfo(const RegisterFile& regs, float pixel_size_x,
|
void GetHostViewportInfo(const RegisterFile& regs, float pixel_size_x,
|
||||||
float pixel_size_y, bool origin_bottom_left,
|
float pixel_size_y, bool origin_bottom_left,
|
||||||
float x_max, float y_max, bool allow_reverse_z,
|
float x_max, float y_max, bool allow_reverse_z,
|
||||||
|
bool convert_z_to_float24,
|
||||||
ViewportInfo& viewport_info_out) {
|
ViewportInfo& viewport_info_out) {
|
||||||
assert_true(pixel_size_x >= 1.0f);
|
assert_true(pixel_size_x >= 1.0f);
|
||||||
assert_true(pixel_size_y >= 1.0f);
|
assert_true(pixel_size_y >= 1.0f);
|
||||||
|
@ -270,6 +271,17 @@ void GetHostViewportInfo(const RegisterFile& regs, float pixel_size_x,
|
||||||
ndc_scale_z = -ndc_scale_z;
|
ndc_scale_z = -ndc_scale_z;
|
||||||
ndc_offset_z = 1.0f - ndc_offset_z;
|
ndc_offset_z = 1.0f - ndc_offset_z;
|
||||||
}
|
}
|
||||||
|
if (convert_z_to_float24 && regs.Get<reg::RB_DEPTHCONTROL>().z_enable &&
|
||||||
|
regs.Get<reg::RB_DEPTH_INFO>().depth_format ==
|
||||||
|
xenos::DepthRenderTargetFormat::kD24FS8) {
|
||||||
|
// Need to adjust the bounds that the resulting depth values will be clamped
|
||||||
|
// to after the pixel shader. Preferring adding some error to interpolated Z
|
||||||
|
// instead if conversion can't be done exactly, without modifying clipping
|
||||||
|
// bounds by adjusting Z in vertex shaders, as that may cause polygons
|
||||||
|
// placed explicitly at Z = 0 or Z = W to be clipped.
|
||||||
|
viewport_z_min = xenos::Float20e4To32(xenos::Float32To20e4(viewport_z_min));
|
||||||
|
viewport_z_max = xenos::Float20e4To32(xenos::Float32To20e4(viewport_z_max));
|
||||||
|
}
|
||||||
|
|
||||||
viewport_info_out.left = viewport_left;
|
viewport_info_out.left = viewport_left;
|
||||||
viewport_info_out.top = viewport_top;
|
viewport_info_out.top = viewport_top;
|
||||||
|
|
|
@ -53,6 +53,7 @@ struct ViewportInfo {
|
||||||
void GetHostViewportInfo(const RegisterFile& regs, float pixel_size_x,
|
void GetHostViewportInfo(const RegisterFile& regs, float pixel_size_x,
|
||||||
float pixel_size_y, bool origin_bottom_left,
|
float pixel_size_y, bool origin_bottom_left,
|
||||||
float x_max, float y_max, bool allow_reverse_z,
|
float x_max, float y_max, bool allow_reverse_z,
|
||||||
|
bool convert_z_to_float24,
|
||||||
ViewportInfo& viewport_info_out);
|
ViewportInfo& viewport_info_out);
|
||||||
|
|
||||||
struct Scissor {
|
struct Scissor {
|
||||||
|
|
|
@ -0,0 +1,27 @@
|
||||||
|
/**
|
||||||
|
******************************************************************************
|
||||||
|
* Xenia : Xbox 360 Emulator Research Project *
|
||||||
|
******************************************************************************
|
||||||
|
* Copyright 2020 Ben Vanik. All rights reserved. *
|
||||||
|
* Released under the BSD license - see LICENSE in the root for more details. *
|
||||||
|
******************************************************************************
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "xenia/gpu/dxbc_shader.h"
|
||||||
|
|
||||||
|
#include <cstring>
|
||||||
|
|
||||||
|
namespace xe {
|
||||||
|
namespace gpu {
|
||||||
|
|
||||||
|
DxbcShader::DxbcShader(xenos::ShaderType shader_type, uint64_t data_hash,
|
||||||
|
const uint32_t* dword_ptr, uint32_t dword_count)
|
||||||
|
: Shader(shader_type, data_hash, dword_ptr, dword_count) {}
|
||||||
|
|
||||||
|
Shader::Translation* DxbcShader::CreateTranslationInstance(
|
||||||
|
uint32_t modification) {
|
||||||
|
return new DxbcTranslation(*this, modification);
|
||||||
|
}
|
||||||
|
|
||||||
|
} // namespace gpu
|
||||||
|
} // namespace xe
|
|
@ -0,0 +1,83 @@
|
||||||
|
/**
|
||||||
|
******************************************************************************
|
||||||
|
* Xenia : Xbox 360 Emulator Research Project *
|
||||||
|
******************************************************************************
|
||||||
|
* Copyright 2020 Ben Vanik. All rights reserved. *
|
||||||
|
* Released under the BSD license - see LICENSE in the root for more details. *
|
||||||
|
******************************************************************************
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef XENIA_GPU_DXBC_SHADER_H_
|
||||||
|
#define XENIA_GPU_DXBC_SHADER_H_
|
||||||
|
|
||||||
|
#include <vector>
|
||||||
|
|
||||||
|
#include "xenia/gpu/dxbc_shader_translator.h"
|
||||||
|
#include "xenia/gpu/shader.h"
|
||||||
|
#include "xenia/gpu/xenos.h"
|
||||||
|
|
||||||
|
namespace xe {
|
||||||
|
namespace gpu {
|
||||||
|
|
||||||
|
class DxbcShader : public Shader {
|
||||||
|
public:
|
||||||
|
class DxbcTranslation : public Translation {
|
||||||
|
public:
|
||||||
|
DxbcTranslation(DxbcShader& shader, uint32_t modification)
|
||||||
|
: Translation(shader, modification) {}
|
||||||
|
};
|
||||||
|
|
||||||
|
DxbcShader(xenos::ShaderType shader_type, uint64_t data_hash,
|
||||||
|
const uint32_t* dword_ptr, uint32_t dword_count);
|
||||||
|
|
||||||
|
static constexpr uint32_t kMaxTextureBindingIndexBits =
|
||||||
|
DxbcShaderTranslator::kMaxTextureBindingIndexBits;
|
||||||
|
static constexpr uint32_t kMaxTextureBindings =
|
||||||
|
DxbcShaderTranslator::kMaxTextureBindings;
|
||||||
|
struct TextureBinding {
|
||||||
|
uint32_t bindless_descriptor_index;
|
||||||
|
uint32_t fetch_constant;
|
||||||
|
// Stacked and 3D are separate TextureBindings, even for bindless for null
|
||||||
|
// descriptor handling simplicity.
|
||||||
|
xenos::FetchOpDimension dimension;
|
||||||
|
bool is_signed;
|
||||||
|
};
|
||||||
|
// Safe to hash and compare with memcmp for layout hashing.
|
||||||
|
const TextureBinding* GetTextureBindings(uint32_t& count_out) const {
|
||||||
|
count_out = uint32_t(texture_bindings_.size());
|
||||||
|
return texture_bindings_.data();
|
||||||
|
}
|
||||||
|
const uint32_t GetUsedTextureMask() const { return used_texture_mask_; }
|
||||||
|
|
||||||
|
static constexpr uint32_t kMaxSamplerBindingIndexBits =
|
||||||
|
DxbcShaderTranslator::kMaxSamplerBindingIndexBits;
|
||||||
|
static constexpr uint32_t kMaxSamplerBindings =
|
||||||
|
DxbcShaderTranslator::kMaxSamplerBindings;
|
||||||
|
struct SamplerBinding {
|
||||||
|
uint32_t bindless_descriptor_index;
|
||||||
|
uint32_t fetch_constant;
|
||||||
|
xenos::TextureFilter mag_filter;
|
||||||
|
xenos::TextureFilter min_filter;
|
||||||
|
xenos::TextureFilter mip_filter;
|
||||||
|
xenos::AnisoFilter aniso_filter;
|
||||||
|
};
|
||||||
|
const SamplerBinding* GetSamplerBindings(uint32_t& count_out) const {
|
||||||
|
count_out = uint32_t(sampler_bindings_.size());
|
||||||
|
return sampler_bindings_.data();
|
||||||
|
}
|
||||||
|
|
||||||
|
protected:
|
||||||
|
Translation* CreateTranslationInstance(uint32_t modification) override;
|
||||||
|
|
||||||
|
private:
|
||||||
|
friend class DxbcShaderTranslator;
|
||||||
|
|
||||||
|
std::vector<TextureBinding> texture_bindings_;
|
||||||
|
std::vector<SamplerBinding> sampler_bindings_;
|
||||||
|
uint32_t used_texture_mask_ = 0;
|
||||||
|
};
|
||||||
|
|
||||||
|
} // namespace gpu
|
||||||
|
} // namespace xe
|
||||||
|
|
||||||
|
#endif // XENIA_GPU_DXBC_SHADER_H_
|
|
@ -19,6 +19,7 @@
|
||||||
#include "xenia/base/assert.h"
|
#include "xenia/base/assert.h"
|
||||||
#include "xenia/base/cvar.h"
|
#include "xenia/base/cvar.h"
|
||||||
#include "xenia/base/math.h"
|
#include "xenia/base/math.h"
|
||||||
|
#include "xenia/gpu/dxbc_shader.h"
|
||||||
|
|
||||||
DEFINE_bool(dxbc_switch, true,
|
DEFINE_bool(dxbc_switch, true,
|
||||||
"Use switch rather than if for flow control. Turning this off or "
|
"Use switch rather than if for flow control. Turning this off or "
|
||||||
|
@ -76,64 +77,31 @@ DxbcShaderTranslator::DxbcShaderTranslator(uint32_t vendor_id,
|
||||||
}
|
}
|
||||||
DxbcShaderTranslator::~DxbcShaderTranslator() = default;
|
DxbcShaderTranslator::~DxbcShaderTranslator() = default;
|
||||||
|
|
||||||
std::vector<uint8_t> DxbcShaderTranslator::ForceEarlyDepthStencil(
|
|
||||||
const uint8_t* shader) {
|
|
||||||
const uint32_t* old_shader = reinterpret_cast<const uint32_t*>(shader);
|
|
||||||
|
|
||||||
// To return something anyway even if patching fails.
|
|
||||||
std::vector<uint8_t> new_shader;
|
|
||||||
uint32_t shader_size_bytes = old_shader[6];
|
|
||||||
new_shader.resize(shader_size_bytes);
|
|
||||||
std::memcpy(new_shader.data(), shader, shader_size_bytes);
|
|
||||||
|
|
||||||
// Find the SHEX chunk.
|
|
||||||
uint32_t chunk_count = old_shader[7];
|
|
||||||
for (uint32_t i = 0; i < chunk_count; ++i) {
|
|
||||||
uint32_t chunk_offset_bytes = old_shader[8 + i];
|
|
||||||
const uint32_t* chunk = old_shader + chunk_offset_bytes / sizeof(uint32_t);
|
|
||||||
if (chunk[0] != 'XEHS') {
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
// Find dcl_globalFlags and patch it.
|
|
||||||
uint32_t code_size_dwords = chunk[3];
|
|
||||||
chunk += 4;
|
|
||||||
for (uint32_t j = 0; j < code_size_dwords;) {
|
|
||||||
uint32_t opcode_token = chunk[j];
|
|
||||||
uint32_t opcode = DECODE_D3D10_SB_OPCODE_TYPE(opcode_token);
|
|
||||||
if (opcode == D3D10_SB_OPCODE_DCL_GLOBAL_FLAGS) {
|
|
||||||
opcode_token |= D3D11_SB_GLOBAL_FLAG_FORCE_EARLY_DEPTH_STENCIL;
|
|
||||||
std::memcpy(new_shader.data() +
|
|
||||||
(chunk_offset_bytes + (4 + j) * sizeof(uint32_t)),
|
|
||||||
&opcode_token, sizeof(uint32_t));
|
|
||||||
// Recalculate the checksum since the shader was modified.
|
|
||||||
CalculateDXBCChecksum(
|
|
||||||
reinterpret_cast<unsigned char*>(new_shader.data()),
|
|
||||||
shader_size_bytes,
|
|
||||||
reinterpret_cast<unsigned int*>(new_shader.data() +
|
|
||||||
sizeof(uint32_t)));
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
if (opcode == D3D10_SB_OPCODE_CUSTOMDATA) {
|
|
||||||
j += chunk[j + 1];
|
|
||||||
} else {
|
|
||||||
j += DECODE_D3D10_SB_TOKENIZED_INSTRUCTION_LENGTH(opcode_token);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
return std::move(new_shader);
|
|
||||||
}
|
|
||||||
|
|
||||||
std::vector<uint8_t> DxbcShaderTranslator::CreateDepthOnlyPixelShader() {
|
std::vector<uint8_t> DxbcShaderTranslator::CreateDepthOnlyPixelShader() {
|
||||||
Reset();
|
Reset(xenos::ShaderType::kPixel);
|
||||||
is_depth_only_pixel_shader_ = true;
|
is_depth_only_pixel_shader_ = true;
|
||||||
StartTranslation();
|
StartTranslation();
|
||||||
return std::move(CompleteTranslation());
|
return std::move(CompleteTranslation());
|
||||||
}
|
}
|
||||||
|
|
||||||
void DxbcShaderTranslator::Reset() {
|
uint32_t DxbcShaderTranslator::GetDefaultModification(
|
||||||
ShaderTranslator::Reset();
|
xenos::ShaderType shader_type,
|
||||||
|
Shader::HostVertexShaderType host_vertex_shader_type) const {
|
||||||
|
Modification shader_modification;
|
||||||
|
switch (shader_type) {
|
||||||
|
case xenos::ShaderType::kVertex:
|
||||||
|
shader_modification.host_vertex_shader_type = host_vertex_shader_type;
|
||||||
|
break;
|
||||||
|
case xenos::ShaderType::kPixel:
|
||||||
|
shader_modification.depth_stencil_mode =
|
||||||
|
Modification::DepthStencilMode::kNoModifiers;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
return shader_modification.value;
|
||||||
|
}
|
||||||
|
|
||||||
|
void DxbcShaderTranslator::Reset(xenos::ShaderType shader_type) {
|
||||||
|
ShaderTranslator::Reset(shader_type);
|
||||||
|
|
||||||
shader_code_.clear();
|
shader_code_.clear();
|
||||||
|
|
||||||
|
@ -152,7 +120,7 @@ void DxbcShaderTranslator::Reset() {
|
||||||
in_domain_location_used_ = 0;
|
in_domain_location_used_ = 0;
|
||||||
in_primitive_id_used_ = false;
|
in_primitive_id_used_ = false;
|
||||||
in_control_point_index_used_ = false;
|
in_control_point_index_used_ = false;
|
||||||
in_position_xy_used_ = false;
|
in_position_used_ = 0;
|
||||||
in_front_face_used_ = false;
|
in_front_face_used_ = false;
|
||||||
|
|
||||||
system_temp_count_current_ = 0;
|
system_temp_count_current_ = 0;
|
||||||
|
@ -457,7 +425,9 @@ void DxbcShaderTranslator::StartVertexOrDomainShader() {
|
||||||
|
|
||||||
// Remember that x# are only accessible via mov load or store - use a
|
// Remember that x# are only accessible via mov load or store - use a
|
||||||
// temporary variable if need to do any computations!
|
// temporary variable if need to do any computations!
|
||||||
switch (host_vertex_shader_type()) {
|
Shader::HostVertexShaderType host_vertex_shader_type =
|
||||||
|
GetDxbcShaderModification().host_vertex_shader_type;
|
||||||
|
switch (host_vertex_shader_type) {
|
||||||
case Shader::HostVertexShaderType::kVertex:
|
case Shader::HostVertexShaderType::kVertex:
|
||||||
StartVertexShader_LoadVertexIndex();
|
StartVertexShader_LoadVertexIndex();
|
||||||
break;
|
break;
|
||||||
|
@ -618,7 +588,7 @@ void DxbcShaderTranslator::StartVertexOrDomainShader() {
|
||||||
|
|
||||||
default:
|
default:
|
||||||
// TODO(Triang3l): Support line and non-adaptive quad patches.
|
// TODO(Triang3l): Support line and non-adaptive quad patches.
|
||||||
assert_unhandled_case(host_vertex_shader_type());
|
assert_unhandled_case(host_vertex_shader_type);
|
||||||
EmitTranslationError(
|
EmitTranslationError(
|
||||||
"Unsupported host vertex shader type in StartVertexOrDomainShader");
|
"Unsupported host vertex shader type in StartVertexOrDomainShader");
|
||||||
break;
|
break;
|
||||||
|
@ -720,7 +690,7 @@ void DxbcShaderTranslator::StartPixelShader() {
|
||||||
// faceness as X sign bit. Using Z as scratch register now.
|
// faceness as X sign bit. Using Z as scratch register now.
|
||||||
if (edram_rov_used_) {
|
if (edram_rov_used_) {
|
||||||
// Get XY address of the current host pixel as float.
|
// Get XY address of the current host pixel as float.
|
||||||
in_position_xy_used_ = true;
|
in_position_used_ |= 0b0011;
|
||||||
DxbcOpRoundZ(DxbcDest::R(param_gen_temp, 0b0011),
|
DxbcOpRoundZ(DxbcDest::R(param_gen_temp, 0b0011),
|
||||||
DxbcSrc::V(uint32_t(InOutRegister::kPSInPosition)));
|
DxbcSrc::V(uint32_t(InOutRegister::kPSInPosition)));
|
||||||
// Revert resolution scale - after truncating, so if the pixel position
|
// Revert resolution scale - after truncating, so if the pixel position
|
||||||
|
@ -744,7 +714,7 @@ void DxbcShaderTranslator::StartPixelShader() {
|
||||||
} else {
|
} else {
|
||||||
// Get XY address of the current SSAA sample by converting
|
// Get XY address of the current SSAA sample by converting
|
||||||
// SV_Position.xy to an integer.
|
// SV_Position.xy to an integer.
|
||||||
in_position_xy_used_ = true;
|
in_position_used_ |= 0b0011;
|
||||||
DxbcOpFToU(DxbcDest::R(param_gen_temp, 0b0011),
|
DxbcOpFToU(DxbcDest::R(param_gen_temp, 0b0011),
|
||||||
DxbcSrc::V(uint32_t(InOutRegister::kPSInPosition)));
|
DxbcSrc::V(uint32_t(InOutRegister::kPSInPosition)));
|
||||||
// Undo SSAA that is used instead of MSAA - since it's used as a
|
// Undo SSAA that is used instead of MSAA - since it's used as a
|
||||||
|
@ -870,7 +840,7 @@ void DxbcShaderTranslator::StartPixelShader() {
|
||||||
void DxbcShaderTranslator::StartTranslation() {
|
void DxbcShaderTranslator::StartTranslation() {
|
||||||
// Allocate global system temporary registers that may also be used in the
|
// Allocate global system temporary registers that may also be used in the
|
||||||
// epilogue.
|
// epilogue.
|
||||||
if (IsDxbcVertexOrDomainShader()) {
|
if (is_vertex_shader()) {
|
||||||
system_temp_position_ = PushSystemTemp(0b1111);
|
system_temp_position_ = PushSystemTemp(0b1111);
|
||||||
system_temp_point_size_edge_flag_kill_vertex_ = PushSystemTemp(0b0100);
|
system_temp_point_size_edge_flag_kill_vertex_ = PushSystemTemp(0b0100);
|
||||||
// Set the point size to a negative value to tell the geometry shader that
|
// Set the point size to a negative value to tell the geometry shader that
|
||||||
|
@ -879,20 +849,21 @@ void DxbcShaderTranslator::StartTranslation() {
|
||||||
DxbcOpMov(
|
DxbcOpMov(
|
||||||
DxbcDest::R(system_temp_point_size_edge_flag_kill_vertex_, 0b0001),
|
DxbcDest::R(system_temp_point_size_edge_flag_kill_vertex_, 0b0001),
|
||||||
DxbcSrc::LF(-1.0f));
|
DxbcSrc::LF(-1.0f));
|
||||||
} else if (IsDxbcPixelShader()) {
|
} else if (is_pixel_shader()) {
|
||||||
if (edram_rov_used_) {
|
if (edram_rov_used_) {
|
||||||
// Will be initialized unconditionally.
|
// Will be initialized unconditionally.
|
||||||
system_temp_rov_params_ = PushSystemTemp();
|
system_temp_rov_params_ = PushSystemTemp();
|
||||||
if (ROV_IsDepthStencilEarly() || writes_depth()) {
|
}
|
||||||
// If the shader doesn't write to oDepth, each component will be written
|
if (IsDepthStencilSystemTempUsed()) {
|
||||||
// to if depth/stencil is enabled and the respective sample is covered -
|
// If the shader doesn't write to oDepth, and ROV is used, each
|
||||||
// so need to initialize now because the first writes will be
|
// component will be written to if depth/stencil is enabled and the
|
||||||
// conditional. If the shader writes to oDepth, this is oDepth of the
|
// respective sample is covered - so need to initialize now because the
|
||||||
// shader, written by the guest code, so initialize because assumptions
|
// first writes will be conditional.
|
||||||
// can't be made about the integrity of the guest code.
|
// If the shader writes to oDepth, this is oDepth of the shader, written
|
||||||
system_temp_rov_depth_stencil_ =
|
// by the guest code, so initialize because assumptions can't be made
|
||||||
PushSystemTemp(writes_depth() ? 0b0001 : 0b1111);
|
// about the integrity of the guest code.
|
||||||
}
|
system_temp_depth_stencil_ =
|
||||||
|
PushSystemTemp(writes_depth() ? 0b0001 : 0b1111);
|
||||||
}
|
}
|
||||||
for (uint32_t i = 0; i < 4; ++i) {
|
for (uint32_t i = 0; i < 4; ++i) {
|
||||||
if (writes_color_target(i)) {
|
if (writes_color_target(i)) {
|
||||||
|
@ -942,7 +913,7 @@ void DxbcShaderTranslator::StartTranslation() {
|
||||||
|
|
||||||
// Zero general-purpose registers to prevent crashes when the game
|
// Zero general-purpose registers to prevent crashes when the game
|
||||||
// references them after only initializing them conditionally.
|
// references them after only initializing them conditionally.
|
||||||
for (uint32_t i = IsDxbcPixelShader() ? xenos::kMaxInterpolators : 0;
|
for (uint32_t i = is_pixel_shader() ? xenos::kMaxInterpolators : 0;
|
||||||
i < register_count(); ++i) {
|
i < register_count(); ++i) {
|
||||||
DxbcOpMov(uses_register_dynamic_addressing() ? DxbcDest::X(0, i)
|
DxbcOpMov(uses_register_dynamic_addressing() ? DxbcDest::X(0, i)
|
||||||
: DxbcDest::R(i),
|
: DxbcDest::R(i),
|
||||||
|
@ -951,9 +922,9 @@ void DxbcShaderTranslator::StartTranslation() {
|
||||||
}
|
}
|
||||||
|
|
||||||
// Write stage-specific prologue.
|
// Write stage-specific prologue.
|
||||||
if (IsDxbcVertexOrDomainShader()) {
|
if (is_vertex_shader()) {
|
||||||
StartVertexOrDomainShader();
|
StartVertexOrDomainShader();
|
||||||
} else if (IsDxbcPixelShader()) {
|
} else if (is_pixel_shader()) {
|
||||||
StartPixelShader();
|
StartPixelShader();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1168,31 +1139,31 @@ void DxbcShaderTranslator::CompleteShaderCode() {
|
||||||
}
|
}
|
||||||
|
|
||||||
// Write stage-specific epilogue.
|
// Write stage-specific epilogue.
|
||||||
if (IsDxbcVertexOrDomainShader()) {
|
if (is_vertex_shader()) {
|
||||||
CompleteVertexOrDomainShader();
|
CompleteVertexOrDomainShader();
|
||||||
} else if (IsDxbcPixelShader()) {
|
} else if (is_pixel_shader()) {
|
||||||
CompletePixelShader();
|
CompletePixelShader();
|
||||||
}
|
}
|
||||||
|
|
||||||
// Return from `main`.
|
// Return from `main`.
|
||||||
DxbcOpRet();
|
DxbcOpRet();
|
||||||
|
|
||||||
if (IsDxbcVertexOrDomainShader()) {
|
if (is_vertex_shader()) {
|
||||||
// Release system_temp_position_ and
|
// Release system_temp_position_ and
|
||||||
// system_temp_point_size_edge_flag_kill_vertex_.
|
// system_temp_point_size_edge_flag_kill_vertex_.
|
||||||
PopSystemTemp(2);
|
PopSystemTemp(2);
|
||||||
} else if (IsDxbcPixelShader()) {
|
} else if (is_pixel_shader()) {
|
||||||
// Release system_temps_color_.
|
// Release system_temps_color_.
|
||||||
for (int32_t i = 3; i >= 0; --i) {
|
for (int32_t i = 3; i >= 0; --i) {
|
||||||
if (writes_color_target(i)) {
|
if (writes_color_target(i)) {
|
||||||
PopSystemTemp();
|
PopSystemTemp();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
if (IsDepthStencilSystemTempUsed()) {
|
||||||
|
// Release system_temp_depth_stencil_.
|
||||||
|
PopSystemTemp();
|
||||||
|
}
|
||||||
if (edram_rov_used_) {
|
if (edram_rov_used_) {
|
||||||
if (ROV_IsDepthStencilEarly() || writes_depth()) {
|
|
||||||
// Release system_temp_rov_depth_stencil_.
|
|
||||||
PopSystemTemp();
|
|
||||||
}
|
|
||||||
// Release system_temp_rov_params_.
|
// Release system_temp_rov_params_.
|
||||||
PopSystemTemp();
|
PopSystemTemp();
|
||||||
}
|
}
|
||||||
|
@ -1303,6 +1274,44 @@ std::vector<uint8_t> DxbcShaderTranslator::CompleteTranslation() {
|
||||||
return shader_object_bytes;
|
return shader_object_bytes;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void DxbcShaderTranslator::PostTranslation(
|
||||||
|
Shader::Translation& translation, bool setup_shader_post_translation_info) {
|
||||||
|
if (setup_shader_post_translation_info) {
|
||||||
|
DxbcShader* dxbc_shader = dynamic_cast<DxbcShader*>(&translation.shader());
|
||||||
|
if (dxbc_shader) {
|
||||||
|
dxbc_shader->texture_bindings_.clear();
|
||||||
|
dxbc_shader->texture_bindings_.reserve(texture_bindings_.size());
|
||||||
|
dxbc_shader->used_texture_mask_ = 0;
|
||||||
|
for (const TextureBinding& translator_binding : texture_bindings_) {
|
||||||
|
DxbcShader::TextureBinding& shader_binding =
|
||||||
|
dxbc_shader->texture_bindings_.emplace_back();
|
||||||
|
// For a stable hash.
|
||||||
|
std::memset(&shader_binding, 0, sizeof(shader_binding));
|
||||||
|
shader_binding.bindless_descriptor_index =
|
||||||
|
translator_binding.bindless_descriptor_index;
|
||||||
|
shader_binding.fetch_constant = translator_binding.fetch_constant;
|
||||||
|
shader_binding.dimension = translator_binding.dimension;
|
||||||
|
shader_binding.is_signed = translator_binding.is_signed;
|
||||||
|
dxbc_shader->used_texture_mask_ |= 1u
|
||||||
|
<< translator_binding.fetch_constant;
|
||||||
|
}
|
||||||
|
dxbc_shader->sampler_bindings_.clear();
|
||||||
|
dxbc_shader->sampler_bindings_.reserve(sampler_bindings_.size());
|
||||||
|
for (const SamplerBinding& translator_binding : sampler_bindings_) {
|
||||||
|
DxbcShader::SamplerBinding& shader_binding =
|
||||||
|
dxbc_shader->sampler_bindings_.emplace_back();
|
||||||
|
shader_binding.bindless_descriptor_index =
|
||||||
|
translator_binding.bindless_descriptor_index;
|
||||||
|
shader_binding.fetch_constant = translator_binding.fetch_constant;
|
||||||
|
shader_binding.mag_filter = translator_binding.mag_filter;
|
||||||
|
shader_binding.min_filter = translator_binding.min_filter;
|
||||||
|
shader_binding.mip_filter = translator_binding.mip_filter;
|
||||||
|
shader_binding.aniso_filter = translator_binding.aniso_filter;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void DxbcShaderTranslator::EmitInstructionDisassembly() {
|
void DxbcShaderTranslator::EmitInstructionDisassembly() {
|
||||||
if (!emit_source_map_) {
|
if (!emit_source_map_) {
|
||||||
return;
|
return;
|
||||||
|
@ -1527,19 +1536,20 @@ void DxbcShaderTranslator::StoreResult(const InstructionResult& result,
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case InstructionStorageTarget::kDepth:
|
case InstructionStorageTarget::kDepth:
|
||||||
// Writes X to scalar oDepth or to X of system_temp_rov_depth_stencil_, no
|
// Writes X to scalar oDepth or to X of system_temp_depth_stencil_, no
|
||||||
// additional swizzling needed.
|
// additional swizzling needed.
|
||||||
assert_true(used_write_mask == 0b0001);
|
assert_true(used_write_mask == 0b0001);
|
||||||
assert_true(writes_depth());
|
assert_true(writes_depth());
|
||||||
if (edram_rov_used_) {
|
if (IsDepthStencilSystemTempUsed()) {
|
||||||
dest = DxbcDest::R(system_temp_rov_depth_stencil_);
|
dest = DxbcDest::R(system_temp_depth_stencil_);
|
||||||
} else {
|
} else {
|
||||||
dest = DxbcDest::ODepth();
|
dest = DxbcDest::ODepth();
|
||||||
}
|
}
|
||||||
// Depth outside [0, 1] is not safe for use with the ROV code. Though 20e4
|
// Depth outside [0, 1] is not safe for use with the ROV code and with
|
||||||
// float depth can store values below 2, it's a very unusual case.
|
// 20e4-as-32 conversion. Though 20e4 float depth can store values between
|
||||||
// Direct3D 10+ SV_Depth, however, can accept any values, including
|
// 1 and 2, it's a very unusual case. Direct3D 10+ SV_Depth, however, can
|
||||||
// specials, when the depth buffer is floating-point.
|
// accept any values, including specials, when the depth buffer is
|
||||||
|
// floating-point; but depth is clamped to the viewport bounds anyway.
|
||||||
is_clamped = true;
|
is_clamped = true;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
@ -2094,7 +2104,7 @@ void DxbcShaderTranslator::WriteResourceDefinitions() {
|
||||||
// ds_5_1
|
// ds_5_1
|
||||||
shader_object_.push_back(0x44530501u);
|
shader_object_.push_back(0x44530501u);
|
||||||
} else {
|
} else {
|
||||||
assert_true(IsDxbcPixelShader());
|
assert_true(is_pixel_shader());
|
||||||
// ps_5_1
|
// ps_5_1
|
||||||
shader_object_.push_back(0xFFFF0501u);
|
shader_object_.push_back(0xFFFF0501u);
|
||||||
}
|
}
|
||||||
|
@ -2765,7 +2775,7 @@ void DxbcShaderTranslator::WriteInputSignature() {
|
||||||
control_point_index.semantic_name = semantic_offset;
|
control_point_index.semantic_name = semantic_offset;
|
||||||
}
|
}
|
||||||
semantic_offset += AppendString(shader_object_, "XEVERTEXID");
|
semantic_offset += AppendString(shader_object_, "XEVERTEXID");
|
||||||
} else if (IsDxbcPixelShader()) {
|
} else if (is_pixel_shader()) {
|
||||||
// Written dynamically, so assume it's always used if it can be written to
|
// Written dynamically, so assume it's always used if it can be written to
|
||||||
// any interpolator register.
|
// any interpolator register.
|
||||||
bool param_gen_used = !is_depth_only_pixel_shader_ && register_count() != 0;
|
bool param_gen_used = !is_depth_only_pixel_shader_ && register_count() != 0;
|
||||||
|
@ -2843,7 +2853,7 @@ void DxbcShaderTranslator::WriteInputSignature() {
|
||||||
position.component_type = DxbcSignatureRegisterComponentType::kFloat32;
|
position.component_type = DxbcSignatureRegisterComponentType::kFloat32;
|
||||||
position.register_index = uint32_t(InOutRegister::kPSInPosition);
|
position.register_index = uint32_t(InOutRegister::kPSInPosition);
|
||||||
position.mask = 0b1111;
|
position.mask = 0b1111;
|
||||||
position.always_reads_mask = in_position_xy_used_ ? 0b0011 : 0b0000;
|
position.always_reads_mask = in_position_used_;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Is front face (SV_IsFrontFace).
|
// Is front face (SV_IsFrontFace).
|
||||||
|
@ -2927,7 +2937,9 @@ void DxbcShaderTranslator::WritePatchConstantSignature() {
|
||||||
DxbcName tess_factor_edge_system_value = DxbcName::kUndefined;
|
DxbcName tess_factor_edge_system_value = DxbcName::kUndefined;
|
||||||
uint32_t tess_factor_inside_count = 0;
|
uint32_t tess_factor_inside_count = 0;
|
||||||
DxbcName tess_factor_inside_system_value = DxbcName::kUndefined;
|
DxbcName tess_factor_inside_system_value = DxbcName::kUndefined;
|
||||||
switch (host_vertex_shader_type()) {
|
Shader::HostVertexShaderType host_vertex_shader_type =
|
||||||
|
GetDxbcShaderModification().host_vertex_shader_type;
|
||||||
|
switch (host_vertex_shader_type) {
|
||||||
case Shader::HostVertexShaderType::kTriangleDomainCPIndexed:
|
case Shader::HostVertexShaderType::kTriangleDomainCPIndexed:
|
||||||
case Shader::HostVertexShaderType::kTriangleDomainPatchIndexed:
|
case Shader::HostVertexShaderType::kTriangleDomainPatchIndexed:
|
||||||
tess_factor_edge_count = 3;
|
tess_factor_edge_count = 3;
|
||||||
|
@ -2944,7 +2956,7 @@ void DxbcShaderTranslator::WritePatchConstantSignature() {
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
// TODO(Triang3l): Support line patches.
|
// TODO(Triang3l): Support line patches.
|
||||||
assert_unhandled_case(host_vertex_shader_type());
|
assert_unhandled_case(host_vertex_shader_type);
|
||||||
EmitTranslationError(
|
EmitTranslationError(
|
||||||
"Unsupported host vertex shader type in WritePatchConstantSignature");
|
"Unsupported host vertex shader type in WritePatchConstantSignature");
|
||||||
}
|
}
|
||||||
|
@ -3033,7 +3045,7 @@ void DxbcShaderTranslator::WriteOutputSignature() {
|
||||||
constexpr size_t kParameterDwords =
|
constexpr size_t kParameterDwords =
|
||||||
sizeof(DxbcSignatureParameter) / sizeof(uint32_t);
|
sizeof(DxbcSignatureParameter) / sizeof(uint32_t);
|
||||||
|
|
||||||
if (IsDxbcVertexOrDomainShader()) {
|
if (is_vertex_shader()) {
|
||||||
// Intepolators (TEXCOORD#).
|
// Intepolators (TEXCOORD#).
|
||||||
size_t interpolator_position = shader_object_.size();
|
size_t interpolator_position = shader_object_.size();
|
||||||
shader_object_.resize(shader_object_.size() +
|
shader_object_.resize(shader_object_.size() +
|
||||||
|
@ -3195,7 +3207,7 @@ void DxbcShaderTranslator::WriteOutputSignature() {
|
||||||
cull_distance.semantic_name = semantic_offset;
|
cull_distance.semantic_name = semantic_offset;
|
||||||
}
|
}
|
||||||
semantic_offset += AppendString(shader_object_, "SV_CullDistance");
|
semantic_offset += AppendString(shader_object_, "SV_CullDistance");
|
||||||
} else if (IsDxbcPixelShader()) {
|
} else if (is_pixel_shader()) {
|
||||||
if (!edram_rov_used_) {
|
if (!edram_rov_used_) {
|
||||||
// Color render targets (SV_Target#).
|
// Color render targets (SV_Target#).
|
||||||
size_t target_position = SIZE_MAX;
|
size_t target_position = SIZE_MAX;
|
||||||
|
@ -3217,9 +3229,11 @@ void DxbcShaderTranslator::WriteOutputSignature() {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Depth (SV_Depth).
|
// Depth (SV_Depth or SV_DepthLessEqual).
|
||||||
|
Modification::DepthStencilMode depth_stencil_mode =
|
||||||
|
GetDxbcShaderModification().depth_stencil_mode;
|
||||||
size_t depth_position = SIZE_MAX;
|
size_t depth_position = SIZE_MAX;
|
||||||
if (writes_depth()) {
|
if (writes_depth() || DSV_IsWritingFloat24Depth()) {
|
||||||
depth_position = shader_object_.size();
|
depth_position = shader_object_.size();
|
||||||
shader_object_.resize(shader_object_.size() + kParameterDwords);
|
shader_object_.resize(shader_object_.size() + kParameterDwords);
|
||||||
++parameter_count;
|
++parameter_count;
|
||||||
|
@ -3253,7 +3267,15 @@ void DxbcShaderTranslator::WriteOutputSignature() {
|
||||||
depth_position);
|
depth_position);
|
||||||
depth.semantic_name = semantic_offset;
|
depth.semantic_name = semantic_offset;
|
||||||
}
|
}
|
||||||
semantic_offset += AppendString(shader_object_, "SV_Depth");
|
const char* depth_semantic_name;
|
||||||
|
if (!writes_depth() &&
|
||||||
|
GetDxbcShaderModification().depth_stencil_mode ==
|
||||||
|
Modification::DepthStencilMode::kFloat24Truncating) {
|
||||||
|
depth_semantic_name = "SV_DepthLessEqual";
|
||||||
|
} else {
|
||||||
|
depth_semantic_name = "SV_Depth";
|
||||||
|
}
|
||||||
|
semantic_offset += AppendString(shader_object_, depth_semantic_name);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -3276,7 +3298,7 @@ void DxbcShaderTranslator::WriteShaderCode() {
|
||||||
} else if (IsDxbcDomainShader()) {
|
} else if (IsDxbcDomainShader()) {
|
||||||
shader_type = D3D11_SB_DOMAIN_SHADER;
|
shader_type = D3D11_SB_DOMAIN_SHADER;
|
||||||
} else {
|
} else {
|
||||||
assert_true(IsDxbcPixelShader());
|
assert_true(is_pixel_shader());
|
||||||
shader_type = D3D10_SB_PIXEL_SHADER;
|
shader_type = D3D10_SB_PIXEL_SHADER;
|
||||||
}
|
}
|
||||||
shader_object_.push_back(
|
shader_object_.push_back(
|
||||||
|
@ -3296,12 +3318,14 @@ void DxbcShaderTranslator::WriteShaderCode() {
|
||||||
// Inputs/outputs have 1D-indexed operands with a component mask and a
|
// Inputs/outputs have 1D-indexed operands with a component mask and a
|
||||||
// register index.
|
// register index.
|
||||||
|
|
||||||
|
Modification shader_modification = GetDxbcShaderModification();
|
||||||
|
|
||||||
if (IsDxbcDomainShader()) {
|
if (IsDxbcDomainShader()) {
|
||||||
// Not using control point data since Xenos only has a vertex shader acting
|
// Not using control point data since Xenos only has a vertex shader acting
|
||||||
// as both vertex shader and domain shader.
|
// as both vertex shader and domain shader.
|
||||||
stat_.c_control_points = 3;
|
stat_.c_control_points = 3;
|
||||||
stat_.tessellator_domain = DxbcTessellatorDomain::kTriangle;
|
stat_.tessellator_domain = DxbcTessellatorDomain::kTriangle;
|
||||||
switch (host_vertex_shader_type()) {
|
switch (shader_modification.host_vertex_shader_type) {
|
||||||
case Shader::HostVertexShaderType::kTriangleDomainCPIndexed:
|
case Shader::HostVertexShaderType::kTriangleDomainCPIndexed:
|
||||||
case Shader::HostVertexShaderType::kTriangleDomainPatchIndexed:
|
case Shader::HostVertexShaderType::kTriangleDomainPatchIndexed:
|
||||||
stat_.c_control_points = 3;
|
stat_.c_control_points = 3;
|
||||||
|
@ -3314,7 +3338,7 @@ void DxbcShaderTranslator::WriteShaderCode() {
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
// TODO(Triang3l): Support line patches.
|
// TODO(Triang3l): Support line patches.
|
||||||
assert_unhandled_case(host_vertex_shader_type());
|
assert_unhandled_case(shader_modification.host_vertex_shader_type);
|
||||||
EmitTranslationError(
|
EmitTranslationError(
|
||||||
"Unsupported host vertex shader type in WriteShaderCode");
|
"Unsupported host vertex shader type in WriteShaderCode");
|
||||||
}
|
}
|
||||||
|
@ -3330,11 +3354,17 @@ void DxbcShaderTranslator::WriteShaderCode() {
|
||||||
}
|
}
|
||||||
|
|
||||||
// Don't allow refactoring when converting to native code to maintain position
|
// Don't allow refactoring when converting to native code to maintain position
|
||||||
// invariance (needed even in pixel shaders for oDepth invariance). Also this
|
// invariance (needed even in pixel shaders for oDepth invariance).
|
||||||
// dcl will be modified by ForceEarlyDepthStencil.
|
uint32_t global_flags_opcode =
|
||||||
shader_object_.push_back(
|
|
||||||
ENCODE_D3D10_SB_OPCODE_TYPE(D3D10_SB_OPCODE_DCL_GLOBAL_FLAGS) |
|
ENCODE_D3D10_SB_OPCODE_TYPE(D3D10_SB_OPCODE_DCL_GLOBAL_FLAGS) |
|
||||||
ENCODE_D3D10_SB_TOKENIZED_INSTRUCTION_LENGTH(1));
|
ENCODE_D3D10_SB_TOKENIZED_INSTRUCTION_LENGTH(1);
|
||||||
|
if (is_pixel_shader() &&
|
||||||
|
GetDxbcShaderModification().depth_stencil_mode ==
|
||||||
|
Modification::DepthStencilMode::kEarlyHint &&
|
||||||
|
!edram_rov_used_ && CanWriteZEarly()) {
|
||||||
|
global_flags_opcode |= D3D11_SB_GLOBAL_FLAG_FORCE_EARLY_DEPTH_STENCIL;
|
||||||
|
}
|
||||||
|
shader_object_.push_back(global_flags_opcode);
|
||||||
|
|
||||||
// Constant buffers, from most frequenly accessed to least frequently accessed
|
// Constant buffers, from most frequenly accessed to least frequently accessed
|
||||||
// (the order is a hint to the driver according to the DXBC header).
|
// (the order is a hint to the driver according to the DXBC header).
|
||||||
|
@ -3560,7 +3590,7 @@ void DxbcShaderTranslator::WriteShaderCode() {
|
||||||
}
|
}
|
||||||
|
|
||||||
// Inputs and outputs.
|
// Inputs and outputs.
|
||||||
if (IsDxbcVertexOrDomainShader()) {
|
if (is_vertex_shader()) {
|
||||||
if (IsDxbcDomainShader()) {
|
if (IsDxbcDomainShader()) {
|
||||||
if (in_domain_location_used_) {
|
if (in_domain_location_used_) {
|
||||||
// Domain location input.
|
// Domain location input.
|
||||||
|
@ -3584,7 +3614,7 @@ void DxbcShaderTranslator::WriteShaderCode() {
|
||||||
if (in_control_point_index_used_) {
|
if (in_control_point_index_used_) {
|
||||||
// Control point indices as float input.
|
// Control point indices as float input.
|
||||||
uint32_t control_point_array_size;
|
uint32_t control_point_array_size;
|
||||||
switch (host_vertex_shader_type()) {
|
switch (shader_modification.host_vertex_shader_type) {
|
||||||
case Shader::HostVertexShaderType::kTriangleDomainCPIndexed:
|
case Shader::HostVertexShaderType::kTriangleDomainCPIndexed:
|
||||||
control_point_array_size = 3;
|
control_point_array_size = 3;
|
||||||
break;
|
break;
|
||||||
|
@ -3593,7 +3623,7 @@ void DxbcShaderTranslator::WriteShaderCode() {
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
// TODO(Triang3l): Support line patches.
|
// TODO(Triang3l): Support line patches.
|
||||||
assert_unhandled_case(host_vertex_shader_type());
|
assert_unhandled_case(shader_modification.host_vertex_shader_type);
|
||||||
EmitTranslationError(
|
EmitTranslationError(
|
||||||
"Unsupported host vertex shader type in "
|
"Unsupported host vertex shader type in "
|
||||||
"StartVertexOrDomainShader");
|
"StartVertexOrDomainShader");
|
||||||
|
@ -3683,7 +3713,8 @@ void DxbcShaderTranslator::WriteShaderCode() {
|
||||||
uint32_t(InOutRegister::kVSDSOutClipDistance45AndCullDistance));
|
uint32_t(InOutRegister::kVSDSOutClipDistance45AndCullDistance));
|
||||||
shader_object_.push_back(ENCODE_D3D10_SB_NAME(D3D10_SB_NAME_CULL_DISTANCE));
|
shader_object_.push_back(ENCODE_D3D10_SB_NAME(D3D10_SB_NAME_CULL_DISTANCE));
|
||||||
++stat_.dcl_count;
|
++stat_.dcl_count;
|
||||||
} else if (IsDxbcPixelShader()) {
|
} else if (is_pixel_shader()) {
|
||||||
|
bool is_writing_float24_depth = DSV_IsWritingFloat24Depth();
|
||||||
// Interpolator input.
|
// Interpolator input.
|
||||||
if (!is_depth_only_pixel_shader_) {
|
if (!is_depth_only_pixel_shader_) {
|
||||||
uint32_t interpolator_count =
|
uint32_t interpolator_count =
|
||||||
|
@ -3725,16 +3756,26 @@ void DxbcShaderTranslator::WriteShaderCode() {
|
||||||
shader_object_.push_back(uint32_t(InOutRegister::kPSInClipSpaceZW));
|
shader_object_.push_back(uint32_t(InOutRegister::kPSInClipSpaceZW));
|
||||||
++stat_.dcl_count;
|
++stat_.dcl_count;
|
||||||
}
|
}
|
||||||
if (in_position_xy_used_) {
|
if (in_position_used_) {
|
||||||
// Position input (only XY needed for ps_param_gen, and the ROV depth code
|
// Position input (XY needed for ps_param_gen, Z needed for non-ROV
|
||||||
// calculates the depth from clip space Z and W).
|
// float24 conversion; the ROV depth code calculates the depth the from
|
||||||
|
// clip space Z and W with pull-mode per-sample interpolation instead).
|
||||||
|
// At the cost of possibility of MSAA with pixel-rate shading, need
|
||||||
|
// per-sample depth - otherwise intersections cannot be antialiased, and
|
||||||
|
// with SV_DepthLessEqual, per-sample (or centroid, but this isn't
|
||||||
|
// applicable here) position is mandatory. However, with depth output, on
|
||||||
|
// the guest, there's only one depth value for the whole pixel.
|
||||||
|
D3D10_SB_INTERPOLATION_MODE position_interpolation_mode =
|
||||||
|
is_writing_float24_depth && !writes_depth()
|
||||||
|
? D3D10_SB_INTERPOLATION_LINEAR_NOPERSPECTIVE_SAMPLE
|
||||||
|
: D3D10_SB_INTERPOLATION_LINEAR_NOPERSPECTIVE;
|
||||||
shader_object_.push_back(
|
shader_object_.push_back(
|
||||||
ENCODE_D3D10_SB_OPCODE_TYPE(D3D10_SB_OPCODE_DCL_INPUT_PS_SIV) |
|
ENCODE_D3D10_SB_OPCODE_TYPE(D3D10_SB_OPCODE_DCL_INPUT_PS_SIV) |
|
||||||
ENCODE_D3D10_SB_INPUT_INTERPOLATION_MODE(
|
ENCODE_D3D10_SB_INPUT_INTERPOLATION_MODE(
|
||||||
D3D10_SB_INTERPOLATION_LINEAR_NOPERSPECTIVE) |
|
position_interpolation_mode) |
|
||||||
ENCODE_D3D10_SB_TOKENIZED_INSTRUCTION_LENGTH(4));
|
ENCODE_D3D10_SB_TOKENIZED_INSTRUCTION_LENGTH(4));
|
||||||
shader_object_.push_back(
|
shader_object_.push_back(EncodeVectorMaskedOperand(
|
||||||
EncodeVectorMaskedOperand(D3D10_SB_OPERAND_TYPE_INPUT, 0b0011, 1));
|
D3D10_SB_OPERAND_TYPE_INPUT, in_position_used_, 1));
|
||||||
shader_object_.push_back(uint32_t(InOutRegister::kPSInPosition));
|
shader_object_.push_back(uint32_t(InOutRegister::kPSInPosition));
|
||||||
shader_object_.push_back(ENCODE_D3D10_SB_NAME(D3D10_SB_NAME_POSITION));
|
shader_object_.push_back(ENCODE_D3D10_SB_NAME(D3D10_SB_NAME_POSITION));
|
||||||
++stat_.dcl_count;
|
++stat_.dcl_count;
|
||||||
|
@ -3778,12 +3819,19 @@ void DxbcShaderTranslator::WriteShaderCode() {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
// Depth output.
|
// Depth output.
|
||||||
if (writes_depth()) {
|
if (is_writing_float24_depth || writes_depth()) {
|
||||||
|
D3D10_SB_OPERAND_TYPE depth_operand_type;
|
||||||
|
if (!writes_depth() &&
|
||||||
|
GetDxbcShaderModification().depth_stencil_mode ==
|
||||||
|
Modification::DepthStencilMode::kFloat24Truncating) {
|
||||||
|
depth_operand_type = D3D11_SB_OPERAND_TYPE_OUTPUT_DEPTH_LESS_EQUAL;
|
||||||
|
} else {
|
||||||
|
depth_operand_type = D3D10_SB_OPERAND_TYPE_OUTPUT_DEPTH;
|
||||||
|
}
|
||||||
shader_object_.push_back(
|
shader_object_.push_back(
|
||||||
ENCODE_D3D10_SB_OPCODE_TYPE(D3D10_SB_OPCODE_DCL_OUTPUT) |
|
ENCODE_D3D10_SB_OPCODE_TYPE(D3D10_SB_OPCODE_DCL_OUTPUT) |
|
||||||
ENCODE_D3D10_SB_TOKENIZED_INSTRUCTION_LENGTH(2));
|
ENCODE_D3D10_SB_TOKENIZED_INSTRUCTION_LENGTH(2));
|
||||||
shader_object_.push_back(
|
shader_object_.push_back(EncodeScalarOperand(depth_operand_type, 0));
|
||||||
EncodeScalarOperand(D3D10_SB_OPERAND_TYPE_OUTPUT_DEPTH, 0));
|
|
||||||
++stat_.dcl_count;
|
++stat_.dcl_count;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -102,6 +102,51 @@ class DxbcShaderTranslator : public ShaderTranslator {
|
||||||
bool edram_rov_used, bool force_emit_source_map = false);
|
bool edram_rov_used, bool force_emit_source_map = false);
|
||||||
~DxbcShaderTranslator() override;
|
~DxbcShaderTranslator() override;
|
||||||
|
|
||||||
|
union Modification {
|
||||||
|
// If anything in this is structure is changed in a way not compatible with
|
||||||
|
// the previous layout, invalidate the pipeline storages by increasing this
|
||||||
|
// version number (0xYYYYMMDD)!
|
||||||
|
static constexpr uint32_t kVersion = 0x20201203;
|
||||||
|
|
||||||
|
enum class DepthStencilMode : uint32_t {
|
||||||
|
kNoModifiers,
|
||||||
|
// [earlydepthstencil] - enable if alpha test and alpha to coverage are
|
||||||
|
// disabled; ignored if anything in the shader blocks early Z writing
|
||||||
|
// (which is not known before translation, so this will be set anyway).
|
||||||
|
kEarlyHint,
|
||||||
|
// Converting the depth to the closest 32-bit float representable exactly
|
||||||
|
// as a 20e4 float, to support invariance in cases when the guest
|
||||||
|
// reuploads a previously resolved depth buffer to the EDRAM, rounding
|
||||||
|
// towards zero (which contradicts the rounding used by the Direct3D 9
|
||||||
|
// reference rasterizer, but allows SV_DepthLessEqual to be used to allow
|
||||||
|
// slightly coarse early Z culling; also truncating regardless of whether
|
||||||
|
// the shader writes depth and thus always uses SV_Depth, for
|
||||||
|
// consistency). MSAA is limited - depth must be per-sample
|
||||||
|
// (SV_DepthLessEqual also explicitly requires sample or centroid position
|
||||||
|
// interpolation), thus the sampler has to run at sample frequency even if
|
||||||
|
// the device supports stencil loading and thus true non-ROV MSAA via
|
||||||
|
// SV_StencilRef.
|
||||||
|
// Fixed-function viewport depth bounds must be snapped to float24 for
|
||||||
|
// clamping purposes.
|
||||||
|
kFloat24Truncating,
|
||||||
|
// Similar to kFloat24Truncating, but rounding to the nearest even,
|
||||||
|
// however, always using SV_Depth rather than SV_DepthLessEqual because
|
||||||
|
// rounding up results in a bigger value. Same viewport usage rules apply.
|
||||||
|
kFloat24Rounding,
|
||||||
|
};
|
||||||
|
|
||||||
|
struct {
|
||||||
|
// VS - pipeline stage and input configuration.
|
||||||
|
Shader::HostVertexShaderType host_vertex_shader_type
|
||||||
|
: Shader::kHostVertexShaderTypeBitCount;
|
||||||
|
// PS, non-ROV - depth / stencil output mode.
|
||||||
|
DepthStencilMode depth_stencil_mode : 2;
|
||||||
|
};
|
||||||
|
uint32_t value = 0;
|
||||||
|
|
||||||
|
Modification(uint32_t modification_value = 0) : value(modification_value) {}
|
||||||
|
};
|
||||||
|
|
||||||
// Constant buffer bindings in space 0.
|
// Constant buffer bindings in space 0.
|
||||||
enum class CbufferRegister {
|
enum class CbufferRegister {
|
||||||
kSystemConstants,
|
kSystemConstants,
|
||||||
|
@ -238,15 +283,15 @@ class DxbcShaderTranslator : public ShaderTranslator {
|
||||||
// EDRAM address calculation.
|
// EDRAM address calculation.
|
||||||
uint32_t sample_count_log2[2];
|
uint32_t sample_count_log2[2];
|
||||||
float alpha_test_reference;
|
float alpha_test_reference;
|
||||||
|
// If alpha to mask is disabled, the entire alpha_to_mask value must be 0.
|
||||||
|
// If alpha to mask is enabled, bits 0:7 are sample offsets, and bit 8 must
|
||||||
|
// be 1.
|
||||||
uint32_t alpha_to_mask;
|
uint32_t alpha_to_mask;
|
||||||
|
|
||||||
float color_exp_bias[4];
|
float color_exp_bias[4];
|
||||||
|
|
||||||
uint32_t color_output_map[4];
|
uint32_t color_output_map[4];
|
||||||
|
|
||||||
// If alpha to mask is disabled, the entire alpha_to_mask value must be 0.
|
|
||||||
// If alpha to mask is enabled, bits 0:7 are sample offsets, and bit 8 must
|
|
||||||
// be 1.
|
|
||||||
uint32_t edram_resolution_square_scale;
|
uint32_t edram_resolution_square_scale;
|
||||||
uint32_t edram_pitch_tiles;
|
uint32_t edram_pitch_tiles;
|
||||||
union {
|
union {
|
||||||
|
@ -358,12 +403,6 @@ class DxbcShaderTranslator : public ShaderTranslator {
|
||||||
bool is_signed;
|
bool is_signed;
|
||||||
std::string name;
|
std::string name;
|
||||||
};
|
};
|
||||||
// The first binding returned is at t[SRVMainRegister::kBindfulTexturesStart]
|
|
||||||
// of space SRVSpace::kMain.
|
|
||||||
const TextureBinding* GetTextureBindings(uint32_t& count_out) const {
|
|
||||||
count_out = uint32_t(texture_bindings_.size());
|
|
||||||
return texture_bindings_.data();
|
|
||||||
}
|
|
||||||
|
|
||||||
// Arbitrary limit - there can't be more than 2048 in a shader-visible
|
// Arbitrary limit - there can't be more than 2048 in a shader-visible
|
||||||
// descriptor heap, though some older hardware (tier 1 resource binding -
|
// descriptor heap, though some older hardware (tier 1 resource binding -
|
||||||
|
@ -385,16 +424,6 @@ class DxbcShaderTranslator : public ShaderTranslator {
|
||||||
xenos::AnisoFilter aniso_filter;
|
xenos::AnisoFilter aniso_filter;
|
||||||
std::string name;
|
std::string name;
|
||||||
};
|
};
|
||||||
const SamplerBinding* GetSamplerBindings(uint32_t& count_out) const {
|
|
||||||
count_out = uint32_t(sampler_bindings_.size());
|
|
||||||
return sampler_bindings_.data();
|
|
||||||
}
|
|
||||||
|
|
||||||
// Returns the number of texture SRV and sampler offsets that need to be
|
|
||||||
// passed via a constant buffer to the shader.
|
|
||||||
uint32_t GetBindlessResourceCount() const {
|
|
||||||
return uint32_t(texture_bindings_.size() + sampler_bindings_.size());
|
|
||||||
}
|
|
||||||
|
|
||||||
// Unordered access view bindings in space 0.
|
// Unordered access view bindings in space 0.
|
||||||
enum class UAVRegister {
|
enum class UAVRegister {
|
||||||
|
@ -402,10 +431,6 @@ class DxbcShaderTranslator : public ShaderTranslator {
|
||||||
kEdram,
|
kEdram,
|
||||||
};
|
};
|
||||||
|
|
||||||
// Creates a copy of the shader with early depth/stencil testing forced,
|
|
||||||
// overriding that alpha testing is used in the shader.
|
|
||||||
static std::vector<uint8_t> ForceEarlyDepthStencil(const uint8_t* shader);
|
|
||||||
|
|
||||||
// Returns the format with internal flags for passing via the
|
// Returns the format with internal flags for passing via the
|
||||||
// edram_rt_format_flags system constant.
|
// edram_rt_format_flags system constant.
|
||||||
static constexpr uint32_t ROV_AddColorFormatFlags(
|
static constexpr uint32_t ROV_AddColorFormatFlags(
|
||||||
|
@ -440,16 +465,22 @@ class DxbcShaderTranslator : public ShaderTranslator {
|
||||||
float& clamp_alpha_high, uint32_t& keep_mask_low,
|
float& clamp_alpha_high, uint32_t& keep_mask_low,
|
||||||
uint32_t& keep_mask_high);
|
uint32_t& keep_mask_high);
|
||||||
|
|
||||||
|
uint32_t GetDefaultModification(
|
||||||
|
xenos::ShaderType shader_type,
|
||||||
|
Shader::HostVertexShaderType host_vertex_shader_type =
|
||||||
|
Shader::HostVertexShaderType::kVertex) const override;
|
||||||
|
|
||||||
// Creates a special pixel shader without color outputs - this resets the
|
// Creates a special pixel shader without color outputs - this resets the
|
||||||
// state of the translator.
|
// state of the translator.
|
||||||
std::vector<uint8_t> CreateDepthOnlyPixelShader();
|
std::vector<uint8_t> CreateDepthOnlyPixelShader();
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
void Reset() override;
|
void Reset(xenos::ShaderType shader_type) override;
|
||||||
|
|
||||||
void StartTranslation() override;
|
void StartTranslation() override;
|
||||||
|
|
||||||
std::vector<uint8_t> CompleteTranslation() override;
|
std::vector<uint8_t> CompleteTranslation() override;
|
||||||
|
void PostTranslation(Shader::Translation& translation,
|
||||||
|
bool setup_shader_post_translation_info) override;
|
||||||
|
|
||||||
void ProcessLabel(uint32_t cf_index) override;
|
void ProcessLabel(uint32_t cf_index) override;
|
||||||
|
|
||||||
|
@ -650,6 +681,7 @@ class DxbcShaderTranslator : public ShaderTranslator {
|
||||||
kInputDomainPoint = 28,
|
kInputDomainPoint = 28,
|
||||||
kUnorderedAccessView = 30,
|
kUnorderedAccessView = 30,
|
||||||
kInputCoverageMask = 35,
|
kInputCoverageMask = 35,
|
||||||
|
kOutputDepthLessEqual = 39,
|
||||||
};
|
};
|
||||||
|
|
||||||
// D3D10_SB_OPERAND_INDEX_DIMENSION
|
// D3D10_SB_OPERAND_INDEX_DIMENSION
|
||||||
|
@ -689,6 +721,7 @@ class DxbcShaderTranslator : public ShaderTranslator {
|
||||||
return DxbcOperandDimension::kNoData;
|
return DxbcOperandDimension::kNoData;
|
||||||
case DxbcOperandType::kInputPrimitiveID:
|
case DxbcOperandType::kInputPrimitiveID:
|
||||||
case DxbcOperandType::kOutputDepth:
|
case DxbcOperandType::kOutputDepth:
|
||||||
|
case DxbcOperandType::kOutputDepthLessEqual:
|
||||||
return DxbcOperandDimension::kScalar;
|
return DxbcOperandDimension::kScalar;
|
||||||
case DxbcOperandType::kInputCoverageMask:
|
case DxbcOperandType::kInputCoverageMask:
|
||||||
return dest_in_dcl ? DxbcOperandDimension::kScalar
|
return dest_in_dcl ? DxbcOperandDimension::kScalar
|
||||||
|
@ -860,6 +893,9 @@ class DxbcShaderTranslator : public ShaderTranslator {
|
||||||
return DxbcDest(DxbcOperandType::kUnorderedAccessView, write_mask,
|
return DxbcDest(DxbcOperandType::kUnorderedAccessView, write_mask,
|
||||||
index_1d, index_2d);
|
index_1d, index_2d);
|
||||||
}
|
}
|
||||||
|
static DxbcDest ODepthLE() {
|
||||||
|
return DxbcDest(DxbcOperandType::kOutputDepthLessEqual, 0b0001);
|
||||||
|
}
|
||||||
|
|
||||||
uint32_t GetMask() const {
|
uint32_t GetMask() const {
|
||||||
switch (GetDimension()) {
|
switch (GetDimension()) {
|
||||||
|
@ -2145,21 +2181,19 @@ class DxbcShaderTranslator : public ShaderTranslator {
|
||||||
(index_representation_1 << 25) | (index_representation_2 << 28);
|
(index_representation_1 << 25) | (index_representation_2 << 28);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Use these instead of is_vertex_shader/is_pixel_shader because they don't
|
Modification GetDxbcShaderModification() const {
|
||||||
// take is_depth_only_pixel_shader_ into account.
|
return Modification(modification());
|
||||||
inline bool IsDxbcVertexOrDomainShader() const {
|
|
||||||
return !is_depth_only_pixel_shader_ && is_vertex_shader();
|
|
||||||
}
|
}
|
||||||
inline bool IsDxbcVertexShader() const {
|
|
||||||
return IsDxbcVertexOrDomainShader() &&
|
bool IsDxbcVertexShader() const {
|
||||||
host_vertex_shader_type() == Shader::HostVertexShaderType::kVertex;
|
return is_vertex_shader() &&
|
||||||
|
GetDxbcShaderModification().host_vertex_shader_type ==
|
||||||
|
Shader::HostVertexShaderType::kVertex;
|
||||||
}
|
}
|
||||||
inline bool IsDxbcDomainShader() const {
|
bool IsDxbcDomainShader() const {
|
||||||
return IsDxbcVertexOrDomainShader() &&
|
return is_vertex_shader() &&
|
||||||
host_vertex_shader_type() != Shader::HostVertexShaderType::kVertex;
|
GetDxbcShaderModification().host_vertex_shader_type !=
|
||||||
}
|
Shader::HostVertexShaderType::kVertex;
|
||||||
inline bool IsDxbcPixelShader() const {
|
|
||||||
return is_depth_only_pixel_shader_ || is_pixel_shader();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Whether to use switch-case rather than if (pc >= label) for control flow.
|
// Whether to use switch-case rather than if (pc >= label) for control flow.
|
||||||
|
@ -2181,10 +2215,37 @@ class DxbcShaderTranslator : public ShaderTranslator {
|
||||||
uint32_t piece_temp_component, uint32_t accumulator_temp,
|
uint32_t piece_temp_component, uint32_t accumulator_temp,
|
||||||
uint32_t accumulator_temp_component);
|
uint32_t accumulator_temp_component);
|
||||||
|
|
||||||
|
// Converts the depth value externally clamped to the representable [0, 2)
|
||||||
|
// range to 20e4 floating point, with zeros in bits 24:31, rounding to the
|
||||||
|
// nearest even. Source and destination may be the same, temporary must be
|
||||||
|
// different than both.
|
||||||
|
void PreClampedDepthTo20e4(uint32_t d24_temp, uint32_t d24_temp_component,
|
||||||
|
uint32_t d32_temp, uint32_t d32_temp_component,
|
||||||
|
uint32_t temp_temp, uint32_t temp_temp_component);
|
||||||
|
bool IsDepthStencilSystemTempUsed() const {
|
||||||
|
// See system_temp_depth_stencil_ documentation for explanation of cases.
|
||||||
|
if (edram_rov_used_) {
|
||||||
|
return writes_depth() || ROV_IsDepthStencilEarly();
|
||||||
|
}
|
||||||
|
return writes_depth() && DSV_IsWritingFloat24Depth();
|
||||||
|
}
|
||||||
|
// Whether the current non-ROV pixel shader should convert the depth to 20e4.
|
||||||
|
bool DSV_IsWritingFloat24Depth() const {
|
||||||
|
if (edram_rov_used_) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
Modification::DepthStencilMode depth_stencil_mode =
|
||||||
|
GetDxbcShaderModification().depth_stencil_mode;
|
||||||
|
return depth_stencil_mode ==
|
||||||
|
Modification::DepthStencilMode::kFloat24Truncating ||
|
||||||
|
depth_stencil_mode ==
|
||||||
|
Modification::DepthStencilMode::kFloat24Rounding;
|
||||||
|
}
|
||||||
// Whether it's possible and worth skipping running the translated shader for
|
// Whether it's possible and worth skipping running the translated shader for
|
||||||
// 2x2 quads.
|
// 2x2 quads.
|
||||||
bool ROV_IsDepthStencilEarly() const {
|
bool ROV_IsDepthStencilEarly() const {
|
||||||
return !is_depth_only_pixel_shader_ && !writes_depth();
|
return !is_depth_only_pixel_shader_ && !writes_depth() &&
|
||||||
|
memexport_stream_constants().empty();
|
||||||
}
|
}
|
||||||
// Converts the depth value to 24-bit (storing the result in bits 0:23 and
|
// Converts the depth value to 24-bit (storing the result in bits 0:23 and
|
||||||
// zeros in 24:31, not creating room for stencil - since this may be involved
|
// zeros in 24:31, not creating room for stencil - since this may be involved
|
||||||
|
@ -2197,8 +2258,8 @@ class DxbcShaderTranslator : public ShaderTranslator {
|
||||||
// Does all the depth/stencil-related things, including or not including
|
// Does all the depth/stencil-related things, including or not including
|
||||||
// writing based on whether it's late, or on whether it's safe to do it early.
|
// writing based on whether it's late, or on whether it's safe to do it early.
|
||||||
// Updates system_temp_rov_params_ result and coverage if allowed and safe,
|
// Updates system_temp_rov_params_ result and coverage if allowed and safe,
|
||||||
// updates system_temp_rov_depth_stencil_, and if early and the coverage is
|
// updates system_temp_depth_stencil_, and if early and the coverage is empty
|
||||||
// empty for all pixels in the 2x2 quad and safe to return early (stencil is
|
// for all pixels in the 2x2 quad and safe to return early (stencil is
|
||||||
// unchanged or known that it's safe not to await kills/alphatest/AtoC),
|
// unchanged or known that it's safe not to await kills/alphatest/AtoC),
|
||||||
// returns from the shader.
|
// returns from the shader.
|
||||||
void ROV_DepthStencilTest();
|
void ROV_DepthStencilTest();
|
||||||
|
@ -2248,6 +2309,7 @@ class DxbcShaderTranslator : public ShaderTranslator {
|
||||||
// Discards the SSAA sample if it's masked out by alpha to coverage.
|
// Discards the SSAA sample if it's masked out by alpha to coverage.
|
||||||
void CompletePixelShader_WriteToRTVs_AlphaToMask();
|
void CompletePixelShader_WriteToRTVs_AlphaToMask();
|
||||||
void CompletePixelShader_WriteToRTVs();
|
void CompletePixelShader_WriteToRTVs();
|
||||||
|
void CompletePixelShader_DSV_DepthTo24Bit();
|
||||||
// Masks the sample away from system_temp_rov_params_.x if it's not covered.
|
// Masks the sample away from system_temp_rov_params_.x if it's not covered.
|
||||||
// threshold_offset and temp.temp_component can be the same if needed.
|
// threshold_offset and temp.temp_component can be the same if needed.
|
||||||
void CompletePixelShader_ROV_AlphaToMaskSample(
|
void CompletePixelShader_ROV_AlphaToMaskSample(
|
||||||
|
@ -2333,6 +2395,11 @@ class DxbcShaderTranslator : public ShaderTranslator {
|
||||||
xenos::TextureFilter min_filter,
|
xenos::TextureFilter min_filter,
|
||||||
xenos::TextureFilter mip_filter,
|
xenos::TextureFilter mip_filter,
|
||||||
xenos::AnisoFilter aniso_filter);
|
xenos::AnisoFilter aniso_filter);
|
||||||
|
// Returns the number of texture SRV and sampler offsets that need to be
|
||||||
|
// passed via a constant buffer to the shader.
|
||||||
|
uint32_t GetBindlessResourceCount() const {
|
||||||
|
return uint32_t(texture_bindings_.size() + sampler_bindings_.size());
|
||||||
|
}
|
||||||
// Marks fetch constants as used by the DXBC shader and returns DxbcSrc
|
// Marks fetch constants as used by the DXBC shader and returns DxbcSrc
|
||||||
// for the words 01 (pair 0), 23 (pair 1) or 45 (pair 2) of the texture fetch
|
// for the words 01 (pair 0), 23 (pair 1) or 45 (pair 2) of the texture fetch
|
||||||
// constant.
|
// constant.
|
||||||
|
@ -2364,7 +2431,7 @@ class DxbcShaderTranslator : public ShaderTranslator {
|
||||||
static uint32_t AppendString(std::vector<uint32_t>& dest, const char* source);
|
static uint32_t AppendString(std::vector<uint32_t>& dest, const char* source);
|
||||||
// Returns the length of a string as if it was appended to a DWORD stream, in
|
// Returns the length of a string as if it was appended to a DWORD stream, in
|
||||||
// bytes.
|
// bytes.
|
||||||
static inline uint32_t GetStringLength(const char* source) {
|
static uint32_t GetStringLength(const char* source) {
|
||||||
return uint32_t(xe::align(std::strlen(source) + 1, sizeof(uint32_t)));
|
return uint32_t(xe::align(std::strlen(source) + 1, sizeof(uint32_t)));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -2479,8 +2546,8 @@ class DxbcShaderTranslator : public ShaderTranslator {
|
||||||
bool in_primitive_id_used_;
|
bool in_primitive_id_used_;
|
||||||
// Whether InOutRegister::kDSInControlPointIndex has been used in the shader.
|
// Whether InOutRegister::kDSInControlPointIndex has been used in the shader.
|
||||||
bool in_control_point_index_used_;
|
bool in_control_point_index_used_;
|
||||||
// Whether the XY of the pixel position has been used in the pixel shader.
|
// Mask of the pixel/sample position actually used in the pixel shader.
|
||||||
bool in_position_xy_used_;
|
uint32_t in_position_used_;
|
||||||
// Whether the faceness has been used in the pixel shader.
|
// Whether the faceness has been used in the pixel shader.
|
||||||
bool in_front_face_used_;
|
bool in_front_face_used_;
|
||||||
|
|
||||||
|
@ -2518,15 +2585,14 @@ class DxbcShaderTranslator : public ShaderTranslator {
|
||||||
// W - Base-relative resolution-scaled EDRAM offset for 64bpp color data, in
|
// W - Base-relative resolution-scaled EDRAM offset for 64bpp color data, in
|
||||||
// dwords.
|
// dwords.
|
||||||
uint32_t system_temp_rov_params_;
|
uint32_t system_temp_rov_params_;
|
||||||
// ROV only - new depth/stencil data. 4 VGPRs when not writing to oDepth, 1
|
// Two purposes:
|
||||||
// VGPR when writing to oDepth. Not used in the depth-only pixel shader (or,
|
// - When writing to oDepth, and either using ROV or converting the depth to
|
||||||
// more formally, if neither early depth-stencil nor oDepth are used) because
|
// float24: X also used to hold the depth written by the shader,
|
||||||
// it always calculates and writes in the same place.
|
// later used as a temporary during depth/stencil testing.
|
||||||
// When not writing to oDepth: New per-sample depth/stencil values, generated
|
// - Otherwise, when using ROV output with ROV_IsDepthStencilEarly being true:
|
||||||
// during early depth/stencil test (actual writing checks coverage bits).
|
// New per-sample depth/stencil values, generated during early depth/stencil
|
||||||
// When writing to oDepth: X also used to hold the depth written by the
|
// test (actual writing checks coverage bits).
|
||||||
// shader, later used as a temporary during depth/stencil testing.
|
uint32_t system_temp_depth_stencil_;
|
||||||
uint32_t system_temp_rov_depth_stencil_;
|
|
||||||
// Up to 4 color outputs in pixel shaders (because of exponent bias, alpha
|
// Up to 4 color outputs in pixel shaders (because of exponent bias, alpha
|
||||||
// test and remapping, and also for ROV writing).
|
// test and remapping, and also for ROV writing).
|
||||||
uint32_t system_temps_color_[4];
|
uint32_t system_temps_color_[4];
|
||||||
|
@ -2587,6 +2653,8 @@ class DxbcShaderTranslator : public ShaderTranslator {
|
||||||
uint32_t srv_index_bindless_textures_3d_;
|
uint32_t srv_index_bindless_textures_3d_;
|
||||||
uint32_t srv_index_bindless_textures_cube_;
|
uint32_t srv_index_bindless_textures_cube_;
|
||||||
|
|
||||||
|
// The first binding is at t[SRVMainRegister::kBindfulTexturesStart] of space
|
||||||
|
// SRVSpace::kMain.
|
||||||
std::vector<TextureBinding> texture_bindings_;
|
std::vector<TextureBinding> texture_bindings_;
|
||||||
std::unordered_map<uint32_t, uint32_t>
|
std::unordered_map<uint32_t, uint32_t>
|
||||||
texture_bindings_for_bindful_srv_indices_;
|
texture_bindings_for_bindful_srv_indices_;
|
||||||
|
|
|
@ -677,7 +677,7 @@ void DxbcShaderTranslator::ProcessTextureFetchInstruction(
|
||||||
// Whether to use gradients (implicit or explicit) for LOD calculation.
|
// Whether to use gradients (implicit or explicit) for LOD calculation.
|
||||||
bool use_computed_lod =
|
bool use_computed_lod =
|
||||||
instr.attributes.use_computed_lod &&
|
instr.attributes.use_computed_lod &&
|
||||||
(IsDxbcPixelShader() || instr.attributes.use_register_gradients);
|
(is_pixel_shader() || instr.attributes.use_register_gradients);
|
||||||
if (instr.opcode == FetchOpcode::kGetTextureComputedLod &&
|
if (instr.opcode == FetchOpcode::kGetTextureComputedLod &&
|
||||||
(!use_computed_lod || instr.attributes.use_register_gradients)) {
|
(!use_computed_lod || instr.attributes.use_register_gradients)) {
|
||||||
assert_always();
|
assert_always();
|
||||||
|
|
|
@ -106,7 +106,7 @@ void DxbcShaderTranslator::ExportToMemory() {
|
||||||
kSysConst_Flags_Vec)
|
kSysConst_Flags_Vec)
|
||||||
.Select(kSysConst_Flags_Comp),
|
.Select(kSysConst_Flags_Comp),
|
||||||
DxbcSrc::LU(kSysFlag_SharedMemoryIsUAV));
|
DxbcSrc::LU(kSysFlag_SharedMemoryIsUAV));
|
||||||
if (IsDxbcPixelShader()) {
|
if (is_pixel_shader()) {
|
||||||
// Disable memexport in pixel shaders with supersampling since VPOS is
|
// Disable memexport in pixel shaders with supersampling since VPOS is
|
||||||
// ambiguous.
|
// ambiguous.
|
||||||
if (edram_rov_used_) {
|
if (edram_rov_used_) {
|
||||||
|
|
|
@ -167,7 +167,7 @@ void DxbcShaderTranslator::StartPixelShader_LoadROVParameters() {
|
||||||
// bigger) to integer to system_temp_rov_params_.zw.
|
// bigger) to integer to system_temp_rov_params_.zw.
|
||||||
// system_temp_rov_params_.z = X host pixel position as uint
|
// system_temp_rov_params_.z = X host pixel position as uint
|
||||||
// system_temp_rov_params_.w = Y host pixel position as uint
|
// system_temp_rov_params_.w = Y host pixel position as uint
|
||||||
in_position_xy_used_ = true;
|
in_position_used_ |= 0b0011;
|
||||||
DxbcOpFToU(DxbcDest::R(system_temp_rov_params_, 0b1100),
|
DxbcOpFToU(DxbcDest::R(system_temp_rov_params_, 0b1100),
|
||||||
DxbcSrc::V(uint32_t(InOutRegister::kPSInPosition), 0b01000000));
|
DxbcSrc::V(uint32_t(InOutRegister::kPSInPosition), 0b01000000));
|
||||||
// Revert the resolution scale to convert the position to guest pixels.
|
// Revert the resolution scale to convert the position to guest pixels.
|
||||||
|
@ -315,7 +315,7 @@ void DxbcShaderTranslator::StartPixelShader_LoadROVParameters() {
|
||||||
// Add host pixel offsets.
|
// Add host pixel offsets.
|
||||||
// system_temp_rov_params_.y = scaled 32bpp depth/stencil address
|
// system_temp_rov_params_.y = scaled 32bpp depth/stencil address
|
||||||
// system_temp_rov_params_.z = scaled 32bpp color offset if needed
|
// system_temp_rov_params_.z = scaled 32bpp color offset if needed
|
||||||
in_position_xy_used_ = true;
|
in_position_used_ |= 0b0011;
|
||||||
for (uint32_t i = 0; i < 2; ++i) {
|
for (uint32_t i = 0; i < 2; ++i) {
|
||||||
// Convert a position component to integer.
|
// Convert a position component to integer.
|
||||||
DxbcOpFToU(DxbcDest::R(system_temp_rov_params_, 0b0001),
|
DxbcOpFToU(DxbcDest::R(system_temp_rov_params_, 0b0001),
|
||||||
|
@ -417,23 +417,50 @@ void DxbcShaderTranslator::ROV_DepthStencilTest() {
|
||||||
// With early depth/stencil, depth/stencil writing may be deferred to the
|
// With early depth/stencil, depth/stencil writing may be deferred to the
|
||||||
// end of the shader to prevent writing in case something (like alpha test,
|
// end of the shader to prevent writing in case something (like alpha test,
|
||||||
// which is dynamic GPU state) discards the pixel. So, write directly to the
|
// which is dynamic GPU state) discards the pixel. So, write directly to the
|
||||||
// persistent register, system_temp_rov_depth_stencil_, instead of a local
|
// persistent register, system_temp_depth_stencil_, instead of a local
|
||||||
// temporary register.
|
// temporary register.
|
||||||
DxbcDest sample_depth_stencil_dest(
|
DxbcDest sample_depth_stencil_dest(
|
||||||
depth_stencil_early
|
depth_stencil_early ? DxbcDest::R(system_temp_depth_stencil_, 1 << i)
|
||||||
? DxbcDest::R(system_temp_rov_depth_stencil_, 1 << i)
|
: temp_x_dest);
|
||||||
: temp_x_dest);
|
|
||||||
DxbcSrc sample_depth_stencil_src(
|
DxbcSrc sample_depth_stencil_src(
|
||||||
depth_stencil_early
|
depth_stencil_early ? DxbcSrc::R(system_temp_depth_stencil_).Select(i)
|
||||||
? DxbcSrc::R(system_temp_rov_depth_stencil_).Select(i)
|
: temp_x_src);
|
||||||
: temp_x_src);
|
|
||||||
|
|
||||||
if (!i) {
|
if (!i) {
|
||||||
if (writes_depth()) {
|
if (writes_depth()) {
|
||||||
|
// Clamp oDepth to the lower viewport depth bound (depth clamp happens
|
||||||
|
// after the pixel shader in the pipeline, at least on Direct3D 11 and
|
||||||
|
// Vulkan, thus applies to the shader's depth output too).
|
||||||
|
system_constants_used_ |= 1ull << kSysConst_EdramDepthRange_Index;
|
||||||
|
DxbcOpMax(DxbcDest::R(system_temp_depth_stencil_, 0b0001),
|
||||||
|
DxbcSrc::R(system_temp_depth_stencil_, DxbcSrc::kXXXX),
|
||||||
|
DxbcSrc::CB(cbuffer_index_system_constants_,
|
||||||
|
uint32_t(CbufferRegister::kSystemConstants),
|
||||||
|
kSysConst_EdramDepthRange_Vec)
|
||||||
|
.Select(kSysConst_EdramDepthRangeOffset_Comp));
|
||||||
|
// Calculate the upper Z range bound to temp.x for clamping after
|
||||||
|
// biasing.
|
||||||
|
// temp.x = viewport maximum depth
|
||||||
|
system_constants_used_ |= 1ull << kSysConst_EdramDepthRange_Index;
|
||||||
|
DxbcOpAdd(temp_x_dest,
|
||||||
|
DxbcSrc::CB(cbuffer_index_system_constants_,
|
||||||
|
uint32_t(CbufferRegister::kSystemConstants),
|
||||||
|
kSysConst_EdramDepthRange_Vec)
|
||||||
|
.Select(kSysConst_EdramDepthRangeOffset_Comp),
|
||||||
|
DxbcSrc::CB(cbuffer_index_system_constants_,
|
||||||
|
uint32_t(CbufferRegister::kSystemConstants),
|
||||||
|
kSysConst_EdramDepthRange_Vec)
|
||||||
|
.Select(kSysConst_EdramDepthRangeScale_Comp));
|
||||||
|
// Clamp oDepth to the upper viewport depth bound (already not above 1,
|
||||||
|
// but saturate for total safety).
|
||||||
|
// temp.x = free
|
||||||
|
DxbcOpMin(DxbcDest::R(system_temp_depth_stencil_, 0b0001),
|
||||||
|
DxbcSrc::R(system_temp_depth_stencil_, DxbcSrc::kXXXX),
|
||||||
|
temp_x_src, true);
|
||||||
// Convert the shader-generated depth to 24-bit, using temp.x as
|
// Convert the shader-generated depth to 24-bit, using temp.x as
|
||||||
// temporary.
|
// temporary.
|
||||||
ROV_DepthTo24Bit(system_temp_rov_depth_stencil_, 0,
|
ROV_DepthTo24Bit(system_temp_depth_stencil_, 0,
|
||||||
system_temp_rov_depth_stencil_, 0, temp, 0);
|
system_temp_depth_stencil_, 0, temp, 0);
|
||||||
} else {
|
} else {
|
||||||
// Load the first sample's Z*W and W to temp.xy - need this regardless
|
// Load the first sample's Z*W and W to temp.xy - need this regardless
|
||||||
// of coverage for polygon offset.
|
// of coverage for polygon offset.
|
||||||
|
@ -529,14 +556,14 @@ void DxbcShaderTranslator::ROV_DepthStencilTest() {
|
||||||
}
|
}
|
||||||
|
|
||||||
// Get if the current sample is covered to temp.w.
|
// Get if the current sample is covered to temp.w.
|
||||||
// temp.x = first sample's viewport space Z or 24-bit oDepth
|
// temp.x = first sample's viewport space Z if not writing to oDepth
|
||||||
// temp.y = polygon offset if not writing to oDepth
|
// temp.y = polygon offset if not writing to oDepth
|
||||||
// temp.z = viewport maximum depth if not writing to oDepth
|
// temp.z = viewport maximum depth if not writing to oDepth
|
||||||
// temp.w = coverage of the current sample
|
// temp.w = coverage of the current sample
|
||||||
DxbcOpAnd(temp_w_dest, DxbcSrc::R(system_temp_rov_params_, DxbcSrc::kXXXX),
|
DxbcOpAnd(temp_w_dest, DxbcSrc::R(system_temp_rov_params_, DxbcSrc::kXXXX),
|
||||||
DxbcSrc::LU(1 << i));
|
DxbcSrc::LU(1 << i));
|
||||||
// Check if the current sample is covered. Release 1 VGPR.
|
// Check if the current sample is covered. Release 1 VGPR.
|
||||||
// temp.x = first sample's viewport space Z or 24-bit oDepth
|
// temp.x = first sample's viewport space Z if not writing to oDepth
|
||||||
// temp.y = polygon offset if not writing to oDepth
|
// temp.y = polygon offset if not writing to oDepth
|
||||||
// temp.z = viewport maximum depth if not writing to oDepth
|
// temp.z = viewport maximum depth if not writing to oDepth
|
||||||
// temp.w = free
|
// temp.w = free
|
||||||
|
@ -546,7 +573,7 @@ void DxbcShaderTranslator::ROV_DepthStencilTest() {
|
||||||
// Copy the 24-bit depth common to all samples to sample_depth_stencil.
|
// Copy the 24-bit depth common to all samples to sample_depth_stencil.
|
||||||
// temp.x = shader-generated 24-bit depth
|
// temp.x = shader-generated 24-bit depth
|
||||||
DxbcOpMov(sample_depth_stencil_dest,
|
DxbcOpMov(sample_depth_stencil_dest,
|
||||||
DxbcSrc::R(system_temp_rov_depth_stencil_, DxbcSrc::kXXXX));
|
DxbcSrc::R(system_temp_depth_stencil_, DxbcSrc::kXXXX));
|
||||||
} else {
|
} else {
|
||||||
if (i) {
|
if (i) {
|
||||||
// Sample's depth precalculated for sample 0 (for slope-scaled depth
|
// Sample's depth precalculated for sample 0 (for slope-scaled depth
|
||||||
|
@ -1720,7 +1747,7 @@ void DxbcShaderTranslator::CompletePixelShader_WriteToRTVs_AlphaToMask() {
|
||||||
// Convert SSAA sample position to integer to temp.xy (not caring about the
|
// Convert SSAA sample position to integer to temp.xy (not caring about the
|
||||||
// resolution scale because it's not supported anywhere on the RTV output
|
// resolution scale because it's not supported anywhere on the RTV output
|
||||||
// path).
|
// path).
|
||||||
in_position_xy_used_ = true;
|
in_position_used_ |= 0b0011;
|
||||||
DxbcOpFToU(DxbcDest::R(temp, 0b0011),
|
DxbcOpFToU(DxbcDest::R(temp, 0b0011),
|
||||||
DxbcSrc::V(uint32_t(InOutRegister::kPSInPosition)));
|
DxbcSrc::V(uint32_t(InOutRegister::kPSInPosition)));
|
||||||
|
|
||||||
|
@ -1913,6 +1940,139 @@ void DxbcShaderTranslator::CompletePixelShader_WriteToRTVs() {
|
||||||
PopSystemTemp(2);
|
PopSystemTemp(2);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void DxbcShaderTranslator::CompletePixelShader_DSV_DepthTo24Bit() {
|
||||||
|
if (!DSV_IsWritingFloat24Depth()) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
uint32_t temp;
|
||||||
|
if (writes_depth()) {
|
||||||
|
// The depth is already written to system_temp_depth_stencil_.x and clamped
|
||||||
|
// to 0...1 with NaNs dropped (saturating in StoreResult); yzw are free.
|
||||||
|
temp = system_temp_depth_stencil_;
|
||||||
|
} else {
|
||||||
|
// Need a temporary variable; copy the sample's depth input to it and
|
||||||
|
// saturate it (in Direct3D 11, depth is clamped to the viewport bounds
|
||||||
|
// after the pixel shader, and SV_Position.z contains the unclamped depth,
|
||||||
|
// which may be outside the viewport's depth range if it's biased); though
|
||||||
|
// it will be clamped to the viewport bounds anyway, but to be able to make
|
||||||
|
// the assumption of it being clamped while working with the bit
|
||||||
|
// representation.
|
||||||
|
temp = PushSystemTemp();
|
||||||
|
in_position_used_ |= 0b0100;
|
||||||
|
DxbcOpMov(
|
||||||
|
DxbcDest::R(temp, 0b0001),
|
||||||
|
DxbcSrc::V(uint32_t(InOutRegister::kPSInPosition), DxbcSrc::kZZZZ),
|
||||||
|
true);
|
||||||
|
}
|
||||||
|
|
||||||
|
DxbcDest temp_x_dest(DxbcDest::R(temp, 0b0001));
|
||||||
|
DxbcSrc temp_x_src(DxbcSrc::R(temp, DxbcSrc::kXXXX));
|
||||||
|
DxbcDest temp_y_dest(DxbcDest::R(temp, 0b0010));
|
||||||
|
DxbcSrc temp_y_src(DxbcSrc::R(temp, DxbcSrc::kYYYY));
|
||||||
|
|
||||||
|
if (GetDxbcShaderModification().depth_stencil_mode ==
|
||||||
|
Modification::DepthStencilMode::kFloat24Truncating) {
|
||||||
|
// Simplified conversion, always less than or equal to the original value -
|
||||||
|
// just drop the lower bits.
|
||||||
|
// The float32 exponent bias is 127.
|
||||||
|
// After saturating, the exponent range is -127...0.
|
||||||
|
// The smallest normalized 20e4 exponent is -14 - should drop 3 mantissa
|
||||||
|
// bits at -14 or above.
|
||||||
|
// The smallest denormalized 20e4 number is -34 - should drop 23 mantissa
|
||||||
|
// bits at -34.
|
||||||
|
// Anything smaller than 2^-34 becomes 0.
|
||||||
|
DxbcDest truncate_dest(writes_depth() ? DxbcDest::ODepth()
|
||||||
|
: DxbcDest::ODepthLE());
|
||||||
|
// Check if the number is representable as a float24 after truncation - the
|
||||||
|
// exponent is at least -34.
|
||||||
|
DxbcOpUGE(temp_y_dest, temp_x_src, DxbcSrc::LU(0x2E800000));
|
||||||
|
DxbcOpIf(true, temp_y_src);
|
||||||
|
{
|
||||||
|
// Extract the biased float32 exponent to temp.y.
|
||||||
|
// temp.y = 113+ at exponent -14+.
|
||||||
|
// temp.y = 93 at exponent -34.
|
||||||
|
DxbcOpUBFE(temp_y_dest, DxbcSrc::LU(8), DxbcSrc::LU(23), temp_x_src);
|
||||||
|
// Convert exponent to the unclamped number of bits to truncate.
|
||||||
|
// 116 - 113 = 3.
|
||||||
|
// 116 - 93 = 23.
|
||||||
|
// temp.y = 3+ at exponent -14+.
|
||||||
|
// temp.y = 23 at exponent -34.
|
||||||
|
DxbcOpIAdd(temp_y_dest, DxbcSrc::LI(116), -temp_y_src);
|
||||||
|
// Clamp the truncated bit count to drop 3 bits of any normal number.
|
||||||
|
// Exponents below -34 are handled separately.
|
||||||
|
// temp.y = 3 at exponent -14.
|
||||||
|
// temp.y = 23 at exponent -34.
|
||||||
|
DxbcOpIMax(temp_y_dest, temp_y_src, DxbcSrc::LI(3));
|
||||||
|
// Truncate the mantissa - fill the low bits with zeros.
|
||||||
|
DxbcOpBFI(truncate_dest, temp_y_src, DxbcSrc::LU(0), DxbcSrc::LU(0),
|
||||||
|
temp_x_src);
|
||||||
|
}
|
||||||
|
// The number is not representable as float24 after truncation - zero.
|
||||||
|
DxbcOpElse();
|
||||||
|
DxbcOpMov(truncate_dest, DxbcSrc::LF(0.0f));
|
||||||
|
// Close the non-zero result check.
|
||||||
|
DxbcOpEndIf();
|
||||||
|
} else {
|
||||||
|
// Properly convert to 20e4, with rounding to the nearest even.
|
||||||
|
PreClampedDepthTo20e4(temp, 0, temp, 0, temp, 1);
|
||||||
|
// Convert back to float32.
|
||||||
|
// https://github.com/Microsoft/DirectXTex/blob/master/DirectXTex/DirectXTexConvert.cpp
|
||||||
|
// Unpack the exponent to temp.y.
|
||||||
|
DxbcOpUShR(temp_y_dest, temp_x_src, DxbcSrc::LU(20));
|
||||||
|
// Unpack the mantissa to temp.x.
|
||||||
|
DxbcOpAnd(temp_x_dest, temp_x_src, DxbcSrc::LU(0xFFFFF));
|
||||||
|
// Check if the number is denormalized.
|
||||||
|
DxbcOpIf(false, temp_y_src);
|
||||||
|
{
|
||||||
|
// Check if the number is non-zero (if the mantissa isn't zero - the
|
||||||
|
// exponent is known to be zero at this point).
|
||||||
|
DxbcOpIf(true, temp_x_src);
|
||||||
|
{
|
||||||
|
// Normalize the mantissa.
|
||||||
|
// Note that HLSL firstbithigh(x) is compiled to DXBC like:
|
||||||
|
// `x ? 31 - firstbit_hi(x) : -1`
|
||||||
|
// (returns the index from the LSB, not the MSB, but -1 for zero too).
|
||||||
|
// temp.y = firstbit_hi(mantissa)
|
||||||
|
DxbcOpFirstBitHi(temp_y_dest, temp_x_src);
|
||||||
|
// temp.y = 20 - firstbithigh(mantissa)
|
||||||
|
// Or:
|
||||||
|
// temp.y = 20 - (31 - firstbit_hi(mantissa))
|
||||||
|
DxbcOpIAdd(temp_y_dest, temp_y_src, DxbcSrc::LI(20 - 31));
|
||||||
|
// mantissa = mantissa << (20 - firstbithigh(mantissa))
|
||||||
|
// AND 0xFFFFF not needed after this - BFI will do it.
|
||||||
|
DxbcOpIShL(temp_x_dest, temp_x_src, temp_y_src);
|
||||||
|
// Get the normalized exponent.
|
||||||
|
// exponent = 1 - (20 - firstbithigh(mantissa))
|
||||||
|
DxbcOpIAdd(temp_y_dest, DxbcSrc::LI(1), -temp_y_src);
|
||||||
|
}
|
||||||
|
// The number is zero.
|
||||||
|
DxbcOpElse();
|
||||||
|
{
|
||||||
|
// Set the unbiased exponent to -112 for zero - 112 will be added later,
|
||||||
|
// resulting in zero float32.
|
||||||
|
DxbcOpMov(temp_y_dest, DxbcSrc::LI(-112));
|
||||||
|
}
|
||||||
|
// Close the non-zero check.
|
||||||
|
DxbcOpEndIf();
|
||||||
|
}
|
||||||
|
// Close the denormal check.
|
||||||
|
DxbcOpEndIf();
|
||||||
|
// Bias the exponent and move it to the correct location in float32 to
|
||||||
|
// temp.y.
|
||||||
|
DxbcOpIMAd(temp_y_dest, temp_y_src, DxbcSrc::LI(1 << 23),
|
||||||
|
DxbcSrc::LI(112 << 23));
|
||||||
|
// Combine the mantissa and the exponent into the result.
|
||||||
|
DxbcOpBFI(DxbcDest::ODepth(), DxbcSrc::LU(20), DxbcSrc::LU(3), temp_x_src,
|
||||||
|
temp_y_src);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!writes_depth()) {
|
||||||
|
// Release temp.
|
||||||
|
PopSystemTemp();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void DxbcShaderTranslator::CompletePixelShader_ROV_AlphaToMaskSample(
|
void DxbcShaderTranslator::CompletePixelShader_ROV_AlphaToMaskSample(
|
||||||
uint32_t sample_index, float threshold_base, DxbcSrc threshold_offset,
|
uint32_t sample_index, float threshold_base, DxbcSrc threshold_offset,
|
||||||
float threshold_offset_scale, uint32_t temp, uint32_t temp_component) {
|
float threshold_offset_scale, uint32_t temp, uint32_t temp_component) {
|
||||||
|
@ -1957,7 +2117,7 @@ void DxbcShaderTranslator::CompletePixelShader_ROV_AlphaToMask() {
|
||||||
// floating-point. With resolution scaling, still using host pixels, to
|
// floating-point. With resolution scaling, still using host pixels, to
|
||||||
// preserve the idea of dithering.
|
// preserve the idea of dithering.
|
||||||
// temp.x = alpha to coverage offset as float 0.0...3.0.
|
// temp.x = alpha to coverage offset as float 0.0...3.0.
|
||||||
in_position_xy_used_ = true;
|
in_position_used_ |= 0b0011;
|
||||||
DxbcOpFToU(DxbcDest::R(temp, 0b0011),
|
DxbcOpFToU(DxbcDest::R(temp, 0b0011),
|
||||||
DxbcSrc::V(uint32_t(InOutRegister::kPSInPosition)));
|
DxbcSrc::V(uint32_t(InOutRegister::kPSInPosition)));
|
||||||
DxbcOpAnd(DxbcDest::R(temp, 0b0010), DxbcSrc::R(temp, DxbcSrc::kYYYY),
|
DxbcOpAnd(DxbcDest::R(temp, 0b0010), DxbcSrc::R(temp, DxbcSrc::kYYYY),
|
||||||
|
@ -2067,7 +2227,7 @@ void DxbcShaderTranslator::CompletePixelShader_WriteToROV() {
|
||||||
DxbcOpStoreUAVTyped(
|
DxbcOpStoreUAVTyped(
|
||||||
DxbcDest::U(uav_index_edram_, uint32_t(UAVRegister::kEdram)),
|
DxbcDest::U(uav_index_edram_, uint32_t(UAVRegister::kEdram)),
|
||||||
DxbcSrc::R(system_temp_rov_params_, DxbcSrc::kYYYY), 1,
|
DxbcSrc::R(system_temp_rov_params_, DxbcSrc::kYYYY), 1,
|
||||||
DxbcSrc::R(system_temp_rov_depth_stencil_).Select(i));
|
DxbcSrc::R(system_temp_depth_stencil_).Select(i));
|
||||||
}
|
}
|
||||||
// Close the write check.
|
// Close the write check.
|
||||||
DxbcOpEndIf();
|
DxbcOpEndIf();
|
||||||
|
@ -3059,15 +3219,16 @@ void DxbcShaderTranslator::CompletePixelShader() {
|
||||||
CompletePixelShader_WriteToROV();
|
CompletePixelShader_WriteToROV();
|
||||||
} else {
|
} else {
|
||||||
CompletePixelShader_WriteToRTVs();
|
CompletePixelShader_WriteToRTVs();
|
||||||
|
CompletePixelShader_DSV_DepthTo24Bit();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void DxbcShaderTranslator::ROV_DepthTo24Bit(uint32_t d24_temp,
|
void DxbcShaderTranslator::PreClampedDepthTo20e4(uint32_t d24_temp,
|
||||||
uint32_t d24_temp_component,
|
uint32_t d24_temp_component,
|
||||||
uint32_t d32_temp,
|
uint32_t d32_temp,
|
||||||
uint32_t d32_temp_component,
|
uint32_t d32_temp_component,
|
||||||
uint32_t temp_temp,
|
uint32_t temp_temp,
|
||||||
uint32_t temp_temp_component) {
|
uint32_t temp_temp_component) {
|
||||||
assert_true(temp_temp != d24_temp ||
|
assert_true(temp_temp != d24_temp ||
|
||||||
temp_temp_component != d24_temp_component);
|
temp_temp_component != d24_temp_component);
|
||||||
assert_true(temp_temp != d32_temp ||
|
assert_true(temp_temp != d32_temp ||
|
||||||
|
@ -3079,68 +3240,83 @@ void DxbcShaderTranslator::ROV_DepthTo24Bit(uint32_t d24_temp,
|
||||||
DxbcDest temp_dest(DxbcDest::R(temp_temp, 1 << temp_temp_component));
|
DxbcDest temp_dest(DxbcDest::R(temp_temp, 1 << temp_temp_component));
|
||||||
DxbcSrc temp_src(DxbcSrc::R(temp_temp).Select(temp_temp_component));
|
DxbcSrc temp_src(DxbcSrc::R(temp_temp).Select(temp_temp_component));
|
||||||
|
|
||||||
|
// CFloat24 from d3dref9.dll.
|
||||||
|
// Assuming the depth is already clamped to [0, 2) (in all places, the depth
|
||||||
|
// is written with the saturate flag set).
|
||||||
|
|
||||||
|
// Check if the number is too small to be represented as normalized 20e4.
|
||||||
|
// temp = f32 < 2^-14
|
||||||
|
DxbcOpULT(temp_dest, d32_src, DxbcSrc::LU(0x38800000));
|
||||||
|
// Handle denormalized numbers separately.
|
||||||
|
DxbcOpIf(true, temp_src);
|
||||||
|
{
|
||||||
|
// temp = f32 >> 23
|
||||||
|
DxbcOpUShR(temp_dest, d32_src, DxbcSrc::LU(23));
|
||||||
|
// temp = 113 - (f32 >> 23)
|
||||||
|
DxbcOpIAdd(temp_dest, DxbcSrc::LI(113), -temp_src);
|
||||||
|
// Don't allow the shift to overflow, since in DXBC the lower 5 bits of the
|
||||||
|
// shift amount are used (otherwise 0 becomes 8).
|
||||||
|
// temp = min(113 - (f32 >> 23), 24)
|
||||||
|
DxbcOpUMin(temp_dest, temp_src, DxbcSrc::LU(24));
|
||||||
|
// biased_f32 = (f32 & 0x7FFFFF) | 0x800000
|
||||||
|
DxbcOpBFI(d24_dest, DxbcSrc::LU(9), DxbcSrc::LU(23), DxbcSrc::LU(1),
|
||||||
|
d32_src);
|
||||||
|
// biased_f32 = ((f32 & 0x7FFFFF) | 0x800000) >> min(113 - (f32 >> 23), 24)
|
||||||
|
DxbcOpUShR(d24_dest, d24_src, temp_src);
|
||||||
|
}
|
||||||
|
// Not denormalized?
|
||||||
|
DxbcOpElse();
|
||||||
|
{
|
||||||
|
// Bias the exponent.
|
||||||
|
// biased_f32 = f32 + (-112 << 23)
|
||||||
|
// (left shift of a negative value is undefined behavior)
|
||||||
|
DxbcOpIAdd(d24_dest, d32_src, DxbcSrc::LU(0xC8000000u));
|
||||||
|
}
|
||||||
|
// Close the denormal check.
|
||||||
|
DxbcOpEndIf();
|
||||||
|
// Build the 20e4 number.
|
||||||
|
// temp = (biased_f32 >> 3) & 1
|
||||||
|
DxbcOpUBFE(temp_dest, DxbcSrc::LU(1), DxbcSrc::LU(3), d24_src);
|
||||||
|
// f24 = biased_f32 + 3
|
||||||
|
DxbcOpIAdd(d24_dest, d24_src, DxbcSrc::LU(3));
|
||||||
|
// f24 = biased_f32 + 3 + ((biased_f32 >> 3) & 1)
|
||||||
|
DxbcOpIAdd(d24_dest, d24_src, temp_src);
|
||||||
|
// f24 = ((biased_f32 + 3 + ((biased_f32 >> 3) & 1)) >> 3) & 0xFFFFFF
|
||||||
|
DxbcOpUBFE(d24_dest, DxbcSrc::LU(24), DxbcSrc::LU(3), d24_src);
|
||||||
|
}
|
||||||
|
|
||||||
|
void DxbcShaderTranslator::ROV_DepthTo24Bit(uint32_t d24_temp,
|
||||||
|
uint32_t d24_temp_component,
|
||||||
|
uint32_t d32_temp,
|
||||||
|
uint32_t d32_temp_component,
|
||||||
|
uint32_t temp_temp,
|
||||||
|
uint32_t temp_temp_component) {
|
||||||
|
assert_true(temp_temp != d32_temp ||
|
||||||
|
temp_temp_component != d32_temp_component);
|
||||||
|
// Source and destination may be the same.
|
||||||
|
|
||||||
system_constants_used_ |= 1ull << kSysConst_Flags_Index;
|
system_constants_used_ |= 1ull << kSysConst_Flags_Index;
|
||||||
DxbcOpAnd(temp_dest,
|
DxbcOpAnd(DxbcDest::R(temp_temp, 1 << temp_temp_component),
|
||||||
DxbcSrc::CB(cbuffer_index_system_constants_,
|
DxbcSrc::CB(cbuffer_index_system_constants_,
|
||||||
uint32_t(CbufferRegister::kSystemConstants),
|
uint32_t(CbufferRegister::kSystemConstants),
|
||||||
kSysConst_Flags_Vec)
|
kSysConst_Flags_Vec)
|
||||||
.Select(kSysConst_Flags_Comp),
|
.Select(kSysConst_Flags_Comp),
|
||||||
DxbcSrc::LU(kSysFlag_ROVDepthFloat24));
|
DxbcSrc::LU(kSysFlag_ROVDepthFloat24));
|
||||||
// Convert according to the format.
|
// Convert according to the format.
|
||||||
DxbcOpIf(true, temp_src);
|
DxbcOpIf(true, DxbcSrc::R(temp_temp).Select(temp_temp_component));
|
||||||
{
|
{
|
||||||
// 20e4 conversion, using 1 VGPR.
|
// 20e4 conversion.
|
||||||
// CFloat24 from d3dref9.dll.
|
PreClampedDepthTo20e4(d24_temp, d24_temp_component, d32_temp,
|
||||||
// Assuming the depth is already clamped to [0, 2) (in all places, the depth
|
d32_temp_component, temp_temp, temp_temp_component);
|
||||||
// is written with the saturate flag set).
|
|
||||||
|
|
||||||
// Check if the number is too small to be represented as normalized 20e4.
|
|
||||||
// temp = f32 < 2^-14
|
|
||||||
DxbcOpULT(temp_dest, d32_src, DxbcSrc::LU(0x38800000));
|
|
||||||
// Handle denormalized numbers separately.
|
|
||||||
DxbcOpIf(true, temp_src);
|
|
||||||
{
|
|
||||||
// temp = f32 >> 23
|
|
||||||
DxbcOpUShR(temp_dest, d32_src, DxbcSrc::LU(23));
|
|
||||||
// temp = 113 - (f32 >> 23)
|
|
||||||
DxbcOpIAdd(temp_dest, DxbcSrc::LI(113), -temp_src);
|
|
||||||
// Don't allow the shift to overflow, since in DXBC the lower 5 bits of
|
|
||||||
// the shift amount are used (otherwise 0 becomes 8).
|
|
||||||
// temp = min(113 - (f32 >> 23), 24)
|
|
||||||
DxbcOpUMin(temp_dest, temp_src, DxbcSrc::LU(24));
|
|
||||||
// biased_f32 = (f32 & 0x7FFFFF) | 0x800000
|
|
||||||
DxbcOpBFI(d24_dest, DxbcSrc::LU(9), DxbcSrc::LU(23), DxbcSrc::LU(1),
|
|
||||||
d32_src);
|
|
||||||
// biased_f32 =
|
|
||||||
// ((f32 & 0x7FFFFF) | 0x800000) >> min(113 - (f32 >> 23), 24)
|
|
||||||
DxbcOpUShR(d24_dest, d24_src, temp_src);
|
|
||||||
}
|
|
||||||
// Not denormalized?
|
|
||||||
DxbcOpElse();
|
|
||||||
{
|
|
||||||
// Bias the exponent.
|
|
||||||
// biased_f32 = f32 + (-112 << 23)
|
|
||||||
// (left shift of a negative value is undefined behavior)
|
|
||||||
DxbcOpIAdd(d24_dest, d32_src, DxbcSrc::LU(0xC8000000u));
|
|
||||||
}
|
|
||||||
// Close the denormal check.
|
|
||||||
DxbcOpEndIf();
|
|
||||||
// Build the 20e4 number.
|
|
||||||
// temp = (biased_f32 >> 3) & 1
|
|
||||||
DxbcOpUBFE(temp_dest, DxbcSrc::LU(1), DxbcSrc::LU(3), d24_src);
|
|
||||||
// f24 = biased_f32 + 3
|
|
||||||
DxbcOpIAdd(d24_dest, d24_src, DxbcSrc::LU(3));
|
|
||||||
// f24 = biased_f32 + 3 + ((biased_f32 >> 3) & 1)
|
|
||||||
DxbcOpIAdd(d24_dest, d24_src, temp_src);
|
|
||||||
// f24 = ((biased_f32 + 3 + ((biased_f32 >> 3) & 1)) >> 3) & 0xFFFFFF
|
|
||||||
DxbcOpUBFE(d24_dest, DxbcSrc::LU(24), DxbcSrc::LU(3), d24_src);
|
|
||||||
}
|
}
|
||||||
DxbcOpElse();
|
DxbcOpElse();
|
||||||
{
|
{
|
||||||
// Unorm24 conversion.
|
// Unorm24 conversion.
|
||||||
|
DxbcDest d24_dest(DxbcDest::R(d24_temp, 1 << d24_temp_component));
|
||||||
|
DxbcSrc d24_src(DxbcSrc::R(d24_temp).Select(d24_temp_component));
|
||||||
// Multiply by float(0xFFFFFF).
|
// Multiply by float(0xFFFFFF).
|
||||||
DxbcOpMul(d24_dest, d32_src, DxbcSrc::LF(16777215.0f));
|
DxbcOpMul(d24_dest, DxbcSrc::R(d32_temp).Select(d32_temp_component),
|
||||||
|
DxbcSrc::LF(16777215.0f));
|
||||||
// Round to the nearest even integer. This seems to be the correct way:
|
// Round to the nearest even integer. This seems to be the correct way:
|
||||||
// rounding towards zero gives 0xFF instead of 0x100 in clear shaders in,
|
// rounding towards zero gives 0xFF instead of 0x100 in clear shaders in,
|
||||||
// for instance, Halo 3, but other clear shaders in it are also broken if
|
// for instance, Halo 3, but other clear shaders in it are also broken if
|
||||||
|
|
|
@ -40,9 +40,63 @@ DEFINE_bool(
|
||||||
"be fully covered when MSAA is used with fullscreen passes.",
|
"be fully covered when MSAA is used with fullscreen passes.",
|
||||||
"GPU");
|
"GPU");
|
||||||
|
|
||||||
|
DEFINE_string(
|
||||||
|
depth_float24_conversion, "",
|
||||||
|
"Method for converting 32-bit Z values to 20e4 floating point when using "
|
||||||
|
"host depth buffers without native 20e4 support (when not using rasterizer-"
|
||||||
|
"ordered views / fragment shader interlocks to perform depth testing "
|
||||||
|
"manually).\n"
|
||||||
|
"Use: [any, on_copy, truncate, round]\n"
|
||||||
|
" on_copy:\n"
|
||||||
|
" Do depth testing at host precision, converting when copying between "
|
||||||
|
"host depth buffers and the EDRAM buffer to support reinterpretation, "
|
||||||
|
"maintaining two copies, in both host and 20e4 formats, for reloading data "
|
||||||
|
"to host depth buffers when it wasn't overwritten.\n"
|
||||||
|
" + Highest performance, allows early depth test and writing.\n"
|
||||||
|
" + Host MSAA is possible with pixel-rate shading where supported.\n"
|
||||||
|
" - EDRAM > RAM > EDRAM depth buffer round trip done in certain games "
|
||||||
|
"(such as GTA IV) destroys precision irreparably, causing artifacts if "
|
||||||
|
"another rendering pass is done after the EDRAM reupload.\n"
|
||||||
|
" truncate:\n"
|
||||||
|
" Convert to 20e4 directly in pixel shaders, always rounding down.\n"
|
||||||
|
" + Good performance, conservative early depth test is possible.\n"
|
||||||
|
" + No precision loss when anything changes in the storage of the depth "
|
||||||
|
"buffer, EDRAM > RAM > EDRAM copying preserves precision.\n"
|
||||||
|
" - Rounding mode is incorrect, sometimes giving results smaller than "
|
||||||
|
"they should be - may cause inaccuracy especially in edge cases when the "
|
||||||
|
"game wants to write an exact value.\n"
|
||||||
|
" - Host MSAA is only possible at SSAA speed, with per-sample shading.\n"
|
||||||
|
" round:\n"
|
||||||
|
" Convert to 20e4 directly in pixel shaders, correctly rounding to the "
|
||||||
|
"nearest even.\n"
|
||||||
|
" + Highest accuracy.\n"
|
||||||
|
" - Significantly limited performance, early depth test is not possible.\n"
|
||||||
|
" - Host MSAA is only possible at SSAA speed, with per-sample shading.\n"
|
||||||
|
" Any other value:\n"
|
||||||
|
" Choose what is considered the most optimal (currently \"on_copy\").",
|
||||||
|
"GPU");
|
||||||
|
|
||||||
DEFINE_int32(query_occlusion_fake_sample_count, 1000,
|
DEFINE_int32(query_occlusion_fake_sample_count, 1000,
|
||||||
"If set to -1 no sample counts are written, games may hang. Else, "
|
"If set to -1 no sample counts are written, games may hang. Else, "
|
||||||
"the sample count of every tile will be incremented on every "
|
"the sample count of every tile will be incremented on every "
|
||||||
"EVENT_WRITE_ZPD by this number. Setting this to 0 means "
|
"EVENT_WRITE_ZPD by this number. Setting this to 0 means "
|
||||||
"everything is reported as occluded.",
|
"everything is reported as occluded.",
|
||||||
"GPU");
|
"GPU");
|
||||||
|
|
||||||
|
namespace xe {
|
||||||
|
namespace gpu {
|
||||||
|
namespace flags {
|
||||||
|
|
||||||
|
DepthFloat24Conversion GetDepthFloat24Conversion() {
|
||||||
|
if (cvars::depth_float24_conversion == "truncate") {
|
||||||
|
return DepthFloat24Conversion::kOnOutputTruncating;
|
||||||
|
}
|
||||||
|
if (cvars::depth_float24_conversion == "round") {
|
||||||
|
return DepthFloat24Conversion::kOnOutputRounding;
|
||||||
|
}
|
||||||
|
return DepthFloat24Conversion::kOnCopy;
|
||||||
|
}
|
||||||
|
|
||||||
|
} // namespace flags
|
||||||
|
} // namespace gpu
|
||||||
|
} // namespace xe
|
||||||
|
|
|
@ -22,6 +22,69 @@ DECLARE_bool(gpu_allow_invalid_fetch_constants);
|
||||||
|
|
||||||
DECLARE_bool(half_pixel_offset);
|
DECLARE_bool(half_pixel_offset);
|
||||||
|
|
||||||
|
DECLARE_string(depth_float24_conversion);
|
||||||
|
|
||||||
DECLARE_int32(query_occlusion_fake_sample_count);
|
DECLARE_int32(query_occlusion_fake_sample_count);
|
||||||
|
|
||||||
|
namespace xe {
|
||||||
|
namespace gpu {
|
||||||
|
namespace flags {
|
||||||
|
|
||||||
|
enum class DepthFloat24Conversion {
|
||||||
|
// Doing depth test at the host precision, converting to 20e4 to support
|
||||||
|
// reinterpretation, but keeping a separate EDRAM view containing depth values
|
||||||
|
// in the host format. When copying from the EDRAM buffer to host depth
|
||||||
|
// buffers, writing the stored host pixel if stored_f24 == to_f24(stored_host)
|
||||||
|
// (otherwise it was overwritten by something else, like clearing, or a color
|
||||||
|
// buffer; this is inexact though, and will incorrectly load pixels that were
|
||||||
|
// overwritten by something else in the EDRAM, but turned out to have the same
|
||||||
|
// value on the guest as before - an outdated host-precision value will be
|
||||||
|
// loaded in these cases instead).
|
||||||
|
//
|
||||||
|
// EDRAM > RAM, then reusing the EDRAM region for something else > EDRAM round
|
||||||
|
// trip destroys precision beyond repair.
|
||||||
|
//
|
||||||
|
// Full host early Z and MSAA with pixel-rate shading are supported.
|
||||||
|
kOnCopy,
|
||||||
|
// Converting the depth to the closest host value representable exactly as a
|
||||||
|
// 20e4 float in pixel shaders, to support invariance in cases when the guest
|
||||||
|
// reuploads a previously resolved depth buffer to the EDRAM, rounding towards
|
||||||
|
// zero (which contradicts the rounding used by the Direct3D 9 reference
|
||||||
|
// rasterizer, but allows less-than-or-equal pixel shader depth output to be
|
||||||
|
// used to preserve most of early Z culling when the game is using reversed
|
||||||
|
// depth, which is the usual way of doing depth testing on the Xbox 360 and of
|
||||||
|
// utilizing the advantages of a floating-point encoding).
|
||||||
|
//
|
||||||
|
// With MSAA, pixel shaders must run at sample frequency - otherwise, if the
|
||||||
|
// depth is the same for the entire pixel, intersections of polygons cannot be
|
||||||
|
// antialiased.
|
||||||
|
//
|
||||||
|
// Important usage note: When using this mode, bounds of the fixed-function
|
||||||
|
// viewport must be converted to and back from float24 too (preferably using
|
||||||
|
// correct rounding to the nearest even, to reduce the error already caused by
|
||||||
|
// truncation rather than to amplify it). This ensures that clamping to the
|
||||||
|
// viewport bounds, which happens after the pixel shader even if it overwrites
|
||||||
|
// the resulting depth, is never done to a value not representable as float24
|
||||||
|
// (for example, if the minimum Z is a number too small to be represented as
|
||||||
|
// float24, but not zero, it won't be possible to write what should become
|
||||||
|
// 0x000000 to the depth buffer). Note that this may add some error to the
|
||||||
|
// depth values from the rasterizer; however, modifying Z in the vertex shader
|
||||||
|
// to make interpolated depth values would cause clipping to be done to
|
||||||
|
// different bounds, which may be more undesirable, especially in cases when Z
|
||||||
|
// is explicitly set to a value like 0 or W (in such cases, the adjusted
|
||||||
|
// polygon may go outside 0...W in clip space and disappear).
|
||||||
|
kOnOutputTruncating,
|
||||||
|
// Similar to kOnOutputTruncating, but rounding to the nearest even, more
|
||||||
|
// correctly, however, because the resulting depth can be bigger than the
|
||||||
|
// original host value, early depth testing can't be used at all. Same
|
||||||
|
// viewport usage rules apply.
|
||||||
|
kOnOutputRounding,
|
||||||
|
};
|
||||||
|
|
||||||
|
DepthFloat24Conversion GetDepthFloat24Conversion();
|
||||||
|
|
||||||
|
} // namespace flags
|
||||||
|
} // namespace gpu
|
||||||
|
} // namespace xe
|
||||||
|
|
||||||
#endif // XENIA_GPU_GPU_FLAGS_H_
|
#endif // XENIA_GPU_GPU_FLAGS_H_
|
||||||
|
|
|
@ -276,8 +276,7 @@ void GraphicsSystem::ClearCaches() {
|
||||||
}
|
}
|
||||||
|
|
||||||
void GraphicsSystem::InitializeShaderStorage(
|
void GraphicsSystem::InitializeShaderStorage(
|
||||||
const std::filesystem::path& storage_root, uint32_t title_id,
|
const std::filesystem::path& cache_root, uint32_t title_id, bool blocking) {
|
||||||
bool blocking) {
|
|
||||||
if (!cvars::store_shaders) {
|
if (!cvars::store_shaders) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
@ -285,21 +284,18 @@ void GraphicsSystem::InitializeShaderStorage(
|
||||||
if (command_processor_->is_paused()) {
|
if (command_processor_->is_paused()) {
|
||||||
// Safe to run on any thread while the command processor is paused, no
|
// Safe to run on any thread while the command processor is paused, no
|
||||||
// race condition.
|
// race condition.
|
||||||
command_processor_->InitializeShaderStorage(storage_root, title_id, true);
|
command_processor_->InitializeShaderStorage(cache_root, title_id, true);
|
||||||
} else {
|
} else {
|
||||||
xe::threading::Fence fence;
|
xe::threading::Fence fence;
|
||||||
command_processor_->CallInThread(
|
command_processor_->CallInThread([this, cache_root, title_id, &fence]() {
|
||||||
[this, storage_root, title_id, &fence]() {
|
command_processor_->InitializeShaderStorage(cache_root, title_id, true);
|
||||||
command_processor_->InitializeShaderStorage(storage_root, title_id,
|
fence.Signal();
|
||||||
true);
|
});
|
||||||
fence.Signal();
|
|
||||||
});
|
|
||||||
fence.Wait();
|
fence.Wait();
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
command_processor_->CallInThread([this, storage_root, title_id]() {
|
command_processor_->CallInThread([this, cache_root, title_id]() {
|
||||||
command_processor_->InitializeShaderStorage(storage_root, title_id,
|
command_processor_->InitializeShaderStorage(cache_root, title_id, false);
|
||||||
false);
|
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -63,7 +63,7 @@ class GraphicsSystem {
|
||||||
|
|
||||||
virtual void ClearCaches();
|
virtual void ClearCaches();
|
||||||
|
|
||||||
void InitializeShaderStorage(const std::filesystem::path& storage_root,
|
void InitializeShaderStorage(const std::filesystem::path& cache_root,
|
||||||
uint32_t title_id, bool blocking);
|
uint32_t title_id, bool blocking);
|
||||||
|
|
||||||
void RequestFrameTrace();
|
void RequestFrameTrace();
|
||||||
|
|
|
@ -31,9 +31,13 @@ Shader::Shader(xenos::ShaderType shader_type, uint64_t ucode_data_hash,
|
||||||
xe::copy_and_swap(ucode_data_.data(), ucode_dwords, ucode_dword_count);
|
xe::copy_and_swap(ucode_data_.data(), ucode_dwords, ucode_dword_count);
|
||||||
}
|
}
|
||||||
|
|
||||||
Shader::~Shader() = default;
|
Shader::~Shader() {
|
||||||
|
for (auto it : translations_) {
|
||||||
|
delete it.second;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
std::string Shader::GetTranslatedBinaryString() const {
|
std::string Shader::Translation::GetTranslatedBinaryString() const {
|
||||||
std::string result;
|
std::string result;
|
||||||
result.resize(translated_binary_.size());
|
result.resize(translated_binary_.size());
|
||||||
std::memcpy(const_cast<char*>(result.data()), translated_binary_.data(),
|
std::memcpy(const_cast<char*>(result.data()), translated_binary_.data(),
|
||||||
|
@ -41,36 +45,24 @@ std::string Shader::GetTranslatedBinaryString() const {
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::pair<std::filesystem::path, std::filesystem::path> Shader::Dump(
|
std::filesystem::path Shader::Translation::Dump(
|
||||||
const std::filesystem::path& base_path, const char* path_prefix) {
|
const std::filesystem::path& base_path, const char* path_prefix) {
|
||||||
|
std::filesystem::path path = base_path;
|
||||||
// Ensure target path exists.
|
// Ensure target path exists.
|
||||||
auto target_path = base_path;
|
if (!path.empty()) {
|
||||||
if (!target_path.empty()) {
|
path = std::filesystem::absolute(path);
|
||||||
target_path = std::filesystem::absolute(target_path);
|
std::filesystem::create_directories(path);
|
||||||
std::filesystem::create_directories(target_path);
|
|
||||||
}
|
}
|
||||||
|
path = path /
|
||||||
auto base_name =
|
fmt::format(
|
||||||
fmt::format("shader_{}_{:016X}", path_prefix, ucode_data_hash_);
|
"shader_{:016X}_{:08X}.{}.{}", shader().ucode_data_hash(),
|
||||||
|
modification(), path_prefix,
|
||||||
std::string txt_name, bin_name;
|
shader().type() == xenos::ShaderType::kVertex ? "vert" : "frag");
|
||||||
if (shader_type_ == xenos::ShaderType::kVertex) {
|
FILE* f = filesystem::OpenFile(path, "wb");
|
||||||
txt_name = base_name + ".vert";
|
|
||||||
bin_name = base_name + ".bin.vert";
|
|
||||||
} else {
|
|
||||||
txt_name = base_name + ".frag";
|
|
||||||
bin_name = base_name + ".bin.frag";
|
|
||||||
}
|
|
||||||
|
|
||||||
std::filesystem::path txt_path, bin_path;
|
|
||||||
txt_path = base_path / txt_name;
|
|
||||||
bin_path = base_path / bin_name;
|
|
||||||
|
|
||||||
FILE* f = filesystem::OpenFile(txt_path, "wb");
|
|
||||||
if (f) {
|
if (f) {
|
||||||
fwrite(translated_binary_.data(), 1, translated_binary_.size(), f);
|
fwrite(translated_binary_.data(), 1, translated_binary_.size(), f);
|
||||||
fprintf(f, "\n\n");
|
fprintf(f, "\n\n");
|
||||||
auto ucode_disasm_ptr = ucode_disassembly().c_str();
|
auto ucode_disasm_ptr = shader().ucode_disassembly().c_str();
|
||||||
while (*ucode_disasm_ptr) {
|
while (*ucode_disasm_ptr) {
|
||||||
auto line_end = std::strchr(ucode_disasm_ptr, '\n');
|
auto line_end = std::strchr(ucode_disasm_ptr, '\n');
|
||||||
fprintf(f, "// ");
|
fprintf(f, "// ");
|
||||||
|
@ -83,14 +75,58 @@ std::pair<std::filesystem::path, std::filesystem::path> Shader::Dump(
|
||||||
}
|
}
|
||||||
fclose(f);
|
fclose(f);
|
||||||
}
|
}
|
||||||
|
return std::move(path);
|
||||||
|
}
|
||||||
|
|
||||||
f = filesystem::OpenFile(bin_path, "wb");
|
Shader::Translation* Shader::GetOrCreateTranslation(uint32_t modification,
|
||||||
|
bool* is_new) {
|
||||||
|
auto it = translations_.find(modification);
|
||||||
|
if (it != translations_.end()) {
|
||||||
|
if (is_new) {
|
||||||
|
*is_new = false;
|
||||||
|
}
|
||||||
|
return it->second;
|
||||||
|
}
|
||||||
|
Translation* translation = CreateTranslationInstance(modification);
|
||||||
|
translations_.emplace(modification, translation);
|
||||||
|
if (is_new) {
|
||||||
|
*is_new = true;
|
||||||
|
}
|
||||||
|
return translation;
|
||||||
|
}
|
||||||
|
|
||||||
|
void Shader::DestroyTranslation(uint32_t modification) {
|
||||||
|
auto it = translations_.find(modification);
|
||||||
|
if (it == translations_.end()) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
delete it->second;
|
||||||
|
translations_.erase(it);
|
||||||
|
}
|
||||||
|
|
||||||
|
std::filesystem::path Shader::DumpUcodeBinary(
|
||||||
|
const std::filesystem::path& base_path) {
|
||||||
|
// Ensure target path exists.
|
||||||
|
std::filesystem::path path = base_path;
|
||||||
|
if (!path.empty()) {
|
||||||
|
path = std::filesystem::absolute(path);
|
||||||
|
std::filesystem::create_directories(path);
|
||||||
|
}
|
||||||
|
path = path /
|
||||||
|
fmt::format("shader_{:016X}.ucode.bin.{}", ucode_data_hash(),
|
||||||
|
type() == xenos::ShaderType::kVertex ? "vert" : "frag");
|
||||||
|
|
||||||
|
FILE* f = filesystem::OpenFile(path, "wb");
|
||||||
if (f) {
|
if (f) {
|
||||||
fwrite(ucode_data_.data(), 4, ucode_data_.size(), f);
|
fwrite(ucode_data().data(), 4, ucode_data().size(), f);
|
||||||
fclose(f);
|
fclose(f);
|
||||||
}
|
}
|
||||||
|
return std::move(path);
|
||||||
|
}
|
||||||
|
|
||||||
return {std::move(txt_path), std::move(bin_path)};
|
Shader::Translation* Shader::CreateTranslationInstance(uint32_t modification) {
|
||||||
|
// Default implementation for simple cases like ucode disassembly.
|
||||||
|
return new Translation(*this, modification);
|
||||||
}
|
}
|
||||||
|
|
||||||
} // namespace gpu
|
} // namespace gpu
|
||||||
|
|
|
@ -11,8 +11,12 @@
|
||||||
#define XENIA_GPU_SHADER_H_
|
#define XENIA_GPU_SHADER_H_
|
||||||
|
|
||||||
#include <algorithm>
|
#include <algorithm>
|
||||||
|
#include <atomic>
|
||||||
|
#include <cstdint>
|
||||||
#include <filesystem>
|
#include <filesystem>
|
||||||
#include <string>
|
#include <string>
|
||||||
|
#include <unordered_map>
|
||||||
|
#include <utility>
|
||||||
#include <vector>
|
#include <vector>
|
||||||
|
|
||||||
#include "xenia/base/math.h"
|
#include "xenia/base/math.h"
|
||||||
|
@ -591,6 +595,8 @@ struct ParsedAluInstruction {
|
||||||
|
|
||||||
class Shader {
|
class Shader {
|
||||||
public:
|
public:
|
||||||
|
// Type of the vertex shader in a D3D11-like rendering pipeline - shader
|
||||||
|
// interface depends on in, so it must be known at translation time.
|
||||||
// If values are changed, INVALIDATE SHADER STORAGES (increase their version
|
// If values are changed, INVALIDATE SHADER STORAGES (increase their version
|
||||||
// constexpr) where those are stored! And check bit count where this is
|
// constexpr) where those are stored! And check bit count where this is
|
||||||
// packed. This is : uint32_t for simplicity of packing in bit fields.
|
// packed. This is : uint32_t for simplicity of packing in bit fields.
|
||||||
|
@ -603,6 +609,8 @@ class Shader {
|
||||||
kQuadDomainCPIndexed,
|
kQuadDomainCPIndexed,
|
||||||
kQuadDomainPatchIndexed,
|
kQuadDomainPatchIndexed,
|
||||||
};
|
};
|
||||||
|
// For packing HostVertexShaderType in bit fields.
|
||||||
|
static constexpr uint32_t kHostVertexShaderTypeBitCount = 3;
|
||||||
|
|
||||||
struct Error {
|
struct Error {
|
||||||
bool is_fatal = false;
|
bool is_fatal = false;
|
||||||
|
@ -683,6 +691,67 @@ class Shader {
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
class Translation {
|
||||||
|
public:
|
||||||
|
virtual ~Translation() {}
|
||||||
|
|
||||||
|
Shader& shader() const { return shader_; }
|
||||||
|
|
||||||
|
// Translator-specific modification bits.
|
||||||
|
uint32_t modification() const { return modification_; }
|
||||||
|
|
||||||
|
// True if the shader was translated and prepared without error.
|
||||||
|
bool is_valid() const { return is_valid_; }
|
||||||
|
|
||||||
|
// True if the shader has already been translated.
|
||||||
|
bool is_translated() const { return is_translated_; }
|
||||||
|
|
||||||
|
// Errors that occurred during translation.
|
||||||
|
const std::vector<Error>& errors() const { return errors_; }
|
||||||
|
|
||||||
|
// Translated shader binary (or text).
|
||||||
|
const std::vector<uint8_t>& translated_binary() const {
|
||||||
|
return translated_binary_;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Gets the translated shader binary as a string.
|
||||||
|
// This is only valid if it is actually text.
|
||||||
|
std::string GetTranslatedBinaryString() const;
|
||||||
|
|
||||||
|
// Disassembly of the translated from the host graphics layer.
|
||||||
|
// May be empty if the host does not support disassembly.
|
||||||
|
const std::string& host_disassembly() const { return host_disassembly_; }
|
||||||
|
|
||||||
|
// In case disassembly depends on the GPU backend, for setting it
|
||||||
|
// externally.
|
||||||
|
void set_host_disassembly(std::string disassembly) {
|
||||||
|
host_disassembly_ = std::move(disassembly);
|
||||||
|
}
|
||||||
|
|
||||||
|
// For dumping after translation. Dumps the shader's disassembled microcode,
|
||||||
|
// translated code, and, if available, translated disassembly, to a file in
|
||||||
|
// the given path based on ucode hash. Returns the name of the written file.
|
||||||
|
std::filesystem::path Dump(const std::filesystem::path& base_path,
|
||||||
|
const char* path_prefix);
|
||||||
|
|
||||||
|
protected:
|
||||||
|
Translation(Shader& shader, uint32_t modification)
|
||||||
|
: shader_(shader), modification_(modification) {}
|
||||||
|
|
||||||
|
private:
|
||||||
|
friend class Shader;
|
||||||
|
friend class ShaderTranslator;
|
||||||
|
|
||||||
|
Shader& shader_;
|
||||||
|
uint32_t modification_;
|
||||||
|
|
||||||
|
bool is_valid_ = false;
|
||||||
|
bool is_translated_ = false;
|
||||||
|
std::vector<Error> errors_;
|
||||||
|
std::vector<uint8_t> translated_binary_;
|
||||||
|
std::string host_disassembly_;
|
||||||
|
};
|
||||||
|
|
||||||
Shader(xenos::ShaderType shader_type, uint64_t ucode_data_hash,
|
Shader(xenos::ShaderType shader_type, uint64_t ucode_data_hash,
|
||||||
const uint32_t* ucode_dwords, size_t ucode_dword_count);
|
const uint32_t* ucode_dwords, size_t ucode_dword_count);
|
||||||
virtual ~Shader();
|
virtual ~Shader();
|
||||||
|
@ -690,19 +759,30 @@ class Shader {
|
||||||
// Whether the shader is identified as a vertex or pixel shader.
|
// Whether the shader is identified as a vertex or pixel shader.
|
||||||
xenos::ShaderType type() const { return shader_type_; }
|
xenos::ShaderType type() const { return shader_type_; }
|
||||||
|
|
||||||
// If this is a vertex shader, and it has been translated, type of the shader
|
|
||||||
// in a D3D11-like rendering pipeline - shader interface depends on in, so it
|
|
||||||
// must be known at translation time.
|
|
||||||
HostVertexShaderType host_vertex_shader_type() const {
|
|
||||||
return host_vertex_shader_type_;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Microcode dwords in host endianness.
|
// Microcode dwords in host endianness.
|
||||||
const std::vector<uint32_t>& ucode_data() const { return ucode_data_; }
|
const std::vector<uint32_t>& ucode_data() const { return ucode_data_; }
|
||||||
uint64_t ucode_data_hash() const { return ucode_data_hash_; }
|
uint64_t ucode_data_hash() const { return ucode_data_hash_; }
|
||||||
const uint32_t* ucode_dwords() const { return ucode_data_.data(); }
|
const uint32_t* ucode_dwords() const { return ucode_data_.data(); }
|
||||||
size_t ucode_dword_count() const { return ucode_data_.size(); }
|
size_t ucode_dword_count() const { return ucode_data_.size(); }
|
||||||
|
|
||||||
|
// Host translations with the specified modification bits. Not thread-safe
|
||||||
|
// with respect to translation creation/destruction.
|
||||||
|
const std::unordered_map<uint32_t, Translation*>& translations() const {
|
||||||
|
return translations_;
|
||||||
|
}
|
||||||
|
Translation* GetTranslation(uint32_t modification) const {
|
||||||
|
auto it = translations_.find(modification);
|
||||||
|
if (it != translations_.cend()) {
|
||||||
|
return it->second;
|
||||||
|
}
|
||||||
|
return nullptr;
|
||||||
|
}
|
||||||
|
Translation* GetOrCreateTranslation(uint32_t modification,
|
||||||
|
bool* is_new = nullptr);
|
||||||
|
// For shader storage loading, to remove a modification in case of translation
|
||||||
|
// failure. Not thread-safe.
|
||||||
|
void DestroyTranslation(uint32_t modification);
|
||||||
|
|
||||||
// All vertex bindings used in the shader.
|
// All vertex bindings used in the shader.
|
||||||
// Valid for vertex shaders only.
|
// Valid for vertex shaders only.
|
||||||
const std::vector<VertexBinding>& vertex_bindings() const {
|
const std::vector<VertexBinding>& vertex_bindings() const {
|
||||||
|
@ -733,73 +813,55 @@ class Shader {
|
||||||
// True if the shader overrides the pixel depth.
|
// True if the shader overrides the pixel depth.
|
||||||
bool writes_depth() const { return writes_depth_; }
|
bool writes_depth() const { return writes_depth_; }
|
||||||
|
|
||||||
// True if Xenia can automatically enable early depth/stencil for the pixel
|
// True if the current shader has any `kill` instructions.
|
||||||
// shader when RB_DEPTHCONTROL EARLY_Z_ENABLE is not set, provided alpha
|
bool kills_pixels() const { return kills_pixels_; }
|
||||||
// testing and alpha to coverage are disabled.
|
|
||||||
bool implicit_early_z_allowed() const { return implicit_early_z_allowed_; }
|
|
||||||
|
|
||||||
// True if the shader was translated and prepared without error.
|
|
||||||
bool is_valid() const { return is_valid_; }
|
|
||||||
|
|
||||||
// True if the shader has already been translated.
|
|
||||||
bool is_translated() const { return is_translated_; }
|
|
||||||
|
|
||||||
// Errors that occurred during translation.
|
|
||||||
const std::vector<Error>& errors() const { return errors_; }
|
|
||||||
|
|
||||||
// Microcode disassembly in D3D format.
|
// Microcode disassembly in D3D format.
|
||||||
const std::string& ucode_disassembly() const { return ucode_disassembly_; }
|
const std::string& ucode_disassembly() const { return ucode_disassembly_; }
|
||||||
|
|
||||||
// Translated shader binary (or text).
|
// An externally managed identifier of the shader storage the microcode of the
|
||||||
const std::vector<uint8_t>& translated_binary() const {
|
// shader was last written to, or was loaded from, to only write the shader
|
||||||
return translated_binary_;
|
// microcode to the storage once. UINT32_MAX by default.
|
||||||
|
uint32_t ucode_storage_index() const { return ucode_storage_index_; }
|
||||||
|
void set_ucode_storage_index(uint32_t storage_index) {
|
||||||
|
ucode_storage_index_ = storage_index;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Gets the translated shader binary as a string.
|
// Dumps the shader's microcode binary to a file in the given path based on
|
||||||
// This is only valid if it is actually text.
|
// ucode hash. Returns the name of the written file. Can be called at any
|
||||||
std::string GetTranslatedBinaryString() const;
|
// time, doesn't require the shader to be translated.
|
||||||
|
std::filesystem::path DumpUcodeBinary(const std::filesystem::path& base_path);
|
||||||
// Disassembly of the translated from the host graphics layer.
|
|
||||||
// May be empty if the host does not support disassembly.
|
|
||||||
const std::string& host_disassembly() const { return host_disassembly_; }
|
|
||||||
// A lot of errors that occurred during preparation of the host shader.
|
|
||||||
const std::string& host_error_log() const { return host_error_log_; }
|
|
||||||
// Host binary that can be saved and reused across runs.
|
|
||||||
// May be empty if the host does not support saving binaries.
|
|
||||||
const std::vector<uint8_t>& host_binary() const { return host_binary_; }
|
|
||||||
|
|
||||||
// Dumps the shader to a file in the given path based on ucode hash.
|
|
||||||
// Both the ucode binary and disassembled and translated shader will be
|
|
||||||
// written.
|
|
||||||
// Returns the filename of the shader and the binary.
|
|
||||||
std::pair<std::filesystem::path, std::filesystem::path> Dump(
|
|
||||||
const std::filesystem::path& base_path, const char* path_prefix);
|
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
friend class ShaderTranslator;
|
friend class ShaderTranslator;
|
||||||
|
|
||||||
|
virtual Translation* CreateTranslationInstance(uint32_t modification);
|
||||||
|
|
||||||
xenos::ShaderType shader_type_;
|
xenos::ShaderType shader_type_;
|
||||||
HostVertexShaderType host_vertex_shader_type_ = HostVertexShaderType::kVertex;
|
|
||||||
std::vector<uint32_t> ucode_data_;
|
std::vector<uint32_t> ucode_data_;
|
||||||
uint64_t ucode_data_hash_;
|
uint64_t ucode_data_hash_;
|
||||||
|
|
||||||
|
// Modification bits -> translation.
|
||||||
|
std::unordered_map<uint32_t, Translation*> translations_;
|
||||||
|
|
||||||
|
// Whether setup of the post-translation parameters (listed below, plus those
|
||||||
|
// specific to the implementation) has been initiated, by any thread. If
|
||||||
|
// translation is performed on multiple threads, only one thread must be
|
||||||
|
// setting this up (other threads would write the same data anyway).
|
||||||
|
std::atomic_flag post_translation_info_set_up_ = ATOMIC_FLAG_INIT;
|
||||||
|
|
||||||
|
// Initialized after the first successful translation (these don't depend on
|
||||||
|
// the host-side modification bits).
|
||||||
|
std::string ucode_disassembly_;
|
||||||
std::vector<VertexBinding> vertex_bindings_;
|
std::vector<VertexBinding> vertex_bindings_;
|
||||||
std::vector<TextureBinding> texture_bindings_;
|
std::vector<TextureBinding> texture_bindings_;
|
||||||
ConstantRegisterMap constant_register_map_ = {0};
|
ConstantRegisterMap constant_register_map_ = {0};
|
||||||
bool writes_color_targets_[4] = {false, false, false, false};
|
bool writes_color_targets_[4] = {false, false, false, false};
|
||||||
bool writes_depth_ = false;
|
bool writes_depth_ = false;
|
||||||
bool implicit_early_z_allowed_ = true;
|
bool kills_pixels_ = false;
|
||||||
std::vector<uint32_t> memexport_stream_constants_;
|
std::vector<uint32_t> memexport_stream_constants_;
|
||||||
|
|
||||||
bool is_valid_ = false;
|
uint32_t ucode_storage_index_ = UINT32_MAX;
|
||||||
bool is_translated_ = false;
|
|
||||||
std::vector<Error> errors_;
|
|
||||||
|
|
||||||
std::string ucode_disassembly_;
|
|
||||||
std::vector<uint8_t> translated_binary_;
|
|
||||||
std::string host_disassembly_;
|
|
||||||
std::string host_error_log_;
|
|
||||||
std::vector<uint8_t> host_binary_;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
} // namespace gpu
|
} // namespace gpu
|
||||||
|
|
|
@ -140,11 +140,15 @@ int shader_compiler_main(const std::vector<std::string>& args) {
|
||||||
Shader::HostVertexShaderType::kQuadDomainPatchIndexed;
|
Shader::HostVertexShaderType::kQuadDomainPatchIndexed;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
uint32_t modification =
|
||||||
|
translator->GetDefaultModification(shader_type, host_vertex_shader_type);
|
||||||
|
|
||||||
translator->Translate(shader.get(), host_vertex_shader_type);
|
Shader::Translation* translation =
|
||||||
|
shader->GetOrCreateTranslation(modification);
|
||||||
|
translator->Translate(*translation);
|
||||||
|
|
||||||
const void* source_data = shader->translated_binary().data();
|
const void* source_data = translation->translated_binary().data();
|
||||||
size_t source_data_size = shader->translated_binary().size();
|
size_t source_data_size = translation->translated_binary().size();
|
||||||
|
|
||||||
std::unique_ptr<xe::ui::spirv::SpirvDisassembler::Result> spirv_disasm_result;
|
std::unique_ptr<xe::ui::spirv::SpirvDisassembler::Result> spirv_disasm_result;
|
||||||
if (cvars::shader_output_type == "spirvtext") {
|
if (cvars::shader_output_type == "spirvtext") {
|
||||||
|
|
|
@ -1,4 +1,3 @@
|
||||||
#include "shader_translator.h"
|
|
||||||
/**
|
/**
|
||||||
******************************************************************************
|
******************************************************************************
|
||||||
* Xenia : Xbox 360 Emulator Research Project *
|
* Xenia : Xbox 360 Emulator Research Project *
|
||||||
|
@ -14,6 +13,7 @@
|
||||||
#include <set>
|
#include <set>
|
||||||
#include <string>
|
#include <string>
|
||||||
|
|
||||||
|
#include "xenia/base/assert.h"
|
||||||
#include "xenia/base/logging.h"
|
#include "xenia/base/logging.h"
|
||||||
#include "xenia/base/math.h"
|
#include "xenia/base/math.h"
|
||||||
|
|
||||||
|
@ -46,7 +46,9 @@ ShaderTranslator::ShaderTranslator() = default;
|
||||||
|
|
||||||
ShaderTranslator::~ShaderTranslator() = default;
|
ShaderTranslator::~ShaderTranslator() = default;
|
||||||
|
|
||||||
void ShaderTranslator::Reset() {
|
void ShaderTranslator::Reset(xenos::ShaderType shader_type) {
|
||||||
|
shader_type_ = shader_type;
|
||||||
|
modification_ = GetDefaultModification(shader_type);
|
||||||
errors_.clear();
|
errors_.clear();
|
||||||
ucode_disasm_buffer_.Reset();
|
ucode_disasm_buffer_.Reset();
|
||||||
ucode_disasm_line_number_ = 0;
|
ucode_disasm_line_number_ = 0;
|
||||||
|
@ -64,37 +66,37 @@ void ShaderTranslator::Reset() {
|
||||||
writes_color_targets_[i] = false;
|
writes_color_targets_[i] = false;
|
||||||
}
|
}
|
||||||
writes_depth_ = false;
|
writes_depth_ = false;
|
||||||
implicit_early_z_allowed_ = true;
|
kills_pixels_ = false;
|
||||||
memexport_alloc_count_ = 0;
|
memexport_alloc_count_ = 0;
|
||||||
memexport_eA_written_ = 0;
|
memexport_eA_written_ = 0;
|
||||||
std::memset(&memexport_eM_written_, 0, sizeof(memexport_eM_written_));
|
std::memset(&memexport_eM_written_, 0, sizeof(memexport_eM_written_));
|
||||||
memexport_stream_constants_.clear();
|
memexport_stream_constants_.clear();
|
||||||
}
|
}
|
||||||
|
|
||||||
bool ShaderTranslator::Translate(
|
bool ShaderTranslator::Translate(Shader::Translation& translation,
|
||||||
Shader* shader, reg::SQ_PROGRAM_CNTL cntl,
|
reg::SQ_PROGRAM_CNTL cntl) {
|
||||||
Shader::HostVertexShaderType host_vertex_shader_type) {
|
xenos::ShaderType shader_type = translation.shader().type();
|
||||||
Reset();
|
Reset(shader_type);
|
||||||
uint32_t cntl_num_reg = shader->type() == xenos::ShaderType::kVertex
|
uint32_t cntl_num_reg = shader_type == xenos::ShaderType::kVertex
|
||||||
? cntl.vs_num_reg
|
? cntl.vs_num_reg
|
||||||
: cntl.ps_num_reg;
|
: cntl.ps_num_reg;
|
||||||
register_count_ = (cntl_num_reg & 0x80) ? 0 : (cntl_num_reg + 1);
|
register_count_ = (cntl_num_reg & 0x80) ? 0 : (cntl_num_reg + 1);
|
||||||
|
|
||||||
return TranslateInternal(shader, host_vertex_shader_type);
|
return TranslateInternal(translation);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool ShaderTranslator::Translate(
|
bool ShaderTranslator::Translate(Shader::Translation& translation) {
|
||||||
Shader* shader, Shader::HostVertexShaderType host_vertex_shader_type) {
|
Reset(translation.shader().type());
|
||||||
Reset();
|
return TranslateInternal(translation);
|
||||||
return TranslateInternal(shader, host_vertex_shader_type);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
bool ShaderTranslator::TranslateInternal(
|
bool ShaderTranslator::TranslateInternal(Shader::Translation& translation) {
|
||||||
Shader* shader, Shader::HostVertexShaderType host_vertex_shader_type) {
|
Shader& shader = translation.shader();
|
||||||
shader_type_ = shader->type();
|
assert_true(shader_type_ == shader.type());
|
||||||
host_vertex_shader_type_ = host_vertex_shader_type;
|
shader_type_ = shader.type();
|
||||||
ucode_dwords_ = shader->ucode_dwords();
|
ucode_dwords_ = shader.ucode_dwords();
|
||||||
ucode_dword_count_ = shader->ucode_dword_count();
|
ucode_dword_count_ = shader.ucode_dword_count();
|
||||||
|
modification_ = translation.modification();
|
||||||
|
|
||||||
// Control flow instructions come paired in blocks of 3 dwords and all are
|
// Control flow instructions come paired in blocks of 3 dwords and all are
|
||||||
// listed at the top of the ucode.
|
// listed at the top of the ucode.
|
||||||
|
@ -150,12 +152,6 @@ bool ShaderTranslator::TranslateInternal(
|
||||||
if (memexport_eA_written_ == 0) {
|
if (memexport_eA_written_ == 0) {
|
||||||
memexport_stream_constants_.clear();
|
memexport_stream_constants_.clear();
|
||||||
}
|
}
|
||||||
if (!memexport_stream_constants_.empty()) {
|
|
||||||
// TODO(Triang3l): Investigate what happens to memexport when the pixel
|
|
||||||
// fails the depth/stencil test, but in Direct3D 11 UAV writes disable early
|
|
||||||
// depth/stencil.
|
|
||||||
implicit_early_z_allowed_ = false;
|
|
||||||
}
|
|
||||||
|
|
||||||
StartTranslation();
|
StartTranslation();
|
||||||
|
|
||||||
|
@ -192,35 +188,44 @@ bool ShaderTranslator::TranslateInternal(
|
||||||
++cf_index;
|
++cf_index;
|
||||||
}
|
}
|
||||||
|
|
||||||
shader->errors_ = std::move(errors_);
|
translation.errors_ = std::move(errors_);
|
||||||
shader->translated_binary_ = CompleteTranslation();
|
translation.translated_binary_ = CompleteTranslation();
|
||||||
shader->ucode_disassembly_ = ucode_disasm_buffer_.to_string();
|
translation.is_translated_ = true;
|
||||||
shader->host_vertex_shader_type_ = host_vertex_shader_type_;
|
|
||||||
shader->vertex_bindings_ = std::move(vertex_bindings_);
|
|
||||||
shader->texture_bindings_ = std::move(texture_bindings_);
|
|
||||||
shader->constant_register_map_ = std::move(constant_register_map_);
|
|
||||||
for (size_t i = 0; i < xe::countof(writes_color_targets_); ++i) {
|
|
||||||
shader->writes_color_targets_[i] = writes_color_targets_[i];
|
|
||||||
}
|
|
||||||
shader->writes_depth_ = writes_depth_;
|
|
||||||
shader->implicit_early_z_allowed_ = implicit_early_z_allowed_;
|
|
||||||
shader->memexport_stream_constants_.clear();
|
|
||||||
for (uint32_t memexport_stream_constant : memexport_stream_constants_) {
|
|
||||||
shader->memexport_stream_constants_.push_back(memexport_stream_constant);
|
|
||||||
}
|
|
||||||
|
|
||||||
shader->is_valid_ = true;
|
bool is_valid = true;
|
||||||
shader->is_translated_ = true;
|
for (const auto& error : translation.errors_) {
|
||||||
for (const auto& error : shader->errors_) {
|
|
||||||
if (error.is_fatal) {
|
if (error.is_fatal) {
|
||||||
shader->is_valid_ = false;
|
is_valid = false;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
translation.is_valid_ = is_valid;
|
||||||
|
|
||||||
PostTranslation(shader);
|
// Setup info that doesn't depend on the modification only once.
|
||||||
|
bool setup_shader_post_translation_info =
|
||||||
|
is_valid && !shader.post_translation_info_set_up_.test_and_set();
|
||||||
|
if (setup_shader_post_translation_info) {
|
||||||
|
shader.ucode_disassembly_ = ucode_disasm_buffer_.to_string();
|
||||||
|
shader.vertex_bindings_ = std::move(vertex_bindings_);
|
||||||
|
shader.texture_bindings_ = std::move(texture_bindings_);
|
||||||
|
shader.constant_register_map_ = std::move(constant_register_map_);
|
||||||
|
for (size_t i = 0; i < xe::countof(writes_color_targets_); ++i) {
|
||||||
|
shader.writes_color_targets_[i] = writes_color_targets_[i];
|
||||||
|
}
|
||||||
|
shader.writes_depth_ = writes_depth_;
|
||||||
|
shader.kills_pixels_ = kills_pixels_;
|
||||||
|
shader.memexport_stream_constants_.clear();
|
||||||
|
shader.memexport_stream_constants_.reserve(
|
||||||
|
memexport_stream_constants_.size());
|
||||||
|
shader.memexport_stream_constants_.insert(
|
||||||
|
shader.memexport_stream_constants_.cend(),
|
||||||
|
memexport_stream_constants_.cbegin(),
|
||||||
|
memexport_stream_constants_.cend());
|
||||||
|
}
|
||||||
|
PostTranslation(translation, setup_shader_post_translation_info);
|
||||||
|
|
||||||
return shader->is_valid_;
|
// In case is_valid_ is modified by PostTranslation, reload.
|
||||||
|
return translation.is_valid_;
|
||||||
}
|
}
|
||||||
|
|
||||||
void ShaderTranslator::MarkUcodeInstruction(uint32_t dword_offset) {
|
void ShaderTranslator::MarkUcodeInstruction(uint32_t dword_offset) {
|
||||||
|
@ -343,14 +348,9 @@ void ShaderTranslator::GatherInstructionInformation(
|
||||||
ParsedAluInstruction instr;
|
ParsedAluInstruction instr;
|
||||||
ParseAluInstruction(op, instr);
|
ParseAluInstruction(op, instr);
|
||||||
|
|
||||||
const auto& vector_opcode_info =
|
kills_pixels_ = kills_pixels_ ||
|
||||||
alu_vector_opcode_infos_[uint32_t(op.vector_opcode())];
|
ucode::AluVectorOpcodeIsKill(op.vector_opcode()) ||
|
||||||
implicit_early_z_allowed_ &=
|
ucode::AluScalarOpcodeIsKill(op.scalar_opcode());
|
||||||
!vector_opcode_info.disable_implicit_early_z;
|
|
||||||
const auto& scalar_opcode_info =
|
|
||||||
alu_scalar_opcode_infos_[uint32_t(op.scalar_opcode())];
|
|
||||||
implicit_early_z_allowed_ &=
|
|
||||||
!scalar_opcode_info.disable_implicit_early_z;
|
|
||||||
|
|
||||||
if (instr.vector_and_constant_result.storage_target !=
|
if (instr.vector_and_constant_result.storage_target !=
|
||||||
InstructionStorageTarget::kRegister ||
|
InstructionStorageTarget::kRegister ||
|
||||||
|
@ -408,7 +408,6 @@ void ShaderTranslator::GatherInstructionInformation(
|
||||||
break;
|
break;
|
||||||
case InstructionStorageTarget::kDepth:
|
case InstructionStorageTarget::kDepth:
|
||||||
writes_depth_ = true;
|
writes_depth_ = true;
|
||||||
implicit_early_z_allowed_ = false;
|
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
break;
|
break;
|
||||||
|
@ -1082,91 +1081,91 @@ uint32_t ParsedTextureFetchInstruction::GetNonZeroResultComponents() const {
|
||||||
|
|
||||||
const ShaderTranslator::AluOpcodeInfo
|
const ShaderTranslator::AluOpcodeInfo
|
||||||
ShaderTranslator::alu_vector_opcode_infos_[0x20] = {
|
ShaderTranslator::alu_vector_opcode_infos_[0x20] = {
|
||||||
{"add", 2, 4, false}, // 0
|
{"add", 2, 4}, // 0
|
||||||
{"mul", 2, 4, false}, // 1
|
{"mul", 2, 4}, // 1
|
||||||
{"max", 2, 4, false}, // 2
|
{"max", 2, 4}, // 2
|
||||||
{"min", 2, 4, false}, // 3
|
{"min", 2, 4}, // 3
|
||||||
{"seq", 2, 4, false}, // 4
|
{"seq", 2, 4}, // 4
|
||||||
{"sgt", 2, 4, false}, // 5
|
{"sgt", 2, 4}, // 5
|
||||||
{"sge", 2, 4, false}, // 6
|
{"sge", 2, 4}, // 6
|
||||||
{"sne", 2, 4, false}, // 7
|
{"sne", 2, 4}, // 7
|
||||||
{"frc", 1, 4, false}, // 8
|
{"frc", 1, 4}, // 8
|
||||||
{"trunc", 1, 4, false}, // 9
|
{"trunc", 1, 4}, // 9
|
||||||
{"floor", 1, 4, false}, // 10
|
{"floor", 1, 4}, // 10
|
||||||
{"mad", 3, 4, false}, // 11
|
{"mad", 3, 4}, // 11
|
||||||
{"cndeq", 3, 4, false}, // 12
|
{"cndeq", 3, 4}, // 12
|
||||||
{"cndge", 3, 4, false}, // 13
|
{"cndge", 3, 4}, // 13
|
||||||
{"cndgt", 3, 4, false}, // 14
|
{"cndgt", 3, 4}, // 14
|
||||||
{"dp4", 2, 4, false}, // 15
|
{"dp4", 2, 4}, // 15
|
||||||
{"dp3", 2, 4, false}, // 16
|
{"dp3", 2, 4}, // 16
|
||||||
{"dp2add", 3, 4, false}, // 17
|
{"dp2add", 3, 4}, // 17
|
||||||
{"cube", 2, 4, false}, // 18
|
{"cube", 2, 4}, // 18
|
||||||
{"max4", 1, 4, false}, // 19
|
{"max4", 1, 4}, // 19
|
||||||
{"setp_eq_push", 2, 4, false}, // 20
|
{"setp_eq_push", 2, 4}, // 20
|
||||||
{"setp_ne_push", 2, 4, false}, // 21
|
{"setp_ne_push", 2, 4}, // 21
|
||||||
{"setp_gt_push", 2, 4, false}, // 22
|
{"setp_gt_push", 2, 4}, // 22
|
||||||
{"setp_ge_push", 2, 4, false}, // 23
|
{"setp_ge_push", 2, 4}, // 23
|
||||||
{"kill_eq", 2, 4, true}, // 24
|
{"kill_eq", 2, 4}, // 24
|
||||||
{"kill_gt", 2, 4, true}, // 25
|
{"kill_gt", 2, 4}, // 25
|
||||||
{"kill_ge", 2, 4, true}, // 26
|
{"kill_ge", 2, 4}, // 26
|
||||||
{"kill_ne", 2, 4, true}, // 27
|
{"kill_ne", 2, 4}, // 27
|
||||||
{"dst", 2, 4, false}, // 28
|
{"dst", 2, 4}, // 28
|
||||||
{"maxa", 2, 4, false}, // 29
|
{"maxa", 2, 4}, // 29
|
||||||
};
|
};
|
||||||
|
|
||||||
const ShaderTranslator::AluOpcodeInfo
|
const ShaderTranslator::AluOpcodeInfo
|
||||||
ShaderTranslator::alu_scalar_opcode_infos_[0x40] = {
|
ShaderTranslator::alu_scalar_opcode_infos_[0x40] = {
|
||||||
{"adds", 1, 2, false}, // 0
|
{"adds", 1, 2}, // 0
|
||||||
{"adds_prev", 1, 1, false}, // 1
|
{"adds_prev", 1, 1}, // 1
|
||||||
{"muls", 1, 2, false}, // 2
|
{"muls", 1, 2}, // 2
|
||||||
{"muls_prev", 1, 1, false}, // 3
|
{"muls_prev", 1, 1}, // 3
|
||||||
{"muls_prev2", 1, 2, false}, // 4
|
{"muls_prev2", 1, 2}, // 4
|
||||||
{"maxs", 1, 2, false}, // 5
|
{"maxs", 1, 2}, // 5
|
||||||
{"mins", 1, 2, false}, // 6
|
{"mins", 1, 2}, // 6
|
||||||
{"seqs", 1, 1, false}, // 7
|
{"seqs", 1, 1}, // 7
|
||||||
{"sgts", 1, 1, false}, // 8
|
{"sgts", 1, 1}, // 8
|
||||||
{"sges", 1, 1, false}, // 9
|
{"sges", 1, 1}, // 9
|
||||||
{"snes", 1, 1, false}, // 10
|
{"snes", 1, 1}, // 10
|
||||||
{"frcs", 1, 1, false}, // 11
|
{"frcs", 1, 1}, // 11
|
||||||
{"truncs", 1, 1, false}, // 12
|
{"truncs", 1, 1}, // 12
|
||||||
{"floors", 1, 1, false}, // 13
|
{"floors", 1, 1}, // 13
|
||||||
{"exp", 1, 1, false}, // 14
|
{"exp", 1, 1}, // 14
|
||||||
{"logc", 1, 1, false}, // 15
|
{"logc", 1, 1}, // 15
|
||||||
{"log", 1, 1, false}, // 16
|
{"log", 1, 1}, // 16
|
||||||
{"rcpc", 1, 1, false}, // 17
|
{"rcpc", 1, 1}, // 17
|
||||||
{"rcpf", 1, 1, false}, // 18
|
{"rcpf", 1, 1}, // 18
|
||||||
{"rcp", 1, 1, false}, // 19
|
{"rcp", 1, 1}, // 19
|
||||||
{"rsqc", 1, 1, false}, // 20
|
{"rsqc", 1, 1}, // 20
|
||||||
{"rsqf", 1, 1, false}, // 21
|
{"rsqf", 1, 1}, // 21
|
||||||
{"rsq", 1, 1, false}, // 22
|
{"rsq", 1, 1}, // 22
|
||||||
{"maxas", 1, 2, false}, // 23
|
{"maxas", 1, 2}, // 23
|
||||||
{"maxasf", 1, 2, false}, // 24
|
{"maxasf", 1, 2}, // 24
|
||||||
{"subs", 1, 2, false}, // 25
|
{"subs", 1, 2}, // 25
|
||||||
{"subs_prev", 1, 1, false}, // 26
|
{"subs_prev", 1, 1}, // 26
|
||||||
{"setp_eq", 1, 1, false}, // 27
|
{"setp_eq", 1, 1}, // 27
|
||||||
{"setp_ne", 1, 1, false}, // 28
|
{"setp_ne", 1, 1}, // 28
|
||||||
{"setp_gt", 1, 1, false}, // 29
|
{"setp_gt", 1, 1}, // 29
|
||||||
{"setp_ge", 1, 1, false}, // 30
|
{"setp_ge", 1, 1}, // 30
|
||||||
{"setp_inv", 1, 1, false}, // 31
|
{"setp_inv", 1, 1}, // 31
|
||||||
{"setp_pop", 1, 1, false}, // 32
|
{"setp_pop", 1, 1}, // 32
|
||||||
{"setp_clr", 0, 0, false}, // 33
|
{"setp_clr", 0, 0}, // 33
|
||||||
{"setp_rstr", 1, 1, false}, // 34
|
{"setp_rstr", 1, 1}, // 34
|
||||||
{"kills_eq", 1, 1, true}, // 35
|
{"kills_eq", 1, 1}, // 35
|
||||||
{"kills_gt", 1, 1, true}, // 36
|
{"kills_gt", 1, 1}, // 36
|
||||||
{"kills_ge", 1, 1, true}, // 37
|
{"kills_ge", 1, 1}, // 37
|
||||||
{"kills_ne", 1, 1, true}, // 38
|
{"kills_ne", 1, 1}, // 38
|
||||||
{"kills_one", 1, 1, true}, // 39
|
{"kills_one", 1, 1}, // 39
|
||||||
{"sqrt", 1, 1, false}, // 40
|
{"sqrt", 1, 1}, // 40
|
||||||
{"UNKNOWN", 0, 0, false}, // 41
|
{"UNKNOWN", 0, 0}, // 41
|
||||||
{"mulsc", 2, 1, false}, // 42
|
{"mulsc", 2, 1}, // 42
|
||||||
{"mulsc", 2, 1, false}, // 43
|
{"mulsc", 2, 1}, // 43
|
||||||
{"addsc", 2, 1, false}, // 44
|
{"addsc", 2, 1}, // 44
|
||||||
{"addsc", 2, 1, false}, // 45
|
{"addsc", 2, 1}, // 45
|
||||||
{"subsc", 2, 1, false}, // 46
|
{"subsc", 2, 1}, // 46
|
||||||
{"subsc", 2, 1, false}, // 47
|
{"subsc", 2, 1}, // 47
|
||||||
{"sin", 1, 1, false}, // 48
|
{"sin", 1, 1}, // 48
|
||||||
{"cos", 1, 1, false}, // 49
|
{"cos", 1, 1}, // 49
|
||||||
{"retain_prev", 0, 0, false}, // 50
|
{"retain_prev", 0, 0}, // 50
|
||||||
};
|
};
|
||||||
|
|
||||||
void ShaderTranslator::TranslateAluInstruction(const AluInstruction& op) {
|
void ShaderTranslator::TranslateAluInstruction(const AluInstruction& op) {
|
||||||
|
|
|
@ -29,18 +29,27 @@ class ShaderTranslator {
|
||||||
public:
|
public:
|
||||||
virtual ~ShaderTranslator();
|
virtual ~ShaderTranslator();
|
||||||
|
|
||||||
bool Translate(Shader* shader, reg::SQ_PROGRAM_CNTL cntl,
|
virtual uint32_t GetDefaultModification(
|
||||||
Shader::HostVertexShaderType host_vertex_shader_type =
|
xenos::ShaderType shader_type,
|
||||||
Shader::HostVertexShaderType::kVertex);
|
Shader::HostVertexShaderType host_vertex_shader_type =
|
||||||
bool Translate(Shader* shader,
|
Shader::HostVertexShaderType::kVertex) const {
|
||||||
Shader::HostVertexShaderType host_vertex_shader_type =
|
return 0;
|
||||||
Shader::HostVertexShaderType::kVertex);
|
}
|
||||||
|
|
||||||
|
bool Translate(Shader::Translation& translation, reg::SQ_PROGRAM_CNTL cntl);
|
||||||
|
bool Translate(Shader::Translation& translation);
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
ShaderTranslator();
|
ShaderTranslator();
|
||||||
|
|
||||||
// Resets translator state before beginning translation.
|
// Resets translator state before beginning translation.
|
||||||
virtual void Reset();
|
// shader_type is passed here so translator implementations can generate
|
||||||
|
// special fixed shaders for internal use, and set up the type for this
|
||||||
|
// purpose.
|
||||||
|
virtual void Reset(xenos::ShaderType shader_type);
|
||||||
|
|
||||||
|
// Current host-side modification being generated.
|
||||||
|
uint32_t modification() const { return modification_; }
|
||||||
|
|
||||||
// Register count.
|
// Register count.
|
||||||
uint32_t register_count() const { return register_count_; }
|
uint32_t register_count() const { return register_count_; }
|
||||||
|
@ -48,11 +57,6 @@ class ShaderTranslator {
|
||||||
bool is_vertex_shader() const {
|
bool is_vertex_shader() const {
|
||||||
return shader_type_ == xenos::ShaderType::kVertex;
|
return shader_type_ == xenos::ShaderType::kVertex;
|
||||||
}
|
}
|
||||||
// If translating a vertex shader, type of the shader in a D3D11-like
|
|
||||||
// rendering pipeline.
|
|
||||||
Shader::HostVertexShaderType host_vertex_shader_type() const {
|
|
||||||
return host_vertex_shader_type_;
|
|
||||||
}
|
|
||||||
// True if the current shader is a pixel shader.
|
// True if the current shader is a pixel shader.
|
||||||
bool is_pixel_shader() const {
|
bool is_pixel_shader() const {
|
||||||
return shader_type_ == xenos::ShaderType::kPixel;
|
return shader_type_ == xenos::ShaderType::kPixel;
|
||||||
|
@ -85,10 +89,8 @@ class ShaderTranslator {
|
||||||
// True if the current shader overrides the pixel depth, set before
|
// True if the current shader overrides the pixel depth, set before
|
||||||
// translation. Doesn't include writes with an empty used write mask.
|
// translation. Doesn't include writes with an empty used write mask.
|
||||||
bool writes_depth() const { return writes_depth_; }
|
bool writes_depth() const { return writes_depth_; }
|
||||||
// True if Xenia can automatically enable early depth/stencil for the pixel
|
// True if the current shader has any `kill` instructions.
|
||||||
// shader when RB_DEPTHCONTROL EARLY_Z_ENABLE is not set, provided alpha
|
bool kills_pixels() const { return kills_pixels_; }
|
||||||
// testing and alpha to coverage are disabled.
|
|
||||||
bool implicit_early_z_allowed() const { return implicit_early_z_allowed_; }
|
|
||||||
// A list of all vertex bindings, populated before translation occurs.
|
// A list of all vertex bindings, populated before translation occurs.
|
||||||
const std::vector<Shader::VertexBinding>& vertex_bindings() const {
|
const std::vector<Shader::VertexBinding>& vertex_bindings() const {
|
||||||
return vertex_bindings_;
|
return vertex_bindings_;
|
||||||
|
@ -112,6 +114,17 @@ class ShaderTranslator {
|
||||||
return memexport_stream_constants_;
|
return memexport_stream_constants_;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Whether the shader can have early depth and stencil writing enabled, unless
|
||||||
|
// alpha test or alpha to coverage is enabled. Data gathered before
|
||||||
|
// translation.
|
||||||
|
bool CanWriteZEarly() const {
|
||||||
|
// TODO(Triang3l): Investigate what happens to memexport when the pixel
|
||||||
|
// fails the depth/stencil test, but in Direct3D 11 UAV writes disable early
|
||||||
|
// depth/stencil.
|
||||||
|
return !writes_depth_ && !kills_pixels_ &&
|
||||||
|
memexport_stream_constants_.empty();
|
||||||
|
}
|
||||||
|
|
||||||
// Current line number in the ucode disassembly.
|
// Current line number in the ucode disassembly.
|
||||||
size_t ucode_disasm_line_number() const { return ucode_disasm_line_number_; }
|
size_t ucode_disasm_line_number() const { return ucode_disasm_line_number_; }
|
||||||
// Ucode disassembly buffer accumulated during translation.
|
// Ucode disassembly buffer accumulated during translation.
|
||||||
|
@ -130,10 +143,14 @@ class ShaderTranslator {
|
||||||
}
|
}
|
||||||
|
|
||||||
// Handles post-translation tasks when the shader has been fully translated.
|
// Handles post-translation tasks when the shader has been fully translated.
|
||||||
virtual void PostTranslation(Shader* shader) {}
|
// setup_shader_post_translation_info if non-modification-specific parameters
|
||||||
|
// of the Shader object behind the Translation can be set by this invocation.
|
||||||
|
virtual void PostTranslation(Shader::Translation& translation,
|
||||||
|
bool setup_shader_post_translation_info) {}
|
||||||
// Sets the host disassembly on a shader.
|
// Sets the host disassembly on a shader.
|
||||||
void set_host_disassembly(Shader* shader, std::string value) {
|
void set_host_disassembly(Shader::Translation& translation,
|
||||||
shader->host_disassembly_ = std::move(value);
|
std::string value) {
|
||||||
|
translation.host_disassembly_ = std::move(value);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Pre-process a control-flow instruction before anything else.
|
// Pre-process a control-flow instruction before anything else.
|
||||||
|
@ -188,11 +205,9 @@ class ShaderTranslator {
|
||||||
const char* name;
|
const char* name;
|
||||||
uint32_t argument_count;
|
uint32_t argument_count;
|
||||||
uint32_t src_swizzle_component_count;
|
uint32_t src_swizzle_component_count;
|
||||||
bool disable_implicit_early_z;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
bool TranslateInternal(Shader* shader,
|
bool TranslateInternal(Shader::Translation& translation);
|
||||||
Shader::HostVertexShaderType host_vertex_shader_type);
|
|
||||||
|
|
||||||
void MarkUcodeInstruction(uint32_t dword_offset);
|
void MarkUcodeInstruction(uint32_t dword_offset);
|
||||||
void AppendUcodeDisasm(char c);
|
void AppendUcodeDisasm(char c);
|
||||||
|
@ -246,12 +261,13 @@ class ShaderTranslator {
|
||||||
|
|
||||||
// Input shader metadata and microcode.
|
// Input shader metadata and microcode.
|
||||||
xenos::ShaderType shader_type_;
|
xenos::ShaderType shader_type_;
|
||||||
Shader::HostVertexShaderType host_vertex_shader_type_;
|
|
||||||
const uint32_t* ucode_dwords_;
|
const uint32_t* ucode_dwords_;
|
||||||
size_t ucode_dword_count_;
|
size_t ucode_dword_count_;
|
||||||
reg::SQ_PROGRAM_CNTL program_cntl_;
|
|
||||||
uint32_t register_count_;
|
uint32_t register_count_;
|
||||||
|
|
||||||
|
// Current host-side modification being generated.
|
||||||
|
uint32_t modification_ = 0;
|
||||||
|
|
||||||
// Accumulated translation errors.
|
// Accumulated translation errors.
|
||||||
std::vector<Shader::Error> errors_;
|
std::vector<Shader::Error> errors_;
|
||||||
|
|
||||||
|
@ -272,7 +288,8 @@ class ShaderTranslator {
|
||||||
// translation.
|
// translation.
|
||||||
std::set<uint32_t> label_addresses_;
|
std::set<uint32_t> label_addresses_;
|
||||||
|
|
||||||
// Detected binding information gathered before translation.
|
// Detected binding information gathered before translation. Must not be
|
||||||
|
// affected by the modification index.
|
||||||
int total_attrib_count_ = 0;
|
int total_attrib_count_ = 0;
|
||||||
std::vector<Shader::VertexBinding> vertex_bindings_;
|
std::vector<Shader::VertexBinding> vertex_bindings_;
|
||||||
std::vector<Shader::TextureBinding> texture_bindings_;
|
std::vector<Shader::TextureBinding> texture_bindings_;
|
||||||
|
@ -282,13 +299,15 @@ class ShaderTranslator {
|
||||||
// These all are gathered before translation.
|
// These all are gathered before translation.
|
||||||
// uses_register_dynamic_addressing_ for writes, writes_color_targets_,
|
// uses_register_dynamic_addressing_ for writes, writes_color_targets_,
|
||||||
// writes_depth_ don't include empty used write masks.
|
// writes_depth_ don't include empty used write masks.
|
||||||
|
// Must not be affected by the modification index.
|
||||||
Shader::ConstantRegisterMap constant_register_map_ = {0};
|
Shader::ConstantRegisterMap constant_register_map_ = {0};
|
||||||
bool uses_register_dynamic_addressing_ = false;
|
bool uses_register_dynamic_addressing_ = false;
|
||||||
bool writes_color_targets_[4] = {false, false, false, false};
|
bool writes_color_targets_[4] = {false, false, false, false};
|
||||||
bool writes_depth_ = false;
|
bool writes_depth_ = false;
|
||||||
bool implicit_early_z_allowed_ = true;
|
bool kills_pixels_ = false;
|
||||||
|
|
||||||
// Memexport info is gathered before translation.
|
// Memexport info is gathered before translation.
|
||||||
|
// Must not be affected by the modification index.
|
||||||
uint32_t memexport_alloc_count_ = 0;
|
uint32_t memexport_alloc_count_ = 0;
|
||||||
// For register allocation in implementations - what was used after each
|
// For register allocation in implementations - what was used after each
|
||||||
// `alloc export`.
|
// `alloc export`.
|
||||||
|
|
|
@ -667,12 +667,14 @@ std::vector<uint8_t> SpirvShaderTranslator::CompleteTranslation() {
|
||||||
return spirv_bytes;
|
return spirv_bytes;
|
||||||
}
|
}
|
||||||
|
|
||||||
void SpirvShaderTranslator::PostTranslation(Shader* shader) {
|
void SpirvShaderTranslator::PostTranslation(
|
||||||
|
Shader::Translation& translation, bool setup_shader_post_translation_info) {
|
||||||
// Validation.
|
// Validation.
|
||||||
if (cvars::spv_validate) {
|
if (cvars::spv_validate) {
|
||||||
auto validation = validator_.Validate(
|
auto validation = validator_.Validate(
|
||||||
reinterpret_cast<const uint32_t*>(shader->translated_binary().data()),
|
reinterpret_cast<const uint32_t*>(
|
||||||
shader->translated_binary().size() / sizeof(uint32_t));
|
translation.translated_binary().data()),
|
||||||
|
translation.translated_binary().size() / sizeof(uint32_t));
|
||||||
if (validation->has_error()) {
|
if (validation->has_error()) {
|
||||||
XELOGE("SPIR-V Shader Validation failed! Error: {}",
|
XELOGE("SPIR-V Shader Validation failed! Error: {}",
|
||||||
validation->error_string());
|
validation->error_string());
|
||||||
|
@ -682,12 +684,13 @@ void SpirvShaderTranslator::PostTranslation(Shader* shader) {
|
||||||
if (cvars::spv_disasm) {
|
if (cvars::spv_disasm) {
|
||||||
// TODO(benvanik): only if needed? could be slowish.
|
// TODO(benvanik): only if needed? could be slowish.
|
||||||
auto disasm = disassembler_.Disassemble(
|
auto disasm = disassembler_.Disassemble(
|
||||||
reinterpret_cast<const uint32_t*>(shader->translated_binary().data()),
|
reinterpret_cast<const uint32_t*>(
|
||||||
shader->translated_binary().size() / 4);
|
translation.translated_binary().data()),
|
||||||
|
translation.translated_binary().size() / sizeof(uint32_t));
|
||||||
if (disasm->has_error()) {
|
if (disasm->has_error()) {
|
||||||
XELOGE("Failed to disassemble SPIRV - invalid?");
|
XELOGE("Failed to disassemble SPIRV - invalid?");
|
||||||
} else {
|
} else {
|
||||||
set_host_disassembly(shader, disasm->to_string());
|
set_host_disassembly(translation, disasm->to_string());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -61,7 +61,8 @@ class SpirvShaderTranslator : public ShaderTranslator {
|
||||||
protected:
|
protected:
|
||||||
void StartTranslation() override;
|
void StartTranslation() override;
|
||||||
std::vector<uint8_t> CompleteTranslation() override;
|
std::vector<uint8_t> CompleteTranslation() override;
|
||||||
void PostTranslation(Shader* shader) override;
|
void PostTranslation(Shader::Translation& translation,
|
||||||
|
bool setup_shader_post_translation_info) override;
|
||||||
|
|
||||||
void PreProcessControlFlowInstructions(
|
void PreProcessControlFlowInstructions(
|
||||||
std::vector<ucode::ControlFlowInstruction> instrs) override;
|
std::vector<ucode::ControlFlowInstruction> instrs) override;
|
||||||
|
|
|
@ -92,7 +92,7 @@ int TraceDump::Main(const std::vector<std::string>& args) {
|
||||||
|
|
||||||
bool TraceDump::Setup() {
|
bool TraceDump::Setup() {
|
||||||
// Create the emulator but don't initialize so we can setup the window.
|
// Create the emulator but don't initialize so we can setup the window.
|
||||||
emulator_ = std::make_unique<Emulator>("", "", "");
|
emulator_ = std::make_unique<Emulator>("", "", "", "");
|
||||||
X_STATUS result = emulator_->Setup(
|
X_STATUS result = emulator_->Setup(
|
||||||
nullptr, nullptr, [this]() { return CreateGraphicsSystem(); }, nullptr);
|
nullptr, nullptr, [this]() { return CreateGraphicsSystem(); }, nullptr);
|
||||||
if (XFAILED(result)) {
|
if (XFAILED(result)) {
|
||||||
|
|
|
@ -121,7 +121,7 @@ bool TraceViewer::Setup() {
|
||||||
window_->Resize(1920, 1200);
|
window_->Resize(1920, 1200);
|
||||||
|
|
||||||
// Create the emulator but don't initialize so we can setup the window.
|
// Create the emulator but don't initialize so we can setup the window.
|
||||||
emulator_ = std::make_unique<Emulator>("", "", "");
|
emulator_ = std::make_unique<Emulator>("", "", "", "");
|
||||||
X_STATUS result = emulator_->Setup(
|
X_STATUS result = emulator_->Setup(
|
||||||
window_.get(), nullptr, [this]() { return CreateGraphicsSystem(); },
|
window_.get(), nullptr, [this]() { return CreateGraphicsSystem(); },
|
||||||
nullptr);
|
nullptr);
|
||||||
|
@ -566,8 +566,21 @@ TraceViewer::ShaderDisplayType TraceViewer::DrawShaderTypeUI() {
|
||||||
|
|
||||||
void TraceViewer::DrawShaderUI(Shader* shader, ShaderDisplayType display_type) {
|
void TraceViewer::DrawShaderUI(Shader* shader, ShaderDisplayType display_type) {
|
||||||
// Must be prepared for advanced display modes.
|
// Must be prepared for advanced display modes.
|
||||||
|
// FIXME(Triang3l): This should display the actual translation used in the
|
||||||
|
// draw, but it may depend on multiple backend-related factors, including
|
||||||
|
// drawing multiple times with multiple modifications, even depending on
|
||||||
|
// values obtained during translation of other modifications (for instance,
|
||||||
|
// a memexporting shader can be executed both as a vertex shader (to draw the
|
||||||
|
// points) and as a compute shader (to actually export) if the host doesn't
|
||||||
|
// support writes from vertex shaders.
|
||||||
|
const Shader::Translation* translation = nullptr;
|
||||||
if (display_type != ShaderDisplayType::kUcode) {
|
if (display_type != ShaderDisplayType::kUcode) {
|
||||||
if (!shader->is_valid()) {
|
for (const auto& translation_pair : shader->translations()) {
|
||||||
|
if (translation_pair.second->is_valid()) {
|
||||||
|
translation = translation_pair.second;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (!translation) {
|
||||||
ImGui::TextColored(kColorError,
|
ImGui::TextColored(kColorError,
|
||||||
"ERROR: shader error during parsing/translation");
|
"ERROR: shader error during parsing/translation");
|
||||||
return;
|
return;
|
||||||
|
@ -580,7 +593,7 @@ void TraceViewer::DrawShaderUI(Shader* shader, ShaderDisplayType display_type) {
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case ShaderDisplayType::kTranslated: {
|
case ShaderDisplayType::kTranslated: {
|
||||||
const auto& str = shader->GetTranslatedBinaryString();
|
const auto& str = translation->GetTranslatedBinaryString();
|
||||||
size_t i = 0;
|
size_t i = 0;
|
||||||
bool done = false;
|
bool done = false;
|
||||||
while (!done && i < str.size()) {
|
while (!done && i < str.size()) {
|
||||||
|
@ -600,7 +613,7 @@ void TraceViewer::DrawShaderUI(Shader* shader, ShaderDisplayType display_type) {
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case ShaderDisplayType::kHostDisasm: {
|
case ShaderDisplayType::kHostDisasm: {
|
||||||
DrawMultilineString(shader->host_disassembly());
|
DrawMultilineString(translation->host_disassembly());
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1147,6 +1147,19 @@ enum class AluScalarOpcode : uint32_t {
|
||||||
kRetainPrev = 50,
|
kRetainPrev = 50,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
constexpr bool AluScalarOpcodeIsKill(AluScalarOpcode scalar_opcode) {
|
||||||
|
switch (scalar_opcode) {
|
||||||
|
case AluScalarOpcode::kKillsEq:
|
||||||
|
case AluScalarOpcode::kKillsGt:
|
||||||
|
case AluScalarOpcode::kKillsGe:
|
||||||
|
case AluScalarOpcode::kKillsNe:
|
||||||
|
case AluScalarOpcode::kKillsOne:
|
||||||
|
return true;
|
||||||
|
default:
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
enum class AluVectorOpcode : uint32_t {
|
enum class AluVectorOpcode : uint32_t {
|
||||||
// Per-Component Floating-Point Add
|
// Per-Component Floating-Point Add
|
||||||
// add/ADDv dest, src0, src1
|
// add/ADDv dest, src0, src1
|
||||||
|
@ -1471,27 +1484,37 @@ enum class AluVectorOpcode : uint32_t {
|
||||||
kMaxA = 29,
|
kMaxA = 29,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
constexpr bool AluVectorOpcodeIsKill(AluVectorOpcode vector_opcode) {
|
||||||
|
switch (vector_opcode) {
|
||||||
|
case AluVectorOpcode::kKillEq:
|
||||||
|
case AluVectorOpcode::kKillGt:
|
||||||
|
case AluVectorOpcode::kKillGe:
|
||||||
|
case AluVectorOpcode::kKillNe:
|
||||||
|
return true;
|
||||||
|
default:
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// Whether the vector instruction has side effects such as discarding a pixel or
|
// Whether the vector instruction has side effects such as discarding a pixel or
|
||||||
// setting the predicate and can't be ignored even if it doesn't write to
|
// setting the predicate and can't be ignored even if it doesn't write to
|
||||||
// anywhere. Note that all scalar operations except for retain_prev have a side
|
// anywhere. Note that all scalar operations except for retain_prev have a side
|
||||||
// effect of modifying the previous scalar result register, so they must always
|
// effect of modifying the previous scalar result register, so they must always
|
||||||
// be executed even if not writing.
|
// be executed even if not writing.
|
||||||
constexpr bool AluVectorOpHasSideEffects(AluVectorOpcode vector_opcode) {
|
constexpr bool AluVectorOpHasSideEffects(AluVectorOpcode vector_opcode) {
|
||||||
|
if (AluVectorOpcodeIsKill(vector_opcode)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
switch (vector_opcode) {
|
switch (vector_opcode) {
|
||||||
case AluVectorOpcode::kSetpEqPush:
|
case AluVectorOpcode::kSetpEqPush:
|
||||||
case AluVectorOpcode::kSetpNePush:
|
case AluVectorOpcode::kSetpNePush:
|
||||||
case AluVectorOpcode::kSetpGtPush:
|
case AluVectorOpcode::kSetpGtPush:
|
||||||
case AluVectorOpcode::kSetpGePush:
|
case AluVectorOpcode::kSetpGePush:
|
||||||
case AluVectorOpcode::kKillEq:
|
|
||||||
case AluVectorOpcode::kKillGt:
|
|
||||||
case AluVectorOpcode::kKillGe:
|
|
||||||
case AluVectorOpcode::kKillNe:
|
|
||||||
case AluVectorOpcode::kMaxA:
|
case AluVectorOpcode::kMaxA:
|
||||||
return true;
|
return true;
|
||||||
default:
|
default:
|
||||||
break;
|
return false;
|
||||||
}
|
}
|
||||||
return false;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Whether each component of a source operand is used at all in the instruction
|
// Whether each component of a source operand is used at all in the instruction
|
||||||
|
|
|
@ -362,35 +362,38 @@ VkPipeline PipelineCache::GetPipeline(const RenderState* render_state,
|
||||||
return pipeline;
|
return pipeline;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool PipelineCache::TranslateShader(VulkanShader* shader,
|
bool PipelineCache::TranslateShader(
|
||||||
reg::SQ_PROGRAM_CNTL cntl) {
|
VulkanShader::VulkanTranslation& translation, reg::SQ_PROGRAM_CNTL cntl) {
|
||||||
// Perform translation.
|
// Perform translation.
|
||||||
// If this fails the shader will be marked as invalid and ignored later.
|
// If this fails the shader will be marked as invalid and ignored later.
|
||||||
if (!shader_translator_->Translate(shader, cntl)) {
|
if (!shader_translator_->Translate(translation, cntl)) {
|
||||||
XELOGE("Shader translation failed; marking shader as ignored");
|
XELOGE("Shader translation failed; marking shader as ignored");
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Prepare the shader for use (creates our VkShaderModule).
|
// Prepare the shader for use (creates our VkShaderModule).
|
||||||
// It could still fail at this point.
|
// It could still fail at this point.
|
||||||
if (!shader->Prepare()) {
|
if (!translation.Prepare()) {
|
||||||
XELOGE("Shader preparation failed; marking shader as ignored");
|
XELOGE("Shader preparation failed; marking shader as ignored");
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (shader->is_valid()) {
|
if (translation.is_valid()) {
|
||||||
XELOGGPU("Generated {} shader ({}b) - hash {:016X}:\n{}\n",
|
XELOGGPU("Generated {} shader ({}b) - hash {:016X}:\n{}\n",
|
||||||
shader->type() == xenos::ShaderType::kVertex ? "vertex" : "pixel",
|
translation.shader().type() == xenos::ShaderType::kVertex
|
||||||
shader->ucode_dword_count() * 4, shader->ucode_data_hash(),
|
? "vertex"
|
||||||
shader->ucode_disassembly());
|
: "pixel",
|
||||||
|
translation.shader().ucode_dword_count() * 4,
|
||||||
|
translation.shader().ucode_data_hash(),
|
||||||
|
translation.shader().ucode_disassembly());
|
||||||
}
|
}
|
||||||
|
|
||||||
// Dump shader files if desired.
|
// Dump shader files if desired.
|
||||||
if (!cvars::dump_shaders.empty()) {
|
if (!cvars::dump_shaders.empty()) {
|
||||||
shader->Dump(cvars::dump_shaders, "vk");
|
translation.Dump(cvars::dump_shaders, "vk");
|
||||||
}
|
}
|
||||||
|
|
||||||
return shader->is_valid();
|
return translation.is_valid();
|
||||||
}
|
}
|
||||||
|
|
||||||
static void DumpShaderStatisticsAMD(const VkShaderStatisticsInfoAMD& stats) {
|
static void DumpShaderStatisticsAMD(const VkShaderStatisticsInfoAMD& stats) {
|
||||||
|
@ -1063,16 +1066,28 @@ PipelineCache::UpdateStatus PipelineCache::UpdateShaderStages(
|
||||||
return UpdateStatus::kCompatible;
|
return UpdateStatus::kCompatible;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!vertex_shader->is_translated() &&
|
VulkanShader::VulkanTranslation* vertex_shader_translation =
|
||||||
!TranslateShader(vertex_shader, regs.sq_program_cntl)) {
|
static_cast<VulkanShader::VulkanTranslation*>(
|
||||||
|
vertex_shader->GetOrCreateTranslation(
|
||||||
|
shader_translator_->GetDefaultModification(
|
||||||
|
xenos::ShaderType::kVertex)));
|
||||||
|
if (!vertex_shader_translation->is_translated() &&
|
||||||
|
!TranslateShader(*vertex_shader_translation, regs.sq_program_cntl)) {
|
||||||
XELOGE("Failed to translate the vertex shader!");
|
XELOGE("Failed to translate the vertex shader!");
|
||||||
return UpdateStatus::kError;
|
return UpdateStatus::kError;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (pixel_shader && !pixel_shader->is_translated() &&
|
VulkanShader::VulkanTranslation* pixel_shader_translation = nullptr;
|
||||||
!TranslateShader(pixel_shader, regs.sq_program_cntl)) {
|
if (pixel_shader) {
|
||||||
XELOGE("Failed to translate the pixel shader!");
|
pixel_shader_translation = static_cast<VulkanShader::VulkanTranslation*>(
|
||||||
return UpdateStatus::kError;
|
pixel_shader->GetOrCreateTranslation(
|
||||||
|
shader_translator_->GetDefaultModification(
|
||||||
|
xenos::ShaderType::kPixel)));
|
||||||
|
if (!pixel_shader_translation->is_translated() &&
|
||||||
|
!TranslateShader(*pixel_shader_translation, regs.sq_program_cntl)) {
|
||||||
|
XELOGE("Failed to translate the pixel shader!");
|
||||||
|
return UpdateStatus::kError;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
update_shader_stages_stage_count_ = 0;
|
update_shader_stages_stage_count_ = 0;
|
||||||
|
@ -1084,7 +1099,7 @@ PipelineCache::UpdateStatus PipelineCache::UpdateShaderStages(
|
||||||
vertex_pipeline_stage.pNext = nullptr;
|
vertex_pipeline_stage.pNext = nullptr;
|
||||||
vertex_pipeline_stage.flags = 0;
|
vertex_pipeline_stage.flags = 0;
|
||||||
vertex_pipeline_stage.stage = VK_SHADER_STAGE_VERTEX_BIT;
|
vertex_pipeline_stage.stage = VK_SHADER_STAGE_VERTEX_BIT;
|
||||||
vertex_pipeline_stage.module = vertex_shader->shader_module();
|
vertex_pipeline_stage.module = vertex_shader_translation->shader_module();
|
||||||
vertex_pipeline_stage.pName = "main";
|
vertex_pipeline_stage.pName = "main";
|
||||||
vertex_pipeline_stage.pSpecializationInfo = nullptr;
|
vertex_pipeline_stage.pSpecializationInfo = nullptr;
|
||||||
|
|
||||||
|
@ -1116,8 +1131,9 @@ PipelineCache::UpdateStatus PipelineCache::UpdateShaderStages(
|
||||||
pixel_pipeline_stage.pNext = nullptr;
|
pixel_pipeline_stage.pNext = nullptr;
|
||||||
pixel_pipeline_stage.flags = 0;
|
pixel_pipeline_stage.flags = 0;
|
||||||
pixel_pipeline_stage.stage = VK_SHADER_STAGE_FRAGMENT_BIT;
|
pixel_pipeline_stage.stage = VK_SHADER_STAGE_FRAGMENT_BIT;
|
||||||
pixel_pipeline_stage.module =
|
pixel_pipeline_stage.module = pixel_shader_translation
|
||||||
pixel_shader ? pixel_shader->shader_module() : dummy_pixel_shader_;
|
? pixel_shader_translation->shader_module()
|
||||||
|
: dummy_pixel_shader_;
|
||||||
pixel_pipeline_stage.pName = "main";
|
pixel_pipeline_stage.pName = "main";
|
||||||
pixel_pipeline_stage.pSpecializationInfo = nullptr;
|
pixel_pipeline_stage.pSpecializationInfo = nullptr;
|
||||||
|
|
||||||
|
|
|
@ -79,7 +79,8 @@ class PipelineCache {
|
||||||
// state.
|
// state.
|
||||||
VkPipeline GetPipeline(const RenderState* render_state, uint64_t hash_key);
|
VkPipeline GetPipeline(const RenderState* render_state, uint64_t hash_key);
|
||||||
|
|
||||||
bool TranslateShader(VulkanShader* shader, reg::SQ_PROGRAM_CNTL cntl);
|
bool TranslateShader(VulkanShader::VulkanTranslation& translation,
|
||||||
|
reg::SQ_PROGRAM_CNTL cntl);
|
||||||
|
|
||||||
void DumpShaderDisasmAMD(VkPipeline pipeline);
|
void DumpShaderDisasmAMD(VkPipeline pipeline);
|
||||||
void DumpShaderDisasmNV(const VkGraphicsPipelineCreateInfo& info);
|
void DumpShaderDisasmNV(const VkGraphicsPipelineCreateInfo& info);
|
||||||
|
|
|
@ -27,38 +27,56 @@ VulkanShader::VulkanShader(ui::vulkan::VulkanDevice* device,
|
||||||
const uint32_t* dword_ptr, uint32_t dword_count)
|
const uint32_t* dword_ptr, uint32_t dword_count)
|
||||||
: Shader(shader_type, data_hash, dword_ptr, dword_count), device_(device) {}
|
: Shader(shader_type, data_hash, dword_ptr, dword_count), device_(device) {}
|
||||||
|
|
||||||
VulkanShader::~VulkanShader() {
|
VulkanShader::VulkanTranslation::~VulkanTranslation() {
|
||||||
if (shader_module_) {
|
if (shader_module_) {
|
||||||
vkDestroyShaderModule(*device_, shader_module_, nullptr);
|
const VulkanShader& vulkan_shader = static_cast<VulkanShader&>(shader());
|
||||||
|
vkDestroyShaderModule(*vulkan_shader.device_, shader_module_, nullptr);
|
||||||
shader_module_ = nullptr;
|
shader_module_ = nullptr;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
bool VulkanShader::Prepare() {
|
bool VulkanShader::VulkanTranslation::Prepare() {
|
||||||
assert_null(shader_module_);
|
assert_null(shader_module_);
|
||||||
assert_true(is_valid());
|
assert_true(is_valid());
|
||||||
|
|
||||||
|
const VulkanShader& vulkan_shader = static_cast<VulkanShader&>(shader());
|
||||||
|
ui::vulkan::VulkanDevice* device = vulkan_shader.device_;
|
||||||
|
|
||||||
// Create the shader module.
|
// Create the shader module.
|
||||||
VkShaderModuleCreateInfo shader_info;
|
VkShaderModuleCreateInfo shader_info;
|
||||||
shader_info.sType = VK_STRUCTURE_TYPE_SHADER_MODULE_CREATE_INFO;
|
shader_info.sType = VK_STRUCTURE_TYPE_SHADER_MODULE_CREATE_INFO;
|
||||||
shader_info.pNext = nullptr;
|
shader_info.pNext = nullptr;
|
||||||
shader_info.flags = 0;
|
shader_info.flags = 0;
|
||||||
shader_info.codeSize = translated_binary_.size();
|
shader_info.codeSize = translated_binary().size();
|
||||||
shader_info.pCode =
|
shader_info.pCode =
|
||||||
reinterpret_cast<const uint32_t*>(translated_binary_.data());
|
reinterpret_cast<const uint32_t*>(translated_binary().data());
|
||||||
auto status =
|
auto status =
|
||||||
vkCreateShaderModule(*device_, &shader_info, nullptr, &shader_module_);
|
vkCreateShaderModule(*device, &shader_info, nullptr, &shader_module_);
|
||||||
CheckResult(status, "vkCreateShaderModule");
|
CheckResult(status, "vkCreateShaderModule");
|
||||||
|
|
||||||
char typeChar = shader_type_ == xenos::ShaderType::kPixel
|
char type_char;
|
||||||
? 'p'
|
switch (vulkan_shader.type()) {
|
||||||
: shader_type_ == xenos::ShaderType::kVertex ? 'v' : 'u';
|
case xenos::ShaderType::kVertex:
|
||||||
device_->DbgSetObjectName(
|
type_char = 'v';
|
||||||
uint64_t(shader_module_), VK_DEBUG_REPORT_OBJECT_TYPE_SHADER_MODULE_EXT,
|
break;
|
||||||
fmt::format("S({}): {:016X}", typeChar, ucode_data_hash()));
|
case xenos::ShaderType::kPixel:
|
||||||
|
type_char = 'p';
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
type_char = 'u';
|
||||||
|
}
|
||||||
|
device->DbgSetObjectName(uint64_t(shader_module_),
|
||||||
|
VK_DEBUG_REPORT_OBJECT_TYPE_SHADER_MODULE_EXT,
|
||||||
|
fmt::format("S({}): {:016X}", type_char,
|
||||||
|
vulkan_shader.ucode_data_hash()));
|
||||||
return status == VK_SUCCESS;
|
return status == VK_SUCCESS;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Shader::Translation* VulkanShader::CreateTranslationInstance(
|
||||||
|
uint32_t modification) {
|
||||||
|
return new VulkanTranslation(*this, modification);
|
||||||
|
}
|
||||||
|
|
||||||
} // namespace vulkan
|
} // namespace vulkan
|
||||||
} // namespace gpu
|
} // namespace gpu
|
||||||
} // namespace xe
|
} // namespace xe
|
||||||
|
|
|
@ -21,19 +21,30 @@ namespace vulkan {
|
||||||
|
|
||||||
class VulkanShader : public Shader {
|
class VulkanShader : public Shader {
|
||||||
public:
|
public:
|
||||||
|
class VulkanTranslation : public Translation {
|
||||||
|
public:
|
||||||
|
VulkanTranslation(VulkanShader& shader, uint32_t modification)
|
||||||
|
: Translation(shader, modification) {}
|
||||||
|
~VulkanTranslation() override;
|
||||||
|
|
||||||
|
bool Prepare();
|
||||||
|
|
||||||
|
// Available only if the translation is_valid and has been prepared.
|
||||||
|
VkShaderModule shader_module() const { return shader_module_; }
|
||||||
|
|
||||||
|
private:
|
||||||
|
VkShaderModule shader_module_ = nullptr;
|
||||||
|
};
|
||||||
|
|
||||||
VulkanShader(ui::vulkan::VulkanDevice* device, xenos::ShaderType shader_type,
|
VulkanShader(ui::vulkan::VulkanDevice* device, xenos::ShaderType shader_type,
|
||||||
uint64_t data_hash, const uint32_t* dword_ptr,
|
uint64_t data_hash, const uint32_t* dword_ptr,
|
||||||
uint32_t dword_count);
|
uint32_t dword_count);
|
||||||
~VulkanShader() override;
|
|
||||||
|
|
||||||
// Available only if the shader is_valid and has been prepared.
|
protected:
|
||||||
VkShaderModule shader_module() const { return shader_module_; }
|
Translation* CreateTranslationInstance(uint32_t modification) override;
|
||||||
|
|
||||||
bool Prepare();
|
|
||||||
|
|
||||||
private:
|
private:
|
||||||
ui::vulkan::VulkanDevice* device_ = nullptr;
|
ui::vulkan::VulkanDevice* device_ = nullptr;
|
||||||
VkShaderModule shader_module_ = nullptr;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
} // namespace vulkan
|
} // namespace vulkan
|
||||||
|
|
|
@ -9,17 +9,41 @@
|
||||||
|
|
||||||
#include "xenia/gpu/xenos.h"
|
#include "xenia/gpu/xenos.h"
|
||||||
|
|
||||||
|
#include <cmath>
|
||||||
|
|
||||||
#include "xenia/base/math.h"
|
#include "xenia/base/math.h"
|
||||||
|
|
||||||
namespace xe {
|
namespace xe {
|
||||||
namespace gpu {
|
namespace gpu {
|
||||||
namespace xenos {
|
namespace xenos {
|
||||||
|
|
||||||
|
// Based on CFloat24 from d3dref9.dll and the 6e4 code from:
|
||||||
|
// https://github.com/Microsoft/DirectXTex/blob/master/DirectXTex/DirectXTexConvert.cpp
|
||||||
|
// 6e4 has a different exponent bias allowing [0,512) values, 20e4 allows [0,2).
|
||||||
|
|
||||||
|
uint32_t Float32To20e4(float f32) {
|
||||||
|
if (!(f32 > 0.0f)) {
|
||||||
|
// Positive only, and not -0 or NaN.
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
uint32_t f32u32 = *reinterpret_cast<const uint32_t*>(&f32);
|
||||||
|
if (f32u32 >= 0x3FFFFFF8) {
|
||||||
|
// Saturate.
|
||||||
|
return 0xFFFFFF;
|
||||||
|
}
|
||||||
|
if (f32u32 < 0x38800000) {
|
||||||
|
// The number is too small to be represented as a normalized 20e4.
|
||||||
|
// Convert it to a denormalized value.
|
||||||
|
uint32_t shift = std::min(uint32_t(113 - (f32u32 >> 23)), uint32_t(24));
|
||||||
|
f32u32 = (0x800000 | (f32u32 & 0x7FFFFF)) >> shift;
|
||||||
|
} else {
|
||||||
|
// Rebias the exponent to represent the value as a normalized 20e4.
|
||||||
|
f32u32 += 0xC8000000u;
|
||||||
|
}
|
||||||
|
return ((f32u32 + 3 + ((f32u32 >> 3) & 1)) >> 3) & 0xFFFFFF;
|
||||||
|
}
|
||||||
|
|
||||||
float Float20e4To32(uint32_t f24) {
|
float Float20e4To32(uint32_t f24) {
|
||||||
// Based on CFloat24 from d3dref9.dll and the 6e4 code from:
|
|
||||||
// https://github.com/Microsoft/DirectXTex/blob/master/DirectXTex/DirectXTexConvert.cpp
|
|
||||||
// 6e4 has a different exponent bias allowing [0,512) values, 20e4 allows
|
|
||||||
// [0,2).
|
|
||||||
f24 &= 0xFFFFFF;
|
f24 &= 0xFFFFFF;
|
||||||
if (!f24) {
|
if (!f24) {
|
||||||
return 0.0f;
|
return 0.0f;
|
||||||
|
|
|
@ -305,6 +305,9 @@ enum class DepthRenderTargetFormat : uint32_t {
|
||||||
|
|
||||||
const char* GetDepthRenderTargetFormatName(DepthRenderTargetFormat format);
|
const char* GetDepthRenderTargetFormatName(DepthRenderTargetFormat format);
|
||||||
|
|
||||||
|
// Converts an IEEE-754 32-bit floating-point number to Xenos floating-point
|
||||||
|
// depth, rounding to the nearest even.
|
||||||
|
uint32_t Float32To20e4(float f32);
|
||||||
// Converts Xenos floating-point depth in bits 0:23 (not clamping) to an
|
// Converts Xenos floating-point depth in bits 0:23 (not clamping) to an
|
||||||
// IEEE-754 32-bit floating-point number.
|
// IEEE-754 32-bit floating-point number.
|
||||||
float Float20e4To32(uint32_t f24);
|
float Float20e4To32(uint32_t f24);
|
||||||
|
|
Loading…
Reference in New Issue