diff options
Diffstat (limited to '')
| -rw-r--r-- | src/video_core/engines/maxwell_3d.cpp | 25 | ||||
| -rw-r--r-- | src/video_core/engines/maxwell_3d.h | 23 |
2 files changed, 41 insertions, 7 deletions
diff --git a/src/video_core/engines/maxwell_3d.cpp b/src/video_core/engines/maxwell_3d.cpp index ce536e29b..ba63b44b4 100644 --- a/src/video_core/engines/maxwell_3d.cpp +++ b/src/video_core/engines/maxwell_3d.cpp | |||
| @@ -98,6 +98,8 @@ void Maxwell3D::InitializeRegisterDefaults() { | |||
| 98 | regs.framebuffer_srgb = 1; | 98 | regs.framebuffer_srgb = 1; |
| 99 | regs.front_face = Maxwell3D::Regs::FrontFace::ClockWise; | 99 | regs.front_face = Maxwell3D::Regs::FrontFace::ClockWise; |
| 100 | 100 | ||
| 101 | shadow_state = regs; | ||
| 102 | |||
| 101 | mme_inline[MAXWELL3D_REG_INDEX(draw.vertex_end_gl)] = true; | 103 | mme_inline[MAXWELL3D_REG_INDEX(draw.vertex_end_gl)] = true; |
| 102 | mme_inline[MAXWELL3D_REG_INDEX(draw.vertex_begin_gl)] = true; | 104 | mme_inline[MAXWELL3D_REG_INDEX(draw.vertex_begin_gl)] = true; |
| 103 | mme_inline[MAXWELL3D_REG_INDEX(vertex_buffer.count)] = true; | 105 | mme_inline[MAXWELL3D_REG_INDEX(vertex_buffer.count)] = true; |
| @@ -160,8 +162,17 @@ void Maxwell3D::CallMethod(const GPU::MethodCall& method_call) { | |||
| 160 | ASSERT_MSG(method < Regs::NUM_REGS, | 162 | ASSERT_MSG(method < Regs::NUM_REGS, |
| 161 | "Invalid Maxwell3D register, increase the size of the Regs structure"); | 163 | "Invalid Maxwell3D register, increase the size of the Regs structure"); |
| 162 | 164 | ||
| 163 | if (regs.reg_array[method] != method_call.argument) { | 165 | u32 arg = method_call.argument; |
| 164 | regs.reg_array[method] = method_call.argument; | 166 | // Keep track of the register value in shadow_state when requested. |
| 167 | if (shadow_state.shadow_ram_control == Regs::ShadowRamControl::Track || | ||
| 168 | shadow_state.shadow_ram_control == Regs::ShadowRamControl::TrackWithFilter) { | ||
| 169 | shadow_state.reg_array[method] = arg; | ||
| 170 | } else if (shadow_state.shadow_ram_control == Regs::ShadowRamControl::Replay) { | ||
| 171 | arg = shadow_state.reg_array[method]; | ||
| 172 | } | ||
| 173 | |||
| 174 | if (regs.reg_array[method] != arg) { | ||
| 175 | regs.reg_array[method] = arg; | ||
| 165 | 176 | ||
| 166 | for (const auto& table : dirty.tables) { | 177 | for (const auto& table : dirty.tables) { |
| 167 | dirty.flags[table[method]] = true; | 178 | dirty.flags[table[method]] = true; |
| @@ -169,12 +180,16 @@ void Maxwell3D::CallMethod(const GPU::MethodCall& method_call) { | |||
| 169 | } | 180 | } |
| 170 | 181 | ||
| 171 | switch (method) { | 182 | switch (method) { |
| 183 | case MAXWELL3D_REG_INDEX(shadow_ram_control): { | ||
| 184 | shadow_state.shadow_ram_control = static_cast<Regs::ShadowRamControl>(method_call.argument); | ||
| 185 | break; | ||
| 186 | } | ||
| 172 | case MAXWELL3D_REG_INDEX(macros.data): { | 187 | case MAXWELL3D_REG_INDEX(macros.data): { |
| 173 | ProcessMacroUpload(method_call.argument); | 188 | ProcessMacroUpload(arg); |
| 174 | break; | 189 | break; |
| 175 | } | 190 | } |
| 176 | case MAXWELL3D_REG_INDEX(macros.bind): { | 191 | case MAXWELL3D_REG_INDEX(macros.bind): { |
| 177 | ProcessMacroBind(method_call.argument); | 192 | ProcessMacroBind(arg); |
| 178 | break; | 193 | break; |
| 179 | } | 194 | } |
| 180 | case MAXWELL3D_REG_INDEX(firmware[4]): { | 195 | case MAXWELL3D_REG_INDEX(firmware[4]): { |
| @@ -250,7 +265,7 @@ void Maxwell3D::CallMethod(const GPU::MethodCall& method_call) { | |||
| 250 | } | 265 | } |
| 251 | case MAXWELL3D_REG_INDEX(data_upload): { | 266 | case MAXWELL3D_REG_INDEX(data_upload): { |
| 252 | const bool is_last_call = method_call.IsLastCall(); | 267 | const bool is_last_call = method_call.IsLastCall(); |
| 253 | upload_state.ProcessData(method_call.argument, is_last_call); | 268 | upload_state.ProcessData(arg, is_last_call); |
| 254 | if (is_last_call) { | 269 | if (is_last_call) { |
| 255 | OnMemoryWrite(); | 270 | OnMemoryWrite(); |
| 256 | } | 271 | } |
diff --git a/src/video_core/engines/maxwell_3d.h b/src/video_core/engines/maxwell_3d.h index 8a9e9992e..d24c9f657 100644 --- a/src/video_core/engines/maxwell_3d.h +++ b/src/video_core/engines/maxwell_3d.h | |||
| @@ -531,6 +531,17 @@ public: | |||
| 531 | Fill = 0x1b02, | 531 | Fill = 0x1b02, |
| 532 | }; | 532 | }; |
| 533 | 533 | ||
| 534 | enum class ShadowRamControl : u32 { | ||
| 535 | // write value to shadow ram | ||
| 536 | Track = 0, | ||
| 537 | // write value to shadow ram ( with validation ??? ) | ||
| 538 | TrackWithFilter = 1, | ||
| 539 | // only write to real hw register | ||
| 540 | Passthrough = 2, | ||
| 541 | // write value from shadow ram to real hw register | ||
| 542 | Replay = 3, | ||
| 543 | }; | ||
| 544 | |||
| 534 | struct RenderTargetConfig { | 545 | struct RenderTargetConfig { |
| 535 | u32 address_high; | 546 | u32 address_high; |
| 536 | u32 address_low; | 547 | u32 address_low; |
| @@ -674,7 +685,9 @@ public: | |||
| 674 | u32 bind; | 685 | u32 bind; |
| 675 | } macros; | 686 | } macros; |
| 676 | 687 | ||
| 677 | INSERT_UNION_PADDING_WORDS(0x17); | 688 | ShadowRamControl shadow_ram_control; |
| 689 | |||
| 690 | INSERT_UNION_PADDING_WORDS(0x16); | ||
| 678 | 691 | ||
| 679 | Upload::Registers upload; | 692 | Upload::Registers upload; |
| 680 | struct { | 693 | struct { |
| @@ -1263,7 +1276,12 @@ public: | |||
| 1263 | }; | 1276 | }; |
| 1264 | std::array<u32, NUM_REGS> reg_array; | 1277 | std::array<u32, NUM_REGS> reg_array; |
| 1265 | }; | 1278 | }; |
| 1266 | } regs{}; | 1279 | }; |
| 1280 | |||
| 1281 | Regs regs{}; | ||
| 1282 | |||
| 1283 | /// Store temporary hw register values, used by some calls to restore state after a operation | ||
| 1284 | Regs shadow_state; | ||
| 1267 | 1285 | ||
| 1268 | static_assert(sizeof(Regs) == Regs::NUM_REGS * sizeof(u32), "Maxwell3D Regs has wrong size"); | 1286 | static_assert(sizeof(Regs) == Regs::NUM_REGS * sizeof(u32), "Maxwell3D Regs has wrong size"); |
| 1269 | static_assert(std::is_trivially_copyable_v<Regs>, "Maxwell3D Regs must be trivially copyable"); | 1287 | static_assert(std::is_trivially_copyable_v<Regs>, "Maxwell3D Regs must be trivially copyable"); |
| @@ -1458,6 +1476,7 @@ private: | |||
| 1458 | "Field " #field_name " has invalid position") | 1476 | "Field " #field_name " has invalid position") |
| 1459 | 1477 | ||
| 1460 | ASSERT_REG_POSITION(macros, 0x45); | 1478 | ASSERT_REG_POSITION(macros, 0x45); |
| 1479 | ASSERT_REG_POSITION(shadow_ram_control, 0x49); | ||
| 1461 | ASSERT_REG_POSITION(upload, 0x60); | 1480 | ASSERT_REG_POSITION(upload, 0x60); |
| 1462 | ASSERT_REG_POSITION(exec_upload, 0x6C); | 1481 | ASSERT_REG_POSITION(exec_upload, 0x6C); |
| 1463 | ASSERT_REG_POSITION(data_upload, 0x6D); | 1482 | ASSERT_REG_POSITION(data_upload, 0x6D); |