Buffer_Cache: Implement flushing.

This commit is contained in:
Fernando Sahmkow 2019-07-20 12:54:31 -04:00 committed by FernandoS27
parent de8ff8a1c6
commit 6ce2c85047
2 changed files with 30 additions and 1 deletions

View file

@ -79,12 +79,16 @@ public:
} }
void Map(std::size_t max_size) { void Map(std::size_t max_size) {
std::lock_guard lock{mutex};
std::tie(buffer_ptr, buffer_offset_base, invalidated) = stream_buffer->Map(max_size, 4); std::tie(buffer_ptr, buffer_offset_base, invalidated) = stream_buffer->Map(max_size, 4);
buffer_offset = buffer_offset_base; buffer_offset = buffer_offset_base;
} }
/// Finishes the upload stream, returns true on bindings invalidation. /// Finishes the upload stream, returns true on bindings invalidation.
bool Unmap() { bool Unmap() {
std::lock_guard lock{mutex};
stream_buffer->Unmap(buffer_offset - buffer_offset_base); stream_buffer->Unmap(buffer_offset - buffer_offset_base);
return std::exchange(invalidated, false); return std::exchange(invalidated, false);
} }
@ -103,7 +107,15 @@ public:
void FlushRegion(CacheAddr addr, std::size_t size) { void FlushRegion(CacheAddr addr, std::size_t size) {
std::lock_guard lock{mutex}; std::lock_guard lock{mutex};
// TODO std::vector<MapInterval> objects = GetMapsInRange(addr, size);
std::sort(objects.begin(), objects.end(), [](const MapInterval& a, const MapInterval& b) {
return a->GetModificationTick() < b->GetModificationTick();
});
for (auto& object : objects) {
if (object->IsModified() && object->IsRegistered()) {
FlushMap(object);
}
}
} }
/// Mark the specified region as being invalidated /// Mark the specified region as being invalidated
@ -205,11 +217,13 @@ private:
CacheAddr new_start = cache_addr; CacheAddr new_start = cache_addr;
CacheAddr new_end = cache_addr_end; CacheAddr new_end = cache_addr_end;
bool write_inheritance = false; bool write_inheritance = false;
bool modified_inheritance = false;
// Calculate new buffer parameters // Calculate new buffer parameters
for (auto& overlap : overlaps) { for (auto& overlap : overlaps) {
new_start = std::min(overlap->GetStart(), new_start); new_start = std::min(overlap->GetStart(), new_start);
new_end = std::max(overlap->GetEnd(), new_end); new_end = std::max(overlap->GetEnd(), new_end);
write_inheritance |= overlap->IsWritten(); write_inheritance |= overlap->IsWritten();
modified_inheritance |= overlap->IsModified();
} }
GPUVAddr new_gpu_addr = gpu_addr + new_start - cache_addr; GPUVAddr new_gpu_addr = gpu_addr + new_start - cache_addr;
for (auto& overlap : overlaps) { for (auto& overlap : overlaps) {
@ -217,6 +231,9 @@ private:
} }
UpdateBlock(block, new_start, new_end, overlaps); UpdateBlock(block, new_start, new_end, overlaps);
MapInterval new_map = CreateMap(new_start, new_end, new_gpu_addr); MapInterval new_map = CreateMap(new_start, new_end, new_gpu_addr);
if (modified_inheritance) {
new_map->MarkAsModified(true, GetModifiedTicks());
}
Register(new_map, write_inheritance); Register(new_map, write_inheritance);
return new_map; return new_map;
} }
@ -258,6 +275,14 @@ private:
return ++modified_ticks; return ++modified_ticks;
} }
void FlushMap(MapInterval map) {
std::size_t size = map->GetEnd() - map->GetStart();
TBuffer block = blocks[map->GetStart() >> block_page_bits];
u8* host_ptr = FromCacheAddr(map->GetStart());
DownloadBlockData(block, block->GetOffset(map->GetStart()), size, host_ptr);
map->MarkAsModified(false, 0);
}
BufferInfo StreamBufferUpload(const void* raw_pointer, std::size_t size, BufferInfo StreamBufferUpload(const void* raw_pointer, std::size_t size,
std::size_t alignment) { std::size_t alignment) {
AlignBuffer(alignment); AlignBuffer(alignment);

View file

@ -7,12 +7,15 @@
#include <glad/glad.h> #include <glad/glad.h>
#include "common/assert.h" #include "common/assert.h"
#include "common/microprofile.h"
#include "video_core/renderer_opengl/gl_buffer_cache.h" #include "video_core/renderer_opengl/gl_buffer_cache.h"
#include "video_core/renderer_opengl/gl_rasterizer.h" #include "video_core/renderer_opengl/gl_rasterizer.h"
#include "video_core/renderer_opengl/gl_resource_manager.h" #include "video_core/renderer_opengl/gl_resource_manager.h"
namespace OpenGL { namespace OpenGL {
MICROPROFILE_DEFINE(OpenGL_Buffer_Download, "OpenGL", "Buffer Download", MP_RGB(192, 192, 128));
CachedBufferBlock::CachedBufferBlock(CacheAddr cache_addr, const std::size_t size) CachedBufferBlock::CachedBufferBlock(CacheAddr cache_addr, const std::size_t size)
: VideoCommon::BufferBlock{cache_addr, size} { : VideoCommon::BufferBlock{cache_addr, size} {
gl_buffer.Create(); gl_buffer.Create();
@ -53,6 +56,7 @@ void OGLBufferCache::UploadBlockData(const Buffer& buffer, std::size_t offset, s
void OGLBufferCache::DownloadBlockData(const Buffer& buffer, std::size_t offset, std::size_t size, void OGLBufferCache::DownloadBlockData(const Buffer& buffer, std::size_t offset, std::size_t size,
u8* data) { u8* data) {
MICROPROFILE_SCOPE(OpenGL_Buffer_Download);
glGetNamedBufferSubData(*buffer->GetHandle(), static_cast<GLintptr>(offset), glGetNamedBufferSubData(*buffer->GetHandle(), static_cast<GLintptr>(offset),
static_cast<GLsizeiptr>(size), data); static_cast<GLsizeiptr>(size), data);
} }