mirror of
https://github.com/GTNewHorizons/Angelica.git
synced 2026-11-08 12:35:01 +00:00
Fix tests & SDL-GPU framebuffers losing attachments on resize or texture delete (#2282)
This commit is contained in:
1 parent
e98c927a93
commit
ed260a34c4
5 files changed
+55
-62
No files matched your search
@@ -4660,9 +4660,7 @@ public class SDLGPURenderBackend extends RenderBackend {
|
||||
|
||||
@Override
|
||||
public void renderbufferStorage(int target, int internalformat, int width, int height) {
|
||||
if (boundRenderbufferId == 0) return;
|
||||
resourceManager.deleteTexture(boundRenderbufferId);
|
||||
resourceManager.createTexture(boundRenderbufferId, GL11.GL_TEXTURE_2D, internalformat, width, height, 1, 1);
|
||||
texStorageImpl(s(), boundRenderbufferId, GL11.GL_TEXTURE_2D, internalformat, width, height, 1, 1);
|
||||
}
|
||||
|
||||
private boolean warnedMSAARenderbuffer = false;
|
||||
|
||||
+3
-12
@@ -331,19 +331,9 @@ public final class ResourceManager {
|
||||
fboAttachedGlIds.remove(glId);
|
||||
for (FboState fbo : fboStates.values()) {
|
||||
for (int i = 0; i < ContextState.MAX_COLOR_ATTACHMENTS; i++) {
|
||||
if (fbo.colorGlIds[i] == glId) {
|
||||
fbo.colorTextures[i] = 0;
|
||||
fbo.colorGlIds[i] = 0;
|
||||
fbo.colorFormats[i] = 0;
|
||||
fbo.targetsDirty = true;
|
||||
}
|
||||
}
|
||||
if (fbo.depthGlId == glId) {
|
||||
fbo.depthTexture = 0;
|
||||
fbo.depthGlId = 0;
|
||||
fbo.depthFormat = 0;
|
||||
fbo.targetsDirty = true;
|
||||
if (fbo.colorGlIds[i] == glId) fbo.detachColor(i);
|
||||
}
|
||||
if (fbo.depthGlId == glId) fbo.detachDepth();
|
||||
}
|
||||
texSamplerStates.remove(glId);
|
||||
} finally {
|
||||
@@ -514,6 +504,7 @@ public final class ResourceManager {
|
||||
if (fbo.colorGlIds[i] == glId) {
|
||||
fbo.colorTextures[i] = newHandle;
|
||||
fbo.targetsDirty = true;
|
||||
fbo.cachedFormatsDirty = true;
|
||||
if (meta != null) {
|
||||
fbo.colorFormats[i] = meta.sdlFormat();
|
||||
if (i == 0) {
|
||||
|
||||
+21
@@ -455,6 +455,27 @@ class GlsmSdlAttachmentClearTest {
|
||||
GlsmSdlHeadlessRig.bindTarget();
|
||||
}
|
||||
|
||||
@Test
|
||||
void clearReachesARenderbufferRespecifiedWhileAttached() {
|
||||
final int rb = GLStateManager.glGenRenderbuffers();
|
||||
GLStateManager.glBindRenderbuffer(GL30.GL_RENDERBUFFER, rb);
|
||||
GLStateManager.glRenderbufferStorage(GL30.GL_RENDERBUFFER, GL11.GL_RGBA8, SIZE / 4, SIZE / 4);
|
||||
final int fbo = GLStateManager.glGenFramebuffers();
|
||||
GLStateManager.glBindFramebuffer(GL30.GL_FRAMEBUFFER, fbo);
|
||||
GLStateManager.glFramebufferRenderbuffer(GL30.GL_FRAMEBUFFER, GL30.GL_COLOR_ATTACHMENT0, GL30.GL_RENDERBUFFER, rb);
|
||||
|
||||
GLStateManager.glRenderbufferStorage(GL30.GL_RENDERBUFFER, GL11.GL_RGBA8, SIZE, SIZE);
|
||||
GLStateManager.glViewport(0, 0, SIZE, SIZE);
|
||||
GLStateManager.glClearColor(1.0f, 0.0f, 0.0f, 1.0f);
|
||||
GLStateManager.glClear(GL11.GL_COLOR_BUFFER_BIT);
|
||||
|
||||
GlsmSdlHeadlessRig.assertUniform(GlsmSdlHeadlessRig.readTarget(), RED, "respecified renderbuffer must stay attached");
|
||||
|
||||
GLStateManager.glDeleteFramebuffers(fbo);
|
||||
GLStateManager.glDeleteRenderbuffers(rb);
|
||||
GlsmSdlHeadlessRig.bindTarget();
|
||||
}
|
||||
|
||||
private static int createColorTexture() {
|
||||
return createColorTexture(GL11.GL_RGBA8, GL11.GL_RGBA);
|
||||
}
|
||||
|
||||
-47
@@ -84,53 +84,6 @@ class ResourceManagerConcurrencyTest {
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
void textureDeleteAndFboCleanupAreAtomic() throws Exception {
|
||||
final ResourceManager rm = SdlTestRig.resourceManager();
|
||||
final int textureId = 42;
|
||||
final int fboId = rm.genFboId();
|
||||
final FboState fbo = rm.createFbo(fboId);
|
||||
fbo.colorGlIds[0] = textureId;
|
||||
fbo.colorTextures[0] = 0xDEADBEEFL;
|
||||
fbo.colorFormats[0] = 1;
|
||||
|
||||
final AtomicBoolean done = new AtomicBoolean(false);
|
||||
final AtomicBoolean violation = new AtomicBoolean(false);
|
||||
final CountDownLatch readerStarted = new CountDownLatch(1);
|
||||
|
||||
final Thread reader = new Thread(() -> {
|
||||
readerStarted.countDown();
|
||||
int iters = 0;
|
||||
while (!done.get() && iters < 5_000_000) {
|
||||
final FboState f = rm.getFbo(fboId);
|
||||
if (f != null) {
|
||||
final boolean idSet = f.colorGlIds[0] == textureId;
|
||||
final boolean handleSet = f.colorTextures[0] != 0 || f.colorFormats[0] != 0;
|
||||
if (idSet != handleSet) {
|
||||
violation.set(true);
|
||||
return;
|
||||
}
|
||||
}
|
||||
iters++;
|
||||
}
|
||||
}, "reader");
|
||||
reader.start();
|
||||
readerStarted.await();
|
||||
|
||||
Thread.sleep(10);
|
||||
rm.deleteTexture(textureId);
|
||||
Thread.sleep(20);
|
||||
done.set(true);
|
||||
reader.join(2000);
|
||||
|
||||
assertFalse(violation.get(), "Reader observed half-cleaned FBO state");
|
||||
|
||||
final FboState f = rm.getFbo(fboId);
|
||||
assertEquals(0, f.colorGlIds[0]);
|
||||
assertEquals(0L, f.colorTextures[0]);
|
||||
assertEquals(0, f.colorFormats[0]);
|
||||
}
|
||||
|
||||
@Test
|
||||
void concurrentCreateLookupDelete_noRaces() throws Exception {
|
||||
final ResourceManager rm = SdlTestRig.resourceManager();
|
||||
|
||||
+30
@@ -1,11 +1,14 @@
|
||||
package com.gtnewhorizons.angelica.sdlgpu.resource;
|
||||
|
||||
|
||||
import com.gtnewhorizons.angelica.glsm.testutil.Reflect;
|
||||
import com.gtnewhorizons.angelica.sdlgpu.SdlTestRig;
|
||||
import com.gtnewhorizons.angelica.sdlgpu.frame.ContextState;
|
||||
import org.junit.jupiter.api.Test;
|
||||
import org.junit.jupiter.params.ParameterizedTest;
|
||||
import org.junit.jupiter.params.provider.Arguments;
|
||||
import org.junit.jupiter.params.provider.MethodSource;
|
||||
import org.lwjgl.opengl.GL11;
|
||||
|
||||
import java.util.function.Consumer;
|
||||
import java.util.stream.Stream;
|
||||
@@ -166,4 +169,31 @@ class SDLGPUFboTargetCacheTest {
|
||||
assertFalse(fbo.targetsDirty);
|
||||
assertFalse(fbo.cachedFormatsDirty);
|
||||
}
|
||||
|
||||
@Test
|
||||
void textureDeleteAndRespecUpdateAttachedFbos() {
|
||||
final ResourceManager rm = SdlTestRig.resourceManager();
|
||||
final FboState fbo = rm.createFbo(rm.genFboId());
|
||||
fbo.colorGlIds[0] = 42; fbo.colorTextures[0] = 0xAAAAL; fbo.colorFormats[0] = 1;
|
||||
fbo.colorGlIds[1] = 43; fbo.colorTextures[1] = 0xBBBBL; fbo.colorFormats[1] = 1; fbo.colorLevels[1] = 1;
|
||||
fbo.depthGlId = 43; fbo.depthTexture = 0xBBBBL; fbo.depthLevel = 1;
|
||||
fbo.colorAttachmentCount = 2;
|
||||
|
||||
fbo.cachedFormatsDirty = false;
|
||||
Reflect.invoke(rm, "restoreTextureHandle", new Class<?>[] { int.class, long.class, ResourceManager.TextureMeta.class }, 42, 0xCCCCL, new ResourceManager.TextureMeta(GL11.GL_TEXTURE_2D, GL11.GL_RGBA8, 2, 16, 16, 1, 1, 0));
|
||||
rm.refreshTextureReferences(42);
|
||||
assertEquals(0xCCCCL, fbo.colorTextures[0]);
|
||||
assertEquals(2, fbo.colorFormats[0]);
|
||||
assertTrue(fbo.cachedFormatsDirty, "a respecified color attachment must rebuild the pipeline color formats");
|
||||
|
||||
fbo.cachedFormatsDirty = false;
|
||||
rm.deleteTexture(43);
|
||||
assertEquals(0, fbo.colorGlIds[1]);
|
||||
assertEquals(0, fbo.colorLevels[1]);
|
||||
assertEquals(1, fbo.colorAttachmentCount);
|
||||
assertTrue(fbo.cachedFormatsDirty, "a deleted color attachment must rebuild the pipeline color formats");
|
||||
assertEquals(0, fbo.depthGlId);
|
||||
assertEquals(0, fbo.depthLevel);
|
||||
assertEquals(42, fbo.colorGlIds[0]);
|
||||
}
|
||||
}
|
||||
Reference in new issue
Block a user