Skip to content

Commit

Permalink
gapii: Work around tracing issue with PCS on S7.
Browse files Browse the repository at this point in the history
Fixes: #1456
  • Loading branch information
ben-clayton committed Dec 6, 2017
1 parent 27a4ce9 commit 247f126
Showing 1 changed file with 57 additions and 4 deletions.
61 changes: 57 additions & 4 deletions gapii/cc/spy_disable_precompiled_shaders.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,8 @@

#include "gapis/api/gfxtrace.pb.h"

#include <core/cc/id.h>

// This file contains a number of GLES method 'overrides' to optionally lie to the
// application about the driver not supporting precompiled shaders or programs.

Expand All @@ -27,6 +29,39 @@ namespace {
const char* kOESGetProgramBinary = "OES_get_program_binary";
const char* kReplacementExtension = "__GAPID_PCS_DISABLED__"; // Must be the same length as kOESGetProgramBinary

#define NELEM(x) (sizeof(x) / sizeof(x[0]))

// HACK: Workaround for devices that do not check the error status after calling
// glProgramBinary() or glProgramBinaryOES(). As the error is not checked, this
// can cause logic later on in the application to fail, sometimes leading to
// application termination.
// See https://github.com/google/gapid/issues/1456#issuecomment-349611106 for
// more information.
const core::Id kProgramHashesForNoError[] = {
// 0xe14cc04bd723f9c2c46eeef948b08a379f090235
{0xe1, 0x4c, 0xc0, 0x4b, 0xd7, 0x23, 0xf9, 0xc2, 0xc4, 0x6e,
0xee, 0xf9, 0x48, 0xb0, 0x8a, 0x37, 0x9f, 0x09, 0x02, 0x35},

// 0xc231a3a4b597f45244a4745fecdcba918bb8eacc
{0xc2, 0x31, 0xa3, 0xa4, 0xb5, 0x97, 0xf4, 0x52, 0x44, 0xa4,
0x74, 0x5f, 0xec, 0xdc, 0xba, 0x91, 0x8b, 0xb8, 0xea, 0xcc},

// 0x55626b9bc73964f52fd5bcf6710659df97997d83
{0x55, 0x62, 0x6b, 0x9b, 0xc7, 0x39, 0x64, 0xf5, 0x2f, 0xd5,
0xbc, 0xf6, 0x71, 0x06, 0x59, 0xdf, 0x97, 0x99, 0x7d, 0x83},
};

bool shouldErrorForProgram(const core::Id& id) {
for (int i = 0; i < NELEM(kProgramHashesForNoError); i++) {
if (id == kProgramHashesForNoError[i]) {
GAPID_WARNING("Not setting error for program with ID (blacklisted): %s", id.string().c_str());
return false;
}
}
GAPID_INFO("Program ID: %s", id.string().c_str());
return true;
}

} // anonymous namespace

using namespace gapii::GLenum;
Expand All @@ -36,9 +71,16 @@ namespace gapii {
void Spy::glProgramBinary(CallObserver* observer, uint32_t program, uint32_t binary_format, void* binary,
int32_t binary_size) {
if (mDisablePrecompiledShaders) {
GAPID_WARNING("glProgramBinary(%" PRIu32 ", 0x%X, %p, %" PRId32 ") "
"called when precompiled shaders are disabled",
program, binary_format, binary, binary_size);

// GL_INVALID_ENUM is generated if binaryformat is not a supported format returned in
// GL_SHADER_BINARY_FORMATS.
setFakeGlError(observer, GL_INVALID_ENUM);
auto id = core::Id::Hash(binary, binary_size);
if (shouldErrorForProgram(id)) {
setFakeGlError(observer, GL_INVALID_ENUM);
}

observer->encode(cmd::glProgramBinary{
observer->getCurrentThread(), program, binary_format, binary, binary_size
Expand All @@ -56,9 +98,16 @@ void Spy::glProgramBinary(CallObserver* observer, uint32_t program, uint32_t bin
void Spy::glProgramBinaryOES(CallObserver* observer, uint32_t program, uint32_t binary_format, void* binary,
int32_t binary_size) {
if (mDisablePrecompiledShaders) {
GAPID_WARNING("glProgramBinaryOES(%" PRIu32 ", 0x%X, %p, %" PRId32 ") "
"called when precompiled shaders are disabled",
program, binary_format, binary, binary_size);

// GL_INVALID_ENUM is generated if binaryformat is not a supported format returned in
// GL_SHADER_BINARY_FORMATS.
setFakeGlError(observer, GL_INVALID_ENUM);
auto id = core::Id::Hash(binary, binary_size);
if (shouldErrorForProgram(id)) {
setFakeGlError(observer, GL_INVALID_ENUM);
}

observer->encode(cmd::glProgramBinaryOES{
observer->getCurrentThread(), program, binary_format, binary, binary_size
Expand All @@ -76,6 +125,10 @@ void Spy::glProgramBinaryOES(CallObserver* observer, uint32_t program, uint32_t
void Spy::glShaderBinary(CallObserver* observer, int32_t count, uint32_t* shaders, uint32_t binary_format, void* binary,
int32_t binary_size) {
if (mDisablePrecompiledShaders) {
GAPID_WARNING("glShaderBinary(%" PRId32 ", %p, 0x%X, %p, %" PRId32 ") "
"called when precompiled shaders are disabled",
count, shaders, binary_format, binary, binary_size);

// GL_INVALID_ENUM is generated if binaryFormat is not a value recognized by the implementation.
setFakeGlError(observer, GL_INVALID_ENUM);

Expand Down Expand Up @@ -136,7 +189,7 @@ GLubyte* Spy::glGetString(CallObserver* observer, uint32_t name) {
if (start != std::string::npos) {
static std::string copy = list;
copy.replace(start, strlen(kOESGetProgramBinary), kReplacementExtension);
// TODO: write atom.
// TODO: write command.
return reinterpret_cast<GLubyte*>(const_cast<char*>(copy.c_str()));
}
}
Expand All @@ -147,7 +200,7 @@ GLubyte* Spy::glGetStringi(CallObserver* observer, uint32_t name, GLuint index)
if (mDisablePrecompiledShaders && (name == GL_EXTENSIONS)) {
const char* extension = reinterpret_cast<const char*>(GlesSpy::mImports.glGetStringi(name, index));
if (strcmp(extension, kOESGetProgramBinary) == 0) {
// TODO: write atom.
// TODO: write command.
return reinterpret_cast<GLubyte*>(const_cast<char*>(kReplacementExtension));
}
}
Expand Down

0 comments on commit 247f126

Please sign in to comment.