Commit e3b10e8d by Corentin Wallez

Make eglMakeCurrent validate for config compatibility

See section 2.2 of the EGL 1.5 specification. BUG=angleproject:892 Change-Id: I2a43260e53cb045b2e06b0e50915e228cec96f33 Reviewed-on: https://chromium-review.googlesource.com/272370Reviewed-by: 's avatarGeoff Lang <geofflang@chromium.org> Tested-by: 's avatarCorentin Wallez <cwallez@chromium.org>
parent 5b2545bf
...@@ -38,6 +38,7 @@ namespace gl ...@@ -38,6 +38,7 @@ namespace gl
Context::Context(const egl::Config *config, int clientVersion, const Context *shareContext, rx::Renderer *renderer, bool notifyResets, bool robustAccess) Context::Context(const egl::Config *config, int clientVersion, const Context *shareContext, rx::Renderer *renderer, bool notifyResets, bool robustAccess)
: mRenderer(renderer), : mRenderer(renderer),
mConfig(config),
mData(clientVersion, mState, mCaps, mTextureCaps, mExtensions, nullptr) mData(clientVersion, mState, mCaps, mTextureCaps, mExtensions, nullptr)
{ {
ASSERT(robustAccess == false); // Unimplemented ASSERT(robustAccess == false); // Unimplemented
...@@ -47,7 +48,6 @@ Context::Context(const egl::Config *config, int clientVersion, const Context *sh ...@@ -47,7 +48,6 @@ Context::Context(const egl::Config *config, int clientVersion, const Context *sh
mClientVersion = clientVersion; mClientVersion = clientVersion;
mConfigID = config->configID;
mClientType = EGL_OPENGL_ES_API; mClientType = EGL_OPENGL_ES_API;
mFenceNVHandleAllocator.setBaseHandle(0); mFenceNVHandleAllocator.setBaseHandle(0);
...@@ -1320,9 +1320,9 @@ int Context::getClientVersion() const ...@@ -1320,9 +1320,9 @@ int Context::getClientVersion() const
return mClientVersion; return mClientVersion;
} }
EGLint Context::getConfigID() const const egl::Config *Context::getConfig() const
{ {
return mConfigID; return mConfig;
} }
EGLenum Context::getClientType() const EGLenum Context::getClientType() const
......
...@@ -179,7 +179,7 @@ class Context final : angle::NonCopyable ...@@ -179,7 +179,7 @@ class Context final : angle::NonCopyable
virtual int getClientVersion() const; virtual int getClientVersion() const;
EGLint getConfigID() const; const egl::Config *getConfig() const;
EGLenum getClientType() const; EGLenum getClientType() const;
EGLenum getRenderBuffer() const; EGLenum getRenderBuffer() const;
...@@ -227,7 +227,7 @@ class Context final : angle::NonCopyable ...@@ -227,7 +227,7 @@ class Context final : angle::NonCopyable
int mClientVersion; int mClientVersion;
EGLint mConfigID; const egl::Config *mConfig;
EGLenum mClientType; EGLenum mClientType;
TextureMap mZeroTextures; TextureMap mZeroTextures;
......
...@@ -498,4 +498,37 @@ Error ValidateCreatePbufferFromClientBuffer(Display *display, EGLenum buftype, E ...@@ -498,4 +498,37 @@ Error ValidateCreatePbufferFromClientBuffer(Display *display, EGLenum buftype, E
return Error(EGL_SUCCESS); return Error(EGL_SUCCESS);
} }
Error ValidateCompatibleConfigs(const Config *config1, const Config *config2, EGLint surfaceType)
{
// Config compatibility is defined in section 2.2 of the EGL 1.5 spec
bool colorBufferCompat = config1->colorBufferType == config2->colorBufferType;
if (!colorBufferCompat)
{
return Error(EGL_BAD_MATCH, "Color buffer types are not compatible.");
}
bool colorCompat = config1->redSize == config2->redSize && config1->greenSize == config2->greenSize &&
config1->blueSize == config2->blueSize && config1->alphaSize == config2->alphaSize &&
config1->luminanceSize == config2->luminanceSize;
if (!colorCompat)
{
return Error(EGL_BAD_MATCH, "Color buffer sizes are not compatible.");
}
bool dsCompat = config1->depthSize == config2->depthSize && config1->stencilSize == config2->stencilSize;
if (!dsCompat)
{
return Error(EGL_BAD_MATCH, "Depth-stencil buffer types are not compatible.");
}
bool surfaceTypeCompat = (config1->surfaceType & config2->surfaceType & surfaceType) != 0;
if (!surfaceTypeCompat)
{
return Error(EGL_BAD_MATCH, "Surface types are not compatible.");
}
return Error(EGL_SUCCESS);
}
} }
...@@ -43,6 +43,8 @@ Error ValidateCreatePbufferSurface(Display *display, Config *config, const Attri ...@@ -43,6 +43,8 @@ Error ValidateCreatePbufferSurface(Display *display, Config *config, const Attri
Error ValidateCreatePbufferFromClientBuffer(Display *display, EGLenum buftype, EGLClientBuffer buffer, Error ValidateCreatePbufferFromClientBuffer(Display *display, EGLenum buftype, EGLClientBuffer buffer,
Config *config, const AttributeMap& attributes); Config *config, const AttributeMap& attributes);
// Other validation
Error ValidateCompatibleConfigs(const Config *config1, const Config *config2, EGLint surfaceType);
} }
......
...@@ -519,8 +519,7 @@ EGLBoolean EGLAPIENTRY MakeCurrent(EGLDisplay dpy, EGLSurface draw, EGLSurface r ...@@ -519,8 +519,7 @@ EGLBoolean EGLAPIENTRY MakeCurrent(EGLDisplay dpy, EGLSurface draw, EGLSurface r
} }
// EGL 1.5 spec: dpy can be uninitialized if all other parameters are null // EGL 1.5 spec: dpy can be uninitialized if all other parameters are null
if (dpy != EGL_NO_DISPLAY && !display->isInitialized() && if (!display->isInitialized() && (ctx != EGL_NO_CONTEXT || draw != EGL_NO_SURFACE || read != EGL_NO_SURFACE))
(ctx != EGL_NO_CONTEXT || draw != EGL_NO_SURFACE || read != EGL_NO_SURFACE))
{ {
SetGlobalError(Error(EGL_NOT_INITIALIZED, "'dpy' not initialized")); SetGlobalError(Error(EGL_NOT_INITIALIZED, "'dpy' not initialized"));
return EGL_FALSE; return EGL_FALSE;
...@@ -536,7 +535,7 @@ EGLBoolean EGLAPIENTRY MakeCurrent(EGLDisplay dpy, EGLSurface draw, EGLSurface r ...@@ -536,7 +535,7 @@ EGLBoolean EGLAPIENTRY MakeCurrent(EGLDisplay dpy, EGLSurface draw, EGLSurface r
} }
} }
if (dpy != EGL_NO_DISPLAY && display->isInitialized()) if (display->isInitialized())
{ {
if (display->testDeviceLost()) if (display->testDeviceLost())
{ {
...@@ -573,9 +572,29 @@ EGLBoolean EGLAPIENTRY MakeCurrent(EGLDisplay dpy, EGLSurface draw, EGLSurface r ...@@ -573,9 +572,29 @@ EGLBoolean EGLAPIENTRY MakeCurrent(EGLDisplay dpy, EGLSurface draw, EGLSurface r
} }
} }
if (readSurface)
{
Error readCompatError = ValidateCompatibleConfigs(readSurface->getConfig(), context->getConfig(), readSurface->getType());
if (readCompatError.isError())
{
SetGlobalError(readCompatError);
return EGL_FALSE;
}
}
if (draw != read) if (draw != read)
{ {
UNIMPLEMENTED(); // FIXME UNIMPLEMENTED(); // FIXME
if (drawSurface)
{
Error drawCompatError = ValidateCompatibleConfigs(drawSurface->getConfig(), context->getConfig(), drawSurface->getType());
if (drawCompatError.isError())
{
SetGlobalError(drawCompatError);
return EGL_FALSE;
}
}
} }
gl::Context *previousContext = GetGlobalContext(); gl::Context *previousContext = GetGlobalContext();
...@@ -647,7 +666,7 @@ EGLBoolean EGLAPIENTRY QueryContext(EGLDisplay dpy, EGLContext ctx, EGLint attri ...@@ -647,7 +666,7 @@ EGLBoolean EGLAPIENTRY QueryContext(EGLDisplay dpy, EGLContext ctx, EGLint attri
switch (attribute) switch (attribute)
{ {
case EGL_CONFIG_ID: case EGL_CONFIG_ID:
*value = context->getConfigID(); *value = context->getConfig()->configID;
break; break;
case EGL_CONTEXT_CLIENT_TYPE: case EGL_CONTEXT_CLIENT_TYPE:
*value = context->getClientType(); *value = context->getClientType();
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment