Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Check for closest render-to-tex, ignore high bits of fb addr #6383

Merged
merged 4 commits into from
Jun 21, 2014
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
18 changes: 9 additions & 9 deletions GPU/GLES/Framebuffer.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -876,7 +876,7 @@ void FramebufferManager::DoSetRenderFrameBuffer() {
gstate_c.cutRTOffsetX = 0;
for (i = 0; i < vfbs_.size(); ++i) {
VirtualFramebuffer *v = vfbs_[i];
if (MaskedEqual(v->fb_address, fb_address)) {
if (v->fb_address == fb_address) {
vfb = v;
// Update fb stride in case it changed
vfb->fb_stride = fb_stride;
Expand Down Expand Up @@ -935,7 +935,7 @@ void FramebufferManager::DoSetRenderFrameBuffer() {
float renderWidthFactor = (float)PSP_CoreParameter().renderWidth / 480.0f;
float renderHeightFactor = (float)PSP_CoreParameter().renderHeight / 272.0f;

if (hackForce04154000Download_ && MaskedEqual(fb_address, 0x04154000)) {
if (hackForce04154000Download_ && fb_address == 0x00154000) {
renderWidthFactor = 1.0;
renderHeightFactor = 1.0;
}
Expand Down Expand Up @@ -997,18 +997,18 @@ void FramebufferManager::DoSetRenderFrameBuffer() {
// Let's check for depth buffer overlap. Might be interesting.
bool sharingReported = false;
for (size_t i = 0, end = vfbs_.size(); i < end; ++i) {
if (vfbs_[i]->z_stride != 0 && MaskedEqual(fb_address, vfbs_[i]->z_address)) {
if (vfbs_[i]->z_stride != 0 && fb_address == vfbs_[i]->z_address) {
// If it's clearing it, most likely it just needs more video memory.
// Technically it could write something interesting and the other might not clear, but that's not likely.
if (!gstate.isModeClear() || !gstate.isClearModeColorMask() || !gstate.isClearModeAlphaMask()) {
WARN_LOG_REPORT(SCEGE, "FBO created from existing depthbuffer as color, %08x/%08x and %08x/%08x", fb_address, z_address, vfbs_[i]->fb_address, vfbs_[i]->z_address);
}
} else if (z_stride != 0 && MaskedEqual(z_address, vfbs_[i]->fb_address)) {
} else if (z_stride != 0 && z_address == vfbs_[i]->fb_address) {
// If it's clearing it, then it's probably just the reverse of the above case.
if (!gstate.isModeClear() || !gstate.isClearModeDepthMask()) {
WARN_LOG_REPORT(SCEGE, "FBO using existing buffer as depthbuffer, %08x/%08x and %08x/%08x", fb_address, z_address, vfbs_[i]->fb_address, vfbs_[i]->z_address);
}
} else if (vfbs_[i]->z_stride != 0 && MaskedEqual(z_address, vfbs_[i]->z_address) && fb_address != vfbs_[i]->fb_address && !sharingReported) {
} else if (vfbs_[i]->z_stride != 0 && z_address == vfbs_[i]->z_address && fb_address != vfbs_[i]->fb_address && !sharingReported) {
// This happens a lot, but virtually always it's cleared.
// It's possible the other might not clear, but when every game is reported it's not useful.
if (!gstate.isModeClear() || !gstate.isClearModeDepthMask()) {
Expand Down Expand Up @@ -1115,7 +1115,7 @@ void FramebufferManager::BlitFramebufferDepth(VirtualFramebuffer *sourceframebuf
return;
}

if (MaskedEqual(sourceframebuffer->z_address, targetframebuffer->z_address) &&
if (sourceframebuffer->z_address == targetframebuffer->z_address &&
sourceframebuffer->z_stride != 0 &&
targetframebuffer->z_stride != 0 &&
sourceframebuffer->renderWidth == targetframebuffer->renderWidth &&
Expand Down Expand Up @@ -1180,7 +1180,7 @@ void FramebufferManager::BindFramebufferColor(VirtualFramebuffer *framebuffer, b
if (GPUStepping::IsStepping()) {
skipCopy = true;
}
if (!skipCopy && currentRenderVfb_ && MaskedEqual(framebuffer->fb_address, gstate.getFrameBufRawAddress())) {
if (!skipCopy && currentRenderVfb_ && framebuffer->fb_address == gstate.getFrameBufRawAddress()) {
// TODO: Maybe merge with bvfbs_? Not sure if those could be packing, and they're created at a different size.
FBO *renderCopy = GetTempFBO(framebuffer->renderWidth, framebuffer->renderHeight, framebuffer->colorDepth);
if (renderCopy) {
Expand Down Expand Up @@ -1342,7 +1342,7 @@ void FramebufferManager::CopyDisplayToOutput() {
}

inline bool FramebufferManager::ShouldDownloadFramebuffer(const VirtualFramebuffer *vfb) const {
return updateVRAM_ || (hackForce04154000Download_ && MaskedEqual(vfb->fb_address, 0x04154000));
return updateVRAM_ || (hackForce04154000Download_ && vfb->fb_address == 0x00154000);
}

void FramebufferManager::ReadFramebufferToMemory(VirtualFramebuffer *vfb, bool sync, int x, int y, int w, int h) {
Expand All @@ -1363,7 +1363,7 @@ void FramebufferManager::ReadFramebufferToMemory(VirtualFramebuffer *vfb, bool s
// We maintain a separate vector of framebuffer objects for blitting.
for (size_t i = 0; i < bvfbs_.size(); ++i) {
VirtualFramebuffer *v = bvfbs_[i];
if (MaskedEqual(v->fb_address, vfb->fb_address) && v->format == vfb->format) {
if (v->fb_address == vfb->fb_address && v->format == vfb->format) {
if (v->bufferWidth == vfb->bufferWidth && v->bufferHeight == vfb->bufferHeight) {
nvfb = v;
v->fb_stride = vfb->fb_stride;
Expand Down
36 changes: 22 additions & 14 deletions GPU/GLES/TextureCache.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -221,7 +221,12 @@ void TextureCache::ClearNextFrame() {
void TextureCache::AttachFramebufferValid(TexCacheEntry *entry, VirtualFramebuffer *framebuffer, const AttachedFramebufferInfo &fbInfo) {
const bool hasInvalidFramebuffer = entry->framebuffer == 0 || entry->invalidHint == -1;
const bool hasOlderFramebuffer = entry->framebuffer != 0 && entry->framebuffer->last_frame_render < framebuffer->last_frame_render;
if (hasInvalidFramebuffer || hasOlderFramebuffer) {
bool hasFartherFramebuffer = false;
if (!hasInvalidFramebuffer && !hasOlderFramebuffer) {
// If it's valid, but the offset is greater, then we still win.
hasFartherFramebuffer = fbTexInfo_[entry->addr].yOffset > fbInfo.yOffset;
}
if (hasInvalidFramebuffer || hasOlderFramebuffer || hasFartherFramebuffer) {
entry->framebuffer = framebuffer;
entry->invalidHint = 0;
entry->status &= ~TextureCache::TexCacheEntry::STATUS_DEPALETTIZE;
Expand Down Expand Up @@ -260,18 +265,16 @@ bool TextureCache::AttachFramebuffer(TexCacheEntry *entry, u32 address, VirtualF
return false;

DEBUG_LOG(G3D, "Render to texture detected at %08x!", address);
if (!entry->framebuffer || entry->invalidHint == -1) {
if (framebuffer->fb_stride != entry->bufw) {
WARN_LOG_REPORT_ONCE(diffStrides1, G3D, "Render to texture with different strides %d != %d", entry->bufw, framebuffer->fb_stride);
}
if (entry->format != framebuffer->format) {
WARN_LOG_REPORT_ONCE(diffFormat1, G3D, "Render to texture with different formats %d != %d", entry->format, framebuffer->format);
// Let's avoid rendering when we know the format is wrong. May be a video/etc. updating memory.
DetachFramebuffer(entry, address, framebuffer);
} else {
AttachFramebufferValid(entry, framebuffer, fbInfo);
return true;
}
if (framebuffer->fb_stride != entry->bufw) {
WARN_LOG_REPORT_ONCE(diffStrides1, G3D, "Render to texture with different strides %d != %d", entry->bufw, framebuffer->fb_stride);
}
if (entry->format != framebuffer->format) {
WARN_LOG_REPORT_ONCE(diffFormat1, G3D, "Render to texture with different formats %d != %d", entry->format, framebuffer->format);
// Let's avoid rendering when we know the format is wrong. May be a video/etc. updating memory.
DetachFramebuffer(entry, address, framebuffer);
} else {
AttachFramebufferValid(entry, framebuffer, fbInfo);
return true;
}
} else {
// Apply to buffered mode only.
Expand Down Expand Up @@ -317,7 +320,6 @@ bool TextureCache::AttachFramebuffer(TexCacheEntry *entry, u32 address, VirtualF
WARN_LOG_REPORT_ONCE(subareaClut, G3D, "Render to texture using CLUT with offset at %08x +%dx%d", address, fbInfo.xOffset, fbInfo.yOffset);
}
AttachFramebufferValid(entry, framebuffer, fbInfo);
fbTexInfo_[entry->addr] = fbInfo;
entry->status |= TexCacheEntry::STATUS_DEPALETTIZE;
// We'll validate it compiles later.
return true;
Expand Down Expand Up @@ -1120,6 +1122,12 @@ bool TextureCache::SetOffsetTexture(u32 offset) {
}
}

if (success) {
SetTextureFramebuffer(entry, entry->framebuffer);
lastBoundTexture = -1;
entry->lastFrame = gpuStats.numFlips;
}

return success;
}

Expand Down
6 changes: 3 additions & 3 deletions GPU/GPUState.h
Original file line number Diff line number Diff line change
Expand Up @@ -215,13 +215,13 @@ struct GPUgstate
float tgenMatrix[12];
float boneMatrix[12 * 8]; // Eight bone matrices.

// Framebuffer
u32 getFrameBufRawAddress() const { return (fbptr & 0xFFFFFF) | ((fbwidth & 0xFF0000) << 8); }
// We ignore the high bits of the framebuffer in fbwidth - even 0x08000000 renders to vRAM.
u32 getFrameBufRawAddress() const { return (fbptr & 0xFFFFFF); }
// 0x44000000 is uncached VRAM.
u32 getFrameBufAddress() const { return 0x44000000 | getFrameBufRawAddress(); }
GEBufferFormat FrameBufFormat() const { return static_cast<GEBufferFormat>(framebufpixformat & 3); }
int FrameBufStride() const { return fbwidth&0x7FC; }
u32 getDepthBufRawAddress() const { return (zbptr & 0xFFFFFF) | ((zbwidth & 0xFF0000) << 8); }
u32 getDepthBufRawAddress() const { return (zbptr & 0xFFFFFF); }
u32 getDepthBufAddress() const { return 0x44000000 | getDepthBufRawAddress(); }
int DepthBufStride() const { return zbwidth&0x7FC; }

Expand Down