mirror of
				https://github.com/PabloMK7/citra.git
				synced 2025-10-30 21:30:04 +00:00 
			
		
		
		
	video_core serialization
This commit is contained in:
		
							parent
							
								
									ee2cae2093
								
							
						
					
					
						commit
						6f00976ab5
					
				
					 9 changed files with 142 additions and 21 deletions
				
			
		|  | @ -94,7 +94,7 @@ endif() | |||
| create_target_directory_groups(video_core) | ||||
| 
 | ||||
| target_link_libraries(video_core PUBLIC common core) | ||||
| target_link_libraries(video_core PRIVATE glad nihstro-headers) | ||||
| target_link_libraries(video_core PRIVATE glad nihstro-headers boost_libs) | ||||
| 
 | ||||
| if (ARCHITECTURE_x86_64) | ||||
|     target_link_libraries(video_core PUBLIC xbyak) | ||||
|  |  | |||
|  | @ -640,8 +640,17 @@ static void WritePicaReg(u32 id, u32 value, u32 mask) { | |||
|                                  reinterpret_cast<void*>(&id)); | ||||
| } | ||||
| 
 | ||||
| void ProcessCommandList(const u32* list, u32 size) { | ||||
|     g_state.cmd_list.head_ptr = g_state.cmd_list.current_ptr = list; | ||||
| void ProcessCommandList(PAddr list, u32 size) { | ||||
| 
 | ||||
|     u32* buffer = (u32*)VideoCore::g_memory->GetPhysicalPointer(list); | ||||
| 
 | ||||
|     if (Pica::g_debug_context && Pica::g_debug_context->recorder) { | ||||
|         Pica::g_debug_context->recorder->MemoryAccessed((u8*)buffer, size, | ||||
|                                                         list); | ||||
|     } | ||||
| 
 | ||||
|     g_state.cmd_list.addr = list; | ||||
|     g_state.cmd_list.head_ptr = g_state.cmd_list.current_ptr = buffer; | ||||
|     g_state.cmd_list.length = size / sizeof(u32); | ||||
| 
 | ||||
|     while (g_state.cmd_list.current_ptr < g_state.cmd_list.head_ptr + g_state.cmd_list.length) { | ||||
|  |  | |||
|  | @ -32,6 +32,6 @@ static_assert(std::is_standard_layout<CommandHeader>::value == true, | |||
|               "CommandHeader does not use standard layout"); | ||||
| static_assert(sizeof(CommandHeader) == sizeof(u32), "CommandHeader has incorrect size!"); | ||||
| 
 | ||||
| void ProcessCommandList(const u32* list, u32 size); | ||||
| void ProcessCommandList(PAddr list, u32 size); | ||||
| 
 | ||||
| } // namespace Pica::CommandProcessor
 | ||||
|  |  | |||
|  | @ -5,6 +5,7 @@ | |||
| #pragma once | ||||
| 
 | ||||
| #include <array> | ||||
| #include "boost/serialization/split_member.hpp" | ||||
| #include "common/bit_field.h" | ||||
| #include "common/common_types.h" | ||||
| #include "common/vector_math.h" | ||||
|  | @ -13,6 +14,18 @@ | |||
| #include "video_core/regs.h" | ||||
| #include "video_core/shader/shader.h" | ||||
| 
 | ||||
| // NB, by defining this we can't use the built-in std::array serializer in this file
 | ||||
| namespace boost::serialization { | ||||
| 
 | ||||
| template<class Archive, typename Value, size_t Size> | ||||
| void serialize(Archive & ar, std::array<Value, Size> &array, const unsigned int version) | ||||
| { | ||||
|     static_assert(sizeof(Value) == sizeof(u32)); | ||||
|     ar & *static_cast<u32 (*)[Size]>(static_cast<void *>(array.data())); | ||||
| } | ||||
| 
 | ||||
| } | ||||
| 
 | ||||
| namespace Pica { | ||||
| 
 | ||||
| /// Struct used to describe current Pica state
 | ||||
|  | @ -79,6 +92,18 @@ struct State { | |||
|         std::array<ValueEntry, 128> alpha_map_table; | ||||
|         std::array<ColorEntry, 256> color_table; | ||||
|         std::array<ColorDifferenceEntry, 256> color_diff_table; | ||||
| 
 | ||||
|     private: | ||||
|         friend class boost::serialization::access; | ||||
|         template<class Archive> | ||||
|         void serialize(Archive & ar, const unsigned int file_version) | ||||
|         { | ||||
|             ar & noise_table; | ||||
|             ar & color_map_table; | ||||
|             ar & alpha_map_table; | ||||
|             ar & color_table; | ||||
|             ar & color_diff_table; | ||||
|         } | ||||
|     } proctex; | ||||
| 
 | ||||
|     struct Lighting { | ||||
|  | @ -101,6 +126,12 @@ struct State { | |||
|                 float diff = static_cast<float>(difference) / 2047.f; | ||||
|                 return neg_difference ? -diff : diff; | ||||
|             } | ||||
| 
 | ||||
|             template<class Archive> | ||||
|             void serialize(Archive & ar, const unsigned int file_version) | ||||
|             { | ||||
|                 ar & raw; | ||||
|             } | ||||
|         }; | ||||
| 
 | ||||
|         std::array<std::array<LutEntry, 256>, 24> luts; | ||||
|  | @ -126,8 +157,11 @@ struct State { | |||
|         std::array<LutEntry, 128> lut; | ||||
|     } fog; | ||||
| 
 | ||||
| #undef SERIALIZE_RAW | ||||
| 
 | ||||
|     /// Current Pica command list
 | ||||
|     struct { | ||||
|         PAddr addr; // This exists only for serialization
 | ||||
|         const u32* head_ptr; | ||||
|         const u32* current_ptr; | ||||
|         u32 length; | ||||
|  | @ -141,6 +175,17 @@ struct State { | |||
|         u32 current_attribute = 0; | ||||
|         // Indicates the immediate mode just started and the geometry pipeline needs to reconfigure
 | ||||
|         bool reset_geometry_pipeline = true; | ||||
| 
 | ||||
|     private: | ||||
|         friend class boost::serialization::access; | ||||
|         template<class Archive> | ||||
|         void serialize(Archive & ar, const unsigned int file_version) | ||||
|         { | ||||
|             // ar & input_vertex;
 | ||||
|             ar & current_attribute; | ||||
|             ar & reset_geometry_pipeline; | ||||
|         } | ||||
| 
 | ||||
|     } immediate; | ||||
| 
 | ||||
|     // the geometry shader needs to be kept in the global state because some shaders relie on
 | ||||
|  | @ -161,6 +206,51 @@ struct State { | |||
| 
 | ||||
|     int default_attr_counter = 0; | ||||
|     u32 default_attr_write_buffer[3]{}; | ||||
| 
 | ||||
| private: | ||||
| 
 | ||||
|     friend class boost::serialization::access; | ||||
|     template<class Archive> | ||||
|     void serialize(Archive & ar, const unsigned int file_version) | ||||
|     { | ||||
|         ar & regs.reg_array; | ||||
|         // ar & vs;
 | ||||
|         // ar & gs;
 | ||||
|         // ar & input_default_attributes;
 | ||||
|         ar & proctex; | ||||
|         for (auto i = 0; i < lighting.luts.size(); i++) { | ||||
|             ar & lighting.luts[i]; | ||||
|         } | ||||
|         ar & fog.lut; | ||||
|         ar & cmd_list.addr; | ||||
|         ar & cmd_list.length; | ||||
|         ar & immediate; | ||||
|         // ar & gs_unit;
 | ||||
|         // ar & geometry_pipeline;
 | ||||
|         // ar & primitive_assembler;
 | ||||
|         ar & vs_float_regs_counter; | ||||
|         ar & vs_uniform_write_buffer; | ||||
|         ar & gs_float_regs_counter; | ||||
|         ar & gs_uniform_write_buffer; | ||||
|         ar & default_attr_counter; | ||||
|         ar & default_attr_write_buffer; | ||||
|         boost::serialization::split_member(ar, *this, file_version); | ||||
|     } | ||||
| 
 | ||||
|     template<class Archive> | ||||
|     void save(Archive & ar, const unsigned int file_version) const | ||||
|     { | ||||
|         ar << static_cast<u32>(cmd_list.current_ptr - cmd_list.head_ptr); | ||||
|     } | ||||
| 
 | ||||
|     template<class Archive> | ||||
|     void load(Archive & ar, const unsigned int file_version) | ||||
|     { | ||||
|         u32 offset{}; | ||||
|         ar >> offset; | ||||
|         cmd_list.head_ptr = (u32*)VideoCore::g_memory->GetPhysicalPointer(cmd_list.addr); | ||||
|         cmd_list.current_ptr = cmd_list.head_ptr + offset; | ||||
|     } | ||||
| }; | ||||
| 
 | ||||
| extern State g_state; ///< Current Pica state
 | ||||
|  |  | |||
|  | @ -3,9 +3,11 @@ | |||
| // Refer to the license.txt file included.
 | ||||
| 
 | ||||
| #include <memory> | ||||
| #include "common/archives.h" | ||||
| #include "common/logging/log.h" | ||||
| #include "core/settings.h" | ||||
| #include "video_core/pica.h" | ||||
| #include "video_core/pica_state.h" | ||||
| #include "video_core/renderer_base.h" | ||||
| #include "video_core/renderer_opengl/gl_vars.h" | ||||
| #include "video_core/renderer_opengl/renderer_opengl.h" | ||||
|  | @ -85,4 +87,18 @@ u16 GetResolutionScaleFactor() { | |||
|     } | ||||
| } | ||||
| 
 | ||||
| void Save(std::ostream &stream) | ||||
| { | ||||
|     oarchive oa{stream}; | ||||
|     oa & Pica::g_state; | ||||
| } | ||||
| 
 | ||||
| void Load(std::istream &stream) | ||||
| { | ||||
|     iarchive ia{stream}; | ||||
|     ia & Pica::g_state; | ||||
|     // TODO: Flush/reset things
 | ||||
| 
 | ||||
| } | ||||
| 
 | ||||
| } // namespace VideoCore
 | ||||
|  |  | |||
|  | @ -4,6 +4,7 @@ | |||
| 
 | ||||
| #pragma once | ||||
| 
 | ||||
| #include <iostream> | ||||
| #include <atomic> | ||||
| #include <memory> | ||||
| #include "core/frontend/emu_window.h" | ||||
|  | @ -61,4 +62,7 @@ void RequestScreenshot(void* data, std::function<void()> callback, | |||
| 
 | ||||
| u16 GetResolutionScaleFactor(); | ||||
| 
 | ||||
| void Save(std::ostream &stream); | ||||
| void Load(std::istream &stream); | ||||
| 
 | ||||
| } // namespace VideoCore
 | ||||
|  |  | |||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue