mirror of
https://github.com/MobileGL-Dev/MobileGL
synced 2026-11-07 01:53:24 +09:00
[MG_IntegrationTest] (Disaggregated): P5f close - pin zero residual reads on each backend frame
This commit is contained in:
@@ -2576,3 +2576,28 @@ if (MOBILEGL_BUILD_DISAGGREGATED)
|
||||
ENVIRONMENT "${MGL_ITEST_GLES_DUALBLOCK_ENVIRONMENT}\;MOBILEGL_LOG_FILE_PATH=${CMAKE_CURRENT_BINARY_DIR}/split-logs/DirectGLES.Split.DualBlock.TheTwoRolesHaveDistinctBlocks.log"
|
||||
)
|
||||
endif()
|
||||
|
||||
# P5f exit: observe every one of three real drawing frames on both backend roles.
|
||||
if (MOBILEGL_BUILD_DISAGGREGATED)
|
||||
foreach(backend DirectGLES DirectVulkan)
|
||||
if (backend STREQUAL "DirectGLES")
|
||||
set(p5f_rsp_label "integration-split")
|
||||
else()
|
||||
set(p5f_rsp_label "integration-magma-split")
|
||||
endif()
|
||||
mgl_itest_join_environment(p5f_rsp_environment
|
||||
"MOBILEGL_BACKEND_TYPE=${backend}" "MOBILEGL_TRANSPORT=inproc"
|
||||
"MOBILEGL_IPC_SERVER_PATH=${MGL_ITEST_SPLIT_SERVER_PATH}" "MGITEST_SPLIT_LANE=1"
|
||||
"MGITEST_P5F_RSP_LANE=1" "MOBILEGL_PIPE_STATS=1" "MOBILEGL_PIPE_STATS_PERIOD=1"
|
||||
"MOBILEGL_LOG_FILE_PATH=${CMAKE_CURRENT_BINARY_DIR}/p5f-rsp-${backend}.log"
|
||||
${MGL_ITEST_CAPABILITY_ENV} ${MGL_ITEST_COMMON_ENV})
|
||||
gtest_discover_tests(MobileGLIntegrationTest
|
||||
TEST_PREFIX "${backend}.Split.P5fRsp."
|
||||
TEST_FILTER "F1WireScenario.EachWireFrameHasZeroResidualPulls"
|
||||
DISCOVERY_TIMEOUT 30
|
||||
PROPERTIES LABELS "${p5f_rsp_label}\;integration-p5f-rsp"
|
||||
TIMEOUT ${MGL_ITEST_TIMEOUT}
|
||||
RESOURCE_LOCK "p5f-rsp-${backend}.log"
|
||||
ENVIRONMENT "${p5f_rsp_environment}")
|
||||
endforeach()
|
||||
endif()
|
||||
|
||||
@@ -1,6 +1,8 @@
|
||||
// f1 split-only pixel controls: every result depends on the migrated verb.
|
||||
#include "../Harness/ScenarioFixture.h"
|
||||
#include "../Harness/SplitRuntimePeek.h"
|
||||
#include "../Harness/PipeStatsWindow.h"
|
||||
#include "../Harness/SplitLane.h"
|
||||
#include <array>
|
||||
#include <cstdio>
|
||||
#include <cstdlib>
|
||||
@@ -93,6 +95,61 @@ protected:
|
||||
};
|
||||
}
|
||||
|
||||
// P5f exit: each published frame must have a real draw and server stamp, and
|
||||
// zero residual reads. Missing instrumentation is a failure rather than a false zero.
|
||||
TEST_F(F1WireScenario, EachWireFrameHasZeroResidualPulls) {
|
||||
if (!Ready()) return;
|
||||
if (!SplitLane::MarkerIsOne("MGITEST_P5F_RSP_LANE"))
|
||||
GTEST_SKIP() << "requires the dedicated per-frame stats lane";
|
||||
ASSERT_FALSE(PipeStatsWindow::LibraryLogPath().empty());
|
||||
Attach(GL_RGBA8);
|
||||
const char* fragment = R"(#version 430 core
|
||||
uniform float value;
|
||||
layout(location=0) out vec4 color;
|
||||
void main() { color = vec4(value, 0.25, 0.75, 1.0); }
|
||||
)";
|
||||
const GLuint program = BuildWireProgram({{GL_VERTEX_SHADER, kWireVertexIdTriangle},
|
||||
{GL_FRAGMENT_SHADER, fragment}});
|
||||
ASSERT_NE(program, 0u);
|
||||
GLuint vao = 0;
|
||||
glGenVertexArrays(1, &vao);
|
||||
glBindVertexArray(vao);
|
||||
glUseProgram(program);
|
||||
const GLint location = glGetUniformLocation(program, "value");
|
||||
ASSERT_GE(location, 0);
|
||||
glViewport(0, 0, 8, 8);
|
||||
glDisable(GL_BLEND);
|
||||
glDisable(GL_DEPTH_TEST);
|
||||
glDisable(GL_STENCIL_TEST);
|
||||
glDisable(GL_CULL_FACE);
|
||||
glDisable(GL_RASTERIZER_DISCARD);
|
||||
Gl().EndFrame(); // close setup's counter window
|
||||
for (int frame = 0; frame < 3; ++frame) {
|
||||
const float value = float(frame + 1) / 4.0f;
|
||||
glUniform1f(location, value);
|
||||
glDrawArrays(GL_TRIANGLES, 0, 3);
|
||||
std::array<GLubyte, 4> pixel{};
|
||||
glReadPixels(3, 2, 1, 1, GL_RGBA, GL_UNSIGNED_BYTE, pixel.data());
|
||||
ASSERT_EQ(FirstGLError(), GLenum(GL_NO_ERROR));
|
||||
EXPECT_NEAR(pixel[0], value * 255.0f, 1) << "frame " << frame;
|
||||
EXPECT_NEAR(pixel[1], 64, 1);
|
||||
EXPECT_NEAR(pixel[2], 191, 1);
|
||||
EXPECT_EQ(pixel[3], 255);
|
||||
Gl().EndFrame();
|
||||
const auto window = PipeStatsWindow::LastFromLaneLog();
|
||||
ASSERT_TRUE(window.found) << "P5f rsp window missing on frame " << frame;
|
||||
EXPECT_GT(PipeStatsWindow::CounterOrAbsent(window, "draws"), 0) << window.line;
|
||||
EXPECT_GT(PipeStatsWindow::CounterOrAbsent(window, "vbs"), 0) << window.line;
|
||||
EXPECT_EQ(PipeStatsWindow::CounterOrAbsent(window, "rsp"), 0)
|
||||
<< "P5f residual pull on frame " << frame << ": " << window.line;
|
||||
RecordProperty("p5f_frame_" + std::to_string(frame), window.line);
|
||||
}
|
||||
glUseProgram(0);
|
||||
glBindVertexArray(0);
|
||||
glDeleteVertexArrays(1, &vao);
|
||||
glDeleteProgram(program);
|
||||
}
|
||||
|
||||
TEST_F(F1WireScenario, ClearBufferfvPixels) {
|
||||
// Red once (executed, reverted): zero the clear record values; F1.ClearBufferfv.pixels fails.
|
||||
if (!Ready()) return;
|
||||
|
||||
@@ -381,12 +381,8 @@ void main() { oColor = vec4(vColor, 1.0); }
|
||||
"a green strict lane containing only entries like this one would mean the knob "
|
||||
"was never armed rather than that the debt was paid (ID-115): "
|
||||
<< window.line;
|
||||
EXPECT_TRUE(residual == 0 || residual >= draws)
|
||||
<< "rsp neither scales with draws nor is zero (" << residual << " vs " << draws
|
||||
<< "). ID-119: while this phase's draw-path debt is unretired every draw pulls at "
|
||||
"least one BARRIER-PULLED row, and the retirement is visible as rsp ceasing to "
|
||||
"scale with draws - a value strictly between is neither state: "
|
||||
<< window.line;
|
||||
EXPECT_EQ(residual, 0)
|
||||
<< "P5f exit: a drawing frame still reads client residual state: " << window.line;
|
||||
}
|
||||
|
||||
} // namespace MGITest
|
||||
|
||||
Reference in New Issue
Block a user