blob: 9b112a412ea041395b0531ba4d6de4e7a455712e [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
Jamie Madillb6664922017-07-25 12:55:04 -040048#define ANGLE_HANDLE_ERR(X) \
49 handleError(X); \
50 return;
51#define ANGLE_CONTEXT_TRY(EXPR) ANGLE_TRY_TEMPLATE(EXPR, ANGLE_HANDLE_ERR);
52
Ian Ewell3ffd78b2016-01-22 16:09:42 -050053template <typename T>
Geoff Lang4ddf5af2016-12-01 14:30:44 -050054std::vector<gl::Path *> GatherPaths(gl::PathManager &resourceManager,
Sami Väisänend59ca052016-06-21 16:10:00 +030055 GLsizei numPaths,
56 const void *paths,
57 GLuint pathBase)
58{
59 std::vector<gl::Path *> ret;
60 ret.reserve(numPaths);
61
62 const auto *nameArray = static_cast<const T *>(paths);
63
64 for (GLsizei i = 0; i < numPaths; ++i)
65 {
66 const GLuint pathName = nameArray[i] + pathBase;
67
68 ret.push_back(resourceManager.getPath(pathName));
69 }
70
71 return ret;
72}
73
Geoff Lang4ddf5af2016-12-01 14:30:44 -050074std::vector<gl::Path *> GatherPaths(gl::PathManager &resourceManager,
Sami Väisänend59ca052016-06-21 16:10:00 +030075 GLsizei numPaths,
76 GLenum pathNameType,
77 const void *paths,
78 GLuint pathBase)
79{
80 switch (pathNameType)
81 {
82 case GL_UNSIGNED_BYTE:
83 return GatherPaths<GLubyte>(resourceManager, numPaths, paths, pathBase);
84
85 case GL_BYTE:
86 return GatherPaths<GLbyte>(resourceManager, numPaths, paths, pathBase);
87
88 case GL_UNSIGNED_SHORT:
89 return GatherPaths<GLushort>(resourceManager, numPaths, paths, pathBase);
90
91 case GL_SHORT:
92 return GatherPaths<GLshort>(resourceManager, numPaths, paths, pathBase);
93
94 case GL_UNSIGNED_INT:
95 return GatherPaths<GLuint>(resourceManager, numPaths, paths, pathBase);
96
97 case GL_INT:
98 return GatherPaths<GLint>(resourceManager, numPaths, paths, pathBase);
99 }
100
101 UNREACHABLE();
102 return std::vector<gl::Path *>();
103}
104
105template <typename T>
Geoff Lang2186c382016-10-14 10:54:54 -0400106gl::Error GetQueryObjectParameter(gl::Query *query, GLenum pname, T *params)
Ian Ewell3ffd78b2016-01-22 16:09:42 -0500107{
Geoff Lang2186c382016-10-14 10:54:54 -0400108 ASSERT(query != nullptr);
Ian Ewell3ffd78b2016-01-22 16:09:42 -0500109
110 switch (pname)
111 {
112 case GL_QUERY_RESULT_EXT:
Geoff Lang2186c382016-10-14 10:54:54 -0400113 return query->getResult(params);
Ian Ewell3ffd78b2016-01-22 16:09:42 -0500114 case GL_QUERY_RESULT_AVAILABLE_EXT:
115 {
116 bool available;
Geoff Lang2186c382016-10-14 10:54:54 -0400117 gl::Error error = query->isResultAvailable(&available);
Ian Ewell3ffd78b2016-01-22 16:09:42 -0500118 if (!error.isError())
119 {
Geoff Lang2186c382016-10-14 10:54:54 -0400120 *params = gl::ConvertFromGLboolean<T>(available);
Ian Ewell3ffd78b2016-01-22 16:09:42 -0500121 }
122 return error;
123 }
124 default:
125 UNREACHABLE();
Yuly Novikovc4d18aa2017-03-09 18:45:02 -0500126 return gl::InternalError() << "Unreachable Error";
Ian Ewell3ffd78b2016-01-22 16:09:42 -0500127 }
128}
129
Geoff Langf6db0982015-08-25 13:04:00 -0400130void MarkTransformFeedbackBufferUsage(gl::TransformFeedback *transformFeedback)
131{
Geoff Lang1a683462015-09-29 15:09:59 -0400132 if (transformFeedback && transformFeedback->isActive() && !transformFeedback->isPaused())
Geoff Langf6db0982015-08-25 13:04:00 -0400133 {
134 for (size_t tfBufferIndex = 0; tfBufferIndex < transformFeedback->getIndexedBufferCount();
135 tfBufferIndex++)
136 {
Jamie Madill4928b7c2017-06-20 12:57:39 -0400137 const gl::OffsetBindingPointer<gl::Buffer> &buffer =
Geoff Langf6db0982015-08-25 13:04:00 -0400138 transformFeedback->getIndexedBuffer(tfBufferIndex);
139 if (buffer.get() != nullptr)
140 {
141 buffer->onTransformFeedback();
142 }
143 }
144 }
145}
Jamie Madill46e6c7a2016-01-18 14:42:30 -0500146
147// Attribute map queries.
Martin Radev1be913c2016-07-11 17:59:16 +0300148EGLint GetClientMajorVersion(const egl::AttributeMap &attribs)
Jamie Madill46e6c7a2016-01-18 14:42:30 -0500149{
Ian Ewellec2c0c52016-04-05 13:46:26 -0400150 return static_cast<EGLint>(attribs.get(EGL_CONTEXT_CLIENT_VERSION, 1));
Jamie Madill46e6c7a2016-01-18 14:42:30 -0500151}
152
Martin Radev1be913c2016-07-11 17:59:16 +0300153EGLint GetClientMinorVersion(const egl::AttributeMap &attribs)
154{
155 return static_cast<EGLint>(attribs.get(EGL_CONTEXT_MINOR_VERSION, 0));
156}
157
Geoff Langeb66a6e2016-10-31 13:06:12 -0400158gl::Version GetClientVersion(const egl::AttributeMap &attribs)
159{
160 return gl::Version(GetClientMajorVersion(attribs), GetClientMinorVersion(attribs));
161}
162
Jamie Madill46e6c7a2016-01-18 14:42:30 -0500163GLenum GetResetStrategy(const egl::AttributeMap &attribs)
164{
Ian Ewellec2c0c52016-04-05 13:46:26 -0400165 EGLAttrib attrib = attribs.get(EGL_CONTEXT_OPENGL_RESET_NOTIFICATION_STRATEGY_EXT,
166 EGL_NO_RESET_NOTIFICATION_EXT);
Jamie Madill46e6c7a2016-01-18 14:42:30 -0500167 switch (attrib)
168 {
169 case EGL_NO_RESET_NOTIFICATION:
170 return GL_NO_RESET_NOTIFICATION_EXT;
171 case EGL_LOSE_CONTEXT_ON_RESET:
172 return GL_LOSE_CONTEXT_ON_RESET_EXT;
173 default:
174 UNREACHABLE();
175 return GL_NONE;
176 }
177}
178
179bool GetRobustAccess(const egl::AttributeMap &attribs)
180{
Geoff Lang077f20a2016-11-01 10:08:02 -0400181 return (attribs.get(EGL_CONTEXT_OPENGL_ROBUST_ACCESS_EXT, EGL_FALSE) == EGL_TRUE) ||
182 ((attribs.get(EGL_CONTEXT_FLAGS_KHR, 0) & EGL_CONTEXT_OPENGL_ROBUST_ACCESS_BIT_KHR) !=
183 0);
Jamie Madill46e6c7a2016-01-18 14:42:30 -0500184}
185
186bool GetDebug(const egl::AttributeMap &attribs)
187{
Geoff Lang077f20a2016-11-01 10:08:02 -0400188 return (attribs.get(EGL_CONTEXT_OPENGL_DEBUG, EGL_FALSE) == EGL_TRUE) ||
189 ((attribs.get(EGL_CONTEXT_FLAGS_KHR, 0) & EGL_CONTEXT_OPENGL_DEBUG_BIT_KHR) != 0);
Jamie Madill46e6c7a2016-01-18 14:42:30 -0500190}
191
192bool GetNoError(const egl::AttributeMap &attribs)
193{
194 return (attribs.get(EGL_CONTEXT_OPENGL_NO_ERROR_KHR, EGL_FALSE) == EGL_TRUE);
195}
196
Geoff Langc287ea62016-09-16 14:46:51 -0400197bool GetWebGLContext(const egl::AttributeMap &attribs)
198{
199 return (attribs.get(EGL_CONTEXT_WEBGL_COMPATIBILITY_ANGLE, EGL_FALSE) == EGL_TRUE);
200}
201
Geoff Langf41a7152016-09-19 15:11:17 -0400202bool GetBindGeneratesResource(const egl::AttributeMap &attribs)
203{
204 return (attribs.get(EGL_CONTEXT_BIND_GENERATES_RESOURCE_CHROMIUM, EGL_TRUE) == EGL_TRUE);
205}
206
Geoff Langfeb8c682017-02-13 16:07:35 -0500207bool GetClientArraysEnabled(const egl::AttributeMap &attribs)
208{
209 return (attribs.get(EGL_CONTEXT_CLIENT_ARRAYS_ENABLED_ANGLE, EGL_TRUE) == EGL_TRUE);
210}
211
Martin Radev9d901792016-07-15 15:58:58 +0300212std::string GetObjectLabelFromPointer(GLsizei length, const GLchar *label)
213{
214 std::string labelName;
215 if (label != nullptr)
216 {
217 size_t labelLength = length < 0 ? strlen(label) : length;
218 labelName = std::string(label, labelLength);
219 }
220 return labelName;
221}
222
223void GetObjectLabelBase(const std::string &objectLabel,
224 GLsizei bufSize,
225 GLsizei *length,
226 GLchar *label)
227{
228 size_t writeLength = objectLabel.length();
229 if (label != nullptr && bufSize > 0)
230 {
231 writeLength = std::min(static_cast<size_t>(bufSize) - 1, objectLabel.length());
232 std::copy(objectLabel.begin(), objectLabel.begin() + writeLength, label);
233 label[writeLength] = '\0';
234 }
235
236 if (length != nullptr)
237 {
238 *length = static_cast<GLsizei>(writeLength);
239 }
240}
241
Geoff Langf6db0982015-08-25 13:04:00 -0400242} // anonymous namespace
243
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000244namespace gl
245{
daniel@transgaming.comca1ac1f2013-01-11 04:13:05 +0000246
Jamie Madill53ea9cc2016-05-17 10:12:52 -0400247Context::Context(rx::EGLImplFactory *implFactory,
248 const egl::Config *config,
Corentin Wallez51706ea2015-08-07 14:39:22 -0400249 const Context *shareContext,
Geoff Langce02f082017-02-06 16:46:21 -0500250 TextureManager *shareTextures,
Jamie Madill32447362017-06-28 14:53:52 -0400251 MemoryProgramCache *memoryProgramCache,
Corentin Wallezc295e512017-01-27 17:47:50 -0500252 const egl::AttributeMap &attribs,
Jamie Madill948bbe52017-06-01 13:10:42 -0400253 const egl::DisplayExtensions &displayExtensions,
254 bool robustResourceInit)
Martin Radev1be913c2016-07-11 17:59:16 +0300255
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500256 : ValidationContext(shareContext,
Geoff Langce02f082017-02-06 16:46:21 -0500257 shareTextures,
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500258 GetClientVersion(attribs),
Jamie Madilldfde6ab2016-06-09 07:07:18 -0700259 &mGLState,
Jamie Madillf25855c2015-11-03 11:06:18 -0500260 mCaps,
261 mTextureCaps,
262 mExtensions,
Jamie Madill46e6c7a2016-01-18 14:42:30 -0500263 mLimitations,
264 GetNoError(attribs)),
Jamie Madilldfde6ab2016-06-09 07:07:18 -0700265 mImplementation(implFactory->createContext(mState)),
Jamie Madill2f348d22017-06-05 10:50:59 -0400266 mCompiler(),
Corentin Walleze3b10e82015-05-20 11:06:25 -0400267 mConfig(config),
Jamie Madill46e6c7a2016-01-18 14:42:30 -0500268 mClientType(EGL_OPENGL_ES_API),
269 mHasBeenCurrent(false),
270 mContextLost(false),
271 mResetStatus(GL_NO_ERROR),
Kenneth Russellf2f6f652016-10-05 19:53:23 -0700272 mContextLostForced(false),
Jamie Madill46e6c7a2016-01-18 14:42:30 -0500273 mResetStrategy(GetResetStrategy(attribs)),
274 mRobustAccess(GetRobustAccess(attribs)),
Jamie Madill61e16b42017-06-19 11:13:23 -0400275 mCurrentSurface(static_cast<egl::Surface *>(EGL_NO_SURFACE)),
276 mCurrentDisplay(static_cast<egl::Display *>(EGL_NO_DISPLAY)),
Jamie Madill4e0e6f82017-02-17 11:06:03 -0500277 mSurfacelessFramebuffer(nullptr),
Jamie Madille14951e2017-03-09 18:55:16 -0500278 mWebGLContext(GetWebGLContext(attribs)),
Jamie Madill32447362017-06-28 14:53:52 -0400279 mMemoryProgramCache(memoryProgramCache),
Jamie Madillb3f26b92017-07-19 15:07:41 -0400280 mScratchBuffer(1000u),
281 mZeroFilledBuffer(1000u)
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000282{
Geoff Lang077f20a2016-11-01 10:08:02 -0400283 if (mRobustAccess)
284 {
285 UNIMPLEMENTED();
286 }
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000287
Jamie Madill4e0e6f82017-02-17 11:06:03 -0500288 initCaps(displayExtensions);
Kenneth Russellf2f6f652016-10-05 19:53:23 -0700289 initWorkarounds();
Geoff Langc0b9ef42014-07-02 10:02:37 -0400290
Jamie Madill4928b7c2017-06-20 12:57:39 -0400291 mGLState.initialize(this, GetDebug(attribs), GetBindGeneratesResource(attribs),
Jamie Madillc43be722017-07-13 16:22:14 -0400292 GetClientArraysEnabled(attribs), robustResourceInit,
293 mMemoryProgramCache != nullptr);
Régis Fénéon83107972015-02-05 12:57:44 +0100294
Shannon Woods53a94a82014-06-24 15:20:36 -0400295 mFenceNVHandleAllocator.setBaseHandle(0);
Geoff Lang7dca1862013-07-30 16:30:46 -0400296
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000297 // [OpenGL ES 2.0.24] section 3.7 page 83:
298 // In the initial state, TEXTURE_2D and TEXTURE_CUBE_MAP have twodimensional
299 // and cube map texture state vectors respectively associated with them.
300 // In order that access to these initial textures not be lost, they are treated as texture
301 // objects all of whose names are 0.
302
Jamie Madill53ea9cc2016-05-17 10:12:52 -0400303 Texture *zeroTexture2D = new Texture(mImplementation.get(), 0, GL_TEXTURE_2D);
Jamie Madill4928b7c2017-06-20 12:57:39 -0400304 mZeroTextures[GL_TEXTURE_2D].set(this, zeroTexture2D);
Jamie Madilldedd7b92014-11-05 16:30:36 -0500305
Jamie Madill53ea9cc2016-05-17 10:12:52 -0400306 Texture *zeroTextureCube = new Texture(mImplementation.get(), 0, GL_TEXTURE_CUBE_MAP);
Jamie Madill4928b7c2017-06-20 12:57:39 -0400307 mZeroTextures[GL_TEXTURE_CUBE_MAP].set(this, zeroTextureCube);
Geoff Lang76b10c92014-09-05 16:28:14 -0400308
Geoff Langeb66a6e2016-10-31 13:06:12 -0400309 if (getClientVersion() >= Version(3, 0))
Geoff Lang76b10c92014-09-05 16:28:14 -0400310 {
311 // TODO: These could also be enabled via extension
Jamie Madill53ea9cc2016-05-17 10:12:52 -0400312 Texture *zeroTexture3D = new Texture(mImplementation.get(), 0, GL_TEXTURE_3D);
Jamie Madill4928b7c2017-06-20 12:57:39 -0400313 mZeroTextures[GL_TEXTURE_3D].set(this, zeroTexture3D);
Geoff Lang76b10c92014-09-05 16:28:14 -0400314
Jamie Madill53ea9cc2016-05-17 10:12:52 -0400315 Texture *zeroTexture2DArray = new Texture(mImplementation.get(), 0, GL_TEXTURE_2D_ARRAY);
Jamie Madill4928b7c2017-06-20 12:57:39 -0400316 mZeroTextures[GL_TEXTURE_2D_ARRAY].set(this, zeroTexture2DArray);
Geoff Lang76b10c92014-09-05 16:28:14 -0400317 }
Geoff Lang3b573612016-10-31 14:08:10 -0400318 if (getClientVersion() >= Version(3, 1))
319 {
320 Texture *zeroTexture2DMultisample =
321 new Texture(mImplementation.get(), 0, GL_TEXTURE_2D_MULTISAMPLE);
Jamie Madill4928b7c2017-06-20 12:57:39 -0400322 mZeroTextures[GL_TEXTURE_2D_MULTISAMPLE].set(this, zeroTexture2DMultisample);
Jiajia Qin6eafb042016-12-27 17:04:07 +0800323
324 bindGenericAtomicCounterBuffer(0);
325 for (unsigned int i = 0; i < mCaps.maxAtomicCounterBufferBindings; i++)
326 {
327 bindIndexedAtomicCounterBuffer(0, i, 0, 0);
328 }
Jiajia Qinf546e7d2017-03-27 14:12:59 +0800329
330 bindGenericShaderStorageBuffer(0);
331 for (unsigned int i = 0; i < mCaps.maxShaderStorageBufferBindings; i++)
332 {
333 bindIndexedShaderStorageBuffer(0, i, 0, 0);
334 }
Geoff Lang3b573612016-10-31 14:08:10 -0400335 }
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000336
Corentin Wallez13c0dd42017-07-04 18:27:01 -0400337 if (mExtensions.textureRectangle)
338 {
339 Texture *zeroTextureRectangle =
340 new Texture(mImplementation.get(), 0, GL_TEXTURE_RECTANGLE_ANGLE);
341 mZeroTextures[GL_TEXTURE_RECTANGLE_ANGLE].set(this, zeroTextureRectangle);
342 }
343
Ian Ewellbda75592016-04-18 17:25:54 -0400344 if (mExtensions.eglImageExternal || mExtensions.eglStreamConsumerExternal)
345 {
Jamie Madill53ea9cc2016-05-17 10:12:52 -0400346 Texture *zeroTextureExternal =
347 new Texture(mImplementation.get(), 0, GL_TEXTURE_EXTERNAL_OES);
Jamie Madill4928b7c2017-06-20 12:57:39 -0400348 mZeroTextures[GL_TEXTURE_EXTERNAL_OES].set(this, zeroTextureExternal);
Ian Ewellbda75592016-04-18 17:25:54 -0400349 }
350
Jamie Madill4928b7c2017-06-20 12:57:39 -0400351 mGLState.initializeZeroTextures(this, mZeroTextures);
Jamie Madille6382c32014-11-07 15:05:26 -0500352
Jamie Madill57a89722013-07-02 11:57:03 -0400353 bindVertexArray(0);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000354 bindArrayBuffer(0);
Jiajia Qin9d7d0b12016-11-29 16:30:31 +0800355 bindDrawIndirectBuffer(0);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000356 bindElementArrayBuffer(0);
Geoff Lang76b10c92014-09-05 16:28:14 -0400357
Jamie Madill01a80ee2016-11-07 12:06:18 -0500358 bindRenderbuffer(GL_RENDERBUFFER, 0);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000359
shannon.woods%transgaming.com@gtempaccount.com667a29c2013-04-13 03:39:04 +0000360 bindGenericUniformBuffer(0);
Geoff Lang4dc3af02016-11-18 14:09:27 -0500361 for (unsigned int i = 0; i < mCaps.maxUniformBufferBindings; i++)
shannon.woods%transgaming.com@gtempaccount.com667a29c2013-04-13 03:39:04 +0000362 {
363 bindIndexedUniformBuffer(0, i, 0, -1);
364 }
365
shannon.woods%transgaming.com@gtempaccount.com51171882013-04-13 03:39:10 +0000366 bindCopyReadBuffer(0);
367 bindCopyWriteBuffer(0);
shannon.woods%transgaming.com@gtempaccount.comc926e5f2013-04-13 03:39:18 +0000368 bindPixelPackBuffer(0);
369 bindPixelUnpackBuffer(0);
shannon.woods%transgaming.com@gtempaccount.com51171882013-04-13 03:39:10 +0000370
Geoff Langeb66a6e2016-10-31 13:06:12 -0400371 if (getClientVersion() >= Version(3, 0))
Geoff Lang1a683462015-09-29 15:09:59 -0400372 {
373 // [OpenGL ES 3.0.2] section 2.14.1 pg 85:
374 // In the initial state, a default transform feedback object is bound and treated as
375 // a transform feedback object with a name of zero. That object is bound any time
376 // BindTransformFeedback is called with id of zero
Geoff Lang1a683462015-09-29 15:09:59 -0400377 bindTransformFeedback(0);
378 }
Geoff Langc8058452014-02-03 12:04:11 -0500379
Jamie Madillad9f24e2016-02-12 09:27:24 -0500380 // Initialize dirty bit masks
381 // TODO(jmadill): additional ES3 state
382 mTexImageDirtyBits.set(State::DIRTY_BIT_UNPACK_ALIGNMENT);
383 mTexImageDirtyBits.set(State::DIRTY_BIT_UNPACK_ROW_LENGTH);
384 mTexImageDirtyBits.set(State::DIRTY_BIT_UNPACK_IMAGE_HEIGHT);
385 mTexImageDirtyBits.set(State::DIRTY_BIT_UNPACK_SKIP_IMAGES);
386 mTexImageDirtyBits.set(State::DIRTY_BIT_UNPACK_SKIP_ROWS);
387 mTexImageDirtyBits.set(State::DIRTY_BIT_UNPACK_SKIP_PIXELS);
Corentin Wallezbbd663a2016-04-20 17:49:17 -0400388 mTexImageDirtyBits.set(State::DIRTY_BIT_UNPACK_BUFFER_BINDING);
Jamie Madillad9f24e2016-02-12 09:27:24 -0500389 // No dirty objects.
390
391 // Readpixels uses the pack state and read FBO
392 mReadPixelsDirtyBits.set(State::DIRTY_BIT_PACK_ALIGNMENT);
393 mReadPixelsDirtyBits.set(State::DIRTY_BIT_PACK_REVERSE_ROW_ORDER);
394 mReadPixelsDirtyBits.set(State::DIRTY_BIT_PACK_ROW_LENGTH);
395 mReadPixelsDirtyBits.set(State::DIRTY_BIT_PACK_SKIP_ROWS);
396 mReadPixelsDirtyBits.set(State::DIRTY_BIT_PACK_SKIP_PIXELS);
Corentin Wallezbbd663a2016-04-20 17:49:17 -0400397 mReadPixelsDirtyBits.set(State::DIRTY_BIT_PACK_BUFFER_BINDING);
Jamie Madillad9f24e2016-02-12 09:27:24 -0500398 mReadPixelsDirtyObjects.set(State::DIRTY_OBJECT_READ_FRAMEBUFFER);
399
400 mClearDirtyBits.set(State::DIRTY_BIT_RASTERIZER_DISCARD_ENABLED);
401 mClearDirtyBits.set(State::DIRTY_BIT_SCISSOR_TEST_ENABLED);
402 mClearDirtyBits.set(State::DIRTY_BIT_SCISSOR);
403 mClearDirtyBits.set(State::DIRTY_BIT_VIEWPORT);
404 mClearDirtyBits.set(State::DIRTY_BIT_CLEAR_COLOR);
405 mClearDirtyBits.set(State::DIRTY_BIT_CLEAR_DEPTH);
406 mClearDirtyBits.set(State::DIRTY_BIT_CLEAR_STENCIL);
407 mClearDirtyBits.set(State::DIRTY_BIT_COLOR_MASK);
408 mClearDirtyBits.set(State::DIRTY_BIT_DEPTH_MASK);
409 mClearDirtyBits.set(State::DIRTY_BIT_STENCIL_WRITEMASK_FRONT);
410 mClearDirtyBits.set(State::DIRTY_BIT_STENCIL_WRITEMASK_BACK);
411 mClearDirtyObjects.set(State::DIRTY_OBJECT_DRAW_FRAMEBUFFER);
412
413 mBlitDirtyBits.set(State::DIRTY_BIT_SCISSOR_TEST_ENABLED);
414 mBlitDirtyBits.set(State::DIRTY_BIT_SCISSOR);
Geoff Lang1d2c41d2016-10-19 16:14:46 -0700415 mBlitDirtyBits.set(State::DIRTY_BIT_FRAMEBUFFER_SRGB);
Jamie Madillad9f24e2016-02-12 09:27:24 -0500416 mBlitDirtyObjects.set(State::DIRTY_OBJECT_READ_FRAMEBUFFER);
417 mBlitDirtyObjects.set(State::DIRTY_OBJECT_DRAW_FRAMEBUFFER);
Jamie Madill437fa652016-05-03 15:13:24 -0400418
Jamie Madill53ea9cc2016-05-17 10:12:52 -0400419 handleError(mImplementation->initialize());
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000420}
421
Jamie Madill4928b7c2017-06-20 12:57:39 -0400422egl::Error Context::onDestroy(const egl::Display *display)
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000423{
Corentin Wallez80b24112015-08-25 16:41:57 -0400424 for (auto fence : mFenceNVMap)
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000425 {
Corentin Wallez80b24112015-08-25 16:41:57 -0400426 SafeDelete(fence.second);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000427 }
Jamie Madill96a483b2017-06-27 16:49:21 -0400428 mFenceNVMap.clear();
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000429
Corentin Wallez80b24112015-08-25 16:41:57 -0400430 for (auto query : mQueryMap)
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000431 {
Geoff Langf0aa8422015-09-29 15:08:34 -0400432 if (query.second != nullptr)
433 {
Jamie Madill4928b7c2017-06-20 12:57:39 -0400434 query.second->release(this);
Geoff Langf0aa8422015-09-29 15:08:34 -0400435 }
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000436 }
Jamie Madill96a483b2017-06-27 16:49:21 -0400437 mQueryMap.clear();
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000438
Corentin Wallez80b24112015-08-25 16:41:57 -0400439 for (auto vertexArray : mVertexArrayMap)
Jamie Madill57a89722013-07-02 11:57:03 -0400440 {
Jamie Madill4928b7c2017-06-20 12:57:39 -0400441 if (vertexArray.second)
442 {
443 vertexArray.second->onDestroy(this);
444 }
Jamie Madill57a89722013-07-02 11:57:03 -0400445 }
Jamie Madill96a483b2017-06-27 16:49:21 -0400446 mVertexArrayMap.clear();
Jamie Madill57a89722013-07-02 11:57:03 -0400447
Corentin Wallez80b24112015-08-25 16:41:57 -0400448 for (auto transformFeedback : mTransformFeedbackMap)
Geoff Langc8058452014-02-03 12:04:11 -0500449 {
Geoff Lang36167ab2015-12-07 10:27:14 -0500450 if (transformFeedback.second != nullptr)
451 {
Jamie Madill6c1f6712017-02-14 19:08:04 -0500452 transformFeedback.second->release(this);
Geoff Lang36167ab2015-12-07 10:27:14 -0500453 }
Geoff Langc8058452014-02-03 12:04:11 -0500454 }
Jamie Madill96a483b2017-06-27 16:49:21 -0400455 mTransformFeedbackMap.clear();
Geoff Langc8058452014-02-03 12:04:11 -0500456
Jamie Madilldedd7b92014-11-05 16:30:36 -0500457 for (auto &zeroTexture : mZeroTextures)
Geoff Lang76b10c92014-09-05 16:28:14 -0400458 {
Jamie Madill4928b7c2017-06-20 12:57:39 -0400459 zeroTexture.second->onDestroy(this);
460 zeroTexture.second.set(this, nullptr);
Geoff Lang76b10c92014-09-05 16:28:14 -0400461 }
462 mZeroTextures.clear();
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000463
Corentin Wallezccab69d2017-01-27 16:57:15 -0500464 SafeDelete(mSurfacelessFramebuffer);
465
Jamie Madill4928b7c2017-06-20 12:57:39 -0400466 ANGLE_TRY(releaseSurface(display));
Jamie Madill2f348d22017-06-05 10:50:59 -0400467 releaseShaderCompiler();
Jamie Madill6c1f6712017-02-14 19:08:04 -0500468
Jamie Madill4928b7c2017-06-20 12:57:39 -0400469 mGLState.reset(this);
470
Jamie Madill6c1f6712017-02-14 19:08:04 -0500471 mState.mBuffers->release(this);
472 mState.mShaderPrograms->release(this);
473 mState.mTextures->release(this);
474 mState.mRenderbuffers->release(this);
475 mState.mSamplers->release(this);
476 mState.mFenceSyncs->release(this);
477 mState.mPaths->release(this);
478 mState.mFramebuffers->release(this);
Jamie Madill4928b7c2017-06-20 12:57:39 -0400479
480 return egl::NoError();
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000481}
482
Jamie Madill70ee0f62017-02-06 16:04:20 -0500483Context::~Context()
484{
485}
486
Jamie Madill4928b7c2017-06-20 12:57:39 -0400487egl::Error Context::makeCurrent(egl::Display *display, egl::Surface *surface)
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000488{
Jamie Madill61e16b42017-06-19 11:13:23 -0400489 mCurrentDisplay = display;
490
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000491 if (!mHasBeenCurrent)
492 {
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000493 initRendererString();
Geoff Langc339c4e2016-11-29 10:37:36 -0500494 initVersionStrings();
Geoff Langcec35902014-04-16 10:52:36 -0400495 initExtensionStrings();
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000496
Corentin Wallezc295e512017-01-27 17:47:50 -0500497 int width = 0;
498 int height = 0;
499 if (surface != nullptr)
500 {
501 width = surface->getWidth();
502 height = surface->getHeight();
503 }
504
505 mGLState.setViewportParams(0, 0, width, height);
506 mGLState.setScissorParams(0, 0, width, height);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000507
508 mHasBeenCurrent = true;
509 }
510
Jamie Madill1b94d432015-08-07 13:23:23 -0400511 // TODO(jmadill): Rework this when we support ContextImpl
Jamie Madilldfde6ab2016-06-09 07:07:18 -0700512 mGLState.setAllDirtyBits();
Jamie Madill1b94d432015-08-07 13:23:23 -0400513
Jamie Madill4928b7c2017-06-20 12:57:39 -0400514 ANGLE_TRY(releaseSurface(display));
Corentin Wallezccab69d2017-01-27 16:57:15 -0500515
516 Framebuffer *newDefault = nullptr;
517 if (surface != nullptr)
518 {
Jamie Madill4928b7c2017-06-20 12:57:39 -0400519 ANGLE_TRY(surface->setIsCurrent(this, true));
Corentin Wallezccab69d2017-01-27 16:57:15 -0500520 mCurrentSurface = surface;
521 newDefault = surface->getDefaultFramebuffer();
522 }
523 else
524 {
525 if (mSurfacelessFramebuffer == nullptr)
526 {
527 mSurfacelessFramebuffer = new Framebuffer(mImplementation.get());
528 }
529
530 newDefault = mSurfacelessFramebuffer;
531 }
Jamie Madill18fdcbc2015-08-19 18:12:44 +0000532
Corentin Wallez37c39792015-08-20 14:19:46 -0400533 // Update default framebuffer, the binding of the previous default
534 // framebuffer (or lack of) will have a nullptr.
Jamie Madillc1c1cdc2015-04-30 09:42:26 -0400535 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -0700536 if (mGLState.getReadFramebuffer() == nullptr)
Corentin Wallez37c39792015-08-20 14:19:46 -0400537 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -0700538 mGLState.setReadFramebufferBinding(newDefault);
Corentin Wallez37c39792015-08-20 14:19:46 -0400539 }
Jamie Madilldfde6ab2016-06-09 07:07:18 -0700540 if (mGLState.getDrawFramebuffer() == nullptr)
Corentin Wallez37c39792015-08-20 14:19:46 -0400541 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -0700542 mGLState.setDrawFramebufferBinding(newDefault);
Corentin Wallez37c39792015-08-20 14:19:46 -0400543 }
Geoff Lang3bf8e3a2016-12-01 17:28:52 -0500544 mState.mFramebuffers->setDefaultFramebuffer(newDefault);
Jamie Madillc1c1cdc2015-04-30 09:42:26 -0400545 }
Ian Ewell292f0052016-02-04 10:37:32 -0500546
547 // Notify the renderer of a context switch
Jamie Madill4928b7c2017-06-20 12:57:39 -0400548 mImplementation->onMakeCurrent(this);
549 return egl::NoError();
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000550}
551
Jamie Madill4928b7c2017-06-20 12:57:39 -0400552egl::Error Context::releaseSurface(const egl::Display *display)
Jamie Madill77a72f62015-04-14 11:18:32 -0400553{
Corentin Wallez37c39792015-08-20 14:19:46 -0400554 // Remove the default framebuffer
Corentin Wallezc295e512017-01-27 17:47:50 -0500555 Framebuffer *currentDefault = nullptr;
556 if (mCurrentSurface != nullptr)
Corentin Wallez51706ea2015-08-07 14:39:22 -0400557 {
Corentin Wallezc295e512017-01-27 17:47:50 -0500558 currentDefault = mCurrentSurface->getDefaultFramebuffer();
559 }
560 else if (mSurfacelessFramebuffer != nullptr)
561 {
562 currentDefault = mSurfacelessFramebuffer;
Corentin Wallez51706ea2015-08-07 14:39:22 -0400563 }
564
Corentin Wallezc295e512017-01-27 17:47:50 -0500565 if (mGLState.getReadFramebuffer() == currentDefault)
566 {
567 mGLState.setReadFramebufferBinding(nullptr);
568 }
569 if (mGLState.getDrawFramebuffer() == currentDefault)
570 {
571 mGLState.setDrawFramebufferBinding(nullptr);
572 }
573 mState.mFramebuffers->setDefaultFramebuffer(nullptr);
574
575 if (mCurrentSurface)
576 {
Jamie Madill4928b7c2017-06-20 12:57:39 -0400577 ANGLE_TRY(mCurrentSurface->setIsCurrent(this, false));
Corentin Wallezc295e512017-01-27 17:47:50 -0500578 mCurrentSurface = nullptr;
579 }
Jamie Madill4928b7c2017-06-20 12:57:39 -0400580
581 return egl::NoError();
Jamie Madill77a72f62015-04-14 11:18:32 -0400582}
583
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000584GLuint Context::createBuffer()
585{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500586 return mState.mBuffers->createBuffer();
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000587}
588
589GLuint Context::createProgram()
590{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500591 return mState.mShaderPrograms->createProgram(mImplementation.get());
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000592}
593
594GLuint Context::createShader(GLenum type)
595{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500596 return mState.mShaderPrograms->createShader(mImplementation.get(), mLimitations, type);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000597}
598
599GLuint Context::createTexture()
600{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500601 return mState.mTextures->createTexture();
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000602}
603
604GLuint Context::createRenderbuffer()
605{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500606 return mState.mRenderbuffers->createRenderbuffer();
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000607}
608
Geoff Lang882033e2014-09-30 11:26:07 -0400609GLsync Context::createFenceSync()
Jamie Madillcd055f82013-07-26 11:55:15 -0400610{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500611 GLuint handle = mState.mFenceSyncs->createFenceSync(mImplementation.get());
Jamie Madillcd055f82013-07-26 11:55:15 -0400612
Cooper Partind8e62a32015-01-29 15:21:25 -0800613 return reinterpret_cast<GLsync>(static_cast<uintptr_t>(handle));
Jamie Madillcd055f82013-07-26 11:55:15 -0400614}
615
Sami Väisänene45e53b2016-05-25 10:36:04 +0300616GLuint Context::createPaths(GLsizei range)
617{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500618 auto resultOrError = mState.mPaths->createPaths(mImplementation.get(), range);
Sami Väisänene45e53b2016-05-25 10:36:04 +0300619 if (resultOrError.isError())
620 {
621 handleError(resultOrError.getError());
622 return 0;
623 }
624 return resultOrError.getResult();
625}
626
Jamie Madilldc356042013-07-19 16:36:57 -0400627GLuint Context::createSampler()
628{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500629 return mState.mSamplers->createSampler();
Jamie Madilldc356042013-07-19 16:36:57 -0400630}
631
Geoff Langc8058452014-02-03 12:04:11 -0500632GLuint Context::createTransformFeedback()
633{
Yunchao Hea438f4e2017-08-04 13:42:39 +0800634 GLuint transformFeedback = mTransformFeedbackHandleAllocator.allocate();
Jamie Madill96a483b2017-06-27 16:49:21 -0400635 mTransformFeedbackMap.assign(transformFeedback, nullptr);
Geoff Lang36167ab2015-12-07 10:27:14 -0500636 return transformFeedback;
Geoff Langc8058452014-02-03 12:04:11 -0500637}
638
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000639// Returns an unused framebuffer name
640GLuint Context::createFramebuffer()
641{
Geoff Lang3bf8e3a2016-12-01 17:28:52 -0500642 return mState.mFramebuffers->createFramebuffer();
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000643}
644
Jamie Madill33dc8432013-07-26 11:55:05 -0400645GLuint Context::createFenceNV()
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000646{
Jamie Madill33dc8432013-07-26 11:55:05 -0400647 GLuint handle = mFenceNVHandleAllocator.allocate();
Jamie Madill96a483b2017-06-27 16:49:21 -0400648 mFenceNVMap.assign(handle, new FenceNV(mImplementation->createFenceNV()));
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000649 return handle;
650}
651
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000652void Context::deleteBuffer(GLuint buffer)
653{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500654 if (mState.mBuffers->getBuffer(buffer))
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000655 {
656 detachBuffer(buffer);
657 }
Jamie Madill893ab082014-05-16 16:56:10 -0400658
Jamie Madill6c1f6712017-02-14 19:08:04 -0500659 mState.mBuffers->deleteObject(this, buffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000660}
661
662void Context::deleteShader(GLuint shader)
663{
Jamie Madill6c1f6712017-02-14 19:08:04 -0500664 mState.mShaderPrograms->deleteShader(this, shader);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000665}
666
667void Context::deleteProgram(GLuint program)
668{
Jamie Madill6c1f6712017-02-14 19:08:04 -0500669 mState.mShaderPrograms->deleteProgram(this, program);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000670}
671
672void Context::deleteTexture(GLuint texture)
673{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500674 if (mState.mTextures->getTexture(texture))
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000675 {
676 detachTexture(texture);
677 }
678
Jamie Madill6c1f6712017-02-14 19:08:04 -0500679 mState.mTextures->deleteObject(this, texture);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000680}
681
682void Context::deleteRenderbuffer(GLuint renderbuffer)
683{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500684 if (mState.mRenderbuffers->getRenderbuffer(renderbuffer))
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000685 {
686 detachRenderbuffer(renderbuffer);
687 }
Jamie Madill893ab082014-05-16 16:56:10 -0400688
Jamie Madill6c1f6712017-02-14 19:08:04 -0500689 mState.mRenderbuffers->deleteObject(this, renderbuffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000690}
691
Jamie Madillcd055f82013-07-26 11:55:15 -0400692void Context::deleteFenceSync(GLsync fenceSync)
693{
694 // The spec specifies the underlying Fence object is not deleted until all current
695 // wait commands finish. However, since the name becomes invalid, we cannot query the fence,
696 // and since our API is currently designed for being called from a single thread, we can delete
697 // the fence immediately.
Jamie Madill6c1f6712017-02-14 19:08:04 -0500698 mState.mFenceSyncs->deleteObject(this,
699 static_cast<GLuint>(reinterpret_cast<uintptr_t>(fenceSync)));
Jamie Madillcd055f82013-07-26 11:55:15 -0400700}
701
Sami Väisänene45e53b2016-05-25 10:36:04 +0300702void Context::deletePaths(GLuint first, GLsizei range)
703{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500704 mState.mPaths->deletePaths(first, range);
Sami Väisänene45e53b2016-05-25 10:36:04 +0300705}
706
707bool Context::hasPathData(GLuint path) const
708{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500709 const auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +0300710 if (pathObj == nullptr)
711 return false;
712
713 return pathObj->hasPathData();
714}
715
716bool Context::hasPath(GLuint path) const
717{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500718 return mState.mPaths->hasPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +0300719}
720
721void Context::setPathCommands(GLuint path,
722 GLsizei numCommands,
723 const GLubyte *commands,
724 GLsizei numCoords,
725 GLenum coordType,
726 const void *coords)
727{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500728 auto *pathObject = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +0300729
730 handleError(pathObject->setCommands(numCommands, commands, numCoords, coordType, coords));
731}
732
733void Context::setPathParameterf(GLuint path, GLenum pname, GLfloat value)
734{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500735 auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +0300736
737 switch (pname)
738 {
739 case GL_PATH_STROKE_WIDTH_CHROMIUM:
740 pathObj->setStrokeWidth(value);
741 break;
742 case GL_PATH_END_CAPS_CHROMIUM:
743 pathObj->setEndCaps(static_cast<GLenum>(value));
744 break;
745 case GL_PATH_JOIN_STYLE_CHROMIUM:
746 pathObj->setJoinStyle(static_cast<GLenum>(value));
747 break;
748 case GL_PATH_MITER_LIMIT_CHROMIUM:
749 pathObj->setMiterLimit(value);
750 break;
751 case GL_PATH_STROKE_BOUND_CHROMIUM:
752 pathObj->setStrokeBound(value);
753 break;
754 default:
755 UNREACHABLE();
756 break;
757 }
758}
759
760void Context::getPathParameterfv(GLuint path, GLenum pname, GLfloat *value) const
761{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500762 const auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +0300763
764 switch (pname)
765 {
766 case GL_PATH_STROKE_WIDTH_CHROMIUM:
767 *value = pathObj->getStrokeWidth();
768 break;
769 case GL_PATH_END_CAPS_CHROMIUM:
770 *value = static_cast<GLfloat>(pathObj->getEndCaps());
771 break;
772 case GL_PATH_JOIN_STYLE_CHROMIUM:
773 *value = static_cast<GLfloat>(pathObj->getJoinStyle());
774 break;
775 case GL_PATH_MITER_LIMIT_CHROMIUM:
776 *value = pathObj->getMiterLimit();
777 break;
778 case GL_PATH_STROKE_BOUND_CHROMIUM:
779 *value = pathObj->getStrokeBound();
780 break;
781 default:
782 UNREACHABLE();
783 break;
784 }
785}
786
787void Context::setPathStencilFunc(GLenum func, GLint ref, GLuint mask)
788{
789 mGLState.setPathStencilFunc(func, ref, mask);
790}
791
Jamie Madilldc356042013-07-19 16:36:57 -0400792void Context::deleteSampler(GLuint sampler)
793{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500794 if (mState.mSamplers->getSampler(sampler))
Jamie Madilldc356042013-07-19 16:36:57 -0400795 {
796 detachSampler(sampler);
797 }
798
Jamie Madill6c1f6712017-02-14 19:08:04 -0500799 mState.mSamplers->deleteObject(this, sampler);
Jamie Madilldc356042013-07-19 16:36:57 -0400800}
801
Geoff Langc8058452014-02-03 12:04:11 -0500802void Context::deleteTransformFeedback(GLuint transformFeedback)
803{
Geoff Lang6e60d6b2017-04-12 12:59:04 -0400804 if (transformFeedback == 0)
805 {
806 return;
807 }
808
Jamie Madill96a483b2017-06-27 16:49:21 -0400809 TransformFeedback *transformFeedbackObject = nullptr;
810 if (mTransformFeedbackMap.erase(transformFeedback, &transformFeedbackObject))
Geoff Langc8058452014-02-03 12:04:11 -0500811 {
Geoff Lang36167ab2015-12-07 10:27:14 -0500812 if (transformFeedbackObject != nullptr)
813 {
814 detachTransformFeedback(transformFeedback);
Jamie Madill6c1f6712017-02-14 19:08:04 -0500815 transformFeedbackObject->release(this);
Geoff Lang36167ab2015-12-07 10:27:14 -0500816 }
817
Yunchao Hea438f4e2017-08-04 13:42:39 +0800818 mTransformFeedbackHandleAllocator.release(transformFeedback);
Geoff Langc8058452014-02-03 12:04:11 -0500819 }
820}
821
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000822void Context::deleteFramebuffer(GLuint framebuffer)
823{
Geoff Lang3bf8e3a2016-12-01 17:28:52 -0500824 if (mState.mFramebuffers->getFramebuffer(framebuffer))
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000825 {
826 detachFramebuffer(framebuffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000827 }
Geoff Lang3bf8e3a2016-12-01 17:28:52 -0500828
Jamie Madill6c1f6712017-02-14 19:08:04 -0500829 mState.mFramebuffers->deleteObject(this, framebuffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000830}
831
Jamie Madill33dc8432013-07-26 11:55:05 -0400832void Context::deleteFenceNV(GLuint fence)
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000833{
Jamie Madill96a483b2017-06-27 16:49:21 -0400834 FenceNV *fenceObject = nullptr;
835 if (mFenceNVMap.erase(fence, &fenceObject))
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000836 {
Jamie Madill96a483b2017-06-27 16:49:21 -0400837 mFenceNVHandleAllocator.release(fence);
838 delete fenceObject;
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000839 }
840}
841
Geoff Lang70d0f492015-12-10 17:45:46 -0500842Buffer *Context::getBuffer(GLuint handle) const
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000843{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500844 return mState.mBuffers->getBuffer(handle);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000845}
846
Jamie Madill570f7c82014-07-03 10:38:54 -0400847Texture *Context::getTexture(GLuint handle) const
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000848{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500849 return mState.mTextures->getTexture(handle);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000850}
851
Geoff Lang70d0f492015-12-10 17:45:46 -0500852Renderbuffer *Context::getRenderbuffer(GLuint handle) const
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000853{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500854 return mState.mRenderbuffers->getRenderbuffer(handle);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000855}
856
Jamie Madillcd055f82013-07-26 11:55:15 -0400857FenceSync *Context::getFenceSync(GLsync handle) const
858{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500859 return mState.mFenceSyncs->getFenceSync(
860 static_cast<GLuint>(reinterpret_cast<uintptr_t>(handle)));
Jamie Madillcd055f82013-07-26 11:55:15 -0400861}
862
Jamie Madill57a89722013-07-02 11:57:03 -0400863VertexArray *Context::getVertexArray(GLuint handle) const
864{
Jamie Madill96a483b2017-06-27 16:49:21 -0400865 return mVertexArrayMap.query(handle);
Jamie Madill57a89722013-07-02 11:57:03 -0400866}
867
Jamie Madilldc356042013-07-19 16:36:57 -0400868Sampler *Context::getSampler(GLuint handle) const
869{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500870 return mState.mSamplers->getSampler(handle);
Jamie Madilldc356042013-07-19 16:36:57 -0400871}
872
Geoff Langc8058452014-02-03 12:04:11 -0500873TransformFeedback *Context::getTransformFeedback(GLuint handle) const
874{
Jamie Madill96a483b2017-06-27 16:49:21 -0400875 return mTransformFeedbackMap.query(handle);
Geoff Langc8058452014-02-03 12:04:11 -0500876}
877
Geoff Lang70d0f492015-12-10 17:45:46 -0500878LabeledObject *Context::getLabeledObject(GLenum identifier, GLuint name) const
879{
880 switch (identifier)
881 {
882 case GL_BUFFER:
883 return getBuffer(name);
884 case GL_SHADER:
885 return getShader(name);
886 case GL_PROGRAM:
887 return getProgram(name);
888 case GL_VERTEX_ARRAY:
889 return getVertexArray(name);
890 case GL_QUERY:
891 return getQuery(name);
892 case GL_TRANSFORM_FEEDBACK:
893 return getTransformFeedback(name);
894 case GL_SAMPLER:
895 return getSampler(name);
896 case GL_TEXTURE:
897 return getTexture(name);
898 case GL_RENDERBUFFER:
899 return getRenderbuffer(name);
900 case GL_FRAMEBUFFER:
901 return getFramebuffer(name);
902 default:
903 UNREACHABLE();
904 return nullptr;
905 }
906}
907
908LabeledObject *Context::getLabeledObjectFromPtr(const void *ptr) const
909{
910 return getFenceSync(reinterpret_cast<GLsync>(const_cast<void *>(ptr)));
911}
912
Martin Radev9d901792016-07-15 15:58:58 +0300913void Context::objectLabel(GLenum identifier, GLuint name, GLsizei length, const GLchar *label)
914{
915 LabeledObject *object = getLabeledObject(identifier, name);
916 ASSERT(object != nullptr);
917
918 std::string labelName = GetObjectLabelFromPointer(length, label);
919 object->setLabel(labelName);
920}
921
922void Context::objectPtrLabel(const void *ptr, GLsizei length, const GLchar *label)
923{
924 LabeledObject *object = getLabeledObjectFromPtr(ptr);
925 ASSERT(object != nullptr);
926
927 std::string labelName = GetObjectLabelFromPointer(length, label);
928 object->setLabel(labelName);
929}
930
931void Context::getObjectLabel(GLenum identifier,
932 GLuint name,
933 GLsizei bufSize,
934 GLsizei *length,
935 GLchar *label) const
936{
937 LabeledObject *object = getLabeledObject(identifier, name);
938 ASSERT(object != nullptr);
939
940 const std::string &objectLabel = object->getLabel();
941 GetObjectLabelBase(objectLabel, bufSize, length, label);
942}
943
944void Context::getObjectPtrLabel(const void *ptr,
945 GLsizei bufSize,
946 GLsizei *length,
947 GLchar *label) const
948{
949 LabeledObject *object = getLabeledObjectFromPtr(ptr);
950 ASSERT(object != nullptr);
951
952 const std::string &objectLabel = object->getLabel();
953 GetObjectLabelBase(objectLabel, bufSize, length, label);
954}
955
Jamie Madilldc356042013-07-19 16:36:57 -0400956bool Context::isSampler(GLuint samplerName) const
957{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500958 return mState.mSamplers->isSampler(samplerName);
Jamie Madilldc356042013-07-19 16:36:57 -0400959}
960
Jamie Madill3f01e6c2016-03-08 13:53:02 -0500961void Context::bindArrayBuffer(GLuint bufferHandle)
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000962{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500963 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -0400964 mGLState.setArrayBufferBinding(this, buffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000965}
966
Jiajia Qin9d7d0b12016-11-29 16:30:31 +0800967void Context::bindDrawIndirectBuffer(GLuint bufferHandle)
968{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500969 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -0400970 mGLState.setDrawIndirectBufferBinding(this, buffer);
Jiajia Qin9d7d0b12016-11-29 16:30:31 +0800971}
972
Jamie Madill3f01e6c2016-03-08 13:53:02 -0500973void Context::bindElementArrayBuffer(GLuint bufferHandle)
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000974{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500975 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -0400976 mGLState.setElementArrayBuffer(this, buffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000977}
978
Jamie Madilldedd7b92014-11-05 16:30:36 -0500979void Context::bindTexture(GLenum target, GLuint handle)
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000980{
Jamie Madill3f01e6c2016-03-08 13:53:02 -0500981 Texture *texture = nullptr;
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000982
Jamie Madilldedd7b92014-11-05 16:30:36 -0500983 if (handle == 0)
984 {
985 texture = mZeroTextures[target].get();
986 }
987 else
988 {
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500989 texture = mState.mTextures->checkTextureAllocation(mImplementation.get(), handle, target);
Jamie Madilldedd7b92014-11-05 16:30:36 -0500990 }
991
992 ASSERT(texture);
Jamie Madill4928b7c2017-06-20 12:57:39 -0400993 mGLState.setSamplerTexture(this, target, texture);
shannon.woods%transgaming.com@gtempaccount.com90dbc442013-04-13 03:46:14 +0000994}
995
Jamie Madill5bf9ff42016-02-01 11:13:03 -0500996void Context::bindReadFramebuffer(GLuint framebufferHandle)
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000997{
Geoff Lang3bf8e3a2016-12-01 17:28:52 -0500998 Framebuffer *framebuffer = mState.mFramebuffers->checkFramebufferAllocation(
999 mImplementation.get(), mCaps, framebufferHandle);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001000 mGLState.setReadFramebufferBinding(framebuffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001001}
1002
Jamie Madill5bf9ff42016-02-01 11:13:03 -05001003void Context::bindDrawFramebuffer(GLuint framebufferHandle)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001004{
Geoff Lang3bf8e3a2016-12-01 17:28:52 -05001005 Framebuffer *framebuffer = mState.mFramebuffers->checkFramebufferAllocation(
1006 mImplementation.get(), mCaps, framebufferHandle);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001007 mGLState.setDrawFramebufferBinding(framebuffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001008}
1009
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001010void Context::bindVertexArray(GLuint vertexArrayHandle)
Jamie Madill57a89722013-07-02 11:57:03 -04001011{
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001012 VertexArray *vertexArray = checkVertexArrayAllocation(vertexArrayHandle);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001013 mGLState.setVertexArrayBinding(vertexArray);
Jamie Madill57a89722013-07-02 11:57:03 -04001014}
1015
Shao80957d92017-02-20 21:25:59 +08001016void Context::bindVertexBuffer(GLuint bindingIndex,
1017 GLuint bufferHandle,
1018 GLintptr offset,
1019 GLsizei stride)
1020{
1021 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001022 mGLState.bindVertexBuffer(this, bindingIndex, buffer, offset, stride);
Shao80957d92017-02-20 21:25:59 +08001023}
1024
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001025void Context::bindSampler(GLuint textureUnit, GLuint samplerHandle)
Jamie Madilldc356042013-07-19 16:36:57 -04001026{
Geoff Lang76b10c92014-09-05 16:28:14 -04001027 ASSERT(textureUnit < mCaps.maxCombinedTextureImageUnits);
Jamie Madill901b3792016-05-26 09:20:40 -04001028 Sampler *sampler =
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001029 mState.mSamplers->checkSamplerAllocation(mImplementation.get(), samplerHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001030 mGLState.setSamplerBinding(this, textureUnit, sampler);
Jamie Madilldc356042013-07-19 16:36:57 -04001031}
1032
Xinghua Cao65ec0b22017-03-28 16:10:52 +08001033void Context::bindImageTexture(GLuint unit,
1034 GLuint texture,
1035 GLint level,
1036 GLboolean layered,
1037 GLint layer,
1038 GLenum access,
1039 GLenum format)
1040{
1041 Texture *tex = mState.mTextures->getTexture(texture);
1042 mGLState.setImageUnit(this, unit, tex, level, layered, layer, access, format);
1043}
1044
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001045void Context::bindGenericUniformBuffer(GLuint bufferHandle)
shannon.woods%transgaming.com@gtempaccount.com667a29c2013-04-13 03:39:04 +00001046{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001047 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001048 mGLState.setGenericUniformBufferBinding(this, buffer);
shannon.woods%transgaming.com@gtempaccount.com667a29c2013-04-13 03:39:04 +00001049}
1050
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001051void Context::bindIndexedUniformBuffer(GLuint bufferHandle,
1052 GLuint index,
1053 GLintptr offset,
1054 GLsizeiptr size)
shannon.woods%transgaming.com@gtempaccount.com34089352013-04-13 03:36:57 +00001055{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001056 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001057 mGLState.setIndexedUniformBufferBinding(this, index, buffer, offset, size);
shannon.woods%transgaming.com@gtempaccount.com34089352013-04-13 03:36:57 +00001058}
1059
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001060void Context::bindGenericTransformFeedbackBuffer(GLuint bufferHandle)
shannon.woods%transgaming.com@gtempaccount.com667a29c2013-04-13 03:39:04 +00001061{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001062 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001063 mGLState.getCurrentTransformFeedback()->bindGenericBuffer(this, buffer);
shannon.woods%transgaming.com@gtempaccount.com667a29c2013-04-13 03:39:04 +00001064}
1065
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001066void Context::bindIndexedTransformFeedbackBuffer(GLuint bufferHandle,
1067 GLuint index,
1068 GLintptr offset,
1069 GLsizeiptr size)
shannon.woods%transgaming.com@gtempaccount.com34089352013-04-13 03:36:57 +00001070{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001071 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001072 mGLState.getCurrentTransformFeedback()->bindIndexedBuffer(this, index, buffer, offset, size);
shannon.woods%transgaming.com@gtempaccount.com34089352013-04-13 03:36:57 +00001073}
1074
Jiajia Qin6eafb042016-12-27 17:04:07 +08001075void Context::bindGenericAtomicCounterBuffer(GLuint bufferHandle)
1076{
1077 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001078 mGLState.setGenericAtomicCounterBufferBinding(this, buffer);
Jiajia Qin6eafb042016-12-27 17:04:07 +08001079}
1080
1081void Context::bindIndexedAtomicCounterBuffer(GLuint bufferHandle,
1082 GLuint index,
1083 GLintptr offset,
1084 GLsizeiptr size)
1085{
1086 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001087 mGLState.setIndexedAtomicCounterBufferBinding(this, index, buffer, offset, size);
Jiajia Qin6eafb042016-12-27 17:04:07 +08001088}
1089
Jiajia Qinf546e7d2017-03-27 14:12:59 +08001090void Context::bindGenericShaderStorageBuffer(GLuint bufferHandle)
1091{
1092 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001093 mGLState.setGenericShaderStorageBufferBinding(this, buffer);
Jiajia Qinf546e7d2017-03-27 14:12:59 +08001094}
1095
1096void Context::bindIndexedShaderStorageBuffer(GLuint bufferHandle,
1097 GLuint index,
1098 GLintptr offset,
1099 GLsizeiptr size)
1100{
1101 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001102 mGLState.setIndexedShaderStorageBufferBinding(this, index, buffer, offset, size);
Jiajia Qinf546e7d2017-03-27 14:12:59 +08001103}
1104
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001105void Context::bindCopyReadBuffer(GLuint bufferHandle)
shannon.woods%transgaming.com@gtempaccount.com51171882013-04-13 03:39:10 +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.setCopyReadBufferBinding(this, buffer);
shannon.woods%transgaming.com@gtempaccount.com51171882013-04-13 03:39:10 +00001109}
1110
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001111void Context::bindCopyWriteBuffer(GLuint bufferHandle)
shannon.woods%transgaming.com@gtempaccount.com51171882013-04-13 03:39:10 +00001112{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001113 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001114 mGLState.setCopyWriteBufferBinding(this, buffer);
shannon.woods%transgaming.com@gtempaccount.com51171882013-04-13 03:39:10 +00001115}
1116
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001117void Context::bindPixelPackBuffer(GLuint bufferHandle)
shannon.woods%transgaming.com@gtempaccount.comc926e5f2013-04-13 03:39:18 +00001118{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001119 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001120 mGLState.setPixelPackBufferBinding(this, buffer);
shannon.woods%transgaming.com@gtempaccount.comc926e5f2013-04-13 03:39:18 +00001121}
1122
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001123void Context::bindPixelUnpackBuffer(GLuint bufferHandle)
shannon.woods%transgaming.com@gtempaccount.comc926e5f2013-04-13 03:39:18 +00001124{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001125 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001126 mGLState.setPixelUnpackBufferBinding(this, buffer);
shannon.woods%transgaming.com@gtempaccount.comc926e5f2013-04-13 03:39:18 +00001127}
1128
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001129void Context::useProgram(GLuint program)
1130{
Jamie Madill6c1f6712017-02-14 19:08:04 -05001131 mGLState.setProgram(this, getProgram(program));
daniel@transgaming.com95d29422012-07-24 18:36:10 +00001132}
1133
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001134void Context::bindTransformFeedback(GLuint transformFeedbackHandle)
Geoff Langc8058452014-02-03 12:04:11 -05001135{
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001136 TransformFeedback *transformFeedback =
1137 checkTransformFeedbackAllocation(transformFeedbackHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001138 mGLState.setTransformFeedbackBinding(this, transformFeedback);
Geoff Langc8058452014-02-03 12:04:11 -05001139}
1140
Jamie Madillf0e04492017-08-26 15:28:42 -04001141void Context::beginQuery(GLenum target, GLuint query)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001142{
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001143 Query *queryObject = getQuery(query, true, target);
Jamie Madilldb2f14c2014-05-13 13:56:30 -04001144 ASSERT(queryObject);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001145
Geoff Lang5aad9672014-09-08 11:10:42 -04001146 // begin query
Jamie Madillf0e04492017-08-26 15:28:42 -04001147 ANGLE_CONTEXT_TRY(queryObject->begin());
Geoff Lang5aad9672014-09-08 11:10:42 -04001148
1149 // set query as active for specified target only if begin succeeded
Jamie Madill4928b7c2017-06-20 12:57:39 -04001150 mGLState.setActiveQuery(this, target, queryObject);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001151}
1152
Jamie Madillf0e04492017-08-26 15:28:42 -04001153void Context::endQuery(GLenum target)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001154{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001155 Query *queryObject = mGLState.getActiveQuery(target);
Jamie Madill45c785d2014-05-13 14:09:34 -04001156 ASSERT(queryObject);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001157
Jamie Madillf0e04492017-08-26 15:28:42 -04001158 handleError(queryObject->end());
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001159
Geoff Lang5aad9672014-09-08 11:10:42 -04001160 // Always unbind the query, even if there was an error. This may delete the query object.
Jamie Madill4928b7c2017-06-20 12:57:39 -04001161 mGLState.setActiveQuery(this, target, nullptr);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001162}
1163
Jamie Madillf0e04492017-08-26 15:28:42 -04001164void Context::queryCounter(GLuint id, GLenum target)
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001165{
1166 ASSERT(target == GL_TIMESTAMP_EXT);
1167
1168 Query *queryObject = getQuery(id, true, target);
1169 ASSERT(queryObject);
1170
Jamie Madillf0e04492017-08-26 15:28:42 -04001171 handleError(queryObject->queryCounter());
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001172}
1173
1174void Context::getQueryiv(GLenum target, GLenum pname, GLint *params)
1175{
1176 switch (pname)
1177 {
1178 case GL_CURRENT_QUERY_EXT:
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001179 params[0] = mGLState.getActiveQueryId(target);
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001180 break;
1181 case GL_QUERY_COUNTER_BITS_EXT:
1182 switch (target)
1183 {
1184 case GL_TIME_ELAPSED_EXT:
1185 params[0] = getExtensions().queryCounterBitsTimeElapsed;
1186 break;
1187 case GL_TIMESTAMP_EXT:
1188 params[0] = getExtensions().queryCounterBitsTimestamp;
1189 break;
1190 default:
1191 UNREACHABLE();
1192 params[0] = 0;
1193 break;
1194 }
1195 break;
1196 default:
1197 UNREACHABLE();
1198 return;
1199 }
1200}
1201
Geoff Lang2186c382016-10-14 10:54:54 -04001202void Context::getQueryObjectiv(GLuint id, GLenum pname, GLint *params)
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001203{
Geoff Lang2186c382016-10-14 10:54:54 -04001204 handleError(GetQueryObjectParameter(getQuery(id), pname, params));
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001205}
1206
Geoff Lang2186c382016-10-14 10:54:54 -04001207void Context::getQueryObjectuiv(GLuint id, GLenum pname, GLuint *params)
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001208{
Geoff Lang2186c382016-10-14 10:54:54 -04001209 handleError(GetQueryObjectParameter(getQuery(id), pname, params));
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001210}
1211
Geoff Lang2186c382016-10-14 10:54:54 -04001212void Context::getQueryObjecti64v(GLuint id, GLenum pname, GLint64 *params)
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001213{
Geoff Lang2186c382016-10-14 10:54:54 -04001214 handleError(GetQueryObjectParameter(getQuery(id), pname, params));
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001215}
1216
Geoff Lang2186c382016-10-14 10:54:54 -04001217void Context::getQueryObjectui64v(GLuint id, GLenum pname, GLuint64 *params)
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001218{
Geoff Lang2186c382016-10-14 10:54:54 -04001219 handleError(GetQueryObjectParameter(getQuery(id), pname, params));
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001220}
1221
Geoff Lang3bf8e3a2016-12-01 17:28:52 -05001222Framebuffer *Context::getFramebuffer(GLuint handle) const
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001223{
Geoff Lang3bf8e3a2016-12-01 17:28:52 -05001224 return mState.mFramebuffers->getFramebuffer(handle);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001225}
1226
Jamie Madill2f348d22017-06-05 10:50:59 -04001227FenceNV *Context::getFenceNV(GLuint handle)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001228{
Jamie Madill96a483b2017-06-27 16:49:21 -04001229 return mFenceNVMap.query(handle);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001230}
1231
Jamie Madill2f348d22017-06-05 10:50:59 -04001232Query *Context::getQuery(GLuint handle, bool create, GLenum type)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001233{
Jamie Madill96a483b2017-06-27 16:49:21 -04001234 if (!mQueryMap.contains(handle))
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001235 {
Yunchao Hef81ce4a2017-04-24 10:49:17 +08001236 return nullptr;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001237 }
Jamie Madill96a483b2017-06-27 16:49:21 -04001238
1239 Query *query = mQueryMap.query(handle);
1240 if (!query && create)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001241 {
Jamie Madill96a483b2017-06-27 16:49:21 -04001242 query = new Query(mImplementation->createQuery(type), handle);
1243 query->addRef();
1244 mQueryMap.assign(handle, query);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001245 }
Jamie Madill96a483b2017-06-27 16:49:21 -04001246 return query;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001247}
1248
Geoff Lang70d0f492015-12-10 17:45:46 -05001249Query *Context::getQuery(GLuint handle) const
1250{
Jamie Madill96a483b2017-06-27 16:49:21 -04001251 return mQueryMap.query(handle);
Geoff Lang70d0f492015-12-10 17:45:46 -05001252}
1253
Jamie Madill1fc7e2c2014-01-21 16:47:10 -05001254Texture *Context::getTargetTexture(GLenum target) const
1255{
Ian Ewellbda75592016-04-18 17:25:54 -04001256 ASSERT(ValidTextureTarget(this, target) || ValidTextureExternalTarget(this, target));
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001257 return mGLState.getTargetTexture(target);
shannon.woods%transgaming.com@gtempaccount.comc926e5f2013-04-13 03:39:18 +00001258}
1259
Geoff Lang76b10c92014-09-05 16:28:14 -04001260Texture *Context::getSamplerTexture(unsigned int sampler, GLenum type) const
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001261{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001262 return mGLState.getSamplerTexture(sampler, type);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001263}
1264
Geoff Lang492a7e42014-11-05 13:27:06 -05001265Compiler *Context::getCompiler() const
1266{
Jamie Madill2f348d22017-06-05 10:50:59 -04001267 if (mCompiler.get() == nullptr)
1268 {
Jamie Madill4928b7c2017-06-20 12:57:39 -04001269 mCompiler.set(this, new Compiler(mImplementation.get(), mState));
Jamie Madill2f348d22017-06-05 10:50:59 -04001270 }
1271 return mCompiler.get();
Geoff Lang492a7e42014-11-05 13:27:06 -05001272}
1273
Jamie Madillc1d770e2017-04-13 17:31:24 -04001274void Context::getBooleanvImpl(GLenum pname, GLboolean *params)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001275{
1276 switch (pname)
1277 {
Jamie Madill231c7f52017-04-26 13:45:37 -04001278 case GL_SHADER_COMPILER:
1279 *params = GL_TRUE;
1280 break;
1281 case GL_CONTEXT_ROBUST_ACCESS_EXT:
1282 *params = mRobustAccess ? GL_TRUE : GL_FALSE;
1283 break;
1284 default:
1285 mGLState.getBooleanv(pname, params);
1286 break;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001287 }
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001288}
1289
Jamie Madillc1d770e2017-04-13 17:31:24 -04001290void Context::getFloatvImpl(GLenum pname, GLfloat *params)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001291{
Shannon Woods53a94a82014-06-24 15:20:36 -04001292 // Queries about context capabilities and maximums are answered by Context.
1293 // Queries about current GL state values are answered by State.
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001294 switch (pname)
1295 {
Jamie Madill231c7f52017-04-26 13:45:37 -04001296 case GL_ALIASED_LINE_WIDTH_RANGE:
1297 params[0] = mCaps.minAliasedLineWidth;
1298 params[1] = mCaps.maxAliasedLineWidth;
1299 break;
1300 case GL_ALIASED_POINT_SIZE_RANGE:
1301 params[0] = mCaps.minAliasedPointSize;
1302 params[1] = mCaps.maxAliasedPointSize;
1303 break;
1304 case GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT:
1305 ASSERT(mExtensions.textureFilterAnisotropic);
1306 *params = mExtensions.maxTextureAnisotropy;
1307 break;
1308 case GL_MAX_TEXTURE_LOD_BIAS:
1309 *params = mCaps.maxLODBias;
1310 break;
1311
1312 case GL_PATH_MODELVIEW_MATRIX_CHROMIUM:
1313 case GL_PATH_PROJECTION_MATRIX_CHROMIUM:
1314 {
1315 ASSERT(mExtensions.pathRendering);
1316 const GLfloat *m = mGLState.getPathRenderingMatrix(pname);
1317 memcpy(params, m, 16 * sizeof(GLfloat));
1318 }
Geoff Lange6d4e122015-06-29 13:33:55 -04001319 break;
Sami Väisänene45e53b2016-05-25 10:36:04 +03001320
Jamie Madill231c7f52017-04-26 13:45:37 -04001321 default:
1322 mGLState.getFloatv(pname, params);
1323 break;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001324 }
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001325}
1326
Jamie Madillc1d770e2017-04-13 17:31:24 -04001327void Context::getIntegervImpl(GLenum pname, GLint *params)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001328{
Shannon Woods53a94a82014-06-24 15:20:36 -04001329 // Queries about context capabilities and maximums are answered by Context.
1330 // Queries about current GL state values are answered by State.
shannon.woods%transgaming.com@gtempaccount.combc373e52013-04-13 03:31:23 +00001331
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001332 switch (pname)
1333 {
Jamie Madill231c7f52017-04-26 13:45:37 -04001334 case GL_MAX_VERTEX_ATTRIBS:
1335 *params = mCaps.maxVertexAttributes;
1336 break;
1337 case GL_MAX_VERTEX_UNIFORM_VECTORS:
1338 *params = mCaps.maxVertexUniformVectors;
1339 break;
1340 case GL_MAX_VERTEX_UNIFORM_COMPONENTS:
1341 *params = mCaps.maxVertexUniformComponents;
1342 break;
1343 case GL_MAX_VARYING_VECTORS:
1344 *params = mCaps.maxVaryingVectors;
1345 break;
1346 case GL_MAX_VARYING_COMPONENTS:
1347 *params = mCaps.maxVertexOutputComponents;
1348 break;
1349 case GL_MAX_COMBINED_TEXTURE_IMAGE_UNITS:
1350 *params = mCaps.maxCombinedTextureImageUnits;
1351 break;
1352 case GL_MAX_VERTEX_TEXTURE_IMAGE_UNITS:
1353 *params = mCaps.maxVertexTextureImageUnits;
1354 break;
1355 case GL_MAX_TEXTURE_IMAGE_UNITS:
1356 *params = mCaps.maxTextureImageUnits;
1357 break;
1358 case GL_MAX_FRAGMENT_UNIFORM_VECTORS:
1359 *params = mCaps.maxFragmentUniformVectors;
1360 break;
1361 case GL_MAX_FRAGMENT_UNIFORM_COMPONENTS:
1362 *params = mCaps.maxFragmentUniformComponents;
1363 break;
1364 case GL_MAX_RENDERBUFFER_SIZE:
1365 *params = mCaps.maxRenderbufferSize;
1366 break;
1367 case GL_MAX_COLOR_ATTACHMENTS_EXT:
1368 *params = mCaps.maxColorAttachments;
1369 break;
1370 case GL_MAX_DRAW_BUFFERS_EXT:
1371 *params = mCaps.maxDrawBuffers;
1372 break;
1373 // case GL_FRAMEBUFFER_BINDING: // now equivalent to
1374 // GL_DRAW_FRAMEBUFFER_BINDING_ANGLE
1375 case GL_SUBPIXEL_BITS:
1376 *params = 4;
1377 break;
1378 case GL_MAX_TEXTURE_SIZE:
1379 *params = mCaps.max2DTextureSize;
1380 break;
Corentin Wallez13c0dd42017-07-04 18:27:01 -04001381 case GL_MAX_RECTANGLE_TEXTURE_SIZE_ANGLE:
1382 *params = mCaps.maxRectangleTextureSize;
1383 break;
Jamie Madill231c7f52017-04-26 13:45:37 -04001384 case GL_MAX_CUBE_MAP_TEXTURE_SIZE:
1385 *params = mCaps.maxCubeMapTextureSize;
1386 break;
1387 case GL_MAX_3D_TEXTURE_SIZE:
1388 *params = mCaps.max3DTextureSize;
1389 break;
1390 case GL_MAX_ARRAY_TEXTURE_LAYERS:
1391 *params = mCaps.maxArrayTextureLayers;
1392 break;
1393 case GL_UNIFORM_BUFFER_OFFSET_ALIGNMENT:
1394 *params = mCaps.uniformBufferOffsetAlignment;
1395 break;
1396 case GL_MAX_UNIFORM_BUFFER_BINDINGS:
1397 *params = mCaps.maxUniformBufferBindings;
1398 break;
1399 case GL_MAX_VERTEX_UNIFORM_BLOCKS:
1400 *params = mCaps.maxVertexUniformBlocks;
1401 break;
1402 case GL_MAX_FRAGMENT_UNIFORM_BLOCKS:
1403 *params = mCaps.maxFragmentUniformBlocks;
1404 break;
1405 case GL_MAX_COMBINED_UNIFORM_BLOCKS:
1406 *params = mCaps.maxCombinedTextureImageUnits;
1407 break;
1408 case GL_MAX_VERTEX_OUTPUT_COMPONENTS:
1409 *params = mCaps.maxVertexOutputComponents;
1410 break;
1411 case GL_MAX_FRAGMENT_INPUT_COMPONENTS:
1412 *params = mCaps.maxFragmentInputComponents;
1413 break;
1414 case GL_MIN_PROGRAM_TEXEL_OFFSET:
1415 *params = mCaps.minProgramTexelOffset;
1416 break;
1417 case GL_MAX_PROGRAM_TEXEL_OFFSET:
1418 *params = mCaps.maxProgramTexelOffset;
1419 break;
1420 case GL_MAJOR_VERSION:
1421 *params = getClientVersion().major;
1422 break;
1423 case GL_MINOR_VERSION:
1424 *params = getClientVersion().minor;
1425 break;
1426 case GL_MAX_ELEMENTS_INDICES:
1427 *params = mCaps.maxElementsIndices;
1428 break;
1429 case GL_MAX_ELEMENTS_VERTICES:
1430 *params = mCaps.maxElementsVertices;
1431 break;
1432 case GL_MAX_TRANSFORM_FEEDBACK_INTERLEAVED_COMPONENTS:
1433 *params = mCaps.maxTransformFeedbackInterleavedComponents;
1434 break;
1435 case GL_MAX_TRANSFORM_FEEDBACK_SEPARATE_ATTRIBS:
1436 *params = mCaps.maxTransformFeedbackSeparateAttributes;
1437 break;
1438 case GL_MAX_TRANSFORM_FEEDBACK_SEPARATE_COMPONENTS:
1439 *params = mCaps.maxTransformFeedbackSeparateComponents;
1440 break;
1441 case GL_NUM_COMPRESSED_TEXTURE_FORMATS:
1442 *params = static_cast<GLint>(mCaps.compressedTextureFormats.size());
1443 break;
1444 case GL_MAX_SAMPLES_ANGLE:
1445 *params = mCaps.maxSamples;
1446 break;
1447 case GL_MAX_VIEWPORT_DIMS:
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001448 {
Geoff Langc0b9ef42014-07-02 10:02:37 -04001449 params[0] = mCaps.maxViewportWidth;
1450 params[1] = mCaps.maxViewportHeight;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001451 }
1452 break;
Jamie Madill231c7f52017-04-26 13:45:37 -04001453 case GL_COMPRESSED_TEXTURE_FORMATS:
1454 std::copy(mCaps.compressedTextureFormats.begin(), mCaps.compressedTextureFormats.end(),
1455 params);
1456 break;
1457 case GL_RESET_NOTIFICATION_STRATEGY_EXT:
1458 *params = mResetStrategy;
1459 break;
1460 case GL_NUM_SHADER_BINARY_FORMATS:
1461 *params = static_cast<GLint>(mCaps.shaderBinaryFormats.size());
1462 break;
1463 case GL_SHADER_BINARY_FORMATS:
1464 std::copy(mCaps.shaderBinaryFormats.begin(), mCaps.shaderBinaryFormats.end(), params);
1465 break;
1466 case GL_NUM_PROGRAM_BINARY_FORMATS:
1467 *params = static_cast<GLint>(mCaps.programBinaryFormats.size());
1468 break;
1469 case GL_PROGRAM_BINARY_FORMATS:
1470 std::copy(mCaps.programBinaryFormats.begin(), mCaps.programBinaryFormats.end(), params);
1471 break;
1472 case GL_NUM_EXTENSIONS:
1473 *params = static_cast<GLint>(mExtensionStrings.size());
1474 break;
Geoff Lang70d0f492015-12-10 17:45:46 -05001475
Jamie Madill231c7f52017-04-26 13:45:37 -04001476 // GL_KHR_debug
1477 case GL_MAX_DEBUG_MESSAGE_LENGTH:
1478 *params = mExtensions.maxDebugMessageLength;
1479 break;
1480 case GL_MAX_DEBUG_LOGGED_MESSAGES:
1481 *params = mExtensions.maxDebugLoggedMessages;
1482 break;
1483 case GL_MAX_DEBUG_GROUP_STACK_DEPTH:
1484 *params = mExtensions.maxDebugGroupStackDepth;
1485 break;
1486 case GL_MAX_LABEL_LENGTH:
1487 *params = mExtensions.maxLabelLength;
1488 break;
Geoff Lang70d0f492015-12-10 17:45:46 -05001489
Martin Radeve5285d22017-07-14 16:23:53 +03001490 // GL_ANGLE_multiview
1491 case GL_MAX_VIEWS_ANGLE:
1492 *params = mExtensions.maxViews;
1493 break;
1494
Jamie Madill231c7f52017-04-26 13:45:37 -04001495 // GL_EXT_disjoint_timer_query
1496 case GL_GPU_DISJOINT_EXT:
1497 *params = mImplementation->getGPUDisjoint();
1498 break;
1499 case GL_MAX_FRAMEBUFFER_WIDTH:
1500 *params = mCaps.maxFramebufferWidth;
1501 break;
1502 case GL_MAX_FRAMEBUFFER_HEIGHT:
1503 *params = mCaps.maxFramebufferHeight;
1504 break;
1505 case GL_MAX_FRAMEBUFFER_SAMPLES:
1506 *params = mCaps.maxFramebufferSamples;
1507 break;
1508 case GL_MAX_SAMPLE_MASK_WORDS:
1509 *params = mCaps.maxSampleMaskWords;
1510 break;
1511 case GL_MAX_COLOR_TEXTURE_SAMPLES:
1512 *params = mCaps.maxColorTextureSamples;
1513 break;
1514 case GL_MAX_DEPTH_TEXTURE_SAMPLES:
1515 *params = mCaps.maxDepthTextureSamples;
1516 break;
1517 case GL_MAX_INTEGER_SAMPLES:
1518 *params = mCaps.maxIntegerSamples;
1519 break;
1520 case GL_MAX_VERTEX_ATTRIB_RELATIVE_OFFSET:
1521 *params = mCaps.maxVertexAttribRelativeOffset;
1522 break;
1523 case GL_MAX_VERTEX_ATTRIB_BINDINGS:
1524 *params = mCaps.maxVertexAttribBindings;
1525 break;
1526 case GL_MAX_VERTEX_ATTRIB_STRIDE:
1527 *params = mCaps.maxVertexAttribStride;
1528 break;
1529 case GL_MAX_VERTEX_ATOMIC_COUNTER_BUFFERS:
1530 *params = mCaps.maxVertexAtomicCounterBuffers;
1531 break;
1532 case GL_MAX_VERTEX_ATOMIC_COUNTERS:
1533 *params = mCaps.maxVertexAtomicCounters;
1534 break;
1535 case GL_MAX_VERTEX_IMAGE_UNIFORMS:
1536 *params = mCaps.maxVertexImageUniforms;
1537 break;
1538 case GL_MAX_VERTEX_SHADER_STORAGE_BLOCKS:
1539 *params = mCaps.maxVertexShaderStorageBlocks;
1540 break;
1541 case GL_MAX_FRAGMENT_ATOMIC_COUNTER_BUFFERS:
1542 *params = mCaps.maxFragmentAtomicCounterBuffers;
1543 break;
1544 case GL_MAX_FRAGMENT_ATOMIC_COUNTERS:
1545 *params = mCaps.maxFragmentAtomicCounters;
1546 break;
1547 case GL_MAX_FRAGMENT_IMAGE_UNIFORMS:
1548 *params = mCaps.maxFragmentImageUniforms;
1549 break;
1550 case GL_MAX_FRAGMENT_SHADER_STORAGE_BLOCKS:
1551 *params = mCaps.maxFragmentShaderStorageBlocks;
1552 break;
1553 case GL_MIN_PROGRAM_TEXTURE_GATHER_OFFSET:
1554 *params = mCaps.minProgramTextureGatherOffset;
1555 break;
1556 case GL_MAX_PROGRAM_TEXTURE_GATHER_OFFSET:
1557 *params = mCaps.maxProgramTextureGatherOffset;
1558 break;
1559 case GL_MAX_COMPUTE_WORK_GROUP_INVOCATIONS:
1560 *params = mCaps.maxComputeWorkGroupInvocations;
1561 break;
1562 case GL_MAX_COMPUTE_UNIFORM_BLOCKS:
1563 *params = mCaps.maxComputeUniformBlocks;
1564 break;
1565 case GL_MAX_COMPUTE_TEXTURE_IMAGE_UNITS:
1566 *params = mCaps.maxComputeTextureImageUnits;
1567 break;
1568 case GL_MAX_COMPUTE_SHARED_MEMORY_SIZE:
1569 *params = mCaps.maxComputeSharedMemorySize;
1570 break;
1571 case GL_MAX_COMPUTE_UNIFORM_COMPONENTS:
1572 *params = mCaps.maxComputeUniformComponents;
1573 break;
1574 case GL_MAX_COMPUTE_ATOMIC_COUNTER_BUFFERS:
1575 *params = mCaps.maxComputeAtomicCounterBuffers;
1576 break;
1577 case GL_MAX_COMPUTE_ATOMIC_COUNTERS:
1578 *params = mCaps.maxComputeAtomicCounters;
1579 break;
1580 case GL_MAX_COMPUTE_IMAGE_UNIFORMS:
1581 *params = mCaps.maxComputeImageUniforms;
1582 break;
1583 case GL_MAX_COMBINED_COMPUTE_UNIFORM_COMPONENTS:
1584 *params = mCaps.maxCombinedComputeUniformComponents;
1585 break;
1586 case GL_MAX_COMPUTE_SHADER_STORAGE_BLOCKS:
1587 *params = mCaps.maxComputeShaderStorageBlocks;
1588 break;
1589 case GL_MAX_COMBINED_SHADER_OUTPUT_RESOURCES:
1590 *params = mCaps.maxCombinedShaderOutputResources;
1591 break;
1592 case GL_MAX_UNIFORM_LOCATIONS:
1593 *params = mCaps.maxUniformLocations;
1594 break;
1595 case GL_MAX_ATOMIC_COUNTER_BUFFER_BINDINGS:
1596 *params = mCaps.maxAtomicCounterBufferBindings;
1597 break;
1598 case GL_MAX_ATOMIC_COUNTER_BUFFER_SIZE:
1599 *params = mCaps.maxAtomicCounterBufferSize;
1600 break;
1601 case GL_MAX_COMBINED_ATOMIC_COUNTER_BUFFERS:
1602 *params = mCaps.maxCombinedAtomicCounterBuffers;
1603 break;
1604 case GL_MAX_COMBINED_ATOMIC_COUNTERS:
1605 *params = mCaps.maxCombinedAtomicCounters;
1606 break;
1607 case GL_MAX_IMAGE_UNITS:
1608 *params = mCaps.maxImageUnits;
1609 break;
1610 case GL_MAX_COMBINED_IMAGE_UNIFORMS:
1611 *params = mCaps.maxCombinedImageUniforms;
1612 break;
1613 case GL_MAX_SHADER_STORAGE_BUFFER_BINDINGS:
1614 *params = mCaps.maxShaderStorageBufferBindings;
1615 break;
1616 case GL_MAX_COMBINED_SHADER_STORAGE_BLOCKS:
1617 *params = mCaps.maxCombinedShaderStorageBlocks;
1618 break;
1619 case GL_SHADER_STORAGE_BUFFER_OFFSET_ALIGNMENT:
1620 *params = mCaps.shaderStorageBufferOffsetAlignment;
1621 break;
1622 default:
1623 mGLState.getIntegerv(this, pname, params);
1624 break;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001625 }
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001626}
1627
Jamie Madill893ab082014-05-16 16:56:10 -04001628void Context::getInteger64v(GLenum pname, GLint64 *params)
Jamie Madill0fda9862013-07-19 16:36:55 -04001629{
Shannon Woods53a94a82014-06-24 15:20:36 -04001630 // Queries about context capabilities and maximums are answered by Context.
1631 // Queries about current GL state values are answered by State.
Jamie Madill0fda9862013-07-19 16:36:55 -04001632 switch (pname)
1633 {
Jamie Madill231c7f52017-04-26 13:45:37 -04001634 case GL_MAX_ELEMENT_INDEX:
1635 *params = mCaps.maxElementIndex;
1636 break;
1637 case GL_MAX_UNIFORM_BLOCK_SIZE:
1638 *params = mCaps.maxUniformBlockSize;
1639 break;
1640 case GL_MAX_COMBINED_VERTEX_UNIFORM_COMPONENTS:
1641 *params = mCaps.maxCombinedVertexUniformComponents;
1642 break;
1643 case GL_MAX_COMBINED_FRAGMENT_UNIFORM_COMPONENTS:
1644 *params = mCaps.maxCombinedFragmentUniformComponents;
1645 break;
1646 case GL_MAX_SERVER_WAIT_TIMEOUT:
1647 *params = mCaps.maxServerWaitTimeout;
1648 break;
Ian Ewell53f59f42016-01-28 17:36:55 -05001649
Jamie Madill231c7f52017-04-26 13:45:37 -04001650 // GL_EXT_disjoint_timer_query
1651 case GL_TIMESTAMP_EXT:
1652 *params = mImplementation->getTimestamp();
1653 break;
Martin Radev66fb8202016-07-28 11:45:20 +03001654
Jamie Madill231c7f52017-04-26 13:45:37 -04001655 case GL_MAX_SHADER_STORAGE_BLOCK_SIZE:
1656 *params = mCaps.maxShaderStorageBlockSize;
1657 break;
1658 default:
1659 UNREACHABLE();
1660 break;
Jamie Madill0fda9862013-07-19 16:36:55 -04001661 }
Jamie Madill0fda9862013-07-19 16:36:55 -04001662}
1663
Geoff Lang70d0f492015-12-10 17:45:46 -05001664void Context::getPointerv(GLenum pname, void **params) const
1665{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001666 mGLState.getPointerv(pname, params);
Geoff Lang70d0f492015-12-10 17:45:46 -05001667}
1668
Martin Radev66fb8202016-07-28 11:45:20 +03001669void Context::getIntegeri_v(GLenum target, GLuint index, GLint *data)
Shannon Woods1b2fb852013-08-19 14:28:48 -04001670{
Shannon Woods53a94a82014-06-24 15:20:36 -04001671 // Queries about context capabilities and maximums are answered by Context.
1672 // Queries about current GL state values are answered by State.
Martin Radev66fb8202016-07-28 11:45:20 +03001673
1674 GLenum nativeType;
1675 unsigned int numParams;
1676 bool queryStatus = getIndexedQueryParameterInfo(target, &nativeType, &numParams);
1677 ASSERT(queryStatus);
1678
1679 if (nativeType == GL_INT)
1680 {
1681 switch (target)
1682 {
1683 case GL_MAX_COMPUTE_WORK_GROUP_COUNT:
1684 ASSERT(index < 3u);
1685 *data = mCaps.maxComputeWorkGroupCount[index];
1686 break;
1687 case GL_MAX_COMPUTE_WORK_GROUP_SIZE:
1688 ASSERT(index < 3u);
1689 *data = mCaps.maxComputeWorkGroupSize[index];
1690 break;
1691 default:
1692 mGLState.getIntegeri_v(target, index, data);
1693 }
1694 }
1695 else
1696 {
1697 CastIndexedStateValues(this, nativeType, target, index, numParams, data);
1698 }
Shannon Woods1b2fb852013-08-19 14:28:48 -04001699}
1700
Martin Radev66fb8202016-07-28 11:45:20 +03001701void Context::getInteger64i_v(GLenum target, GLuint index, GLint64 *data)
Shannon Woods1b2fb852013-08-19 14:28:48 -04001702{
Shannon Woods53a94a82014-06-24 15:20:36 -04001703 // Queries about context capabilities and maximums are answered by Context.
1704 // Queries about current GL state values are answered by State.
Martin Radev66fb8202016-07-28 11:45:20 +03001705
1706 GLenum nativeType;
1707 unsigned int numParams;
1708 bool queryStatus = getIndexedQueryParameterInfo(target, &nativeType, &numParams);
1709 ASSERT(queryStatus);
1710
1711 if (nativeType == GL_INT_64_ANGLEX)
1712 {
1713 mGLState.getInteger64i_v(target, index, data);
1714 }
1715 else
1716 {
1717 CastIndexedStateValues(this, nativeType, target, index, numParams, data);
1718 }
1719}
1720
1721void Context::getBooleani_v(GLenum target, GLuint index, GLboolean *data)
1722{
1723 // Queries about context capabilities and maximums are answered by Context.
1724 // Queries about current GL state values are answered by State.
1725
1726 GLenum nativeType;
1727 unsigned int numParams;
1728 bool queryStatus = getIndexedQueryParameterInfo(target, &nativeType, &numParams);
1729 ASSERT(queryStatus);
1730
1731 if (nativeType == GL_BOOL)
1732 {
1733 mGLState.getBooleani_v(target, index, data);
1734 }
1735 else
1736 {
1737 CastIndexedStateValues(this, nativeType, target, index, numParams, data);
1738 }
Shannon Woods1b2fb852013-08-19 14:28:48 -04001739}
1740
He Yunchao010e4db2017-03-03 14:22:06 +08001741void Context::getBufferParameteriv(GLenum target, GLenum pname, GLint *params)
1742{
1743 Buffer *buffer = mGLState.getTargetBuffer(target);
1744 QueryBufferParameteriv(buffer, pname, params);
1745}
1746
1747void Context::getFramebufferAttachmentParameteriv(GLenum target,
1748 GLenum attachment,
1749 GLenum pname,
1750 GLint *params)
1751{
1752 const Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
1753 QueryFramebufferAttachmentParameteriv(framebuffer, attachment, pname, params);
1754}
1755
1756void Context::getRenderbufferParameteriv(GLenum target, GLenum pname, GLint *params)
1757{
1758 Renderbuffer *renderbuffer = mGLState.getCurrentRenderbuffer();
1759 QueryRenderbufferiv(this, renderbuffer, pname, params);
1760}
1761
1762void Context::getTexParameterfv(GLenum target, GLenum pname, GLfloat *params)
1763{
1764 Texture *texture = getTargetTexture(target);
1765 QueryTexParameterfv(texture, pname, params);
1766}
1767
1768void Context::getTexParameteriv(GLenum target, GLenum pname, GLint *params)
1769{
1770 Texture *texture = getTargetTexture(target);
1771 QueryTexParameteriv(texture, pname, params);
1772}
1773void Context::texParameterf(GLenum target, GLenum pname, GLfloat param)
1774{
1775 Texture *texture = getTargetTexture(target);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001776 SetTexParameterf(this, texture, pname, param);
He Yunchao010e4db2017-03-03 14:22:06 +08001777}
1778
1779void Context::texParameterfv(GLenum target, GLenum pname, const GLfloat *params)
1780{
1781 Texture *texture = getTargetTexture(target);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001782 SetTexParameterfv(this, texture, pname, params);
He Yunchao010e4db2017-03-03 14:22:06 +08001783}
1784
1785void Context::texParameteri(GLenum target, GLenum pname, GLint param)
1786{
1787 Texture *texture = getTargetTexture(target);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001788 SetTexParameteri(this, texture, pname, param);
He Yunchao010e4db2017-03-03 14:22:06 +08001789}
1790
1791void Context::texParameteriv(GLenum target, GLenum pname, const GLint *params)
1792{
1793 Texture *texture = getTargetTexture(target);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001794 SetTexParameteriv(this, texture, pname, params);
He Yunchao010e4db2017-03-03 14:22:06 +08001795}
1796
Jamie Madill675fe712016-12-19 13:07:54 -05001797void Context::drawArrays(GLenum mode, GLint first, GLsizei count)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001798{
Jamie Madill4c19a8a2017-07-24 11:46:06 -04001799 ANGLE_CONTEXT_TRY(prepareForDraw(mode));
Jamie Madillb6664922017-07-25 12:55:04 -04001800 ANGLE_CONTEXT_TRY(mImplementation->drawArrays(this, mode, first, count));
1801 MarkTransformFeedbackBufferUsage(mGLState.getCurrentTransformFeedback());
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001802}
1803
Jamie Madill675fe712016-12-19 13:07:54 -05001804void Context::drawArraysInstanced(GLenum mode, GLint first, GLsizei count, GLsizei instanceCount)
Geoff Langf6db0982015-08-25 13:04:00 -04001805{
Jamie Madill4c19a8a2017-07-24 11:46:06 -04001806 ANGLE_CONTEXT_TRY(prepareForDraw(mode));
Jamie Madillb6664922017-07-25 12:55:04 -04001807 ANGLE_CONTEXT_TRY(
1808 mImplementation->drawArraysInstanced(this, mode, first, count, instanceCount));
1809 MarkTransformFeedbackBufferUsage(mGLState.getCurrentTransformFeedback());
Geoff Langf6db0982015-08-25 13:04:00 -04001810}
1811
Jamie Madill876429b2017-04-20 15:46:24 -04001812void Context::drawElements(GLenum mode, GLsizei count, GLenum type, const void *indices)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001813{
Jamie Madill4c19a8a2017-07-24 11:46:06 -04001814 ANGLE_CONTEXT_TRY(prepareForDraw(mode));
Jamie Madillb6664922017-07-25 12:55:04 -04001815 ANGLE_CONTEXT_TRY(mImplementation->drawElements(this, mode, count, type, indices));
Geoff Langf6db0982015-08-25 13:04:00 -04001816}
1817
Jamie Madill675fe712016-12-19 13:07:54 -05001818void Context::drawElementsInstanced(GLenum mode,
1819 GLsizei count,
1820 GLenum type,
Jamie Madill876429b2017-04-20 15:46:24 -04001821 const void *indices,
Jamie Madill9c9b40a2017-04-26 16:31:57 -04001822 GLsizei instances)
Geoff Langf6db0982015-08-25 13:04:00 -04001823{
Jamie Madill4c19a8a2017-07-24 11:46:06 -04001824 ANGLE_CONTEXT_TRY(prepareForDraw(mode));
Jamie Madillb6664922017-07-25 12:55:04 -04001825 ANGLE_CONTEXT_TRY(
Qin Jiajia1da00652017-06-20 17:16:25 +08001826 mImplementation->drawElementsInstanced(this, mode, count, type, indices, instances));
Geoff Langf6db0982015-08-25 13:04:00 -04001827}
1828
Jamie Madill675fe712016-12-19 13:07:54 -05001829void Context::drawRangeElements(GLenum mode,
1830 GLuint start,
1831 GLuint end,
1832 GLsizei count,
1833 GLenum type,
Jamie Madill876429b2017-04-20 15:46:24 -04001834 const void *indices)
Geoff Langf6db0982015-08-25 13:04:00 -04001835{
Jamie Madill4c19a8a2017-07-24 11:46:06 -04001836 ANGLE_CONTEXT_TRY(prepareForDraw(mode));
Jamie Madillb6664922017-07-25 12:55:04 -04001837 ANGLE_CONTEXT_TRY(
1838 mImplementation->drawRangeElements(this, mode, start, end, count, type, indices));
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001839}
1840
Jamie Madill876429b2017-04-20 15:46:24 -04001841void Context::drawArraysIndirect(GLenum mode, const void *indirect)
Jiajia Qind9671222016-11-29 16:30:31 +08001842{
Jamie Madill4c19a8a2017-07-24 11:46:06 -04001843 ANGLE_CONTEXT_TRY(prepareForDraw(mode));
Jamie Madillb6664922017-07-25 12:55:04 -04001844 ANGLE_CONTEXT_TRY(mImplementation->drawArraysIndirect(this, mode, indirect));
Jiajia Qind9671222016-11-29 16:30:31 +08001845}
1846
Jamie Madill876429b2017-04-20 15:46:24 -04001847void Context::drawElementsIndirect(GLenum mode, GLenum type, const void *indirect)
Jiajia Qind9671222016-11-29 16:30:31 +08001848{
Jamie Madill4c19a8a2017-07-24 11:46:06 -04001849 ANGLE_CONTEXT_TRY(prepareForDraw(mode));
Jamie Madillb6664922017-07-25 12:55:04 -04001850 ANGLE_CONTEXT_TRY(mImplementation->drawElementsIndirect(this, mode, type, indirect));
Jiajia Qind9671222016-11-29 16:30:31 +08001851}
1852
Jamie Madill675fe712016-12-19 13:07:54 -05001853void Context::flush()
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001854{
Jamie Madill675fe712016-12-19 13:07:54 -05001855 handleError(mImplementation->flush());
Geoff Lang129753a2015-01-09 16:52:09 -05001856}
1857
Jamie Madill675fe712016-12-19 13:07:54 -05001858void Context::finish()
Geoff Lang129753a2015-01-09 16:52:09 -05001859{
Jamie Madill675fe712016-12-19 13:07:54 -05001860 handleError(mImplementation->finish());
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001861}
1862
Austin Kinross6ee1e782015-05-29 17:05:37 -07001863void Context::insertEventMarker(GLsizei length, const char *marker)
1864{
Jamie Madill53ea9cc2016-05-17 10:12:52 -04001865 ASSERT(mImplementation);
1866 mImplementation->insertEventMarker(length, marker);
Austin Kinross6ee1e782015-05-29 17:05:37 -07001867}
1868
1869void Context::pushGroupMarker(GLsizei length, const char *marker)
1870{
Jamie Madill53ea9cc2016-05-17 10:12:52 -04001871 ASSERT(mImplementation);
1872 mImplementation->pushGroupMarker(length, marker);
Austin Kinross6ee1e782015-05-29 17:05:37 -07001873}
1874
1875void Context::popGroupMarker()
1876{
Jamie Madill53ea9cc2016-05-17 10:12:52 -04001877 ASSERT(mImplementation);
1878 mImplementation->popGroupMarker();
Austin Kinross6ee1e782015-05-29 17:05:37 -07001879}
1880
Geoff Langd8605522016-04-13 10:19:12 -04001881void Context::bindUniformLocation(GLuint program, GLint location, const GLchar *name)
1882{
1883 Program *programObject = getProgram(program);
1884 ASSERT(programObject);
1885
1886 programObject->bindUniformLocation(location, name);
1887}
1888
Sami Väisänena797e062016-05-12 15:23:40 +03001889void Context::setCoverageModulation(GLenum components)
1890{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001891 mGLState.setCoverageModulation(components);
Sami Väisänena797e062016-05-12 15:23:40 +03001892}
1893
Sami Väisänene45e53b2016-05-25 10:36:04 +03001894void Context::loadPathRenderingMatrix(GLenum matrixMode, const GLfloat *matrix)
1895{
1896 mGLState.loadPathRenderingMatrix(matrixMode, matrix);
1897}
1898
1899void Context::loadPathRenderingIdentityMatrix(GLenum matrixMode)
1900{
1901 GLfloat I[16];
1902 angle::Matrix<GLfloat>::setToIdentity(I);
1903
1904 mGLState.loadPathRenderingMatrix(matrixMode, I);
1905}
1906
1907void Context::stencilFillPath(GLuint path, GLenum fillMode, GLuint mask)
1908{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001909 const auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +03001910 if (!pathObj)
1911 return;
1912
1913 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
1914 syncRendererState();
1915
1916 mImplementation->stencilFillPath(pathObj, fillMode, mask);
1917}
1918
1919void Context::stencilStrokePath(GLuint path, GLint reference, GLuint mask)
1920{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001921 const auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +03001922 if (!pathObj)
1923 return;
1924
1925 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
1926 syncRendererState();
1927
1928 mImplementation->stencilStrokePath(pathObj, reference, mask);
1929}
1930
1931void Context::coverFillPath(GLuint path, GLenum coverMode)
1932{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001933 const auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +03001934 if (!pathObj)
1935 return;
1936
1937 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
1938 syncRendererState();
1939
1940 mImplementation->coverFillPath(pathObj, coverMode);
1941}
1942
1943void Context::coverStrokePath(GLuint path, GLenum coverMode)
1944{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001945 const auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +03001946 if (!pathObj)
1947 return;
1948
1949 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
1950 syncRendererState();
1951
1952 mImplementation->coverStrokePath(pathObj, coverMode);
1953}
1954
1955void Context::stencilThenCoverFillPath(GLuint path, GLenum fillMode, GLuint mask, GLenum coverMode)
1956{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001957 const auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +03001958 if (!pathObj)
1959 return;
1960
1961 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
1962 syncRendererState();
1963
1964 mImplementation->stencilThenCoverFillPath(pathObj, fillMode, mask, coverMode);
1965}
1966
1967void Context::stencilThenCoverStrokePath(GLuint path,
1968 GLint reference,
1969 GLuint mask,
1970 GLenum coverMode)
1971{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001972 const auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +03001973 if (!pathObj)
1974 return;
1975
1976 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
1977 syncRendererState();
1978
1979 mImplementation->stencilThenCoverStrokePath(pathObj, reference, mask, coverMode);
1980}
1981
Sami Väisänend59ca052016-06-21 16:10:00 +03001982void Context::coverFillPathInstanced(GLsizei numPaths,
1983 GLenum pathNameType,
1984 const void *paths,
1985 GLuint pathBase,
1986 GLenum coverMode,
1987 GLenum transformType,
1988 const GLfloat *transformValues)
1989{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001990 const auto &pathObjects = GatherPaths(*mState.mPaths, numPaths, pathNameType, paths, pathBase);
Sami Väisänend59ca052016-06-21 16:10:00 +03001991
1992 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
1993 syncRendererState();
1994
1995 mImplementation->coverFillPathInstanced(pathObjects, coverMode, transformType, transformValues);
1996}
Sami Väisänen46eaa942016-06-29 10:26:37 +03001997
Sami Väisänend59ca052016-06-21 16:10:00 +03001998void Context::coverStrokePathInstanced(GLsizei numPaths,
1999 GLenum pathNameType,
2000 const void *paths,
2001 GLuint pathBase,
2002 GLenum coverMode,
2003 GLenum transformType,
2004 const GLfloat *transformValues)
2005{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002006 const auto &pathObjects = GatherPaths(*mState.mPaths, numPaths, pathNameType, paths, pathBase);
Sami Väisänend59ca052016-06-21 16:10:00 +03002007
2008 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
2009 syncRendererState();
2010
2011 mImplementation->coverStrokePathInstanced(pathObjects, coverMode, transformType,
2012 transformValues);
2013}
Sami Väisänen46eaa942016-06-29 10:26:37 +03002014
Sami Väisänend59ca052016-06-21 16:10:00 +03002015void Context::stencilFillPathInstanced(GLsizei numPaths,
2016 GLenum pathNameType,
2017 const void *paths,
2018 GLuint pathBase,
2019 GLenum fillMode,
2020 GLuint mask,
2021 GLenum transformType,
2022 const GLfloat *transformValues)
2023{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002024 const auto &pathObjects = GatherPaths(*mState.mPaths, numPaths, pathNameType, paths, pathBase);
Sami Väisänend59ca052016-06-21 16:10:00 +03002025
2026 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
2027 syncRendererState();
2028
2029 mImplementation->stencilFillPathInstanced(pathObjects, fillMode, mask, transformType,
2030 transformValues);
2031}
Sami Väisänen46eaa942016-06-29 10:26:37 +03002032
Sami Väisänend59ca052016-06-21 16:10:00 +03002033void Context::stencilStrokePathInstanced(GLsizei numPaths,
2034 GLenum pathNameType,
2035 const void *paths,
2036 GLuint pathBase,
2037 GLint reference,
2038 GLuint mask,
2039 GLenum transformType,
2040 const GLfloat *transformValues)
2041{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002042 const auto &pathObjects = GatherPaths(*mState.mPaths, numPaths, pathNameType, paths, pathBase);
Sami Väisänend59ca052016-06-21 16:10:00 +03002043
2044 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
2045 syncRendererState();
2046
2047 mImplementation->stencilStrokePathInstanced(pathObjects, reference, mask, transformType,
2048 transformValues);
2049}
Sami Väisänen46eaa942016-06-29 10:26:37 +03002050
Sami Väisänend59ca052016-06-21 16:10:00 +03002051void Context::stencilThenCoverFillPathInstanced(GLsizei numPaths,
2052 GLenum pathNameType,
2053 const void *paths,
2054 GLuint pathBase,
2055 GLenum fillMode,
2056 GLuint mask,
2057 GLenum coverMode,
2058 GLenum transformType,
2059 const GLfloat *transformValues)
2060{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002061 const auto &pathObjects = GatherPaths(*mState.mPaths, numPaths, pathNameType, paths, pathBase);
Sami Väisänend59ca052016-06-21 16:10:00 +03002062
2063 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
2064 syncRendererState();
2065
2066 mImplementation->stencilThenCoverFillPathInstanced(pathObjects, coverMode, fillMode, mask,
2067 transformType, transformValues);
2068}
Sami Väisänen46eaa942016-06-29 10:26:37 +03002069
Sami Väisänend59ca052016-06-21 16:10:00 +03002070void Context::stencilThenCoverStrokePathInstanced(GLsizei numPaths,
2071 GLenum pathNameType,
2072 const void *paths,
2073 GLuint pathBase,
2074 GLint reference,
2075 GLuint mask,
2076 GLenum coverMode,
2077 GLenum transformType,
2078 const GLfloat *transformValues)
2079{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002080 const auto &pathObjects = GatherPaths(*mState.mPaths, numPaths, pathNameType, paths, pathBase);
Sami Väisänend59ca052016-06-21 16:10:00 +03002081
2082 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
2083 syncRendererState();
2084
2085 mImplementation->stencilThenCoverStrokePathInstanced(pathObjects, coverMode, reference, mask,
2086 transformType, transformValues);
2087}
2088
Sami Väisänen46eaa942016-06-29 10:26:37 +03002089void Context::bindFragmentInputLocation(GLuint program, GLint location, const GLchar *name)
2090{
2091 auto *programObject = getProgram(program);
2092
2093 programObject->bindFragmentInputLocation(location, name);
2094}
2095
2096void Context::programPathFragmentInputGen(GLuint program,
2097 GLint location,
2098 GLenum genMode,
2099 GLint components,
2100 const GLfloat *coeffs)
2101{
2102 auto *programObject = getProgram(program);
2103
Jamie Madillbd044ed2017-06-05 12:59:21 -04002104 programObject->pathFragmentInputGen(this, location, genMode, components, coeffs);
Sami Väisänen46eaa942016-06-29 10:26:37 +03002105}
2106
jchen1015015f72017-03-16 13:54:21 +08002107GLuint Context::getProgramResourceIndex(GLuint program, GLenum programInterface, const GLchar *name)
2108{
jchen10fd7c3b52017-03-21 15:36:03 +08002109 const auto *programObject = getProgram(program);
jchen1015015f72017-03-16 13:54:21 +08002110 return QueryProgramResourceIndex(programObject, programInterface, name);
2111}
2112
jchen10fd7c3b52017-03-21 15:36:03 +08002113void Context::getProgramResourceName(GLuint program,
2114 GLenum programInterface,
2115 GLuint index,
2116 GLsizei bufSize,
2117 GLsizei *length,
2118 GLchar *name)
2119{
2120 const auto *programObject = getProgram(program);
2121 QueryProgramResourceName(programObject, programInterface, index, bufSize, length, name);
2122}
2123
jchen10191381f2017-04-11 13:59:04 +08002124GLint Context::getProgramResourceLocation(GLuint program,
2125 GLenum programInterface,
2126 const GLchar *name)
2127{
2128 const auto *programObject = getProgram(program);
2129 return QueryProgramResourceLocation(programObject, programInterface, name);
2130}
2131
jchen10880683b2017-04-12 16:21:55 +08002132void Context::getProgramResourceiv(GLuint program,
2133 GLenum programInterface,
2134 GLuint index,
2135 GLsizei propCount,
2136 const GLenum *props,
2137 GLsizei bufSize,
2138 GLsizei *length,
2139 GLint *params)
2140{
2141 const auto *programObject = getProgram(program);
2142 QueryProgramResourceiv(programObject, programInterface, index, propCount, props, bufSize,
2143 length, params);
2144}
2145
Jamie Madill4c19a8a2017-07-24 11:46:06 -04002146Error Context::handleError(const Error &error)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002147{
Geoff Langda5777c2014-07-11 09:52:58 -04002148 if (error.isError())
2149 {
Kenneth Russellf2f6f652016-10-05 19:53:23 -07002150 GLenum code = error.getCode();
2151 mErrors.insert(code);
2152 if (code == GL_OUT_OF_MEMORY && getWorkarounds().loseContextOnOutOfMemory)
2153 {
2154 markContextLost();
2155 }
Geoff Lang70d0f492015-12-10 17:45:46 -05002156
2157 if (!error.getMessage().empty())
2158 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002159 auto *debug = &mGLState.getDebug();
2160 debug->insertMessage(GL_DEBUG_SOURCE_API, GL_DEBUG_TYPE_ERROR, error.getID(),
2161 GL_DEBUG_SEVERITY_HIGH, error.getMessage());
Geoff Lang70d0f492015-12-10 17:45:46 -05002162 }
Geoff Langda5777c2014-07-11 09:52:58 -04002163 }
Jamie Madill4c19a8a2017-07-24 11:46:06 -04002164
2165 return error;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002166}
2167
2168// Get one of the recorded errors and clear its flag, if any.
2169// [OpenGL ES 2.0.24] section 2.5 page 13.
2170GLenum Context::getError()
2171{
Geoff Langda5777c2014-07-11 09:52:58 -04002172 if (mErrors.empty())
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002173 {
Geoff Langda5777c2014-07-11 09:52:58 -04002174 return GL_NO_ERROR;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002175 }
Geoff Langda5777c2014-07-11 09:52:58 -04002176 else
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002177 {
Geoff Langda5777c2014-07-11 09:52:58 -04002178 GLenum error = *mErrors.begin();
2179 mErrors.erase(mErrors.begin());
2180 return error;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002181 }
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002182}
2183
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002184// NOTE: this function should not assume that this context is current!
2185void Context::markContextLost()
2186{
2187 if (mResetStrategy == GL_LOSE_CONTEXT_ON_RESET_EXT)
Kenneth Russellf2f6f652016-10-05 19:53:23 -07002188 {
Jamie Madill231c7f52017-04-26 13:45:37 -04002189 mResetStatus = GL_UNKNOWN_CONTEXT_RESET_EXT;
Kenneth Russellf2f6f652016-10-05 19:53:23 -07002190 mContextLostForced = true;
2191 }
Jamie Madill231c7f52017-04-26 13:45:37 -04002192 mContextLost = true;
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002193}
2194
2195bool Context::isContextLost()
2196{
2197 return mContextLost;
2198}
2199
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002200GLenum Context::getResetStatus()
2201{
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002202 // Even if the application doesn't want to know about resets, we want to know
2203 // as it will allow us to skip all the calls.
2204 if (mResetStrategy == GL_NO_RESET_NOTIFICATION_EXT)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002205 {
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002206 if (!mContextLost && mImplementation->getResetStatus() != GL_NO_ERROR)
Jamie Madill9dd0cf02014-11-24 11:38:51 -05002207 {
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002208 mContextLost = true;
Jamie Madill9dd0cf02014-11-24 11:38:51 -05002209 }
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002210
2211 // EXT_robustness, section 2.6: If the reset notification behavior is
2212 // NO_RESET_NOTIFICATION_EXT, then the implementation will never deliver notification of
2213 // reset events, and GetGraphicsResetStatusEXT will always return NO_ERROR.
2214 return GL_NO_ERROR;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002215 }
2216
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002217 // The GL_EXT_robustness spec says that if a reset is encountered, a reset
2218 // status should be returned at least once, and GL_NO_ERROR should be returned
2219 // once the device has finished resetting.
2220 if (!mContextLost)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002221 {
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002222 ASSERT(mResetStatus == GL_NO_ERROR);
2223 mResetStatus = mImplementation->getResetStatus();
shannon.woods@transgaming.comddd6c802013-02-28 23:05:14 +00002224
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002225 if (mResetStatus != GL_NO_ERROR)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002226 {
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002227 mContextLost = true;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002228 }
2229 }
Kenneth Russellf2f6f652016-10-05 19:53:23 -07002230 else if (!mContextLostForced && mResetStatus != GL_NO_ERROR)
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002231 {
Kenneth Russellf2f6f652016-10-05 19:53:23 -07002232 // If markContextLost was used to mark the context lost then
2233 // assume that is not recoverable, and continue to report the
2234 // lost reset status for the lifetime of this context.
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002235 mResetStatus = mImplementation->getResetStatus();
2236 }
Jamie Madill893ab082014-05-16 16:56:10 -04002237
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002238 return mResetStatus;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002239}
2240
2241bool Context::isResetNotificationEnabled()
2242{
2243 return (mResetStrategy == GL_LOSE_CONTEXT_ON_RESET_EXT);
2244}
2245
Corentin Walleze3b10e82015-05-20 11:06:25 -04002246const egl::Config *Context::getConfig() const
Régis Fénéon83107972015-02-05 12:57:44 +01002247{
Corentin Walleze3b10e82015-05-20 11:06:25 -04002248 return mConfig;
Régis Fénéon83107972015-02-05 12:57:44 +01002249}
2250
2251EGLenum Context::getClientType() const
2252{
2253 return mClientType;
2254}
2255
2256EGLenum Context::getRenderBuffer() const
2257{
Geoff Lang3bf8e3a2016-12-01 17:28:52 -05002258 const Framebuffer *framebuffer = mState.mFramebuffers->getFramebuffer(0);
2259 if (framebuffer == nullptr)
Corentin Wallez37c39792015-08-20 14:19:46 -04002260 {
2261 return EGL_NONE;
2262 }
Geoff Lang3bf8e3a2016-12-01 17:28:52 -05002263
2264 const FramebufferAttachment *backAttachment = framebuffer->getAttachment(GL_BACK);
2265 ASSERT(backAttachment != nullptr);
2266 return backAttachment->getSurface()->getRenderBuffer();
Régis Fénéon83107972015-02-05 12:57:44 +01002267}
2268
Jamie Madill3f01e6c2016-03-08 13:53:02 -05002269VertexArray *Context::checkVertexArrayAllocation(GLuint vertexArrayHandle)
Geoff Lang36167ab2015-12-07 10:27:14 -05002270{
Jamie Madill5bf9ff42016-02-01 11:13:03 -05002271 // Only called after a prior call to Gen.
Jamie Madill3f01e6c2016-03-08 13:53:02 -05002272 VertexArray *vertexArray = getVertexArray(vertexArrayHandle);
2273 if (!vertexArray)
Geoff Lang36167ab2015-12-07 10:27:14 -05002274 {
Jiawei-Shao2597fb62016-12-09 16:38:02 +08002275 vertexArray = new VertexArray(mImplementation.get(), vertexArrayHandle,
2276 mCaps.maxVertexAttributes, mCaps.maxVertexAttribBindings);
Jamie Madill53ea9cc2016-05-17 10:12:52 -04002277
Jamie Madill96a483b2017-06-27 16:49:21 -04002278 mVertexArrayMap.assign(vertexArrayHandle, vertexArray);
Geoff Lang36167ab2015-12-07 10:27:14 -05002279 }
Jamie Madill3f01e6c2016-03-08 13:53:02 -05002280
2281 return vertexArray;
Geoff Lang36167ab2015-12-07 10:27:14 -05002282}
2283
Jamie Madill3f01e6c2016-03-08 13:53:02 -05002284TransformFeedback *Context::checkTransformFeedbackAllocation(GLuint transformFeedbackHandle)
Geoff Lang36167ab2015-12-07 10:27:14 -05002285{
Jamie Madill5bf9ff42016-02-01 11:13:03 -05002286 // Only called after a prior call to Gen.
Jamie Madill3f01e6c2016-03-08 13:53:02 -05002287 TransformFeedback *transformFeedback = getTransformFeedback(transformFeedbackHandle);
2288 if (!transformFeedback)
Geoff Lang36167ab2015-12-07 10:27:14 -05002289 {
Jamie Madill53ea9cc2016-05-17 10:12:52 -04002290 transformFeedback =
2291 new TransformFeedback(mImplementation.get(), transformFeedbackHandle, mCaps);
Jamie Madill3f01e6c2016-03-08 13:53:02 -05002292 transformFeedback->addRef();
Jamie Madill96a483b2017-06-27 16:49:21 -04002293 mTransformFeedbackMap.assign(transformFeedbackHandle, transformFeedback);
Geoff Lang36167ab2015-12-07 10:27:14 -05002294 }
Jamie Madill3f01e6c2016-03-08 13:53:02 -05002295
2296 return transformFeedback;
Geoff Lang36167ab2015-12-07 10:27:14 -05002297}
2298
2299bool Context::isVertexArrayGenerated(GLuint vertexArray)
2300{
Jamie Madill96a483b2017-06-27 16:49:21 -04002301 ASSERT(mVertexArrayMap.contains(0));
2302 return mVertexArrayMap.contains(vertexArray);
Geoff Lang36167ab2015-12-07 10:27:14 -05002303}
2304
2305bool Context::isTransformFeedbackGenerated(GLuint transformFeedback)
2306{
Jamie Madill96a483b2017-06-27 16:49:21 -04002307 ASSERT(mTransformFeedbackMap.contains(0));
2308 return mTransformFeedbackMap.contains(transformFeedback);
Geoff Lang36167ab2015-12-07 10:27:14 -05002309}
2310
Shannon Woods53a94a82014-06-24 15:20:36 -04002311void Context::detachTexture(GLuint texture)
2312{
2313 // Simple pass-through to State's detachTexture method, as textures do not require
2314 // allocation map management either here or in the resource manager at detach time.
2315 // Zero textures are held by the Context, and we don't attempt to request them from
2316 // the State.
Jamie Madilla02315b2017-02-23 14:14:47 -05002317 mGLState.detachTexture(this, mZeroTextures, texture);
Shannon Woods53a94a82014-06-24 15:20:36 -04002318}
2319
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002320void Context::detachBuffer(GLuint buffer)
2321{
Yuly Novikov5807a532015-12-03 13:01:22 -05002322 // Simple pass-through to State's detachBuffer method, since
2323 // only buffer attachments to container objects that are bound to the current context
2324 // should be detached. And all those are available in State.
Shannon Woods53a94a82014-06-24 15:20:36 -04002325
Yuly Novikov5807a532015-12-03 13:01:22 -05002326 // [OpenGL ES 3.2] section 5.1.2 page 45:
2327 // Attachments to unbound container objects, such as
2328 // deletion of a buffer attached to a vertex array object which is not bound to the context,
2329 // are not affected and continue to act as references on the deleted object
Jamie Madill4928b7c2017-06-20 12:57:39 -04002330 mGLState.detachBuffer(this, buffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002331}
2332
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002333void Context::detachFramebuffer(GLuint framebuffer)
2334{
Shannon Woods53a94a82014-06-24 15:20:36 -04002335 // Framebuffer detachment is handled by Context, because 0 is a valid
2336 // Framebuffer object, and a pointer to it must be passed from Context
2337 // to State at binding time.
2338
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002339 // [OpenGL ES 2.0.24] section 4.4 page 107:
Jamie Madill231c7f52017-04-26 13:45:37 -04002340 // If a framebuffer that is currently bound to the target FRAMEBUFFER is deleted, it is as
2341 // though BindFramebuffer had been executed with the target of FRAMEBUFFER and framebuffer of
2342 // zero.
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002343
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002344 if (mGLState.removeReadFramebufferBinding(framebuffer) && framebuffer != 0)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002345 {
2346 bindReadFramebuffer(0);
2347 }
2348
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002349 if (mGLState.removeDrawFramebufferBinding(framebuffer) && framebuffer != 0)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002350 {
2351 bindDrawFramebuffer(0);
2352 }
2353}
2354
2355void Context::detachRenderbuffer(GLuint renderbuffer)
2356{
Jamie Madilla02315b2017-02-23 14:14:47 -05002357 mGLState.detachRenderbuffer(this, renderbuffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002358}
2359
Jamie Madill57a89722013-07-02 11:57:03 -04002360void Context::detachVertexArray(GLuint vertexArray)
2361{
Jamie Madill77a72f62015-04-14 11:18:32 -04002362 // Vertex array detachment is handled by Context, because 0 is a valid
2363 // VAO, and a pointer to it must be passed from Context to State at
Shannon Woods53a94a82014-06-24 15:20:36 -04002364 // binding time.
2365
Jamie Madill57a89722013-07-02 11:57:03 -04002366 // [OpenGL ES 3.0.2] section 2.10 page 43:
2367 // If a vertex array object that is currently bound is deleted, the binding
2368 // for that object reverts to zero and the default vertex array becomes current.
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002369 if (mGLState.removeVertexArrayBinding(vertexArray))
Jamie Madill57a89722013-07-02 11:57:03 -04002370 {
2371 bindVertexArray(0);
2372 }
2373}
2374
Geoff Langc8058452014-02-03 12:04:11 -05002375void Context::detachTransformFeedback(GLuint transformFeedback)
2376{
Corentin Walleza2257da2016-04-19 16:43:12 -04002377 // Transform feedback detachment is handled by Context, because 0 is a valid
2378 // transform feedback, and a pointer to it must be passed from Context to State at
2379 // binding time.
2380
2381 // The OpenGL specification doesn't mention what should happen when the currently bound
2382 // transform feedback object is deleted. Since it is a container object, we treat it like
2383 // VAOs and FBOs and set the current bound transform feedback back to 0.
Jamie Madill4928b7c2017-06-20 12:57:39 -04002384 if (mGLState.removeTransformFeedbackBinding(this, transformFeedback))
Corentin Walleza2257da2016-04-19 16:43:12 -04002385 {
2386 bindTransformFeedback(0);
2387 }
Geoff Langc8058452014-02-03 12:04:11 -05002388}
2389
Jamie Madilldc356042013-07-19 16:36:57 -04002390void Context::detachSampler(GLuint sampler)
2391{
Jamie Madill4928b7c2017-06-20 12:57:39 -04002392 mGLState.detachSampler(this, sampler);
Jamie Madilldc356042013-07-19 16:36:57 -04002393}
2394
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002395void Context::setVertexAttribDivisor(GLuint index, GLuint divisor)
2396{
Shaodde78e82017-05-22 14:13:27 +08002397 mGLState.setVertexAttribDivisor(this, index, divisor);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002398}
2399
Jamie Madille29d1672013-07-19 16:36:57 -04002400void Context::samplerParameteri(GLuint sampler, GLenum pname, GLint param)
2401{
Geoff Langc1984ed2016-10-07 12:41:00 -04002402 Sampler *samplerObject =
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002403 mState.mSamplers->checkSamplerAllocation(mImplementation.get(), sampler);
Geoff Langc1984ed2016-10-07 12:41:00 -04002404 SetSamplerParameteri(samplerObject, pname, param);
2405}
Jamie Madille29d1672013-07-19 16:36:57 -04002406
Geoff Langc1984ed2016-10-07 12:41:00 -04002407void Context::samplerParameteriv(GLuint sampler, GLenum pname, const GLint *param)
2408{
2409 Sampler *samplerObject =
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002410 mState.mSamplers->checkSamplerAllocation(mImplementation.get(), sampler);
Geoff Langc1984ed2016-10-07 12:41:00 -04002411 SetSamplerParameteriv(samplerObject, pname, param);
Jamie Madille29d1672013-07-19 16:36:57 -04002412}
2413
2414void Context::samplerParameterf(GLuint sampler, GLenum pname, GLfloat param)
2415{
Geoff Langc1984ed2016-10-07 12:41:00 -04002416 Sampler *samplerObject =
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002417 mState.mSamplers->checkSamplerAllocation(mImplementation.get(), sampler);
Geoff Langc1984ed2016-10-07 12:41:00 -04002418 SetSamplerParameterf(samplerObject, pname, param);
Jamie Madille29d1672013-07-19 16:36:57 -04002419}
2420
Geoff Langc1984ed2016-10-07 12:41:00 -04002421void Context::samplerParameterfv(GLuint sampler, GLenum pname, const GLfloat *param)
Jamie Madill9675b802013-07-19 16:36:59 -04002422{
Geoff Langc1984ed2016-10-07 12:41:00 -04002423 Sampler *samplerObject =
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002424 mState.mSamplers->checkSamplerAllocation(mImplementation.get(), sampler);
Geoff Langc1984ed2016-10-07 12:41:00 -04002425 SetSamplerParameterfv(samplerObject, pname, param);
Jamie Madill9675b802013-07-19 16:36:59 -04002426}
2427
Geoff Langc1984ed2016-10-07 12:41:00 -04002428void Context::getSamplerParameteriv(GLuint sampler, GLenum pname, GLint *params)
Jamie Madill9675b802013-07-19 16:36:59 -04002429{
Geoff Langc1984ed2016-10-07 12:41:00 -04002430 const Sampler *samplerObject =
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002431 mState.mSamplers->checkSamplerAllocation(mImplementation.get(), sampler);
Geoff Langc1984ed2016-10-07 12:41:00 -04002432 QuerySamplerParameteriv(samplerObject, pname, params);
2433}
Jamie Madill9675b802013-07-19 16:36:59 -04002434
Geoff Langc1984ed2016-10-07 12:41:00 -04002435void Context::getSamplerParameterfv(GLuint sampler, GLenum pname, GLfloat *params)
2436{
2437 const Sampler *samplerObject =
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002438 mState.mSamplers->checkSamplerAllocation(mImplementation.get(), sampler);
Geoff Langc1984ed2016-10-07 12:41:00 -04002439 QuerySamplerParameterfv(samplerObject, pname, params);
Jamie Madill9675b802013-07-19 16:36:59 -04002440}
2441
Olli Etuahof0fee072016-03-30 15:11:58 +03002442void Context::programParameteri(GLuint program, GLenum pname, GLint value)
2443{
2444 gl::Program *programObject = getProgram(program);
Yunchao He61afff12017-03-14 15:34:03 +08002445 SetProgramParameteri(programObject, pname, value);
Olli Etuahof0fee072016-03-30 15:11:58 +03002446}
2447
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002448void Context::initRendererString()
2449{
daniel@transgaming.comca1ac1f2013-01-11 04:13:05 +00002450 std::ostringstream rendererString;
2451 rendererString << "ANGLE (";
Jamie Madill53ea9cc2016-05-17 10:12:52 -04002452 rendererString << mImplementation->getRendererDescription();
daniel@transgaming.comca1ac1f2013-01-11 04:13:05 +00002453 rendererString << ")";
2454
Geoff Langcec35902014-04-16 10:52:36 -04002455 mRendererString = MakeStaticString(rendererString.str());
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002456}
2457
Geoff Langc339c4e2016-11-29 10:37:36 -05002458void Context::initVersionStrings()
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002459{
Geoff Langc339c4e2016-11-29 10:37:36 -05002460 const Version &clientVersion = getClientVersion();
2461
2462 std::ostringstream versionString;
2463 versionString << "OpenGL ES " << clientVersion.major << "." << clientVersion.minor << " (ANGLE "
2464 << ANGLE_VERSION_STRING << ")";
2465 mVersionString = MakeStaticString(versionString.str());
2466
2467 std::ostringstream shadingLanguageVersionString;
2468 shadingLanguageVersionString << "OpenGL ES GLSL ES "
2469 << (clientVersion.major == 2 ? 1 : clientVersion.major) << "."
2470 << clientVersion.minor << "0 (ANGLE " << ANGLE_VERSION_STRING
2471 << ")";
2472 mShadingLanguageString = MakeStaticString(shadingLanguageVersionString.str());
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002473}
2474
Geoff Langcec35902014-04-16 10:52:36 -04002475void Context::initExtensionStrings()
2476{
Geoff Langc339c4e2016-11-29 10:37:36 -05002477 auto mergeExtensionStrings = [](const std::vector<const char *> &strings) {
2478 std::ostringstream combinedStringStream;
2479 std::copy(strings.begin(), strings.end(),
2480 std::ostream_iterator<const char *>(combinedStringStream, " "));
2481 return MakeStaticString(combinedStringStream.str());
2482 };
2483
2484 mExtensionStrings.clear();
Geoff Langc287ea62016-09-16 14:46:51 -04002485 for (const auto &extensionString : mExtensions.getStrings())
2486 {
2487 mExtensionStrings.push_back(MakeStaticString(extensionString));
2488 }
Geoff Langc339c4e2016-11-29 10:37:36 -05002489 mExtensionString = mergeExtensionStrings(mExtensionStrings);
Geoff Langcec35902014-04-16 10:52:36 -04002490
Bryan Bernhart58806562017-01-05 13:09:31 -08002491 const gl::Extensions &nativeExtensions = mImplementation->getNativeExtensions();
2492
Geoff Langc339c4e2016-11-29 10:37:36 -05002493 mRequestableExtensionStrings.clear();
2494 for (const auto &extensionInfo : GetExtensionInfoMap())
2495 {
2496 if (extensionInfo.second.Requestable &&
Bryan Bernhart58806562017-01-05 13:09:31 -08002497 !(mExtensions.*(extensionInfo.second.ExtensionsMember)) &&
2498 nativeExtensions.*(extensionInfo.second.ExtensionsMember))
Geoff Langc339c4e2016-11-29 10:37:36 -05002499 {
2500 mRequestableExtensionStrings.push_back(MakeStaticString(extensionInfo.first));
2501 }
2502 }
2503 mRequestableExtensionString = mergeExtensionStrings(mRequestableExtensionStrings);
Geoff Langcec35902014-04-16 10:52:36 -04002504}
2505
Geoff Langc339c4e2016-11-29 10:37:36 -05002506const GLubyte *Context::getString(GLenum name) const
Geoff Langcec35902014-04-16 10:52:36 -04002507{
Geoff Langc339c4e2016-11-29 10:37:36 -05002508 switch (name)
2509 {
2510 case GL_VENDOR:
2511 return reinterpret_cast<const GLubyte *>("Google Inc.");
2512
2513 case GL_RENDERER:
2514 return reinterpret_cast<const GLubyte *>(mRendererString);
2515
2516 case GL_VERSION:
2517 return reinterpret_cast<const GLubyte *>(mVersionString);
2518
2519 case GL_SHADING_LANGUAGE_VERSION:
2520 return reinterpret_cast<const GLubyte *>(mShadingLanguageString);
2521
2522 case GL_EXTENSIONS:
2523 return reinterpret_cast<const GLubyte *>(mExtensionString);
2524
2525 case GL_REQUESTABLE_EXTENSIONS_ANGLE:
2526 return reinterpret_cast<const GLubyte *>(mRequestableExtensionString);
2527
2528 default:
2529 UNREACHABLE();
2530 return nullptr;
2531 }
Geoff Langcec35902014-04-16 10:52:36 -04002532}
2533
Geoff Langc339c4e2016-11-29 10:37:36 -05002534const GLubyte *Context::getStringi(GLenum name, GLuint index) const
Geoff Langcec35902014-04-16 10:52:36 -04002535{
Geoff Langc339c4e2016-11-29 10:37:36 -05002536 switch (name)
2537 {
2538 case GL_EXTENSIONS:
2539 return reinterpret_cast<const GLubyte *>(mExtensionStrings[index]);
2540
2541 case GL_REQUESTABLE_EXTENSIONS_ANGLE:
2542 return reinterpret_cast<const GLubyte *>(mRequestableExtensionStrings[index]);
2543
2544 default:
2545 UNREACHABLE();
2546 return nullptr;
2547 }
Geoff Langcec35902014-04-16 10:52:36 -04002548}
2549
2550size_t Context::getExtensionStringCount() const
2551{
2552 return mExtensionStrings.size();
2553}
2554
Geoff Langc339c4e2016-11-29 10:37:36 -05002555void Context::requestExtension(const char *name)
2556{
2557 const ExtensionInfoMap &extensionInfos = GetExtensionInfoMap();
2558 ASSERT(extensionInfos.find(name) != extensionInfos.end());
2559 const auto &extension = extensionInfos.at(name);
2560 ASSERT(extension.Requestable);
2561
2562 if (mExtensions.*(extension.ExtensionsMember))
2563 {
2564 // Extension already enabled
2565 return;
2566 }
2567
2568 mExtensions.*(extension.ExtensionsMember) = true;
2569 updateCaps();
2570 initExtensionStrings();
Bryan Bernhart58806562017-01-05 13:09:31 -08002571
Jamie Madill2f348d22017-06-05 10:50:59 -04002572 // Release the shader compiler so it will be re-created with the requested extensions enabled.
2573 releaseShaderCompiler();
Geoff Lang9aded172017-04-05 11:07:56 -04002574
2575 // Invalidate all cached completenesses for textures and framebuffer. Some extensions make new
2576 // formats renderable or sampleable.
2577 mState.mTextures->invalidateTextureComplenessCache();
2578 for (auto &zeroTexture : mZeroTextures)
2579 {
2580 zeroTexture.second->invalidateCompletenessCache();
2581 }
2582
2583 mState.mFramebuffers->invalidateFramebufferComplenessCache();
Geoff Langc339c4e2016-11-29 10:37:36 -05002584}
2585
2586size_t Context::getRequestableExtensionStringCount() const
2587{
2588 return mRequestableExtensionStrings.size();
2589}
2590
Olli Etuahoc3e55a42016-03-09 16:29:18 +02002591void Context::beginTransformFeedback(GLenum primitiveMode)
2592{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002593 TransformFeedback *transformFeedback = mGLState.getCurrentTransformFeedback();
Olli Etuahoc3e55a42016-03-09 16:29:18 +02002594 ASSERT(transformFeedback != nullptr);
2595 ASSERT(!transformFeedback->isPaused());
2596
Jamie Madill6c1f6712017-02-14 19:08:04 -05002597 transformFeedback->begin(this, primitiveMode, mGLState.getProgram());
Olli Etuahoc3e55a42016-03-09 16:29:18 +02002598}
2599
2600bool Context::hasActiveTransformFeedback(GLuint program) const
2601{
2602 for (auto pair : mTransformFeedbackMap)
2603 {
2604 if (pair.second != nullptr && pair.second->hasBoundProgram(program))
2605 {
2606 return true;
2607 }
2608 }
2609 return false;
2610}
2611
Jamie Madill4e0e6f82017-02-17 11:06:03 -05002612void Context::initCaps(const egl::DisplayExtensions &displayExtensions)
Geoff Lang493daf52014-07-03 13:38:44 -04002613{
Jamie Madill53ea9cc2016-05-17 10:12:52 -04002614 mCaps = mImplementation->getNativeCaps();
Geoff Lang493daf52014-07-03 13:38:44 -04002615
Jamie Madill53ea9cc2016-05-17 10:12:52 -04002616 mExtensions = mImplementation->getNativeExtensions();
Geoff Lang493daf52014-07-03 13:38:44 -04002617
Jamie Madill53ea9cc2016-05-17 10:12:52 -04002618 mLimitations = mImplementation->getNativeLimitations();
Austin Kinross02df7962015-07-01 10:03:42 -07002619
Geoff Langeb66a6e2016-10-31 13:06:12 -04002620 if (getClientVersion() < Version(3, 0))
Geoff Lang493daf52014-07-03 13:38:44 -04002621 {
2622 // Disable ES3+ extensions
Jamie Madill231c7f52017-04-26 13:45:37 -04002623 mExtensions.colorBufferFloat = false;
Geoff Langb66a9092016-05-16 15:59:14 -04002624 mExtensions.eglImageExternalEssl3 = false;
Vincent Lang25ab4512016-05-13 18:13:59 +02002625 mExtensions.textureNorm16 = false;
Martin Radev137032d2017-07-13 10:11:12 +03002626 mExtensions.multiview = false;
2627 mExtensions.maxViews = 1u;
Geoff Lang493daf52014-07-03 13:38:44 -04002628 }
2629
Geoff Langeb66a6e2016-10-31 13:06:12 -04002630 if (getClientVersion() > Version(2, 0))
Geoff Lang493daf52014-07-03 13:38:44 -04002631 {
2632 // FIXME(geofflang): Don't support EXT_sRGB in non-ES2 contexts
Jamie Madill231c7f52017-04-26 13:45:37 -04002633 // mExtensions.sRGB = false;
Geoff Lang493daf52014-07-03 13:38:44 -04002634 }
2635
Jamie Madill00ed7a12016-05-19 13:13:38 -04002636 // Some extensions are always available because they are implemented in the GL layer.
Jamie Madill231c7f52017-04-26 13:45:37 -04002637 mExtensions.bindUniformLocation = true;
2638 mExtensions.vertexArrayObject = true;
Geoff Langf41a7152016-09-19 15:11:17 -04002639 mExtensions.bindGeneratesResource = true;
Geoff Langfeb8c682017-02-13 16:07:35 -05002640 mExtensions.clientArrays = true;
Geoff Langc339c4e2016-11-29 10:37:36 -05002641 mExtensions.requestExtension = true;
Jamie Madill00ed7a12016-05-19 13:13:38 -04002642
2643 // Enable the no error extension if the context was created with the flag.
2644 mExtensions.noError = mSkipValidation;
2645
Corentin Wallezccab69d2017-01-27 16:57:15 -05002646 // Enable surfaceless to advertise we'll have the correct behavior when there is no default FBO
Corentin Wallezc295e512017-01-27 17:47:50 -05002647 mExtensions.surfacelessContext = displayExtensions.surfacelessContext;
Corentin Wallezccab69d2017-01-27 16:57:15 -05002648
Geoff Lang70d0f492015-12-10 17:45:46 -05002649 // Explicitly enable GL_KHR_debug
2650 mExtensions.debug = true;
2651 mExtensions.maxDebugMessageLength = 1024;
2652 mExtensions.maxDebugLoggedMessages = 1024;
2653 mExtensions.maxDebugGroupStackDepth = 1024;
2654 mExtensions.maxLabelLength = 1024;
2655
Geoff Langff5b2d52016-09-07 11:32:23 -04002656 // Explicitly enable GL_ANGLE_robust_client_memory
2657 mExtensions.robustClientMemory = true;
2658
Jamie Madille08a1d32017-03-07 17:24:06 -05002659 // Determine robust resource init availability from EGL.
2660 mExtensions.robustResourceInitialization =
Jamie Madill948bbe52017-06-01 13:10:42 -04002661 egl::Display::GetClientExtensions().displayRobustResourceInitialization;
Jamie Madille08a1d32017-03-07 17:24:06 -05002662
Jamie Madillc43be722017-07-13 16:22:14 -04002663 // Enable the cache control query unconditionally.
2664 mExtensions.programCacheControl = true;
2665
Geoff Lang301d1612014-07-09 10:34:37 -04002666 // Apply implementation limits
2667 mCaps.maxVertexAttributes = std::min<GLuint>(mCaps.maxVertexAttributes, MAX_VERTEX_ATTRIBS);
Jiawei-Shao2597fb62016-12-09 16:38:02 +08002668 mCaps.maxVertexAttribBindings =
2669 getClientVersion() < ES_3_1
2670 ? mCaps.maxVertexAttributes
2671 : std::min<GLuint>(mCaps.maxVertexAttribBindings, MAX_VERTEX_ATTRIB_BINDINGS);
2672
Jamie Madill231c7f52017-04-26 13:45:37 -04002673 mCaps.maxVertexUniformBlocks = std::min<GLuint>(
2674 mCaps.maxVertexUniformBlocks, IMPLEMENTATION_MAX_VERTEX_SHADER_UNIFORM_BUFFERS);
2675 mCaps.maxVertexOutputComponents =
2676 std::min<GLuint>(mCaps.maxVertexOutputComponents, IMPLEMENTATION_MAX_VARYING_VECTORS * 4);
Geoff Lang301d1612014-07-09 10:34:37 -04002677
Jamie Madill231c7f52017-04-26 13:45:37 -04002678 mCaps.maxFragmentInputComponents =
2679 std::min<GLuint>(mCaps.maxFragmentInputComponents, IMPLEMENTATION_MAX_VARYING_VECTORS * 4);
Geoff Lang3a61c322014-07-10 13:01:54 -04002680
Geoff Langc287ea62016-09-16 14:46:51 -04002681 // WebGL compatibility
Jamie Madill4e0e6f82017-02-17 11:06:03 -05002682 mExtensions.webglCompatibility = mWebGLContext;
Geoff Langc287ea62016-09-16 14:46:51 -04002683 for (const auto &extensionInfo : GetExtensionInfoMap())
2684 {
2685 // If this context is for WebGL, disable all enableable extensions
Jamie Madill4e0e6f82017-02-17 11:06:03 -05002686 if (mWebGLContext && extensionInfo.second.Requestable)
Geoff Langc287ea62016-09-16 14:46:51 -04002687 {
2688 mExtensions.*(extensionInfo.second.ExtensionsMember) = false;
2689 }
2690 }
2691
2692 // Generate texture caps
2693 updateCaps();
2694}
2695
2696void Context::updateCaps()
2697{
Geoff Lang900013c2014-07-07 11:32:19 -04002698 mCaps.compressedTextureFormats.clear();
Geoff Langc287ea62016-09-16 14:46:51 -04002699 mTextureCaps.clear();
Geoff Lang900013c2014-07-07 11:32:19 -04002700
Jamie Madill4e0e6f82017-02-17 11:06:03 -05002701 for (auto capsIt : mImplementation->getNativeTextureCaps())
Geoff Lang493daf52014-07-03 13:38:44 -04002702 {
Geoff Langca271392017-04-05 12:30:00 -04002703 GLenum sizedInternalFormat = capsIt.first;
Jamie Madill231c7f52017-04-26 13:45:37 -04002704 TextureCaps formatCaps = capsIt.second;
Geoff Lang493daf52014-07-03 13:38:44 -04002705
Geoff Langca271392017-04-05 12:30:00 -04002706 const InternalFormat &formatInfo = GetSizedInternalFormatInfo(sizedInternalFormat);
Geoff Langd87878e2014-09-19 15:42:59 -04002707
Geoff Lang0d8b7242015-09-09 14:56:53 -04002708 // Update the format caps based on the client version and extensions.
2709 // Caps are AND'd with the renderer caps because some core formats are still unsupported in
2710 // ES3.
2711 formatCaps.texturable =
Geoff Langeb66a6e2016-10-31 13:06:12 -04002712 formatCaps.texturable && formatInfo.textureSupport(getClientVersion(), mExtensions);
Geoff Lang0d8b7242015-09-09 14:56:53 -04002713 formatCaps.renderable =
Geoff Langeb66a6e2016-10-31 13:06:12 -04002714 formatCaps.renderable && formatInfo.renderSupport(getClientVersion(), mExtensions);
Geoff Lang0d8b7242015-09-09 14:56:53 -04002715 formatCaps.filterable =
Geoff Langeb66a6e2016-10-31 13:06:12 -04002716 formatCaps.filterable && formatInfo.filterSupport(getClientVersion(), mExtensions);
Geoff Langd87878e2014-09-19 15:42:59 -04002717
He Yunchaoccd8c9b2017-01-18 17:36:14 +08002718 // OpenGL ES does not support multisampling with non-rendererable formats
2719 // OpenGL ES 3.0 or prior does not support multisampling with integer formats
Olli Etuaho50c562d2017-06-06 14:43:30 +03002720 if (!formatCaps.renderable ||
He Yunchaoccd8c9b2017-01-18 17:36:14 +08002721 (getClientVersion() < ES_3_1 &&
2722 (formatInfo.componentType == GL_INT || formatInfo.componentType == GL_UNSIGNED_INT)))
Geoff Lang493daf52014-07-03 13:38:44 -04002723 {
Geoff Langd87878e2014-09-19 15:42:59 -04002724 formatCaps.sampleCounts.clear();
Geoff Lang493daf52014-07-03 13:38:44 -04002725 }
Olli Etuaho50c562d2017-06-06 14:43:30 +03002726 else
2727 {
2728 // We may have limited the max samples for some required renderbuffer formats due to
2729 // non-conformant formats. In this case MAX_SAMPLES needs to be lowered accordingly.
2730 GLuint formatMaxSamples = formatCaps.getMaxSamples();
2731
2732 // GLES 3.0.5 section 4.4.2.2: "Implementations must support creation of renderbuffers
2733 // in these required formats with up to the value of MAX_SAMPLES multisamples, with the
2734 // exception of signed and unsigned integer formats."
2735 if (formatInfo.componentType != GL_INT && formatInfo.componentType != GL_UNSIGNED_INT &&
2736 formatInfo.isRequiredRenderbufferFormat(getClientVersion()))
2737 {
2738 ASSERT(getClientVersion() < ES_3_0 || formatMaxSamples >= 4);
2739 mCaps.maxSamples = std::min(mCaps.maxSamples, formatMaxSamples);
2740 }
2741
2742 // Handle GLES 3.1 MAX_*_SAMPLES values similarly to MAX_SAMPLES.
2743 if (getClientVersion() >= ES_3_1)
2744 {
2745 // GLES 3.1 section 9.2.5: "Implementations must support creation of renderbuffers
2746 // in these required formats with up to the value of MAX_SAMPLES multisamples, with
2747 // the exception that the signed and unsigned integer formats are required only to
2748 // support creation of renderbuffers with up to the value of MAX_INTEGER_SAMPLES
2749 // multisamples, which must be at least one."
2750 if (formatInfo.componentType == GL_INT ||
2751 formatInfo.componentType == GL_UNSIGNED_INT)
2752 {
2753 mCaps.maxIntegerSamples = std::min(mCaps.maxIntegerSamples, formatMaxSamples);
2754 }
2755
2756 // GLES 3.1 section 19.3.1.
2757 if (formatCaps.texturable)
2758 {
2759 if (formatInfo.depthBits > 0)
2760 {
2761 mCaps.maxDepthTextureSamples =
2762 std::min(mCaps.maxDepthTextureSamples, formatMaxSamples);
2763 }
2764 else if (formatInfo.redBits > 0)
2765 {
2766 mCaps.maxColorTextureSamples =
2767 std::min(mCaps.maxColorTextureSamples, formatMaxSamples);
2768 }
2769 }
2770 }
2771 }
Geoff Langd87878e2014-09-19 15:42:59 -04002772
2773 if (formatCaps.texturable && formatInfo.compressed)
2774 {
Geoff Langca271392017-04-05 12:30:00 -04002775 mCaps.compressedTextureFormats.push_back(sizedInternalFormat);
Geoff Langd87878e2014-09-19 15:42:59 -04002776 }
2777
Geoff Langca271392017-04-05 12:30:00 -04002778 mTextureCaps.insert(sizedInternalFormat, formatCaps);
Geoff Lang493daf52014-07-03 13:38:44 -04002779 }
Jamie Madill32447362017-06-28 14:53:52 -04002780
2781 // If program binary is disabled, blank out the memory cache pointer.
2782 if (!mImplementation->getNativeExtensions().getProgramBinary)
2783 {
2784 mMemoryProgramCache = nullptr;
2785 }
Geoff Lang493daf52014-07-03 13:38:44 -04002786}
2787
Kenneth Russellf2f6f652016-10-05 19:53:23 -07002788void Context::initWorkarounds()
2789{
Jamie Madill761b02c2017-06-23 16:27:06 -04002790 // Apply back-end workarounds.
2791 mImplementation->applyNativeWorkarounds(&mWorkarounds);
2792
Kenneth Russellf2f6f652016-10-05 19:53:23 -07002793 // Lose the context upon out of memory error if the application is
2794 // expecting to watch for those events.
2795 mWorkarounds.loseContextOnOutOfMemory = (mResetStrategy == GL_LOSE_CONTEXT_ON_RESET_EXT);
2796}
2797
Jamie Madill4c19a8a2017-07-24 11:46:06 -04002798Error Context::prepareForDraw(GLenum drawMode)
Jamie Madillb6664922017-07-25 12:55:04 -04002799{
2800 syncRendererState();
Jamie Madill4c19a8a2017-07-24 11:46:06 -04002801
2802 InfoLog infoLog;
2803 Error err = mImplementation->triggerDrawCallProgramRecompilation(this, &infoLog,
2804 mMemoryProgramCache, drawMode);
Jamie Madilla836b462017-08-16 14:58:35 -04002805 if (err.isError() || infoLog.getLength() > 0)
Jamie Madill4c19a8a2017-07-24 11:46:06 -04002806 {
2807 WARN() << "Dynamic recompilation error log: " << infoLog.str();
2808 }
2809 return err;
Jamie Madillb6664922017-07-25 12:55:04 -04002810}
2811
Jamie Madill1b94d432015-08-07 13:23:23 -04002812void Context::syncRendererState()
2813{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002814 const State::DirtyBits &dirtyBits = mGLState.getDirtyBits();
Jamie Madillfe548342017-06-19 11:13:24 -04002815 mImplementation->syncState(this, dirtyBits);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002816 mGLState.clearDirtyBits();
Jamie Madilldd43e6c2017-03-24 14:18:49 -04002817 mGLState.syncDirtyObjects(this);
Jamie Madill1b94d432015-08-07 13:23:23 -04002818}
2819
Jamie Madillad9f24e2016-02-12 09:27:24 -05002820void Context::syncRendererState(const State::DirtyBits &bitMask,
2821 const State::DirtyObjects &objectMask)
Jamie Madill1b94d432015-08-07 13:23:23 -04002822{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002823 const State::DirtyBits &dirtyBits = (mGLState.getDirtyBits() & bitMask);
Jamie Madillfe548342017-06-19 11:13:24 -04002824 mImplementation->syncState(this, dirtyBits);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002825 mGLState.clearDirtyBits(dirtyBits);
Jamie Madilldd43e6c2017-03-24 14:18:49 -04002826 mGLState.syncDirtyObjects(this, objectMask);
Jamie Madill1b94d432015-08-07 13:23:23 -04002827}
Jamie Madillc29968b2016-01-20 11:17:23 -05002828
2829void Context::blitFramebuffer(GLint srcX0,
2830 GLint srcY0,
2831 GLint srcX1,
2832 GLint srcY1,
2833 GLint dstX0,
2834 GLint dstY0,
2835 GLint dstX1,
2836 GLint dstY1,
2837 GLbitfield mask,
2838 GLenum filter)
2839{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002840 Framebuffer *drawFramebuffer = mGLState.getDrawFramebuffer();
Jamie Madillc29968b2016-01-20 11:17:23 -05002841 ASSERT(drawFramebuffer);
2842
2843 Rectangle srcArea(srcX0, srcY0, srcX1 - srcX0, srcY1 - srcY0);
2844 Rectangle dstArea(dstX0, dstY0, dstX1 - dstX0, dstY1 - dstY0);
2845
Jamie Madillad9f24e2016-02-12 09:27:24 -05002846 syncStateForBlit();
Jamie Madillc29968b2016-01-20 11:17:23 -05002847
Jamie Madillc564c072017-06-01 12:45:42 -04002848 handleError(drawFramebuffer->blit(this, srcArea, dstArea, mask, filter));
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002849}
Jamie Madillc29968b2016-01-20 11:17:23 -05002850
2851void Context::clear(GLbitfield mask)
2852{
Jamie Madillad9f24e2016-02-12 09:27:24 -05002853 syncStateForClear();
Jamie Madillc564c072017-06-01 12:45:42 -04002854 handleError(mGLState.getDrawFramebuffer()->clear(this, mask));
Jamie Madillc29968b2016-01-20 11:17:23 -05002855}
2856
2857void Context::clearBufferfv(GLenum buffer, GLint drawbuffer, const GLfloat *values)
2858{
Jamie Madillad9f24e2016-02-12 09:27:24 -05002859 syncStateForClear();
Jamie Madillc564c072017-06-01 12:45:42 -04002860 handleError(mGLState.getDrawFramebuffer()->clearBufferfv(this, buffer, drawbuffer, values));
Jamie Madillc29968b2016-01-20 11:17:23 -05002861}
2862
2863void Context::clearBufferuiv(GLenum buffer, GLint drawbuffer, const GLuint *values)
2864{
Jamie Madillad9f24e2016-02-12 09:27:24 -05002865 syncStateForClear();
Jamie Madillc564c072017-06-01 12:45:42 -04002866 handleError(mGLState.getDrawFramebuffer()->clearBufferuiv(this, buffer, drawbuffer, values));
Jamie Madillc29968b2016-01-20 11:17:23 -05002867}
2868
2869void Context::clearBufferiv(GLenum buffer, GLint drawbuffer, const GLint *values)
2870{
Jamie Madillad9f24e2016-02-12 09:27:24 -05002871 syncStateForClear();
Jamie Madillc564c072017-06-01 12:45:42 -04002872 handleError(mGLState.getDrawFramebuffer()->clearBufferiv(this, buffer, drawbuffer, values));
Jamie Madillc29968b2016-01-20 11:17:23 -05002873}
2874
2875void Context::clearBufferfi(GLenum buffer, GLint drawbuffer, GLfloat depth, GLint stencil)
2876{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002877 Framebuffer *framebufferObject = mGLState.getDrawFramebuffer();
Jamie Madillc29968b2016-01-20 11:17:23 -05002878 ASSERT(framebufferObject);
2879
2880 // If a buffer is not present, the clear has no effect
2881 if (framebufferObject->getDepthbuffer() == nullptr &&
2882 framebufferObject->getStencilbuffer() == nullptr)
2883 {
2884 return;
2885 }
2886
Jamie Madillad9f24e2016-02-12 09:27:24 -05002887 syncStateForClear();
Jamie Madillc564c072017-06-01 12:45:42 -04002888 handleError(framebufferObject->clearBufferfi(this, buffer, drawbuffer, depth, stencil));
Jamie Madillc29968b2016-01-20 11:17:23 -05002889}
2890
2891void Context::readPixels(GLint x,
2892 GLint y,
2893 GLsizei width,
2894 GLsizei height,
2895 GLenum format,
2896 GLenum type,
Jamie Madill876429b2017-04-20 15:46:24 -04002897 void *pixels)
Jamie Madillc29968b2016-01-20 11:17:23 -05002898{
Corentin Wallez9a8d3662016-09-22 12:18:29 -04002899 if (width == 0 || height == 0)
2900 {
2901 return;
2902 }
2903
Jamie Madillad9f24e2016-02-12 09:27:24 -05002904 syncStateForReadPixels();
Jamie Madillc29968b2016-01-20 11:17:23 -05002905
Jamie Madillb6664922017-07-25 12:55:04 -04002906 Framebuffer *readFBO = mGLState.getReadFramebuffer();
2907 ASSERT(readFBO);
Jamie Madillc29968b2016-01-20 11:17:23 -05002908
2909 Rectangle area(x, y, width, height);
Jamie Madillb6664922017-07-25 12:55:04 -04002910 handleError(readFBO->readPixels(this, area, format, type, pixels));
Jamie Madillc29968b2016-01-20 11:17:23 -05002911}
2912
2913void Context::copyTexImage2D(GLenum target,
2914 GLint level,
2915 GLenum internalformat,
2916 GLint x,
2917 GLint y,
2918 GLsizei width,
2919 GLsizei height,
2920 GLint border)
2921{
Jamie Madill60ec6ea2016-01-22 15:27:19 -05002922 // Only sync the read FBO
Jamie Madilldd43e6c2017-03-24 14:18:49 -04002923 mGLState.syncDirtyObject(this, GL_READ_FRAMEBUFFER);
Jamie Madill60ec6ea2016-01-22 15:27:19 -05002924
Jamie Madillc29968b2016-01-20 11:17:23 -05002925 Rectangle sourceArea(x, y, width, height);
2926
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002927 const Framebuffer *framebuffer = mGLState.getReadFramebuffer();
Jamie Madillc29968b2016-01-20 11:17:23 -05002928 Texture *texture =
2929 getTargetTexture(IsCubeMapTextureTarget(target) ? GL_TEXTURE_CUBE_MAP : target);
Jamie Madill8897afa2017-02-06 17:17:23 -05002930 handleError(texture->copyImage(this, target, level, sourceArea, internalformat, framebuffer));
Jamie Madillc29968b2016-01-20 11:17:23 -05002931}
2932
2933void Context::copyTexSubImage2D(GLenum target,
2934 GLint level,
2935 GLint xoffset,
2936 GLint yoffset,
2937 GLint x,
2938 GLint y,
2939 GLsizei width,
2940 GLsizei height)
2941{
Corentin Wallez9a8d3662016-09-22 12:18:29 -04002942 if (width == 0 || height == 0)
2943 {
2944 return;
2945 }
2946
Jamie Madill60ec6ea2016-01-22 15:27:19 -05002947 // Only sync the read FBO
Jamie Madilldd43e6c2017-03-24 14:18:49 -04002948 mGLState.syncDirtyObject(this, GL_READ_FRAMEBUFFER);
Jamie Madill60ec6ea2016-01-22 15:27:19 -05002949
Jamie Madillc29968b2016-01-20 11:17:23 -05002950 Offset destOffset(xoffset, yoffset, 0);
2951 Rectangle sourceArea(x, y, width, height);
2952
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002953 const Framebuffer *framebuffer = mGLState.getReadFramebuffer();
Jamie Madillc29968b2016-01-20 11:17:23 -05002954 Texture *texture =
2955 getTargetTexture(IsCubeMapTextureTarget(target) ? GL_TEXTURE_CUBE_MAP : target);
Jamie Madill8897afa2017-02-06 17:17:23 -05002956 handleError(texture->copySubImage(this, target, level, destOffset, sourceArea, framebuffer));
Jamie Madillc29968b2016-01-20 11:17:23 -05002957}
2958
2959void Context::copyTexSubImage3D(GLenum target,
2960 GLint level,
2961 GLint xoffset,
2962 GLint yoffset,
2963 GLint zoffset,
2964 GLint x,
2965 GLint y,
2966 GLsizei width,
2967 GLsizei height)
2968{
Corentin Wallez9a8d3662016-09-22 12:18:29 -04002969 if (width == 0 || height == 0)
2970 {
2971 return;
2972 }
2973
Jamie Madill60ec6ea2016-01-22 15:27:19 -05002974 // Only sync the read FBO
Jamie Madilldd43e6c2017-03-24 14:18:49 -04002975 mGLState.syncDirtyObject(this, GL_READ_FRAMEBUFFER);
Jamie Madill60ec6ea2016-01-22 15:27:19 -05002976
Jamie Madillc29968b2016-01-20 11:17:23 -05002977 Offset destOffset(xoffset, yoffset, zoffset);
2978 Rectangle sourceArea(x, y, width, height);
2979
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002980 const Framebuffer *framebuffer = mGLState.getReadFramebuffer();
Jamie Madillc29968b2016-01-20 11:17:23 -05002981 Texture *texture = getTargetTexture(target);
Jamie Madill8897afa2017-02-06 17:17:23 -05002982 handleError(texture->copySubImage(this, target, level, destOffset, sourceArea, framebuffer));
Jamie Madillc29968b2016-01-20 11:17:23 -05002983}
2984
2985void Context::framebufferTexture2D(GLenum target,
2986 GLenum attachment,
2987 GLenum textarget,
2988 GLuint texture,
2989 GLint level)
2990{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002991 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05002992 ASSERT(framebuffer);
2993
2994 if (texture != 0)
2995 {
2996 Texture *textureObj = getTexture(texture);
2997
2998 ImageIndex index = ImageIndex::MakeInvalid();
2999
3000 if (textarget == GL_TEXTURE_2D)
3001 {
3002 index = ImageIndex::Make2D(level);
3003 }
Corentin Wallez13c0dd42017-07-04 18:27:01 -04003004 else if (textarget == GL_TEXTURE_RECTANGLE_ANGLE)
3005 {
3006 index = ImageIndex::MakeRectangle(level);
3007 }
JiangYizhoubddc46b2016-12-09 09:50:51 +08003008 else if (textarget == GL_TEXTURE_2D_MULTISAMPLE)
3009 {
3010 ASSERT(level == 0);
3011 index = ImageIndex::Make2DMultisample();
3012 }
Jamie Madillc29968b2016-01-20 11:17:23 -05003013 else
3014 {
3015 ASSERT(IsCubeMapTextureTarget(textarget));
3016 index = ImageIndex::MakeCube(textarget, level);
3017 }
3018
Jamie Madilla02315b2017-02-23 14:14:47 -05003019 framebuffer->setAttachment(this, GL_TEXTURE, attachment, index, textureObj);
Jamie Madillc29968b2016-01-20 11:17:23 -05003020 }
3021 else
3022 {
Jamie Madilla02315b2017-02-23 14:14:47 -05003023 framebuffer->resetAttachment(this, attachment);
Jamie Madillc29968b2016-01-20 11:17:23 -05003024 }
Jamie Madill60ec6ea2016-01-22 15:27:19 -05003025
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003026 mGLState.setObjectDirty(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05003027}
3028
3029void Context::framebufferRenderbuffer(GLenum target,
3030 GLenum attachment,
3031 GLenum renderbuffertarget,
3032 GLuint renderbuffer)
3033{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003034 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05003035 ASSERT(framebuffer);
3036
3037 if (renderbuffer != 0)
3038 {
3039 Renderbuffer *renderbufferObject = getRenderbuffer(renderbuffer);
Jamie Madilla02315b2017-02-23 14:14:47 -05003040
3041 framebuffer->setAttachment(this, GL_RENDERBUFFER, attachment, gl::ImageIndex::MakeInvalid(),
Jamie Madillc29968b2016-01-20 11:17:23 -05003042 renderbufferObject);
3043 }
3044 else
3045 {
Jamie Madilla02315b2017-02-23 14:14:47 -05003046 framebuffer->resetAttachment(this, attachment);
Jamie Madillc29968b2016-01-20 11:17:23 -05003047 }
Jamie Madill60ec6ea2016-01-22 15:27:19 -05003048
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003049 mGLState.setObjectDirty(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05003050}
3051
3052void Context::framebufferTextureLayer(GLenum target,
3053 GLenum attachment,
3054 GLuint texture,
3055 GLint level,
3056 GLint layer)
3057{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003058 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05003059 ASSERT(framebuffer);
3060
3061 if (texture != 0)
3062 {
3063 Texture *textureObject = getTexture(texture);
3064
3065 ImageIndex index = ImageIndex::MakeInvalid();
3066
3067 if (textureObject->getTarget() == GL_TEXTURE_3D)
3068 {
3069 index = ImageIndex::Make3D(level, layer);
3070 }
3071 else
3072 {
3073 ASSERT(textureObject->getTarget() == GL_TEXTURE_2D_ARRAY);
3074 index = ImageIndex::Make2DArray(level, layer);
3075 }
3076
Jamie Madilla02315b2017-02-23 14:14:47 -05003077 framebuffer->setAttachment(this, GL_TEXTURE, attachment, index, textureObject);
Jamie Madillc29968b2016-01-20 11:17:23 -05003078 }
3079 else
3080 {
Jamie Madilla02315b2017-02-23 14:14:47 -05003081 framebuffer->resetAttachment(this, attachment);
Jamie Madillc29968b2016-01-20 11:17:23 -05003082 }
Jamie Madill60ec6ea2016-01-22 15:27:19 -05003083
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003084 mGLState.setObjectDirty(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05003085}
3086
Martin Radev137032d2017-07-13 10:11:12 +03003087void Context::framebufferTextureMultiviewLayeredANGLE(GLenum target,
3088 GLenum attachment,
3089 GLuint texture,
3090 GLint level,
3091 GLint baseViewIndex,
3092 GLsizei numViews)
3093{
Martin Radev82ef7742017-08-08 17:44:58 +03003094 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
3095 ASSERT(framebuffer);
3096
3097 if (texture != 0)
3098 {
3099 Texture *textureObj = getTexture(texture);
3100
3101 ImageIndex index = ImageIndex::Make2DArray(level, baseViewIndex);
3102 framebuffer->setAttachmentMultiviewLayered(this, GL_TEXTURE, attachment, index, textureObj,
3103 numViews, baseViewIndex);
3104 }
3105 else
3106 {
3107 framebuffer->resetAttachment(this, attachment);
3108 }
3109
3110 mGLState.setObjectDirty(target);
Martin Radev137032d2017-07-13 10:11:12 +03003111}
3112
3113void Context::framebufferTextureMultiviewSideBySideANGLE(GLenum target,
3114 GLenum attachment,
3115 GLuint texture,
3116 GLint level,
3117 GLsizei numViews,
3118 const GLint *viewportOffsets)
3119{
Martin Radev5dae57b2017-07-14 16:15:55 +03003120 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
3121 ASSERT(framebuffer);
3122
3123 if (texture != 0)
3124 {
3125 Texture *textureObj = getTexture(texture);
3126
3127 ImageIndex index = ImageIndex::Make2D(level);
3128 framebuffer->setAttachmentMultiviewSideBySide(this, GL_TEXTURE, attachment, index,
3129 textureObj, numViews, viewportOffsets);
3130 }
3131 else
3132 {
3133 framebuffer->resetAttachment(this, attachment);
3134 }
3135
3136 mGLState.setObjectDirty(target);
Martin Radev137032d2017-07-13 10:11:12 +03003137}
3138
Jamie Madillc29968b2016-01-20 11:17:23 -05003139void Context::drawBuffers(GLsizei n, const GLenum *bufs)
3140{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003141 Framebuffer *framebuffer = mGLState.getDrawFramebuffer();
Jamie Madillc29968b2016-01-20 11:17:23 -05003142 ASSERT(framebuffer);
3143 framebuffer->setDrawBuffers(n, bufs);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003144 mGLState.setObjectDirty(GL_DRAW_FRAMEBUFFER);
Jamie Madillc29968b2016-01-20 11:17:23 -05003145}
3146
3147void Context::readBuffer(GLenum mode)
3148{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003149 Framebuffer *readFBO = mGLState.getReadFramebuffer();
Jamie Madillc29968b2016-01-20 11:17:23 -05003150 readFBO->setReadBuffer(mode);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003151 mGLState.setObjectDirty(GL_READ_FRAMEBUFFER);
Jamie Madillc29968b2016-01-20 11:17:23 -05003152}
3153
3154void Context::discardFramebuffer(GLenum target, GLsizei numAttachments, const GLenum *attachments)
3155{
Jamie Madill60ec6ea2016-01-22 15:27:19 -05003156 // Only sync the FBO
Jamie Madilldd43e6c2017-03-24 14:18:49 -04003157 mGLState.syncDirtyObject(this, target);
Jamie Madill60ec6ea2016-01-22 15:27:19 -05003158
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003159 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05003160 ASSERT(framebuffer);
3161
3162 // The specification isn't clear what should be done when the framebuffer isn't complete.
3163 // We leave it up to the framebuffer implementation to decide what to do.
Jamie Madill4928b7c2017-06-20 12:57:39 -04003164 handleError(framebuffer->discard(this, numAttachments, attachments));
Jamie Madillc29968b2016-01-20 11:17:23 -05003165}
3166
3167void Context::invalidateFramebuffer(GLenum target,
3168 GLsizei numAttachments,
3169 const GLenum *attachments)
3170{
Jamie Madill60ec6ea2016-01-22 15:27:19 -05003171 // Only sync the FBO
Jamie Madilldd43e6c2017-03-24 14:18:49 -04003172 mGLState.syncDirtyObject(this, target);
Jamie Madill60ec6ea2016-01-22 15:27:19 -05003173
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003174 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05003175 ASSERT(framebuffer);
3176
Jamie Madilldd43e6c2017-03-24 14:18:49 -04003177 if (framebuffer->checkStatus(this) != GL_FRAMEBUFFER_COMPLETE)
Jamie Madillc29968b2016-01-20 11:17:23 -05003178 {
Jamie Madill437fa652016-05-03 15:13:24 -04003179 return;
Jamie Madillc29968b2016-01-20 11:17:23 -05003180 }
Jamie Madill437fa652016-05-03 15:13:24 -04003181
Jamie Madill4928b7c2017-06-20 12:57:39 -04003182 handleError(framebuffer->invalidate(this, numAttachments, attachments));
Jamie Madillc29968b2016-01-20 11:17:23 -05003183}
3184
3185void Context::invalidateSubFramebuffer(GLenum target,
3186 GLsizei numAttachments,
3187 const GLenum *attachments,
3188 GLint x,
3189 GLint y,
3190 GLsizei width,
3191 GLsizei height)
3192{
Jamie Madill60ec6ea2016-01-22 15:27:19 -05003193 // Only sync the FBO
Jamie Madilldd43e6c2017-03-24 14:18:49 -04003194 mGLState.syncDirtyObject(this, target);
Jamie Madill60ec6ea2016-01-22 15:27:19 -05003195
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003196 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05003197 ASSERT(framebuffer);
3198
Jamie Madilldd43e6c2017-03-24 14:18:49 -04003199 if (framebuffer->checkStatus(this) != GL_FRAMEBUFFER_COMPLETE)
Jamie Madillc29968b2016-01-20 11:17:23 -05003200 {
Jamie Madill437fa652016-05-03 15:13:24 -04003201 return;
Jamie Madillc29968b2016-01-20 11:17:23 -05003202 }
Jamie Madill437fa652016-05-03 15:13:24 -04003203
3204 Rectangle area(x, y, width, height);
Jamie Madill4928b7c2017-06-20 12:57:39 -04003205 handleError(framebuffer->invalidateSub(this, numAttachments, attachments, area));
Jamie Madillc29968b2016-01-20 11:17:23 -05003206}
3207
Jamie Madill73a84962016-02-12 09:27:23 -05003208void Context::texImage2D(GLenum target,
3209 GLint level,
3210 GLint internalformat,
3211 GLsizei width,
3212 GLsizei height,
3213 GLint border,
3214 GLenum format,
3215 GLenum type,
Jamie Madill876429b2017-04-20 15:46:24 -04003216 const void *pixels)
Jamie Madill73a84962016-02-12 09:27:23 -05003217{
Jamie Madillad9f24e2016-02-12 09:27:24 -05003218 syncStateForTexImage();
Jamie Madill73a84962016-02-12 09:27:23 -05003219
3220 Extents size(width, height, 1);
3221 Texture *texture =
3222 getTargetTexture(IsCubeMapTextureTarget(target) ? GL_TEXTURE_CUBE_MAP : target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003223 handleError(texture->setImage(this, mGLState.getUnpackState(), target, level, internalformat,
3224 size, format, type, reinterpret_cast<const uint8_t *>(pixels)));
Jamie Madill73a84962016-02-12 09:27:23 -05003225}
3226
3227void Context::texImage3D(GLenum target,
3228 GLint level,
3229 GLint internalformat,
3230 GLsizei width,
3231 GLsizei height,
3232 GLsizei depth,
3233 GLint border,
3234 GLenum format,
3235 GLenum type,
Jamie Madill876429b2017-04-20 15:46:24 -04003236 const void *pixels)
Jamie Madill73a84962016-02-12 09:27:23 -05003237{
Jamie Madillad9f24e2016-02-12 09:27:24 -05003238 syncStateForTexImage();
Jamie Madill73a84962016-02-12 09:27:23 -05003239
3240 Extents size(width, height, depth);
3241 Texture *texture = getTargetTexture(target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003242 handleError(texture->setImage(this, mGLState.getUnpackState(), target, level, internalformat,
3243 size, format, type, reinterpret_cast<const uint8_t *>(pixels)));
Jamie Madill73a84962016-02-12 09:27:23 -05003244}
3245
3246void Context::texSubImage2D(GLenum target,
3247 GLint level,
3248 GLint xoffset,
3249 GLint yoffset,
3250 GLsizei width,
3251 GLsizei height,
3252 GLenum format,
3253 GLenum type,
Jamie Madill876429b2017-04-20 15:46:24 -04003254 const void *pixels)
Jamie Madill73a84962016-02-12 09:27:23 -05003255{
3256 // Zero sized uploads are valid but no-ops
3257 if (width == 0 || height == 0)
3258 {
3259 return;
3260 }
3261
Jamie Madillad9f24e2016-02-12 09:27:24 -05003262 syncStateForTexImage();
Jamie Madill73a84962016-02-12 09:27:23 -05003263
3264 Box area(xoffset, yoffset, 0, width, height, 1);
3265 Texture *texture =
3266 getTargetTexture(IsCubeMapTextureTarget(target) ? GL_TEXTURE_CUBE_MAP : target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003267 handleError(texture->setSubImage(this, mGLState.getUnpackState(), target, level, area, format,
3268 type, reinterpret_cast<const uint8_t *>(pixels)));
Jamie Madill73a84962016-02-12 09:27:23 -05003269}
3270
3271void Context::texSubImage3D(GLenum target,
3272 GLint level,
3273 GLint xoffset,
3274 GLint yoffset,
3275 GLint zoffset,
3276 GLsizei width,
3277 GLsizei height,
3278 GLsizei depth,
3279 GLenum format,
3280 GLenum type,
Jamie Madill876429b2017-04-20 15:46:24 -04003281 const void *pixels)
Jamie Madill73a84962016-02-12 09:27:23 -05003282{
3283 // Zero sized uploads are valid but no-ops
3284 if (width == 0 || height == 0 || depth == 0)
3285 {
3286 return;
3287 }
3288
Jamie Madillad9f24e2016-02-12 09:27:24 -05003289 syncStateForTexImage();
Jamie Madill73a84962016-02-12 09:27:23 -05003290
3291 Box area(xoffset, yoffset, zoffset, width, height, depth);
3292 Texture *texture = getTargetTexture(target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003293 handleError(texture->setSubImage(this, mGLState.getUnpackState(), target, level, area, format,
3294 type, reinterpret_cast<const uint8_t *>(pixels)));
Jamie Madill73a84962016-02-12 09:27:23 -05003295}
3296
3297void Context::compressedTexImage2D(GLenum target,
3298 GLint level,
3299 GLenum internalformat,
3300 GLsizei width,
3301 GLsizei height,
3302 GLint border,
3303 GLsizei imageSize,
Jamie Madill876429b2017-04-20 15:46:24 -04003304 const void *data)
Jamie Madill73a84962016-02-12 09:27:23 -05003305{
Jamie Madillad9f24e2016-02-12 09:27:24 -05003306 syncStateForTexImage();
Jamie Madill73a84962016-02-12 09:27:23 -05003307
3308 Extents size(width, height, 1);
3309 Texture *texture =
3310 getTargetTexture(IsCubeMapTextureTarget(target) ? GL_TEXTURE_CUBE_MAP : target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003311 handleError(texture->setCompressedImage(this, mGLState.getUnpackState(), target, level,
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003312 internalformat, size, imageSize,
Jamie Madill437fa652016-05-03 15:13:24 -04003313 reinterpret_cast<const uint8_t *>(data)));
Jamie Madill73a84962016-02-12 09:27:23 -05003314}
3315
3316void Context::compressedTexImage3D(GLenum target,
3317 GLint level,
3318 GLenum internalformat,
3319 GLsizei width,
3320 GLsizei height,
3321 GLsizei depth,
3322 GLint border,
3323 GLsizei imageSize,
Jamie Madill876429b2017-04-20 15:46:24 -04003324 const void *data)
Jamie Madill73a84962016-02-12 09:27:23 -05003325{
Jamie Madillad9f24e2016-02-12 09:27:24 -05003326 syncStateForTexImage();
Jamie Madill73a84962016-02-12 09:27:23 -05003327
3328 Extents size(width, height, depth);
3329 Texture *texture = getTargetTexture(target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003330 handleError(texture->setCompressedImage(this, mGLState.getUnpackState(), target, level,
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003331 internalformat, size, imageSize,
Jamie Madill437fa652016-05-03 15:13:24 -04003332 reinterpret_cast<const uint8_t *>(data)));
Jamie Madill73a84962016-02-12 09:27:23 -05003333}
3334
3335void Context::compressedTexSubImage2D(GLenum target,
3336 GLint level,
3337 GLint xoffset,
3338 GLint yoffset,
3339 GLsizei width,
3340 GLsizei height,
3341 GLenum format,
3342 GLsizei imageSize,
Jamie Madill876429b2017-04-20 15:46:24 -04003343 const void *data)
Jamie Madill73a84962016-02-12 09:27:23 -05003344{
Jamie Madillad9f24e2016-02-12 09:27:24 -05003345 syncStateForTexImage();
Jamie Madill73a84962016-02-12 09:27:23 -05003346
3347 Box area(xoffset, yoffset, 0, width, height, 1);
3348 Texture *texture =
3349 getTargetTexture(IsCubeMapTextureTarget(target) ? GL_TEXTURE_CUBE_MAP : target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003350 handleError(texture->setCompressedSubImage(this, mGLState.getUnpackState(), target, level, area,
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003351 format, imageSize,
3352 reinterpret_cast<const uint8_t *>(data)));
Jamie Madill73a84962016-02-12 09:27:23 -05003353}
3354
3355void Context::compressedTexSubImage3D(GLenum target,
3356 GLint level,
3357 GLint xoffset,
3358 GLint yoffset,
3359 GLint zoffset,
3360 GLsizei width,
3361 GLsizei height,
3362 GLsizei depth,
3363 GLenum format,
3364 GLsizei imageSize,
Jamie Madill876429b2017-04-20 15:46:24 -04003365 const void *data)
Jamie Madill73a84962016-02-12 09:27:23 -05003366{
3367 // Zero sized uploads are valid but no-ops
3368 if (width == 0 || height == 0)
3369 {
3370 return;
3371 }
3372
Jamie Madillad9f24e2016-02-12 09:27:24 -05003373 syncStateForTexImage();
Jamie Madill73a84962016-02-12 09:27:23 -05003374
3375 Box area(xoffset, yoffset, zoffset, width, height, depth);
3376 Texture *texture = getTargetTexture(target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003377 handleError(texture->setCompressedSubImage(this, mGLState.getUnpackState(), target, level, area,
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003378 format, imageSize,
3379 reinterpret_cast<const uint8_t *>(data)));
Jamie Madill73a84962016-02-12 09:27:23 -05003380}
3381
Olli Etuaho0f2b1562016-05-13 16:15:35 +03003382void Context::generateMipmap(GLenum target)
3383{
3384 Texture *texture = getTargetTexture(target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003385 handleError(texture->generateMipmap(this));
Olli Etuaho0f2b1562016-05-13 16:15:35 +03003386}
3387
Geoff Lang97073d12016-04-20 10:42:34 -07003388void Context::copyTextureCHROMIUM(GLuint sourceId,
Geoff Langfc72a072017-03-24 14:52:39 -04003389 GLint sourceLevel,
3390 GLenum destTarget,
Geoff Lang97073d12016-04-20 10:42:34 -07003391 GLuint destId,
Geoff Langfc72a072017-03-24 14:52:39 -04003392 GLint destLevel,
Geoff Lang97073d12016-04-20 10:42:34 -07003393 GLint internalFormat,
3394 GLenum destType,
3395 GLboolean unpackFlipY,
3396 GLboolean unpackPremultiplyAlpha,
3397 GLboolean unpackUnmultiplyAlpha)
3398{
3399 syncStateForTexImage();
3400
3401 gl::Texture *sourceTexture = getTexture(sourceId);
3402 gl::Texture *destTexture = getTexture(destId);
Geoff Langfc72a072017-03-24 14:52:39 -04003403 handleError(destTexture->copyTexture(
3404 this, destTarget, destLevel, internalFormat, destType, sourceLevel, unpackFlipY == GL_TRUE,
3405 unpackPremultiplyAlpha == GL_TRUE, unpackUnmultiplyAlpha == GL_TRUE, sourceTexture));
Geoff Lang97073d12016-04-20 10:42:34 -07003406}
3407
3408void Context::copySubTextureCHROMIUM(GLuint sourceId,
Geoff Langfc72a072017-03-24 14:52:39 -04003409 GLint sourceLevel,
3410 GLenum destTarget,
Geoff Lang97073d12016-04-20 10:42:34 -07003411 GLuint destId,
Geoff Langfc72a072017-03-24 14:52:39 -04003412 GLint destLevel,
Geoff Lang97073d12016-04-20 10:42:34 -07003413 GLint xoffset,
3414 GLint yoffset,
3415 GLint x,
3416 GLint y,
3417 GLsizei width,
3418 GLsizei height,
3419 GLboolean unpackFlipY,
3420 GLboolean unpackPremultiplyAlpha,
3421 GLboolean unpackUnmultiplyAlpha)
3422{
3423 // Zero sized copies are valid but no-ops
3424 if (width == 0 || height == 0)
3425 {
3426 return;
3427 }
3428
3429 syncStateForTexImage();
3430
3431 gl::Texture *sourceTexture = getTexture(sourceId);
3432 gl::Texture *destTexture = getTexture(destId);
3433 Offset offset(xoffset, yoffset, 0);
3434 Rectangle area(x, y, width, height);
Geoff Langfc72a072017-03-24 14:52:39 -04003435 handleError(destTexture->copySubTexture(
3436 this, destTarget, destLevel, offset, sourceLevel, area, unpackFlipY == GL_TRUE,
3437 unpackPremultiplyAlpha == GL_TRUE, unpackUnmultiplyAlpha == GL_TRUE, sourceTexture));
Geoff Lang97073d12016-04-20 10:42:34 -07003438}
3439
Geoff Lang47110bf2016-04-20 11:13:22 -07003440void Context::compressedCopyTextureCHROMIUM(GLuint sourceId, GLuint destId)
3441{
3442 syncStateForTexImage();
3443
3444 gl::Texture *sourceTexture = getTexture(sourceId);
3445 gl::Texture *destTexture = getTexture(destId);
Jamie Madill8897afa2017-02-06 17:17:23 -05003446 handleError(destTexture->copyCompressedTexture(this, sourceTexture));
Geoff Lang47110bf2016-04-20 11:13:22 -07003447}
3448
Geoff Lang496c02d2016-10-20 11:38:11 -07003449void Context::getBufferPointerv(GLenum target, GLenum pname, void **params)
Olli Etuaho4f667482016-03-30 15:56:35 +03003450{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003451 Buffer *buffer = mGLState.getTargetBuffer(target);
Olli Etuaho4f667482016-03-30 15:56:35 +03003452 ASSERT(buffer);
3453
Geoff Lang496c02d2016-10-20 11:38:11 -07003454 QueryBufferPointerv(buffer, pname, params);
Olli Etuaho4f667482016-03-30 15:56:35 +03003455}
3456
Jamie Madill876429b2017-04-20 15:46:24 -04003457void *Context::mapBuffer(GLenum target, GLenum access)
Olli Etuaho4f667482016-03-30 15:56:35 +03003458{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003459 Buffer *buffer = mGLState.getTargetBuffer(target);
Olli Etuaho4f667482016-03-30 15:56:35 +03003460 ASSERT(buffer);
3461
Jamie Madill5f56ddb2017-01-13 17:29:55 -05003462 Error error = buffer->map(this, access);
Olli Etuaho4f667482016-03-30 15:56:35 +03003463 if (error.isError())
3464 {
Jamie Madill437fa652016-05-03 15:13:24 -04003465 handleError(error);
Olli Etuaho4f667482016-03-30 15:56:35 +03003466 return nullptr;
3467 }
3468
3469 return buffer->getMapPointer();
3470}
3471
3472GLboolean Context::unmapBuffer(GLenum target)
3473{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003474 Buffer *buffer = mGLState.getTargetBuffer(target);
Olli Etuaho4f667482016-03-30 15:56:35 +03003475 ASSERT(buffer);
3476
3477 GLboolean result;
Jamie Madill5f56ddb2017-01-13 17:29:55 -05003478 Error error = buffer->unmap(this, &result);
Olli Etuaho4f667482016-03-30 15:56:35 +03003479 if (error.isError())
3480 {
Jamie Madill437fa652016-05-03 15:13:24 -04003481 handleError(error);
Olli Etuaho4f667482016-03-30 15:56:35 +03003482 return GL_FALSE;
3483 }
3484
3485 return result;
3486}
3487
Jamie Madill876429b2017-04-20 15:46:24 -04003488void *Context::mapBufferRange(GLenum target, GLintptr offset, GLsizeiptr length, GLbitfield access)
Olli Etuaho4f667482016-03-30 15:56:35 +03003489{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003490 Buffer *buffer = mGLState.getTargetBuffer(target);
Olli Etuaho4f667482016-03-30 15:56:35 +03003491 ASSERT(buffer);
3492
Jamie Madill5f56ddb2017-01-13 17:29:55 -05003493 Error error = buffer->mapRange(this, offset, length, access);
Olli Etuaho4f667482016-03-30 15:56:35 +03003494 if (error.isError())
3495 {
Jamie Madill437fa652016-05-03 15:13:24 -04003496 handleError(error);
Olli Etuaho4f667482016-03-30 15:56:35 +03003497 return nullptr;
3498 }
3499
3500 return buffer->getMapPointer();
3501}
3502
3503void Context::flushMappedBufferRange(GLenum /*target*/, GLintptr /*offset*/, GLsizeiptr /*length*/)
3504{
3505 // We do not currently support a non-trivial implementation of FlushMappedBufferRange
3506}
3507
Jamie Madillad9f24e2016-02-12 09:27:24 -05003508void Context::syncStateForReadPixels()
3509{
3510 syncRendererState(mReadPixelsDirtyBits, mReadPixelsDirtyObjects);
3511}
3512
3513void Context::syncStateForTexImage()
3514{
3515 syncRendererState(mTexImageDirtyBits, mTexImageDirtyObjects);
3516}
3517
3518void Context::syncStateForClear()
3519{
3520 syncRendererState(mClearDirtyBits, mClearDirtyObjects);
3521}
3522
3523void Context::syncStateForBlit()
3524{
3525 syncRendererState(mBlitDirtyBits, mBlitDirtyObjects);
3526}
3527
Jamie Madillc20ab272016-06-09 07:20:46 -07003528void Context::activeTexture(GLenum texture)
3529{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003530 mGLState.setActiveSampler(texture - GL_TEXTURE0);
Jamie Madillc20ab272016-06-09 07:20:46 -07003531}
3532
Jamie Madill876429b2017-04-20 15:46:24 -04003533void Context::blendColor(GLfloat red, GLfloat green, GLfloat blue, GLfloat alpha)
Jamie Madillc20ab272016-06-09 07:20:46 -07003534{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003535 mGLState.setBlendColor(clamp01(red), clamp01(green), clamp01(blue), clamp01(alpha));
Jamie Madillc20ab272016-06-09 07:20:46 -07003536}
3537
Jamie Madill8a9e4bc2016-11-13 20:02:12 -05003538void Context::blendEquation(GLenum mode)
3539{
3540 mGLState.setBlendEquation(mode, mode);
3541}
3542
Jamie Madillc20ab272016-06-09 07:20:46 -07003543void Context::blendEquationSeparate(GLenum modeRGB, GLenum modeAlpha)
3544{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003545 mGLState.setBlendEquation(modeRGB, modeAlpha);
Jamie Madillc20ab272016-06-09 07:20:46 -07003546}
3547
Jamie Madill8a9e4bc2016-11-13 20:02:12 -05003548void Context::blendFunc(GLenum sfactor, GLenum dfactor)
3549{
3550 mGLState.setBlendFactors(sfactor, dfactor, sfactor, dfactor);
3551}
3552
Jamie Madillc20ab272016-06-09 07:20:46 -07003553void Context::blendFuncSeparate(GLenum srcRGB, GLenum dstRGB, GLenum srcAlpha, GLenum dstAlpha)
3554{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003555 mGLState.setBlendFactors(srcRGB, dstRGB, srcAlpha, dstAlpha);
Jamie Madillc20ab272016-06-09 07:20:46 -07003556}
3557
Jamie Madill876429b2017-04-20 15:46:24 -04003558void Context::clearColor(GLfloat red, GLfloat green, GLfloat blue, GLfloat alpha)
Jamie Madillc20ab272016-06-09 07:20:46 -07003559{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003560 mGLState.setColorClearValue(red, green, blue, alpha);
Jamie Madillc20ab272016-06-09 07:20:46 -07003561}
3562
Jamie Madill876429b2017-04-20 15:46:24 -04003563void Context::clearDepthf(GLfloat depth)
Jamie Madillc20ab272016-06-09 07:20:46 -07003564{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003565 mGLState.setDepthClearValue(depth);
Jamie Madillc20ab272016-06-09 07:20:46 -07003566}
3567
3568void Context::clearStencil(GLint s)
3569{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003570 mGLState.setStencilClearValue(s);
Jamie Madillc20ab272016-06-09 07:20:46 -07003571}
3572
3573void Context::colorMask(GLboolean red, GLboolean green, GLboolean blue, GLboolean alpha)
3574{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003575 mGLState.setColorMask(red == GL_TRUE, green == GL_TRUE, blue == GL_TRUE, alpha == GL_TRUE);
Jamie Madillc20ab272016-06-09 07:20:46 -07003576}
3577
3578void Context::cullFace(GLenum mode)
3579{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003580 mGLState.setCullMode(mode);
Jamie Madillc20ab272016-06-09 07:20:46 -07003581}
3582
3583void Context::depthFunc(GLenum func)
3584{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003585 mGLState.setDepthFunc(func);
Jamie Madillc20ab272016-06-09 07:20:46 -07003586}
3587
3588void Context::depthMask(GLboolean flag)
3589{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003590 mGLState.setDepthMask(flag != GL_FALSE);
Jamie Madillc20ab272016-06-09 07:20:46 -07003591}
3592
Jamie Madill876429b2017-04-20 15:46:24 -04003593void Context::depthRangef(GLfloat zNear, GLfloat zFar)
Jamie Madillc20ab272016-06-09 07:20:46 -07003594{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003595 mGLState.setDepthRange(zNear, zFar);
Jamie Madillc20ab272016-06-09 07:20:46 -07003596}
3597
3598void Context::disable(GLenum cap)
3599{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003600 mGLState.setEnableFeature(cap, false);
Jamie Madillc20ab272016-06-09 07:20:46 -07003601}
3602
3603void Context::disableVertexAttribArray(GLuint index)
3604{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003605 mGLState.setEnableVertexAttribArray(index, false);
Jamie Madillc20ab272016-06-09 07:20:46 -07003606}
3607
3608void Context::enable(GLenum cap)
3609{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003610 mGLState.setEnableFeature(cap, true);
Jamie Madillc20ab272016-06-09 07:20:46 -07003611}
3612
3613void Context::enableVertexAttribArray(GLuint index)
3614{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003615 mGLState.setEnableVertexAttribArray(index, true);
Jamie Madillc20ab272016-06-09 07:20:46 -07003616}
3617
3618void Context::frontFace(GLenum mode)
3619{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003620 mGLState.setFrontFace(mode);
Jamie Madillc20ab272016-06-09 07:20:46 -07003621}
3622
3623void Context::hint(GLenum target, GLenum mode)
3624{
3625 switch (target)
3626 {
3627 case GL_GENERATE_MIPMAP_HINT:
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003628 mGLState.setGenerateMipmapHint(mode);
Jamie Madillc20ab272016-06-09 07:20:46 -07003629 break;
3630
3631 case GL_FRAGMENT_SHADER_DERIVATIVE_HINT_OES:
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003632 mGLState.setFragmentShaderDerivativeHint(mode);
Jamie Madillc20ab272016-06-09 07:20:46 -07003633 break;
3634
3635 default:
3636 UNREACHABLE();
3637 return;
3638 }
3639}
3640
3641void Context::lineWidth(GLfloat width)
3642{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003643 mGLState.setLineWidth(width);
Jamie Madillc20ab272016-06-09 07:20:46 -07003644}
3645
3646void Context::pixelStorei(GLenum pname, GLint param)
3647{
3648 switch (pname)
3649 {
3650 case GL_UNPACK_ALIGNMENT:
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003651 mGLState.setUnpackAlignment(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003652 break;
3653
3654 case GL_PACK_ALIGNMENT:
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003655 mGLState.setPackAlignment(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003656 break;
3657
3658 case GL_PACK_REVERSE_ROW_ORDER_ANGLE:
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003659 mGLState.setPackReverseRowOrder(param != 0);
Jamie Madillc20ab272016-06-09 07:20:46 -07003660 break;
3661
3662 case GL_UNPACK_ROW_LENGTH:
Martin Radev1be913c2016-07-11 17:59:16 +03003663 ASSERT((getClientMajorVersion() >= 3) || getExtensions().unpackSubimage);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003664 mGLState.setUnpackRowLength(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003665 break;
3666
3667 case GL_UNPACK_IMAGE_HEIGHT:
Martin Radev1be913c2016-07-11 17:59:16 +03003668 ASSERT(getClientMajorVersion() >= 3);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003669 mGLState.setUnpackImageHeight(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003670 break;
3671
3672 case GL_UNPACK_SKIP_IMAGES:
Martin Radev1be913c2016-07-11 17:59:16 +03003673 ASSERT(getClientMajorVersion() >= 3);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003674 mGLState.setUnpackSkipImages(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003675 break;
3676
3677 case GL_UNPACK_SKIP_ROWS:
Martin Radev1be913c2016-07-11 17:59:16 +03003678 ASSERT((getClientMajorVersion() >= 3) || getExtensions().unpackSubimage);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003679 mGLState.setUnpackSkipRows(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003680 break;
3681
3682 case GL_UNPACK_SKIP_PIXELS:
Martin Radev1be913c2016-07-11 17:59:16 +03003683 ASSERT((getClientMajorVersion() >= 3) || getExtensions().unpackSubimage);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003684 mGLState.setUnpackSkipPixels(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003685 break;
3686
3687 case GL_PACK_ROW_LENGTH:
Martin Radev1be913c2016-07-11 17:59:16 +03003688 ASSERT((getClientMajorVersion() >= 3) || getExtensions().packSubimage);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003689 mGLState.setPackRowLength(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003690 break;
3691
3692 case GL_PACK_SKIP_ROWS:
Martin Radev1be913c2016-07-11 17:59:16 +03003693 ASSERT((getClientMajorVersion() >= 3) || getExtensions().packSubimage);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003694 mGLState.setPackSkipRows(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003695 break;
3696
3697 case GL_PACK_SKIP_PIXELS:
Martin Radev1be913c2016-07-11 17:59:16 +03003698 ASSERT((getClientMajorVersion() >= 3) || getExtensions().packSubimage);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003699 mGLState.setPackSkipPixels(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003700 break;
3701
3702 default:
3703 UNREACHABLE();
3704 return;
3705 }
3706}
3707
3708void Context::polygonOffset(GLfloat factor, GLfloat units)
3709{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003710 mGLState.setPolygonOffsetParams(factor, units);
Jamie Madillc20ab272016-06-09 07:20:46 -07003711}
3712
Jamie Madill876429b2017-04-20 15:46:24 -04003713void Context::sampleCoverage(GLfloat value, GLboolean invert)
Jamie Madillc20ab272016-06-09 07:20:46 -07003714{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003715 mGLState.setSampleCoverageParams(clamp01(value), invert == GL_TRUE);
Jamie Madillc20ab272016-06-09 07:20:46 -07003716}
3717
3718void Context::scissor(GLint x, GLint y, GLsizei width, GLsizei height)
3719{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003720 mGLState.setScissorParams(x, y, width, height);
Jamie Madillc20ab272016-06-09 07:20:46 -07003721}
3722
3723void Context::stencilFuncSeparate(GLenum face, GLenum func, GLint ref, GLuint mask)
3724{
3725 if (face == GL_FRONT || face == GL_FRONT_AND_BACK)
3726 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003727 mGLState.setStencilParams(func, ref, mask);
Jamie Madillc20ab272016-06-09 07:20:46 -07003728 }
3729
3730 if (face == GL_BACK || face == GL_FRONT_AND_BACK)
3731 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003732 mGLState.setStencilBackParams(func, ref, mask);
Jamie Madillc20ab272016-06-09 07:20:46 -07003733 }
3734}
3735
3736void Context::stencilMaskSeparate(GLenum face, GLuint mask)
3737{
3738 if (face == GL_FRONT || face == GL_FRONT_AND_BACK)
3739 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003740 mGLState.setStencilWritemask(mask);
Jamie Madillc20ab272016-06-09 07:20:46 -07003741 }
3742
3743 if (face == GL_BACK || face == GL_FRONT_AND_BACK)
3744 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003745 mGLState.setStencilBackWritemask(mask);
Jamie Madillc20ab272016-06-09 07:20:46 -07003746 }
3747}
3748
3749void Context::stencilOpSeparate(GLenum face, GLenum fail, GLenum zfail, GLenum zpass)
3750{
3751 if (face == GL_FRONT || face == GL_FRONT_AND_BACK)
3752 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003753 mGLState.setStencilOperations(fail, zfail, zpass);
Jamie Madillc20ab272016-06-09 07:20:46 -07003754 }
3755
3756 if (face == GL_BACK || face == GL_FRONT_AND_BACK)
3757 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003758 mGLState.setStencilBackOperations(fail, zfail, zpass);
Jamie Madillc20ab272016-06-09 07:20:46 -07003759 }
3760}
3761
3762void Context::vertexAttrib1f(GLuint index, GLfloat x)
3763{
3764 GLfloat vals[4] = {x, 0, 0, 1};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003765 mGLState.setVertexAttribf(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003766}
3767
3768void Context::vertexAttrib1fv(GLuint index, const GLfloat *values)
3769{
3770 GLfloat vals[4] = {values[0], 0, 0, 1};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003771 mGLState.setVertexAttribf(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003772}
3773
3774void Context::vertexAttrib2f(GLuint index, GLfloat x, GLfloat y)
3775{
3776 GLfloat vals[4] = {x, y, 0, 1};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003777 mGLState.setVertexAttribf(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003778}
3779
3780void Context::vertexAttrib2fv(GLuint index, const GLfloat *values)
3781{
3782 GLfloat vals[4] = {values[0], values[1], 0, 1};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003783 mGLState.setVertexAttribf(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003784}
3785
3786void Context::vertexAttrib3f(GLuint index, GLfloat x, GLfloat y, GLfloat z)
3787{
3788 GLfloat vals[4] = {x, y, z, 1};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003789 mGLState.setVertexAttribf(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003790}
3791
3792void Context::vertexAttrib3fv(GLuint index, const GLfloat *values)
3793{
3794 GLfloat vals[4] = {values[0], values[1], values[2], 1};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003795 mGLState.setVertexAttribf(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003796}
3797
3798void Context::vertexAttrib4f(GLuint index, GLfloat x, GLfloat y, GLfloat z, GLfloat w)
3799{
3800 GLfloat vals[4] = {x, y, z, w};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003801 mGLState.setVertexAttribf(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003802}
3803
3804void Context::vertexAttrib4fv(GLuint index, const GLfloat *values)
3805{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003806 mGLState.setVertexAttribf(index, values);
Jamie Madillc20ab272016-06-09 07:20:46 -07003807}
3808
3809void Context::vertexAttribPointer(GLuint index,
3810 GLint size,
3811 GLenum type,
3812 GLboolean normalized,
3813 GLsizei stride,
Jamie Madill876429b2017-04-20 15:46:24 -04003814 const void *ptr)
Jamie Madillc20ab272016-06-09 07:20:46 -07003815{
Shaodde78e82017-05-22 14:13:27 +08003816 mGLState.setVertexAttribPointer(this, index, mGLState.getTargetBuffer(GL_ARRAY_BUFFER), size,
3817 type, normalized == GL_TRUE, false, stride, ptr);
Jamie Madillc20ab272016-06-09 07:20:46 -07003818}
3819
Shao80957d92017-02-20 21:25:59 +08003820void Context::vertexAttribFormat(GLuint attribIndex,
3821 GLint size,
3822 GLenum type,
3823 GLboolean normalized,
3824 GLuint relativeOffset)
3825{
3826 mGLState.setVertexAttribFormat(attribIndex, size, type, normalized == GL_TRUE, false,
3827 relativeOffset);
3828}
3829
3830void Context::vertexAttribIFormat(GLuint attribIndex,
3831 GLint size,
3832 GLenum type,
3833 GLuint relativeOffset)
3834{
3835 mGLState.setVertexAttribFormat(attribIndex, size, type, false, true, relativeOffset);
3836}
3837
3838void Context::vertexAttribBinding(GLuint attribIndex, GLuint bindingIndex)
3839{
Shaodde78e82017-05-22 14:13:27 +08003840 mGLState.setVertexAttribBinding(this, attribIndex, bindingIndex);
Shao80957d92017-02-20 21:25:59 +08003841}
3842
3843void Context::setVertexBindingDivisor(GLuint bindingIndex, GLuint divisor)
3844{
3845 mGLState.setVertexBindingDivisor(bindingIndex, divisor);
3846}
3847
Jamie Madillc20ab272016-06-09 07:20:46 -07003848void Context::viewport(GLint x, GLint y, GLsizei width, GLsizei height)
3849{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003850 mGLState.setViewportParams(x, y, width, height);
Jamie Madillc20ab272016-06-09 07:20:46 -07003851}
3852
3853void Context::vertexAttribIPointer(GLuint index,
3854 GLint size,
3855 GLenum type,
3856 GLsizei stride,
Jamie Madill876429b2017-04-20 15:46:24 -04003857 const void *pointer)
Jamie Madillc20ab272016-06-09 07:20:46 -07003858{
Shaodde78e82017-05-22 14:13:27 +08003859 mGLState.setVertexAttribPointer(this, index, mGLState.getTargetBuffer(GL_ARRAY_BUFFER), size,
3860 type, false, true, stride, pointer);
Jamie Madillc20ab272016-06-09 07:20:46 -07003861}
3862
3863void Context::vertexAttribI4i(GLuint index, GLint x, GLint y, GLint z, GLint w)
3864{
3865 GLint vals[4] = {x, y, z, w};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003866 mGLState.setVertexAttribi(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003867}
3868
3869void Context::vertexAttribI4ui(GLuint index, GLuint x, GLuint y, GLuint z, GLuint w)
3870{
3871 GLuint vals[4] = {x, y, z, w};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003872 mGLState.setVertexAttribu(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003873}
3874
3875void Context::vertexAttribI4iv(GLuint index, const GLint *v)
3876{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003877 mGLState.setVertexAttribi(index, v);
Jamie Madillc20ab272016-06-09 07:20:46 -07003878}
3879
3880void Context::vertexAttribI4uiv(GLuint index, const GLuint *v)
3881{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003882 mGLState.setVertexAttribu(index, v);
Jamie Madillc20ab272016-06-09 07:20:46 -07003883}
3884
Jiawei-Shao2597fb62016-12-09 16:38:02 +08003885void Context::getVertexAttribiv(GLuint index, GLenum pname, GLint *params)
3886{
3887 const VertexAttribCurrentValueData &currentValues =
3888 getGLState().getVertexAttribCurrentValue(index);
3889 const VertexArray *vao = getGLState().getVertexArray();
3890 QueryVertexAttribiv(vao->getVertexAttribute(index), vao->getBindingFromAttribIndex(index),
3891 currentValues, pname, params);
3892}
3893
3894void Context::getVertexAttribfv(GLuint index, GLenum pname, GLfloat *params)
3895{
3896 const VertexAttribCurrentValueData &currentValues =
3897 getGLState().getVertexAttribCurrentValue(index);
3898 const VertexArray *vao = getGLState().getVertexArray();
3899 QueryVertexAttribfv(vao->getVertexAttribute(index), vao->getBindingFromAttribIndex(index),
3900 currentValues, pname, params);
3901}
3902
3903void Context::getVertexAttribIiv(GLuint index, GLenum pname, GLint *params)
3904{
3905 const VertexAttribCurrentValueData &currentValues =
3906 getGLState().getVertexAttribCurrentValue(index);
3907 const VertexArray *vao = getGLState().getVertexArray();
3908 QueryVertexAttribIiv(vao->getVertexAttribute(index), vao->getBindingFromAttribIndex(index),
3909 currentValues, pname, params);
3910}
3911
3912void Context::getVertexAttribIuiv(GLuint index, GLenum pname, GLuint *params)
3913{
3914 const VertexAttribCurrentValueData &currentValues =
3915 getGLState().getVertexAttribCurrentValue(index);
3916 const VertexArray *vao = getGLState().getVertexArray();
3917 QueryVertexAttribIuiv(vao->getVertexAttribute(index), vao->getBindingFromAttribIndex(index),
3918 currentValues, pname, params);
3919}
3920
Jamie Madill876429b2017-04-20 15:46:24 -04003921void Context::getVertexAttribPointerv(GLuint index, GLenum pname, void **pointer)
Jiawei-Shao2597fb62016-12-09 16:38:02 +08003922{
3923 const VertexAttribute &attrib = getGLState().getVertexArray()->getVertexAttribute(index);
3924 QueryVertexAttribPointerv(attrib, pname, pointer);
3925}
3926
Jamie Madillc20ab272016-06-09 07:20:46 -07003927void Context::debugMessageControl(GLenum source,
3928 GLenum type,
3929 GLenum severity,
3930 GLsizei count,
3931 const GLuint *ids,
3932 GLboolean enabled)
3933{
3934 std::vector<GLuint> idVector(ids, ids + count);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003935 mGLState.getDebug().setMessageControl(source, type, severity, std::move(idVector),
3936 (enabled != GL_FALSE));
Jamie Madillc20ab272016-06-09 07:20:46 -07003937}
3938
3939void Context::debugMessageInsert(GLenum source,
3940 GLenum type,
3941 GLuint id,
3942 GLenum severity,
3943 GLsizei length,
3944 const GLchar *buf)
3945{
3946 std::string msg(buf, (length > 0) ? static_cast<size_t>(length) : strlen(buf));
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003947 mGLState.getDebug().insertMessage(source, type, id, severity, std::move(msg));
Jamie Madillc20ab272016-06-09 07:20:46 -07003948}
3949
3950void Context::debugMessageCallback(GLDEBUGPROCKHR callback, const void *userParam)
3951{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003952 mGLState.getDebug().setCallback(callback, userParam);
Jamie Madillc20ab272016-06-09 07:20:46 -07003953}
3954
3955GLuint Context::getDebugMessageLog(GLuint count,
3956 GLsizei bufSize,
3957 GLenum *sources,
3958 GLenum *types,
3959 GLuint *ids,
3960 GLenum *severities,
3961 GLsizei *lengths,
3962 GLchar *messageLog)
3963{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003964 return static_cast<GLuint>(mGLState.getDebug().getMessages(count, bufSize, sources, types, ids,
3965 severities, lengths, messageLog));
Jamie Madillc20ab272016-06-09 07:20:46 -07003966}
3967
3968void Context::pushDebugGroup(GLenum source, GLuint id, GLsizei length, const GLchar *message)
3969{
3970 std::string msg(message, (length > 0) ? static_cast<size_t>(length) : strlen(message));
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003971 mGLState.getDebug().pushGroup(source, id, std::move(msg));
Jamie Madillc20ab272016-06-09 07:20:46 -07003972}
3973
3974void Context::popDebugGroup()
3975{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003976 mGLState.getDebug().popGroup();
Jamie Madillc20ab272016-06-09 07:20:46 -07003977}
3978
Jamie Madill876429b2017-04-20 15:46:24 -04003979void Context::bufferData(GLenum target, GLsizeiptr size, const void *data, GLenum usage)
Jamie Madill29639852016-09-02 15:00:09 -04003980{
3981 Buffer *buffer = mGLState.getTargetBuffer(target);
3982 ASSERT(buffer);
Jamie Madillb8353b02017-01-25 12:57:21 -08003983 handleError(buffer->bufferData(this, target, data, size, usage));
Jamie Madill29639852016-09-02 15:00:09 -04003984}
3985
Jamie Madill876429b2017-04-20 15:46:24 -04003986void Context::bufferSubData(GLenum target, GLintptr offset, GLsizeiptr size, const void *data)
Jamie Madill29639852016-09-02 15:00:09 -04003987{
3988 if (data == nullptr)
3989 {
3990 return;
3991 }
3992
3993 Buffer *buffer = mGLState.getTargetBuffer(target);
3994 ASSERT(buffer);
Jamie Madillb8353b02017-01-25 12:57:21 -08003995 handleError(buffer->bufferSubData(this, target, data, size, offset));
Jamie Madill29639852016-09-02 15:00:09 -04003996}
3997
Jamie Madillef300b12016-10-07 15:12:09 -04003998void Context::attachShader(GLuint program, GLuint shader)
3999{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05004000 auto programObject = mState.mShaderPrograms->getProgram(program);
4001 auto shaderObject = mState.mShaderPrograms->getShader(shader);
Jamie Madillef300b12016-10-07 15:12:09 -04004002 ASSERT(programObject && shaderObject);
4003 programObject->attachShader(shaderObject);
4004}
4005
Kenneth Russellf2f6f652016-10-05 19:53:23 -07004006const Workarounds &Context::getWorkarounds() const
4007{
4008 return mWorkarounds;
4009}
4010
Jamie Madillb0817d12016-11-01 15:48:31 -04004011void Context::copyBufferSubData(GLenum readTarget,
4012 GLenum writeTarget,
4013 GLintptr readOffset,
4014 GLintptr writeOffset,
4015 GLsizeiptr size)
4016{
4017 // if size is zero, the copy is a successful no-op
4018 if (size == 0)
4019 {
4020 return;
4021 }
4022
4023 // TODO(jmadill): cache these.
4024 Buffer *readBuffer = mGLState.getTargetBuffer(readTarget);
4025 Buffer *writeBuffer = mGLState.getTargetBuffer(writeTarget);
4026
Jamie Madill5f56ddb2017-01-13 17:29:55 -05004027 handleError(writeBuffer->copyBufferSubData(this, readBuffer, readOffset, writeOffset, size));
Jamie Madillb0817d12016-11-01 15:48:31 -04004028}
4029
Jamie Madill01a80ee2016-11-07 12:06:18 -05004030void Context::bindAttribLocation(GLuint program, GLuint index, const GLchar *name)
4031{
4032 Program *programObject = getProgram(program);
4033 // TODO(jmadill): Re-use this from the validation if possible.
4034 ASSERT(programObject);
4035 programObject->bindAttributeLocation(index, name);
4036}
4037
4038void Context::bindBuffer(GLenum target, GLuint buffer)
4039{
4040 switch (target)
4041 {
4042 case GL_ARRAY_BUFFER:
4043 bindArrayBuffer(buffer);
4044 break;
4045 case GL_ELEMENT_ARRAY_BUFFER:
4046 bindElementArrayBuffer(buffer);
4047 break;
4048 case GL_COPY_READ_BUFFER:
4049 bindCopyReadBuffer(buffer);
4050 break;
4051 case GL_COPY_WRITE_BUFFER:
4052 bindCopyWriteBuffer(buffer);
4053 break;
4054 case GL_PIXEL_PACK_BUFFER:
4055 bindPixelPackBuffer(buffer);
4056 break;
4057 case GL_PIXEL_UNPACK_BUFFER:
4058 bindPixelUnpackBuffer(buffer);
4059 break;
4060 case GL_UNIFORM_BUFFER:
4061 bindGenericUniformBuffer(buffer);
4062 break;
4063 case GL_TRANSFORM_FEEDBACK_BUFFER:
4064 bindGenericTransformFeedbackBuffer(buffer);
4065 break;
Geoff Lang3b573612016-10-31 14:08:10 -04004066 case GL_ATOMIC_COUNTER_BUFFER:
Jiajia Qin6eafb042016-12-27 17:04:07 +08004067 bindGenericAtomicCounterBuffer(buffer);
Geoff Lang3b573612016-10-31 14:08:10 -04004068 break;
4069 case GL_SHADER_STORAGE_BUFFER:
Jiajia Qinf546e7d2017-03-27 14:12:59 +08004070 bindGenericShaderStorageBuffer(buffer);
Geoff Lang3b573612016-10-31 14:08:10 -04004071 break;
4072 case GL_DRAW_INDIRECT_BUFFER:
Jiajia Qin9d7d0b12016-11-29 16:30:31 +08004073 bindDrawIndirectBuffer(buffer);
Geoff Lang3b573612016-10-31 14:08:10 -04004074 break;
4075 case GL_DISPATCH_INDIRECT_BUFFER:
Geoff Lang9f090372016-12-02 10:20:43 -05004076 if (buffer != 0)
4077 {
4078 // Binding buffers to this binding point is not implemented yet.
4079 UNIMPLEMENTED();
4080 }
Geoff Lang3b573612016-10-31 14:08:10 -04004081 break;
Jamie Madill01a80ee2016-11-07 12:06:18 -05004082
4083 default:
4084 UNREACHABLE();
4085 break;
4086 }
4087}
4088
Jiajia Qin6eafb042016-12-27 17:04:07 +08004089void Context::bindBufferBase(GLenum target, GLuint index, GLuint buffer)
4090{
4091 bindBufferRange(target, index, buffer, 0, 0);
4092}
4093
4094void Context::bindBufferRange(GLenum target,
4095 GLuint index,
4096 GLuint buffer,
4097 GLintptr offset,
4098 GLsizeiptr size)
4099{
4100 switch (target)
4101 {
4102 case GL_TRANSFORM_FEEDBACK_BUFFER:
4103 bindIndexedTransformFeedbackBuffer(buffer, index, offset, size);
4104 bindGenericTransformFeedbackBuffer(buffer);
4105 break;
4106 case GL_UNIFORM_BUFFER:
4107 bindIndexedUniformBuffer(buffer, index, offset, size);
4108 bindGenericUniformBuffer(buffer);
4109 break;
4110 case GL_ATOMIC_COUNTER_BUFFER:
4111 bindIndexedAtomicCounterBuffer(buffer, index, offset, size);
4112 bindGenericAtomicCounterBuffer(buffer);
4113 break;
4114 case GL_SHADER_STORAGE_BUFFER:
Jiajia Qinf546e7d2017-03-27 14:12:59 +08004115 bindIndexedShaderStorageBuffer(buffer, index, offset, size);
4116 bindGenericShaderStorageBuffer(buffer);
Jiajia Qin6eafb042016-12-27 17:04:07 +08004117 break;
4118 default:
4119 UNREACHABLE();
4120 break;
4121 }
4122}
4123
Jamie Madill01a80ee2016-11-07 12:06:18 -05004124void Context::bindFramebuffer(GLenum target, GLuint framebuffer)
4125{
4126 if (target == GL_READ_FRAMEBUFFER || target == GL_FRAMEBUFFER)
4127 {
4128 bindReadFramebuffer(framebuffer);
4129 }
4130
4131 if (target == GL_DRAW_FRAMEBUFFER || target == GL_FRAMEBUFFER)
4132 {
4133 bindDrawFramebuffer(framebuffer);
4134 }
4135}
4136
4137void Context::bindRenderbuffer(GLenum target, GLuint renderbuffer)
4138{
4139 ASSERT(target == GL_RENDERBUFFER);
4140 Renderbuffer *object =
Geoff Lang4ddf5af2016-12-01 14:30:44 -05004141 mState.mRenderbuffers->checkRenderbufferAllocation(mImplementation.get(), renderbuffer);
Jamie Madill4928b7c2017-06-20 12:57:39 -04004142 mGLState.setRenderbufferBinding(this, object);
Jamie Madill01a80ee2016-11-07 12:06:18 -05004143}
4144
JiangYizhoubddc46b2016-12-09 09:50:51 +08004145void Context::texStorage2DMultisample(GLenum target,
4146 GLsizei samples,
4147 GLenum internalformat,
4148 GLsizei width,
4149 GLsizei height,
4150 GLboolean fixedsamplelocations)
4151{
4152 Extents size(width, height, 1);
4153 Texture *texture = getTargetTexture(target);
Jamie Madill8897afa2017-02-06 17:17:23 -05004154 handleError(texture->setStorageMultisample(this, target, samples, internalformat, size,
JiangYizhoubddc46b2016-12-09 09:50:51 +08004155 fixedsamplelocations));
4156}
4157
4158void Context::getMultisamplefv(GLenum pname, GLuint index, GLfloat *val)
4159{
Jamie Madilldd43e6c2017-03-24 14:18:49 -04004160 mGLState.syncDirtyObject(this, GL_READ_FRAMEBUFFER);
JiangYizhoubddc46b2016-12-09 09:50:51 +08004161 const Framebuffer *framebuffer = mGLState.getReadFramebuffer();
4162
4163 switch (pname)
4164 {
4165 case GL_SAMPLE_POSITION:
4166 handleError(framebuffer->getSamplePosition(index, val));
4167 break;
4168 default:
4169 UNREACHABLE();
4170 }
4171}
4172
Jamie Madille8fb6402017-02-14 17:56:40 -05004173void Context::renderbufferStorage(GLenum target,
4174 GLenum internalformat,
4175 GLsizei width,
4176 GLsizei height)
4177{
Jamie Madill4e0e6f82017-02-17 11:06:03 -05004178 // Hack for the special WebGL 1 "DEPTH_STENCIL" internal format.
4179 GLenum convertedInternalFormat = getConvertedRenderbufferFormat(internalformat);
4180
Jamie Madille8fb6402017-02-14 17:56:40 -05004181 Renderbuffer *renderbuffer = mGLState.getCurrentRenderbuffer();
Jamie Madill4928b7c2017-06-20 12:57:39 -04004182 handleError(renderbuffer->setStorage(this, convertedInternalFormat, width, height));
Jamie Madille8fb6402017-02-14 17:56:40 -05004183}
4184
4185void Context::renderbufferStorageMultisample(GLenum target,
4186 GLsizei samples,
4187 GLenum internalformat,
4188 GLsizei width,
4189 GLsizei height)
4190{
Jamie Madill4e0e6f82017-02-17 11:06:03 -05004191 // Hack for the special WebGL 1 "DEPTH_STENCIL" internal format.
4192 GLenum convertedInternalFormat = getConvertedRenderbufferFormat(internalformat);
Jamie Madille8fb6402017-02-14 17:56:40 -05004193
4194 Renderbuffer *renderbuffer = mGLState.getCurrentRenderbuffer();
Jamie Madill4e0e6f82017-02-17 11:06:03 -05004195 handleError(
Jamie Madill4928b7c2017-06-20 12:57:39 -04004196 renderbuffer->setStorageMultisample(this, samples, convertedInternalFormat, width, height));
Jamie Madille8fb6402017-02-14 17:56:40 -05004197}
4198
Geoff Lang38f2cfb2017-04-11 15:23:08 -04004199void Context::getSynciv(GLsync sync, GLenum pname, GLsizei bufSize, GLsizei *length, GLint *values)
4200{
4201 const FenceSync *syncObject = getFenceSync(sync);
Geoff Lang82483b92017-04-11 15:33:00 -04004202 handleError(QuerySynciv(syncObject, pname, bufSize, length, values));
Geoff Lang38f2cfb2017-04-11 15:23:08 -04004203}
4204
JiangYizhoue18e6392017-02-20 10:32:23 +08004205void Context::getFramebufferParameteriv(GLenum target, GLenum pname, GLint *params)
4206{
4207 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
4208 QueryFramebufferParameteriv(framebuffer, pname, params);
4209}
4210
4211void Context::setFramebufferParameteri(GLenum target, GLenum pname, GLint param)
4212{
4213 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
4214 SetFramebufferParameteri(framebuffer, pname, param);
4215}
4216
Jamie Madillb3f26b92017-07-19 15:07:41 -04004217Error Context::getScratchBuffer(size_t requstedSizeBytes,
4218 angle::MemoryBuffer **scratchBufferOut) const
Jamie Madille14951e2017-03-09 18:55:16 -05004219{
Jamie Madillb3f26b92017-07-19 15:07:41 -04004220 if (!mScratchBuffer.get(requstedSizeBytes, scratchBufferOut))
4221 {
4222 return OutOfMemory() << "Failed to allocate internal buffer.";
4223 }
4224 return NoError();
4225}
4226
4227Error Context::getZeroFilledBuffer(size_t requstedSizeBytes,
4228 angle::MemoryBuffer **zeroBufferOut) const
4229{
4230 if (!mZeroFilledBuffer.getInitialized(requstedSizeBytes, zeroBufferOut, 0))
Jamie Madille14951e2017-03-09 18:55:16 -05004231 {
Yuly Novikovc4d18aa2017-03-09 18:45:02 -05004232 return OutOfMemory() << "Failed to allocate internal buffer.";
Jamie Madille14951e2017-03-09 18:55:16 -05004233 }
Yuly Novikovc4d18aa2017-03-09 18:45:02 -05004234 return NoError();
Jamie Madille14951e2017-03-09 18:55:16 -05004235}
4236
Xinghua Cao2b396592017-03-29 15:36:04 +08004237void Context::dispatchCompute(GLuint numGroupsX, GLuint numGroupsY, GLuint numGroupsZ)
4238{
4239 if (numGroupsX == 0u || numGroupsY == 0u || numGroupsZ == 0u)
4240 {
4241 return;
4242 }
4243
Jamie Madillfe548342017-06-19 11:13:24 -04004244 mImplementation->dispatchCompute(this, numGroupsX, numGroupsY, numGroupsZ);
Xinghua Cao2b396592017-03-29 15:36:04 +08004245}
4246
JiangYizhou165361c2017-06-07 14:56:57 +08004247void Context::texStorage2D(GLenum target,
4248 GLsizei levels,
4249 GLenum internalFormat,
4250 GLsizei width,
4251 GLsizei height)
4252{
4253 Extents size(width, height, 1);
4254 Texture *texture = getTargetTexture(target);
4255 handleError(texture->setStorage(this, target, levels, internalFormat, size));
4256}
4257
4258void Context::texStorage3D(GLenum target,
4259 GLsizei levels,
4260 GLenum internalFormat,
4261 GLsizei width,
4262 GLsizei height,
4263 GLsizei depth)
4264{
4265 Extents size(width, height, depth);
4266 Texture *texture = getTargetTexture(target);
4267 handleError(texture->setStorage(this, target, levels, internalFormat, size));
4268}
4269
Jamie Madillc1d770e2017-04-13 17:31:24 -04004270GLenum Context::checkFramebufferStatus(GLenum target)
4271{
4272 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
4273 ASSERT(framebuffer);
4274
4275 return framebuffer->checkStatus(this);
4276}
4277
4278void Context::compileShader(GLuint shader)
4279{
4280 Shader *shaderObject = GetValidShader(this, shader);
4281 if (!shaderObject)
4282 {
4283 return;
4284 }
4285 shaderObject->compile(this);
4286}
4287
4288void Context::deleteBuffers(GLsizei n, const GLuint *buffers)
4289{
4290 for (int i = 0; i < n; i++)
4291 {
4292 deleteBuffer(buffers[i]);
4293 }
4294}
4295
4296void Context::deleteFramebuffers(GLsizei n, const GLuint *framebuffers)
4297{
4298 for (int i = 0; i < n; i++)
4299 {
4300 if (framebuffers[i] != 0)
4301 {
4302 deleteFramebuffer(framebuffers[i]);
4303 }
4304 }
4305}
4306
4307void Context::deleteRenderbuffers(GLsizei n, const GLuint *renderbuffers)
4308{
4309 for (int i = 0; i < n; i++)
4310 {
4311 deleteRenderbuffer(renderbuffers[i]);
4312 }
4313}
4314
4315void Context::deleteTextures(GLsizei n, const GLuint *textures)
4316{
4317 for (int i = 0; i < n; i++)
4318 {
4319 if (textures[i] != 0)
4320 {
4321 deleteTexture(textures[i]);
4322 }
4323 }
4324}
4325
4326void Context::detachShader(GLuint program, GLuint shader)
4327{
4328 Program *programObject = getProgram(program);
4329 ASSERT(programObject);
4330
4331 Shader *shaderObject = getShader(shader);
4332 ASSERT(shaderObject);
4333
4334 programObject->detachShader(this, shaderObject);
4335}
4336
4337void Context::genBuffers(GLsizei n, GLuint *buffers)
4338{
4339 for (int i = 0; i < n; i++)
4340 {
4341 buffers[i] = createBuffer();
4342 }
4343}
4344
4345void Context::genFramebuffers(GLsizei n, GLuint *framebuffers)
4346{
4347 for (int i = 0; i < n; i++)
4348 {
4349 framebuffers[i] = createFramebuffer();
4350 }
4351}
4352
4353void Context::genRenderbuffers(GLsizei n, GLuint *renderbuffers)
4354{
4355 for (int i = 0; i < n; i++)
4356 {
4357 renderbuffers[i] = createRenderbuffer();
4358 }
4359}
4360
4361void Context::genTextures(GLsizei n, GLuint *textures)
4362{
4363 for (int i = 0; i < n; i++)
4364 {
4365 textures[i] = createTexture();
4366 }
4367}
4368
4369void Context::getActiveAttrib(GLuint program,
4370 GLuint index,
4371 GLsizei bufsize,
4372 GLsizei *length,
4373 GLint *size,
4374 GLenum *type,
4375 GLchar *name)
4376{
4377 Program *programObject = getProgram(program);
4378 ASSERT(programObject);
4379 programObject->getActiveAttribute(index, bufsize, length, size, type, name);
4380}
4381
4382void Context::getActiveUniform(GLuint program,
4383 GLuint index,
4384 GLsizei bufsize,
4385 GLsizei *length,
4386 GLint *size,
4387 GLenum *type,
4388 GLchar *name)
4389{
4390 Program *programObject = getProgram(program);
4391 ASSERT(programObject);
4392 programObject->getActiveUniform(index, bufsize, length, size, type, name);
4393}
4394
4395void Context::getAttachedShaders(GLuint program, GLsizei maxcount, GLsizei *count, GLuint *shaders)
4396{
4397 Program *programObject = getProgram(program);
4398 ASSERT(programObject);
4399 programObject->getAttachedShaders(maxcount, count, shaders);
4400}
4401
4402GLint Context::getAttribLocation(GLuint program, const GLchar *name)
4403{
4404 Program *programObject = getProgram(program);
4405 ASSERT(programObject);
4406 return programObject->getAttributeLocation(name);
4407}
4408
4409void Context::getBooleanv(GLenum pname, GLboolean *params)
4410{
4411 GLenum nativeType;
4412 unsigned int numParams = 0;
4413 getQueryParameterInfo(pname, &nativeType, &numParams);
4414
4415 if (nativeType == GL_BOOL)
4416 {
4417 getBooleanvImpl(pname, params);
4418 }
4419 else
4420 {
4421 CastStateValues(this, nativeType, pname, numParams, params);
4422 }
4423}
4424
4425void Context::getFloatv(GLenum pname, GLfloat *params)
4426{
4427 GLenum nativeType;
4428 unsigned int numParams = 0;
4429 getQueryParameterInfo(pname, &nativeType, &numParams);
4430
4431 if (nativeType == GL_FLOAT)
4432 {
4433 getFloatvImpl(pname, params);
4434 }
4435 else
4436 {
4437 CastStateValues(this, nativeType, pname, numParams, params);
4438 }
4439}
4440
4441void Context::getIntegerv(GLenum pname, GLint *params)
4442{
4443 GLenum nativeType;
4444 unsigned int numParams = 0;
4445 getQueryParameterInfo(pname, &nativeType, &numParams);
4446
4447 if (nativeType == GL_INT)
4448 {
4449 getIntegervImpl(pname, params);
4450 }
4451 else
4452 {
4453 CastStateValues(this, nativeType, pname, numParams, params);
4454 }
4455}
4456
4457void Context::getProgramiv(GLuint program, GLenum pname, GLint *params)
4458{
4459 Program *programObject = getProgram(program);
4460 ASSERT(programObject);
Jamie Madillffe00c02017-06-27 16:26:55 -04004461 QueryProgramiv(this, programObject, pname, params);
Jamie Madillc1d770e2017-04-13 17:31:24 -04004462}
4463
Jamie Madillbe849e42017-05-02 15:49:00 -04004464void Context::getProgramInfoLog(GLuint program, GLsizei bufsize, GLsizei *length, GLchar *infolog)
Jamie Madillc1d770e2017-04-13 17:31:24 -04004465{
4466 Program *programObject = getProgram(program);
4467 ASSERT(programObject);
4468 programObject->getInfoLog(bufsize, length, infolog);
4469}
4470
4471void Context::getShaderiv(GLuint shader, GLenum pname, GLint *params)
4472{
4473 Shader *shaderObject = getShader(shader);
4474 ASSERT(shaderObject);
Jamie Madillbd044ed2017-06-05 12:59:21 -04004475 QueryShaderiv(this, shaderObject, pname, params);
Jamie Madillc1d770e2017-04-13 17:31:24 -04004476}
4477
4478void Context::getShaderInfoLog(GLuint shader, GLsizei bufsize, GLsizei *length, GLchar *infolog)
4479{
4480 Shader *shaderObject = getShader(shader);
4481 ASSERT(shaderObject);
Jamie Madillbd044ed2017-06-05 12:59:21 -04004482 shaderObject->getInfoLog(this, bufsize, length, infolog);
Jamie Madillc1d770e2017-04-13 17:31:24 -04004483}
4484
4485void Context::getShaderPrecisionFormat(GLenum shadertype,
4486 GLenum precisiontype,
4487 GLint *range,
4488 GLint *precision)
4489{
4490 // TODO(jmadill): Compute shaders.
4491
4492 switch (shadertype)
4493 {
4494 case GL_VERTEX_SHADER:
4495 switch (precisiontype)
4496 {
4497 case GL_LOW_FLOAT:
4498 mCaps.vertexLowpFloat.get(range, precision);
4499 break;
4500 case GL_MEDIUM_FLOAT:
4501 mCaps.vertexMediumpFloat.get(range, precision);
4502 break;
4503 case GL_HIGH_FLOAT:
4504 mCaps.vertexHighpFloat.get(range, precision);
4505 break;
4506
4507 case GL_LOW_INT:
4508 mCaps.vertexLowpInt.get(range, precision);
4509 break;
4510 case GL_MEDIUM_INT:
4511 mCaps.vertexMediumpInt.get(range, precision);
4512 break;
4513 case GL_HIGH_INT:
4514 mCaps.vertexHighpInt.get(range, precision);
4515 break;
4516
4517 default:
4518 UNREACHABLE();
4519 return;
4520 }
4521 break;
4522
4523 case GL_FRAGMENT_SHADER:
4524 switch (precisiontype)
4525 {
4526 case GL_LOW_FLOAT:
4527 mCaps.fragmentLowpFloat.get(range, precision);
4528 break;
4529 case GL_MEDIUM_FLOAT:
4530 mCaps.fragmentMediumpFloat.get(range, precision);
4531 break;
4532 case GL_HIGH_FLOAT:
4533 mCaps.fragmentHighpFloat.get(range, precision);
4534 break;
4535
4536 case GL_LOW_INT:
4537 mCaps.fragmentLowpInt.get(range, precision);
4538 break;
4539 case GL_MEDIUM_INT:
4540 mCaps.fragmentMediumpInt.get(range, precision);
4541 break;
4542 case GL_HIGH_INT:
4543 mCaps.fragmentHighpInt.get(range, precision);
4544 break;
4545
4546 default:
4547 UNREACHABLE();
4548 return;
4549 }
4550 break;
4551
4552 default:
4553 UNREACHABLE();
4554 return;
4555 }
4556}
4557
4558void Context::getShaderSource(GLuint shader, GLsizei bufsize, GLsizei *length, GLchar *source)
4559{
4560 Shader *shaderObject = getShader(shader);
4561 ASSERT(shaderObject);
4562 shaderObject->getSource(bufsize, length, source);
4563}
4564
4565void Context::getUniformfv(GLuint program, GLint location, GLfloat *params)
4566{
4567 Program *programObject = getProgram(program);
4568 ASSERT(programObject);
4569 programObject->getUniformfv(location, params);
4570}
4571
4572void Context::getUniformiv(GLuint program, GLint location, GLint *params)
4573{
4574 Program *programObject = getProgram(program);
4575 ASSERT(programObject);
4576 programObject->getUniformiv(location, params);
4577}
4578
4579GLint Context::getUniformLocation(GLuint program, const GLchar *name)
4580{
4581 Program *programObject = getProgram(program);
4582 ASSERT(programObject);
4583 return programObject->getUniformLocation(name);
4584}
4585
4586GLboolean Context::isBuffer(GLuint buffer)
4587{
4588 if (buffer == 0)
4589 {
4590 return GL_FALSE;
4591 }
4592
4593 return (getBuffer(buffer) ? GL_TRUE : GL_FALSE);
4594}
4595
4596GLboolean Context::isEnabled(GLenum cap)
4597{
4598 return mGLState.getEnableFeature(cap);
4599}
4600
4601GLboolean Context::isFramebuffer(GLuint framebuffer)
4602{
4603 if (framebuffer == 0)
4604 {
4605 return GL_FALSE;
4606 }
4607
4608 return (getFramebuffer(framebuffer) ? GL_TRUE : GL_FALSE);
4609}
4610
4611GLboolean Context::isProgram(GLuint program)
4612{
4613 if (program == 0)
4614 {
4615 return GL_FALSE;
4616 }
4617
4618 return (getProgram(program) ? GL_TRUE : GL_FALSE);
4619}
4620
4621GLboolean Context::isRenderbuffer(GLuint renderbuffer)
4622{
4623 if (renderbuffer == 0)
4624 {
4625 return GL_FALSE;
4626 }
4627
4628 return (getRenderbuffer(renderbuffer) ? GL_TRUE : GL_FALSE);
4629}
4630
4631GLboolean Context::isShader(GLuint shader)
4632{
4633 if (shader == 0)
4634 {
4635 return GL_FALSE;
4636 }
4637
4638 return (getShader(shader) ? GL_TRUE : GL_FALSE);
4639}
4640
4641GLboolean Context::isTexture(GLuint texture)
4642{
4643 if (texture == 0)
4644 {
4645 return GL_FALSE;
4646 }
4647
4648 return (getTexture(texture) ? GL_TRUE : GL_FALSE);
4649}
4650
4651void Context::linkProgram(GLuint program)
4652{
4653 Program *programObject = getProgram(program);
4654 ASSERT(programObject);
4655 handleError(programObject->link(this));
4656}
4657
4658void Context::releaseShaderCompiler()
4659{
Jamie Madill4928b7c2017-06-20 12:57:39 -04004660 mCompiler.set(this, nullptr);
Jamie Madillc1d770e2017-04-13 17:31:24 -04004661}
4662
4663void Context::shaderBinary(GLsizei n,
4664 const GLuint *shaders,
4665 GLenum binaryformat,
Jamie Madill876429b2017-04-20 15:46:24 -04004666 const void *binary,
Jamie Madillc1d770e2017-04-13 17:31:24 -04004667 GLsizei length)
4668{
4669 // No binary shader formats are supported.
4670 UNIMPLEMENTED();
4671}
4672
4673void Context::shaderSource(GLuint shader,
4674 GLsizei count,
4675 const GLchar *const *string,
4676 const GLint *length)
4677{
4678 Shader *shaderObject = getShader(shader);
4679 ASSERT(shaderObject);
4680 shaderObject->setSource(count, string, length);
4681}
4682
4683void Context::stencilFunc(GLenum func, GLint ref, GLuint mask)
4684{
4685 stencilFuncSeparate(GL_FRONT_AND_BACK, func, ref, mask);
4686}
4687
4688void Context::stencilMask(GLuint mask)
4689{
4690 stencilMaskSeparate(GL_FRONT_AND_BACK, mask);
4691}
4692
4693void Context::stencilOp(GLenum fail, GLenum zfail, GLenum zpass)
4694{
4695 stencilOpSeparate(GL_FRONT_AND_BACK, fail, zfail, zpass);
4696}
4697
4698void Context::uniform1f(GLint location, GLfloat x)
4699{
4700 Program *program = mGLState.getProgram();
4701 program->setUniform1fv(location, 1, &x);
4702}
4703
4704void Context::uniform1fv(GLint location, GLsizei count, const GLfloat *v)
4705{
4706 Program *program = mGLState.getProgram();
4707 program->setUniform1fv(location, count, v);
4708}
4709
4710void Context::uniform1i(GLint location, GLint x)
4711{
4712 Program *program = mGLState.getProgram();
4713 program->setUniform1iv(location, 1, &x);
4714}
4715
4716void Context::uniform1iv(GLint location, GLsizei count, const GLint *v)
4717{
4718 Program *program = mGLState.getProgram();
4719 program->setUniform1iv(location, count, v);
4720}
4721
4722void Context::uniform2f(GLint location, GLfloat x, GLfloat y)
4723{
4724 GLfloat xy[2] = {x, y};
4725 Program *program = mGLState.getProgram();
4726 program->setUniform2fv(location, 1, xy);
4727}
4728
4729void Context::uniform2fv(GLint location, GLsizei count, const GLfloat *v)
4730{
4731 Program *program = mGLState.getProgram();
4732 program->setUniform2fv(location, count, v);
4733}
4734
4735void Context::uniform2i(GLint location, GLint x, GLint y)
4736{
4737 GLint xy[2] = {x, y};
4738 Program *program = mGLState.getProgram();
4739 program->setUniform2iv(location, 1, xy);
4740}
4741
4742void Context::uniform2iv(GLint location, GLsizei count, const GLint *v)
4743{
4744 Program *program = mGLState.getProgram();
4745 program->setUniform2iv(location, count, v);
4746}
4747
4748void Context::uniform3f(GLint location, GLfloat x, GLfloat y, GLfloat z)
4749{
4750 GLfloat xyz[3] = {x, y, z};
4751 Program *program = mGLState.getProgram();
4752 program->setUniform3fv(location, 1, xyz);
4753}
4754
4755void Context::uniform3fv(GLint location, GLsizei count, const GLfloat *v)
4756{
4757 Program *program = mGLState.getProgram();
4758 program->setUniform3fv(location, count, v);
4759}
4760
4761void Context::uniform3i(GLint location, GLint x, GLint y, GLint z)
4762{
4763 GLint xyz[3] = {x, y, z};
4764 Program *program = mGLState.getProgram();
4765 program->setUniform3iv(location, 1, xyz);
4766}
4767
4768void Context::uniform3iv(GLint location, GLsizei count, const GLint *v)
4769{
4770 Program *program = mGLState.getProgram();
4771 program->setUniform3iv(location, count, v);
4772}
4773
4774void Context::uniform4f(GLint location, GLfloat x, GLfloat y, GLfloat z, GLfloat w)
4775{
4776 GLfloat xyzw[4] = {x, y, z, w};
4777 Program *program = mGLState.getProgram();
4778 program->setUniform4fv(location, 1, xyzw);
4779}
4780
4781void Context::uniform4fv(GLint location, GLsizei count, const GLfloat *v)
4782{
4783 Program *program = mGLState.getProgram();
4784 program->setUniform4fv(location, count, v);
4785}
4786
4787void Context::uniform4i(GLint location, GLint x, GLint y, GLint z, GLint w)
4788{
4789 GLint xyzw[4] = {x, y, z, w};
4790 Program *program = mGLState.getProgram();
4791 program->setUniform4iv(location, 1, xyzw);
4792}
4793
4794void Context::uniform4iv(GLint location, GLsizei count, const GLint *v)
4795{
4796 Program *program = mGLState.getProgram();
4797 program->setUniform4iv(location, count, v);
4798}
4799
4800void Context::uniformMatrix2fv(GLint location,
4801 GLsizei count,
4802 GLboolean transpose,
4803 const GLfloat *value)
4804{
4805 Program *program = mGLState.getProgram();
4806 program->setUniformMatrix2fv(location, count, transpose, value);
4807}
4808
4809void Context::uniformMatrix3fv(GLint location,
4810 GLsizei count,
4811 GLboolean transpose,
4812 const GLfloat *value)
4813{
4814 Program *program = mGLState.getProgram();
4815 program->setUniformMatrix3fv(location, count, transpose, value);
4816}
4817
4818void Context::uniformMatrix4fv(GLint location,
4819 GLsizei count,
4820 GLboolean transpose,
4821 const GLfloat *value)
4822{
4823 Program *program = mGLState.getProgram();
4824 program->setUniformMatrix4fv(location, count, transpose, value);
4825}
4826
4827void Context::validateProgram(GLuint program)
4828{
4829 Program *programObject = getProgram(program);
4830 ASSERT(programObject);
4831 programObject->validate(mCaps);
4832}
4833
Jamie Madilld04908b2017-06-09 14:15:35 -04004834void Context::getProgramBinary(GLuint program,
4835 GLsizei bufSize,
4836 GLsizei *length,
4837 GLenum *binaryFormat,
4838 void *binary)
4839{
4840 Program *programObject = getProgram(program);
4841 ASSERT(programObject != nullptr);
4842
4843 handleError(programObject->saveBinary(this, binaryFormat, binary, bufSize, length));
4844}
4845
4846void Context::programBinary(GLuint program, GLenum binaryFormat, const void *binary, GLsizei length)
4847{
4848 Program *programObject = getProgram(program);
4849 ASSERT(programObject != nullptr);
Jamie Madillb6664922017-07-25 12:55:04 -04004850
Jamie Madilld04908b2017-06-09 14:15:35 -04004851 handleError(programObject->loadBinary(this, binaryFormat, binary, length));
4852}
4853
Jamie Madillff325f12017-08-26 15:06:05 -04004854void Context::uniform1ui(GLint location, GLuint v0)
4855{
4856 Program *program = mGLState.getProgram();
4857 program->setUniform1uiv(location, 1, &v0);
4858}
4859
4860void Context::uniform2ui(GLint location, GLuint v0, GLuint v1)
4861{
4862 Program *program = mGLState.getProgram();
4863 const GLuint xy[] = {v0, v1};
4864 program->setUniform2uiv(location, 1, xy);
4865}
4866
4867void Context::uniform3ui(GLint location, GLuint v0, GLuint v1, GLuint v2)
4868{
4869 Program *program = mGLState.getProgram();
4870 const GLuint xyz[] = {v0, v1, v2};
4871 program->setUniform3uiv(location, 1, xyz);
4872}
4873
4874void Context::uniform4ui(GLint location, GLuint v0, GLuint v1, GLuint v2, GLuint v3)
4875{
4876 Program *program = mGLState.getProgram();
4877 const GLuint xyzw[] = {v0, v1, v2, v3};
4878 program->setUniform4uiv(location, 1, xyzw);
4879}
4880
4881void Context::uniform1uiv(GLint location, GLsizei count, const GLuint *value)
4882{
4883 Program *program = mGLState.getProgram();
4884 program->setUniform1uiv(location, count, value);
4885}
4886void Context::uniform2uiv(GLint location, GLsizei count, const GLuint *value)
4887{
4888 Program *program = mGLState.getProgram();
4889 program->setUniform2uiv(location, count, value);
4890}
4891
4892void Context::uniform3uiv(GLint location, GLsizei count, const GLuint *value)
4893{
4894 Program *program = mGLState.getProgram();
4895 program->setUniform3uiv(location, count, value);
4896}
4897
4898void Context::uniform4uiv(GLint location, GLsizei count, const GLuint *value)
4899{
4900 Program *program = mGLState.getProgram();
4901 program->setUniform4uiv(location, count, value);
4902}
4903
Jamie Madillf0e04492017-08-26 15:28:42 -04004904void Context::genQueries(GLsizei n, GLuint *ids)
4905{
4906 for (GLsizei i = 0; i < n; i++)
4907 {
4908 GLuint handle = mQueryHandleAllocator.allocate();
4909 mQueryMap.assign(handle, nullptr);
4910 ids[i] = handle;
4911 }
4912}
4913
4914void Context::deleteQueries(GLsizei n, const GLuint *ids)
4915{
4916 for (int i = 0; i < n; i++)
4917 {
4918 GLuint query = ids[i];
4919
4920 Query *queryObject = nullptr;
4921 if (mQueryMap.erase(query, &queryObject))
4922 {
4923 mQueryHandleAllocator.release(query);
4924 if (queryObject)
4925 {
4926 queryObject->release(this);
4927 }
4928 }
4929 }
4930}
4931
4932GLboolean Context::isQuery(GLuint id)
4933{
4934 return (getQuery(id, false, GL_NONE) != nullptr) ? GL_TRUE : GL_FALSE;
4935}
4936
Jamie Madillc8c95812017-08-26 18:40:09 -04004937void Context::uniformMatrix2x3fv(GLint location,
4938 GLsizei count,
4939 GLboolean transpose,
4940 const GLfloat *value)
4941{
4942 Program *program = mGLState.getProgram();
4943 program->setUniformMatrix2x3fv(location, count, transpose, value);
4944}
4945
4946void Context::uniformMatrix3x2fv(GLint location,
4947 GLsizei count,
4948 GLboolean transpose,
4949 const GLfloat *value)
4950{
4951 Program *program = mGLState.getProgram();
4952 program->setUniformMatrix3x2fv(location, count, transpose, value);
4953}
4954
4955void Context::uniformMatrix2x4fv(GLint location,
4956 GLsizei count,
4957 GLboolean transpose,
4958 const GLfloat *value)
4959{
4960 Program *program = mGLState.getProgram();
4961 program->setUniformMatrix2x4fv(location, count, transpose, value);
4962}
4963
4964void Context::uniformMatrix4x2fv(GLint location,
4965 GLsizei count,
4966 GLboolean transpose,
4967 const GLfloat *value)
4968{
4969 Program *program = mGLState.getProgram();
4970 program->setUniformMatrix4x2fv(location, count, transpose, value);
4971}
4972
4973void Context::uniformMatrix3x4fv(GLint location,
4974 GLsizei count,
4975 GLboolean transpose,
4976 const GLfloat *value)
4977{
4978 Program *program = mGLState.getProgram();
4979 program->setUniformMatrix3x4fv(location, count, transpose, value);
4980}
4981
4982void Context::uniformMatrix4x3fv(GLint location,
4983 GLsizei count,
4984 GLboolean transpose,
4985 const GLfloat *value)
4986{
4987 Program *program = mGLState.getProgram();
4988 program->setUniformMatrix4x3fv(location, count, transpose, value);
4989}
4990
Jamie Madilld7576732017-08-26 18:49:50 -04004991void Context::deleteVertexArrays(GLsizei n, const GLuint *arrays)
4992{
4993 for (int arrayIndex = 0; arrayIndex < n; arrayIndex++)
4994 {
4995 GLuint vertexArray = arrays[arrayIndex];
4996
4997 if (arrays[arrayIndex] != 0)
4998 {
4999 VertexArray *vertexArrayObject = nullptr;
5000 if (mVertexArrayMap.erase(vertexArray, &vertexArrayObject))
5001 {
5002 if (vertexArrayObject != nullptr)
5003 {
5004 detachVertexArray(vertexArray);
5005 vertexArrayObject->onDestroy(this);
5006 }
5007
5008 mVertexArrayHandleAllocator.release(vertexArray);
5009 }
5010 }
5011 }
5012}
5013
5014void Context::genVertexArrays(GLsizei n, GLuint *arrays)
5015{
5016 for (int arrayIndex = 0; arrayIndex < n; arrayIndex++)
5017 {
5018 GLuint vertexArray = mVertexArrayHandleAllocator.allocate();
5019 mVertexArrayMap.assign(vertexArray, nullptr);
5020 arrays[arrayIndex] = vertexArray;
5021 }
5022}
5023
5024bool Context::isVertexArray(GLuint array)
5025{
5026 if (array == 0)
5027 {
5028 return GL_FALSE;
5029 }
5030
5031 VertexArray *vao = getVertexArray(array);
5032 return (vao != nullptr ? GL_TRUE : GL_FALSE);
5033}
5034
Jamie Madillc29968b2016-01-20 11:17:23 -05005035} // namespace gl