mirror of
https://github.com/citra-mirror/citra.git
synced 2024-08-20 10:23:23 +02:00
GSP: Implement command 0x05, used for flushing caches
May fix additional texture caching issues. (Though mostly in homebrew, I haven't seen any commercial software use this to flush anything but command lists.)
This commit is contained in:
parent
5fdfd782cc
commit
1ed7f3e028
@ -30,11 +30,11 @@ QVariant GPUCommandStreamItemModel::data(const QModelIndex& index, int role) con
|
|||||||
{
|
{
|
||||||
std::map<GSP_GPU::CommandId, const char*> command_names = {
|
std::map<GSP_GPU::CommandId, const char*> command_names = {
|
||||||
{ GSP_GPU::CommandId::REQUEST_DMA, "REQUEST_DMA" },
|
{ GSP_GPU::CommandId::REQUEST_DMA, "REQUEST_DMA" },
|
||||||
{ GSP_GPU::CommandId::SET_COMMAND_LIST_FIRST, "SET_COMMAND_LIST_FIRST" },
|
{ GSP_GPU::CommandId::SUBMIT_GPU_CMDLIST, "SUBMIT_GPU_CMDLIST" },
|
||||||
{ GSP_GPU::CommandId::SET_MEMORY_FILL, "SET_MEMORY_FILL" },
|
{ GSP_GPU::CommandId::SET_MEMORY_FILL, "SET_MEMORY_FILL" },
|
||||||
{ GSP_GPU::CommandId::SET_DISPLAY_TRANSFER, "SET_DISPLAY_TRANSFER" },
|
{ GSP_GPU::CommandId::SET_DISPLAY_TRANSFER, "SET_DISPLAY_TRANSFER" },
|
||||||
{ GSP_GPU::CommandId::SET_TEXTURE_COPY, "SET_TEXTURE_COPY" },
|
{ GSP_GPU::CommandId::SET_TEXTURE_COPY, "SET_TEXTURE_COPY" },
|
||||||
{ GSP_GPU::CommandId::SET_COMMAND_LIST_LAST, "SET_COMMAND_LIST_LAST" }
|
{ GSP_GPU::CommandId::CACHE_FLUSH, "CACHE_FLUSH" },
|
||||||
};
|
};
|
||||||
const u32* command_data = reinterpret_cast<const u32*>(&command);
|
const u32* command_data = reinterpret_cast<const u32*>(&command);
|
||||||
QString str = QString("%1 %2 %3 %4 %5 %6 %7 %8 %9").arg(command_names[command.id])
|
QString str = QString("%1 %2 %3 %4 %5 %6 %7 %8 %9").arg(command_names[command.id])
|
||||||
|
@ -377,12 +377,16 @@ static void ExecuteCommand(const Command& command, u32 thread_id) {
|
|||||||
command.dma_request.size);
|
command.dma_request.size);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
// ctrulib homebrew sends all relevant command list data with this command,
|
// TODO: This will need some rework in the future. (why?)
|
||||||
// hence we do all "interesting" stuff here and do nothing in SET_COMMAND_LIST_FIRST.
|
case CommandId::SUBMIT_GPU_CMDLIST:
|
||||||
// TODO: This will need some rework in the future.
|
|
||||||
case CommandId::SET_COMMAND_LIST_LAST:
|
|
||||||
{
|
{
|
||||||
auto& params = command.set_command_list_last;
|
auto& params = command.submit_gpu_cmdlist;
|
||||||
|
|
||||||
|
if (params.do_flush) {
|
||||||
|
// This flag flushes the command list (params.address, params.size) from the cache.
|
||||||
|
// Command lists are not processed by the hardware renderer, so we don't need to
|
||||||
|
// actually flush them in Citra.
|
||||||
|
}
|
||||||
|
|
||||||
WriteGPURegister(static_cast<u32>(GPU_REG_INDEX(command_processor_config.address)),
|
WriteGPURegister(static_cast<u32>(GPU_REG_INDEX(command_processor_config.address)),
|
||||||
Memory::VirtualToPhysicalAddress(params.address) >> 3);
|
Memory::VirtualToPhysicalAddress(params.address) >> 3);
|
||||||
@ -391,6 +395,8 @@ static void ExecuteCommand(const Command& command, u32 thread_id) {
|
|||||||
// TODO: Not sure if we are supposed to always write this .. seems to trigger processing though
|
// TODO: Not sure if we are supposed to always write this .. seems to trigger processing though
|
||||||
WriteGPURegister(static_cast<u32>(GPU_REG_INDEX(command_processor_config.trigger)), 1);
|
WriteGPURegister(static_cast<u32>(GPU_REG_INDEX(command_processor_config.trigger)), 1);
|
||||||
|
|
||||||
|
// TODO(yuriks): Figure out the meaning of the `flags` field.
|
||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -434,7 +440,6 @@ static void ExecuteCommand(const Command& command, u32 thread_id) {
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO: Check if texture copies are implemented correctly..
|
|
||||||
case CommandId::SET_TEXTURE_COPY:
|
case CommandId::SET_TEXTURE_COPY:
|
||||||
{
|
{
|
||||||
auto& params = command.texture_copy;
|
auto& params = command.texture_copy;
|
||||||
@ -456,10 +461,15 @@ static void ExecuteCommand(const Command& command, u32 thread_id) {
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO: Figure out what exactly SET_COMMAND_LIST_FIRST and SET_COMMAND_LIST_LAST
|
case CommandId::CACHE_FLUSH:
|
||||||
// are supposed to do.
|
|
||||||
case CommandId::SET_COMMAND_LIST_FIRST:
|
|
||||||
{
|
{
|
||||||
|
for (auto& region : command.cache_flush.regions) {
|
||||||
|
if (region.size == 0)
|
||||||
|
break;
|
||||||
|
|
||||||
|
VideoCore::g_renderer->hw_rasterizer->NotifyFlush(
|
||||||
|
Memory::VirtualToPhysicalAddress(region.address), region.size);
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -31,7 +31,8 @@ enum class InterruptId : u8 {
|
|||||||
/// GSP command ID
|
/// GSP command ID
|
||||||
enum class CommandId : u32 {
|
enum class CommandId : u32 {
|
||||||
REQUEST_DMA = 0x00,
|
REQUEST_DMA = 0x00,
|
||||||
SET_COMMAND_LIST_LAST = 0x01,
|
/// Submits a commandlist for execution by the GPU.
|
||||||
|
SUBMIT_GPU_CMDLIST = 0x01,
|
||||||
|
|
||||||
// Fills a given memory range with a particular value
|
// Fills a given memory range with a particular value
|
||||||
SET_MEMORY_FILL = 0x02,
|
SET_MEMORY_FILL = 0x02,
|
||||||
@ -42,8 +43,8 @@ enum class CommandId : u32 {
|
|||||||
|
|
||||||
// Conceptionally similar to SET_DISPLAY_TRANSFER and presumable uses the same hardware path
|
// Conceptionally similar to SET_DISPLAY_TRANSFER and presumable uses the same hardware path
|
||||||
SET_TEXTURE_COPY = 0x04,
|
SET_TEXTURE_COPY = 0x04,
|
||||||
|
/// Flushes up to 3 cache regions in a single command.
|
||||||
SET_COMMAND_LIST_FIRST = 0x05,
|
CACHE_FLUSH = 0x05,
|
||||||
};
|
};
|
||||||
|
|
||||||
/// GSP thread interrupt relay queue
|
/// GSP thread interrupt relay queue
|
||||||
@ -106,7 +107,10 @@ struct Command {
|
|||||||
struct {
|
struct {
|
||||||
u32 address;
|
u32 address;
|
||||||
u32 size;
|
u32 size;
|
||||||
} set_command_list_last;
|
u32 flags;
|
||||||
|
u32 unused[3];
|
||||||
|
u32 do_flush;
|
||||||
|
} submit_gpu_cmdlist;
|
||||||
|
|
||||||
struct {
|
struct {
|
||||||
u32 start1;
|
u32 start1;
|
||||||
@ -138,6 +142,13 @@ struct Command {
|
|||||||
u32 flags;
|
u32 flags;
|
||||||
} texture_copy;
|
} texture_copy;
|
||||||
|
|
||||||
|
struct {
|
||||||
|
struct {
|
||||||
|
u32 address;
|
||||||
|
u32 size;
|
||||||
|
} regions[3];
|
||||||
|
} cache_flush;
|
||||||
|
|
||||||
u8 raw_data[0x1C];
|
u8 raw_data[0x1C];
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
Loading…
Reference in New Issue
Block a user