aboutsummaryrefslogtreecommitdiffstats
path: root/emulator
diff options
context:
space:
mode:
authorbohu <bohu@google.com>2014-11-06 18:47:49 +0000
committerGerrit Code Review <noreply-gerritcodereview@google.com>2014-11-06 18:47:49 +0000
commit7a7798075ebb730b9594f283706f370abe60fbcf (patch)
treed3a992a79fc538c245d30903875477ed878b15cc /emulator
parent4f80477b0f021b3e099e792add4c5badd42aa9bf (diff)
parentbc42a0598f6e5ffb0ebd646e0bad8d94c50ec193 (diff)
downloadsdk-7a7798075ebb730b9594f283706f370abe60fbcf.zip
sdk-7a7798075ebb730b9594f283706f370abe60fbcf.tar.gz
sdk-7a7798075ebb730b9594f283706f370abe60fbcf.tar.bz2
Merge "Properly handle shader deletion"
Diffstat (limited to 'emulator')
-rw-r--r--emulator/opengl/host/libs/Translator/GLES_V2/GLESv2Imp.cpp49
-rw-r--r--emulator/opengl/host/libs/Translator/GLES_V2/ShaderParser.cpp8
-rw-r--r--emulator/opengl/host/libs/Translator/GLES_V2/ShaderParser.h7
3 files changed, 61 insertions, 3 deletions
diff --git a/emulator/opengl/host/libs/Translator/GLES_V2/GLESv2Imp.cpp b/emulator/opengl/host/libs/Translator/GLES_V2/GLESv2Imp.cpp
index 4aac5f8..45b39d5 100644
--- a/emulator/opengl/host/libs/Translator/GLES_V2/GLESv2Imp.cpp
+++ b/emulator/opengl/host/libs/Translator/GLES_V2/GLESv2Imp.cpp
@@ -116,6 +116,27 @@ GL_APICALL GLESiface* __translator_getIfaces(EGLiface* eglIface){
}
+static void s_attachShader(GLEScontext* ctx, GLuint program, GLuint shader) {
+ if (ctx && program && shader && ctx->shareGroup().Ptr()) {
+ ObjectDataPtr shaderData = ctx->shareGroup()->getObjectData(SHADER,shader);
+ if (!shaderData.Ptr()) return;
+ ShaderParser* shaderParser = (ShaderParser*)shaderData.Ptr();
+ shaderParser->setAttachedProgram(program);
+ }
+}
+
+static void s_detachShader(GLEScontext* ctx, GLuint shader) {
+ if (ctx && shader && ctx->shareGroup().Ptr()) {
+ ObjectDataPtr shaderData = ctx->shareGroup()->getObjectData(SHADER,shader);
+ if (!shaderData.Ptr()) return;
+ ShaderParser* shaderParser = (ShaderParser*)shaderData.Ptr();
+ shaderParser->setAttachedProgram(0);
+ if (shaderParser->getDeleteStatus()) {
+ ctx->shareGroup()->deleteName(SHADER, shader);
+ }
+ }
+}
+
static ObjectLocalName TextureLocalName(GLenum target,unsigned int tex) {
GET_CTX_RET(0);
return (tex!=0? tex : ctx->getDefaultTextureName(target));
@@ -165,6 +186,7 @@ GL_APICALL void GL_APIENTRY glAttachShader(GLuint program, GLuint shader){
ProgramData* pData = (ProgramData*)programData.Ptr();
SET_ERROR_IF((pData->getAttachedShader(shaderType)!=0), GL_INVALID_OPERATION);
pData->attachShader(shader,shaderType);
+ s_attachShader(ctx, program, shader);
ctx->dispatcher().glAttachShader(globalProgramName,globalShaderName);
}
}
@@ -521,6 +543,12 @@ GL_APICALL void GL_APIENTRY glDeleteProgram(GLuint program){
if(program && ctx->shareGroup().Ptr()) {
const GLuint globalProgramName = ctx->shareGroup()->getGlobalName(SHADER,program);
SET_ERROR_IF(!globalProgramName, GL_INVALID_VALUE);
+
+ ObjectDataPtr programData = ctx->shareGroup()->getObjectData(SHADER,program);
+ ProgramData* pData = (ProgramData*)programData.Ptr();
+ s_detachShader(ctx, pData->getAttachedVertexShader());
+ s_detachShader(ctx, pData->getAttachedFragmentShader());
+
ctx->shareGroup()->deleteName(SHADER,program);
ctx->dispatcher().glDeleteProgram(globalProgramName);
}
@@ -531,7 +559,15 @@ GL_APICALL void GL_APIENTRY glDeleteShader(GLuint shader){
if(shader && ctx->shareGroup().Ptr()) {
const GLuint globalShaderName = ctx->shareGroup()->getGlobalName(SHADER,shader);
SET_ERROR_IF(!globalShaderName, GL_INVALID_VALUE);
- ctx->shareGroup()->deleteName(SHADER,shader);
+ ObjectDataPtr objData = ctx->shareGroup()->getObjectData(SHADER,shader);
+ SET_ERROR_IF(!objData.Ptr() ,GL_INVALID_OPERATION);
+ SET_ERROR_IF(objData.Ptr()->getDataType()!=SHADER_DATA,GL_INVALID_OPERATION);
+ ShaderParser* sp = (ShaderParser*)objData.Ptr();
+ if (sp->getAttachedProgram()) {
+ sp->setDeleteStatus(true);
+ } else {
+ ctx->shareGroup()->deleteName(SHADER,shader);
+ }
ctx->dispatcher().glDeleteShader(globalShaderName);
}
@@ -566,6 +602,8 @@ GL_APICALL void GL_APIENTRY glDetachShader(GLuint program, GLuint shader){
SET_ERROR_IF(!programData->isAttached(shader),GL_INVALID_OPERATION);
programData->detachShader(shader);
+ s_detachShader(ctx, shader);
+
ctx->dispatcher().glDetachShader(globalProgramName,globalShaderName);
}
}
@@ -1251,6 +1289,15 @@ GL_APICALL void GL_APIENTRY glGetShaderiv(GLuint shader, GLenum pname, GLint* p
GET_CTX();
if(ctx->shareGroup().Ptr()) {
const GLuint globalShaderName = ctx->shareGroup()->getGlobalName(SHADER,shader);
+ if (pname == GL_DELETE_STATUS) {
+ SET_ERROR_IF(globalShaderName == 0, GL_INVALID_VALUE);
+ ObjectDataPtr objData = ctx->shareGroup()->getObjectData(SHADER,shader);
+ SET_ERROR_IF(!objData.Ptr() ,GL_INVALID_VALUE);
+ SET_ERROR_IF(objData.Ptr()->getDataType()!=SHADER_DATA,GL_INVALID_VALUE);
+ ShaderParser* sp = (ShaderParser*)objData.Ptr();
+ params[0] = (sp->getDeleteStatus()) ? GL_TRUE : GL_FALSE;
+ return;
+ }
SET_ERROR_IF(globalShaderName==0, GL_INVALID_VALUE);
switch(pname) {
case GL_INFO_LOG_LENGTH:
diff --git a/emulator/opengl/host/libs/Translator/GLES_V2/ShaderParser.cpp b/emulator/opengl/host/libs/Translator/GLES_V2/ShaderParser.cpp
index e0e19e9..4e14a29 100644
--- a/emulator/opengl/host/libs/Translator/GLES_V2/ShaderParser.cpp
+++ b/emulator/opengl/host/libs/Translator/GLES_V2/ShaderParser.cpp
@@ -21,7 +21,9 @@
ShaderParser::ShaderParser():ObjectData(SHADER_DATA),
m_type(0),
m_originalSrc(NULL),
- m_parsedLines(NULL) {
+ m_parsedLines(NULL),
+ m_deleteStatus(false),
+ m_program(0) {
m_infoLog = new GLchar[1];
m_infoLog[0] = '\0';
};
@@ -29,7 +31,9 @@ ShaderParser::ShaderParser():ObjectData(SHADER_DATA),
ShaderParser::ShaderParser(GLenum type):ObjectData(SHADER_DATA),
m_type(type),
m_originalSrc(NULL),
- m_parsedLines(NULL) {
+ m_parsedLines(NULL),
+ m_deleteStatus(false),
+ m_program(0) {
m_infoLog = new GLchar[1];
m_infoLog[0] = '\0';
diff --git a/emulator/opengl/host/libs/Translator/GLES_V2/ShaderParser.h b/emulator/opengl/host/libs/Translator/GLES_V2/ShaderParser.h
index 6374000..8cd3940 100644
--- a/emulator/opengl/host/libs/Translator/GLES_V2/ShaderParser.h
+++ b/emulator/opengl/host/libs/Translator/GLES_V2/ShaderParser.h
@@ -35,6 +35,11 @@ public:
void setInfoLog(GLchar * infoLog);
GLchar* getInfoLog();
+ void setDeleteStatus(bool val) { m_deleteStatus = val; }
+ bool getDeleteStatus() const { return m_deleteStatus; }
+
+ void setAttachedProgram(GLuint program) { m_program = program; }
+ GLuint getAttachedProgram() const { return m_program; }
private:
void parseOriginalSrc();
void parseGLSLversion();
@@ -50,5 +55,7 @@ private:
std::string m_parsedSrc;
GLchar* m_parsedLines;
GLchar* m_infoLog;
+ bool m_deleteStatus;
+ GLuint m_program;
};
#endif