blob: 645fab8f175b5ca5e9033076bed3fa2a5e3da552 [file] [log] [blame]
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001//
Geoff Langeeba6e12014-02-03 13:12:30 -05002// Copyright (c) 2002-2014 The ANGLE Project Authors. All rights reserved.
apatrick@chromium.org144f2802012-07-12 01:42:34 +00003// Use of this source code is governed by a BSD-style license that can be
4// found in the LICENSE file.
5//
6
7// Context.cpp: Implements the gl::Context class, managing all GL state and performing
8// rendering operations. It is the GLES2 specific implementation of EGLContext.
9
Geoff Lang2b5420c2014-11-19 14:20:15 -050010#include "libANGLE/Context.h"
apatrick@chromium.org144f2802012-07-12 01:42:34 +000011
Jamie Madill231c7f52017-04-26 13:45:37 -040012#include <string.h>
Jamie Madillb9293972015-02-19 11:07:54 -050013#include <iterator>
14#include <sstream>
Sami Väisänend59ca052016-06-21 16:10:00 +030015#include <vector>
Jamie Madillb9293972015-02-19 11:07:54 -050016
Sami Väisänene45e53b2016-05-25 10:36:04 +030017#include "common/matrix_utils.h"
Geoff Lang0b7eef72014-06-12 14:10:47 -040018#include "common/platform.h"
Jamie Madillb9293972015-02-19 11:07:54 -050019#include "common/utilities.h"
Geoff Langc339c4e2016-11-29 10:37:36 -050020#include "common/version.h"
Geoff Lang2b5420c2014-11-19 14:20:15 -050021#include "libANGLE/Buffer.h"
Jamie Madillb9293972015-02-19 11:07:54 -050022#include "libANGLE/Compiler.h"
Jamie Madill948bbe52017-06-01 13:10:42 -040023#include "libANGLE/Display.h"
Geoff Lang2b5420c2014-11-19 14:20:15 -050024#include "libANGLE/Fence.h"
25#include "libANGLE/Framebuffer.h"
26#include "libANGLE/FramebufferAttachment.h"
Sami Väisänene45e53b2016-05-25 10:36:04 +030027#include "libANGLE/Path.h"
Geoff Lang2b5420c2014-11-19 14:20:15 -050028#include "libANGLE/Program.h"
Geoff Lang2b5420c2014-11-19 14:20:15 -050029#include "libANGLE/Query.h"
Jamie Madillb9293972015-02-19 11:07:54 -050030#include "libANGLE/Renderbuffer.h"
Geoff Lang2b5420c2014-11-19 14:20:15 -050031#include "libANGLE/ResourceManager.h"
32#include "libANGLE/Sampler.h"
Jamie Madill9dd0cf02014-11-24 11:38:51 -050033#include "libANGLE/Surface.h"
Geoff Lang2b5420c2014-11-19 14:20:15 -050034#include "libANGLE/Texture.h"
35#include "libANGLE/TransformFeedback.h"
36#include "libANGLE/VertexArray.h"
Kenneth Russellf2f6f652016-10-05 19:53:23 -070037#include "libANGLE/Workarounds.h"
Jamie Madill231c7f52017-04-26 13:45:37 -040038#include "libANGLE/formatutils.h"
Martin Radev66fb8202016-07-28 11:45:20 +030039#include "libANGLE/queryconversions.h"
Geoff Langc1984ed2016-10-07 12:41:00 -040040#include "libANGLE/queryutils.h"
Jamie Madill231c7f52017-04-26 13:45:37 -040041#include "libANGLE/renderer/ContextImpl.h"
42#include "libANGLE/renderer/EGLImplFactory.h"
43#include "libANGLE/validationES.h"
shannon.woods@transgaming.com486d9e92013-02-28 23:15:41 +000044
Geoff Langf6db0982015-08-25 13:04:00 -040045namespace
46{
47
Ian Ewell3ffd78b2016-01-22 16:09:42 -050048template <typename T>
Geoff Lang4ddf5af2016-12-01 14:30:44 -050049std::vector<gl::Path *> GatherPaths(gl::PathManager &resourceManager,
Sami Väisänend59ca052016-06-21 16:10:00 +030050 GLsizei numPaths,
51 const void *paths,
52 GLuint pathBase)
53{
54 std::vector<gl::Path *> ret;
55 ret.reserve(numPaths);
56
57 const auto *nameArray = static_cast<const T *>(paths);
58
59 for (GLsizei i = 0; i < numPaths; ++i)
60 {
61 const GLuint pathName = nameArray[i] + pathBase;
62
63 ret.push_back(resourceManager.getPath(pathName));
64 }
65
66 return ret;
67}
68
Geoff Lang4ddf5af2016-12-01 14:30:44 -050069std::vector<gl::Path *> GatherPaths(gl::PathManager &resourceManager,
Sami Väisänend59ca052016-06-21 16:10:00 +030070 GLsizei numPaths,
71 GLenum pathNameType,
72 const void *paths,
73 GLuint pathBase)
74{
75 switch (pathNameType)
76 {
77 case GL_UNSIGNED_BYTE:
78 return GatherPaths<GLubyte>(resourceManager, numPaths, paths, pathBase);
79
80 case GL_BYTE:
81 return GatherPaths<GLbyte>(resourceManager, numPaths, paths, pathBase);
82
83 case GL_UNSIGNED_SHORT:
84 return GatherPaths<GLushort>(resourceManager, numPaths, paths, pathBase);
85
86 case GL_SHORT:
87 return GatherPaths<GLshort>(resourceManager, numPaths, paths, pathBase);
88
89 case GL_UNSIGNED_INT:
90 return GatherPaths<GLuint>(resourceManager, numPaths, paths, pathBase);
91
92 case GL_INT:
93 return GatherPaths<GLint>(resourceManager, numPaths, paths, pathBase);
94 }
95
96 UNREACHABLE();
97 return std::vector<gl::Path *>();
98}
99
100template <typename T>
Geoff Lang2186c382016-10-14 10:54:54 -0400101gl::Error GetQueryObjectParameter(gl::Query *query, GLenum pname, T *params)
Ian Ewell3ffd78b2016-01-22 16:09:42 -0500102{
Geoff Lang2186c382016-10-14 10:54:54 -0400103 ASSERT(query != nullptr);
Ian Ewell3ffd78b2016-01-22 16:09:42 -0500104
105 switch (pname)
106 {
107 case GL_QUERY_RESULT_EXT:
Geoff Lang2186c382016-10-14 10:54:54 -0400108 return query->getResult(params);
Ian Ewell3ffd78b2016-01-22 16:09:42 -0500109 case GL_QUERY_RESULT_AVAILABLE_EXT:
110 {
111 bool available;
Geoff Lang2186c382016-10-14 10:54:54 -0400112 gl::Error error = query->isResultAvailable(&available);
Ian Ewell3ffd78b2016-01-22 16:09:42 -0500113 if (!error.isError())
114 {
Geoff Lang2186c382016-10-14 10:54:54 -0400115 *params = gl::ConvertFromGLboolean<T>(available);
Ian Ewell3ffd78b2016-01-22 16:09:42 -0500116 }
117 return error;
118 }
119 default:
120 UNREACHABLE();
Yuly Novikovc4d18aa2017-03-09 18:45:02 -0500121 return gl::InternalError() << "Unreachable Error";
Ian Ewell3ffd78b2016-01-22 16:09:42 -0500122 }
123}
124
Geoff Langf6db0982015-08-25 13:04:00 -0400125void MarkTransformFeedbackBufferUsage(gl::TransformFeedback *transformFeedback)
126{
Geoff Lang1a683462015-09-29 15:09:59 -0400127 if (transformFeedback && transformFeedback->isActive() && !transformFeedback->isPaused())
Geoff Langf6db0982015-08-25 13:04:00 -0400128 {
129 for (size_t tfBufferIndex = 0; tfBufferIndex < transformFeedback->getIndexedBufferCount();
130 tfBufferIndex++)
131 {
Jamie Madill4928b7c2017-06-20 12:57:39 -0400132 const gl::OffsetBindingPointer<gl::Buffer> &buffer =
Geoff Langf6db0982015-08-25 13:04:00 -0400133 transformFeedback->getIndexedBuffer(tfBufferIndex);
134 if (buffer.get() != nullptr)
135 {
136 buffer->onTransformFeedback();
137 }
138 }
139 }
140}
Jamie Madill46e6c7a2016-01-18 14:42:30 -0500141
142// Attribute map queries.
Martin Radev1be913c2016-07-11 17:59:16 +0300143EGLint GetClientMajorVersion(const egl::AttributeMap &attribs)
Jamie Madill46e6c7a2016-01-18 14:42:30 -0500144{
Ian Ewellec2c0c52016-04-05 13:46:26 -0400145 return static_cast<EGLint>(attribs.get(EGL_CONTEXT_CLIENT_VERSION, 1));
Jamie Madill46e6c7a2016-01-18 14:42:30 -0500146}
147
Martin Radev1be913c2016-07-11 17:59:16 +0300148EGLint GetClientMinorVersion(const egl::AttributeMap &attribs)
149{
150 return static_cast<EGLint>(attribs.get(EGL_CONTEXT_MINOR_VERSION, 0));
151}
152
Geoff Langeb66a6e2016-10-31 13:06:12 -0400153gl::Version GetClientVersion(const egl::AttributeMap &attribs)
154{
155 return gl::Version(GetClientMajorVersion(attribs), GetClientMinorVersion(attribs));
156}
157
Jamie Madill46e6c7a2016-01-18 14:42:30 -0500158GLenum GetResetStrategy(const egl::AttributeMap &attribs)
159{
Ian Ewellec2c0c52016-04-05 13:46:26 -0400160 EGLAttrib attrib = attribs.get(EGL_CONTEXT_OPENGL_RESET_NOTIFICATION_STRATEGY_EXT,
161 EGL_NO_RESET_NOTIFICATION_EXT);
Jamie Madill46e6c7a2016-01-18 14:42:30 -0500162 switch (attrib)
163 {
164 case EGL_NO_RESET_NOTIFICATION:
165 return GL_NO_RESET_NOTIFICATION_EXT;
166 case EGL_LOSE_CONTEXT_ON_RESET:
167 return GL_LOSE_CONTEXT_ON_RESET_EXT;
168 default:
169 UNREACHABLE();
170 return GL_NONE;
171 }
172}
173
174bool GetRobustAccess(const egl::AttributeMap &attribs)
175{
Geoff Lang077f20a2016-11-01 10:08:02 -0400176 return (attribs.get(EGL_CONTEXT_OPENGL_ROBUST_ACCESS_EXT, EGL_FALSE) == EGL_TRUE) ||
177 ((attribs.get(EGL_CONTEXT_FLAGS_KHR, 0) & EGL_CONTEXT_OPENGL_ROBUST_ACCESS_BIT_KHR) !=
178 0);
Jamie Madill46e6c7a2016-01-18 14:42:30 -0500179}
180
181bool GetDebug(const egl::AttributeMap &attribs)
182{
Geoff Lang077f20a2016-11-01 10:08:02 -0400183 return (attribs.get(EGL_CONTEXT_OPENGL_DEBUG, EGL_FALSE) == EGL_TRUE) ||
184 ((attribs.get(EGL_CONTEXT_FLAGS_KHR, 0) & EGL_CONTEXT_OPENGL_DEBUG_BIT_KHR) != 0);
Jamie Madill46e6c7a2016-01-18 14:42:30 -0500185}
186
187bool GetNoError(const egl::AttributeMap &attribs)
188{
189 return (attribs.get(EGL_CONTEXT_OPENGL_NO_ERROR_KHR, EGL_FALSE) == EGL_TRUE);
190}
191
Geoff Langc287ea62016-09-16 14:46:51 -0400192bool GetWebGLContext(const egl::AttributeMap &attribs)
193{
194 return (attribs.get(EGL_CONTEXT_WEBGL_COMPATIBILITY_ANGLE, EGL_FALSE) == EGL_TRUE);
195}
196
Geoff Langf41a7152016-09-19 15:11:17 -0400197bool GetBindGeneratesResource(const egl::AttributeMap &attribs)
198{
199 return (attribs.get(EGL_CONTEXT_BIND_GENERATES_RESOURCE_CHROMIUM, EGL_TRUE) == EGL_TRUE);
200}
201
Geoff Langfeb8c682017-02-13 16:07:35 -0500202bool GetClientArraysEnabled(const egl::AttributeMap &attribs)
203{
204 return (attribs.get(EGL_CONTEXT_CLIENT_ARRAYS_ENABLED_ANGLE, EGL_TRUE) == EGL_TRUE);
205}
206
Martin Radev9d901792016-07-15 15:58:58 +0300207std::string GetObjectLabelFromPointer(GLsizei length, const GLchar *label)
208{
209 std::string labelName;
210 if (label != nullptr)
211 {
212 size_t labelLength = length < 0 ? strlen(label) : length;
213 labelName = std::string(label, labelLength);
214 }
215 return labelName;
216}
217
218void GetObjectLabelBase(const std::string &objectLabel,
219 GLsizei bufSize,
220 GLsizei *length,
221 GLchar *label)
222{
223 size_t writeLength = objectLabel.length();
224 if (label != nullptr && bufSize > 0)
225 {
226 writeLength = std::min(static_cast<size_t>(bufSize) - 1, objectLabel.length());
227 std::copy(objectLabel.begin(), objectLabel.begin() + writeLength, label);
228 label[writeLength] = '\0';
229 }
230
231 if (length != nullptr)
232 {
233 *length = static_cast<GLsizei>(writeLength);
234 }
235}
236
Geoff Langf6db0982015-08-25 13:04:00 -0400237} // anonymous namespace
238
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000239namespace gl
240{
daniel@transgaming.comca1ac1f2013-01-11 04:13:05 +0000241
Jamie Madill53ea9cc2016-05-17 10:12:52 -0400242Context::Context(rx::EGLImplFactory *implFactory,
243 const egl::Config *config,
Corentin Wallez51706ea2015-08-07 14:39:22 -0400244 const Context *shareContext,
Geoff Langce02f082017-02-06 16:46:21 -0500245 TextureManager *shareTextures,
Corentin Wallezc295e512017-01-27 17:47:50 -0500246 const egl::AttributeMap &attribs,
Jamie Madill948bbe52017-06-01 13:10:42 -0400247 const egl::DisplayExtensions &displayExtensions,
248 bool robustResourceInit)
Martin Radev1be913c2016-07-11 17:59:16 +0300249
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500250 : ValidationContext(shareContext,
Geoff Langce02f082017-02-06 16:46:21 -0500251 shareTextures,
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500252 GetClientVersion(attribs),
Jamie Madilldfde6ab2016-06-09 07:07:18 -0700253 &mGLState,
Jamie Madillf25855c2015-11-03 11:06:18 -0500254 mCaps,
255 mTextureCaps,
256 mExtensions,
Jamie Madill46e6c7a2016-01-18 14:42:30 -0500257 mLimitations,
258 GetNoError(attribs)),
Jamie Madilldfde6ab2016-06-09 07:07:18 -0700259 mImplementation(implFactory->createContext(mState)),
Jamie Madill2f348d22017-06-05 10:50:59 -0400260 mCompiler(),
Corentin Walleze3b10e82015-05-20 11:06:25 -0400261 mConfig(config),
Jamie Madill46e6c7a2016-01-18 14:42:30 -0500262 mClientType(EGL_OPENGL_ES_API),
263 mHasBeenCurrent(false),
264 mContextLost(false),
265 mResetStatus(GL_NO_ERROR),
Kenneth Russellf2f6f652016-10-05 19:53:23 -0700266 mContextLostForced(false),
Jamie Madill46e6c7a2016-01-18 14:42:30 -0500267 mResetStrategy(GetResetStrategy(attribs)),
268 mRobustAccess(GetRobustAccess(attribs)),
Jamie Madill61e16b42017-06-19 11:13:23 -0400269 mCurrentSurface(static_cast<egl::Surface *>(EGL_NO_SURFACE)),
270 mCurrentDisplay(static_cast<egl::Display *>(EGL_NO_DISPLAY)),
Jamie Madill4e0e6f82017-02-17 11:06:03 -0500271 mSurfacelessFramebuffer(nullptr),
Jamie Madille14951e2017-03-09 18:55:16 -0500272 mWebGLContext(GetWebGLContext(attribs)),
273 mScratchBuffer(1000u)
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000274{
Geoff Lang077f20a2016-11-01 10:08:02 -0400275 if (mRobustAccess)
276 {
277 UNIMPLEMENTED();
278 }
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000279
Jamie Madill4e0e6f82017-02-17 11:06:03 -0500280 initCaps(displayExtensions);
Kenneth Russellf2f6f652016-10-05 19:53:23 -0700281 initWorkarounds();
Geoff Langc0b9ef42014-07-02 10:02:37 -0400282
Jamie Madill4928b7c2017-06-20 12:57:39 -0400283 mGLState.initialize(this, GetDebug(attribs), GetBindGeneratesResource(attribs),
284 GetClientArraysEnabled(attribs), robustResourceInit);
Régis Fénéon83107972015-02-05 12:57:44 +0100285
Shannon Woods53a94a82014-06-24 15:20:36 -0400286 mFenceNVHandleAllocator.setBaseHandle(0);
Geoff Lang7dca1862013-07-30 16:30:46 -0400287
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000288 // [OpenGL ES 2.0.24] section 3.7 page 83:
289 // In the initial state, TEXTURE_2D and TEXTURE_CUBE_MAP have twodimensional
290 // and cube map texture state vectors respectively associated with them.
291 // In order that access to these initial textures not be lost, they are treated as texture
292 // objects all of whose names are 0.
293
Jamie Madill53ea9cc2016-05-17 10:12:52 -0400294 Texture *zeroTexture2D = new Texture(mImplementation.get(), 0, GL_TEXTURE_2D);
Jamie Madill4928b7c2017-06-20 12:57:39 -0400295 mZeroTextures[GL_TEXTURE_2D].set(this, zeroTexture2D);
Jamie Madilldedd7b92014-11-05 16:30:36 -0500296
Jamie Madill53ea9cc2016-05-17 10:12:52 -0400297 Texture *zeroTextureCube = new Texture(mImplementation.get(), 0, GL_TEXTURE_CUBE_MAP);
Jamie Madill4928b7c2017-06-20 12:57:39 -0400298 mZeroTextures[GL_TEXTURE_CUBE_MAP].set(this, zeroTextureCube);
Geoff Lang76b10c92014-09-05 16:28:14 -0400299
Geoff Langeb66a6e2016-10-31 13:06:12 -0400300 if (getClientVersion() >= Version(3, 0))
Geoff Lang76b10c92014-09-05 16:28:14 -0400301 {
302 // TODO: These could also be enabled via extension
Jamie Madill53ea9cc2016-05-17 10:12:52 -0400303 Texture *zeroTexture3D = new Texture(mImplementation.get(), 0, GL_TEXTURE_3D);
Jamie Madill4928b7c2017-06-20 12:57:39 -0400304 mZeroTextures[GL_TEXTURE_3D].set(this, zeroTexture3D);
Geoff Lang76b10c92014-09-05 16:28:14 -0400305
Jamie Madill53ea9cc2016-05-17 10:12:52 -0400306 Texture *zeroTexture2DArray = new Texture(mImplementation.get(), 0, GL_TEXTURE_2D_ARRAY);
Jamie Madill4928b7c2017-06-20 12:57:39 -0400307 mZeroTextures[GL_TEXTURE_2D_ARRAY].set(this, zeroTexture2DArray);
Geoff Lang76b10c92014-09-05 16:28:14 -0400308 }
Geoff Lang3b573612016-10-31 14:08:10 -0400309 if (getClientVersion() >= Version(3, 1))
310 {
311 Texture *zeroTexture2DMultisample =
312 new Texture(mImplementation.get(), 0, GL_TEXTURE_2D_MULTISAMPLE);
Jamie Madill4928b7c2017-06-20 12:57:39 -0400313 mZeroTextures[GL_TEXTURE_2D_MULTISAMPLE].set(this, zeroTexture2DMultisample);
Jiajia Qin6eafb042016-12-27 17:04:07 +0800314
315 bindGenericAtomicCounterBuffer(0);
316 for (unsigned int i = 0; i < mCaps.maxAtomicCounterBufferBindings; i++)
317 {
318 bindIndexedAtomicCounterBuffer(0, i, 0, 0);
319 }
Jiajia Qinf546e7d2017-03-27 14:12:59 +0800320
321 bindGenericShaderStorageBuffer(0);
322 for (unsigned int i = 0; i < mCaps.maxShaderStorageBufferBindings; i++)
323 {
324 bindIndexedShaderStorageBuffer(0, i, 0, 0);
325 }
Geoff Lang3b573612016-10-31 14:08:10 -0400326 }
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000327
Ian Ewellbda75592016-04-18 17:25:54 -0400328 if (mExtensions.eglImageExternal || mExtensions.eglStreamConsumerExternal)
329 {
Jamie Madill53ea9cc2016-05-17 10:12:52 -0400330 Texture *zeroTextureExternal =
331 new Texture(mImplementation.get(), 0, GL_TEXTURE_EXTERNAL_OES);
Jamie Madill4928b7c2017-06-20 12:57:39 -0400332 mZeroTextures[GL_TEXTURE_EXTERNAL_OES].set(this, zeroTextureExternal);
Ian Ewellbda75592016-04-18 17:25:54 -0400333 }
334
Jamie Madill4928b7c2017-06-20 12:57:39 -0400335 mGLState.initializeZeroTextures(this, mZeroTextures);
Jamie Madille6382c32014-11-07 15:05:26 -0500336
Jamie Madill57a89722013-07-02 11:57:03 -0400337 bindVertexArray(0);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000338 bindArrayBuffer(0);
Jiajia Qin9d7d0b12016-11-29 16:30:31 +0800339 bindDrawIndirectBuffer(0);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000340 bindElementArrayBuffer(0);
Geoff Lang76b10c92014-09-05 16:28:14 -0400341
Jamie Madill01a80ee2016-11-07 12:06:18 -0500342 bindRenderbuffer(GL_RENDERBUFFER, 0);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000343
shannon.woods%transgaming.com@gtempaccount.com667a29c2013-04-13 03:39:04 +0000344 bindGenericUniformBuffer(0);
Geoff Lang4dc3af02016-11-18 14:09:27 -0500345 for (unsigned int i = 0; i < mCaps.maxUniformBufferBindings; i++)
shannon.woods%transgaming.com@gtempaccount.com667a29c2013-04-13 03:39:04 +0000346 {
347 bindIndexedUniformBuffer(0, i, 0, -1);
348 }
349
shannon.woods%transgaming.com@gtempaccount.com51171882013-04-13 03:39:10 +0000350 bindCopyReadBuffer(0);
351 bindCopyWriteBuffer(0);
shannon.woods%transgaming.com@gtempaccount.comc926e5f2013-04-13 03:39:18 +0000352 bindPixelPackBuffer(0);
353 bindPixelUnpackBuffer(0);
shannon.woods%transgaming.com@gtempaccount.com51171882013-04-13 03:39:10 +0000354
Geoff Langeb66a6e2016-10-31 13:06:12 -0400355 if (getClientVersion() >= Version(3, 0))
Geoff Lang1a683462015-09-29 15:09:59 -0400356 {
357 // [OpenGL ES 3.0.2] section 2.14.1 pg 85:
358 // In the initial state, a default transform feedback object is bound and treated as
359 // a transform feedback object with a name of zero. That object is bound any time
360 // BindTransformFeedback is called with id of zero
Geoff Lang1a683462015-09-29 15:09:59 -0400361 bindTransformFeedback(0);
362 }
Geoff Langc8058452014-02-03 12:04:11 -0500363
Jamie Madillad9f24e2016-02-12 09:27:24 -0500364 // Initialize dirty bit masks
365 // TODO(jmadill): additional ES3 state
366 mTexImageDirtyBits.set(State::DIRTY_BIT_UNPACK_ALIGNMENT);
367 mTexImageDirtyBits.set(State::DIRTY_BIT_UNPACK_ROW_LENGTH);
368 mTexImageDirtyBits.set(State::DIRTY_BIT_UNPACK_IMAGE_HEIGHT);
369 mTexImageDirtyBits.set(State::DIRTY_BIT_UNPACK_SKIP_IMAGES);
370 mTexImageDirtyBits.set(State::DIRTY_BIT_UNPACK_SKIP_ROWS);
371 mTexImageDirtyBits.set(State::DIRTY_BIT_UNPACK_SKIP_PIXELS);
Corentin Wallezbbd663a2016-04-20 17:49:17 -0400372 mTexImageDirtyBits.set(State::DIRTY_BIT_UNPACK_BUFFER_BINDING);
Jamie Madillad9f24e2016-02-12 09:27:24 -0500373 // No dirty objects.
374
375 // Readpixels uses the pack state and read FBO
376 mReadPixelsDirtyBits.set(State::DIRTY_BIT_PACK_ALIGNMENT);
377 mReadPixelsDirtyBits.set(State::DIRTY_BIT_PACK_REVERSE_ROW_ORDER);
378 mReadPixelsDirtyBits.set(State::DIRTY_BIT_PACK_ROW_LENGTH);
379 mReadPixelsDirtyBits.set(State::DIRTY_BIT_PACK_SKIP_ROWS);
380 mReadPixelsDirtyBits.set(State::DIRTY_BIT_PACK_SKIP_PIXELS);
Corentin Wallezbbd663a2016-04-20 17:49:17 -0400381 mReadPixelsDirtyBits.set(State::DIRTY_BIT_PACK_BUFFER_BINDING);
Jamie Madillad9f24e2016-02-12 09:27:24 -0500382 mReadPixelsDirtyObjects.set(State::DIRTY_OBJECT_READ_FRAMEBUFFER);
383
384 mClearDirtyBits.set(State::DIRTY_BIT_RASTERIZER_DISCARD_ENABLED);
385 mClearDirtyBits.set(State::DIRTY_BIT_SCISSOR_TEST_ENABLED);
386 mClearDirtyBits.set(State::DIRTY_BIT_SCISSOR);
387 mClearDirtyBits.set(State::DIRTY_BIT_VIEWPORT);
388 mClearDirtyBits.set(State::DIRTY_BIT_CLEAR_COLOR);
389 mClearDirtyBits.set(State::DIRTY_BIT_CLEAR_DEPTH);
390 mClearDirtyBits.set(State::DIRTY_BIT_CLEAR_STENCIL);
391 mClearDirtyBits.set(State::DIRTY_BIT_COLOR_MASK);
392 mClearDirtyBits.set(State::DIRTY_BIT_DEPTH_MASK);
393 mClearDirtyBits.set(State::DIRTY_BIT_STENCIL_WRITEMASK_FRONT);
394 mClearDirtyBits.set(State::DIRTY_BIT_STENCIL_WRITEMASK_BACK);
395 mClearDirtyObjects.set(State::DIRTY_OBJECT_DRAW_FRAMEBUFFER);
396
397 mBlitDirtyBits.set(State::DIRTY_BIT_SCISSOR_TEST_ENABLED);
398 mBlitDirtyBits.set(State::DIRTY_BIT_SCISSOR);
Geoff Lang1d2c41d2016-10-19 16:14:46 -0700399 mBlitDirtyBits.set(State::DIRTY_BIT_FRAMEBUFFER_SRGB);
Jamie Madillad9f24e2016-02-12 09:27:24 -0500400 mBlitDirtyObjects.set(State::DIRTY_OBJECT_READ_FRAMEBUFFER);
401 mBlitDirtyObjects.set(State::DIRTY_OBJECT_DRAW_FRAMEBUFFER);
Jamie Madill437fa652016-05-03 15:13:24 -0400402
Jamie Madill53ea9cc2016-05-17 10:12:52 -0400403 handleError(mImplementation->initialize());
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000404}
405
Jamie Madill4928b7c2017-06-20 12:57:39 -0400406egl::Error Context::onDestroy(const egl::Display *display)
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000407{
Corentin Wallez80b24112015-08-25 16:41:57 -0400408 for (auto fence : mFenceNVMap)
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000409 {
Corentin Wallez80b24112015-08-25 16:41:57 -0400410 SafeDelete(fence.second);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000411 }
412
Corentin Wallez80b24112015-08-25 16:41:57 -0400413 for (auto query : mQueryMap)
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000414 {
Geoff Langf0aa8422015-09-29 15:08:34 -0400415 if (query.second != nullptr)
416 {
Jamie Madill4928b7c2017-06-20 12:57:39 -0400417 query.second->release(this);
Geoff Langf0aa8422015-09-29 15:08:34 -0400418 }
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000419 }
420
Corentin Wallez80b24112015-08-25 16:41:57 -0400421 for (auto vertexArray : mVertexArrayMap)
Jamie Madill57a89722013-07-02 11:57:03 -0400422 {
Jamie Madill4928b7c2017-06-20 12:57:39 -0400423 if (vertexArray.second)
424 {
425 vertexArray.second->onDestroy(this);
426 }
Jamie Madill57a89722013-07-02 11:57:03 -0400427 }
428
Corentin Wallez80b24112015-08-25 16:41:57 -0400429 for (auto transformFeedback : mTransformFeedbackMap)
Geoff Langc8058452014-02-03 12:04:11 -0500430 {
Geoff Lang36167ab2015-12-07 10:27:14 -0500431 if (transformFeedback.second != nullptr)
432 {
Jamie Madill6c1f6712017-02-14 19:08:04 -0500433 transformFeedback.second->release(this);
Geoff Lang36167ab2015-12-07 10:27:14 -0500434 }
Geoff Langc8058452014-02-03 12:04:11 -0500435 }
436
Jamie Madilldedd7b92014-11-05 16:30:36 -0500437 for (auto &zeroTexture : mZeroTextures)
Geoff Lang76b10c92014-09-05 16:28:14 -0400438 {
Jamie Madill4928b7c2017-06-20 12:57:39 -0400439 zeroTexture.second->onDestroy(this);
440 zeroTexture.second.set(this, nullptr);
Geoff Lang76b10c92014-09-05 16:28:14 -0400441 }
442 mZeroTextures.clear();
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000443
Corentin Wallezccab69d2017-01-27 16:57:15 -0500444 SafeDelete(mSurfacelessFramebuffer);
445
Jamie Madill4928b7c2017-06-20 12:57:39 -0400446 ANGLE_TRY(releaseSurface(display));
Jamie Madill2f348d22017-06-05 10:50:59 -0400447 releaseShaderCompiler();
Jamie Madill6c1f6712017-02-14 19:08:04 -0500448
Jamie Madill4928b7c2017-06-20 12:57:39 -0400449 mGLState.reset(this);
450
Jamie Madill6c1f6712017-02-14 19:08:04 -0500451 mState.mBuffers->release(this);
452 mState.mShaderPrograms->release(this);
453 mState.mTextures->release(this);
454 mState.mRenderbuffers->release(this);
455 mState.mSamplers->release(this);
456 mState.mFenceSyncs->release(this);
457 mState.mPaths->release(this);
458 mState.mFramebuffers->release(this);
Jamie Madill4928b7c2017-06-20 12:57:39 -0400459
460 return egl::NoError();
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000461}
462
Jamie Madill70ee0f62017-02-06 16:04:20 -0500463Context::~Context()
464{
465}
466
Jamie Madill4928b7c2017-06-20 12:57:39 -0400467egl::Error Context::makeCurrent(egl::Display *display, egl::Surface *surface)
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000468{
Jamie Madill61e16b42017-06-19 11:13:23 -0400469 mCurrentDisplay = display;
470
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000471 if (!mHasBeenCurrent)
472 {
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000473 initRendererString();
Geoff Langc339c4e2016-11-29 10:37:36 -0500474 initVersionStrings();
Geoff Langcec35902014-04-16 10:52:36 -0400475 initExtensionStrings();
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000476
Corentin Wallezc295e512017-01-27 17:47:50 -0500477 int width = 0;
478 int height = 0;
479 if (surface != nullptr)
480 {
481 width = surface->getWidth();
482 height = surface->getHeight();
483 }
484
485 mGLState.setViewportParams(0, 0, width, height);
486 mGLState.setScissorParams(0, 0, width, height);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000487
488 mHasBeenCurrent = true;
489 }
490
Jamie Madill1b94d432015-08-07 13:23:23 -0400491 // TODO(jmadill): Rework this when we support ContextImpl
Jamie Madilldfde6ab2016-06-09 07:07:18 -0700492 mGLState.setAllDirtyBits();
Jamie Madill1b94d432015-08-07 13:23:23 -0400493
Jamie Madill4928b7c2017-06-20 12:57:39 -0400494 ANGLE_TRY(releaseSurface(display));
Corentin Wallezccab69d2017-01-27 16:57:15 -0500495
496 Framebuffer *newDefault = nullptr;
497 if (surface != nullptr)
498 {
Jamie Madill4928b7c2017-06-20 12:57:39 -0400499 ANGLE_TRY(surface->setIsCurrent(this, true));
Corentin Wallezccab69d2017-01-27 16:57:15 -0500500 mCurrentSurface = surface;
501 newDefault = surface->getDefaultFramebuffer();
502 }
503 else
504 {
505 if (mSurfacelessFramebuffer == nullptr)
506 {
507 mSurfacelessFramebuffer = new Framebuffer(mImplementation.get());
508 }
509
510 newDefault = mSurfacelessFramebuffer;
511 }
Jamie Madill18fdcbc2015-08-19 18:12:44 +0000512
Corentin Wallez37c39792015-08-20 14:19:46 -0400513 // Update default framebuffer, the binding of the previous default
514 // framebuffer (or lack of) will have a nullptr.
Jamie Madillc1c1cdc2015-04-30 09:42:26 -0400515 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -0700516 if (mGLState.getReadFramebuffer() == nullptr)
Corentin Wallez37c39792015-08-20 14:19:46 -0400517 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -0700518 mGLState.setReadFramebufferBinding(newDefault);
Corentin Wallez37c39792015-08-20 14:19:46 -0400519 }
Jamie Madilldfde6ab2016-06-09 07:07:18 -0700520 if (mGLState.getDrawFramebuffer() == nullptr)
Corentin Wallez37c39792015-08-20 14:19:46 -0400521 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -0700522 mGLState.setDrawFramebufferBinding(newDefault);
Corentin Wallez37c39792015-08-20 14:19:46 -0400523 }
Geoff Lang3bf8e3a2016-12-01 17:28:52 -0500524 mState.mFramebuffers->setDefaultFramebuffer(newDefault);
Jamie Madillc1c1cdc2015-04-30 09:42:26 -0400525 }
Ian Ewell292f0052016-02-04 10:37:32 -0500526
527 // Notify the renderer of a context switch
Jamie Madill4928b7c2017-06-20 12:57:39 -0400528 mImplementation->onMakeCurrent(this);
529 return egl::NoError();
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000530}
531
Jamie Madill4928b7c2017-06-20 12:57:39 -0400532egl::Error Context::releaseSurface(const egl::Display *display)
Jamie Madill77a72f62015-04-14 11:18:32 -0400533{
Corentin Wallez37c39792015-08-20 14:19:46 -0400534 // Remove the default framebuffer
Corentin Wallezc295e512017-01-27 17:47:50 -0500535 Framebuffer *currentDefault = nullptr;
536 if (mCurrentSurface != nullptr)
Corentin Wallez51706ea2015-08-07 14:39:22 -0400537 {
Corentin Wallezc295e512017-01-27 17:47:50 -0500538 currentDefault = mCurrentSurface->getDefaultFramebuffer();
539 }
540 else if (mSurfacelessFramebuffer != nullptr)
541 {
542 currentDefault = mSurfacelessFramebuffer;
Corentin Wallez51706ea2015-08-07 14:39:22 -0400543 }
544
Corentin Wallezc295e512017-01-27 17:47:50 -0500545 if (mGLState.getReadFramebuffer() == currentDefault)
546 {
547 mGLState.setReadFramebufferBinding(nullptr);
548 }
549 if (mGLState.getDrawFramebuffer() == currentDefault)
550 {
551 mGLState.setDrawFramebufferBinding(nullptr);
552 }
553 mState.mFramebuffers->setDefaultFramebuffer(nullptr);
554
555 if (mCurrentSurface)
556 {
Jamie Madill4928b7c2017-06-20 12:57:39 -0400557 ANGLE_TRY(mCurrentSurface->setIsCurrent(this, false));
Corentin Wallezc295e512017-01-27 17:47:50 -0500558 mCurrentSurface = nullptr;
559 }
Jamie Madill4928b7c2017-06-20 12:57:39 -0400560
561 return egl::NoError();
Jamie Madill77a72f62015-04-14 11:18:32 -0400562}
563
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000564GLuint Context::createBuffer()
565{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500566 return mState.mBuffers->createBuffer();
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000567}
568
569GLuint Context::createProgram()
570{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500571 return mState.mShaderPrograms->createProgram(mImplementation.get());
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000572}
573
574GLuint Context::createShader(GLenum type)
575{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500576 return mState.mShaderPrograms->createShader(mImplementation.get(), mLimitations, type);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000577}
578
579GLuint Context::createTexture()
580{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500581 return mState.mTextures->createTexture();
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000582}
583
584GLuint Context::createRenderbuffer()
585{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500586 return mState.mRenderbuffers->createRenderbuffer();
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000587}
588
Geoff Lang882033e2014-09-30 11:26:07 -0400589GLsync Context::createFenceSync()
Jamie Madillcd055f82013-07-26 11:55:15 -0400590{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500591 GLuint handle = mState.mFenceSyncs->createFenceSync(mImplementation.get());
Jamie Madillcd055f82013-07-26 11:55:15 -0400592
Cooper Partind8e62a32015-01-29 15:21:25 -0800593 return reinterpret_cast<GLsync>(static_cast<uintptr_t>(handle));
Jamie Madillcd055f82013-07-26 11:55:15 -0400594}
595
Sami Väisänene45e53b2016-05-25 10:36:04 +0300596GLuint Context::createPaths(GLsizei range)
597{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500598 auto resultOrError = mState.mPaths->createPaths(mImplementation.get(), range);
Sami Väisänene45e53b2016-05-25 10:36:04 +0300599 if (resultOrError.isError())
600 {
601 handleError(resultOrError.getError());
602 return 0;
603 }
604 return resultOrError.getResult();
605}
606
Jamie Madill57a89722013-07-02 11:57:03 -0400607GLuint Context::createVertexArray()
608{
Geoff Lang36167ab2015-12-07 10:27:14 -0500609 GLuint vertexArray = mVertexArrayHandleAllocator.allocate();
610 mVertexArrayMap[vertexArray] = nullptr;
611 return vertexArray;
Jamie Madill57a89722013-07-02 11:57:03 -0400612}
613
Jamie Madilldc356042013-07-19 16:36:57 -0400614GLuint Context::createSampler()
615{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500616 return mState.mSamplers->createSampler();
Jamie Madilldc356042013-07-19 16:36:57 -0400617}
618
Geoff Langc8058452014-02-03 12:04:11 -0500619GLuint Context::createTransformFeedback()
620{
Geoff Lang36167ab2015-12-07 10:27:14 -0500621 GLuint transformFeedback = mTransformFeedbackAllocator.allocate();
622 mTransformFeedbackMap[transformFeedback] = nullptr;
623 return transformFeedback;
Geoff Langc8058452014-02-03 12:04:11 -0500624}
625
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000626// Returns an unused framebuffer name
627GLuint Context::createFramebuffer()
628{
Geoff Lang3bf8e3a2016-12-01 17:28:52 -0500629 return mState.mFramebuffers->createFramebuffer();
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000630}
631
Jamie Madill33dc8432013-07-26 11:55:05 -0400632GLuint Context::createFenceNV()
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000633{
Jamie Madill33dc8432013-07-26 11:55:05 -0400634 GLuint handle = mFenceNVHandleAllocator.allocate();
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000635
Jamie Madill53ea9cc2016-05-17 10:12:52 -0400636 mFenceNVMap[handle] = new FenceNV(mImplementation->createFenceNV());
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000637
638 return handle;
639}
640
641// Returns an unused query name
642GLuint Context::createQuery()
643{
644 GLuint handle = mQueryHandleAllocator.allocate();
645
Yunchao Hed7297bf2017-04-19 15:27:10 +0800646 mQueryMap[handle] = nullptr;
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000647
648 return handle;
649}
650
651void Context::deleteBuffer(GLuint buffer)
652{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500653 if (mState.mBuffers->getBuffer(buffer))
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000654 {
655 detachBuffer(buffer);
656 }
Jamie Madill893ab082014-05-16 16:56:10 -0400657
Jamie Madill6c1f6712017-02-14 19:08:04 -0500658 mState.mBuffers->deleteObject(this, buffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000659}
660
661void Context::deleteShader(GLuint shader)
662{
Jamie Madill6c1f6712017-02-14 19:08:04 -0500663 mState.mShaderPrograms->deleteShader(this, shader);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000664}
665
666void Context::deleteProgram(GLuint program)
667{
Jamie Madill6c1f6712017-02-14 19:08:04 -0500668 mState.mShaderPrograms->deleteProgram(this, program);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000669}
670
671void Context::deleteTexture(GLuint texture)
672{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500673 if (mState.mTextures->getTexture(texture))
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000674 {
675 detachTexture(texture);
676 }
677
Jamie Madill6c1f6712017-02-14 19:08:04 -0500678 mState.mTextures->deleteObject(this, texture);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000679}
680
681void Context::deleteRenderbuffer(GLuint renderbuffer)
682{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500683 if (mState.mRenderbuffers->getRenderbuffer(renderbuffer))
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000684 {
685 detachRenderbuffer(renderbuffer);
686 }
Jamie Madill893ab082014-05-16 16:56:10 -0400687
Jamie Madill6c1f6712017-02-14 19:08:04 -0500688 mState.mRenderbuffers->deleteObject(this, renderbuffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000689}
690
Jamie Madillcd055f82013-07-26 11:55:15 -0400691void Context::deleteFenceSync(GLsync fenceSync)
692{
693 // The spec specifies the underlying Fence object is not deleted until all current
694 // wait commands finish. However, since the name becomes invalid, we cannot query the fence,
695 // and since our API is currently designed for being called from a single thread, we can delete
696 // the fence immediately.
Jamie Madill6c1f6712017-02-14 19:08:04 -0500697 mState.mFenceSyncs->deleteObject(this,
698 static_cast<GLuint>(reinterpret_cast<uintptr_t>(fenceSync)));
Jamie Madillcd055f82013-07-26 11:55:15 -0400699}
700
Sami Väisänene45e53b2016-05-25 10:36:04 +0300701void Context::deletePaths(GLuint first, GLsizei range)
702{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500703 mState.mPaths->deletePaths(first, range);
Sami Väisänene45e53b2016-05-25 10:36:04 +0300704}
705
706bool Context::hasPathData(GLuint path) const
707{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500708 const auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +0300709 if (pathObj == nullptr)
710 return false;
711
712 return pathObj->hasPathData();
713}
714
715bool Context::hasPath(GLuint path) const
716{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500717 return mState.mPaths->hasPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +0300718}
719
720void Context::setPathCommands(GLuint path,
721 GLsizei numCommands,
722 const GLubyte *commands,
723 GLsizei numCoords,
724 GLenum coordType,
725 const void *coords)
726{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500727 auto *pathObject = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +0300728
729 handleError(pathObject->setCommands(numCommands, commands, numCoords, coordType, coords));
730}
731
732void Context::setPathParameterf(GLuint path, GLenum pname, GLfloat value)
733{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500734 auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +0300735
736 switch (pname)
737 {
738 case GL_PATH_STROKE_WIDTH_CHROMIUM:
739 pathObj->setStrokeWidth(value);
740 break;
741 case GL_PATH_END_CAPS_CHROMIUM:
742 pathObj->setEndCaps(static_cast<GLenum>(value));
743 break;
744 case GL_PATH_JOIN_STYLE_CHROMIUM:
745 pathObj->setJoinStyle(static_cast<GLenum>(value));
746 break;
747 case GL_PATH_MITER_LIMIT_CHROMIUM:
748 pathObj->setMiterLimit(value);
749 break;
750 case GL_PATH_STROKE_BOUND_CHROMIUM:
751 pathObj->setStrokeBound(value);
752 break;
753 default:
754 UNREACHABLE();
755 break;
756 }
757}
758
759void Context::getPathParameterfv(GLuint path, GLenum pname, GLfloat *value) const
760{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500761 const auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +0300762
763 switch (pname)
764 {
765 case GL_PATH_STROKE_WIDTH_CHROMIUM:
766 *value = pathObj->getStrokeWidth();
767 break;
768 case GL_PATH_END_CAPS_CHROMIUM:
769 *value = static_cast<GLfloat>(pathObj->getEndCaps());
770 break;
771 case GL_PATH_JOIN_STYLE_CHROMIUM:
772 *value = static_cast<GLfloat>(pathObj->getJoinStyle());
773 break;
774 case GL_PATH_MITER_LIMIT_CHROMIUM:
775 *value = pathObj->getMiterLimit();
776 break;
777 case GL_PATH_STROKE_BOUND_CHROMIUM:
778 *value = pathObj->getStrokeBound();
779 break;
780 default:
781 UNREACHABLE();
782 break;
783 }
784}
785
786void Context::setPathStencilFunc(GLenum func, GLint ref, GLuint mask)
787{
788 mGLState.setPathStencilFunc(func, ref, mask);
789}
790
Jamie Madill57a89722013-07-02 11:57:03 -0400791void Context::deleteVertexArray(GLuint vertexArray)
792{
Geoff Lang36167ab2015-12-07 10:27:14 -0500793 auto iter = mVertexArrayMap.find(vertexArray);
794 if (iter != mVertexArrayMap.end())
Geoff Lang50b3fe82015-12-08 14:49:12 +0000795 {
Geoff Lang36167ab2015-12-07 10:27:14 -0500796 VertexArray *vertexArrayObject = iter->second;
797 if (vertexArrayObject != nullptr)
798 {
799 detachVertexArray(vertexArray);
Jamie Madill4928b7c2017-06-20 12:57:39 -0400800 vertexArrayObject->onDestroy(this);
Geoff Lang36167ab2015-12-07 10:27:14 -0500801 }
Geoff Lang50b3fe82015-12-08 14:49:12 +0000802
Geoff Lang36167ab2015-12-07 10:27:14 -0500803 mVertexArrayMap.erase(iter);
804 mVertexArrayHandleAllocator.release(vertexArray);
Jamie Madill57a89722013-07-02 11:57:03 -0400805 }
806}
807
Jamie Madilldc356042013-07-19 16:36:57 -0400808void Context::deleteSampler(GLuint sampler)
809{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500810 if (mState.mSamplers->getSampler(sampler))
Jamie Madilldc356042013-07-19 16:36:57 -0400811 {
812 detachSampler(sampler);
813 }
814
Jamie Madill6c1f6712017-02-14 19:08:04 -0500815 mState.mSamplers->deleteObject(this, sampler);
Jamie Madilldc356042013-07-19 16:36:57 -0400816}
817
Geoff Langc8058452014-02-03 12:04:11 -0500818void Context::deleteTransformFeedback(GLuint transformFeedback)
819{
Geoff Lang6e60d6b2017-04-12 12:59:04 -0400820 if (transformFeedback == 0)
821 {
822 return;
823 }
824
Jamie Madill5fd0b2d2015-01-05 13:38:44 -0500825 auto iter = mTransformFeedbackMap.find(transformFeedback);
Geoff Langc8058452014-02-03 12:04:11 -0500826 if (iter != mTransformFeedbackMap.end())
827 {
Geoff Lang36167ab2015-12-07 10:27:14 -0500828 TransformFeedback *transformFeedbackObject = iter->second;
829 if (transformFeedbackObject != nullptr)
830 {
831 detachTransformFeedback(transformFeedback);
Jamie Madill6c1f6712017-02-14 19:08:04 -0500832 transformFeedbackObject->release(this);
Geoff Lang36167ab2015-12-07 10:27:14 -0500833 }
834
Geoff Lang50b3fe82015-12-08 14:49:12 +0000835 mTransformFeedbackMap.erase(iter);
Geoff Lang36167ab2015-12-07 10:27:14 -0500836 mTransformFeedbackAllocator.release(transformFeedback);
Geoff Langc8058452014-02-03 12:04:11 -0500837 }
838}
839
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000840void Context::deleteFramebuffer(GLuint framebuffer)
841{
Geoff Lang3bf8e3a2016-12-01 17:28:52 -0500842 if (mState.mFramebuffers->getFramebuffer(framebuffer))
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000843 {
844 detachFramebuffer(framebuffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000845 }
Geoff Lang3bf8e3a2016-12-01 17:28:52 -0500846
Jamie Madill6c1f6712017-02-14 19:08:04 -0500847 mState.mFramebuffers->deleteObject(this, framebuffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000848}
849
Jamie Madill33dc8432013-07-26 11:55:05 -0400850void Context::deleteFenceNV(GLuint fence)
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000851{
Jamie Madill4e25a0d2016-03-08 13:53:03 -0500852 auto fenceObject = mFenceNVMap.find(fence);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000853
Jamie Madill33dc8432013-07-26 11:55:05 -0400854 if (fenceObject != mFenceNVMap.end())
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000855 {
Jamie Madill33dc8432013-07-26 11:55:05 -0400856 mFenceNVHandleAllocator.release(fenceObject->first);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000857 delete fenceObject->second;
Jamie Madill33dc8432013-07-26 11:55:05 -0400858 mFenceNVMap.erase(fenceObject);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000859 }
860}
861
862void Context::deleteQuery(GLuint query)
863{
Jamie Madill4e25a0d2016-03-08 13:53:03 -0500864 auto queryObject = mQueryMap.find(query);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000865 if (queryObject != mQueryMap.end())
866 {
867 mQueryHandleAllocator.release(queryObject->first);
868 if (queryObject->second)
869 {
Jamie Madill4928b7c2017-06-20 12:57:39 -0400870 queryObject->second->release(this);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000871 }
872 mQueryMap.erase(queryObject);
873 }
874}
875
Geoff Lang70d0f492015-12-10 17:45:46 -0500876Buffer *Context::getBuffer(GLuint handle) const
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000877{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500878 return mState.mBuffers->getBuffer(handle);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000879}
880
Jamie Madill570f7c82014-07-03 10:38:54 -0400881Texture *Context::getTexture(GLuint handle) const
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000882{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500883 return mState.mTextures->getTexture(handle);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000884}
885
Geoff Lang70d0f492015-12-10 17:45:46 -0500886Renderbuffer *Context::getRenderbuffer(GLuint handle) const
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000887{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500888 return mState.mRenderbuffers->getRenderbuffer(handle);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000889}
890
Jamie Madillcd055f82013-07-26 11:55:15 -0400891FenceSync *Context::getFenceSync(GLsync handle) const
892{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500893 return mState.mFenceSyncs->getFenceSync(
894 static_cast<GLuint>(reinterpret_cast<uintptr_t>(handle)));
Jamie Madillcd055f82013-07-26 11:55:15 -0400895}
896
Jamie Madill57a89722013-07-02 11:57:03 -0400897VertexArray *Context::getVertexArray(GLuint handle) const
898{
899 auto vertexArray = mVertexArrayMap.find(handle);
Geoff Lang36167ab2015-12-07 10:27:14 -0500900 return (vertexArray != mVertexArrayMap.end()) ? vertexArray->second : nullptr;
Jamie Madill57a89722013-07-02 11:57:03 -0400901}
902
Jamie Madilldc356042013-07-19 16:36:57 -0400903Sampler *Context::getSampler(GLuint handle) const
904{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500905 return mState.mSamplers->getSampler(handle);
Jamie Madilldc356042013-07-19 16:36:57 -0400906}
907
Geoff Langc8058452014-02-03 12:04:11 -0500908TransformFeedback *Context::getTransformFeedback(GLuint handle) const
909{
Geoff Lang36167ab2015-12-07 10:27:14 -0500910 auto iter = mTransformFeedbackMap.find(handle);
911 return (iter != mTransformFeedbackMap.end()) ? iter->second : nullptr;
Geoff Langc8058452014-02-03 12:04:11 -0500912}
913
Geoff Lang70d0f492015-12-10 17:45:46 -0500914LabeledObject *Context::getLabeledObject(GLenum identifier, GLuint name) const
915{
916 switch (identifier)
917 {
918 case GL_BUFFER:
919 return getBuffer(name);
920 case GL_SHADER:
921 return getShader(name);
922 case GL_PROGRAM:
923 return getProgram(name);
924 case GL_VERTEX_ARRAY:
925 return getVertexArray(name);
926 case GL_QUERY:
927 return getQuery(name);
928 case GL_TRANSFORM_FEEDBACK:
929 return getTransformFeedback(name);
930 case GL_SAMPLER:
931 return getSampler(name);
932 case GL_TEXTURE:
933 return getTexture(name);
934 case GL_RENDERBUFFER:
935 return getRenderbuffer(name);
936 case GL_FRAMEBUFFER:
937 return getFramebuffer(name);
938 default:
939 UNREACHABLE();
940 return nullptr;
941 }
942}
943
944LabeledObject *Context::getLabeledObjectFromPtr(const void *ptr) const
945{
946 return getFenceSync(reinterpret_cast<GLsync>(const_cast<void *>(ptr)));
947}
948
Martin Radev9d901792016-07-15 15:58:58 +0300949void Context::objectLabel(GLenum identifier, GLuint name, GLsizei length, const GLchar *label)
950{
951 LabeledObject *object = getLabeledObject(identifier, name);
952 ASSERT(object != nullptr);
953
954 std::string labelName = GetObjectLabelFromPointer(length, label);
955 object->setLabel(labelName);
956}
957
958void Context::objectPtrLabel(const void *ptr, GLsizei length, const GLchar *label)
959{
960 LabeledObject *object = getLabeledObjectFromPtr(ptr);
961 ASSERT(object != nullptr);
962
963 std::string labelName = GetObjectLabelFromPointer(length, label);
964 object->setLabel(labelName);
965}
966
967void Context::getObjectLabel(GLenum identifier,
968 GLuint name,
969 GLsizei bufSize,
970 GLsizei *length,
971 GLchar *label) const
972{
973 LabeledObject *object = getLabeledObject(identifier, name);
974 ASSERT(object != nullptr);
975
976 const std::string &objectLabel = object->getLabel();
977 GetObjectLabelBase(objectLabel, bufSize, length, label);
978}
979
980void Context::getObjectPtrLabel(const void *ptr,
981 GLsizei bufSize,
982 GLsizei *length,
983 GLchar *label) const
984{
985 LabeledObject *object = getLabeledObjectFromPtr(ptr);
986 ASSERT(object != nullptr);
987
988 const std::string &objectLabel = object->getLabel();
989 GetObjectLabelBase(objectLabel, bufSize, length, label);
990}
991
Jamie Madilldc356042013-07-19 16:36:57 -0400992bool Context::isSampler(GLuint samplerName) const
993{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500994 return mState.mSamplers->isSampler(samplerName);
Jamie Madilldc356042013-07-19 16:36:57 -0400995}
996
Jamie Madill3f01e6c2016-03-08 13:53:02 -0500997void Context::bindArrayBuffer(GLuint bufferHandle)
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000998{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500999 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001000 mGLState.setArrayBufferBinding(this, buffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001001}
1002
Jiajia Qin9d7d0b12016-11-29 16:30:31 +08001003void Context::bindDrawIndirectBuffer(GLuint bufferHandle)
1004{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001005 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001006 mGLState.setDrawIndirectBufferBinding(this, buffer);
Jiajia Qin9d7d0b12016-11-29 16:30:31 +08001007}
1008
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001009void Context::bindElementArrayBuffer(GLuint bufferHandle)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001010{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001011 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001012 mGLState.setElementArrayBuffer(this, buffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001013}
1014
Jamie Madilldedd7b92014-11-05 16:30:36 -05001015void Context::bindTexture(GLenum target, GLuint handle)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001016{
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001017 Texture *texture = nullptr;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001018
Jamie Madilldedd7b92014-11-05 16:30:36 -05001019 if (handle == 0)
1020 {
1021 texture = mZeroTextures[target].get();
1022 }
1023 else
1024 {
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001025 texture = mState.mTextures->checkTextureAllocation(mImplementation.get(), handle, target);
Jamie Madilldedd7b92014-11-05 16:30:36 -05001026 }
1027
1028 ASSERT(texture);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001029 mGLState.setSamplerTexture(this, target, texture);
shannon.woods%transgaming.com@gtempaccount.com90dbc442013-04-13 03:46:14 +00001030}
1031
Jamie Madill5bf9ff42016-02-01 11:13:03 -05001032void Context::bindReadFramebuffer(GLuint framebufferHandle)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001033{
Geoff Lang3bf8e3a2016-12-01 17:28:52 -05001034 Framebuffer *framebuffer = mState.mFramebuffers->checkFramebufferAllocation(
1035 mImplementation.get(), mCaps, framebufferHandle);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001036 mGLState.setReadFramebufferBinding(framebuffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001037}
1038
Jamie Madill5bf9ff42016-02-01 11:13:03 -05001039void Context::bindDrawFramebuffer(GLuint framebufferHandle)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001040{
Geoff Lang3bf8e3a2016-12-01 17:28:52 -05001041 Framebuffer *framebuffer = mState.mFramebuffers->checkFramebufferAllocation(
1042 mImplementation.get(), mCaps, framebufferHandle);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001043 mGLState.setDrawFramebufferBinding(framebuffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001044}
1045
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001046void Context::bindVertexArray(GLuint vertexArrayHandle)
Jamie Madill57a89722013-07-02 11:57:03 -04001047{
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001048 VertexArray *vertexArray = checkVertexArrayAllocation(vertexArrayHandle);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001049 mGLState.setVertexArrayBinding(vertexArray);
Jamie Madill57a89722013-07-02 11:57:03 -04001050}
1051
Shao80957d92017-02-20 21:25:59 +08001052void Context::bindVertexBuffer(GLuint bindingIndex,
1053 GLuint bufferHandle,
1054 GLintptr offset,
1055 GLsizei stride)
1056{
1057 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001058 mGLState.bindVertexBuffer(this, bindingIndex, buffer, offset, stride);
Shao80957d92017-02-20 21:25:59 +08001059}
1060
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001061void Context::bindSampler(GLuint textureUnit, GLuint samplerHandle)
Jamie Madilldc356042013-07-19 16:36:57 -04001062{
Geoff Lang76b10c92014-09-05 16:28:14 -04001063 ASSERT(textureUnit < mCaps.maxCombinedTextureImageUnits);
Jamie Madill901b3792016-05-26 09:20:40 -04001064 Sampler *sampler =
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001065 mState.mSamplers->checkSamplerAllocation(mImplementation.get(), samplerHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001066 mGLState.setSamplerBinding(this, textureUnit, sampler);
Jamie Madilldc356042013-07-19 16:36:57 -04001067}
1068
Xinghua Cao65ec0b22017-03-28 16:10:52 +08001069void Context::bindImageTexture(GLuint unit,
1070 GLuint texture,
1071 GLint level,
1072 GLboolean layered,
1073 GLint layer,
1074 GLenum access,
1075 GLenum format)
1076{
1077 Texture *tex = mState.mTextures->getTexture(texture);
1078 mGLState.setImageUnit(this, unit, tex, level, layered, layer, access, format);
1079}
1080
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001081void Context::bindGenericUniformBuffer(GLuint bufferHandle)
shannon.woods%transgaming.com@gtempaccount.com667a29c2013-04-13 03:39:04 +00001082{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001083 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001084 mGLState.setGenericUniformBufferBinding(this, buffer);
shannon.woods%transgaming.com@gtempaccount.com667a29c2013-04-13 03:39:04 +00001085}
1086
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001087void Context::bindIndexedUniformBuffer(GLuint bufferHandle,
1088 GLuint index,
1089 GLintptr offset,
1090 GLsizeiptr size)
shannon.woods%transgaming.com@gtempaccount.com34089352013-04-13 03:36:57 +00001091{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001092 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001093 mGLState.setIndexedUniformBufferBinding(this, index, buffer, offset, size);
shannon.woods%transgaming.com@gtempaccount.com34089352013-04-13 03:36:57 +00001094}
1095
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001096void Context::bindGenericTransformFeedbackBuffer(GLuint bufferHandle)
shannon.woods%transgaming.com@gtempaccount.com667a29c2013-04-13 03:39:04 +00001097{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001098 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001099 mGLState.getCurrentTransformFeedback()->bindGenericBuffer(this, buffer);
shannon.woods%transgaming.com@gtempaccount.com667a29c2013-04-13 03:39:04 +00001100}
1101
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001102void Context::bindIndexedTransformFeedbackBuffer(GLuint bufferHandle,
1103 GLuint index,
1104 GLintptr offset,
1105 GLsizeiptr size)
shannon.woods%transgaming.com@gtempaccount.com34089352013-04-13 03:36:57 +00001106{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001107 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001108 mGLState.getCurrentTransformFeedback()->bindIndexedBuffer(this, index, buffer, offset, size);
shannon.woods%transgaming.com@gtempaccount.com34089352013-04-13 03:36:57 +00001109}
1110
Jiajia Qin6eafb042016-12-27 17:04:07 +08001111void Context::bindGenericAtomicCounterBuffer(GLuint bufferHandle)
1112{
1113 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001114 mGLState.setGenericAtomicCounterBufferBinding(this, buffer);
Jiajia Qin6eafb042016-12-27 17:04:07 +08001115}
1116
1117void Context::bindIndexedAtomicCounterBuffer(GLuint bufferHandle,
1118 GLuint index,
1119 GLintptr offset,
1120 GLsizeiptr size)
1121{
1122 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001123 mGLState.setIndexedAtomicCounterBufferBinding(this, index, buffer, offset, size);
Jiajia Qin6eafb042016-12-27 17:04:07 +08001124}
1125
Jiajia Qinf546e7d2017-03-27 14:12:59 +08001126void Context::bindGenericShaderStorageBuffer(GLuint bufferHandle)
1127{
1128 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001129 mGLState.setGenericShaderStorageBufferBinding(this, buffer);
Jiajia Qinf546e7d2017-03-27 14:12:59 +08001130}
1131
1132void Context::bindIndexedShaderStorageBuffer(GLuint bufferHandle,
1133 GLuint index,
1134 GLintptr offset,
1135 GLsizeiptr size)
1136{
1137 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001138 mGLState.setIndexedShaderStorageBufferBinding(this, index, buffer, offset, size);
Jiajia Qinf546e7d2017-03-27 14:12:59 +08001139}
1140
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001141void Context::bindCopyReadBuffer(GLuint bufferHandle)
shannon.woods%transgaming.com@gtempaccount.com51171882013-04-13 03:39:10 +00001142{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001143 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001144 mGLState.setCopyReadBufferBinding(this, buffer);
shannon.woods%transgaming.com@gtempaccount.com51171882013-04-13 03:39:10 +00001145}
1146
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001147void Context::bindCopyWriteBuffer(GLuint bufferHandle)
shannon.woods%transgaming.com@gtempaccount.com51171882013-04-13 03:39:10 +00001148{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001149 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001150 mGLState.setCopyWriteBufferBinding(this, buffer);
shannon.woods%transgaming.com@gtempaccount.com51171882013-04-13 03:39:10 +00001151}
1152
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001153void Context::bindPixelPackBuffer(GLuint bufferHandle)
shannon.woods%transgaming.com@gtempaccount.comc926e5f2013-04-13 03:39:18 +00001154{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001155 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001156 mGLState.setPixelPackBufferBinding(this, buffer);
shannon.woods%transgaming.com@gtempaccount.comc926e5f2013-04-13 03:39:18 +00001157}
1158
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001159void Context::bindPixelUnpackBuffer(GLuint bufferHandle)
shannon.woods%transgaming.com@gtempaccount.comc926e5f2013-04-13 03:39:18 +00001160{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001161 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001162 mGLState.setPixelUnpackBufferBinding(this, buffer);
shannon.woods%transgaming.com@gtempaccount.comc926e5f2013-04-13 03:39:18 +00001163}
1164
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001165void Context::useProgram(GLuint program)
1166{
Jamie Madill6c1f6712017-02-14 19:08:04 -05001167 mGLState.setProgram(this, getProgram(program));
daniel@transgaming.com95d29422012-07-24 18:36:10 +00001168}
1169
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001170void Context::bindTransformFeedback(GLuint transformFeedbackHandle)
Geoff Langc8058452014-02-03 12:04:11 -05001171{
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001172 TransformFeedback *transformFeedback =
1173 checkTransformFeedbackAllocation(transformFeedbackHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001174 mGLState.setTransformFeedbackBinding(this, transformFeedback);
Geoff Langc8058452014-02-03 12:04:11 -05001175}
1176
Geoff Lang5aad9672014-09-08 11:10:42 -04001177Error Context::beginQuery(GLenum target, GLuint query)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001178{
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001179 Query *queryObject = getQuery(query, true, target);
Jamie Madilldb2f14c2014-05-13 13:56:30 -04001180 ASSERT(queryObject);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001181
Geoff Lang5aad9672014-09-08 11:10:42 -04001182 // begin query
1183 Error error = queryObject->begin();
1184 if (error.isError())
1185 {
1186 return error;
1187 }
1188
1189 // set query as active for specified target only if begin succeeded
Jamie Madill4928b7c2017-06-20 12:57:39 -04001190 mGLState.setActiveQuery(this, target, queryObject);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001191
He Yunchaoacd18982017-01-04 10:46:42 +08001192 return NoError();
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001193}
1194
Geoff Lang5aad9672014-09-08 11:10:42 -04001195Error Context::endQuery(GLenum target)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001196{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001197 Query *queryObject = mGLState.getActiveQuery(target);
Jamie Madill45c785d2014-05-13 14:09:34 -04001198 ASSERT(queryObject);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001199
Geoff Lang5aad9672014-09-08 11:10:42 -04001200 gl::Error error = queryObject->end();
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001201
Geoff Lang5aad9672014-09-08 11:10:42 -04001202 // Always unbind the query, even if there was an error. This may delete the query object.
Jamie Madill4928b7c2017-06-20 12:57:39 -04001203 mGLState.setActiveQuery(this, target, nullptr);
Geoff Lang5aad9672014-09-08 11:10:42 -04001204
1205 return error;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001206}
1207
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001208Error Context::queryCounter(GLuint id, GLenum target)
1209{
1210 ASSERT(target == GL_TIMESTAMP_EXT);
1211
1212 Query *queryObject = getQuery(id, true, target);
1213 ASSERT(queryObject);
1214
1215 return queryObject->queryCounter();
1216}
1217
1218void Context::getQueryiv(GLenum target, GLenum pname, GLint *params)
1219{
1220 switch (pname)
1221 {
1222 case GL_CURRENT_QUERY_EXT:
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001223 params[0] = mGLState.getActiveQueryId(target);
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001224 break;
1225 case GL_QUERY_COUNTER_BITS_EXT:
1226 switch (target)
1227 {
1228 case GL_TIME_ELAPSED_EXT:
1229 params[0] = getExtensions().queryCounterBitsTimeElapsed;
1230 break;
1231 case GL_TIMESTAMP_EXT:
1232 params[0] = getExtensions().queryCounterBitsTimestamp;
1233 break;
1234 default:
1235 UNREACHABLE();
1236 params[0] = 0;
1237 break;
1238 }
1239 break;
1240 default:
1241 UNREACHABLE();
1242 return;
1243 }
1244}
1245
Geoff Lang2186c382016-10-14 10:54:54 -04001246void Context::getQueryObjectiv(GLuint id, GLenum pname, GLint *params)
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001247{
Geoff Lang2186c382016-10-14 10:54:54 -04001248 handleError(GetQueryObjectParameter(getQuery(id), pname, params));
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001249}
1250
Geoff Lang2186c382016-10-14 10:54:54 -04001251void Context::getQueryObjectuiv(GLuint id, GLenum pname, GLuint *params)
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001252{
Geoff Lang2186c382016-10-14 10:54:54 -04001253 handleError(GetQueryObjectParameter(getQuery(id), pname, params));
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001254}
1255
Geoff Lang2186c382016-10-14 10:54:54 -04001256void Context::getQueryObjecti64v(GLuint id, GLenum pname, GLint64 *params)
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001257{
Geoff Lang2186c382016-10-14 10:54:54 -04001258 handleError(GetQueryObjectParameter(getQuery(id), pname, params));
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001259}
1260
Geoff Lang2186c382016-10-14 10:54:54 -04001261void Context::getQueryObjectui64v(GLuint id, GLenum pname, GLuint64 *params)
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001262{
Geoff Lang2186c382016-10-14 10:54:54 -04001263 handleError(GetQueryObjectParameter(getQuery(id), pname, params));
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001264}
1265
Geoff Lang3bf8e3a2016-12-01 17:28:52 -05001266Framebuffer *Context::getFramebuffer(GLuint handle) const
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001267{
Geoff Lang3bf8e3a2016-12-01 17:28:52 -05001268 return mState.mFramebuffers->getFramebuffer(handle);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001269}
1270
Jamie Madill2f348d22017-06-05 10:50:59 -04001271FenceNV *Context::getFenceNV(GLuint handle)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001272{
Jamie Madill4e25a0d2016-03-08 13:53:03 -05001273 auto fence = mFenceNVMap.find(handle);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001274
Jamie Madill33dc8432013-07-26 11:55:05 -04001275 if (fence == mFenceNVMap.end())
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001276 {
Yunchao Hef81ce4a2017-04-24 10:49:17 +08001277 return nullptr;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001278 }
1279 else
1280 {
1281 return fence->second;
1282 }
1283}
1284
Jamie Madill2f348d22017-06-05 10:50:59 -04001285Query *Context::getQuery(GLuint handle, bool create, GLenum type)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001286{
Jamie Madill4e25a0d2016-03-08 13:53:03 -05001287 auto query = mQueryMap.find(handle);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001288
1289 if (query == mQueryMap.end())
1290 {
Yunchao Hef81ce4a2017-04-24 10:49:17 +08001291 return nullptr;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001292 }
1293 else
1294 {
1295 if (!query->second && create)
1296 {
Jamie Madill53ea9cc2016-05-17 10:12:52 -04001297 query->second = new Query(mImplementation->createQuery(type), handle);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001298 query->second->addRef();
1299 }
1300 return query->second;
1301 }
1302}
1303
Geoff Lang70d0f492015-12-10 17:45:46 -05001304Query *Context::getQuery(GLuint handle) const
1305{
1306 auto iter = mQueryMap.find(handle);
1307 return (iter != mQueryMap.end()) ? iter->second : nullptr;
1308}
1309
Jamie Madill1fc7e2c2014-01-21 16:47:10 -05001310Texture *Context::getTargetTexture(GLenum target) const
1311{
Ian Ewellbda75592016-04-18 17:25:54 -04001312 ASSERT(ValidTextureTarget(this, target) || ValidTextureExternalTarget(this, target));
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001313 return mGLState.getTargetTexture(target);
shannon.woods%transgaming.com@gtempaccount.comc926e5f2013-04-13 03:39:18 +00001314}
1315
Geoff Lang76b10c92014-09-05 16:28:14 -04001316Texture *Context::getSamplerTexture(unsigned int sampler, GLenum type) const
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001317{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001318 return mGLState.getSamplerTexture(sampler, type);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001319}
1320
Geoff Lang492a7e42014-11-05 13:27:06 -05001321Compiler *Context::getCompiler() const
1322{
Jamie Madill2f348d22017-06-05 10:50:59 -04001323 if (mCompiler.get() == nullptr)
1324 {
Jamie Madill4928b7c2017-06-20 12:57:39 -04001325 mCompiler.set(this, new Compiler(mImplementation.get(), mState));
Jamie Madill2f348d22017-06-05 10:50:59 -04001326 }
1327 return mCompiler.get();
Geoff Lang492a7e42014-11-05 13:27:06 -05001328}
1329
Jamie Madillc1d770e2017-04-13 17:31:24 -04001330void Context::getBooleanvImpl(GLenum pname, GLboolean *params)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001331{
1332 switch (pname)
1333 {
Jamie Madill231c7f52017-04-26 13:45:37 -04001334 case GL_SHADER_COMPILER:
1335 *params = GL_TRUE;
1336 break;
1337 case GL_CONTEXT_ROBUST_ACCESS_EXT:
1338 *params = mRobustAccess ? GL_TRUE : GL_FALSE;
1339 break;
1340 default:
1341 mGLState.getBooleanv(pname, params);
1342 break;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001343 }
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001344}
1345
Jamie Madillc1d770e2017-04-13 17:31:24 -04001346void Context::getFloatvImpl(GLenum pname, GLfloat *params)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001347{
Shannon Woods53a94a82014-06-24 15:20:36 -04001348 // Queries about context capabilities and maximums are answered by Context.
1349 // Queries about current GL state values are answered by State.
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001350 switch (pname)
1351 {
Jamie Madill231c7f52017-04-26 13:45:37 -04001352 case GL_ALIASED_LINE_WIDTH_RANGE:
1353 params[0] = mCaps.minAliasedLineWidth;
1354 params[1] = mCaps.maxAliasedLineWidth;
1355 break;
1356 case GL_ALIASED_POINT_SIZE_RANGE:
1357 params[0] = mCaps.minAliasedPointSize;
1358 params[1] = mCaps.maxAliasedPointSize;
1359 break;
1360 case GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT:
1361 ASSERT(mExtensions.textureFilterAnisotropic);
1362 *params = mExtensions.maxTextureAnisotropy;
1363 break;
1364 case GL_MAX_TEXTURE_LOD_BIAS:
1365 *params = mCaps.maxLODBias;
1366 break;
1367
1368 case GL_PATH_MODELVIEW_MATRIX_CHROMIUM:
1369 case GL_PATH_PROJECTION_MATRIX_CHROMIUM:
1370 {
1371 ASSERT(mExtensions.pathRendering);
1372 const GLfloat *m = mGLState.getPathRenderingMatrix(pname);
1373 memcpy(params, m, 16 * sizeof(GLfloat));
1374 }
Geoff Lange6d4e122015-06-29 13:33:55 -04001375 break;
Sami Väisänene45e53b2016-05-25 10:36:04 +03001376
Jamie Madill231c7f52017-04-26 13:45:37 -04001377 default:
1378 mGLState.getFloatv(pname, params);
1379 break;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001380 }
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001381}
1382
Jamie Madillc1d770e2017-04-13 17:31:24 -04001383void Context::getIntegervImpl(GLenum pname, GLint *params)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001384{
Shannon Woods53a94a82014-06-24 15:20:36 -04001385 // Queries about context capabilities and maximums are answered by Context.
1386 // Queries about current GL state values are answered by State.
shannon.woods%transgaming.com@gtempaccount.combc373e52013-04-13 03:31:23 +00001387
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001388 switch (pname)
1389 {
Jamie Madill231c7f52017-04-26 13:45:37 -04001390 case GL_MAX_VERTEX_ATTRIBS:
1391 *params = mCaps.maxVertexAttributes;
1392 break;
1393 case GL_MAX_VERTEX_UNIFORM_VECTORS:
1394 *params = mCaps.maxVertexUniformVectors;
1395 break;
1396 case GL_MAX_VERTEX_UNIFORM_COMPONENTS:
1397 *params = mCaps.maxVertexUniformComponents;
1398 break;
1399 case GL_MAX_VARYING_VECTORS:
1400 *params = mCaps.maxVaryingVectors;
1401 break;
1402 case GL_MAX_VARYING_COMPONENTS:
1403 *params = mCaps.maxVertexOutputComponents;
1404 break;
1405 case GL_MAX_COMBINED_TEXTURE_IMAGE_UNITS:
1406 *params = mCaps.maxCombinedTextureImageUnits;
1407 break;
1408 case GL_MAX_VERTEX_TEXTURE_IMAGE_UNITS:
1409 *params = mCaps.maxVertexTextureImageUnits;
1410 break;
1411 case GL_MAX_TEXTURE_IMAGE_UNITS:
1412 *params = mCaps.maxTextureImageUnits;
1413 break;
1414 case GL_MAX_FRAGMENT_UNIFORM_VECTORS:
1415 *params = mCaps.maxFragmentUniformVectors;
1416 break;
1417 case GL_MAX_FRAGMENT_UNIFORM_COMPONENTS:
1418 *params = mCaps.maxFragmentUniformComponents;
1419 break;
1420 case GL_MAX_RENDERBUFFER_SIZE:
1421 *params = mCaps.maxRenderbufferSize;
1422 break;
1423 case GL_MAX_COLOR_ATTACHMENTS_EXT:
1424 *params = mCaps.maxColorAttachments;
1425 break;
1426 case GL_MAX_DRAW_BUFFERS_EXT:
1427 *params = mCaps.maxDrawBuffers;
1428 break;
1429 // case GL_FRAMEBUFFER_BINDING: // now equivalent to
1430 // GL_DRAW_FRAMEBUFFER_BINDING_ANGLE
1431 case GL_SUBPIXEL_BITS:
1432 *params = 4;
1433 break;
1434 case GL_MAX_TEXTURE_SIZE:
1435 *params = mCaps.max2DTextureSize;
1436 break;
1437 case GL_MAX_CUBE_MAP_TEXTURE_SIZE:
1438 *params = mCaps.maxCubeMapTextureSize;
1439 break;
1440 case GL_MAX_3D_TEXTURE_SIZE:
1441 *params = mCaps.max3DTextureSize;
1442 break;
1443 case GL_MAX_ARRAY_TEXTURE_LAYERS:
1444 *params = mCaps.maxArrayTextureLayers;
1445 break;
1446 case GL_UNIFORM_BUFFER_OFFSET_ALIGNMENT:
1447 *params = mCaps.uniformBufferOffsetAlignment;
1448 break;
1449 case GL_MAX_UNIFORM_BUFFER_BINDINGS:
1450 *params = mCaps.maxUniformBufferBindings;
1451 break;
1452 case GL_MAX_VERTEX_UNIFORM_BLOCKS:
1453 *params = mCaps.maxVertexUniformBlocks;
1454 break;
1455 case GL_MAX_FRAGMENT_UNIFORM_BLOCKS:
1456 *params = mCaps.maxFragmentUniformBlocks;
1457 break;
1458 case GL_MAX_COMBINED_UNIFORM_BLOCKS:
1459 *params = mCaps.maxCombinedTextureImageUnits;
1460 break;
1461 case GL_MAX_VERTEX_OUTPUT_COMPONENTS:
1462 *params = mCaps.maxVertexOutputComponents;
1463 break;
1464 case GL_MAX_FRAGMENT_INPUT_COMPONENTS:
1465 *params = mCaps.maxFragmentInputComponents;
1466 break;
1467 case GL_MIN_PROGRAM_TEXEL_OFFSET:
1468 *params = mCaps.minProgramTexelOffset;
1469 break;
1470 case GL_MAX_PROGRAM_TEXEL_OFFSET:
1471 *params = mCaps.maxProgramTexelOffset;
1472 break;
1473 case GL_MAJOR_VERSION:
1474 *params = getClientVersion().major;
1475 break;
1476 case GL_MINOR_VERSION:
1477 *params = getClientVersion().minor;
1478 break;
1479 case GL_MAX_ELEMENTS_INDICES:
1480 *params = mCaps.maxElementsIndices;
1481 break;
1482 case GL_MAX_ELEMENTS_VERTICES:
1483 *params = mCaps.maxElementsVertices;
1484 break;
1485 case GL_MAX_TRANSFORM_FEEDBACK_INTERLEAVED_COMPONENTS:
1486 *params = mCaps.maxTransformFeedbackInterleavedComponents;
1487 break;
1488 case GL_MAX_TRANSFORM_FEEDBACK_SEPARATE_ATTRIBS:
1489 *params = mCaps.maxTransformFeedbackSeparateAttributes;
1490 break;
1491 case GL_MAX_TRANSFORM_FEEDBACK_SEPARATE_COMPONENTS:
1492 *params = mCaps.maxTransformFeedbackSeparateComponents;
1493 break;
1494 case GL_NUM_COMPRESSED_TEXTURE_FORMATS:
1495 *params = static_cast<GLint>(mCaps.compressedTextureFormats.size());
1496 break;
1497 case GL_MAX_SAMPLES_ANGLE:
1498 *params = mCaps.maxSamples;
1499 break;
1500 case GL_MAX_VIEWPORT_DIMS:
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001501 {
Geoff Langc0b9ef42014-07-02 10:02:37 -04001502 params[0] = mCaps.maxViewportWidth;
1503 params[1] = mCaps.maxViewportHeight;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001504 }
1505 break;
Jamie Madill231c7f52017-04-26 13:45:37 -04001506 case GL_COMPRESSED_TEXTURE_FORMATS:
1507 std::copy(mCaps.compressedTextureFormats.begin(), mCaps.compressedTextureFormats.end(),
1508 params);
1509 break;
1510 case GL_RESET_NOTIFICATION_STRATEGY_EXT:
1511 *params = mResetStrategy;
1512 break;
1513 case GL_NUM_SHADER_BINARY_FORMATS:
1514 *params = static_cast<GLint>(mCaps.shaderBinaryFormats.size());
1515 break;
1516 case GL_SHADER_BINARY_FORMATS:
1517 std::copy(mCaps.shaderBinaryFormats.begin(), mCaps.shaderBinaryFormats.end(), params);
1518 break;
1519 case GL_NUM_PROGRAM_BINARY_FORMATS:
1520 *params = static_cast<GLint>(mCaps.programBinaryFormats.size());
1521 break;
1522 case GL_PROGRAM_BINARY_FORMATS:
1523 std::copy(mCaps.programBinaryFormats.begin(), mCaps.programBinaryFormats.end(), params);
1524 break;
1525 case GL_NUM_EXTENSIONS:
1526 *params = static_cast<GLint>(mExtensionStrings.size());
1527 break;
Geoff Lang70d0f492015-12-10 17:45:46 -05001528
Jamie Madill231c7f52017-04-26 13:45:37 -04001529 // GL_KHR_debug
1530 case GL_MAX_DEBUG_MESSAGE_LENGTH:
1531 *params = mExtensions.maxDebugMessageLength;
1532 break;
1533 case GL_MAX_DEBUG_LOGGED_MESSAGES:
1534 *params = mExtensions.maxDebugLoggedMessages;
1535 break;
1536 case GL_MAX_DEBUG_GROUP_STACK_DEPTH:
1537 *params = mExtensions.maxDebugGroupStackDepth;
1538 break;
1539 case GL_MAX_LABEL_LENGTH:
1540 *params = mExtensions.maxLabelLength;
1541 break;
Geoff Lang70d0f492015-12-10 17:45:46 -05001542
Jamie Madill231c7f52017-04-26 13:45:37 -04001543 // GL_EXT_disjoint_timer_query
1544 case GL_GPU_DISJOINT_EXT:
1545 *params = mImplementation->getGPUDisjoint();
1546 break;
1547 case GL_MAX_FRAMEBUFFER_WIDTH:
1548 *params = mCaps.maxFramebufferWidth;
1549 break;
1550 case GL_MAX_FRAMEBUFFER_HEIGHT:
1551 *params = mCaps.maxFramebufferHeight;
1552 break;
1553 case GL_MAX_FRAMEBUFFER_SAMPLES:
1554 *params = mCaps.maxFramebufferSamples;
1555 break;
1556 case GL_MAX_SAMPLE_MASK_WORDS:
1557 *params = mCaps.maxSampleMaskWords;
1558 break;
1559 case GL_MAX_COLOR_TEXTURE_SAMPLES:
1560 *params = mCaps.maxColorTextureSamples;
1561 break;
1562 case GL_MAX_DEPTH_TEXTURE_SAMPLES:
1563 *params = mCaps.maxDepthTextureSamples;
1564 break;
1565 case GL_MAX_INTEGER_SAMPLES:
1566 *params = mCaps.maxIntegerSamples;
1567 break;
1568 case GL_MAX_VERTEX_ATTRIB_RELATIVE_OFFSET:
1569 *params = mCaps.maxVertexAttribRelativeOffset;
1570 break;
1571 case GL_MAX_VERTEX_ATTRIB_BINDINGS:
1572 *params = mCaps.maxVertexAttribBindings;
1573 break;
1574 case GL_MAX_VERTEX_ATTRIB_STRIDE:
1575 *params = mCaps.maxVertexAttribStride;
1576 break;
1577 case GL_MAX_VERTEX_ATOMIC_COUNTER_BUFFERS:
1578 *params = mCaps.maxVertexAtomicCounterBuffers;
1579 break;
1580 case GL_MAX_VERTEX_ATOMIC_COUNTERS:
1581 *params = mCaps.maxVertexAtomicCounters;
1582 break;
1583 case GL_MAX_VERTEX_IMAGE_UNIFORMS:
1584 *params = mCaps.maxVertexImageUniforms;
1585 break;
1586 case GL_MAX_VERTEX_SHADER_STORAGE_BLOCKS:
1587 *params = mCaps.maxVertexShaderStorageBlocks;
1588 break;
1589 case GL_MAX_FRAGMENT_ATOMIC_COUNTER_BUFFERS:
1590 *params = mCaps.maxFragmentAtomicCounterBuffers;
1591 break;
1592 case GL_MAX_FRAGMENT_ATOMIC_COUNTERS:
1593 *params = mCaps.maxFragmentAtomicCounters;
1594 break;
1595 case GL_MAX_FRAGMENT_IMAGE_UNIFORMS:
1596 *params = mCaps.maxFragmentImageUniforms;
1597 break;
1598 case GL_MAX_FRAGMENT_SHADER_STORAGE_BLOCKS:
1599 *params = mCaps.maxFragmentShaderStorageBlocks;
1600 break;
1601 case GL_MIN_PROGRAM_TEXTURE_GATHER_OFFSET:
1602 *params = mCaps.minProgramTextureGatherOffset;
1603 break;
1604 case GL_MAX_PROGRAM_TEXTURE_GATHER_OFFSET:
1605 *params = mCaps.maxProgramTextureGatherOffset;
1606 break;
1607 case GL_MAX_COMPUTE_WORK_GROUP_INVOCATIONS:
1608 *params = mCaps.maxComputeWorkGroupInvocations;
1609 break;
1610 case GL_MAX_COMPUTE_UNIFORM_BLOCKS:
1611 *params = mCaps.maxComputeUniformBlocks;
1612 break;
1613 case GL_MAX_COMPUTE_TEXTURE_IMAGE_UNITS:
1614 *params = mCaps.maxComputeTextureImageUnits;
1615 break;
1616 case GL_MAX_COMPUTE_SHARED_MEMORY_SIZE:
1617 *params = mCaps.maxComputeSharedMemorySize;
1618 break;
1619 case GL_MAX_COMPUTE_UNIFORM_COMPONENTS:
1620 *params = mCaps.maxComputeUniformComponents;
1621 break;
1622 case GL_MAX_COMPUTE_ATOMIC_COUNTER_BUFFERS:
1623 *params = mCaps.maxComputeAtomicCounterBuffers;
1624 break;
1625 case GL_MAX_COMPUTE_ATOMIC_COUNTERS:
1626 *params = mCaps.maxComputeAtomicCounters;
1627 break;
1628 case GL_MAX_COMPUTE_IMAGE_UNIFORMS:
1629 *params = mCaps.maxComputeImageUniforms;
1630 break;
1631 case GL_MAX_COMBINED_COMPUTE_UNIFORM_COMPONENTS:
1632 *params = mCaps.maxCombinedComputeUniformComponents;
1633 break;
1634 case GL_MAX_COMPUTE_SHADER_STORAGE_BLOCKS:
1635 *params = mCaps.maxComputeShaderStorageBlocks;
1636 break;
1637 case GL_MAX_COMBINED_SHADER_OUTPUT_RESOURCES:
1638 *params = mCaps.maxCombinedShaderOutputResources;
1639 break;
1640 case GL_MAX_UNIFORM_LOCATIONS:
1641 *params = mCaps.maxUniformLocations;
1642 break;
1643 case GL_MAX_ATOMIC_COUNTER_BUFFER_BINDINGS:
1644 *params = mCaps.maxAtomicCounterBufferBindings;
1645 break;
1646 case GL_MAX_ATOMIC_COUNTER_BUFFER_SIZE:
1647 *params = mCaps.maxAtomicCounterBufferSize;
1648 break;
1649 case GL_MAX_COMBINED_ATOMIC_COUNTER_BUFFERS:
1650 *params = mCaps.maxCombinedAtomicCounterBuffers;
1651 break;
1652 case GL_MAX_COMBINED_ATOMIC_COUNTERS:
1653 *params = mCaps.maxCombinedAtomicCounters;
1654 break;
1655 case GL_MAX_IMAGE_UNITS:
1656 *params = mCaps.maxImageUnits;
1657 break;
1658 case GL_MAX_COMBINED_IMAGE_UNIFORMS:
1659 *params = mCaps.maxCombinedImageUniforms;
1660 break;
1661 case GL_MAX_SHADER_STORAGE_BUFFER_BINDINGS:
1662 *params = mCaps.maxShaderStorageBufferBindings;
1663 break;
1664 case GL_MAX_COMBINED_SHADER_STORAGE_BLOCKS:
1665 *params = mCaps.maxCombinedShaderStorageBlocks;
1666 break;
1667 case GL_SHADER_STORAGE_BUFFER_OFFSET_ALIGNMENT:
1668 *params = mCaps.shaderStorageBufferOffsetAlignment;
1669 break;
1670 default:
1671 mGLState.getIntegerv(this, pname, params);
1672 break;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001673 }
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001674}
1675
Jamie Madill893ab082014-05-16 16:56:10 -04001676void Context::getInteger64v(GLenum pname, GLint64 *params)
Jamie Madill0fda9862013-07-19 16:36:55 -04001677{
Shannon Woods53a94a82014-06-24 15:20:36 -04001678 // Queries about context capabilities and maximums are answered by Context.
1679 // Queries about current GL state values are answered by State.
Jamie Madill0fda9862013-07-19 16:36:55 -04001680 switch (pname)
1681 {
Jamie Madill231c7f52017-04-26 13:45:37 -04001682 case GL_MAX_ELEMENT_INDEX:
1683 *params = mCaps.maxElementIndex;
1684 break;
1685 case GL_MAX_UNIFORM_BLOCK_SIZE:
1686 *params = mCaps.maxUniformBlockSize;
1687 break;
1688 case GL_MAX_COMBINED_VERTEX_UNIFORM_COMPONENTS:
1689 *params = mCaps.maxCombinedVertexUniformComponents;
1690 break;
1691 case GL_MAX_COMBINED_FRAGMENT_UNIFORM_COMPONENTS:
1692 *params = mCaps.maxCombinedFragmentUniformComponents;
1693 break;
1694 case GL_MAX_SERVER_WAIT_TIMEOUT:
1695 *params = mCaps.maxServerWaitTimeout;
1696 break;
Ian Ewell53f59f42016-01-28 17:36:55 -05001697
Jamie Madill231c7f52017-04-26 13:45:37 -04001698 // GL_EXT_disjoint_timer_query
1699 case GL_TIMESTAMP_EXT:
1700 *params = mImplementation->getTimestamp();
1701 break;
Martin Radev66fb8202016-07-28 11:45:20 +03001702
Jamie Madill231c7f52017-04-26 13:45:37 -04001703 case GL_MAX_SHADER_STORAGE_BLOCK_SIZE:
1704 *params = mCaps.maxShaderStorageBlockSize;
1705 break;
1706 default:
1707 UNREACHABLE();
1708 break;
Jamie Madill0fda9862013-07-19 16:36:55 -04001709 }
Jamie Madill0fda9862013-07-19 16:36:55 -04001710}
1711
Geoff Lang70d0f492015-12-10 17:45:46 -05001712void Context::getPointerv(GLenum pname, void **params) const
1713{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001714 mGLState.getPointerv(pname, params);
Geoff Lang70d0f492015-12-10 17:45:46 -05001715}
1716
Martin Radev66fb8202016-07-28 11:45:20 +03001717void Context::getIntegeri_v(GLenum target, GLuint index, GLint *data)
Shannon Woods1b2fb852013-08-19 14:28:48 -04001718{
Shannon Woods53a94a82014-06-24 15:20:36 -04001719 // Queries about context capabilities and maximums are answered by Context.
1720 // Queries about current GL state values are answered by State.
Martin Radev66fb8202016-07-28 11:45:20 +03001721
1722 GLenum nativeType;
1723 unsigned int numParams;
1724 bool queryStatus = getIndexedQueryParameterInfo(target, &nativeType, &numParams);
1725 ASSERT(queryStatus);
1726
1727 if (nativeType == GL_INT)
1728 {
1729 switch (target)
1730 {
1731 case GL_MAX_COMPUTE_WORK_GROUP_COUNT:
1732 ASSERT(index < 3u);
1733 *data = mCaps.maxComputeWorkGroupCount[index];
1734 break;
1735 case GL_MAX_COMPUTE_WORK_GROUP_SIZE:
1736 ASSERT(index < 3u);
1737 *data = mCaps.maxComputeWorkGroupSize[index];
1738 break;
1739 default:
1740 mGLState.getIntegeri_v(target, index, data);
1741 }
1742 }
1743 else
1744 {
1745 CastIndexedStateValues(this, nativeType, target, index, numParams, data);
1746 }
Shannon Woods1b2fb852013-08-19 14:28:48 -04001747}
1748
Martin Radev66fb8202016-07-28 11:45:20 +03001749void Context::getInteger64i_v(GLenum target, GLuint index, GLint64 *data)
Shannon Woods1b2fb852013-08-19 14:28:48 -04001750{
Shannon Woods53a94a82014-06-24 15:20:36 -04001751 // Queries about context capabilities and maximums are answered by Context.
1752 // Queries about current GL state values are answered by State.
Martin Radev66fb8202016-07-28 11:45:20 +03001753
1754 GLenum nativeType;
1755 unsigned int numParams;
1756 bool queryStatus = getIndexedQueryParameterInfo(target, &nativeType, &numParams);
1757 ASSERT(queryStatus);
1758
1759 if (nativeType == GL_INT_64_ANGLEX)
1760 {
1761 mGLState.getInteger64i_v(target, index, data);
1762 }
1763 else
1764 {
1765 CastIndexedStateValues(this, nativeType, target, index, numParams, data);
1766 }
1767}
1768
1769void Context::getBooleani_v(GLenum target, GLuint index, GLboolean *data)
1770{
1771 // Queries about context capabilities and maximums are answered by Context.
1772 // Queries about current GL state values are answered by State.
1773
1774 GLenum nativeType;
1775 unsigned int numParams;
1776 bool queryStatus = getIndexedQueryParameterInfo(target, &nativeType, &numParams);
1777 ASSERT(queryStatus);
1778
1779 if (nativeType == GL_BOOL)
1780 {
1781 mGLState.getBooleani_v(target, index, data);
1782 }
1783 else
1784 {
1785 CastIndexedStateValues(this, nativeType, target, index, numParams, data);
1786 }
Shannon Woods1b2fb852013-08-19 14:28:48 -04001787}
1788
He Yunchao010e4db2017-03-03 14:22:06 +08001789void Context::getBufferParameteriv(GLenum target, GLenum pname, GLint *params)
1790{
1791 Buffer *buffer = mGLState.getTargetBuffer(target);
1792 QueryBufferParameteriv(buffer, pname, params);
1793}
1794
1795void Context::getFramebufferAttachmentParameteriv(GLenum target,
1796 GLenum attachment,
1797 GLenum pname,
1798 GLint *params)
1799{
1800 const Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
1801 QueryFramebufferAttachmentParameteriv(framebuffer, attachment, pname, params);
1802}
1803
1804void Context::getRenderbufferParameteriv(GLenum target, GLenum pname, GLint *params)
1805{
1806 Renderbuffer *renderbuffer = mGLState.getCurrentRenderbuffer();
1807 QueryRenderbufferiv(this, renderbuffer, pname, params);
1808}
1809
1810void Context::getTexParameterfv(GLenum target, GLenum pname, GLfloat *params)
1811{
1812 Texture *texture = getTargetTexture(target);
1813 QueryTexParameterfv(texture, pname, params);
1814}
1815
1816void Context::getTexParameteriv(GLenum target, GLenum pname, GLint *params)
1817{
1818 Texture *texture = getTargetTexture(target);
1819 QueryTexParameteriv(texture, pname, params);
1820}
1821void Context::texParameterf(GLenum target, GLenum pname, GLfloat param)
1822{
1823 Texture *texture = getTargetTexture(target);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001824 SetTexParameterf(this, texture, pname, param);
He Yunchao010e4db2017-03-03 14:22:06 +08001825}
1826
1827void Context::texParameterfv(GLenum target, GLenum pname, const GLfloat *params)
1828{
1829 Texture *texture = getTargetTexture(target);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001830 SetTexParameterfv(this, texture, pname, params);
He Yunchao010e4db2017-03-03 14:22:06 +08001831}
1832
1833void Context::texParameteri(GLenum target, GLenum pname, GLint param)
1834{
1835 Texture *texture = getTargetTexture(target);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001836 SetTexParameteri(this, texture, pname, param);
He Yunchao010e4db2017-03-03 14:22:06 +08001837}
1838
1839void Context::texParameteriv(GLenum target, GLenum pname, const GLint *params)
1840{
1841 Texture *texture = getTargetTexture(target);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001842 SetTexParameteriv(this, texture, pname, params);
He Yunchao010e4db2017-03-03 14:22:06 +08001843}
1844
Jamie Madill675fe712016-12-19 13:07:54 -05001845void Context::drawArrays(GLenum mode, GLint first, GLsizei count)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001846{
Jamie Madill1b94d432015-08-07 13:23:23 -04001847 syncRendererState();
Jamie Madillc564c072017-06-01 12:45:42 -04001848 auto error = mImplementation->drawArrays(this, mode, first, count);
Jamie Madill675fe712016-12-19 13:07:54 -05001849 handleError(error);
1850 if (!error.isError())
1851 {
1852 MarkTransformFeedbackBufferUsage(mGLState.getCurrentTransformFeedback());
1853 }
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001854}
1855
Jamie Madill675fe712016-12-19 13:07:54 -05001856void Context::drawArraysInstanced(GLenum mode, GLint first, GLsizei count, GLsizei instanceCount)
Geoff Langf6db0982015-08-25 13:04:00 -04001857{
1858 syncRendererState();
Jamie Madillc564c072017-06-01 12:45:42 -04001859 auto error = mImplementation->drawArraysInstanced(this, mode, first, count, instanceCount);
Jamie Madill675fe712016-12-19 13:07:54 -05001860 handleError(error);
1861 if (!error.isError())
1862 {
1863 MarkTransformFeedbackBufferUsage(mGLState.getCurrentTransformFeedback());
1864 }
Geoff Langf6db0982015-08-25 13:04:00 -04001865}
1866
Jamie Madill876429b2017-04-20 15:46:24 -04001867void Context::drawElements(GLenum mode, GLsizei count, GLenum type, const void *indices)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001868{
Jamie Madill1b94d432015-08-07 13:23:23 -04001869 syncRendererState();
Jamie Madill9c9b40a2017-04-26 16:31:57 -04001870 const IndexRange &indexRange = getParams<HasIndexRange>().getIndexRange().value();
Jamie Madillc564c072017-06-01 12:45:42 -04001871 handleError(mImplementation->drawElements(this, mode, count, type, indices, indexRange));
Geoff Langf6db0982015-08-25 13:04:00 -04001872}
1873
Jamie Madill675fe712016-12-19 13:07:54 -05001874void Context::drawElementsInstanced(GLenum mode,
1875 GLsizei count,
1876 GLenum type,
Jamie Madill876429b2017-04-20 15:46:24 -04001877 const void *indices,
Jamie Madill9c9b40a2017-04-26 16:31:57 -04001878 GLsizei instances)
Geoff Langf6db0982015-08-25 13:04:00 -04001879{
1880 syncRendererState();
Jamie Madill9c9b40a2017-04-26 16:31:57 -04001881 const IndexRange &indexRange = getParams<HasIndexRange>().getIndexRange().value();
Jamie Madillc564c072017-06-01 12:45:42 -04001882 handleError(mImplementation->drawElementsInstanced(this, mode, count, type, indices, instances,
1883 indexRange));
Geoff Langf6db0982015-08-25 13:04:00 -04001884}
1885
Jamie Madill675fe712016-12-19 13:07:54 -05001886void Context::drawRangeElements(GLenum mode,
1887 GLuint start,
1888 GLuint end,
1889 GLsizei count,
1890 GLenum type,
Jamie Madill876429b2017-04-20 15:46:24 -04001891 const void *indices)
Geoff Langf6db0982015-08-25 13:04:00 -04001892{
1893 syncRendererState();
Jamie Madill9c9b40a2017-04-26 16:31:57 -04001894 const IndexRange &indexRange = getParams<HasIndexRange>().getIndexRange().value();
Jamie Madillc564c072017-06-01 12:45:42 -04001895 handleError(mImplementation->drawRangeElements(this, mode, start, end, count, type, indices,
1896 indexRange));
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001897}
1898
Jamie Madill876429b2017-04-20 15:46:24 -04001899void Context::drawArraysIndirect(GLenum mode, const void *indirect)
Jiajia Qind9671222016-11-29 16:30:31 +08001900{
1901 syncRendererState();
Jamie Madillc564c072017-06-01 12:45:42 -04001902 handleError(mImplementation->drawArraysIndirect(this, mode, indirect));
Jiajia Qind9671222016-11-29 16:30:31 +08001903}
1904
Jamie Madill876429b2017-04-20 15:46:24 -04001905void Context::drawElementsIndirect(GLenum mode, GLenum type, const void *indirect)
Jiajia Qind9671222016-11-29 16:30:31 +08001906{
1907 syncRendererState();
Jamie Madillc564c072017-06-01 12:45:42 -04001908 handleError(mImplementation->drawElementsIndirect(this, mode, type, indirect));
Jiajia Qind9671222016-11-29 16:30:31 +08001909}
1910
Jamie Madill675fe712016-12-19 13:07:54 -05001911void Context::flush()
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001912{
Jamie Madill675fe712016-12-19 13:07:54 -05001913 handleError(mImplementation->flush());
Geoff Lang129753a2015-01-09 16:52:09 -05001914}
1915
Jamie Madill675fe712016-12-19 13:07:54 -05001916void Context::finish()
Geoff Lang129753a2015-01-09 16:52:09 -05001917{
Jamie Madill675fe712016-12-19 13:07:54 -05001918 handleError(mImplementation->finish());
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001919}
1920
Austin Kinross6ee1e782015-05-29 17:05:37 -07001921void Context::insertEventMarker(GLsizei length, const char *marker)
1922{
Jamie Madill53ea9cc2016-05-17 10:12:52 -04001923 ASSERT(mImplementation);
1924 mImplementation->insertEventMarker(length, marker);
Austin Kinross6ee1e782015-05-29 17:05:37 -07001925}
1926
1927void Context::pushGroupMarker(GLsizei length, const char *marker)
1928{
Jamie Madill53ea9cc2016-05-17 10:12:52 -04001929 ASSERT(mImplementation);
1930 mImplementation->pushGroupMarker(length, marker);
Austin Kinross6ee1e782015-05-29 17:05:37 -07001931}
1932
1933void Context::popGroupMarker()
1934{
Jamie Madill53ea9cc2016-05-17 10:12:52 -04001935 ASSERT(mImplementation);
1936 mImplementation->popGroupMarker();
Austin Kinross6ee1e782015-05-29 17:05:37 -07001937}
1938
Geoff Langd8605522016-04-13 10:19:12 -04001939void Context::bindUniformLocation(GLuint program, GLint location, const GLchar *name)
1940{
1941 Program *programObject = getProgram(program);
1942 ASSERT(programObject);
1943
1944 programObject->bindUniformLocation(location, name);
1945}
1946
Sami Väisänena797e062016-05-12 15:23:40 +03001947void Context::setCoverageModulation(GLenum components)
1948{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001949 mGLState.setCoverageModulation(components);
Sami Väisänena797e062016-05-12 15:23:40 +03001950}
1951
Sami Väisänene45e53b2016-05-25 10:36:04 +03001952void Context::loadPathRenderingMatrix(GLenum matrixMode, const GLfloat *matrix)
1953{
1954 mGLState.loadPathRenderingMatrix(matrixMode, matrix);
1955}
1956
1957void Context::loadPathRenderingIdentityMatrix(GLenum matrixMode)
1958{
1959 GLfloat I[16];
1960 angle::Matrix<GLfloat>::setToIdentity(I);
1961
1962 mGLState.loadPathRenderingMatrix(matrixMode, I);
1963}
1964
1965void Context::stencilFillPath(GLuint path, GLenum fillMode, GLuint mask)
1966{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001967 const auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +03001968 if (!pathObj)
1969 return;
1970
1971 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
1972 syncRendererState();
1973
1974 mImplementation->stencilFillPath(pathObj, fillMode, mask);
1975}
1976
1977void Context::stencilStrokePath(GLuint path, GLint reference, GLuint mask)
1978{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001979 const auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +03001980 if (!pathObj)
1981 return;
1982
1983 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
1984 syncRendererState();
1985
1986 mImplementation->stencilStrokePath(pathObj, reference, mask);
1987}
1988
1989void Context::coverFillPath(GLuint path, GLenum coverMode)
1990{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001991 const auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +03001992 if (!pathObj)
1993 return;
1994
1995 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
1996 syncRendererState();
1997
1998 mImplementation->coverFillPath(pathObj, coverMode);
1999}
2000
2001void Context::coverStrokePath(GLuint path, GLenum coverMode)
2002{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002003 const auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +03002004 if (!pathObj)
2005 return;
2006
2007 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
2008 syncRendererState();
2009
2010 mImplementation->coverStrokePath(pathObj, coverMode);
2011}
2012
2013void Context::stencilThenCoverFillPath(GLuint path, GLenum fillMode, GLuint mask, GLenum coverMode)
2014{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002015 const auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +03002016 if (!pathObj)
2017 return;
2018
2019 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
2020 syncRendererState();
2021
2022 mImplementation->stencilThenCoverFillPath(pathObj, fillMode, mask, coverMode);
2023}
2024
2025void Context::stencilThenCoverStrokePath(GLuint path,
2026 GLint reference,
2027 GLuint mask,
2028 GLenum coverMode)
2029{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002030 const auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +03002031 if (!pathObj)
2032 return;
2033
2034 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
2035 syncRendererState();
2036
2037 mImplementation->stencilThenCoverStrokePath(pathObj, reference, mask, coverMode);
2038}
2039
Sami Väisänend59ca052016-06-21 16:10:00 +03002040void Context::coverFillPathInstanced(GLsizei numPaths,
2041 GLenum pathNameType,
2042 const void *paths,
2043 GLuint pathBase,
2044 GLenum coverMode,
2045 GLenum transformType,
2046 const GLfloat *transformValues)
2047{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002048 const auto &pathObjects = GatherPaths(*mState.mPaths, numPaths, pathNameType, paths, pathBase);
Sami Väisänend59ca052016-06-21 16:10:00 +03002049
2050 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
2051 syncRendererState();
2052
2053 mImplementation->coverFillPathInstanced(pathObjects, coverMode, transformType, transformValues);
2054}
Sami Väisänen46eaa942016-06-29 10:26:37 +03002055
Sami Väisänend59ca052016-06-21 16:10:00 +03002056void Context::coverStrokePathInstanced(GLsizei numPaths,
2057 GLenum pathNameType,
2058 const void *paths,
2059 GLuint pathBase,
2060 GLenum coverMode,
2061 GLenum transformType,
2062 const GLfloat *transformValues)
2063{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002064 const auto &pathObjects = GatherPaths(*mState.mPaths, numPaths, pathNameType, paths, pathBase);
Sami Väisänend59ca052016-06-21 16:10:00 +03002065
2066 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
2067 syncRendererState();
2068
2069 mImplementation->coverStrokePathInstanced(pathObjects, coverMode, transformType,
2070 transformValues);
2071}
Sami Väisänen46eaa942016-06-29 10:26:37 +03002072
Sami Väisänend59ca052016-06-21 16:10:00 +03002073void Context::stencilFillPathInstanced(GLsizei numPaths,
2074 GLenum pathNameType,
2075 const void *paths,
2076 GLuint pathBase,
2077 GLenum fillMode,
2078 GLuint mask,
2079 GLenum transformType,
2080 const GLfloat *transformValues)
2081{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002082 const auto &pathObjects = GatherPaths(*mState.mPaths, numPaths, pathNameType, paths, pathBase);
Sami Väisänend59ca052016-06-21 16:10:00 +03002083
2084 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
2085 syncRendererState();
2086
2087 mImplementation->stencilFillPathInstanced(pathObjects, fillMode, mask, transformType,
2088 transformValues);
2089}
Sami Väisänen46eaa942016-06-29 10:26:37 +03002090
Sami Väisänend59ca052016-06-21 16:10:00 +03002091void Context::stencilStrokePathInstanced(GLsizei numPaths,
2092 GLenum pathNameType,
2093 const void *paths,
2094 GLuint pathBase,
2095 GLint reference,
2096 GLuint mask,
2097 GLenum transformType,
2098 const GLfloat *transformValues)
2099{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002100 const auto &pathObjects = GatherPaths(*mState.mPaths, numPaths, pathNameType, paths, pathBase);
Sami Väisänend59ca052016-06-21 16:10:00 +03002101
2102 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
2103 syncRendererState();
2104
2105 mImplementation->stencilStrokePathInstanced(pathObjects, reference, mask, transformType,
2106 transformValues);
2107}
Sami Väisänen46eaa942016-06-29 10:26:37 +03002108
Sami Väisänend59ca052016-06-21 16:10:00 +03002109void Context::stencilThenCoverFillPathInstanced(GLsizei numPaths,
2110 GLenum pathNameType,
2111 const void *paths,
2112 GLuint pathBase,
2113 GLenum fillMode,
2114 GLuint mask,
2115 GLenum coverMode,
2116 GLenum transformType,
2117 const GLfloat *transformValues)
2118{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002119 const auto &pathObjects = GatherPaths(*mState.mPaths, numPaths, pathNameType, paths, pathBase);
Sami Väisänend59ca052016-06-21 16:10:00 +03002120
2121 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
2122 syncRendererState();
2123
2124 mImplementation->stencilThenCoverFillPathInstanced(pathObjects, coverMode, fillMode, mask,
2125 transformType, transformValues);
2126}
Sami Väisänen46eaa942016-06-29 10:26:37 +03002127
Sami Väisänend59ca052016-06-21 16:10:00 +03002128void Context::stencilThenCoverStrokePathInstanced(GLsizei numPaths,
2129 GLenum pathNameType,
2130 const void *paths,
2131 GLuint pathBase,
2132 GLint reference,
2133 GLuint mask,
2134 GLenum coverMode,
2135 GLenum transformType,
2136 const GLfloat *transformValues)
2137{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002138 const auto &pathObjects = GatherPaths(*mState.mPaths, numPaths, pathNameType, paths, pathBase);
Sami Väisänend59ca052016-06-21 16:10:00 +03002139
2140 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
2141 syncRendererState();
2142
2143 mImplementation->stencilThenCoverStrokePathInstanced(pathObjects, coverMode, reference, mask,
2144 transformType, transformValues);
2145}
2146
Sami Väisänen46eaa942016-06-29 10:26:37 +03002147void Context::bindFragmentInputLocation(GLuint program, GLint location, const GLchar *name)
2148{
2149 auto *programObject = getProgram(program);
2150
2151 programObject->bindFragmentInputLocation(location, name);
2152}
2153
2154void Context::programPathFragmentInputGen(GLuint program,
2155 GLint location,
2156 GLenum genMode,
2157 GLint components,
2158 const GLfloat *coeffs)
2159{
2160 auto *programObject = getProgram(program);
2161
Jamie Madillbd044ed2017-06-05 12:59:21 -04002162 programObject->pathFragmentInputGen(this, location, genMode, components, coeffs);
Sami Väisänen46eaa942016-06-29 10:26:37 +03002163}
2164
jchen1015015f72017-03-16 13:54:21 +08002165GLuint Context::getProgramResourceIndex(GLuint program, GLenum programInterface, const GLchar *name)
2166{
jchen10fd7c3b52017-03-21 15:36:03 +08002167 const auto *programObject = getProgram(program);
jchen1015015f72017-03-16 13:54:21 +08002168 return QueryProgramResourceIndex(programObject, programInterface, name);
2169}
2170
jchen10fd7c3b52017-03-21 15:36:03 +08002171void Context::getProgramResourceName(GLuint program,
2172 GLenum programInterface,
2173 GLuint index,
2174 GLsizei bufSize,
2175 GLsizei *length,
2176 GLchar *name)
2177{
2178 const auto *programObject = getProgram(program);
2179 QueryProgramResourceName(programObject, programInterface, index, bufSize, length, name);
2180}
2181
Jamie Madill437fa652016-05-03 15:13:24 -04002182void Context::handleError(const Error &error)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002183{
Geoff Langda5777c2014-07-11 09:52:58 -04002184 if (error.isError())
2185 {
Kenneth Russellf2f6f652016-10-05 19:53:23 -07002186 GLenum code = error.getCode();
2187 mErrors.insert(code);
2188 if (code == GL_OUT_OF_MEMORY && getWorkarounds().loseContextOnOutOfMemory)
2189 {
2190 markContextLost();
2191 }
Geoff Lang70d0f492015-12-10 17:45:46 -05002192
2193 if (!error.getMessage().empty())
2194 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002195 auto *debug = &mGLState.getDebug();
2196 debug->insertMessage(GL_DEBUG_SOURCE_API, GL_DEBUG_TYPE_ERROR, error.getID(),
2197 GL_DEBUG_SEVERITY_HIGH, error.getMessage());
Geoff Lang70d0f492015-12-10 17:45:46 -05002198 }
Geoff Langda5777c2014-07-11 09:52:58 -04002199 }
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002200}
2201
2202// Get one of the recorded errors and clear its flag, if any.
2203// [OpenGL ES 2.0.24] section 2.5 page 13.
2204GLenum Context::getError()
2205{
Geoff Langda5777c2014-07-11 09:52:58 -04002206 if (mErrors.empty())
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002207 {
Geoff Langda5777c2014-07-11 09:52:58 -04002208 return GL_NO_ERROR;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002209 }
Geoff Langda5777c2014-07-11 09:52:58 -04002210 else
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002211 {
Geoff Langda5777c2014-07-11 09:52:58 -04002212 GLenum error = *mErrors.begin();
2213 mErrors.erase(mErrors.begin());
2214 return error;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002215 }
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002216}
2217
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002218// NOTE: this function should not assume that this context is current!
2219void Context::markContextLost()
2220{
2221 if (mResetStrategy == GL_LOSE_CONTEXT_ON_RESET_EXT)
Kenneth Russellf2f6f652016-10-05 19:53:23 -07002222 {
Jamie Madill231c7f52017-04-26 13:45:37 -04002223 mResetStatus = GL_UNKNOWN_CONTEXT_RESET_EXT;
Kenneth Russellf2f6f652016-10-05 19:53:23 -07002224 mContextLostForced = true;
2225 }
Jamie Madill231c7f52017-04-26 13:45:37 -04002226 mContextLost = true;
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002227}
2228
2229bool Context::isContextLost()
2230{
2231 return mContextLost;
2232}
2233
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002234GLenum Context::getResetStatus()
2235{
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002236 // Even if the application doesn't want to know about resets, we want to know
2237 // as it will allow us to skip all the calls.
2238 if (mResetStrategy == GL_NO_RESET_NOTIFICATION_EXT)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002239 {
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002240 if (!mContextLost && mImplementation->getResetStatus() != GL_NO_ERROR)
Jamie Madill9dd0cf02014-11-24 11:38:51 -05002241 {
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002242 mContextLost = true;
Jamie Madill9dd0cf02014-11-24 11:38:51 -05002243 }
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002244
2245 // EXT_robustness, section 2.6: If the reset notification behavior is
2246 // NO_RESET_NOTIFICATION_EXT, then the implementation will never deliver notification of
2247 // reset events, and GetGraphicsResetStatusEXT will always return NO_ERROR.
2248 return GL_NO_ERROR;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002249 }
2250
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002251 // The GL_EXT_robustness spec says that if a reset is encountered, a reset
2252 // status should be returned at least once, and GL_NO_ERROR should be returned
2253 // once the device has finished resetting.
2254 if (!mContextLost)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002255 {
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002256 ASSERT(mResetStatus == GL_NO_ERROR);
2257 mResetStatus = mImplementation->getResetStatus();
shannon.woods@transgaming.comddd6c802013-02-28 23:05:14 +00002258
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002259 if (mResetStatus != GL_NO_ERROR)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002260 {
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002261 mContextLost = true;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002262 }
2263 }
Kenneth Russellf2f6f652016-10-05 19:53:23 -07002264 else if (!mContextLostForced && mResetStatus != GL_NO_ERROR)
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002265 {
Kenneth Russellf2f6f652016-10-05 19:53:23 -07002266 // If markContextLost was used to mark the context lost then
2267 // assume that is not recoverable, and continue to report the
2268 // lost reset status for the lifetime of this context.
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002269 mResetStatus = mImplementation->getResetStatus();
2270 }
Jamie Madill893ab082014-05-16 16:56:10 -04002271
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002272 return mResetStatus;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002273}
2274
2275bool Context::isResetNotificationEnabled()
2276{
2277 return (mResetStrategy == GL_LOSE_CONTEXT_ON_RESET_EXT);
2278}
2279
Corentin Walleze3b10e82015-05-20 11:06:25 -04002280const egl::Config *Context::getConfig() const
Régis Fénéon83107972015-02-05 12:57:44 +01002281{
Corentin Walleze3b10e82015-05-20 11:06:25 -04002282 return mConfig;
Régis Fénéon83107972015-02-05 12:57:44 +01002283}
2284
2285EGLenum Context::getClientType() const
2286{
2287 return mClientType;
2288}
2289
2290EGLenum Context::getRenderBuffer() const
2291{
Geoff Lang3bf8e3a2016-12-01 17:28:52 -05002292 const Framebuffer *framebuffer = mState.mFramebuffers->getFramebuffer(0);
2293 if (framebuffer == nullptr)
Corentin Wallez37c39792015-08-20 14:19:46 -04002294 {
2295 return EGL_NONE;
2296 }
Geoff Lang3bf8e3a2016-12-01 17:28:52 -05002297
2298 const FramebufferAttachment *backAttachment = framebuffer->getAttachment(GL_BACK);
2299 ASSERT(backAttachment != nullptr);
2300 return backAttachment->getSurface()->getRenderBuffer();
Régis Fénéon83107972015-02-05 12:57:44 +01002301}
2302
Jamie Madill3f01e6c2016-03-08 13:53:02 -05002303VertexArray *Context::checkVertexArrayAllocation(GLuint vertexArrayHandle)
Geoff Lang36167ab2015-12-07 10:27:14 -05002304{
Jamie Madill5bf9ff42016-02-01 11:13:03 -05002305 // Only called after a prior call to Gen.
Jamie Madill3f01e6c2016-03-08 13:53:02 -05002306 VertexArray *vertexArray = getVertexArray(vertexArrayHandle);
2307 if (!vertexArray)
Geoff Lang36167ab2015-12-07 10:27:14 -05002308 {
Jiawei-Shao2597fb62016-12-09 16:38:02 +08002309 vertexArray = new VertexArray(mImplementation.get(), vertexArrayHandle,
2310 mCaps.maxVertexAttributes, mCaps.maxVertexAttribBindings);
Jamie Madill53ea9cc2016-05-17 10:12:52 -04002311
Jamie Madill3f01e6c2016-03-08 13:53:02 -05002312 mVertexArrayMap[vertexArrayHandle] = vertexArray;
Geoff Lang36167ab2015-12-07 10:27:14 -05002313 }
Jamie Madill3f01e6c2016-03-08 13:53:02 -05002314
2315 return vertexArray;
Geoff Lang36167ab2015-12-07 10:27:14 -05002316}
2317
Jamie Madill3f01e6c2016-03-08 13:53:02 -05002318TransformFeedback *Context::checkTransformFeedbackAllocation(GLuint transformFeedbackHandle)
Geoff Lang36167ab2015-12-07 10:27:14 -05002319{
Jamie Madill5bf9ff42016-02-01 11:13:03 -05002320 // Only called after a prior call to Gen.
Jamie Madill3f01e6c2016-03-08 13:53:02 -05002321 TransformFeedback *transformFeedback = getTransformFeedback(transformFeedbackHandle);
2322 if (!transformFeedback)
Geoff Lang36167ab2015-12-07 10:27:14 -05002323 {
Jamie Madill53ea9cc2016-05-17 10:12:52 -04002324 transformFeedback =
2325 new TransformFeedback(mImplementation.get(), transformFeedbackHandle, mCaps);
Jamie Madill3f01e6c2016-03-08 13:53:02 -05002326 transformFeedback->addRef();
2327 mTransformFeedbackMap[transformFeedbackHandle] = transformFeedback;
Geoff Lang36167ab2015-12-07 10:27:14 -05002328 }
Jamie Madill3f01e6c2016-03-08 13:53:02 -05002329
2330 return transformFeedback;
Geoff Lang36167ab2015-12-07 10:27:14 -05002331}
2332
2333bool Context::isVertexArrayGenerated(GLuint vertexArray)
2334{
Geoff Langf41a7152016-09-19 15:11:17 -04002335 ASSERT(mVertexArrayMap.find(0) != mVertexArrayMap.end());
Geoff Lang36167ab2015-12-07 10:27:14 -05002336 return mVertexArrayMap.find(vertexArray) != mVertexArrayMap.end();
2337}
2338
2339bool Context::isTransformFeedbackGenerated(GLuint transformFeedback)
2340{
Geoff Langf41a7152016-09-19 15:11:17 -04002341 ASSERT(mTransformFeedbackMap.find(0) != mTransformFeedbackMap.end());
Geoff Lang36167ab2015-12-07 10:27:14 -05002342 return mTransformFeedbackMap.find(transformFeedback) != mTransformFeedbackMap.end();
2343}
2344
Shannon Woods53a94a82014-06-24 15:20:36 -04002345void Context::detachTexture(GLuint texture)
2346{
2347 // Simple pass-through to State's detachTexture method, as textures do not require
2348 // allocation map management either here or in the resource manager at detach time.
2349 // Zero textures are held by the Context, and we don't attempt to request them from
2350 // the State.
Jamie Madilla02315b2017-02-23 14:14:47 -05002351 mGLState.detachTexture(this, mZeroTextures, texture);
Shannon Woods53a94a82014-06-24 15:20:36 -04002352}
2353
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002354void Context::detachBuffer(GLuint buffer)
2355{
Yuly Novikov5807a532015-12-03 13:01:22 -05002356 // Simple pass-through to State's detachBuffer method, since
2357 // only buffer attachments to container objects that are bound to the current context
2358 // should be detached. And all those are available in State.
Shannon Woods53a94a82014-06-24 15:20:36 -04002359
Yuly Novikov5807a532015-12-03 13:01:22 -05002360 // [OpenGL ES 3.2] section 5.1.2 page 45:
2361 // Attachments to unbound container objects, such as
2362 // deletion of a buffer attached to a vertex array object which is not bound to the context,
2363 // are not affected and continue to act as references on the deleted object
Jamie Madill4928b7c2017-06-20 12:57:39 -04002364 mGLState.detachBuffer(this, buffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002365}
2366
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002367void Context::detachFramebuffer(GLuint framebuffer)
2368{
Shannon Woods53a94a82014-06-24 15:20:36 -04002369 // Framebuffer detachment is handled by Context, because 0 is a valid
2370 // Framebuffer object, and a pointer to it must be passed from Context
2371 // to State at binding time.
2372
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002373 // [OpenGL ES 2.0.24] section 4.4 page 107:
Jamie Madill231c7f52017-04-26 13:45:37 -04002374 // If a framebuffer that is currently bound to the target FRAMEBUFFER is deleted, it is as
2375 // though BindFramebuffer had been executed with the target of FRAMEBUFFER and framebuffer of
2376 // zero.
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002377
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002378 if (mGLState.removeReadFramebufferBinding(framebuffer) && framebuffer != 0)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002379 {
2380 bindReadFramebuffer(0);
2381 }
2382
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002383 if (mGLState.removeDrawFramebufferBinding(framebuffer) && framebuffer != 0)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002384 {
2385 bindDrawFramebuffer(0);
2386 }
2387}
2388
2389void Context::detachRenderbuffer(GLuint renderbuffer)
2390{
Jamie Madilla02315b2017-02-23 14:14:47 -05002391 mGLState.detachRenderbuffer(this, renderbuffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002392}
2393
Jamie Madill57a89722013-07-02 11:57:03 -04002394void Context::detachVertexArray(GLuint vertexArray)
2395{
Jamie Madill77a72f62015-04-14 11:18:32 -04002396 // Vertex array detachment is handled by Context, because 0 is a valid
2397 // VAO, and a pointer to it must be passed from Context to State at
Shannon Woods53a94a82014-06-24 15:20:36 -04002398 // binding time.
2399
Jamie Madill57a89722013-07-02 11:57:03 -04002400 // [OpenGL ES 3.0.2] section 2.10 page 43:
2401 // If a vertex array object that is currently bound is deleted, the binding
2402 // for that object reverts to zero and the default vertex array becomes current.
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002403 if (mGLState.removeVertexArrayBinding(vertexArray))
Jamie Madill57a89722013-07-02 11:57:03 -04002404 {
2405 bindVertexArray(0);
2406 }
2407}
2408
Geoff Langc8058452014-02-03 12:04:11 -05002409void Context::detachTransformFeedback(GLuint transformFeedback)
2410{
Corentin Walleza2257da2016-04-19 16:43:12 -04002411 // Transform feedback detachment is handled by Context, because 0 is a valid
2412 // transform feedback, and a pointer to it must be passed from Context to State at
2413 // binding time.
2414
2415 // The OpenGL specification doesn't mention what should happen when the currently bound
2416 // transform feedback object is deleted. Since it is a container object, we treat it like
2417 // VAOs and FBOs and set the current bound transform feedback back to 0.
Jamie Madill4928b7c2017-06-20 12:57:39 -04002418 if (mGLState.removeTransformFeedbackBinding(this, transformFeedback))
Corentin Walleza2257da2016-04-19 16:43:12 -04002419 {
2420 bindTransformFeedback(0);
2421 }
Geoff Langc8058452014-02-03 12:04:11 -05002422}
2423
Jamie Madilldc356042013-07-19 16:36:57 -04002424void Context::detachSampler(GLuint sampler)
2425{
Jamie Madill4928b7c2017-06-20 12:57:39 -04002426 mGLState.detachSampler(this, sampler);
Jamie Madilldc356042013-07-19 16:36:57 -04002427}
2428
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002429void Context::setVertexAttribDivisor(GLuint index, GLuint divisor)
2430{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002431 mGLState.setVertexAttribDivisor(index, divisor);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002432}
2433
Jamie Madille29d1672013-07-19 16:36:57 -04002434void Context::samplerParameteri(GLuint sampler, GLenum pname, GLint param)
2435{
Geoff Langc1984ed2016-10-07 12:41:00 -04002436 Sampler *samplerObject =
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002437 mState.mSamplers->checkSamplerAllocation(mImplementation.get(), sampler);
Geoff Langc1984ed2016-10-07 12:41:00 -04002438 SetSamplerParameteri(samplerObject, pname, param);
2439}
Jamie Madille29d1672013-07-19 16:36:57 -04002440
Geoff Langc1984ed2016-10-07 12:41:00 -04002441void Context::samplerParameteriv(GLuint sampler, GLenum pname, const GLint *param)
2442{
2443 Sampler *samplerObject =
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002444 mState.mSamplers->checkSamplerAllocation(mImplementation.get(), sampler);
Geoff Langc1984ed2016-10-07 12:41:00 -04002445 SetSamplerParameteriv(samplerObject, pname, param);
Jamie Madille29d1672013-07-19 16:36:57 -04002446}
2447
2448void Context::samplerParameterf(GLuint sampler, GLenum pname, GLfloat param)
2449{
Geoff Langc1984ed2016-10-07 12:41:00 -04002450 Sampler *samplerObject =
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002451 mState.mSamplers->checkSamplerAllocation(mImplementation.get(), sampler);
Geoff Langc1984ed2016-10-07 12:41:00 -04002452 SetSamplerParameterf(samplerObject, pname, param);
Jamie Madille29d1672013-07-19 16:36:57 -04002453}
2454
Geoff Langc1984ed2016-10-07 12:41:00 -04002455void Context::samplerParameterfv(GLuint sampler, GLenum pname, const GLfloat *param)
Jamie Madill9675b802013-07-19 16:36:59 -04002456{
Geoff Langc1984ed2016-10-07 12:41:00 -04002457 Sampler *samplerObject =
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002458 mState.mSamplers->checkSamplerAllocation(mImplementation.get(), sampler);
Geoff Langc1984ed2016-10-07 12:41:00 -04002459 SetSamplerParameterfv(samplerObject, pname, param);
Jamie Madill9675b802013-07-19 16:36:59 -04002460}
2461
Geoff Langc1984ed2016-10-07 12:41:00 -04002462void Context::getSamplerParameteriv(GLuint sampler, GLenum pname, GLint *params)
Jamie Madill9675b802013-07-19 16:36:59 -04002463{
Geoff Langc1984ed2016-10-07 12:41:00 -04002464 const Sampler *samplerObject =
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002465 mState.mSamplers->checkSamplerAllocation(mImplementation.get(), sampler);
Geoff Langc1984ed2016-10-07 12:41:00 -04002466 QuerySamplerParameteriv(samplerObject, pname, params);
2467}
Jamie Madill9675b802013-07-19 16:36:59 -04002468
Geoff Langc1984ed2016-10-07 12:41:00 -04002469void Context::getSamplerParameterfv(GLuint sampler, GLenum pname, GLfloat *params)
2470{
2471 const Sampler *samplerObject =
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002472 mState.mSamplers->checkSamplerAllocation(mImplementation.get(), sampler);
Geoff Langc1984ed2016-10-07 12:41:00 -04002473 QuerySamplerParameterfv(samplerObject, pname, params);
Jamie Madill9675b802013-07-19 16:36:59 -04002474}
2475
Olli Etuahof0fee072016-03-30 15:11:58 +03002476void Context::programParameteri(GLuint program, GLenum pname, GLint value)
2477{
2478 gl::Program *programObject = getProgram(program);
Yunchao He61afff12017-03-14 15:34:03 +08002479 SetProgramParameteri(programObject, pname, value);
Olli Etuahof0fee072016-03-30 15:11:58 +03002480}
2481
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002482void Context::initRendererString()
2483{
daniel@transgaming.comca1ac1f2013-01-11 04:13:05 +00002484 std::ostringstream rendererString;
2485 rendererString << "ANGLE (";
Jamie Madill53ea9cc2016-05-17 10:12:52 -04002486 rendererString << mImplementation->getRendererDescription();
daniel@transgaming.comca1ac1f2013-01-11 04:13:05 +00002487 rendererString << ")";
2488
Geoff Langcec35902014-04-16 10:52:36 -04002489 mRendererString = MakeStaticString(rendererString.str());
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002490}
2491
Geoff Langc339c4e2016-11-29 10:37:36 -05002492void Context::initVersionStrings()
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002493{
Geoff Langc339c4e2016-11-29 10:37:36 -05002494 const Version &clientVersion = getClientVersion();
2495
2496 std::ostringstream versionString;
2497 versionString << "OpenGL ES " << clientVersion.major << "." << clientVersion.minor << " (ANGLE "
2498 << ANGLE_VERSION_STRING << ")";
2499 mVersionString = MakeStaticString(versionString.str());
2500
2501 std::ostringstream shadingLanguageVersionString;
2502 shadingLanguageVersionString << "OpenGL ES GLSL ES "
2503 << (clientVersion.major == 2 ? 1 : clientVersion.major) << "."
2504 << clientVersion.minor << "0 (ANGLE " << ANGLE_VERSION_STRING
2505 << ")";
2506 mShadingLanguageString = MakeStaticString(shadingLanguageVersionString.str());
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002507}
2508
Geoff Langcec35902014-04-16 10:52:36 -04002509void Context::initExtensionStrings()
2510{
Geoff Langc339c4e2016-11-29 10:37:36 -05002511 auto mergeExtensionStrings = [](const std::vector<const char *> &strings) {
2512 std::ostringstream combinedStringStream;
2513 std::copy(strings.begin(), strings.end(),
2514 std::ostream_iterator<const char *>(combinedStringStream, " "));
2515 return MakeStaticString(combinedStringStream.str());
2516 };
2517
2518 mExtensionStrings.clear();
Geoff Langc287ea62016-09-16 14:46:51 -04002519 for (const auto &extensionString : mExtensions.getStrings())
2520 {
2521 mExtensionStrings.push_back(MakeStaticString(extensionString));
2522 }
Geoff Langc339c4e2016-11-29 10:37:36 -05002523 mExtensionString = mergeExtensionStrings(mExtensionStrings);
Geoff Langcec35902014-04-16 10:52:36 -04002524
Bryan Bernhart58806562017-01-05 13:09:31 -08002525 const gl::Extensions &nativeExtensions = mImplementation->getNativeExtensions();
2526
Geoff Langc339c4e2016-11-29 10:37:36 -05002527 mRequestableExtensionStrings.clear();
2528 for (const auto &extensionInfo : GetExtensionInfoMap())
2529 {
2530 if (extensionInfo.second.Requestable &&
Bryan Bernhart58806562017-01-05 13:09:31 -08002531 !(mExtensions.*(extensionInfo.second.ExtensionsMember)) &&
2532 nativeExtensions.*(extensionInfo.second.ExtensionsMember))
Geoff Langc339c4e2016-11-29 10:37:36 -05002533 {
2534 mRequestableExtensionStrings.push_back(MakeStaticString(extensionInfo.first));
2535 }
2536 }
2537 mRequestableExtensionString = mergeExtensionStrings(mRequestableExtensionStrings);
Geoff Langcec35902014-04-16 10:52:36 -04002538}
2539
Geoff Langc339c4e2016-11-29 10:37:36 -05002540const GLubyte *Context::getString(GLenum name) const
Geoff Langcec35902014-04-16 10:52:36 -04002541{
Geoff Langc339c4e2016-11-29 10:37:36 -05002542 switch (name)
2543 {
2544 case GL_VENDOR:
2545 return reinterpret_cast<const GLubyte *>("Google Inc.");
2546
2547 case GL_RENDERER:
2548 return reinterpret_cast<const GLubyte *>(mRendererString);
2549
2550 case GL_VERSION:
2551 return reinterpret_cast<const GLubyte *>(mVersionString);
2552
2553 case GL_SHADING_LANGUAGE_VERSION:
2554 return reinterpret_cast<const GLubyte *>(mShadingLanguageString);
2555
2556 case GL_EXTENSIONS:
2557 return reinterpret_cast<const GLubyte *>(mExtensionString);
2558
2559 case GL_REQUESTABLE_EXTENSIONS_ANGLE:
2560 return reinterpret_cast<const GLubyte *>(mRequestableExtensionString);
2561
2562 default:
2563 UNREACHABLE();
2564 return nullptr;
2565 }
Geoff Langcec35902014-04-16 10:52:36 -04002566}
2567
Geoff Langc339c4e2016-11-29 10:37:36 -05002568const GLubyte *Context::getStringi(GLenum name, GLuint index) const
Geoff Langcec35902014-04-16 10:52:36 -04002569{
Geoff Langc339c4e2016-11-29 10:37:36 -05002570 switch (name)
2571 {
2572 case GL_EXTENSIONS:
2573 return reinterpret_cast<const GLubyte *>(mExtensionStrings[index]);
2574
2575 case GL_REQUESTABLE_EXTENSIONS_ANGLE:
2576 return reinterpret_cast<const GLubyte *>(mRequestableExtensionStrings[index]);
2577
2578 default:
2579 UNREACHABLE();
2580 return nullptr;
2581 }
Geoff Langcec35902014-04-16 10:52:36 -04002582}
2583
2584size_t Context::getExtensionStringCount() const
2585{
2586 return mExtensionStrings.size();
2587}
2588
Geoff Langc339c4e2016-11-29 10:37:36 -05002589void Context::requestExtension(const char *name)
2590{
2591 const ExtensionInfoMap &extensionInfos = GetExtensionInfoMap();
2592 ASSERT(extensionInfos.find(name) != extensionInfos.end());
2593 const auto &extension = extensionInfos.at(name);
2594 ASSERT(extension.Requestable);
2595
2596 if (mExtensions.*(extension.ExtensionsMember))
2597 {
2598 // Extension already enabled
2599 return;
2600 }
2601
2602 mExtensions.*(extension.ExtensionsMember) = true;
2603 updateCaps();
2604 initExtensionStrings();
Bryan Bernhart58806562017-01-05 13:09:31 -08002605
Jamie Madill2f348d22017-06-05 10:50:59 -04002606 // Release the shader compiler so it will be re-created with the requested extensions enabled.
2607 releaseShaderCompiler();
Geoff Lang9aded172017-04-05 11:07:56 -04002608
2609 // Invalidate all cached completenesses for textures and framebuffer. Some extensions make new
2610 // formats renderable or sampleable.
2611 mState.mTextures->invalidateTextureComplenessCache();
2612 for (auto &zeroTexture : mZeroTextures)
2613 {
2614 zeroTexture.second->invalidateCompletenessCache();
2615 }
2616
2617 mState.mFramebuffers->invalidateFramebufferComplenessCache();
Geoff Langc339c4e2016-11-29 10:37:36 -05002618}
2619
2620size_t Context::getRequestableExtensionStringCount() const
2621{
2622 return mRequestableExtensionStrings.size();
2623}
2624
Olli Etuahoc3e55a42016-03-09 16:29:18 +02002625void Context::beginTransformFeedback(GLenum primitiveMode)
2626{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002627 TransformFeedback *transformFeedback = mGLState.getCurrentTransformFeedback();
Olli Etuahoc3e55a42016-03-09 16:29:18 +02002628 ASSERT(transformFeedback != nullptr);
2629 ASSERT(!transformFeedback->isPaused());
2630
Jamie Madill6c1f6712017-02-14 19:08:04 -05002631 transformFeedback->begin(this, primitiveMode, mGLState.getProgram());
Olli Etuahoc3e55a42016-03-09 16:29:18 +02002632}
2633
2634bool Context::hasActiveTransformFeedback(GLuint program) const
2635{
2636 for (auto pair : mTransformFeedbackMap)
2637 {
2638 if (pair.second != nullptr && pair.second->hasBoundProgram(program))
2639 {
2640 return true;
2641 }
2642 }
2643 return false;
2644}
2645
Jamie Madill4e0e6f82017-02-17 11:06:03 -05002646void Context::initCaps(const egl::DisplayExtensions &displayExtensions)
Geoff Lang493daf52014-07-03 13:38:44 -04002647{
Jamie Madill53ea9cc2016-05-17 10:12:52 -04002648 mCaps = mImplementation->getNativeCaps();
Geoff Lang493daf52014-07-03 13:38:44 -04002649
Jamie Madill53ea9cc2016-05-17 10:12:52 -04002650 mExtensions = mImplementation->getNativeExtensions();
Geoff Lang493daf52014-07-03 13:38:44 -04002651
Jamie Madill53ea9cc2016-05-17 10:12:52 -04002652 mLimitations = mImplementation->getNativeLimitations();
Austin Kinross02df7962015-07-01 10:03:42 -07002653
Geoff Langeb66a6e2016-10-31 13:06:12 -04002654 if (getClientVersion() < Version(3, 0))
Geoff Lang493daf52014-07-03 13:38:44 -04002655 {
2656 // Disable ES3+ extensions
Jamie Madill231c7f52017-04-26 13:45:37 -04002657 mExtensions.colorBufferFloat = false;
Geoff Langb66a9092016-05-16 15:59:14 -04002658 mExtensions.eglImageExternalEssl3 = false;
Vincent Lang25ab4512016-05-13 18:13:59 +02002659 mExtensions.textureNorm16 = false;
Geoff Lang493daf52014-07-03 13:38:44 -04002660 }
2661
Geoff Langeb66a6e2016-10-31 13:06:12 -04002662 if (getClientVersion() > Version(2, 0))
Geoff Lang493daf52014-07-03 13:38:44 -04002663 {
2664 // FIXME(geofflang): Don't support EXT_sRGB in non-ES2 contexts
Jamie Madill231c7f52017-04-26 13:45:37 -04002665 // mExtensions.sRGB = false;
Geoff Lang493daf52014-07-03 13:38:44 -04002666 }
2667
Jamie Madill00ed7a12016-05-19 13:13:38 -04002668 // Some extensions are always available because they are implemented in the GL layer.
Jamie Madill231c7f52017-04-26 13:45:37 -04002669 mExtensions.bindUniformLocation = true;
2670 mExtensions.vertexArrayObject = true;
Geoff Langf41a7152016-09-19 15:11:17 -04002671 mExtensions.bindGeneratesResource = true;
Geoff Langfeb8c682017-02-13 16:07:35 -05002672 mExtensions.clientArrays = true;
Geoff Langc339c4e2016-11-29 10:37:36 -05002673 mExtensions.requestExtension = true;
Jamie Madill00ed7a12016-05-19 13:13:38 -04002674
2675 // Enable the no error extension if the context was created with the flag.
2676 mExtensions.noError = mSkipValidation;
2677
Corentin Wallezccab69d2017-01-27 16:57:15 -05002678 // Enable surfaceless to advertise we'll have the correct behavior when there is no default FBO
Corentin Wallezc295e512017-01-27 17:47:50 -05002679 mExtensions.surfacelessContext = displayExtensions.surfacelessContext;
Corentin Wallezccab69d2017-01-27 16:57:15 -05002680
Geoff Lang70d0f492015-12-10 17:45:46 -05002681 // Explicitly enable GL_KHR_debug
2682 mExtensions.debug = true;
2683 mExtensions.maxDebugMessageLength = 1024;
2684 mExtensions.maxDebugLoggedMessages = 1024;
2685 mExtensions.maxDebugGroupStackDepth = 1024;
2686 mExtensions.maxLabelLength = 1024;
2687
Geoff Langff5b2d52016-09-07 11:32:23 -04002688 // Explicitly enable GL_ANGLE_robust_client_memory
2689 mExtensions.robustClientMemory = true;
2690
Jamie Madille08a1d32017-03-07 17:24:06 -05002691 // Determine robust resource init availability from EGL.
2692 mExtensions.robustResourceInitialization =
Jamie Madill948bbe52017-06-01 13:10:42 -04002693 egl::Display::GetClientExtensions().displayRobustResourceInitialization;
Jamie Madille08a1d32017-03-07 17:24:06 -05002694
Geoff Lang301d1612014-07-09 10:34:37 -04002695 // Apply implementation limits
2696 mCaps.maxVertexAttributes = std::min<GLuint>(mCaps.maxVertexAttributes, MAX_VERTEX_ATTRIBS);
Jiawei-Shao2597fb62016-12-09 16:38:02 +08002697 mCaps.maxVertexAttribBindings =
2698 getClientVersion() < ES_3_1
2699 ? mCaps.maxVertexAttributes
2700 : std::min<GLuint>(mCaps.maxVertexAttribBindings, MAX_VERTEX_ATTRIB_BINDINGS);
2701
Jamie Madill231c7f52017-04-26 13:45:37 -04002702 mCaps.maxVertexUniformBlocks = std::min<GLuint>(
2703 mCaps.maxVertexUniformBlocks, IMPLEMENTATION_MAX_VERTEX_SHADER_UNIFORM_BUFFERS);
2704 mCaps.maxVertexOutputComponents =
2705 std::min<GLuint>(mCaps.maxVertexOutputComponents, IMPLEMENTATION_MAX_VARYING_VECTORS * 4);
Geoff Lang301d1612014-07-09 10:34:37 -04002706
Jamie Madill231c7f52017-04-26 13:45:37 -04002707 mCaps.maxFragmentInputComponents =
2708 std::min<GLuint>(mCaps.maxFragmentInputComponents, IMPLEMENTATION_MAX_VARYING_VECTORS * 4);
Geoff Lang3a61c322014-07-10 13:01:54 -04002709
Geoff Langc287ea62016-09-16 14:46:51 -04002710 // WebGL compatibility
Jamie Madill4e0e6f82017-02-17 11:06:03 -05002711 mExtensions.webglCompatibility = mWebGLContext;
Geoff Langc287ea62016-09-16 14:46:51 -04002712 for (const auto &extensionInfo : GetExtensionInfoMap())
2713 {
2714 // If this context is for WebGL, disable all enableable extensions
Jamie Madill4e0e6f82017-02-17 11:06:03 -05002715 if (mWebGLContext && extensionInfo.second.Requestable)
Geoff Langc287ea62016-09-16 14:46:51 -04002716 {
2717 mExtensions.*(extensionInfo.second.ExtensionsMember) = false;
2718 }
2719 }
2720
2721 // Generate texture caps
2722 updateCaps();
2723}
2724
2725void Context::updateCaps()
2726{
Geoff Lang900013c2014-07-07 11:32:19 -04002727 mCaps.compressedTextureFormats.clear();
Geoff Langc287ea62016-09-16 14:46:51 -04002728 mTextureCaps.clear();
Geoff Lang900013c2014-07-07 11:32:19 -04002729
Jamie Madill4e0e6f82017-02-17 11:06:03 -05002730 for (auto capsIt : mImplementation->getNativeTextureCaps())
Geoff Lang493daf52014-07-03 13:38:44 -04002731 {
Geoff Langca271392017-04-05 12:30:00 -04002732 GLenum sizedInternalFormat = capsIt.first;
Jamie Madill231c7f52017-04-26 13:45:37 -04002733 TextureCaps formatCaps = capsIt.second;
Geoff Lang493daf52014-07-03 13:38:44 -04002734
Geoff Langca271392017-04-05 12:30:00 -04002735 const InternalFormat &formatInfo = GetSizedInternalFormatInfo(sizedInternalFormat);
Geoff Langd87878e2014-09-19 15:42:59 -04002736
Geoff Lang0d8b7242015-09-09 14:56:53 -04002737 // Update the format caps based on the client version and extensions.
2738 // Caps are AND'd with the renderer caps because some core formats are still unsupported in
2739 // ES3.
2740 formatCaps.texturable =
Geoff Langeb66a6e2016-10-31 13:06:12 -04002741 formatCaps.texturable && formatInfo.textureSupport(getClientVersion(), mExtensions);
Geoff Lang0d8b7242015-09-09 14:56:53 -04002742 formatCaps.renderable =
Geoff Langeb66a6e2016-10-31 13:06:12 -04002743 formatCaps.renderable && formatInfo.renderSupport(getClientVersion(), mExtensions);
Geoff Lang0d8b7242015-09-09 14:56:53 -04002744 formatCaps.filterable =
Geoff Langeb66a6e2016-10-31 13:06:12 -04002745 formatCaps.filterable && formatInfo.filterSupport(getClientVersion(), mExtensions);
Geoff Langd87878e2014-09-19 15:42:59 -04002746
He Yunchaoccd8c9b2017-01-18 17:36:14 +08002747 // OpenGL ES does not support multisampling with non-rendererable formats
2748 // OpenGL ES 3.0 or prior does not support multisampling with integer formats
Olli Etuaho3cd0dd32017-06-06 14:43:30 +03002749 if (!formatCaps.renderable ||
He Yunchaoccd8c9b2017-01-18 17:36:14 +08002750 (getClientVersion() < ES_3_1 &&
2751 (formatInfo.componentType == GL_INT || formatInfo.componentType == GL_UNSIGNED_INT)))
Geoff Lang493daf52014-07-03 13:38:44 -04002752 {
Geoff Langd87878e2014-09-19 15:42:59 -04002753 formatCaps.sampleCounts.clear();
Geoff Lang493daf52014-07-03 13:38:44 -04002754 }
Olli Etuaho3cd0dd32017-06-06 14:43:30 +03002755 else
2756 {
2757 // We may have limited the max samples for some required renderbuffer formats due to
2758 // non-conformant formats. In this case MAX_SAMPLES needs to be lowered accordingly.
2759 GLuint formatMaxSamples = formatCaps.getMaxSamples();
2760
2761 // GLES 3.0.5 section 4.4.2.2: "Implementations must support creation of renderbuffers
2762 // in these required formats with up to the value of MAX_SAMPLES multisamples, with the
2763 // exception of signed and unsigned integer formats."
2764 if (formatInfo.componentType != GL_INT && formatInfo.componentType != GL_UNSIGNED_INT &&
2765 formatInfo.isRequiredRenderbufferFormat(getClientVersion()))
2766 {
2767 ASSERT(getClientVersion() < ES_3_0 || formatMaxSamples >= 4);
2768 mCaps.maxSamples = std::min(mCaps.maxSamples, formatMaxSamples);
2769 }
2770
2771 // Handle GLES 3.1 MAX_*_SAMPLES values similarly to MAX_SAMPLES.
2772 if (getClientVersion() >= ES_3_1)
2773 {
2774 // GLES 3.1 section 9.2.5: "Implementations must support creation of renderbuffers
2775 // in these required formats with up to the value of MAX_SAMPLES multisamples, with
2776 // the exception that the signed and unsigned integer formats are required only to
2777 // support creation of renderbuffers with up to the value of MAX_INTEGER_SAMPLES
2778 // multisamples, which must be at least one."
2779 if (formatInfo.componentType == GL_INT ||
2780 formatInfo.componentType == GL_UNSIGNED_INT)
2781 {
2782 mCaps.maxIntegerSamples = std::min(mCaps.maxIntegerSamples, formatMaxSamples);
2783 }
2784
2785 // GLES 3.1 section 19.3.1.
2786 if (formatCaps.texturable)
2787 {
2788 if (formatInfo.depthBits > 0)
2789 {
2790 mCaps.maxDepthTextureSamples =
2791 std::min(mCaps.maxDepthTextureSamples, formatMaxSamples);
2792 }
2793 else if (formatInfo.redBits > 0)
2794 {
2795 mCaps.maxColorTextureSamples =
2796 std::min(mCaps.maxColorTextureSamples, formatMaxSamples);
2797 }
2798 }
2799 }
2800 }
Geoff Langd87878e2014-09-19 15:42:59 -04002801
2802 if (formatCaps.texturable && formatInfo.compressed)
2803 {
Geoff Langca271392017-04-05 12:30:00 -04002804 mCaps.compressedTextureFormats.push_back(sizedInternalFormat);
Geoff Langd87878e2014-09-19 15:42:59 -04002805 }
2806
Geoff Langca271392017-04-05 12:30:00 -04002807 mTextureCaps.insert(sizedInternalFormat, formatCaps);
Geoff Lang493daf52014-07-03 13:38:44 -04002808 }
2809}
2810
Kenneth Russellf2f6f652016-10-05 19:53:23 -07002811void Context::initWorkarounds()
2812{
Jamie Madill761b02c2017-06-23 16:27:06 -04002813 // Apply back-end workarounds.
2814 mImplementation->applyNativeWorkarounds(&mWorkarounds);
2815
Kenneth Russellf2f6f652016-10-05 19:53:23 -07002816 // Lose the context upon out of memory error if the application is
2817 // expecting to watch for those events.
2818 mWorkarounds.loseContextOnOutOfMemory = (mResetStrategy == GL_LOSE_CONTEXT_ON_RESET_EXT);
2819}
2820
Jamie Madill1b94d432015-08-07 13:23:23 -04002821void Context::syncRendererState()
2822{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002823 const State::DirtyBits &dirtyBits = mGLState.getDirtyBits();
Jamie Madillfe548342017-06-19 11:13:24 -04002824 mImplementation->syncState(this, dirtyBits);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002825 mGLState.clearDirtyBits();
Jamie Madilldd43e6c2017-03-24 14:18:49 -04002826 mGLState.syncDirtyObjects(this);
Jamie Madill1b94d432015-08-07 13:23:23 -04002827}
2828
Jamie Madillad9f24e2016-02-12 09:27:24 -05002829void Context::syncRendererState(const State::DirtyBits &bitMask,
2830 const State::DirtyObjects &objectMask)
Jamie Madill1b94d432015-08-07 13:23:23 -04002831{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002832 const State::DirtyBits &dirtyBits = (mGLState.getDirtyBits() & bitMask);
Jamie Madillfe548342017-06-19 11:13:24 -04002833 mImplementation->syncState(this, dirtyBits);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002834 mGLState.clearDirtyBits(dirtyBits);
Jamie Madilldd43e6c2017-03-24 14:18:49 -04002835 mGLState.syncDirtyObjects(this, objectMask);
Jamie Madill1b94d432015-08-07 13:23:23 -04002836}
Jamie Madillc29968b2016-01-20 11:17:23 -05002837
2838void Context::blitFramebuffer(GLint srcX0,
2839 GLint srcY0,
2840 GLint srcX1,
2841 GLint srcY1,
2842 GLint dstX0,
2843 GLint dstY0,
2844 GLint dstX1,
2845 GLint dstY1,
2846 GLbitfield mask,
2847 GLenum filter)
2848{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002849 Framebuffer *drawFramebuffer = mGLState.getDrawFramebuffer();
Jamie Madillc29968b2016-01-20 11:17:23 -05002850 ASSERT(drawFramebuffer);
2851
2852 Rectangle srcArea(srcX0, srcY0, srcX1 - srcX0, srcY1 - srcY0);
2853 Rectangle dstArea(dstX0, dstY0, dstX1 - dstX0, dstY1 - dstY0);
2854
Jamie Madillad9f24e2016-02-12 09:27:24 -05002855 syncStateForBlit();
Jamie Madillc29968b2016-01-20 11:17:23 -05002856
Jamie Madillc564c072017-06-01 12:45:42 -04002857 handleError(drawFramebuffer->blit(this, srcArea, dstArea, mask, filter));
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002858}
Jamie Madillc29968b2016-01-20 11:17:23 -05002859
2860void Context::clear(GLbitfield mask)
2861{
Jamie Madillad9f24e2016-02-12 09:27:24 -05002862 syncStateForClear();
Jamie Madillc564c072017-06-01 12:45:42 -04002863 handleError(mGLState.getDrawFramebuffer()->clear(this, mask));
Jamie Madillc29968b2016-01-20 11:17:23 -05002864}
2865
2866void Context::clearBufferfv(GLenum buffer, GLint drawbuffer, const GLfloat *values)
2867{
Jamie Madillad9f24e2016-02-12 09:27:24 -05002868 syncStateForClear();
Jamie Madillc564c072017-06-01 12:45:42 -04002869 handleError(mGLState.getDrawFramebuffer()->clearBufferfv(this, buffer, drawbuffer, values));
Jamie Madillc29968b2016-01-20 11:17:23 -05002870}
2871
2872void Context::clearBufferuiv(GLenum buffer, GLint drawbuffer, const GLuint *values)
2873{
Jamie Madillad9f24e2016-02-12 09:27:24 -05002874 syncStateForClear();
Jamie Madillc564c072017-06-01 12:45:42 -04002875 handleError(mGLState.getDrawFramebuffer()->clearBufferuiv(this, buffer, drawbuffer, values));
Jamie Madillc29968b2016-01-20 11:17:23 -05002876}
2877
2878void Context::clearBufferiv(GLenum buffer, GLint drawbuffer, const GLint *values)
2879{
Jamie Madillad9f24e2016-02-12 09:27:24 -05002880 syncStateForClear();
Jamie Madillc564c072017-06-01 12:45:42 -04002881 handleError(mGLState.getDrawFramebuffer()->clearBufferiv(this, buffer, drawbuffer, values));
Jamie Madillc29968b2016-01-20 11:17:23 -05002882}
2883
2884void Context::clearBufferfi(GLenum buffer, GLint drawbuffer, GLfloat depth, GLint stencil)
2885{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002886 Framebuffer *framebufferObject = mGLState.getDrawFramebuffer();
Jamie Madillc29968b2016-01-20 11:17:23 -05002887 ASSERT(framebufferObject);
2888
2889 // If a buffer is not present, the clear has no effect
2890 if (framebufferObject->getDepthbuffer() == nullptr &&
2891 framebufferObject->getStencilbuffer() == nullptr)
2892 {
2893 return;
2894 }
2895
Jamie Madillad9f24e2016-02-12 09:27:24 -05002896 syncStateForClear();
Jamie Madillc564c072017-06-01 12:45:42 -04002897 handleError(framebufferObject->clearBufferfi(this, buffer, drawbuffer, depth, stencil));
Jamie Madillc29968b2016-01-20 11:17:23 -05002898}
2899
2900void Context::readPixels(GLint x,
2901 GLint y,
2902 GLsizei width,
2903 GLsizei height,
2904 GLenum format,
2905 GLenum type,
Jamie Madill876429b2017-04-20 15:46:24 -04002906 void *pixels)
Jamie Madillc29968b2016-01-20 11:17:23 -05002907{
Corentin Wallez9a8d3662016-09-22 12:18:29 -04002908 if (width == 0 || height == 0)
2909 {
2910 return;
2911 }
2912
Jamie Madillad9f24e2016-02-12 09:27:24 -05002913 syncStateForReadPixels();
Jamie Madillc29968b2016-01-20 11:17:23 -05002914
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002915 Framebuffer *framebufferObject = mGLState.getReadFramebuffer();
Jamie Madillc29968b2016-01-20 11:17:23 -05002916 ASSERT(framebufferObject);
2917
2918 Rectangle area(x, y, width, height);
Jamie Madillc564c072017-06-01 12:45:42 -04002919 handleError(framebufferObject->readPixels(this, area, format, type, pixels));
Jamie Madillc29968b2016-01-20 11:17:23 -05002920}
2921
2922void Context::copyTexImage2D(GLenum target,
2923 GLint level,
2924 GLenum internalformat,
2925 GLint x,
2926 GLint y,
2927 GLsizei width,
2928 GLsizei height,
2929 GLint border)
2930{
Jamie Madill60ec6ea2016-01-22 15:27:19 -05002931 // Only sync the read FBO
Jamie Madilldd43e6c2017-03-24 14:18:49 -04002932 mGLState.syncDirtyObject(this, GL_READ_FRAMEBUFFER);
Jamie Madill60ec6ea2016-01-22 15:27:19 -05002933
Jamie Madillc29968b2016-01-20 11:17:23 -05002934 Rectangle sourceArea(x, y, width, height);
2935
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002936 const Framebuffer *framebuffer = mGLState.getReadFramebuffer();
Jamie Madillc29968b2016-01-20 11:17:23 -05002937 Texture *texture =
2938 getTargetTexture(IsCubeMapTextureTarget(target) ? GL_TEXTURE_CUBE_MAP : target);
Jamie Madill8897afa2017-02-06 17:17:23 -05002939 handleError(texture->copyImage(this, target, level, sourceArea, internalformat, framebuffer));
Jamie Madillc29968b2016-01-20 11:17:23 -05002940}
2941
2942void Context::copyTexSubImage2D(GLenum target,
2943 GLint level,
2944 GLint xoffset,
2945 GLint yoffset,
2946 GLint x,
2947 GLint y,
2948 GLsizei width,
2949 GLsizei height)
2950{
Corentin Wallez9a8d3662016-09-22 12:18:29 -04002951 if (width == 0 || height == 0)
2952 {
2953 return;
2954 }
2955
Jamie Madill60ec6ea2016-01-22 15:27:19 -05002956 // Only sync the read FBO
Jamie Madilldd43e6c2017-03-24 14:18:49 -04002957 mGLState.syncDirtyObject(this, GL_READ_FRAMEBUFFER);
Jamie Madill60ec6ea2016-01-22 15:27:19 -05002958
Jamie Madillc29968b2016-01-20 11:17:23 -05002959 Offset destOffset(xoffset, yoffset, 0);
2960 Rectangle sourceArea(x, y, width, height);
2961
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002962 const Framebuffer *framebuffer = mGLState.getReadFramebuffer();
Jamie Madillc29968b2016-01-20 11:17:23 -05002963 Texture *texture =
2964 getTargetTexture(IsCubeMapTextureTarget(target) ? GL_TEXTURE_CUBE_MAP : target);
Jamie Madill8897afa2017-02-06 17:17:23 -05002965 handleError(texture->copySubImage(this, target, level, destOffset, sourceArea, framebuffer));
Jamie Madillc29968b2016-01-20 11:17:23 -05002966}
2967
2968void Context::copyTexSubImage3D(GLenum target,
2969 GLint level,
2970 GLint xoffset,
2971 GLint yoffset,
2972 GLint zoffset,
2973 GLint x,
2974 GLint y,
2975 GLsizei width,
2976 GLsizei height)
2977{
Corentin Wallez9a8d3662016-09-22 12:18:29 -04002978 if (width == 0 || height == 0)
2979 {
2980 return;
2981 }
2982
Jamie Madill60ec6ea2016-01-22 15:27:19 -05002983 // Only sync the read FBO
Jamie Madilldd43e6c2017-03-24 14:18:49 -04002984 mGLState.syncDirtyObject(this, GL_READ_FRAMEBUFFER);
Jamie Madill60ec6ea2016-01-22 15:27:19 -05002985
Jamie Madillc29968b2016-01-20 11:17:23 -05002986 Offset destOffset(xoffset, yoffset, zoffset);
2987 Rectangle sourceArea(x, y, width, height);
2988
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002989 const Framebuffer *framebuffer = mGLState.getReadFramebuffer();
Jamie Madillc29968b2016-01-20 11:17:23 -05002990 Texture *texture = getTargetTexture(target);
Jamie Madill8897afa2017-02-06 17:17:23 -05002991 handleError(texture->copySubImage(this, target, level, destOffset, sourceArea, framebuffer));
Jamie Madillc29968b2016-01-20 11:17:23 -05002992}
2993
2994void Context::framebufferTexture2D(GLenum target,
2995 GLenum attachment,
2996 GLenum textarget,
2997 GLuint texture,
2998 GLint level)
2999{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003000 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05003001 ASSERT(framebuffer);
3002
3003 if (texture != 0)
3004 {
3005 Texture *textureObj = getTexture(texture);
3006
3007 ImageIndex index = ImageIndex::MakeInvalid();
3008
3009 if (textarget == GL_TEXTURE_2D)
3010 {
3011 index = ImageIndex::Make2D(level);
3012 }
JiangYizhoubddc46b2016-12-09 09:50:51 +08003013 else if (textarget == GL_TEXTURE_2D_MULTISAMPLE)
3014 {
3015 ASSERT(level == 0);
3016 index = ImageIndex::Make2DMultisample();
3017 }
Jamie Madillc29968b2016-01-20 11:17:23 -05003018 else
3019 {
3020 ASSERT(IsCubeMapTextureTarget(textarget));
3021 index = ImageIndex::MakeCube(textarget, level);
3022 }
3023
Jamie Madilla02315b2017-02-23 14:14:47 -05003024 framebuffer->setAttachment(this, GL_TEXTURE, attachment, index, textureObj);
Jamie Madillc29968b2016-01-20 11:17:23 -05003025 }
3026 else
3027 {
Jamie Madilla02315b2017-02-23 14:14:47 -05003028 framebuffer->resetAttachment(this, attachment);
Jamie Madillc29968b2016-01-20 11:17:23 -05003029 }
Jamie Madill60ec6ea2016-01-22 15:27:19 -05003030
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003031 mGLState.setObjectDirty(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05003032}
3033
3034void Context::framebufferRenderbuffer(GLenum target,
3035 GLenum attachment,
3036 GLenum renderbuffertarget,
3037 GLuint renderbuffer)
3038{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003039 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05003040 ASSERT(framebuffer);
3041
3042 if (renderbuffer != 0)
3043 {
3044 Renderbuffer *renderbufferObject = getRenderbuffer(renderbuffer);
Jamie Madilla02315b2017-02-23 14:14:47 -05003045
3046 framebuffer->setAttachment(this, GL_RENDERBUFFER, attachment, gl::ImageIndex::MakeInvalid(),
Jamie Madillc29968b2016-01-20 11:17:23 -05003047 renderbufferObject);
3048 }
3049 else
3050 {
Jamie Madilla02315b2017-02-23 14:14:47 -05003051 framebuffer->resetAttachment(this, attachment);
Jamie Madillc29968b2016-01-20 11:17:23 -05003052 }
Jamie Madill60ec6ea2016-01-22 15:27:19 -05003053
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003054 mGLState.setObjectDirty(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05003055}
3056
3057void Context::framebufferTextureLayer(GLenum target,
3058 GLenum attachment,
3059 GLuint texture,
3060 GLint level,
3061 GLint layer)
3062{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003063 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05003064 ASSERT(framebuffer);
3065
3066 if (texture != 0)
3067 {
3068 Texture *textureObject = getTexture(texture);
3069
3070 ImageIndex index = ImageIndex::MakeInvalid();
3071
3072 if (textureObject->getTarget() == GL_TEXTURE_3D)
3073 {
3074 index = ImageIndex::Make3D(level, layer);
3075 }
3076 else
3077 {
3078 ASSERT(textureObject->getTarget() == GL_TEXTURE_2D_ARRAY);
3079 index = ImageIndex::Make2DArray(level, layer);
3080 }
3081
Jamie Madilla02315b2017-02-23 14:14:47 -05003082 framebuffer->setAttachment(this, GL_TEXTURE, attachment, index, textureObject);
Jamie Madillc29968b2016-01-20 11:17:23 -05003083 }
3084 else
3085 {
Jamie Madilla02315b2017-02-23 14:14:47 -05003086 framebuffer->resetAttachment(this, attachment);
Jamie Madillc29968b2016-01-20 11:17:23 -05003087 }
Jamie Madill60ec6ea2016-01-22 15:27:19 -05003088
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003089 mGLState.setObjectDirty(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05003090}
3091
3092void Context::drawBuffers(GLsizei n, const GLenum *bufs)
3093{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003094 Framebuffer *framebuffer = mGLState.getDrawFramebuffer();
Jamie Madillc29968b2016-01-20 11:17:23 -05003095 ASSERT(framebuffer);
3096 framebuffer->setDrawBuffers(n, bufs);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003097 mGLState.setObjectDirty(GL_DRAW_FRAMEBUFFER);
Jamie Madillc29968b2016-01-20 11:17:23 -05003098}
3099
3100void Context::readBuffer(GLenum mode)
3101{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003102 Framebuffer *readFBO = mGLState.getReadFramebuffer();
Jamie Madillc29968b2016-01-20 11:17:23 -05003103 readFBO->setReadBuffer(mode);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003104 mGLState.setObjectDirty(GL_READ_FRAMEBUFFER);
Jamie Madillc29968b2016-01-20 11:17:23 -05003105}
3106
3107void Context::discardFramebuffer(GLenum target, GLsizei numAttachments, const GLenum *attachments)
3108{
Jamie Madill60ec6ea2016-01-22 15:27:19 -05003109 // Only sync the FBO
Jamie Madilldd43e6c2017-03-24 14:18:49 -04003110 mGLState.syncDirtyObject(this, target);
Jamie Madill60ec6ea2016-01-22 15:27:19 -05003111
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003112 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05003113 ASSERT(framebuffer);
3114
3115 // The specification isn't clear what should be done when the framebuffer isn't complete.
3116 // We leave it up to the framebuffer implementation to decide what to do.
Jamie Madill4928b7c2017-06-20 12:57:39 -04003117 handleError(framebuffer->discard(this, numAttachments, attachments));
Jamie Madillc29968b2016-01-20 11:17:23 -05003118}
3119
3120void Context::invalidateFramebuffer(GLenum target,
3121 GLsizei numAttachments,
3122 const GLenum *attachments)
3123{
Jamie Madill60ec6ea2016-01-22 15:27:19 -05003124 // Only sync the FBO
Jamie Madilldd43e6c2017-03-24 14:18:49 -04003125 mGLState.syncDirtyObject(this, target);
Jamie Madill60ec6ea2016-01-22 15:27:19 -05003126
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003127 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05003128 ASSERT(framebuffer);
3129
Jamie Madilldd43e6c2017-03-24 14:18:49 -04003130 if (framebuffer->checkStatus(this) != GL_FRAMEBUFFER_COMPLETE)
Jamie Madillc29968b2016-01-20 11:17:23 -05003131 {
Jamie Madill437fa652016-05-03 15:13:24 -04003132 return;
Jamie Madillc29968b2016-01-20 11:17:23 -05003133 }
Jamie Madill437fa652016-05-03 15:13:24 -04003134
Jamie Madill4928b7c2017-06-20 12:57:39 -04003135 handleError(framebuffer->invalidate(this, numAttachments, attachments));
Jamie Madillc29968b2016-01-20 11:17:23 -05003136}
3137
3138void Context::invalidateSubFramebuffer(GLenum target,
3139 GLsizei numAttachments,
3140 const GLenum *attachments,
3141 GLint x,
3142 GLint y,
3143 GLsizei width,
3144 GLsizei height)
3145{
Jamie Madill60ec6ea2016-01-22 15:27:19 -05003146 // Only sync the FBO
Jamie Madilldd43e6c2017-03-24 14:18:49 -04003147 mGLState.syncDirtyObject(this, target);
Jamie Madill60ec6ea2016-01-22 15:27:19 -05003148
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003149 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05003150 ASSERT(framebuffer);
3151
Jamie Madilldd43e6c2017-03-24 14:18:49 -04003152 if (framebuffer->checkStatus(this) != GL_FRAMEBUFFER_COMPLETE)
Jamie Madillc29968b2016-01-20 11:17:23 -05003153 {
Jamie Madill437fa652016-05-03 15:13:24 -04003154 return;
Jamie Madillc29968b2016-01-20 11:17:23 -05003155 }
Jamie Madill437fa652016-05-03 15:13:24 -04003156
3157 Rectangle area(x, y, width, height);
Jamie Madill4928b7c2017-06-20 12:57:39 -04003158 handleError(framebuffer->invalidateSub(this, numAttachments, attachments, area));
Jamie Madillc29968b2016-01-20 11:17:23 -05003159}
3160
Jamie Madill73a84962016-02-12 09:27:23 -05003161void Context::texImage2D(GLenum target,
3162 GLint level,
3163 GLint internalformat,
3164 GLsizei width,
3165 GLsizei height,
3166 GLint border,
3167 GLenum format,
3168 GLenum type,
Jamie Madill876429b2017-04-20 15:46:24 -04003169 const void *pixels)
Jamie Madill73a84962016-02-12 09:27:23 -05003170{
Jamie Madillad9f24e2016-02-12 09:27:24 -05003171 syncStateForTexImage();
Jamie Madill73a84962016-02-12 09:27:23 -05003172
3173 Extents size(width, height, 1);
3174 Texture *texture =
3175 getTargetTexture(IsCubeMapTextureTarget(target) ? GL_TEXTURE_CUBE_MAP : target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003176 handleError(texture->setImage(this, mGLState.getUnpackState(), target, level, internalformat,
3177 size, format, type, reinterpret_cast<const uint8_t *>(pixels)));
Jamie Madill73a84962016-02-12 09:27:23 -05003178}
3179
3180void Context::texImage3D(GLenum target,
3181 GLint level,
3182 GLint internalformat,
3183 GLsizei width,
3184 GLsizei height,
3185 GLsizei depth,
3186 GLint border,
3187 GLenum format,
3188 GLenum type,
Jamie Madill876429b2017-04-20 15:46:24 -04003189 const void *pixels)
Jamie Madill73a84962016-02-12 09:27:23 -05003190{
Jamie Madillad9f24e2016-02-12 09:27:24 -05003191 syncStateForTexImage();
Jamie Madill73a84962016-02-12 09:27:23 -05003192
3193 Extents size(width, height, depth);
3194 Texture *texture = getTargetTexture(target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003195 handleError(texture->setImage(this, mGLState.getUnpackState(), target, level, internalformat,
3196 size, format, type, reinterpret_cast<const uint8_t *>(pixels)));
Jamie Madill73a84962016-02-12 09:27:23 -05003197}
3198
3199void Context::texSubImage2D(GLenum target,
3200 GLint level,
3201 GLint xoffset,
3202 GLint yoffset,
3203 GLsizei width,
3204 GLsizei height,
3205 GLenum format,
3206 GLenum type,
Jamie Madill876429b2017-04-20 15:46:24 -04003207 const void *pixels)
Jamie Madill73a84962016-02-12 09:27:23 -05003208{
3209 // Zero sized uploads are valid but no-ops
3210 if (width == 0 || height == 0)
3211 {
3212 return;
3213 }
3214
Jamie Madillad9f24e2016-02-12 09:27:24 -05003215 syncStateForTexImage();
Jamie Madill73a84962016-02-12 09:27:23 -05003216
3217 Box area(xoffset, yoffset, 0, width, height, 1);
3218 Texture *texture =
3219 getTargetTexture(IsCubeMapTextureTarget(target) ? GL_TEXTURE_CUBE_MAP : target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003220 handleError(texture->setSubImage(this, mGLState.getUnpackState(), target, level, area, format,
3221 type, reinterpret_cast<const uint8_t *>(pixels)));
Jamie Madill73a84962016-02-12 09:27:23 -05003222}
3223
3224void Context::texSubImage3D(GLenum target,
3225 GLint level,
3226 GLint xoffset,
3227 GLint yoffset,
3228 GLint zoffset,
3229 GLsizei width,
3230 GLsizei height,
3231 GLsizei depth,
3232 GLenum format,
3233 GLenum type,
Jamie Madill876429b2017-04-20 15:46:24 -04003234 const void *pixels)
Jamie Madill73a84962016-02-12 09:27:23 -05003235{
3236 // Zero sized uploads are valid but no-ops
3237 if (width == 0 || height == 0 || depth == 0)
3238 {
3239 return;
3240 }
3241
Jamie Madillad9f24e2016-02-12 09:27:24 -05003242 syncStateForTexImage();
Jamie Madill73a84962016-02-12 09:27:23 -05003243
3244 Box area(xoffset, yoffset, zoffset, width, height, depth);
3245 Texture *texture = getTargetTexture(target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003246 handleError(texture->setSubImage(this, mGLState.getUnpackState(), target, level, area, format,
3247 type, reinterpret_cast<const uint8_t *>(pixels)));
Jamie Madill73a84962016-02-12 09:27:23 -05003248}
3249
3250void Context::compressedTexImage2D(GLenum target,
3251 GLint level,
3252 GLenum internalformat,
3253 GLsizei width,
3254 GLsizei height,
3255 GLint border,
3256 GLsizei imageSize,
Jamie Madill876429b2017-04-20 15:46:24 -04003257 const void *data)
Jamie Madill73a84962016-02-12 09:27:23 -05003258{
Jamie Madillad9f24e2016-02-12 09:27:24 -05003259 syncStateForTexImage();
Jamie Madill73a84962016-02-12 09:27:23 -05003260
3261 Extents size(width, height, 1);
3262 Texture *texture =
3263 getTargetTexture(IsCubeMapTextureTarget(target) ? GL_TEXTURE_CUBE_MAP : target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003264 handleError(texture->setCompressedImage(this, mGLState.getUnpackState(), target, level,
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003265 internalformat, size, imageSize,
Jamie Madill437fa652016-05-03 15:13:24 -04003266 reinterpret_cast<const uint8_t *>(data)));
Jamie Madill73a84962016-02-12 09:27:23 -05003267}
3268
3269void Context::compressedTexImage3D(GLenum target,
3270 GLint level,
3271 GLenum internalformat,
3272 GLsizei width,
3273 GLsizei height,
3274 GLsizei depth,
3275 GLint border,
3276 GLsizei imageSize,
Jamie Madill876429b2017-04-20 15:46:24 -04003277 const void *data)
Jamie Madill73a84962016-02-12 09:27:23 -05003278{
Jamie Madillad9f24e2016-02-12 09:27:24 -05003279 syncStateForTexImage();
Jamie Madill73a84962016-02-12 09:27:23 -05003280
3281 Extents size(width, height, depth);
3282 Texture *texture = getTargetTexture(target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003283 handleError(texture->setCompressedImage(this, mGLState.getUnpackState(), target, level,
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003284 internalformat, size, imageSize,
Jamie Madill437fa652016-05-03 15:13:24 -04003285 reinterpret_cast<const uint8_t *>(data)));
Jamie Madill73a84962016-02-12 09:27:23 -05003286}
3287
3288void Context::compressedTexSubImage2D(GLenum target,
3289 GLint level,
3290 GLint xoffset,
3291 GLint yoffset,
3292 GLsizei width,
3293 GLsizei height,
3294 GLenum format,
3295 GLsizei imageSize,
Jamie Madill876429b2017-04-20 15:46:24 -04003296 const void *data)
Jamie Madill73a84962016-02-12 09:27:23 -05003297{
Jamie Madillad9f24e2016-02-12 09:27:24 -05003298 syncStateForTexImage();
Jamie Madill73a84962016-02-12 09:27:23 -05003299
3300 Box area(xoffset, yoffset, 0, width, height, 1);
3301 Texture *texture =
3302 getTargetTexture(IsCubeMapTextureTarget(target) ? GL_TEXTURE_CUBE_MAP : target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003303 handleError(texture->setCompressedSubImage(this, mGLState.getUnpackState(), target, level, area,
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003304 format, imageSize,
3305 reinterpret_cast<const uint8_t *>(data)));
Jamie Madill73a84962016-02-12 09:27:23 -05003306}
3307
3308void Context::compressedTexSubImage3D(GLenum target,
3309 GLint level,
3310 GLint xoffset,
3311 GLint yoffset,
3312 GLint zoffset,
3313 GLsizei width,
3314 GLsizei height,
3315 GLsizei depth,
3316 GLenum format,
3317 GLsizei imageSize,
Jamie Madill876429b2017-04-20 15:46:24 -04003318 const void *data)
Jamie Madill73a84962016-02-12 09:27:23 -05003319{
3320 // Zero sized uploads are valid but no-ops
3321 if (width == 0 || height == 0)
3322 {
3323 return;
3324 }
3325
Jamie Madillad9f24e2016-02-12 09:27:24 -05003326 syncStateForTexImage();
Jamie Madill73a84962016-02-12 09:27:23 -05003327
3328 Box area(xoffset, yoffset, zoffset, width, height, depth);
3329 Texture *texture = getTargetTexture(target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003330 handleError(texture->setCompressedSubImage(this, mGLState.getUnpackState(), target, level, area,
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003331 format, imageSize,
3332 reinterpret_cast<const uint8_t *>(data)));
Jamie Madill73a84962016-02-12 09:27:23 -05003333}
3334
Olli Etuaho0f2b1562016-05-13 16:15:35 +03003335void Context::generateMipmap(GLenum target)
3336{
3337 Texture *texture = getTargetTexture(target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003338 handleError(texture->generateMipmap(this));
Olli Etuaho0f2b1562016-05-13 16:15:35 +03003339}
3340
Geoff Lang97073d12016-04-20 10:42:34 -07003341void Context::copyTextureCHROMIUM(GLuint sourceId,
Geoff Langfc72a072017-03-24 14:52:39 -04003342 GLint sourceLevel,
3343 GLenum destTarget,
Geoff Lang97073d12016-04-20 10:42:34 -07003344 GLuint destId,
Geoff Langfc72a072017-03-24 14:52:39 -04003345 GLint destLevel,
Geoff Lang97073d12016-04-20 10:42:34 -07003346 GLint internalFormat,
3347 GLenum destType,
3348 GLboolean unpackFlipY,
3349 GLboolean unpackPremultiplyAlpha,
3350 GLboolean unpackUnmultiplyAlpha)
3351{
3352 syncStateForTexImage();
3353
3354 gl::Texture *sourceTexture = getTexture(sourceId);
3355 gl::Texture *destTexture = getTexture(destId);
Geoff Langfc72a072017-03-24 14:52:39 -04003356 handleError(destTexture->copyTexture(
3357 this, destTarget, destLevel, internalFormat, destType, sourceLevel, unpackFlipY == GL_TRUE,
3358 unpackPremultiplyAlpha == GL_TRUE, unpackUnmultiplyAlpha == GL_TRUE, sourceTexture));
Geoff Lang97073d12016-04-20 10:42:34 -07003359}
3360
3361void Context::copySubTextureCHROMIUM(GLuint sourceId,
Geoff Langfc72a072017-03-24 14:52:39 -04003362 GLint sourceLevel,
3363 GLenum destTarget,
Geoff Lang97073d12016-04-20 10:42:34 -07003364 GLuint destId,
Geoff Langfc72a072017-03-24 14:52:39 -04003365 GLint destLevel,
Geoff Lang97073d12016-04-20 10:42:34 -07003366 GLint xoffset,
3367 GLint yoffset,
3368 GLint x,
3369 GLint y,
3370 GLsizei width,
3371 GLsizei height,
3372 GLboolean unpackFlipY,
3373 GLboolean unpackPremultiplyAlpha,
3374 GLboolean unpackUnmultiplyAlpha)
3375{
3376 // Zero sized copies are valid but no-ops
3377 if (width == 0 || height == 0)
3378 {
3379 return;
3380 }
3381
3382 syncStateForTexImage();
3383
3384 gl::Texture *sourceTexture = getTexture(sourceId);
3385 gl::Texture *destTexture = getTexture(destId);
3386 Offset offset(xoffset, yoffset, 0);
3387 Rectangle area(x, y, width, height);
Geoff Langfc72a072017-03-24 14:52:39 -04003388 handleError(destTexture->copySubTexture(
3389 this, destTarget, destLevel, offset, sourceLevel, area, unpackFlipY == GL_TRUE,
3390 unpackPremultiplyAlpha == GL_TRUE, unpackUnmultiplyAlpha == GL_TRUE, sourceTexture));
Geoff Lang97073d12016-04-20 10:42:34 -07003391}
3392
Geoff Lang47110bf2016-04-20 11:13:22 -07003393void Context::compressedCopyTextureCHROMIUM(GLuint sourceId, GLuint destId)
3394{
3395 syncStateForTexImage();
3396
3397 gl::Texture *sourceTexture = getTexture(sourceId);
3398 gl::Texture *destTexture = getTexture(destId);
Jamie Madill8897afa2017-02-06 17:17:23 -05003399 handleError(destTexture->copyCompressedTexture(this, sourceTexture));
Geoff Lang47110bf2016-04-20 11:13:22 -07003400}
3401
Geoff Lang496c02d2016-10-20 11:38:11 -07003402void Context::getBufferPointerv(GLenum target, GLenum pname, void **params)
Olli Etuaho4f667482016-03-30 15:56:35 +03003403{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003404 Buffer *buffer = mGLState.getTargetBuffer(target);
Olli Etuaho4f667482016-03-30 15:56:35 +03003405 ASSERT(buffer);
3406
Geoff Lang496c02d2016-10-20 11:38:11 -07003407 QueryBufferPointerv(buffer, pname, params);
Olli Etuaho4f667482016-03-30 15:56:35 +03003408}
3409
Jamie Madill876429b2017-04-20 15:46:24 -04003410void *Context::mapBuffer(GLenum target, GLenum access)
Olli Etuaho4f667482016-03-30 15:56:35 +03003411{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003412 Buffer *buffer = mGLState.getTargetBuffer(target);
Olli Etuaho4f667482016-03-30 15:56:35 +03003413 ASSERT(buffer);
3414
Jamie Madill5f56ddb2017-01-13 17:29:55 -05003415 Error error = buffer->map(this, access);
Olli Etuaho4f667482016-03-30 15:56:35 +03003416 if (error.isError())
3417 {
Jamie Madill437fa652016-05-03 15:13:24 -04003418 handleError(error);
Olli Etuaho4f667482016-03-30 15:56:35 +03003419 return nullptr;
3420 }
3421
3422 return buffer->getMapPointer();
3423}
3424
3425GLboolean Context::unmapBuffer(GLenum target)
3426{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003427 Buffer *buffer = mGLState.getTargetBuffer(target);
Olli Etuaho4f667482016-03-30 15:56:35 +03003428 ASSERT(buffer);
3429
3430 GLboolean result;
Jamie Madill5f56ddb2017-01-13 17:29:55 -05003431 Error error = buffer->unmap(this, &result);
Olli Etuaho4f667482016-03-30 15:56:35 +03003432 if (error.isError())
3433 {
Jamie Madill437fa652016-05-03 15:13:24 -04003434 handleError(error);
Olli Etuaho4f667482016-03-30 15:56:35 +03003435 return GL_FALSE;
3436 }
3437
3438 return result;
3439}
3440
Jamie Madill876429b2017-04-20 15:46:24 -04003441void *Context::mapBufferRange(GLenum target, GLintptr offset, GLsizeiptr length, GLbitfield access)
Olli Etuaho4f667482016-03-30 15:56:35 +03003442{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003443 Buffer *buffer = mGLState.getTargetBuffer(target);
Olli Etuaho4f667482016-03-30 15:56:35 +03003444 ASSERT(buffer);
3445
Jamie Madill5f56ddb2017-01-13 17:29:55 -05003446 Error error = buffer->mapRange(this, offset, length, access);
Olli Etuaho4f667482016-03-30 15:56:35 +03003447 if (error.isError())
3448 {
Jamie Madill437fa652016-05-03 15:13:24 -04003449 handleError(error);
Olli Etuaho4f667482016-03-30 15:56:35 +03003450 return nullptr;
3451 }
3452
3453 return buffer->getMapPointer();
3454}
3455
3456void Context::flushMappedBufferRange(GLenum /*target*/, GLintptr /*offset*/, GLsizeiptr /*length*/)
3457{
3458 // We do not currently support a non-trivial implementation of FlushMappedBufferRange
3459}
3460
Jamie Madillad9f24e2016-02-12 09:27:24 -05003461void Context::syncStateForReadPixels()
3462{
3463 syncRendererState(mReadPixelsDirtyBits, mReadPixelsDirtyObjects);
3464}
3465
3466void Context::syncStateForTexImage()
3467{
3468 syncRendererState(mTexImageDirtyBits, mTexImageDirtyObjects);
3469}
3470
3471void Context::syncStateForClear()
3472{
3473 syncRendererState(mClearDirtyBits, mClearDirtyObjects);
3474}
3475
3476void Context::syncStateForBlit()
3477{
3478 syncRendererState(mBlitDirtyBits, mBlitDirtyObjects);
3479}
3480
Jamie Madillc20ab272016-06-09 07:20:46 -07003481void Context::activeTexture(GLenum texture)
3482{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003483 mGLState.setActiveSampler(texture - GL_TEXTURE0);
Jamie Madillc20ab272016-06-09 07:20:46 -07003484}
3485
Jamie Madill876429b2017-04-20 15:46:24 -04003486void Context::blendColor(GLfloat red, GLfloat green, GLfloat blue, GLfloat alpha)
Jamie Madillc20ab272016-06-09 07:20:46 -07003487{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003488 mGLState.setBlendColor(clamp01(red), clamp01(green), clamp01(blue), clamp01(alpha));
Jamie Madillc20ab272016-06-09 07:20:46 -07003489}
3490
Jamie Madill8a9e4bc2016-11-13 20:02:12 -05003491void Context::blendEquation(GLenum mode)
3492{
3493 mGLState.setBlendEquation(mode, mode);
3494}
3495
Jamie Madillc20ab272016-06-09 07:20:46 -07003496void Context::blendEquationSeparate(GLenum modeRGB, GLenum modeAlpha)
3497{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003498 mGLState.setBlendEquation(modeRGB, modeAlpha);
Jamie Madillc20ab272016-06-09 07:20:46 -07003499}
3500
Jamie Madill8a9e4bc2016-11-13 20:02:12 -05003501void Context::blendFunc(GLenum sfactor, GLenum dfactor)
3502{
3503 mGLState.setBlendFactors(sfactor, dfactor, sfactor, dfactor);
3504}
3505
Jamie Madillc20ab272016-06-09 07:20:46 -07003506void Context::blendFuncSeparate(GLenum srcRGB, GLenum dstRGB, GLenum srcAlpha, GLenum dstAlpha)
3507{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003508 mGLState.setBlendFactors(srcRGB, dstRGB, srcAlpha, dstAlpha);
Jamie Madillc20ab272016-06-09 07:20:46 -07003509}
3510
Jamie Madill876429b2017-04-20 15:46:24 -04003511void Context::clearColor(GLfloat red, GLfloat green, GLfloat blue, GLfloat alpha)
Jamie Madillc20ab272016-06-09 07:20:46 -07003512{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003513 mGLState.setColorClearValue(red, green, blue, alpha);
Jamie Madillc20ab272016-06-09 07:20:46 -07003514}
3515
Jamie Madill876429b2017-04-20 15:46:24 -04003516void Context::clearDepthf(GLfloat depth)
Jamie Madillc20ab272016-06-09 07:20:46 -07003517{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003518 mGLState.setDepthClearValue(depth);
Jamie Madillc20ab272016-06-09 07:20:46 -07003519}
3520
3521void Context::clearStencil(GLint s)
3522{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003523 mGLState.setStencilClearValue(s);
Jamie Madillc20ab272016-06-09 07:20:46 -07003524}
3525
3526void Context::colorMask(GLboolean red, GLboolean green, GLboolean blue, GLboolean alpha)
3527{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003528 mGLState.setColorMask(red == GL_TRUE, green == GL_TRUE, blue == GL_TRUE, alpha == GL_TRUE);
Jamie Madillc20ab272016-06-09 07:20:46 -07003529}
3530
3531void Context::cullFace(GLenum mode)
3532{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003533 mGLState.setCullMode(mode);
Jamie Madillc20ab272016-06-09 07:20:46 -07003534}
3535
3536void Context::depthFunc(GLenum func)
3537{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003538 mGLState.setDepthFunc(func);
Jamie Madillc20ab272016-06-09 07:20:46 -07003539}
3540
3541void Context::depthMask(GLboolean flag)
3542{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003543 mGLState.setDepthMask(flag != GL_FALSE);
Jamie Madillc20ab272016-06-09 07:20:46 -07003544}
3545
Jamie Madill876429b2017-04-20 15:46:24 -04003546void Context::depthRangef(GLfloat zNear, GLfloat zFar)
Jamie Madillc20ab272016-06-09 07:20:46 -07003547{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003548 mGLState.setDepthRange(zNear, zFar);
Jamie Madillc20ab272016-06-09 07:20:46 -07003549}
3550
3551void Context::disable(GLenum cap)
3552{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003553 mGLState.setEnableFeature(cap, false);
Jamie Madillc20ab272016-06-09 07:20:46 -07003554}
3555
3556void Context::disableVertexAttribArray(GLuint index)
3557{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003558 mGLState.setEnableVertexAttribArray(index, false);
Jamie Madillc20ab272016-06-09 07:20:46 -07003559}
3560
3561void Context::enable(GLenum cap)
3562{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003563 mGLState.setEnableFeature(cap, true);
Jamie Madillc20ab272016-06-09 07:20:46 -07003564}
3565
3566void Context::enableVertexAttribArray(GLuint index)
3567{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003568 mGLState.setEnableVertexAttribArray(index, true);
Jamie Madillc20ab272016-06-09 07:20:46 -07003569}
3570
3571void Context::frontFace(GLenum mode)
3572{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003573 mGLState.setFrontFace(mode);
Jamie Madillc20ab272016-06-09 07:20:46 -07003574}
3575
3576void Context::hint(GLenum target, GLenum mode)
3577{
3578 switch (target)
3579 {
3580 case GL_GENERATE_MIPMAP_HINT:
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003581 mGLState.setGenerateMipmapHint(mode);
Jamie Madillc20ab272016-06-09 07:20:46 -07003582 break;
3583
3584 case GL_FRAGMENT_SHADER_DERIVATIVE_HINT_OES:
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003585 mGLState.setFragmentShaderDerivativeHint(mode);
Jamie Madillc20ab272016-06-09 07:20:46 -07003586 break;
3587
3588 default:
3589 UNREACHABLE();
3590 return;
3591 }
3592}
3593
3594void Context::lineWidth(GLfloat width)
3595{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003596 mGLState.setLineWidth(width);
Jamie Madillc20ab272016-06-09 07:20:46 -07003597}
3598
3599void Context::pixelStorei(GLenum pname, GLint param)
3600{
3601 switch (pname)
3602 {
3603 case GL_UNPACK_ALIGNMENT:
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003604 mGLState.setUnpackAlignment(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003605 break;
3606
3607 case GL_PACK_ALIGNMENT:
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003608 mGLState.setPackAlignment(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003609 break;
3610
3611 case GL_PACK_REVERSE_ROW_ORDER_ANGLE:
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003612 mGLState.setPackReverseRowOrder(param != 0);
Jamie Madillc20ab272016-06-09 07:20:46 -07003613 break;
3614
3615 case GL_UNPACK_ROW_LENGTH:
Martin Radev1be913c2016-07-11 17:59:16 +03003616 ASSERT((getClientMajorVersion() >= 3) || getExtensions().unpackSubimage);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003617 mGLState.setUnpackRowLength(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003618 break;
3619
3620 case GL_UNPACK_IMAGE_HEIGHT:
Martin Radev1be913c2016-07-11 17:59:16 +03003621 ASSERT(getClientMajorVersion() >= 3);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003622 mGLState.setUnpackImageHeight(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003623 break;
3624
3625 case GL_UNPACK_SKIP_IMAGES:
Martin Radev1be913c2016-07-11 17:59:16 +03003626 ASSERT(getClientMajorVersion() >= 3);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003627 mGLState.setUnpackSkipImages(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003628 break;
3629
3630 case GL_UNPACK_SKIP_ROWS:
Martin Radev1be913c2016-07-11 17:59:16 +03003631 ASSERT((getClientMajorVersion() >= 3) || getExtensions().unpackSubimage);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003632 mGLState.setUnpackSkipRows(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003633 break;
3634
3635 case GL_UNPACK_SKIP_PIXELS:
Martin Radev1be913c2016-07-11 17:59:16 +03003636 ASSERT((getClientMajorVersion() >= 3) || getExtensions().unpackSubimage);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003637 mGLState.setUnpackSkipPixels(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003638 break;
3639
3640 case GL_PACK_ROW_LENGTH:
Martin Radev1be913c2016-07-11 17:59:16 +03003641 ASSERT((getClientMajorVersion() >= 3) || getExtensions().packSubimage);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003642 mGLState.setPackRowLength(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003643 break;
3644
3645 case GL_PACK_SKIP_ROWS:
Martin Radev1be913c2016-07-11 17:59:16 +03003646 ASSERT((getClientMajorVersion() >= 3) || getExtensions().packSubimage);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003647 mGLState.setPackSkipRows(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003648 break;
3649
3650 case GL_PACK_SKIP_PIXELS:
Martin Radev1be913c2016-07-11 17:59:16 +03003651 ASSERT((getClientMajorVersion() >= 3) || getExtensions().packSubimage);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003652 mGLState.setPackSkipPixels(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003653 break;
3654
3655 default:
3656 UNREACHABLE();
3657 return;
3658 }
3659}
3660
3661void Context::polygonOffset(GLfloat factor, GLfloat units)
3662{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003663 mGLState.setPolygonOffsetParams(factor, units);
Jamie Madillc20ab272016-06-09 07:20:46 -07003664}
3665
Jamie Madill876429b2017-04-20 15:46:24 -04003666void Context::sampleCoverage(GLfloat value, GLboolean invert)
Jamie Madillc20ab272016-06-09 07:20:46 -07003667{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003668 mGLState.setSampleCoverageParams(clamp01(value), invert == GL_TRUE);
Jamie Madillc20ab272016-06-09 07:20:46 -07003669}
3670
3671void Context::scissor(GLint x, GLint y, GLsizei width, GLsizei height)
3672{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003673 mGLState.setScissorParams(x, y, width, height);
Jamie Madillc20ab272016-06-09 07:20:46 -07003674}
3675
3676void Context::stencilFuncSeparate(GLenum face, GLenum func, GLint ref, GLuint mask)
3677{
3678 if (face == GL_FRONT || face == GL_FRONT_AND_BACK)
3679 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003680 mGLState.setStencilParams(func, ref, mask);
Jamie Madillc20ab272016-06-09 07:20:46 -07003681 }
3682
3683 if (face == GL_BACK || face == GL_FRONT_AND_BACK)
3684 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003685 mGLState.setStencilBackParams(func, ref, mask);
Jamie Madillc20ab272016-06-09 07:20:46 -07003686 }
3687}
3688
3689void Context::stencilMaskSeparate(GLenum face, GLuint mask)
3690{
3691 if (face == GL_FRONT || face == GL_FRONT_AND_BACK)
3692 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003693 mGLState.setStencilWritemask(mask);
Jamie Madillc20ab272016-06-09 07:20:46 -07003694 }
3695
3696 if (face == GL_BACK || face == GL_FRONT_AND_BACK)
3697 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003698 mGLState.setStencilBackWritemask(mask);
Jamie Madillc20ab272016-06-09 07:20:46 -07003699 }
3700}
3701
3702void Context::stencilOpSeparate(GLenum face, GLenum fail, GLenum zfail, GLenum zpass)
3703{
3704 if (face == GL_FRONT || face == GL_FRONT_AND_BACK)
3705 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003706 mGLState.setStencilOperations(fail, zfail, zpass);
Jamie Madillc20ab272016-06-09 07:20:46 -07003707 }
3708
3709 if (face == GL_BACK || face == GL_FRONT_AND_BACK)
3710 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003711 mGLState.setStencilBackOperations(fail, zfail, zpass);
Jamie Madillc20ab272016-06-09 07:20:46 -07003712 }
3713}
3714
3715void Context::vertexAttrib1f(GLuint index, GLfloat x)
3716{
3717 GLfloat vals[4] = {x, 0, 0, 1};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003718 mGLState.setVertexAttribf(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003719}
3720
3721void Context::vertexAttrib1fv(GLuint index, const GLfloat *values)
3722{
3723 GLfloat vals[4] = {values[0], 0, 0, 1};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003724 mGLState.setVertexAttribf(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003725}
3726
3727void Context::vertexAttrib2f(GLuint index, GLfloat x, GLfloat y)
3728{
3729 GLfloat vals[4] = {x, y, 0, 1};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003730 mGLState.setVertexAttribf(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003731}
3732
3733void Context::vertexAttrib2fv(GLuint index, const GLfloat *values)
3734{
3735 GLfloat vals[4] = {values[0], values[1], 0, 1};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003736 mGLState.setVertexAttribf(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003737}
3738
3739void Context::vertexAttrib3f(GLuint index, GLfloat x, GLfloat y, GLfloat z)
3740{
3741 GLfloat vals[4] = {x, y, z, 1};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003742 mGLState.setVertexAttribf(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003743}
3744
3745void Context::vertexAttrib3fv(GLuint index, const GLfloat *values)
3746{
3747 GLfloat vals[4] = {values[0], values[1], values[2], 1};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003748 mGLState.setVertexAttribf(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003749}
3750
3751void Context::vertexAttrib4f(GLuint index, GLfloat x, GLfloat y, GLfloat z, GLfloat w)
3752{
3753 GLfloat vals[4] = {x, y, z, w};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003754 mGLState.setVertexAttribf(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003755}
3756
3757void Context::vertexAttrib4fv(GLuint index, const GLfloat *values)
3758{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003759 mGLState.setVertexAttribf(index, values);
Jamie Madillc20ab272016-06-09 07:20:46 -07003760}
3761
3762void Context::vertexAttribPointer(GLuint index,
3763 GLint size,
3764 GLenum type,
3765 GLboolean normalized,
3766 GLsizei stride,
Jamie Madill876429b2017-04-20 15:46:24 -04003767 const void *ptr)
Jamie Madillc20ab272016-06-09 07:20:46 -07003768{
Jamie Madill4928b7c2017-06-20 12:57:39 -04003769 mGLState.setVertexAttribState(this, index, mGLState.getTargetBuffer(GL_ARRAY_BUFFER), size,
3770 type, normalized == GL_TRUE, false, stride, ptr);
Jamie Madillc20ab272016-06-09 07:20:46 -07003771}
3772
Shao80957d92017-02-20 21:25:59 +08003773void Context::vertexAttribFormat(GLuint attribIndex,
3774 GLint size,
3775 GLenum type,
3776 GLboolean normalized,
3777 GLuint relativeOffset)
3778{
3779 mGLState.setVertexAttribFormat(attribIndex, size, type, normalized == GL_TRUE, false,
3780 relativeOffset);
3781}
3782
3783void Context::vertexAttribIFormat(GLuint attribIndex,
3784 GLint size,
3785 GLenum type,
3786 GLuint relativeOffset)
3787{
3788 mGLState.setVertexAttribFormat(attribIndex, size, type, false, true, relativeOffset);
3789}
3790
3791void Context::vertexAttribBinding(GLuint attribIndex, GLuint bindingIndex)
3792{
3793 mGLState.setVertexAttribBinding(attribIndex, bindingIndex);
3794}
3795
3796void Context::setVertexBindingDivisor(GLuint bindingIndex, GLuint divisor)
3797{
3798 mGLState.setVertexBindingDivisor(bindingIndex, divisor);
3799}
3800
Jamie Madillc20ab272016-06-09 07:20:46 -07003801void Context::viewport(GLint x, GLint y, GLsizei width, GLsizei height)
3802{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003803 mGLState.setViewportParams(x, y, width, height);
Jamie Madillc20ab272016-06-09 07:20:46 -07003804}
3805
3806void Context::vertexAttribIPointer(GLuint index,
3807 GLint size,
3808 GLenum type,
3809 GLsizei stride,
Jamie Madill876429b2017-04-20 15:46:24 -04003810 const void *pointer)
Jamie Madillc20ab272016-06-09 07:20:46 -07003811{
Jamie Madill4928b7c2017-06-20 12:57:39 -04003812 mGLState.setVertexAttribState(this, index, mGLState.getTargetBuffer(GL_ARRAY_BUFFER), size,
3813 type, false, true, stride, pointer);
Jamie Madillc20ab272016-06-09 07:20:46 -07003814}
3815
3816void Context::vertexAttribI4i(GLuint index, GLint x, GLint y, GLint z, GLint w)
3817{
3818 GLint vals[4] = {x, y, z, w};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003819 mGLState.setVertexAttribi(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003820}
3821
3822void Context::vertexAttribI4ui(GLuint index, GLuint x, GLuint y, GLuint z, GLuint w)
3823{
3824 GLuint vals[4] = {x, y, z, w};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003825 mGLState.setVertexAttribu(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003826}
3827
3828void Context::vertexAttribI4iv(GLuint index, const GLint *v)
3829{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003830 mGLState.setVertexAttribi(index, v);
Jamie Madillc20ab272016-06-09 07:20:46 -07003831}
3832
3833void Context::vertexAttribI4uiv(GLuint index, const GLuint *v)
3834{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003835 mGLState.setVertexAttribu(index, v);
Jamie Madillc20ab272016-06-09 07:20:46 -07003836}
3837
Jiawei-Shao2597fb62016-12-09 16:38:02 +08003838void Context::getVertexAttribiv(GLuint index, GLenum pname, GLint *params)
3839{
3840 const VertexAttribCurrentValueData &currentValues =
3841 getGLState().getVertexAttribCurrentValue(index);
3842 const VertexArray *vao = getGLState().getVertexArray();
3843 QueryVertexAttribiv(vao->getVertexAttribute(index), vao->getBindingFromAttribIndex(index),
3844 currentValues, pname, params);
3845}
3846
3847void Context::getVertexAttribfv(GLuint index, GLenum pname, GLfloat *params)
3848{
3849 const VertexAttribCurrentValueData &currentValues =
3850 getGLState().getVertexAttribCurrentValue(index);
3851 const VertexArray *vao = getGLState().getVertexArray();
3852 QueryVertexAttribfv(vao->getVertexAttribute(index), vao->getBindingFromAttribIndex(index),
3853 currentValues, pname, params);
3854}
3855
3856void Context::getVertexAttribIiv(GLuint index, GLenum pname, GLint *params)
3857{
3858 const VertexAttribCurrentValueData &currentValues =
3859 getGLState().getVertexAttribCurrentValue(index);
3860 const VertexArray *vao = getGLState().getVertexArray();
3861 QueryVertexAttribIiv(vao->getVertexAttribute(index), vao->getBindingFromAttribIndex(index),
3862 currentValues, pname, params);
3863}
3864
3865void Context::getVertexAttribIuiv(GLuint index, GLenum pname, GLuint *params)
3866{
3867 const VertexAttribCurrentValueData &currentValues =
3868 getGLState().getVertexAttribCurrentValue(index);
3869 const VertexArray *vao = getGLState().getVertexArray();
3870 QueryVertexAttribIuiv(vao->getVertexAttribute(index), vao->getBindingFromAttribIndex(index),
3871 currentValues, pname, params);
3872}
3873
Jamie Madill876429b2017-04-20 15:46:24 -04003874void Context::getVertexAttribPointerv(GLuint index, GLenum pname, void **pointer)
Jiawei-Shao2597fb62016-12-09 16:38:02 +08003875{
3876 const VertexAttribute &attrib = getGLState().getVertexArray()->getVertexAttribute(index);
3877 QueryVertexAttribPointerv(attrib, pname, pointer);
3878}
3879
Jamie Madillc20ab272016-06-09 07:20:46 -07003880void Context::debugMessageControl(GLenum source,
3881 GLenum type,
3882 GLenum severity,
3883 GLsizei count,
3884 const GLuint *ids,
3885 GLboolean enabled)
3886{
3887 std::vector<GLuint> idVector(ids, ids + count);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003888 mGLState.getDebug().setMessageControl(source, type, severity, std::move(idVector),
3889 (enabled != GL_FALSE));
Jamie Madillc20ab272016-06-09 07:20:46 -07003890}
3891
3892void Context::debugMessageInsert(GLenum source,
3893 GLenum type,
3894 GLuint id,
3895 GLenum severity,
3896 GLsizei length,
3897 const GLchar *buf)
3898{
3899 std::string msg(buf, (length > 0) ? static_cast<size_t>(length) : strlen(buf));
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003900 mGLState.getDebug().insertMessage(source, type, id, severity, std::move(msg));
Jamie Madillc20ab272016-06-09 07:20:46 -07003901}
3902
3903void Context::debugMessageCallback(GLDEBUGPROCKHR callback, const void *userParam)
3904{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003905 mGLState.getDebug().setCallback(callback, userParam);
Jamie Madillc20ab272016-06-09 07:20:46 -07003906}
3907
3908GLuint Context::getDebugMessageLog(GLuint count,
3909 GLsizei bufSize,
3910 GLenum *sources,
3911 GLenum *types,
3912 GLuint *ids,
3913 GLenum *severities,
3914 GLsizei *lengths,
3915 GLchar *messageLog)
3916{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003917 return static_cast<GLuint>(mGLState.getDebug().getMessages(count, bufSize, sources, types, ids,
3918 severities, lengths, messageLog));
Jamie Madillc20ab272016-06-09 07:20:46 -07003919}
3920
3921void Context::pushDebugGroup(GLenum source, GLuint id, GLsizei length, const GLchar *message)
3922{
3923 std::string msg(message, (length > 0) ? static_cast<size_t>(length) : strlen(message));
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003924 mGLState.getDebug().pushGroup(source, id, std::move(msg));
Jamie Madillc20ab272016-06-09 07:20:46 -07003925}
3926
3927void Context::popDebugGroup()
3928{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003929 mGLState.getDebug().popGroup();
Jamie Madillc20ab272016-06-09 07:20:46 -07003930}
3931
Jamie Madill876429b2017-04-20 15:46:24 -04003932void Context::bufferData(GLenum target, GLsizeiptr size, const void *data, GLenum usage)
Jamie Madill29639852016-09-02 15:00:09 -04003933{
3934 Buffer *buffer = mGLState.getTargetBuffer(target);
3935 ASSERT(buffer);
Jamie Madillb8353b02017-01-25 12:57:21 -08003936 handleError(buffer->bufferData(this, target, data, size, usage));
Jamie Madill29639852016-09-02 15:00:09 -04003937}
3938
Jamie Madill876429b2017-04-20 15:46:24 -04003939void Context::bufferSubData(GLenum target, GLintptr offset, GLsizeiptr size, const void *data)
Jamie Madill29639852016-09-02 15:00:09 -04003940{
3941 if (data == nullptr)
3942 {
3943 return;
3944 }
3945
3946 Buffer *buffer = mGLState.getTargetBuffer(target);
3947 ASSERT(buffer);
Jamie Madillb8353b02017-01-25 12:57:21 -08003948 handleError(buffer->bufferSubData(this, target, data, size, offset));
Jamie Madill29639852016-09-02 15:00:09 -04003949}
3950
Jamie Madillef300b12016-10-07 15:12:09 -04003951void Context::attachShader(GLuint program, GLuint shader)
3952{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05003953 auto programObject = mState.mShaderPrograms->getProgram(program);
3954 auto shaderObject = mState.mShaderPrograms->getShader(shader);
Jamie Madillef300b12016-10-07 15:12:09 -04003955 ASSERT(programObject && shaderObject);
3956 programObject->attachShader(shaderObject);
3957}
3958
Kenneth Russellf2f6f652016-10-05 19:53:23 -07003959const Workarounds &Context::getWorkarounds() const
3960{
3961 return mWorkarounds;
3962}
3963
Jamie Madillb0817d12016-11-01 15:48:31 -04003964void Context::copyBufferSubData(GLenum readTarget,
3965 GLenum writeTarget,
3966 GLintptr readOffset,
3967 GLintptr writeOffset,
3968 GLsizeiptr size)
3969{
3970 // if size is zero, the copy is a successful no-op
3971 if (size == 0)
3972 {
3973 return;
3974 }
3975
3976 // TODO(jmadill): cache these.
3977 Buffer *readBuffer = mGLState.getTargetBuffer(readTarget);
3978 Buffer *writeBuffer = mGLState.getTargetBuffer(writeTarget);
3979
Jamie Madill5f56ddb2017-01-13 17:29:55 -05003980 handleError(writeBuffer->copyBufferSubData(this, readBuffer, readOffset, writeOffset, size));
Jamie Madillb0817d12016-11-01 15:48:31 -04003981}
3982
Jamie Madill01a80ee2016-11-07 12:06:18 -05003983void Context::bindAttribLocation(GLuint program, GLuint index, const GLchar *name)
3984{
3985 Program *programObject = getProgram(program);
3986 // TODO(jmadill): Re-use this from the validation if possible.
3987 ASSERT(programObject);
3988 programObject->bindAttributeLocation(index, name);
3989}
3990
3991void Context::bindBuffer(GLenum target, GLuint buffer)
3992{
3993 switch (target)
3994 {
3995 case GL_ARRAY_BUFFER:
3996 bindArrayBuffer(buffer);
3997 break;
3998 case GL_ELEMENT_ARRAY_BUFFER:
3999 bindElementArrayBuffer(buffer);
4000 break;
4001 case GL_COPY_READ_BUFFER:
4002 bindCopyReadBuffer(buffer);
4003 break;
4004 case GL_COPY_WRITE_BUFFER:
4005 bindCopyWriteBuffer(buffer);
4006 break;
4007 case GL_PIXEL_PACK_BUFFER:
4008 bindPixelPackBuffer(buffer);
4009 break;
4010 case GL_PIXEL_UNPACK_BUFFER:
4011 bindPixelUnpackBuffer(buffer);
4012 break;
4013 case GL_UNIFORM_BUFFER:
4014 bindGenericUniformBuffer(buffer);
4015 break;
4016 case GL_TRANSFORM_FEEDBACK_BUFFER:
4017 bindGenericTransformFeedbackBuffer(buffer);
4018 break;
Geoff Lang3b573612016-10-31 14:08:10 -04004019 case GL_ATOMIC_COUNTER_BUFFER:
Jiajia Qin6eafb042016-12-27 17:04:07 +08004020 bindGenericAtomicCounterBuffer(buffer);
Geoff Lang3b573612016-10-31 14:08:10 -04004021 break;
4022 case GL_SHADER_STORAGE_BUFFER:
Jiajia Qinf546e7d2017-03-27 14:12:59 +08004023 bindGenericShaderStorageBuffer(buffer);
Geoff Lang3b573612016-10-31 14:08:10 -04004024 break;
4025 case GL_DRAW_INDIRECT_BUFFER:
Jiajia Qin9d7d0b12016-11-29 16:30:31 +08004026 bindDrawIndirectBuffer(buffer);
Geoff Lang3b573612016-10-31 14:08:10 -04004027 break;
4028 case GL_DISPATCH_INDIRECT_BUFFER:
Geoff Lang9f090372016-12-02 10:20:43 -05004029 if (buffer != 0)
4030 {
4031 // Binding buffers to this binding point is not implemented yet.
4032 UNIMPLEMENTED();
4033 }
Geoff Lang3b573612016-10-31 14:08:10 -04004034 break;
Jamie Madill01a80ee2016-11-07 12:06:18 -05004035
4036 default:
4037 UNREACHABLE();
4038 break;
4039 }
4040}
4041
Jiajia Qin6eafb042016-12-27 17:04:07 +08004042void Context::bindBufferBase(GLenum target, GLuint index, GLuint buffer)
4043{
4044 bindBufferRange(target, index, buffer, 0, 0);
4045}
4046
4047void Context::bindBufferRange(GLenum target,
4048 GLuint index,
4049 GLuint buffer,
4050 GLintptr offset,
4051 GLsizeiptr size)
4052{
4053 switch (target)
4054 {
4055 case GL_TRANSFORM_FEEDBACK_BUFFER:
4056 bindIndexedTransformFeedbackBuffer(buffer, index, offset, size);
4057 bindGenericTransformFeedbackBuffer(buffer);
4058 break;
4059 case GL_UNIFORM_BUFFER:
4060 bindIndexedUniformBuffer(buffer, index, offset, size);
4061 bindGenericUniformBuffer(buffer);
4062 break;
4063 case GL_ATOMIC_COUNTER_BUFFER:
4064 bindIndexedAtomicCounterBuffer(buffer, index, offset, size);
4065 bindGenericAtomicCounterBuffer(buffer);
4066 break;
4067 case GL_SHADER_STORAGE_BUFFER:
Jiajia Qinf546e7d2017-03-27 14:12:59 +08004068 bindIndexedShaderStorageBuffer(buffer, index, offset, size);
4069 bindGenericShaderStorageBuffer(buffer);
Jiajia Qin6eafb042016-12-27 17:04:07 +08004070 break;
4071 default:
4072 UNREACHABLE();
4073 break;
4074 }
4075}
4076
Jamie Madill01a80ee2016-11-07 12:06:18 -05004077void Context::bindFramebuffer(GLenum target, GLuint framebuffer)
4078{
4079 if (target == GL_READ_FRAMEBUFFER || target == GL_FRAMEBUFFER)
4080 {
4081 bindReadFramebuffer(framebuffer);
4082 }
4083
4084 if (target == GL_DRAW_FRAMEBUFFER || target == GL_FRAMEBUFFER)
4085 {
4086 bindDrawFramebuffer(framebuffer);
4087 }
4088}
4089
4090void Context::bindRenderbuffer(GLenum target, GLuint renderbuffer)
4091{
4092 ASSERT(target == GL_RENDERBUFFER);
4093 Renderbuffer *object =
Geoff Lang4ddf5af2016-12-01 14:30:44 -05004094 mState.mRenderbuffers->checkRenderbufferAllocation(mImplementation.get(), renderbuffer);
Jamie Madill4928b7c2017-06-20 12:57:39 -04004095 mGLState.setRenderbufferBinding(this, object);
Jamie Madill01a80ee2016-11-07 12:06:18 -05004096}
4097
JiangYizhoubddc46b2016-12-09 09:50:51 +08004098void Context::texStorage2DMultisample(GLenum target,
4099 GLsizei samples,
4100 GLenum internalformat,
4101 GLsizei width,
4102 GLsizei height,
4103 GLboolean fixedsamplelocations)
4104{
4105 Extents size(width, height, 1);
4106 Texture *texture = getTargetTexture(target);
Jamie Madill8897afa2017-02-06 17:17:23 -05004107 handleError(texture->setStorageMultisample(this, target, samples, internalformat, size,
JiangYizhoubddc46b2016-12-09 09:50:51 +08004108 fixedsamplelocations));
4109}
4110
4111void Context::getMultisamplefv(GLenum pname, GLuint index, GLfloat *val)
4112{
Jamie Madilldd43e6c2017-03-24 14:18:49 -04004113 mGLState.syncDirtyObject(this, GL_READ_FRAMEBUFFER);
JiangYizhoubddc46b2016-12-09 09:50:51 +08004114 const Framebuffer *framebuffer = mGLState.getReadFramebuffer();
4115
4116 switch (pname)
4117 {
4118 case GL_SAMPLE_POSITION:
4119 handleError(framebuffer->getSamplePosition(index, val));
4120 break;
4121 default:
4122 UNREACHABLE();
4123 }
4124}
4125
Jamie Madille8fb6402017-02-14 17:56:40 -05004126void Context::renderbufferStorage(GLenum target,
4127 GLenum internalformat,
4128 GLsizei width,
4129 GLsizei height)
4130{
Jamie Madill4e0e6f82017-02-17 11:06:03 -05004131 // Hack for the special WebGL 1 "DEPTH_STENCIL" internal format.
4132 GLenum convertedInternalFormat = getConvertedRenderbufferFormat(internalformat);
4133
Jamie Madille8fb6402017-02-14 17:56:40 -05004134 Renderbuffer *renderbuffer = mGLState.getCurrentRenderbuffer();
Jamie Madill4928b7c2017-06-20 12:57:39 -04004135 handleError(renderbuffer->setStorage(this, convertedInternalFormat, width, height));
Jamie Madille8fb6402017-02-14 17:56:40 -05004136}
4137
4138void Context::renderbufferStorageMultisample(GLenum target,
4139 GLsizei samples,
4140 GLenum internalformat,
4141 GLsizei width,
4142 GLsizei height)
4143{
Jamie Madill4e0e6f82017-02-17 11:06:03 -05004144 // Hack for the special WebGL 1 "DEPTH_STENCIL" internal format.
4145 GLenum convertedInternalFormat = getConvertedRenderbufferFormat(internalformat);
Jamie Madille8fb6402017-02-14 17:56:40 -05004146
4147 Renderbuffer *renderbuffer = mGLState.getCurrentRenderbuffer();
Jamie Madill4e0e6f82017-02-17 11:06:03 -05004148 handleError(
Jamie Madill4928b7c2017-06-20 12:57:39 -04004149 renderbuffer->setStorageMultisample(this, samples, convertedInternalFormat, width, height));
Jamie Madille8fb6402017-02-14 17:56:40 -05004150}
4151
Geoff Lang38f2cfb2017-04-11 15:23:08 -04004152void Context::getSynciv(GLsync sync, GLenum pname, GLsizei bufSize, GLsizei *length, GLint *values)
4153{
4154 const FenceSync *syncObject = getFenceSync(sync);
Geoff Lang82483b92017-04-11 15:33:00 -04004155 handleError(QuerySynciv(syncObject, pname, bufSize, length, values));
Geoff Lang38f2cfb2017-04-11 15:23:08 -04004156}
4157
JiangYizhoue18e6392017-02-20 10:32:23 +08004158void Context::getFramebufferParameteriv(GLenum target, GLenum pname, GLint *params)
4159{
4160 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
4161 QueryFramebufferParameteriv(framebuffer, pname, params);
4162}
4163
4164void Context::setFramebufferParameteri(GLenum target, GLenum pname, GLint param)
4165{
4166 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
4167 SetFramebufferParameteri(framebuffer, pname, param);
4168}
4169
Jamie Madille14951e2017-03-09 18:55:16 -05004170Error Context::getScratchBuffer(size_t requestedSize, angle::MemoryBuffer **scratchBufferOut) const
4171{
4172 if (!mScratchBuffer.get(requestedSize, scratchBufferOut))
4173 {
Yuly Novikovc4d18aa2017-03-09 18:45:02 -05004174 return OutOfMemory() << "Failed to allocate internal buffer.";
Jamie Madille14951e2017-03-09 18:55:16 -05004175 }
Yuly Novikovc4d18aa2017-03-09 18:45:02 -05004176 return NoError();
Jamie Madille14951e2017-03-09 18:55:16 -05004177}
4178
Xinghua Cao2b396592017-03-29 15:36:04 +08004179void Context::dispatchCompute(GLuint numGroupsX, GLuint numGroupsY, GLuint numGroupsZ)
4180{
4181 if (numGroupsX == 0u || numGroupsY == 0u || numGroupsZ == 0u)
4182 {
4183 return;
4184 }
4185
Jamie Madillfe548342017-06-19 11:13:24 -04004186 mImplementation->dispatchCompute(this, numGroupsX, numGroupsY, numGroupsZ);
Xinghua Cao2b396592017-03-29 15:36:04 +08004187}
4188
JiangYizhou165361c2017-06-07 14:56:57 +08004189void Context::texStorage2D(GLenum target,
4190 GLsizei levels,
4191 GLenum internalFormat,
4192 GLsizei width,
4193 GLsizei height)
4194{
4195 Extents size(width, height, 1);
4196 Texture *texture = getTargetTexture(target);
4197 handleError(texture->setStorage(this, target, levels, internalFormat, size));
4198}
4199
4200void Context::texStorage3D(GLenum target,
4201 GLsizei levels,
4202 GLenum internalFormat,
4203 GLsizei width,
4204 GLsizei height,
4205 GLsizei depth)
4206{
4207 Extents size(width, height, depth);
4208 Texture *texture = getTargetTexture(target);
4209 handleError(texture->setStorage(this, target, levels, internalFormat, size));
4210}
4211
Jamie Madillc1d770e2017-04-13 17:31:24 -04004212GLenum Context::checkFramebufferStatus(GLenum target)
4213{
4214 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
4215 ASSERT(framebuffer);
4216
4217 return framebuffer->checkStatus(this);
4218}
4219
4220void Context::compileShader(GLuint shader)
4221{
4222 Shader *shaderObject = GetValidShader(this, shader);
4223 if (!shaderObject)
4224 {
4225 return;
4226 }
4227 shaderObject->compile(this);
4228}
4229
4230void Context::deleteBuffers(GLsizei n, const GLuint *buffers)
4231{
4232 for (int i = 0; i < n; i++)
4233 {
4234 deleteBuffer(buffers[i]);
4235 }
4236}
4237
4238void Context::deleteFramebuffers(GLsizei n, const GLuint *framebuffers)
4239{
4240 for (int i = 0; i < n; i++)
4241 {
4242 if (framebuffers[i] != 0)
4243 {
4244 deleteFramebuffer(framebuffers[i]);
4245 }
4246 }
4247}
4248
4249void Context::deleteRenderbuffers(GLsizei n, const GLuint *renderbuffers)
4250{
4251 for (int i = 0; i < n; i++)
4252 {
4253 deleteRenderbuffer(renderbuffers[i]);
4254 }
4255}
4256
4257void Context::deleteTextures(GLsizei n, const GLuint *textures)
4258{
4259 for (int i = 0; i < n; i++)
4260 {
4261 if (textures[i] != 0)
4262 {
4263 deleteTexture(textures[i]);
4264 }
4265 }
4266}
4267
4268void Context::detachShader(GLuint program, GLuint shader)
4269{
4270 Program *programObject = getProgram(program);
4271 ASSERT(programObject);
4272
4273 Shader *shaderObject = getShader(shader);
4274 ASSERT(shaderObject);
4275
4276 programObject->detachShader(this, shaderObject);
4277}
4278
4279void Context::genBuffers(GLsizei n, GLuint *buffers)
4280{
4281 for (int i = 0; i < n; i++)
4282 {
4283 buffers[i] = createBuffer();
4284 }
4285}
4286
4287void Context::genFramebuffers(GLsizei n, GLuint *framebuffers)
4288{
4289 for (int i = 0; i < n; i++)
4290 {
4291 framebuffers[i] = createFramebuffer();
4292 }
4293}
4294
4295void Context::genRenderbuffers(GLsizei n, GLuint *renderbuffers)
4296{
4297 for (int i = 0; i < n; i++)
4298 {
4299 renderbuffers[i] = createRenderbuffer();
4300 }
4301}
4302
4303void Context::genTextures(GLsizei n, GLuint *textures)
4304{
4305 for (int i = 0; i < n; i++)
4306 {
4307 textures[i] = createTexture();
4308 }
4309}
4310
4311void Context::getActiveAttrib(GLuint program,
4312 GLuint index,
4313 GLsizei bufsize,
4314 GLsizei *length,
4315 GLint *size,
4316 GLenum *type,
4317 GLchar *name)
4318{
4319 Program *programObject = getProgram(program);
4320 ASSERT(programObject);
4321 programObject->getActiveAttribute(index, bufsize, length, size, type, name);
4322}
4323
4324void Context::getActiveUniform(GLuint program,
4325 GLuint index,
4326 GLsizei bufsize,
4327 GLsizei *length,
4328 GLint *size,
4329 GLenum *type,
4330 GLchar *name)
4331{
4332 Program *programObject = getProgram(program);
4333 ASSERT(programObject);
4334 programObject->getActiveUniform(index, bufsize, length, size, type, name);
4335}
4336
4337void Context::getAttachedShaders(GLuint program, GLsizei maxcount, GLsizei *count, GLuint *shaders)
4338{
4339 Program *programObject = getProgram(program);
4340 ASSERT(programObject);
4341 programObject->getAttachedShaders(maxcount, count, shaders);
4342}
4343
4344GLint Context::getAttribLocation(GLuint program, const GLchar *name)
4345{
4346 Program *programObject = getProgram(program);
4347 ASSERT(programObject);
4348 return programObject->getAttributeLocation(name);
4349}
4350
4351void Context::getBooleanv(GLenum pname, GLboolean *params)
4352{
4353 GLenum nativeType;
4354 unsigned int numParams = 0;
4355 getQueryParameterInfo(pname, &nativeType, &numParams);
4356
4357 if (nativeType == GL_BOOL)
4358 {
4359 getBooleanvImpl(pname, params);
4360 }
4361 else
4362 {
4363 CastStateValues(this, nativeType, pname, numParams, params);
4364 }
4365}
4366
4367void Context::getFloatv(GLenum pname, GLfloat *params)
4368{
4369 GLenum nativeType;
4370 unsigned int numParams = 0;
4371 getQueryParameterInfo(pname, &nativeType, &numParams);
4372
4373 if (nativeType == GL_FLOAT)
4374 {
4375 getFloatvImpl(pname, params);
4376 }
4377 else
4378 {
4379 CastStateValues(this, nativeType, pname, numParams, params);
4380 }
4381}
4382
4383void Context::getIntegerv(GLenum pname, GLint *params)
4384{
4385 GLenum nativeType;
4386 unsigned int numParams = 0;
4387 getQueryParameterInfo(pname, &nativeType, &numParams);
4388
4389 if (nativeType == GL_INT)
4390 {
4391 getIntegervImpl(pname, params);
4392 }
4393 else
4394 {
4395 CastStateValues(this, nativeType, pname, numParams, params);
4396 }
4397}
4398
4399void Context::getProgramiv(GLuint program, GLenum pname, GLint *params)
4400{
4401 Program *programObject = getProgram(program);
4402 ASSERT(programObject);
Jamie Madillffe00c02017-06-27 16:26:55 -04004403 QueryProgramiv(this, programObject, pname, params);
Jamie Madillc1d770e2017-04-13 17:31:24 -04004404}
4405
Jamie Madillbe849e42017-05-02 15:49:00 -04004406void Context::getProgramInfoLog(GLuint program, GLsizei bufsize, GLsizei *length, GLchar *infolog)
Jamie Madillc1d770e2017-04-13 17:31:24 -04004407{
4408 Program *programObject = getProgram(program);
4409 ASSERT(programObject);
4410 programObject->getInfoLog(bufsize, length, infolog);
4411}
4412
4413void Context::getShaderiv(GLuint shader, GLenum pname, GLint *params)
4414{
4415 Shader *shaderObject = getShader(shader);
4416 ASSERT(shaderObject);
Jamie Madillbd044ed2017-06-05 12:59:21 -04004417 QueryShaderiv(this, shaderObject, pname, params);
Jamie Madillc1d770e2017-04-13 17:31:24 -04004418}
4419
4420void Context::getShaderInfoLog(GLuint shader, GLsizei bufsize, GLsizei *length, GLchar *infolog)
4421{
4422 Shader *shaderObject = getShader(shader);
4423 ASSERT(shaderObject);
Jamie Madillbd044ed2017-06-05 12:59:21 -04004424 shaderObject->getInfoLog(this, bufsize, length, infolog);
Jamie Madillc1d770e2017-04-13 17:31:24 -04004425}
4426
4427void Context::getShaderPrecisionFormat(GLenum shadertype,
4428 GLenum precisiontype,
4429 GLint *range,
4430 GLint *precision)
4431{
4432 // TODO(jmadill): Compute shaders.
4433
4434 switch (shadertype)
4435 {
4436 case GL_VERTEX_SHADER:
4437 switch (precisiontype)
4438 {
4439 case GL_LOW_FLOAT:
4440 mCaps.vertexLowpFloat.get(range, precision);
4441 break;
4442 case GL_MEDIUM_FLOAT:
4443 mCaps.vertexMediumpFloat.get(range, precision);
4444 break;
4445 case GL_HIGH_FLOAT:
4446 mCaps.vertexHighpFloat.get(range, precision);
4447 break;
4448
4449 case GL_LOW_INT:
4450 mCaps.vertexLowpInt.get(range, precision);
4451 break;
4452 case GL_MEDIUM_INT:
4453 mCaps.vertexMediumpInt.get(range, precision);
4454 break;
4455 case GL_HIGH_INT:
4456 mCaps.vertexHighpInt.get(range, precision);
4457 break;
4458
4459 default:
4460 UNREACHABLE();
4461 return;
4462 }
4463 break;
4464
4465 case GL_FRAGMENT_SHADER:
4466 switch (precisiontype)
4467 {
4468 case GL_LOW_FLOAT:
4469 mCaps.fragmentLowpFloat.get(range, precision);
4470 break;
4471 case GL_MEDIUM_FLOAT:
4472 mCaps.fragmentMediumpFloat.get(range, precision);
4473 break;
4474 case GL_HIGH_FLOAT:
4475 mCaps.fragmentHighpFloat.get(range, precision);
4476 break;
4477
4478 case GL_LOW_INT:
4479 mCaps.fragmentLowpInt.get(range, precision);
4480 break;
4481 case GL_MEDIUM_INT:
4482 mCaps.fragmentMediumpInt.get(range, precision);
4483 break;
4484 case GL_HIGH_INT:
4485 mCaps.fragmentHighpInt.get(range, precision);
4486 break;
4487
4488 default:
4489 UNREACHABLE();
4490 return;
4491 }
4492 break;
4493
4494 default:
4495 UNREACHABLE();
4496 return;
4497 }
4498}
4499
4500void Context::getShaderSource(GLuint shader, GLsizei bufsize, GLsizei *length, GLchar *source)
4501{
4502 Shader *shaderObject = getShader(shader);
4503 ASSERT(shaderObject);
4504 shaderObject->getSource(bufsize, length, source);
4505}
4506
4507void Context::getUniformfv(GLuint program, GLint location, GLfloat *params)
4508{
4509 Program *programObject = getProgram(program);
4510 ASSERT(programObject);
4511 programObject->getUniformfv(location, params);
4512}
4513
4514void Context::getUniformiv(GLuint program, GLint location, GLint *params)
4515{
4516 Program *programObject = getProgram(program);
4517 ASSERT(programObject);
4518 programObject->getUniformiv(location, params);
4519}
4520
4521GLint Context::getUniformLocation(GLuint program, const GLchar *name)
4522{
4523 Program *programObject = getProgram(program);
4524 ASSERT(programObject);
4525 return programObject->getUniformLocation(name);
4526}
4527
4528GLboolean Context::isBuffer(GLuint buffer)
4529{
4530 if (buffer == 0)
4531 {
4532 return GL_FALSE;
4533 }
4534
4535 return (getBuffer(buffer) ? GL_TRUE : GL_FALSE);
4536}
4537
4538GLboolean Context::isEnabled(GLenum cap)
4539{
4540 return mGLState.getEnableFeature(cap);
4541}
4542
4543GLboolean Context::isFramebuffer(GLuint framebuffer)
4544{
4545 if (framebuffer == 0)
4546 {
4547 return GL_FALSE;
4548 }
4549
4550 return (getFramebuffer(framebuffer) ? GL_TRUE : GL_FALSE);
4551}
4552
4553GLboolean Context::isProgram(GLuint program)
4554{
4555 if (program == 0)
4556 {
4557 return GL_FALSE;
4558 }
4559
4560 return (getProgram(program) ? GL_TRUE : GL_FALSE);
4561}
4562
4563GLboolean Context::isRenderbuffer(GLuint renderbuffer)
4564{
4565 if (renderbuffer == 0)
4566 {
4567 return GL_FALSE;
4568 }
4569
4570 return (getRenderbuffer(renderbuffer) ? GL_TRUE : GL_FALSE);
4571}
4572
4573GLboolean Context::isShader(GLuint shader)
4574{
4575 if (shader == 0)
4576 {
4577 return GL_FALSE;
4578 }
4579
4580 return (getShader(shader) ? GL_TRUE : GL_FALSE);
4581}
4582
4583GLboolean Context::isTexture(GLuint texture)
4584{
4585 if (texture == 0)
4586 {
4587 return GL_FALSE;
4588 }
4589
4590 return (getTexture(texture) ? GL_TRUE : GL_FALSE);
4591}
4592
4593void Context::linkProgram(GLuint program)
4594{
4595 Program *programObject = getProgram(program);
4596 ASSERT(programObject);
4597 handleError(programObject->link(this));
4598}
4599
4600void Context::releaseShaderCompiler()
4601{
Jamie Madill4928b7c2017-06-20 12:57:39 -04004602 mCompiler.set(this, nullptr);
Jamie Madillc1d770e2017-04-13 17:31:24 -04004603}
4604
4605void Context::shaderBinary(GLsizei n,
4606 const GLuint *shaders,
4607 GLenum binaryformat,
Jamie Madill876429b2017-04-20 15:46:24 -04004608 const void *binary,
Jamie Madillc1d770e2017-04-13 17:31:24 -04004609 GLsizei length)
4610{
4611 // No binary shader formats are supported.
4612 UNIMPLEMENTED();
4613}
4614
4615void Context::shaderSource(GLuint shader,
4616 GLsizei count,
4617 const GLchar *const *string,
4618 const GLint *length)
4619{
4620 Shader *shaderObject = getShader(shader);
4621 ASSERT(shaderObject);
4622 shaderObject->setSource(count, string, length);
4623}
4624
4625void Context::stencilFunc(GLenum func, GLint ref, GLuint mask)
4626{
4627 stencilFuncSeparate(GL_FRONT_AND_BACK, func, ref, mask);
4628}
4629
4630void Context::stencilMask(GLuint mask)
4631{
4632 stencilMaskSeparate(GL_FRONT_AND_BACK, mask);
4633}
4634
4635void Context::stencilOp(GLenum fail, GLenum zfail, GLenum zpass)
4636{
4637 stencilOpSeparate(GL_FRONT_AND_BACK, fail, zfail, zpass);
4638}
4639
4640void Context::uniform1f(GLint location, GLfloat x)
4641{
4642 Program *program = mGLState.getProgram();
4643 program->setUniform1fv(location, 1, &x);
4644}
4645
4646void Context::uniform1fv(GLint location, GLsizei count, const GLfloat *v)
4647{
4648 Program *program = mGLState.getProgram();
4649 program->setUniform1fv(location, count, v);
4650}
4651
4652void Context::uniform1i(GLint location, GLint x)
4653{
4654 Program *program = mGLState.getProgram();
4655 program->setUniform1iv(location, 1, &x);
4656}
4657
4658void Context::uniform1iv(GLint location, GLsizei count, const GLint *v)
4659{
4660 Program *program = mGLState.getProgram();
4661 program->setUniform1iv(location, count, v);
4662}
4663
4664void Context::uniform2f(GLint location, GLfloat x, GLfloat y)
4665{
4666 GLfloat xy[2] = {x, y};
4667 Program *program = mGLState.getProgram();
4668 program->setUniform2fv(location, 1, xy);
4669}
4670
4671void Context::uniform2fv(GLint location, GLsizei count, const GLfloat *v)
4672{
4673 Program *program = mGLState.getProgram();
4674 program->setUniform2fv(location, count, v);
4675}
4676
4677void Context::uniform2i(GLint location, GLint x, GLint y)
4678{
4679 GLint xy[2] = {x, y};
4680 Program *program = mGLState.getProgram();
4681 program->setUniform2iv(location, 1, xy);
4682}
4683
4684void Context::uniform2iv(GLint location, GLsizei count, const GLint *v)
4685{
4686 Program *program = mGLState.getProgram();
4687 program->setUniform2iv(location, count, v);
4688}
4689
4690void Context::uniform3f(GLint location, GLfloat x, GLfloat y, GLfloat z)
4691{
4692 GLfloat xyz[3] = {x, y, z};
4693 Program *program = mGLState.getProgram();
4694 program->setUniform3fv(location, 1, xyz);
4695}
4696
4697void Context::uniform3fv(GLint location, GLsizei count, const GLfloat *v)
4698{
4699 Program *program = mGLState.getProgram();
4700 program->setUniform3fv(location, count, v);
4701}
4702
4703void Context::uniform3i(GLint location, GLint x, GLint y, GLint z)
4704{
4705 GLint xyz[3] = {x, y, z};
4706 Program *program = mGLState.getProgram();
4707 program->setUniform3iv(location, 1, xyz);
4708}
4709
4710void Context::uniform3iv(GLint location, GLsizei count, const GLint *v)
4711{
4712 Program *program = mGLState.getProgram();
4713 program->setUniform3iv(location, count, v);
4714}
4715
4716void Context::uniform4f(GLint location, GLfloat x, GLfloat y, GLfloat z, GLfloat w)
4717{
4718 GLfloat xyzw[4] = {x, y, z, w};
4719 Program *program = mGLState.getProgram();
4720 program->setUniform4fv(location, 1, xyzw);
4721}
4722
4723void Context::uniform4fv(GLint location, GLsizei count, const GLfloat *v)
4724{
4725 Program *program = mGLState.getProgram();
4726 program->setUniform4fv(location, count, v);
4727}
4728
4729void Context::uniform4i(GLint location, GLint x, GLint y, GLint z, GLint w)
4730{
4731 GLint xyzw[4] = {x, y, z, w};
4732 Program *program = mGLState.getProgram();
4733 program->setUniform4iv(location, 1, xyzw);
4734}
4735
4736void Context::uniform4iv(GLint location, GLsizei count, const GLint *v)
4737{
4738 Program *program = mGLState.getProgram();
4739 program->setUniform4iv(location, count, v);
4740}
4741
4742void Context::uniformMatrix2fv(GLint location,
4743 GLsizei count,
4744 GLboolean transpose,
4745 const GLfloat *value)
4746{
4747 Program *program = mGLState.getProgram();
4748 program->setUniformMatrix2fv(location, count, transpose, value);
4749}
4750
4751void Context::uniformMatrix3fv(GLint location,
4752 GLsizei count,
4753 GLboolean transpose,
4754 const GLfloat *value)
4755{
4756 Program *program = mGLState.getProgram();
4757 program->setUniformMatrix3fv(location, count, transpose, value);
4758}
4759
4760void Context::uniformMatrix4fv(GLint location,
4761 GLsizei count,
4762 GLboolean transpose,
4763 const GLfloat *value)
4764{
4765 Program *program = mGLState.getProgram();
4766 program->setUniformMatrix4fv(location, count, transpose, value);
4767}
4768
4769void Context::validateProgram(GLuint program)
4770{
4771 Program *programObject = getProgram(program);
4772 ASSERT(programObject);
4773 programObject->validate(mCaps);
4774}
4775
Jamie Madilld04908b2017-06-09 14:15:35 -04004776void Context::getProgramBinary(GLuint program,
4777 GLsizei bufSize,
4778 GLsizei *length,
4779 GLenum *binaryFormat,
4780 void *binary)
4781{
4782 Program *programObject = getProgram(program);
4783 ASSERT(programObject != nullptr);
4784
4785 handleError(programObject->saveBinary(this, binaryFormat, binary, bufSize, length));
4786}
4787
4788void Context::programBinary(GLuint program, GLenum binaryFormat, const void *binary, GLsizei length)
4789{
4790 Program *programObject = getProgram(program);
4791 ASSERT(programObject != nullptr);
4792
4793 handleError(programObject->loadBinary(this, binaryFormat, binary, length));
4794}
4795
Jamie Madillc29968b2016-01-20 11:17:23 -05004796} // namespace gl