blob: 612ff9c7dd1e69a7d589b5f4b717b7108920e6e9 [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
Jamie Madillf0dcb8b2017-08-26 19:05:13 -0400377 bindTransformFeedback(GL_TRANSFORM_FEEDBACK, 0);
Geoff Lang1a683462015-09-29 15:09:59 -0400378 }
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
Sami Väisänene45e53b2016-05-25 10:36:04 +0300609GLuint Context::createPaths(GLsizei range)
610{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500611 auto resultOrError = mState.mPaths->createPaths(mImplementation.get(), range);
Sami Väisänene45e53b2016-05-25 10:36:04 +0300612 if (resultOrError.isError())
613 {
614 handleError(resultOrError.getError());
615 return 0;
616 }
617 return resultOrError.getResult();
618}
619
Jamie Madilldc356042013-07-19 16:36:57 -0400620GLuint Context::createSampler()
621{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500622 return mState.mSamplers->createSampler();
Jamie Madilldc356042013-07-19 16:36:57 -0400623}
624
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000625// Returns an unused framebuffer name
626GLuint Context::createFramebuffer()
627{
Geoff Lang3bf8e3a2016-12-01 17:28:52 -0500628 return mState.mFramebuffers->createFramebuffer();
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000629}
630
Jamie Madill33dc8432013-07-26 11:55:05 -0400631GLuint Context::createFenceNV()
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000632{
Jamie Madill33dc8432013-07-26 11:55:05 -0400633 GLuint handle = mFenceNVHandleAllocator.allocate();
Jamie Madill96a483b2017-06-27 16:49:21 -0400634 mFenceNVMap.assign(handle, new FenceNV(mImplementation->createFenceNV()));
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000635 return handle;
636}
637
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000638void Context::deleteBuffer(GLuint buffer)
639{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500640 if (mState.mBuffers->getBuffer(buffer))
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000641 {
642 detachBuffer(buffer);
643 }
Jamie Madill893ab082014-05-16 16:56:10 -0400644
Jamie Madill6c1f6712017-02-14 19:08:04 -0500645 mState.mBuffers->deleteObject(this, buffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000646}
647
648void Context::deleteShader(GLuint shader)
649{
Jamie Madill6c1f6712017-02-14 19:08:04 -0500650 mState.mShaderPrograms->deleteShader(this, shader);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000651}
652
653void Context::deleteProgram(GLuint program)
654{
Jamie Madill6c1f6712017-02-14 19:08:04 -0500655 mState.mShaderPrograms->deleteProgram(this, program);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000656}
657
658void Context::deleteTexture(GLuint texture)
659{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500660 if (mState.mTextures->getTexture(texture))
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000661 {
662 detachTexture(texture);
663 }
664
Jamie Madill6c1f6712017-02-14 19:08:04 -0500665 mState.mTextures->deleteObject(this, texture);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000666}
667
668void Context::deleteRenderbuffer(GLuint renderbuffer)
669{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500670 if (mState.mRenderbuffers->getRenderbuffer(renderbuffer))
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000671 {
672 detachRenderbuffer(renderbuffer);
673 }
Jamie Madill893ab082014-05-16 16:56:10 -0400674
Jamie Madill6c1f6712017-02-14 19:08:04 -0500675 mState.mRenderbuffers->deleteObject(this, renderbuffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000676}
677
Jamie Madill7f0c5a42017-08-26 22:43:26 -0400678void Context::deleteSync(GLsync sync)
Jamie Madillcd055f82013-07-26 11:55:15 -0400679{
680 // The spec specifies the underlying Fence object is not deleted until all current
681 // wait commands finish. However, since the name becomes invalid, we cannot query the fence,
682 // and since our API is currently designed for being called from a single thread, we can delete
683 // the fence immediately.
Jamie Madill7f0c5a42017-08-26 22:43:26 -0400684 mState.mFenceSyncs->deleteObject(this, static_cast<GLuint>(reinterpret_cast<uintptr_t>(sync)));
Jamie Madillcd055f82013-07-26 11:55:15 -0400685}
686
Sami Väisänene45e53b2016-05-25 10:36:04 +0300687void Context::deletePaths(GLuint first, GLsizei range)
688{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500689 mState.mPaths->deletePaths(first, range);
Sami Väisänene45e53b2016-05-25 10:36:04 +0300690}
691
692bool Context::hasPathData(GLuint path) const
693{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500694 const auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +0300695 if (pathObj == nullptr)
696 return false;
697
698 return pathObj->hasPathData();
699}
700
701bool Context::hasPath(GLuint path) const
702{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500703 return mState.mPaths->hasPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +0300704}
705
706void Context::setPathCommands(GLuint path,
707 GLsizei numCommands,
708 const GLubyte *commands,
709 GLsizei numCoords,
710 GLenum coordType,
711 const void *coords)
712{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500713 auto *pathObject = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +0300714
715 handleError(pathObject->setCommands(numCommands, commands, numCoords, coordType, coords));
716}
717
718void Context::setPathParameterf(GLuint path, GLenum pname, GLfloat value)
719{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500720 auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +0300721
722 switch (pname)
723 {
724 case GL_PATH_STROKE_WIDTH_CHROMIUM:
725 pathObj->setStrokeWidth(value);
726 break;
727 case GL_PATH_END_CAPS_CHROMIUM:
728 pathObj->setEndCaps(static_cast<GLenum>(value));
729 break;
730 case GL_PATH_JOIN_STYLE_CHROMIUM:
731 pathObj->setJoinStyle(static_cast<GLenum>(value));
732 break;
733 case GL_PATH_MITER_LIMIT_CHROMIUM:
734 pathObj->setMiterLimit(value);
735 break;
736 case GL_PATH_STROKE_BOUND_CHROMIUM:
737 pathObj->setStrokeBound(value);
738 break;
739 default:
740 UNREACHABLE();
741 break;
742 }
743}
744
745void Context::getPathParameterfv(GLuint path, GLenum pname, GLfloat *value) const
746{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500747 const auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +0300748
749 switch (pname)
750 {
751 case GL_PATH_STROKE_WIDTH_CHROMIUM:
752 *value = pathObj->getStrokeWidth();
753 break;
754 case GL_PATH_END_CAPS_CHROMIUM:
755 *value = static_cast<GLfloat>(pathObj->getEndCaps());
756 break;
757 case GL_PATH_JOIN_STYLE_CHROMIUM:
758 *value = static_cast<GLfloat>(pathObj->getJoinStyle());
759 break;
760 case GL_PATH_MITER_LIMIT_CHROMIUM:
761 *value = pathObj->getMiterLimit();
762 break;
763 case GL_PATH_STROKE_BOUND_CHROMIUM:
764 *value = pathObj->getStrokeBound();
765 break;
766 default:
767 UNREACHABLE();
768 break;
769 }
770}
771
772void Context::setPathStencilFunc(GLenum func, GLint ref, GLuint mask)
773{
774 mGLState.setPathStencilFunc(func, ref, mask);
775}
776
Jamie Madilldc356042013-07-19 16:36:57 -0400777void Context::deleteSampler(GLuint sampler)
778{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500779 if (mState.mSamplers->getSampler(sampler))
Jamie Madilldc356042013-07-19 16:36:57 -0400780 {
781 detachSampler(sampler);
782 }
783
Jamie Madill6c1f6712017-02-14 19:08:04 -0500784 mState.mSamplers->deleteObject(this, sampler);
Jamie Madilldc356042013-07-19 16:36:57 -0400785}
786
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000787void Context::deleteFramebuffer(GLuint framebuffer)
788{
Geoff Lang3bf8e3a2016-12-01 17:28:52 -0500789 if (mState.mFramebuffers->getFramebuffer(framebuffer))
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000790 {
791 detachFramebuffer(framebuffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000792 }
Geoff Lang3bf8e3a2016-12-01 17:28:52 -0500793
Jamie Madill6c1f6712017-02-14 19:08:04 -0500794 mState.mFramebuffers->deleteObject(this, framebuffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000795}
796
Jamie Madill33dc8432013-07-26 11:55:05 -0400797void Context::deleteFenceNV(GLuint fence)
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000798{
Jamie Madill96a483b2017-06-27 16:49:21 -0400799 FenceNV *fenceObject = nullptr;
800 if (mFenceNVMap.erase(fence, &fenceObject))
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000801 {
Jamie Madill96a483b2017-06-27 16:49:21 -0400802 mFenceNVHandleAllocator.release(fence);
803 delete fenceObject;
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000804 }
805}
806
Geoff Lang70d0f492015-12-10 17:45:46 -0500807Buffer *Context::getBuffer(GLuint handle) const
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000808{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500809 return mState.mBuffers->getBuffer(handle);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000810}
811
Jamie Madill570f7c82014-07-03 10:38:54 -0400812Texture *Context::getTexture(GLuint handle) const
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000813{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500814 return mState.mTextures->getTexture(handle);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000815}
816
Geoff Lang70d0f492015-12-10 17:45:46 -0500817Renderbuffer *Context::getRenderbuffer(GLuint handle) const
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000818{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500819 return mState.mRenderbuffers->getRenderbuffer(handle);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000820}
821
Jamie Madillcd055f82013-07-26 11:55:15 -0400822FenceSync *Context::getFenceSync(GLsync handle) const
823{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500824 return mState.mFenceSyncs->getFenceSync(
825 static_cast<GLuint>(reinterpret_cast<uintptr_t>(handle)));
Jamie Madillcd055f82013-07-26 11:55:15 -0400826}
827
Jamie Madill57a89722013-07-02 11:57:03 -0400828VertexArray *Context::getVertexArray(GLuint handle) const
829{
Jamie Madill96a483b2017-06-27 16:49:21 -0400830 return mVertexArrayMap.query(handle);
Jamie Madill57a89722013-07-02 11:57:03 -0400831}
832
Jamie Madilldc356042013-07-19 16:36:57 -0400833Sampler *Context::getSampler(GLuint handle) const
834{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500835 return mState.mSamplers->getSampler(handle);
Jamie Madilldc356042013-07-19 16:36:57 -0400836}
837
Geoff Langc8058452014-02-03 12:04:11 -0500838TransformFeedback *Context::getTransformFeedback(GLuint handle) const
839{
Jamie Madill96a483b2017-06-27 16:49:21 -0400840 return mTransformFeedbackMap.query(handle);
Geoff Langc8058452014-02-03 12:04:11 -0500841}
842
Geoff Lang70d0f492015-12-10 17:45:46 -0500843LabeledObject *Context::getLabeledObject(GLenum identifier, GLuint name) const
844{
845 switch (identifier)
846 {
847 case GL_BUFFER:
848 return getBuffer(name);
849 case GL_SHADER:
850 return getShader(name);
851 case GL_PROGRAM:
852 return getProgram(name);
853 case GL_VERTEX_ARRAY:
854 return getVertexArray(name);
855 case GL_QUERY:
856 return getQuery(name);
857 case GL_TRANSFORM_FEEDBACK:
858 return getTransformFeedback(name);
859 case GL_SAMPLER:
860 return getSampler(name);
861 case GL_TEXTURE:
862 return getTexture(name);
863 case GL_RENDERBUFFER:
864 return getRenderbuffer(name);
865 case GL_FRAMEBUFFER:
866 return getFramebuffer(name);
867 default:
868 UNREACHABLE();
869 return nullptr;
870 }
871}
872
873LabeledObject *Context::getLabeledObjectFromPtr(const void *ptr) const
874{
875 return getFenceSync(reinterpret_cast<GLsync>(const_cast<void *>(ptr)));
876}
877
Martin Radev9d901792016-07-15 15:58:58 +0300878void Context::objectLabel(GLenum identifier, GLuint name, GLsizei length, const GLchar *label)
879{
880 LabeledObject *object = getLabeledObject(identifier, name);
881 ASSERT(object != nullptr);
882
883 std::string labelName = GetObjectLabelFromPointer(length, label);
884 object->setLabel(labelName);
885}
886
887void Context::objectPtrLabel(const void *ptr, GLsizei length, const GLchar *label)
888{
889 LabeledObject *object = getLabeledObjectFromPtr(ptr);
890 ASSERT(object != nullptr);
891
892 std::string labelName = GetObjectLabelFromPointer(length, label);
893 object->setLabel(labelName);
894}
895
896void Context::getObjectLabel(GLenum identifier,
897 GLuint name,
898 GLsizei bufSize,
899 GLsizei *length,
900 GLchar *label) const
901{
902 LabeledObject *object = getLabeledObject(identifier, name);
903 ASSERT(object != nullptr);
904
905 const std::string &objectLabel = object->getLabel();
906 GetObjectLabelBase(objectLabel, bufSize, length, label);
907}
908
909void Context::getObjectPtrLabel(const void *ptr,
910 GLsizei bufSize,
911 GLsizei *length,
912 GLchar *label) const
913{
914 LabeledObject *object = getLabeledObjectFromPtr(ptr);
915 ASSERT(object != nullptr);
916
917 const std::string &objectLabel = object->getLabel();
918 GetObjectLabelBase(objectLabel, bufSize, length, label);
919}
920
Jamie Madilldc356042013-07-19 16:36:57 -0400921bool Context::isSampler(GLuint samplerName) const
922{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500923 return mState.mSamplers->isSampler(samplerName);
Jamie Madilldc356042013-07-19 16:36:57 -0400924}
925
Jamie Madill3f01e6c2016-03-08 13:53:02 -0500926void Context::bindArrayBuffer(GLuint bufferHandle)
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000927{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500928 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -0400929 mGLState.setArrayBufferBinding(this, buffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000930}
931
Jiajia Qin9d7d0b12016-11-29 16:30:31 +0800932void Context::bindDrawIndirectBuffer(GLuint bufferHandle)
933{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500934 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -0400935 mGLState.setDrawIndirectBufferBinding(this, buffer);
Jiajia Qin9d7d0b12016-11-29 16:30:31 +0800936}
937
Jamie Madill3f01e6c2016-03-08 13:53:02 -0500938void Context::bindElementArrayBuffer(GLuint bufferHandle)
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000939{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500940 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -0400941 mGLState.setElementArrayBuffer(this, buffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000942}
943
Jamie Madilldedd7b92014-11-05 16:30:36 -0500944void Context::bindTexture(GLenum target, GLuint handle)
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000945{
Jamie Madill3f01e6c2016-03-08 13:53:02 -0500946 Texture *texture = nullptr;
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000947
Jamie Madilldedd7b92014-11-05 16:30:36 -0500948 if (handle == 0)
949 {
950 texture = mZeroTextures[target].get();
951 }
952 else
953 {
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500954 texture = mState.mTextures->checkTextureAllocation(mImplementation.get(), handle, target);
Jamie Madilldedd7b92014-11-05 16:30:36 -0500955 }
956
957 ASSERT(texture);
Jamie Madill4928b7c2017-06-20 12:57:39 -0400958 mGLState.setSamplerTexture(this, target, texture);
shannon.woods%transgaming.com@gtempaccount.com90dbc442013-04-13 03:46:14 +0000959}
960
Jamie Madill5bf9ff42016-02-01 11:13:03 -0500961void Context::bindReadFramebuffer(GLuint framebufferHandle)
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000962{
Geoff Lang3bf8e3a2016-12-01 17:28:52 -0500963 Framebuffer *framebuffer = mState.mFramebuffers->checkFramebufferAllocation(
964 mImplementation.get(), mCaps, framebufferHandle);
Jamie Madilldfde6ab2016-06-09 07:07:18 -0700965 mGLState.setReadFramebufferBinding(framebuffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000966}
967
Jamie Madill5bf9ff42016-02-01 11:13:03 -0500968void Context::bindDrawFramebuffer(GLuint framebufferHandle)
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000969{
Geoff Lang3bf8e3a2016-12-01 17:28:52 -0500970 Framebuffer *framebuffer = mState.mFramebuffers->checkFramebufferAllocation(
971 mImplementation.get(), mCaps, framebufferHandle);
Jamie Madilldfde6ab2016-06-09 07:07:18 -0700972 mGLState.setDrawFramebufferBinding(framebuffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000973}
974
Jamie Madill3f01e6c2016-03-08 13:53:02 -0500975void Context::bindVertexArray(GLuint vertexArrayHandle)
Jamie Madill57a89722013-07-02 11:57:03 -0400976{
Jamie Madill3f01e6c2016-03-08 13:53:02 -0500977 VertexArray *vertexArray = checkVertexArrayAllocation(vertexArrayHandle);
Jamie Madilldfde6ab2016-06-09 07:07:18 -0700978 mGLState.setVertexArrayBinding(vertexArray);
Jamie Madill57a89722013-07-02 11:57:03 -0400979}
980
Shao80957d92017-02-20 21:25:59 +0800981void Context::bindVertexBuffer(GLuint bindingIndex,
982 GLuint bufferHandle,
983 GLintptr offset,
984 GLsizei stride)
985{
986 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -0400987 mGLState.bindVertexBuffer(this, bindingIndex, buffer, offset, stride);
Shao80957d92017-02-20 21:25:59 +0800988}
989
Jamie Madill3f01e6c2016-03-08 13:53:02 -0500990void Context::bindSampler(GLuint textureUnit, GLuint samplerHandle)
Jamie Madilldc356042013-07-19 16:36:57 -0400991{
Geoff Lang76b10c92014-09-05 16:28:14 -0400992 ASSERT(textureUnit < mCaps.maxCombinedTextureImageUnits);
Jamie Madill901b3792016-05-26 09:20:40 -0400993 Sampler *sampler =
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500994 mState.mSamplers->checkSamplerAllocation(mImplementation.get(), samplerHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -0400995 mGLState.setSamplerBinding(this, textureUnit, sampler);
Jamie Madilldc356042013-07-19 16:36:57 -0400996}
997
Xinghua Cao65ec0b22017-03-28 16:10:52 +0800998void Context::bindImageTexture(GLuint unit,
999 GLuint texture,
1000 GLint level,
1001 GLboolean layered,
1002 GLint layer,
1003 GLenum access,
1004 GLenum format)
1005{
1006 Texture *tex = mState.mTextures->getTexture(texture);
1007 mGLState.setImageUnit(this, unit, tex, level, layered, layer, access, format);
1008}
1009
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001010void Context::bindGenericUniformBuffer(GLuint bufferHandle)
shannon.woods%transgaming.com@gtempaccount.com667a29c2013-04-13 03:39:04 +00001011{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001012 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001013 mGLState.setGenericUniformBufferBinding(this, buffer);
shannon.woods%transgaming.com@gtempaccount.com667a29c2013-04-13 03:39:04 +00001014}
1015
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001016void Context::bindIndexedUniformBuffer(GLuint bufferHandle,
1017 GLuint index,
1018 GLintptr offset,
1019 GLsizeiptr size)
shannon.woods%transgaming.com@gtempaccount.com34089352013-04-13 03:36:57 +00001020{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001021 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001022 mGLState.setIndexedUniformBufferBinding(this, index, buffer, offset, size);
shannon.woods%transgaming.com@gtempaccount.com34089352013-04-13 03:36:57 +00001023}
1024
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001025void Context::bindGenericTransformFeedbackBuffer(GLuint bufferHandle)
shannon.woods%transgaming.com@gtempaccount.com667a29c2013-04-13 03:39:04 +00001026{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001027 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001028 mGLState.getCurrentTransformFeedback()->bindGenericBuffer(this, buffer);
shannon.woods%transgaming.com@gtempaccount.com667a29c2013-04-13 03:39:04 +00001029}
1030
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001031void Context::bindIndexedTransformFeedbackBuffer(GLuint bufferHandle,
1032 GLuint index,
1033 GLintptr offset,
1034 GLsizeiptr size)
shannon.woods%transgaming.com@gtempaccount.com34089352013-04-13 03:36:57 +00001035{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001036 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001037 mGLState.getCurrentTransformFeedback()->bindIndexedBuffer(this, index, buffer, offset, size);
shannon.woods%transgaming.com@gtempaccount.com34089352013-04-13 03:36:57 +00001038}
1039
Jiajia Qin6eafb042016-12-27 17:04:07 +08001040void Context::bindGenericAtomicCounterBuffer(GLuint bufferHandle)
1041{
1042 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001043 mGLState.setGenericAtomicCounterBufferBinding(this, buffer);
Jiajia Qin6eafb042016-12-27 17:04:07 +08001044}
1045
1046void Context::bindIndexedAtomicCounterBuffer(GLuint bufferHandle,
1047 GLuint index,
1048 GLintptr offset,
1049 GLsizeiptr size)
1050{
1051 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001052 mGLState.setIndexedAtomicCounterBufferBinding(this, index, buffer, offset, size);
Jiajia Qin6eafb042016-12-27 17:04:07 +08001053}
1054
Jiajia Qinf546e7d2017-03-27 14:12:59 +08001055void Context::bindGenericShaderStorageBuffer(GLuint bufferHandle)
1056{
1057 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001058 mGLState.setGenericShaderStorageBufferBinding(this, buffer);
Jiajia Qinf546e7d2017-03-27 14:12:59 +08001059}
1060
1061void Context::bindIndexedShaderStorageBuffer(GLuint bufferHandle,
1062 GLuint index,
1063 GLintptr offset,
1064 GLsizeiptr size)
1065{
1066 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001067 mGLState.setIndexedShaderStorageBufferBinding(this, index, buffer, offset, size);
Jiajia Qinf546e7d2017-03-27 14:12:59 +08001068}
1069
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001070void Context::bindCopyReadBuffer(GLuint bufferHandle)
shannon.woods%transgaming.com@gtempaccount.com51171882013-04-13 03:39:10 +00001071{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001072 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001073 mGLState.setCopyReadBufferBinding(this, buffer);
shannon.woods%transgaming.com@gtempaccount.com51171882013-04-13 03:39:10 +00001074}
1075
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001076void Context::bindCopyWriteBuffer(GLuint bufferHandle)
shannon.woods%transgaming.com@gtempaccount.com51171882013-04-13 03:39:10 +00001077{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001078 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001079 mGLState.setCopyWriteBufferBinding(this, buffer);
shannon.woods%transgaming.com@gtempaccount.com51171882013-04-13 03:39:10 +00001080}
1081
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001082void Context::bindPixelPackBuffer(GLuint bufferHandle)
shannon.woods%transgaming.com@gtempaccount.comc926e5f2013-04-13 03:39:18 +00001083{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001084 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001085 mGLState.setPixelPackBufferBinding(this, buffer);
shannon.woods%transgaming.com@gtempaccount.comc926e5f2013-04-13 03:39:18 +00001086}
1087
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001088void Context::bindPixelUnpackBuffer(GLuint bufferHandle)
shannon.woods%transgaming.com@gtempaccount.comc926e5f2013-04-13 03:39:18 +00001089{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001090 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001091 mGLState.setPixelUnpackBufferBinding(this, buffer);
shannon.woods%transgaming.com@gtempaccount.comc926e5f2013-04-13 03:39:18 +00001092}
1093
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001094void Context::useProgram(GLuint program)
1095{
Jamie Madill6c1f6712017-02-14 19:08:04 -05001096 mGLState.setProgram(this, getProgram(program));
daniel@transgaming.com95d29422012-07-24 18:36:10 +00001097}
1098
Jamie Madillf0dcb8b2017-08-26 19:05:13 -04001099void Context::bindTransformFeedback(GLenum target, GLuint transformFeedbackHandle)
Geoff Langc8058452014-02-03 12:04:11 -05001100{
Jamie Madillf0dcb8b2017-08-26 19:05:13 -04001101 ASSERT(target == GL_TRANSFORM_FEEDBACK);
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001102 TransformFeedback *transformFeedback =
1103 checkTransformFeedbackAllocation(transformFeedbackHandle);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001104 mGLState.setTransformFeedbackBinding(this, transformFeedback);
Geoff Langc8058452014-02-03 12:04:11 -05001105}
1106
Jamie Madillf0e04492017-08-26 15:28:42 -04001107void Context::beginQuery(GLenum target, GLuint query)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001108{
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001109 Query *queryObject = getQuery(query, true, target);
Jamie Madilldb2f14c2014-05-13 13:56:30 -04001110 ASSERT(queryObject);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001111
Geoff Lang5aad9672014-09-08 11:10:42 -04001112 // begin query
Jamie Madillf0e04492017-08-26 15:28:42 -04001113 ANGLE_CONTEXT_TRY(queryObject->begin());
Geoff Lang5aad9672014-09-08 11:10:42 -04001114
1115 // set query as active for specified target only if begin succeeded
Jamie Madill4928b7c2017-06-20 12:57:39 -04001116 mGLState.setActiveQuery(this, target, queryObject);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001117}
1118
Jamie Madillf0e04492017-08-26 15:28:42 -04001119void Context::endQuery(GLenum target)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001120{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001121 Query *queryObject = mGLState.getActiveQuery(target);
Jamie Madill45c785d2014-05-13 14:09:34 -04001122 ASSERT(queryObject);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001123
Jamie Madillf0e04492017-08-26 15:28:42 -04001124 handleError(queryObject->end());
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001125
Geoff Lang5aad9672014-09-08 11:10:42 -04001126 // Always unbind the query, even if there was an error. This may delete the query object.
Jamie Madill4928b7c2017-06-20 12:57:39 -04001127 mGLState.setActiveQuery(this, target, nullptr);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001128}
1129
Jamie Madillf0e04492017-08-26 15:28:42 -04001130void Context::queryCounter(GLuint id, GLenum target)
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001131{
1132 ASSERT(target == GL_TIMESTAMP_EXT);
1133
1134 Query *queryObject = getQuery(id, true, target);
1135 ASSERT(queryObject);
1136
Jamie Madillf0e04492017-08-26 15:28:42 -04001137 handleError(queryObject->queryCounter());
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001138}
1139
1140void Context::getQueryiv(GLenum target, GLenum pname, GLint *params)
1141{
1142 switch (pname)
1143 {
1144 case GL_CURRENT_QUERY_EXT:
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001145 params[0] = mGLState.getActiveQueryId(target);
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001146 break;
1147 case GL_QUERY_COUNTER_BITS_EXT:
1148 switch (target)
1149 {
1150 case GL_TIME_ELAPSED_EXT:
1151 params[0] = getExtensions().queryCounterBitsTimeElapsed;
1152 break;
1153 case GL_TIMESTAMP_EXT:
1154 params[0] = getExtensions().queryCounterBitsTimestamp;
1155 break;
1156 default:
1157 UNREACHABLE();
1158 params[0] = 0;
1159 break;
1160 }
1161 break;
1162 default:
1163 UNREACHABLE();
1164 return;
1165 }
1166}
1167
Geoff Lang2186c382016-10-14 10:54:54 -04001168void Context::getQueryObjectiv(GLuint id, GLenum pname, GLint *params)
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001169{
Geoff Lang2186c382016-10-14 10:54:54 -04001170 handleError(GetQueryObjectParameter(getQuery(id), pname, params));
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001171}
1172
Geoff Lang2186c382016-10-14 10:54:54 -04001173void Context::getQueryObjectuiv(GLuint id, GLenum pname, GLuint *params)
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001174{
Geoff Lang2186c382016-10-14 10:54:54 -04001175 handleError(GetQueryObjectParameter(getQuery(id), pname, params));
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001176}
1177
Geoff Lang2186c382016-10-14 10:54:54 -04001178void Context::getQueryObjecti64v(GLuint id, GLenum pname, GLint64 *params)
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001179{
Geoff Lang2186c382016-10-14 10:54:54 -04001180 handleError(GetQueryObjectParameter(getQuery(id), pname, params));
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001181}
1182
Geoff Lang2186c382016-10-14 10:54:54 -04001183void Context::getQueryObjectui64v(GLuint id, GLenum pname, GLuint64 *params)
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001184{
Geoff Lang2186c382016-10-14 10:54:54 -04001185 handleError(GetQueryObjectParameter(getQuery(id), pname, params));
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001186}
1187
Geoff Lang3bf8e3a2016-12-01 17:28:52 -05001188Framebuffer *Context::getFramebuffer(GLuint handle) const
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001189{
Geoff Lang3bf8e3a2016-12-01 17:28:52 -05001190 return mState.mFramebuffers->getFramebuffer(handle);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001191}
1192
Jamie Madill2f348d22017-06-05 10:50:59 -04001193FenceNV *Context::getFenceNV(GLuint handle)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001194{
Jamie Madill96a483b2017-06-27 16:49:21 -04001195 return mFenceNVMap.query(handle);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001196}
1197
Jamie Madill2f348d22017-06-05 10:50:59 -04001198Query *Context::getQuery(GLuint handle, bool create, GLenum type)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001199{
Jamie Madill96a483b2017-06-27 16:49:21 -04001200 if (!mQueryMap.contains(handle))
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001201 {
Yunchao Hef81ce4a2017-04-24 10:49:17 +08001202 return nullptr;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001203 }
Jamie Madill96a483b2017-06-27 16:49:21 -04001204
1205 Query *query = mQueryMap.query(handle);
1206 if (!query && create)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001207 {
Jamie Madill96a483b2017-06-27 16:49:21 -04001208 query = new Query(mImplementation->createQuery(type), handle);
1209 query->addRef();
1210 mQueryMap.assign(handle, query);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001211 }
Jamie Madill96a483b2017-06-27 16:49:21 -04001212 return query;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001213}
1214
Geoff Lang70d0f492015-12-10 17:45:46 -05001215Query *Context::getQuery(GLuint handle) const
1216{
Jamie Madill96a483b2017-06-27 16:49:21 -04001217 return mQueryMap.query(handle);
Geoff Lang70d0f492015-12-10 17:45:46 -05001218}
1219
Jamie Madill1fc7e2c2014-01-21 16:47:10 -05001220Texture *Context::getTargetTexture(GLenum target) const
1221{
Ian Ewellbda75592016-04-18 17:25:54 -04001222 ASSERT(ValidTextureTarget(this, target) || ValidTextureExternalTarget(this, target));
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001223 return mGLState.getTargetTexture(target);
shannon.woods%transgaming.com@gtempaccount.comc926e5f2013-04-13 03:39:18 +00001224}
1225
Geoff Lang76b10c92014-09-05 16:28:14 -04001226Texture *Context::getSamplerTexture(unsigned int sampler, GLenum type) const
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001227{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001228 return mGLState.getSamplerTexture(sampler, type);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001229}
1230
Geoff Lang492a7e42014-11-05 13:27:06 -05001231Compiler *Context::getCompiler() const
1232{
Jamie Madill2f348d22017-06-05 10:50:59 -04001233 if (mCompiler.get() == nullptr)
1234 {
Jamie Madill4928b7c2017-06-20 12:57:39 -04001235 mCompiler.set(this, new Compiler(mImplementation.get(), mState));
Jamie Madill2f348d22017-06-05 10:50:59 -04001236 }
1237 return mCompiler.get();
Geoff Lang492a7e42014-11-05 13:27:06 -05001238}
1239
Jamie Madillc1d770e2017-04-13 17:31:24 -04001240void Context::getBooleanvImpl(GLenum pname, GLboolean *params)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001241{
1242 switch (pname)
1243 {
Jamie Madill231c7f52017-04-26 13:45:37 -04001244 case GL_SHADER_COMPILER:
1245 *params = GL_TRUE;
1246 break;
1247 case GL_CONTEXT_ROBUST_ACCESS_EXT:
1248 *params = mRobustAccess ? GL_TRUE : GL_FALSE;
1249 break;
1250 default:
1251 mGLState.getBooleanv(pname, params);
1252 break;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001253 }
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001254}
1255
Jamie Madillc1d770e2017-04-13 17:31:24 -04001256void Context::getFloatvImpl(GLenum pname, GLfloat *params)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001257{
Shannon Woods53a94a82014-06-24 15:20:36 -04001258 // Queries about context capabilities and maximums are answered by Context.
1259 // Queries about current GL state values are answered by State.
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001260 switch (pname)
1261 {
Jamie Madill231c7f52017-04-26 13:45:37 -04001262 case GL_ALIASED_LINE_WIDTH_RANGE:
1263 params[0] = mCaps.minAliasedLineWidth;
1264 params[1] = mCaps.maxAliasedLineWidth;
1265 break;
1266 case GL_ALIASED_POINT_SIZE_RANGE:
1267 params[0] = mCaps.minAliasedPointSize;
1268 params[1] = mCaps.maxAliasedPointSize;
1269 break;
1270 case GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT:
1271 ASSERT(mExtensions.textureFilterAnisotropic);
1272 *params = mExtensions.maxTextureAnisotropy;
1273 break;
1274 case GL_MAX_TEXTURE_LOD_BIAS:
1275 *params = mCaps.maxLODBias;
1276 break;
1277
1278 case GL_PATH_MODELVIEW_MATRIX_CHROMIUM:
1279 case GL_PATH_PROJECTION_MATRIX_CHROMIUM:
1280 {
1281 ASSERT(mExtensions.pathRendering);
1282 const GLfloat *m = mGLState.getPathRenderingMatrix(pname);
1283 memcpy(params, m, 16 * sizeof(GLfloat));
1284 }
Geoff Lange6d4e122015-06-29 13:33:55 -04001285 break;
Sami Väisänene45e53b2016-05-25 10:36:04 +03001286
Jamie Madill231c7f52017-04-26 13:45:37 -04001287 default:
1288 mGLState.getFloatv(pname, params);
1289 break;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001290 }
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001291}
1292
Jamie Madillc1d770e2017-04-13 17:31:24 -04001293void Context::getIntegervImpl(GLenum pname, GLint *params)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001294{
Shannon Woods53a94a82014-06-24 15:20:36 -04001295 // Queries about context capabilities and maximums are answered by Context.
1296 // Queries about current GL state values are answered by State.
shannon.woods%transgaming.com@gtempaccount.combc373e52013-04-13 03:31:23 +00001297
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001298 switch (pname)
1299 {
Jamie Madill231c7f52017-04-26 13:45:37 -04001300 case GL_MAX_VERTEX_ATTRIBS:
1301 *params = mCaps.maxVertexAttributes;
1302 break;
1303 case GL_MAX_VERTEX_UNIFORM_VECTORS:
1304 *params = mCaps.maxVertexUniformVectors;
1305 break;
1306 case GL_MAX_VERTEX_UNIFORM_COMPONENTS:
1307 *params = mCaps.maxVertexUniformComponents;
1308 break;
1309 case GL_MAX_VARYING_VECTORS:
1310 *params = mCaps.maxVaryingVectors;
1311 break;
1312 case GL_MAX_VARYING_COMPONENTS:
1313 *params = mCaps.maxVertexOutputComponents;
1314 break;
1315 case GL_MAX_COMBINED_TEXTURE_IMAGE_UNITS:
1316 *params = mCaps.maxCombinedTextureImageUnits;
1317 break;
1318 case GL_MAX_VERTEX_TEXTURE_IMAGE_UNITS:
1319 *params = mCaps.maxVertexTextureImageUnits;
1320 break;
1321 case GL_MAX_TEXTURE_IMAGE_UNITS:
1322 *params = mCaps.maxTextureImageUnits;
1323 break;
1324 case GL_MAX_FRAGMENT_UNIFORM_VECTORS:
1325 *params = mCaps.maxFragmentUniformVectors;
1326 break;
1327 case GL_MAX_FRAGMENT_UNIFORM_COMPONENTS:
1328 *params = mCaps.maxFragmentUniformComponents;
1329 break;
1330 case GL_MAX_RENDERBUFFER_SIZE:
1331 *params = mCaps.maxRenderbufferSize;
1332 break;
1333 case GL_MAX_COLOR_ATTACHMENTS_EXT:
1334 *params = mCaps.maxColorAttachments;
1335 break;
1336 case GL_MAX_DRAW_BUFFERS_EXT:
1337 *params = mCaps.maxDrawBuffers;
1338 break;
1339 // case GL_FRAMEBUFFER_BINDING: // now equivalent to
1340 // GL_DRAW_FRAMEBUFFER_BINDING_ANGLE
1341 case GL_SUBPIXEL_BITS:
1342 *params = 4;
1343 break;
1344 case GL_MAX_TEXTURE_SIZE:
1345 *params = mCaps.max2DTextureSize;
1346 break;
Corentin Wallez13c0dd42017-07-04 18:27:01 -04001347 case GL_MAX_RECTANGLE_TEXTURE_SIZE_ANGLE:
1348 *params = mCaps.maxRectangleTextureSize;
1349 break;
Jamie Madill231c7f52017-04-26 13:45:37 -04001350 case GL_MAX_CUBE_MAP_TEXTURE_SIZE:
1351 *params = mCaps.maxCubeMapTextureSize;
1352 break;
1353 case GL_MAX_3D_TEXTURE_SIZE:
1354 *params = mCaps.max3DTextureSize;
1355 break;
1356 case GL_MAX_ARRAY_TEXTURE_LAYERS:
1357 *params = mCaps.maxArrayTextureLayers;
1358 break;
1359 case GL_UNIFORM_BUFFER_OFFSET_ALIGNMENT:
1360 *params = mCaps.uniformBufferOffsetAlignment;
1361 break;
1362 case GL_MAX_UNIFORM_BUFFER_BINDINGS:
1363 *params = mCaps.maxUniformBufferBindings;
1364 break;
1365 case GL_MAX_VERTEX_UNIFORM_BLOCKS:
1366 *params = mCaps.maxVertexUniformBlocks;
1367 break;
1368 case GL_MAX_FRAGMENT_UNIFORM_BLOCKS:
1369 *params = mCaps.maxFragmentUniformBlocks;
1370 break;
1371 case GL_MAX_COMBINED_UNIFORM_BLOCKS:
1372 *params = mCaps.maxCombinedTextureImageUnits;
1373 break;
1374 case GL_MAX_VERTEX_OUTPUT_COMPONENTS:
1375 *params = mCaps.maxVertexOutputComponents;
1376 break;
1377 case GL_MAX_FRAGMENT_INPUT_COMPONENTS:
1378 *params = mCaps.maxFragmentInputComponents;
1379 break;
1380 case GL_MIN_PROGRAM_TEXEL_OFFSET:
1381 *params = mCaps.minProgramTexelOffset;
1382 break;
1383 case GL_MAX_PROGRAM_TEXEL_OFFSET:
1384 *params = mCaps.maxProgramTexelOffset;
1385 break;
1386 case GL_MAJOR_VERSION:
1387 *params = getClientVersion().major;
1388 break;
1389 case GL_MINOR_VERSION:
1390 *params = getClientVersion().minor;
1391 break;
1392 case GL_MAX_ELEMENTS_INDICES:
1393 *params = mCaps.maxElementsIndices;
1394 break;
1395 case GL_MAX_ELEMENTS_VERTICES:
1396 *params = mCaps.maxElementsVertices;
1397 break;
1398 case GL_MAX_TRANSFORM_FEEDBACK_INTERLEAVED_COMPONENTS:
1399 *params = mCaps.maxTransformFeedbackInterleavedComponents;
1400 break;
1401 case GL_MAX_TRANSFORM_FEEDBACK_SEPARATE_ATTRIBS:
1402 *params = mCaps.maxTransformFeedbackSeparateAttributes;
1403 break;
1404 case GL_MAX_TRANSFORM_FEEDBACK_SEPARATE_COMPONENTS:
1405 *params = mCaps.maxTransformFeedbackSeparateComponents;
1406 break;
1407 case GL_NUM_COMPRESSED_TEXTURE_FORMATS:
1408 *params = static_cast<GLint>(mCaps.compressedTextureFormats.size());
1409 break;
1410 case GL_MAX_SAMPLES_ANGLE:
1411 *params = mCaps.maxSamples;
1412 break;
1413 case GL_MAX_VIEWPORT_DIMS:
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001414 {
Geoff Langc0b9ef42014-07-02 10:02:37 -04001415 params[0] = mCaps.maxViewportWidth;
1416 params[1] = mCaps.maxViewportHeight;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001417 }
1418 break;
Jamie Madill231c7f52017-04-26 13:45:37 -04001419 case GL_COMPRESSED_TEXTURE_FORMATS:
1420 std::copy(mCaps.compressedTextureFormats.begin(), mCaps.compressedTextureFormats.end(),
1421 params);
1422 break;
1423 case GL_RESET_NOTIFICATION_STRATEGY_EXT:
1424 *params = mResetStrategy;
1425 break;
1426 case GL_NUM_SHADER_BINARY_FORMATS:
1427 *params = static_cast<GLint>(mCaps.shaderBinaryFormats.size());
1428 break;
1429 case GL_SHADER_BINARY_FORMATS:
1430 std::copy(mCaps.shaderBinaryFormats.begin(), mCaps.shaderBinaryFormats.end(), params);
1431 break;
1432 case GL_NUM_PROGRAM_BINARY_FORMATS:
1433 *params = static_cast<GLint>(mCaps.programBinaryFormats.size());
1434 break;
1435 case GL_PROGRAM_BINARY_FORMATS:
1436 std::copy(mCaps.programBinaryFormats.begin(), mCaps.programBinaryFormats.end(), params);
1437 break;
1438 case GL_NUM_EXTENSIONS:
1439 *params = static_cast<GLint>(mExtensionStrings.size());
1440 break;
Geoff Lang70d0f492015-12-10 17:45:46 -05001441
Jamie Madill231c7f52017-04-26 13:45:37 -04001442 // GL_KHR_debug
1443 case GL_MAX_DEBUG_MESSAGE_LENGTH:
1444 *params = mExtensions.maxDebugMessageLength;
1445 break;
1446 case GL_MAX_DEBUG_LOGGED_MESSAGES:
1447 *params = mExtensions.maxDebugLoggedMessages;
1448 break;
1449 case GL_MAX_DEBUG_GROUP_STACK_DEPTH:
1450 *params = mExtensions.maxDebugGroupStackDepth;
1451 break;
1452 case GL_MAX_LABEL_LENGTH:
1453 *params = mExtensions.maxLabelLength;
1454 break;
Geoff Lang70d0f492015-12-10 17:45:46 -05001455
Martin Radeve5285d22017-07-14 16:23:53 +03001456 // GL_ANGLE_multiview
1457 case GL_MAX_VIEWS_ANGLE:
1458 *params = mExtensions.maxViews;
1459 break;
1460
Jamie Madill231c7f52017-04-26 13:45:37 -04001461 // GL_EXT_disjoint_timer_query
1462 case GL_GPU_DISJOINT_EXT:
1463 *params = mImplementation->getGPUDisjoint();
1464 break;
1465 case GL_MAX_FRAMEBUFFER_WIDTH:
1466 *params = mCaps.maxFramebufferWidth;
1467 break;
1468 case GL_MAX_FRAMEBUFFER_HEIGHT:
1469 *params = mCaps.maxFramebufferHeight;
1470 break;
1471 case GL_MAX_FRAMEBUFFER_SAMPLES:
1472 *params = mCaps.maxFramebufferSamples;
1473 break;
1474 case GL_MAX_SAMPLE_MASK_WORDS:
1475 *params = mCaps.maxSampleMaskWords;
1476 break;
1477 case GL_MAX_COLOR_TEXTURE_SAMPLES:
1478 *params = mCaps.maxColorTextureSamples;
1479 break;
1480 case GL_MAX_DEPTH_TEXTURE_SAMPLES:
1481 *params = mCaps.maxDepthTextureSamples;
1482 break;
1483 case GL_MAX_INTEGER_SAMPLES:
1484 *params = mCaps.maxIntegerSamples;
1485 break;
1486 case GL_MAX_VERTEX_ATTRIB_RELATIVE_OFFSET:
1487 *params = mCaps.maxVertexAttribRelativeOffset;
1488 break;
1489 case GL_MAX_VERTEX_ATTRIB_BINDINGS:
1490 *params = mCaps.maxVertexAttribBindings;
1491 break;
1492 case GL_MAX_VERTEX_ATTRIB_STRIDE:
1493 *params = mCaps.maxVertexAttribStride;
1494 break;
1495 case GL_MAX_VERTEX_ATOMIC_COUNTER_BUFFERS:
1496 *params = mCaps.maxVertexAtomicCounterBuffers;
1497 break;
1498 case GL_MAX_VERTEX_ATOMIC_COUNTERS:
1499 *params = mCaps.maxVertexAtomicCounters;
1500 break;
1501 case GL_MAX_VERTEX_IMAGE_UNIFORMS:
1502 *params = mCaps.maxVertexImageUniforms;
1503 break;
1504 case GL_MAX_VERTEX_SHADER_STORAGE_BLOCKS:
1505 *params = mCaps.maxVertexShaderStorageBlocks;
1506 break;
1507 case GL_MAX_FRAGMENT_ATOMIC_COUNTER_BUFFERS:
1508 *params = mCaps.maxFragmentAtomicCounterBuffers;
1509 break;
1510 case GL_MAX_FRAGMENT_ATOMIC_COUNTERS:
1511 *params = mCaps.maxFragmentAtomicCounters;
1512 break;
1513 case GL_MAX_FRAGMENT_IMAGE_UNIFORMS:
1514 *params = mCaps.maxFragmentImageUniforms;
1515 break;
1516 case GL_MAX_FRAGMENT_SHADER_STORAGE_BLOCKS:
1517 *params = mCaps.maxFragmentShaderStorageBlocks;
1518 break;
1519 case GL_MIN_PROGRAM_TEXTURE_GATHER_OFFSET:
1520 *params = mCaps.minProgramTextureGatherOffset;
1521 break;
1522 case GL_MAX_PROGRAM_TEXTURE_GATHER_OFFSET:
1523 *params = mCaps.maxProgramTextureGatherOffset;
1524 break;
1525 case GL_MAX_COMPUTE_WORK_GROUP_INVOCATIONS:
1526 *params = mCaps.maxComputeWorkGroupInvocations;
1527 break;
1528 case GL_MAX_COMPUTE_UNIFORM_BLOCKS:
1529 *params = mCaps.maxComputeUniformBlocks;
1530 break;
1531 case GL_MAX_COMPUTE_TEXTURE_IMAGE_UNITS:
1532 *params = mCaps.maxComputeTextureImageUnits;
1533 break;
1534 case GL_MAX_COMPUTE_SHARED_MEMORY_SIZE:
1535 *params = mCaps.maxComputeSharedMemorySize;
1536 break;
1537 case GL_MAX_COMPUTE_UNIFORM_COMPONENTS:
1538 *params = mCaps.maxComputeUniformComponents;
1539 break;
1540 case GL_MAX_COMPUTE_ATOMIC_COUNTER_BUFFERS:
1541 *params = mCaps.maxComputeAtomicCounterBuffers;
1542 break;
1543 case GL_MAX_COMPUTE_ATOMIC_COUNTERS:
1544 *params = mCaps.maxComputeAtomicCounters;
1545 break;
1546 case GL_MAX_COMPUTE_IMAGE_UNIFORMS:
1547 *params = mCaps.maxComputeImageUniforms;
1548 break;
1549 case GL_MAX_COMBINED_COMPUTE_UNIFORM_COMPONENTS:
1550 *params = mCaps.maxCombinedComputeUniformComponents;
1551 break;
1552 case GL_MAX_COMPUTE_SHADER_STORAGE_BLOCKS:
1553 *params = mCaps.maxComputeShaderStorageBlocks;
1554 break;
1555 case GL_MAX_COMBINED_SHADER_OUTPUT_RESOURCES:
1556 *params = mCaps.maxCombinedShaderOutputResources;
1557 break;
1558 case GL_MAX_UNIFORM_LOCATIONS:
1559 *params = mCaps.maxUniformLocations;
1560 break;
1561 case GL_MAX_ATOMIC_COUNTER_BUFFER_BINDINGS:
1562 *params = mCaps.maxAtomicCounterBufferBindings;
1563 break;
1564 case GL_MAX_ATOMIC_COUNTER_BUFFER_SIZE:
1565 *params = mCaps.maxAtomicCounterBufferSize;
1566 break;
1567 case GL_MAX_COMBINED_ATOMIC_COUNTER_BUFFERS:
1568 *params = mCaps.maxCombinedAtomicCounterBuffers;
1569 break;
1570 case GL_MAX_COMBINED_ATOMIC_COUNTERS:
1571 *params = mCaps.maxCombinedAtomicCounters;
1572 break;
1573 case GL_MAX_IMAGE_UNITS:
1574 *params = mCaps.maxImageUnits;
1575 break;
1576 case GL_MAX_COMBINED_IMAGE_UNIFORMS:
1577 *params = mCaps.maxCombinedImageUniforms;
1578 break;
1579 case GL_MAX_SHADER_STORAGE_BUFFER_BINDINGS:
1580 *params = mCaps.maxShaderStorageBufferBindings;
1581 break;
1582 case GL_MAX_COMBINED_SHADER_STORAGE_BLOCKS:
1583 *params = mCaps.maxCombinedShaderStorageBlocks;
1584 break;
1585 case GL_SHADER_STORAGE_BUFFER_OFFSET_ALIGNMENT:
1586 *params = mCaps.shaderStorageBufferOffsetAlignment;
1587 break;
1588 default:
1589 mGLState.getIntegerv(this, pname, params);
1590 break;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001591 }
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001592}
1593
Jamie Madill7f0c5a42017-08-26 22:43:26 -04001594void Context::getInteger64vImpl(GLenum pname, GLint64 *params)
Jamie Madill0fda9862013-07-19 16:36:55 -04001595{
Shannon Woods53a94a82014-06-24 15:20:36 -04001596 // Queries about context capabilities and maximums are answered by Context.
1597 // Queries about current GL state values are answered by State.
Jamie Madill0fda9862013-07-19 16:36:55 -04001598 switch (pname)
1599 {
Jamie Madill231c7f52017-04-26 13:45:37 -04001600 case GL_MAX_ELEMENT_INDEX:
1601 *params = mCaps.maxElementIndex;
1602 break;
1603 case GL_MAX_UNIFORM_BLOCK_SIZE:
1604 *params = mCaps.maxUniformBlockSize;
1605 break;
1606 case GL_MAX_COMBINED_VERTEX_UNIFORM_COMPONENTS:
1607 *params = mCaps.maxCombinedVertexUniformComponents;
1608 break;
1609 case GL_MAX_COMBINED_FRAGMENT_UNIFORM_COMPONENTS:
1610 *params = mCaps.maxCombinedFragmentUniformComponents;
1611 break;
1612 case GL_MAX_SERVER_WAIT_TIMEOUT:
1613 *params = mCaps.maxServerWaitTimeout;
1614 break;
Ian Ewell53f59f42016-01-28 17:36:55 -05001615
Jamie Madill231c7f52017-04-26 13:45:37 -04001616 // GL_EXT_disjoint_timer_query
1617 case GL_TIMESTAMP_EXT:
1618 *params = mImplementation->getTimestamp();
1619 break;
Martin Radev66fb8202016-07-28 11:45:20 +03001620
Jamie Madill231c7f52017-04-26 13:45:37 -04001621 case GL_MAX_SHADER_STORAGE_BLOCK_SIZE:
1622 *params = mCaps.maxShaderStorageBlockSize;
1623 break;
1624 default:
1625 UNREACHABLE();
1626 break;
Jamie Madill0fda9862013-07-19 16:36:55 -04001627 }
Jamie Madill0fda9862013-07-19 16:36:55 -04001628}
1629
Geoff Lang70d0f492015-12-10 17:45:46 -05001630void Context::getPointerv(GLenum pname, void **params) const
1631{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001632 mGLState.getPointerv(pname, params);
Geoff Lang70d0f492015-12-10 17:45:46 -05001633}
1634
Martin Radev66fb8202016-07-28 11:45:20 +03001635void Context::getIntegeri_v(GLenum target, GLuint index, GLint *data)
Shannon Woods1b2fb852013-08-19 14:28:48 -04001636{
Shannon Woods53a94a82014-06-24 15:20:36 -04001637 // Queries about context capabilities and maximums are answered by Context.
1638 // Queries about current GL state values are answered by State.
Martin Radev66fb8202016-07-28 11:45:20 +03001639
1640 GLenum nativeType;
1641 unsigned int numParams;
1642 bool queryStatus = getIndexedQueryParameterInfo(target, &nativeType, &numParams);
1643 ASSERT(queryStatus);
1644
1645 if (nativeType == GL_INT)
1646 {
1647 switch (target)
1648 {
1649 case GL_MAX_COMPUTE_WORK_GROUP_COUNT:
1650 ASSERT(index < 3u);
1651 *data = mCaps.maxComputeWorkGroupCount[index];
1652 break;
1653 case GL_MAX_COMPUTE_WORK_GROUP_SIZE:
1654 ASSERT(index < 3u);
1655 *data = mCaps.maxComputeWorkGroupSize[index];
1656 break;
1657 default:
1658 mGLState.getIntegeri_v(target, index, data);
1659 }
1660 }
1661 else
1662 {
1663 CastIndexedStateValues(this, nativeType, target, index, numParams, data);
1664 }
Shannon Woods1b2fb852013-08-19 14:28:48 -04001665}
1666
Martin Radev66fb8202016-07-28 11:45:20 +03001667void Context::getInteger64i_v(GLenum target, GLuint index, GLint64 *data)
Shannon Woods1b2fb852013-08-19 14:28:48 -04001668{
Shannon Woods53a94a82014-06-24 15:20:36 -04001669 // Queries about context capabilities and maximums are answered by Context.
1670 // Queries about current GL state values are answered by State.
Martin Radev66fb8202016-07-28 11:45:20 +03001671
1672 GLenum nativeType;
1673 unsigned int numParams;
1674 bool queryStatus = getIndexedQueryParameterInfo(target, &nativeType, &numParams);
1675 ASSERT(queryStatus);
1676
1677 if (nativeType == GL_INT_64_ANGLEX)
1678 {
1679 mGLState.getInteger64i_v(target, index, data);
1680 }
1681 else
1682 {
1683 CastIndexedStateValues(this, nativeType, target, index, numParams, data);
1684 }
1685}
1686
1687void Context::getBooleani_v(GLenum target, GLuint index, GLboolean *data)
1688{
1689 // Queries about context capabilities and maximums are answered by Context.
1690 // Queries about current GL state values are answered by State.
1691
1692 GLenum nativeType;
1693 unsigned int numParams;
1694 bool queryStatus = getIndexedQueryParameterInfo(target, &nativeType, &numParams);
1695 ASSERT(queryStatus);
1696
1697 if (nativeType == GL_BOOL)
1698 {
1699 mGLState.getBooleani_v(target, index, data);
1700 }
1701 else
1702 {
1703 CastIndexedStateValues(this, nativeType, target, index, numParams, data);
1704 }
Shannon Woods1b2fb852013-08-19 14:28:48 -04001705}
1706
He Yunchao010e4db2017-03-03 14:22:06 +08001707void Context::getBufferParameteriv(GLenum target, GLenum pname, GLint *params)
1708{
1709 Buffer *buffer = mGLState.getTargetBuffer(target);
1710 QueryBufferParameteriv(buffer, pname, params);
1711}
1712
1713void Context::getFramebufferAttachmentParameteriv(GLenum target,
1714 GLenum attachment,
1715 GLenum pname,
1716 GLint *params)
1717{
1718 const Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
1719 QueryFramebufferAttachmentParameteriv(framebuffer, attachment, pname, params);
1720}
1721
1722void Context::getRenderbufferParameteriv(GLenum target, GLenum pname, GLint *params)
1723{
1724 Renderbuffer *renderbuffer = mGLState.getCurrentRenderbuffer();
1725 QueryRenderbufferiv(this, renderbuffer, pname, params);
1726}
1727
1728void Context::getTexParameterfv(GLenum target, GLenum pname, GLfloat *params)
1729{
1730 Texture *texture = getTargetTexture(target);
1731 QueryTexParameterfv(texture, pname, params);
1732}
1733
1734void Context::getTexParameteriv(GLenum target, GLenum pname, GLint *params)
1735{
1736 Texture *texture = getTargetTexture(target);
1737 QueryTexParameteriv(texture, pname, params);
1738}
1739void Context::texParameterf(GLenum target, GLenum pname, GLfloat param)
1740{
1741 Texture *texture = getTargetTexture(target);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001742 SetTexParameterf(this, texture, pname, param);
He Yunchao010e4db2017-03-03 14:22:06 +08001743}
1744
1745void Context::texParameterfv(GLenum target, GLenum pname, const GLfloat *params)
1746{
1747 Texture *texture = getTargetTexture(target);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001748 SetTexParameterfv(this, texture, pname, params);
He Yunchao010e4db2017-03-03 14:22:06 +08001749}
1750
1751void Context::texParameteri(GLenum target, GLenum pname, GLint param)
1752{
1753 Texture *texture = getTargetTexture(target);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001754 SetTexParameteri(this, texture, pname, param);
He Yunchao010e4db2017-03-03 14:22:06 +08001755}
1756
1757void Context::texParameteriv(GLenum target, GLenum pname, const GLint *params)
1758{
1759 Texture *texture = getTargetTexture(target);
Jamie Madill4928b7c2017-06-20 12:57:39 -04001760 SetTexParameteriv(this, texture, pname, params);
He Yunchao010e4db2017-03-03 14:22:06 +08001761}
1762
Jamie Madill675fe712016-12-19 13:07:54 -05001763void Context::drawArrays(GLenum mode, GLint first, GLsizei count)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001764{
Jamie Madill4c19a8a2017-07-24 11:46:06 -04001765 ANGLE_CONTEXT_TRY(prepareForDraw(mode));
Jamie Madillb6664922017-07-25 12:55:04 -04001766 ANGLE_CONTEXT_TRY(mImplementation->drawArrays(this, mode, first, count));
1767 MarkTransformFeedbackBufferUsage(mGLState.getCurrentTransformFeedback());
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001768}
1769
Jamie Madill675fe712016-12-19 13:07:54 -05001770void Context::drawArraysInstanced(GLenum mode, GLint first, GLsizei count, GLsizei instanceCount)
Geoff Langf6db0982015-08-25 13:04:00 -04001771{
Jamie Madill4c19a8a2017-07-24 11:46:06 -04001772 ANGLE_CONTEXT_TRY(prepareForDraw(mode));
Jamie Madillb6664922017-07-25 12:55:04 -04001773 ANGLE_CONTEXT_TRY(
1774 mImplementation->drawArraysInstanced(this, mode, first, count, instanceCount));
1775 MarkTransformFeedbackBufferUsage(mGLState.getCurrentTransformFeedback());
Geoff Langf6db0982015-08-25 13:04:00 -04001776}
1777
Jamie Madill876429b2017-04-20 15:46:24 -04001778void Context::drawElements(GLenum mode, GLsizei count, GLenum type, const void *indices)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001779{
Jamie Madill4c19a8a2017-07-24 11:46:06 -04001780 ANGLE_CONTEXT_TRY(prepareForDraw(mode));
Jamie Madillb6664922017-07-25 12:55:04 -04001781 ANGLE_CONTEXT_TRY(mImplementation->drawElements(this, mode, count, type, indices));
Geoff Langf6db0982015-08-25 13:04:00 -04001782}
1783
Jamie Madill675fe712016-12-19 13:07:54 -05001784void Context::drawElementsInstanced(GLenum mode,
1785 GLsizei count,
1786 GLenum type,
Jamie Madill876429b2017-04-20 15:46:24 -04001787 const void *indices,
Jamie Madill9c9b40a2017-04-26 16:31:57 -04001788 GLsizei instances)
Geoff Langf6db0982015-08-25 13:04:00 -04001789{
Jamie Madill4c19a8a2017-07-24 11:46:06 -04001790 ANGLE_CONTEXT_TRY(prepareForDraw(mode));
Jamie Madillb6664922017-07-25 12:55:04 -04001791 ANGLE_CONTEXT_TRY(
Qin Jiajia1da00652017-06-20 17:16:25 +08001792 mImplementation->drawElementsInstanced(this, mode, count, type, indices, instances));
Geoff Langf6db0982015-08-25 13:04:00 -04001793}
1794
Jamie Madill675fe712016-12-19 13:07:54 -05001795void Context::drawRangeElements(GLenum mode,
1796 GLuint start,
1797 GLuint end,
1798 GLsizei count,
1799 GLenum type,
Jamie Madill876429b2017-04-20 15:46:24 -04001800 const void *indices)
Geoff Langf6db0982015-08-25 13:04:00 -04001801{
Jamie Madill4c19a8a2017-07-24 11:46:06 -04001802 ANGLE_CONTEXT_TRY(prepareForDraw(mode));
Jamie Madillb6664922017-07-25 12:55:04 -04001803 ANGLE_CONTEXT_TRY(
1804 mImplementation->drawRangeElements(this, mode, start, end, count, type, indices));
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001805}
1806
Jamie Madill876429b2017-04-20 15:46:24 -04001807void Context::drawArraysIndirect(GLenum mode, const void *indirect)
Jiajia Qind9671222016-11-29 16:30:31 +08001808{
Jamie Madill4c19a8a2017-07-24 11:46:06 -04001809 ANGLE_CONTEXT_TRY(prepareForDraw(mode));
Jamie Madillb6664922017-07-25 12:55:04 -04001810 ANGLE_CONTEXT_TRY(mImplementation->drawArraysIndirect(this, mode, indirect));
Jiajia Qind9671222016-11-29 16:30:31 +08001811}
1812
Jamie Madill876429b2017-04-20 15:46:24 -04001813void Context::drawElementsIndirect(GLenum mode, GLenum type, const void *indirect)
Jiajia Qind9671222016-11-29 16:30:31 +08001814{
Jamie Madill4c19a8a2017-07-24 11:46:06 -04001815 ANGLE_CONTEXT_TRY(prepareForDraw(mode));
Jamie Madillb6664922017-07-25 12:55:04 -04001816 ANGLE_CONTEXT_TRY(mImplementation->drawElementsIndirect(this, mode, type, indirect));
Jiajia Qind9671222016-11-29 16:30:31 +08001817}
1818
Jamie Madill675fe712016-12-19 13:07:54 -05001819void Context::flush()
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001820{
Jamie Madill675fe712016-12-19 13:07:54 -05001821 handleError(mImplementation->flush());
Geoff Lang129753a2015-01-09 16:52:09 -05001822}
1823
Jamie Madill675fe712016-12-19 13:07:54 -05001824void Context::finish()
Geoff Lang129753a2015-01-09 16:52:09 -05001825{
Jamie Madill675fe712016-12-19 13:07:54 -05001826 handleError(mImplementation->finish());
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001827}
1828
Austin Kinross6ee1e782015-05-29 17:05:37 -07001829void Context::insertEventMarker(GLsizei length, const char *marker)
1830{
Jamie Madill53ea9cc2016-05-17 10:12:52 -04001831 ASSERT(mImplementation);
1832 mImplementation->insertEventMarker(length, marker);
Austin Kinross6ee1e782015-05-29 17:05:37 -07001833}
1834
1835void Context::pushGroupMarker(GLsizei length, const char *marker)
1836{
Jamie Madill53ea9cc2016-05-17 10:12:52 -04001837 ASSERT(mImplementation);
1838 mImplementation->pushGroupMarker(length, marker);
Austin Kinross6ee1e782015-05-29 17:05:37 -07001839}
1840
1841void Context::popGroupMarker()
1842{
Jamie Madill53ea9cc2016-05-17 10:12:52 -04001843 ASSERT(mImplementation);
1844 mImplementation->popGroupMarker();
Austin Kinross6ee1e782015-05-29 17:05:37 -07001845}
1846
Geoff Langd8605522016-04-13 10:19:12 -04001847void Context::bindUniformLocation(GLuint program, GLint location, const GLchar *name)
1848{
1849 Program *programObject = getProgram(program);
1850 ASSERT(programObject);
1851
1852 programObject->bindUniformLocation(location, name);
1853}
1854
Sami Väisänena797e062016-05-12 15:23:40 +03001855void Context::setCoverageModulation(GLenum components)
1856{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001857 mGLState.setCoverageModulation(components);
Sami Väisänena797e062016-05-12 15:23:40 +03001858}
1859
Sami Väisänene45e53b2016-05-25 10:36:04 +03001860void Context::loadPathRenderingMatrix(GLenum matrixMode, const GLfloat *matrix)
1861{
1862 mGLState.loadPathRenderingMatrix(matrixMode, matrix);
1863}
1864
1865void Context::loadPathRenderingIdentityMatrix(GLenum matrixMode)
1866{
1867 GLfloat I[16];
1868 angle::Matrix<GLfloat>::setToIdentity(I);
1869
1870 mGLState.loadPathRenderingMatrix(matrixMode, I);
1871}
1872
1873void Context::stencilFillPath(GLuint path, GLenum fillMode, GLuint mask)
1874{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001875 const auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +03001876 if (!pathObj)
1877 return;
1878
1879 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
1880 syncRendererState();
1881
1882 mImplementation->stencilFillPath(pathObj, fillMode, mask);
1883}
1884
1885void Context::stencilStrokePath(GLuint path, GLint reference, GLuint mask)
1886{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001887 const auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +03001888 if (!pathObj)
1889 return;
1890
1891 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
1892 syncRendererState();
1893
1894 mImplementation->stencilStrokePath(pathObj, reference, mask);
1895}
1896
1897void Context::coverFillPath(GLuint path, GLenum coverMode)
1898{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001899 const auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +03001900 if (!pathObj)
1901 return;
1902
1903 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
1904 syncRendererState();
1905
1906 mImplementation->coverFillPath(pathObj, coverMode);
1907}
1908
1909void Context::coverStrokePath(GLuint path, GLenum coverMode)
1910{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001911 const auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +03001912 if (!pathObj)
1913 return;
1914
1915 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
1916 syncRendererState();
1917
1918 mImplementation->coverStrokePath(pathObj, coverMode);
1919}
1920
1921void Context::stencilThenCoverFillPath(GLuint path, GLenum fillMode, GLuint mask, GLenum coverMode)
1922{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001923 const auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +03001924 if (!pathObj)
1925 return;
1926
1927 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
1928 syncRendererState();
1929
1930 mImplementation->stencilThenCoverFillPath(pathObj, fillMode, mask, coverMode);
1931}
1932
1933void Context::stencilThenCoverStrokePath(GLuint path,
1934 GLint reference,
1935 GLuint mask,
1936 GLenum coverMode)
1937{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001938 const auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +03001939 if (!pathObj)
1940 return;
1941
1942 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
1943 syncRendererState();
1944
1945 mImplementation->stencilThenCoverStrokePath(pathObj, reference, mask, coverMode);
1946}
1947
Sami Väisänend59ca052016-06-21 16:10:00 +03001948void Context::coverFillPathInstanced(GLsizei numPaths,
1949 GLenum pathNameType,
1950 const void *paths,
1951 GLuint pathBase,
1952 GLenum coverMode,
1953 GLenum transformType,
1954 const GLfloat *transformValues)
1955{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001956 const auto &pathObjects = GatherPaths(*mState.mPaths, numPaths, pathNameType, paths, pathBase);
Sami Väisänend59ca052016-06-21 16:10:00 +03001957
1958 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
1959 syncRendererState();
1960
1961 mImplementation->coverFillPathInstanced(pathObjects, coverMode, transformType, transformValues);
1962}
Sami Väisänen46eaa942016-06-29 10:26:37 +03001963
Sami Väisänend59ca052016-06-21 16:10:00 +03001964void Context::coverStrokePathInstanced(GLsizei numPaths,
1965 GLenum pathNameType,
1966 const void *paths,
1967 GLuint pathBase,
1968 GLenum coverMode,
1969 GLenum transformType,
1970 const GLfloat *transformValues)
1971{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001972 const auto &pathObjects = GatherPaths(*mState.mPaths, numPaths, pathNameType, paths, pathBase);
Sami Väisänend59ca052016-06-21 16:10:00 +03001973
1974 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
1975 syncRendererState();
1976
1977 mImplementation->coverStrokePathInstanced(pathObjects, coverMode, transformType,
1978 transformValues);
1979}
Sami Väisänen46eaa942016-06-29 10:26:37 +03001980
Sami Väisänend59ca052016-06-21 16:10:00 +03001981void Context::stencilFillPathInstanced(GLsizei numPaths,
1982 GLenum pathNameType,
1983 const void *paths,
1984 GLuint pathBase,
1985 GLenum fillMode,
1986 GLuint mask,
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->stencilFillPathInstanced(pathObjects, fillMode, mask, transformType,
1996 transformValues);
1997}
Sami Väisänen46eaa942016-06-29 10:26:37 +03001998
Sami Väisänend59ca052016-06-21 16:10:00 +03001999void Context::stencilStrokePathInstanced(GLsizei numPaths,
2000 GLenum pathNameType,
2001 const void *paths,
2002 GLuint pathBase,
2003 GLint reference,
2004 GLuint mask,
2005 GLenum transformType,
2006 const GLfloat *transformValues)
2007{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002008 const auto &pathObjects = GatherPaths(*mState.mPaths, numPaths, pathNameType, paths, pathBase);
Sami Väisänend59ca052016-06-21 16:10:00 +03002009
2010 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
2011 syncRendererState();
2012
2013 mImplementation->stencilStrokePathInstanced(pathObjects, reference, mask, transformType,
2014 transformValues);
2015}
Sami Väisänen46eaa942016-06-29 10:26:37 +03002016
Sami Väisänend59ca052016-06-21 16:10:00 +03002017void Context::stencilThenCoverFillPathInstanced(GLsizei numPaths,
2018 GLenum pathNameType,
2019 const void *paths,
2020 GLuint pathBase,
2021 GLenum fillMode,
2022 GLuint mask,
2023 GLenum coverMode,
2024 GLenum transformType,
2025 const GLfloat *transformValues)
2026{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002027 const auto &pathObjects = GatherPaths(*mState.mPaths, numPaths, pathNameType, paths, pathBase);
Sami Väisänend59ca052016-06-21 16:10:00 +03002028
2029 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
2030 syncRendererState();
2031
2032 mImplementation->stencilThenCoverFillPathInstanced(pathObjects, coverMode, fillMode, mask,
2033 transformType, transformValues);
2034}
Sami Väisänen46eaa942016-06-29 10:26:37 +03002035
Sami Väisänend59ca052016-06-21 16:10:00 +03002036void Context::stencilThenCoverStrokePathInstanced(GLsizei numPaths,
2037 GLenum pathNameType,
2038 const void *paths,
2039 GLuint pathBase,
2040 GLint reference,
2041 GLuint mask,
2042 GLenum coverMode,
2043 GLenum transformType,
2044 const GLfloat *transformValues)
2045{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002046 const auto &pathObjects = GatherPaths(*mState.mPaths, numPaths, pathNameType, paths, pathBase);
Sami Väisänend59ca052016-06-21 16:10:00 +03002047
2048 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
2049 syncRendererState();
2050
2051 mImplementation->stencilThenCoverStrokePathInstanced(pathObjects, coverMode, reference, mask,
2052 transformType, transformValues);
2053}
2054
Sami Väisänen46eaa942016-06-29 10:26:37 +03002055void Context::bindFragmentInputLocation(GLuint program, GLint location, const GLchar *name)
2056{
2057 auto *programObject = getProgram(program);
2058
2059 programObject->bindFragmentInputLocation(location, name);
2060}
2061
2062void Context::programPathFragmentInputGen(GLuint program,
2063 GLint location,
2064 GLenum genMode,
2065 GLint components,
2066 const GLfloat *coeffs)
2067{
2068 auto *programObject = getProgram(program);
2069
Jamie Madillbd044ed2017-06-05 12:59:21 -04002070 programObject->pathFragmentInputGen(this, location, genMode, components, coeffs);
Sami Väisänen46eaa942016-06-29 10:26:37 +03002071}
2072
jchen1015015f72017-03-16 13:54:21 +08002073GLuint Context::getProgramResourceIndex(GLuint program, GLenum programInterface, const GLchar *name)
2074{
jchen10fd7c3b52017-03-21 15:36:03 +08002075 const auto *programObject = getProgram(program);
jchen1015015f72017-03-16 13:54:21 +08002076 return QueryProgramResourceIndex(programObject, programInterface, name);
2077}
2078
jchen10fd7c3b52017-03-21 15:36:03 +08002079void Context::getProgramResourceName(GLuint program,
2080 GLenum programInterface,
2081 GLuint index,
2082 GLsizei bufSize,
2083 GLsizei *length,
2084 GLchar *name)
2085{
2086 const auto *programObject = getProgram(program);
2087 QueryProgramResourceName(programObject, programInterface, index, bufSize, length, name);
2088}
2089
jchen10191381f2017-04-11 13:59:04 +08002090GLint Context::getProgramResourceLocation(GLuint program,
2091 GLenum programInterface,
2092 const GLchar *name)
2093{
2094 const auto *programObject = getProgram(program);
2095 return QueryProgramResourceLocation(programObject, programInterface, name);
2096}
2097
jchen10880683b2017-04-12 16:21:55 +08002098void Context::getProgramResourceiv(GLuint program,
2099 GLenum programInterface,
2100 GLuint index,
2101 GLsizei propCount,
2102 const GLenum *props,
2103 GLsizei bufSize,
2104 GLsizei *length,
2105 GLint *params)
2106{
2107 const auto *programObject = getProgram(program);
2108 QueryProgramResourceiv(programObject, programInterface, index, propCount, props, bufSize,
2109 length, params);
2110}
2111
Jamie Madill4c19a8a2017-07-24 11:46:06 -04002112Error Context::handleError(const Error &error)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002113{
Geoff Langda5777c2014-07-11 09:52:58 -04002114 if (error.isError())
2115 {
Kenneth Russellf2f6f652016-10-05 19:53:23 -07002116 GLenum code = error.getCode();
2117 mErrors.insert(code);
2118 if (code == GL_OUT_OF_MEMORY && getWorkarounds().loseContextOnOutOfMemory)
2119 {
2120 markContextLost();
2121 }
Geoff Lang70d0f492015-12-10 17:45:46 -05002122
2123 if (!error.getMessage().empty())
2124 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002125 auto *debug = &mGLState.getDebug();
2126 debug->insertMessage(GL_DEBUG_SOURCE_API, GL_DEBUG_TYPE_ERROR, error.getID(),
2127 GL_DEBUG_SEVERITY_HIGH, error.getMessage());
Geoff Lang70d0f492015-12-10 17:45:46 -05002128 }
Geoff Langda5777c2014-07-11 09:52:58 -04002129 }
Jamie Madill4c19a8a2017-07-24 11:46:06 -04002130
2131 return error;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002132}
2133
2134// Get one of the recorded errors and clear its flag, if any.
2135// [OpenGL ES 2.0.24] section 2.5 page 13.
2136GLenum Context::getError()
2137{
Geoff Langda5777c2014-07-11 09:52:58 -04002138 if (mErrors.empty())
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002139 {
Geoff Langda5777c2014-07-11 09:52:58 -04002140 return GL_NO_ERROR;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002141 }
Geoff Langda5777c2014-07-11 09:52:58 -04002142 else
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002143 {
Geoff Langda5777c2014-07-11 09:52:58 -04002144 GLenum error = *mErrors.begin();
2145 mErrors.erase(mErrors.begin());
2146 return error;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002147 }
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002148}
2149
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002150// NOTE: this function should not assume that this context is current!
2151void Context::markContextLost()
2152{
2153 if (mResetStrategy == GL_LOSE_CONTEXT_ON_RESET_EXT)
Kenneth Russellf2f6f652016-10-05 19:53:23 -07002154 {
Jamie Madill231c7f52017-04-26 13:45:37 -04002155 mResetStatus = GL_UNKNOWN_CONTEXT_RESET_EXT;
Kenneth Russellf2f6f652016-10-05 19:53:23 -07002156 mContextLostForced = true;
2157 }
Jamie Madill231c7f52017-04-26 13:45:37 -04002158 mContextLost = true;
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002159}
2160
2161bool Context::isContextLost()
2162{
2163 return mContextLost;
2164}
2165
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002166GLenum Context::getResetStatus()
2167{
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002168 // Even if the application doesn't want to know about resets, we want to know
2169 // as it will allow us to skip all the calls.
2170 if (mResetStrategy == GL_NO_RESET_NOTIFICATION_EXT)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002171 {
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002172 if (!mContextLost && mImplementation->getResetStatus() != GL_NO_ERROR)
Jamie Madill9dd0cf02014-11-24 11:38:51 -05002173 {
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002174 mContextLost = true;
Jamie Madill9dd0cf02014-11-24 11:38:51 -05002175 }
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002176
2177 // EXT_robustness, section 2.6: If the reset notification behavior is
2178 // NO_RESET_NOTIFICATION_EXT, then the implementation will never deliver notification of
2179 // reset events, and GetGraphicsResetStatusEXT will always return NO_ERROR.
2180 return GL_NO_ERROR;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002181 }
2182
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002183 // The GL_EXT_robustness spec says that if a reset is encountered, a reset
2184 // status should be returned at least once, and GL_NO_ERROR should be returned
2185 // once the device has finished resetting.
2186 if (!mContextLost)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002187 {
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002188 ASSERT(mResetStatus == GL_NO_ERROR);
2189 mResetStatus = mImplementation->getResetStatus();
shannon.woods@transgaming.comddd6c802013-02-28 23:05:14 +00002190
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002191 if (mResetStatus != GL_NO_ERROR)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002192 {
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002193 mContextLost = true;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002194 }
2195 }
Kenneth Russellf2f6f652016-10-05 19:53:23 -07002196 else if (!mContextLostForced && mResetStatus != GL_NO_ERROR)
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002197 {
Kenneth Russellf2f6f652016-10-05 19:53:23 -07002198 // If markContextLost was used to mark the context lost then
2199 // assume that is not recoverable, and continue to report the
2200 // lost reset status for the lifetime of this context.
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002201 mResetStatus = mImplementation->getResetStatus();
2202 }
Jamie Madill893ab082014-05-16 16:56:10 -04002203
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002204 return mResetStatus;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002205}
2206
2207bool Context::isResetNotificationEnabled()
2208{
2209 return (mResetStrategy == GL_LOSE_CONTEXT_ON_RESET_EXT);
2210}
2211
Corentin Walleze3b10e82015-05-20 11:06:25 -04002212const egl::Config *Context::getConfig() const
Régis Fénéon83107972015-02-05 12:57:44 +01002213{
Corentin Walleze3b10e82015-05-20 11:06:25 -04002214 return mConfig;
Régis Fénéon83107972015-02-05 12:57:44 +01002215}
2216
2217EGLenum Context::getClientType() const
2218{
2219 return mClientType;
2220}
2221
2222EGLenum Context::getRenderBuffer() const
2223{
Geoff Lang3bf8e3a2016-12-01 17:28:52 -05002224 const Framebuffer *framebuffer = mState.mFramebuffers->getFramebuffer(0);
2225 if (framebuffer == nullptr)
Corentin Wallez37c39792015-08-20 14:19:46 -04002226 {
2227 return EGL_NONE;
2228 }
Geoff Lang3bf8e3a2016-12-01 17:28:52 -05002229
2230 const FramebufferAttachment *backAttachment = framebuffer->getAttachment(GL_BACK);
2231 ASSERT(backAttachment != nullptr);
2232 return backAttachment->getSurface()->getRenderBuffer();
Régis Fénéon83107972015-02-05 12:57:44 +01002233}
2234
Jamie Madill3f01e6c2016-03-08 13:53:02 -05002235VertexArray *Context::checkVertexArrayAllocation(GLuint vertexArrayHandle)
Geoff Lang36167ab2015-12-07 10:27:14 -05002236{
Jamie Madill5bf9ff42016-02-01 11:13:03 -05002237 // Only called after a prior call to Gen.
Jamie Madill3f01e6c2016-03-08 13:53:02 -05002238 VertexArray *vertexArray = getVertexArray(vertexArrayHandle);
2239 if (!vertexArray)
Geoff Lang36167ab2015-12-07 10:27:14 -05002240 {
Jiawei-Shao2597fb62016-12-09 16:38:02 +08002241 vertexArray = new VertexArray(mImplementation.get(), vertexArrayHandle,
2242 mCaps.maxVertexAttributes, mCaps.maxVertexAttribBindings);
Jamie Madill53ea9cc2016-05-17 10:12:52 -04002243
Jamie Madill96a483b2017-06-27 16:49:21 -04002244 mVertexArrayMap.assign(vertexArrayHandle, vertexArray);
Geoff Lang36167ab2015-12-07 10:27:14 -05002245 }
Jamie Madill3f01e6c2016-03-08 13:53:02 -05002246
2247 return vertexArray;
Geoff Lang36167ab2015-12-07 10:27:14 -05002248}
2249
Jamie Madill3f01e6c2016-03-08 13:53:02 -05002250TransformFeedback *Context::checkTransformFeedbackAllocation(GLuint transformFeedbackHandle)
Geoff Lang36167ab2015-12-07 10:27:14 -05002251{
Jamie Madill5bf9ff42016-02-01 11:13:03 -05002252 // Only called after a prior call to Gen.
Jamie Madill3f01e6c2016-03-08 13:53:02 -05002253 TransformFeedback *transformFeedback = getTransformFeedback(transformFeedbackHandle);
2254 if (!transformFeedback)
Geoff Lang36167ab2015-12-07 10:27:14 -05002255 {
Jamie Madill53ea9cc2016-05-17 10:12:52 -04002256 transformFeedback =
2257 new TransformFeedback(mImplementation.get(), transformFeedbackHandle, mCaps);
Jamie Madill3f01e6c2016-03-08 13:53:02 -05002258 transformFeedback->addRef();
Jamie Madill96a483b2017-06-27 16:49:21 -04002259 mTransformFeedbackMap.assign(transformFeedbackHandle, transformFeedback);
Geoff Lang36167ab2015-12-07 10:27:14 -05002260 }
Jamie Madill3f01e6c2016-03-08 13:53:02 -05002261
2262 return transformFeedback;
Geoff Lang36167ab2015-12-07 10:27:14 -05002263}
2264
2265bool Context::isVertexArrayGenerated(GLuint vertexArray)
2266{
Jamie Madill96a483b2017-06-27 16:49:21 -04002267 ASSERT(mVertexArrayMap.contains(0));
2268 return mVertexArrayMap.contains(vertexArray);
Geoff Lang36167ab2015-12-07 10:27:14 -05002269}
2270
2271bool Context::isTransformFeedbackGenerated(GLuint transformFeedback)
2272{
Jamie Madill96a483b2017-06-27 16:49:21 -04002273 ASSERT(mTransformFeedbackMap.contains(0));
2274 return mTransformFeedbackMap.contains(transformFeedback);
Geoff Lang36167ab2015-12-07 10:27:14 -05002275}
2276
Shannon Woods53a94a82014-06-24 15:20:36 -04002277void Context::detachTexture(GLuint texture)
2278{
2279 // Simple pass-through to State's detachTexture method, as textures do not require
2280 // allocation map management either here or in the resource manager at detach time.
2281 // Zero textures are held by the Context, and we don't attempt to request them from
2282 // the State.
Jamie Madilla02315b2017-02-23 14:14:47 -05002283 mGLState.detachTexture(this, mZeroTextures, texture);
Shannon Woods53a94a82014-06-24 15:20:36 -04002284}
2285
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002286void Context::detachBuffer(GLuint buffer)
2287{
Yuly Novikov5807a532015-12-03 13:01:22 -05002288 // Simple pass-through to State's detachBuffer method, since
2289 // only buffer attachments to container objects that are bound to the current context
2290 // should be detached. And all those are available in State.
Shannon Woods53a94a82014-06-24 15:20:36 -04002291
Yuly Novikov5807a532015-12-03 13:01:22 -05002292 // [OpenGL ES 3.2] section 5.1.2 page 45:
2293 // Attachments to unbound container objects, such as
2294 // deletion of a buffer attached to a vertex array object which is not bound to the context,
2295 // are not affected and continue to act as references on the deleted object
Jamie Madill4928b7c2017-06-20 12:57:39 -04002296 mGLState.detachBuffer(this, buffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002297}
2298
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002299void Context::detachFramebuffer(GLuint framebuffer)
2300{
Shannon Woods53a94a82014-06-24 15:20:36 -04002301 // Framebuffer detachment is handled by Context, because 0 is a valid
2302 // Framebuffer object, and a pointer to it must be passed from Context
2303 // to State at binding time.
2304
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002305 // [OpenGL ES 2.0.24] section 4.4 page 107:
Jamie Madill231c7f52017-04-26 13:45:37 -04002306 // If a framebuffer that is currently bound to the target FRAMEBUFFER is deleted, it is as
2307 // though BindFramebuffer had been executed with the target of FRAMEBUFFER and framebuffer of
2308 // zero.
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002309
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002310 if (mGLState.removeReadFramebufferBinding(framebuffer) && framebuffer != 0)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002311 {
2312 bindReadFramebuffer(0);
2313 }
2314
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002315 if (mGLState.removeDrawFramebufferBinding(framebuffer) && framebuffer != 0)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002316 {
2317 bindDrawFramebuffer(0);
2318 }
2319}
2320
2321void Context::detachRenderbuffer(GLuint renderbuffer)
2322{
Jamie Madilla02315b2017-02-23 14:14:47 -05002323 mGLState.detachRenderbuffer(this, renderbuffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002324}
2325
Jamie Madill57a89722013-07-02 11:57:03 -04002326void Context::detachVertexArray(GLuint vertexArray)
2327{
Jamie Madill77a72f62015-04-14 11:18:32 -04002328 // Vertex array detachment is handled by Context, because 0 is a valid
2329 // VAO, and a pointer to it must be passed from Context to State at
Shannon Woods53a94a82014-06-24 15:20:36 -04002330 // binding time.
2331
Jamie Madill57a89722013-07-02 11:57:03 -04002332 // [OpenGL ES 3.0.2] section 2.10 page 43:
2333 // If a vertex array object that is currently bound is deleted, the binding
2334 // for that object reverts to zero and the default vertex array becomes current.
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002335 if (mGLState.removeVertexArrayBinding(vertexArray))
Jamie Madill57a89722013-07-02 11:57:03 -04002336 {
2337 bindVertexArray(0);
2338 }
2339}
2340
Geoff Langc8058452014-02-03 12:04:11 -05002341void Context::detachTransformFeedback(GLuint transformFeedback)
2342{
Corentin Walleza2257da2016-04-19 16:43:12 -04002343 // Transform feedback detachment is handled by Context, because 0 is a valid
2344 // transform feedback, and a pointer to it must be passed from Context to State at
2345 // binding time.
2346
2347 // The OpenGL specification doesn't mention what should happen when the currently bound
2348 // transform feedback object is deleted. Since it is a container object, we treat it like
2349 // VAOs and FBOs and set the current bound transform feedback back to 0.
Jamie Madill4928b7c2017-06-20 12:57:39 -04002350 if (mGLState.removeTransformFeedbackBinding(this, transformFeedback))
Corentin Walleza2257da2016-04-19 16:43:12 -04002351 {
Jamie Madillf0dcb8b2017-08-26 19:05:13 -04002352 bindTransformFeedback(GL_TRANSFORM_FEEDBACK, 0);
Corentin Walleza2257da2016-04-19 16:43:12 -04002353 }
Geoff Langc8058452014-02-03 12:04:11 -05002354}
2355
Jamie Madilldc356042013-07-19 16:36:57 -04002356void Context::detachSampler(GLuint sampler)
2357{
Jamie Madill4928b7c2017-06-20 12:57:39 -04002358 mGLState.detachSampler(this, sampler);
Jamie Madilldc356042013-07-19 16:36:57 -04002359}
2360
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002361void Context::setVertexAttribDivisor(GLuint index, GLuint divisor)
2362{
Shaodde78e82017-05-22 14:13:27 +08002363 mGLState.setVertexAttribDivisor(this, index, divisor);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002364}
2365
Jamie Madille29d1672013-07-19 16:36:57 -04002366void Context::samplerParameteri(GLuint sampler, GLenum pname, GLint param)
2367{
Geoff Langc1984ed2016-10-07 12:41:00 -04002368 Sampler *samplerObject =
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002369 mState.mSamplers->checkSamplerAllocation(mImplementation.get(), sampler);
Geoff Langc1984ed2016-10-07 12:41:00 -04002370 SetSamplerParameteri(samplerObject, pname, param);
2371}
Jamie Madille29d1672013-07-19 16:36:57 -04002372
Geoff Langc1984ed2016-10-07 12:41:00 -04002373void Context::samplerParameteriv(GLuint sampler, GLenum pname, const GLint *param)
2374{
2375 Sampler *samplerObject =
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002376 mState.mSamplers->checkSamplerAllocation(mImplementation.get(), sampler);
Geoff Langc1984ed2016-10-07 12:41:00 -04002377 SetSamplerParameteriv(samplerObject, pname, param);
Jamie Madille29d1672013-07-19 16:36:57 -04002378}
2379
2380void Context::samplerParameterf(GLuint sampler, GLenum pname, GLfloat param)
2381{
Geoff Langc1984ed2016-10-07 12:41:00 -04002382 Sampler *samplerObject =
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002383 mState.mSamplers->checkSamplerAllocation(mImplementation.get(), sampler);
Geoff Langc1984ed2016-10-07 12:41:00 -04002384 SetSamplerParameterf(samplerObject, pname, param);
Jamie Madille29d1672013-07-19 16:36:57 -04002385}
2386
Geoff Langc1984ed2016-10-07 12:41:00 -04002387void Context::samplerParameterfv(GLuint sampler, GLenum pname, const GLfloat *param)
Jamie Madill9675b802013-07-19 16:36:59 -04002388{
Geoff Langc1984ed2016-10-07 12:41:00 -04002389 Sampler *samplerObject =
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002390 mState.mSamplers->checkSamplerAllocation(mImplementation.get(), sampler);
Geoff Langc1984ed2016-10-07 12:41:00 -04002391 SetSamplerParameterfv(samplerObject, pname, param);
Jamie Madill9675b802013-07-19 16:36:59 -04002392}
2393
Geoff Langc1984ed2016-10-07 12:41:00 -04002394void Context::getSamplerParameteriv(GLuint sampler, GLenum pname, GLint *params)
Jamie Madill9675b802013-07-19 16:36:59 -04002395{
Geoff Langc1984ed2016-10-07 12:41:00 -04002396 const Sampler *samplerObject =
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002397 mState.mSamplers->checkSamplerAllocation(mImplementation.get(), sampler);
Geoff Langc1984ed2016-10-07 12:41:00 -04002398 QuerySamplerParameteriv(samplerObject, pname, params);
2399}
Jamie Madill9675b802013-07-19 16:36:59 -04002400
Geoff Langc1984ed2016-10-07 12:41:00 -04002401void Context::getSamplerParameterfv(GLuint sampler, GLenum pname, GLfloat *params)
2402{
2403 const Sampler *samplerObject =
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002404 mState.mSamplers->checkSamplerAllocation(mImplementation.get(), sampler);
Geoff Langc1984ed2016-10-07 12:41:00 -04002405 QuerySamplerParameterfv(samplerObject, pname, params);
Jamie Madill9675b802013-07-19 16:36:59 -04002406}
2407
Olli Etuahof0fee072016-03-30 15:11:58 +03002408void Context::programParameteri(GLuint program, GLenum pname, GLint value)
2409{
2410 gl::Program *programObject = getProgram(program);
Yunchao He61afff12017-03-14 15:34:03 +08002411 SetProgramParameteri(programObject, pname, value);
Olli Etuahof0fee072016-03-30 15:11:58 +03002412}
2413
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002414void Context::initRendererString()
2415{
daniel@transgaming.comca1ac1f2013-01-11 04:13:05 +00002416 std::ostringstream rendererString;
2417 rendererString << "ANGLE (";
Jamie Madill53ea9cc2016-05-17 10:12:52 -04002418 rendererString << mImplementation->getRendererDescription();
daniel@transgaming.comca1ac1f2013-01-11 04:13:05 +00002419 rendererString << ")";
2420
Geoff Langcec35902014-04-16 10:52:36 -04002421 mRendererString = MakeStaticString(rendererString.str());
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002422}
2423
Geoff Langc339c4e2016-11-29 10:37:36 -05002424void Context::initVersionStrings()
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002425{
Geoff Langc339c4e2016-11-29 10:37:36 -05002426 const Version &clientVersion = getClientVersion();
2427
2428 std::ostringstream versionString;
2429 versionString << "OpenGL ES " << clientVersion.major << "." << clientVersion.minor << " (ANGLE "
2430 << ANGLE_VERSION_STRING << ")";
2431 mVersionString = MakeStaticString(versionString.str());
2432
2433 std::ostringstream shadingLanguageVersionString;
2434 shadingLanguageVersionString << "OpenGL ES GLSL ES "
2435 << (clientVersion.major == 2 ? 1 : clientVersion.major) << "."
2436 << clientVersion.minor << "0 (ANGLE " << ANGLE_VERSION_STRING
2437 << ")";
2438 mShadingLanguageString = MakeStaticString(shadingLanguageVersionString.str());
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002439}
2440
Geoff Langcec35902014-04-16 10:52:36 -04002441void Context::initExtensionStrings()
2442{
Geoff Langc339c4e2016-11-29 10:37:36 -05002443 auto mergeExtensionStrings = [](const std::vector<const char *> &strings) {
2444 std::ostringstream combinedStringStream;
2445 std::copy(strings.begin(), strings.end(),
2446 std::ostream_iterator<const char *>(combinedStringStream, " "));
2447 return MakeStaticString(combinedStringStream.str());
2448 };
2449
2450 mExtensionStrings.clear();
Geoff Langc287ea62016-09-16 14:46:51 -04002451 for (const auto &extensionString : mExtensions.getStrings())
2452 {
2453 mExtensionStrings.push_back(MakeStaticString(extensionString));
2454 }
Geoff Langc339c4e2016-11-29 10:37:36 -05002455 mExtensionString = mergeExtensionStrings(mExtensionStrings);
Geoff Langcec35902014-04-16 10:52:36 -04002456
Bryan Bernhart58806562017-01-05 13:09:31 -08002457 const gl::Extensions &nativeExtensions = mImplementation->getNativeExtensions();
2458
Geoff Langc339c4e2016-11-29 10:37:36 -05002459 mRequestableExtensionStrings.clear();
2460 for (const auto &extensionInfo : GetExtensionInfoMap())
2461 {
2462 if (extensionInfo.second.Requestable &&
Bryan Bernhart58806562017-01-05 13:09:31 -08002463 !(mExtensions.*(extensionInfo.second.ExtensionsMember)) &&
2464 nativeExtensions.*(extensionInfo.second.ExtensionsMember))
Geoff Langc339c4e2016-11-29 10:37:36 -05002465 {
2466 mRequestableExtensionStrings.push_back(MakeStaticString(extensionInfo.first));
2467 }
2468 }
2469 mRequestableExtensionString = mergeExtensionStrings(mRequestableExtensionStrings);
Geoff Langcec35902014-04-16 10:52:36 -04002470}
2471
Geoff Langc339c4e2016-11-29 10:37:36 -05002472const GLubyte *Context::getString(GLenum name) const
Geoff Langcec35902014-04-16 10:52:36 -04002473{
Geoff Langc339c4e2016-11-29 10:37:36 -05002474 switch (name)
2475 {
2476 case GL_VENDOR:
2477 return reinterpret_cast<const GLubyte *>("Google Inc.");
2478
2479 case GL_RENDERER:
2480 return reinterpret_cast<const GLubyte *>(mRendererString);
2481
2482 case GL_VERSION:
2483 return reinterpret_cast<const GLubyte *>(mVersionString);
2484
2485 case GL_SHADING_LANGUAGE_VERSION:
2486 return reinterpret_cast<const GLubyte *>(mShadingLanguageString);
2487
2488 case GL_EXTENSIONS:
2489 return reinterpret_cast<const GLubyte *>(mExtensionString);
2490
2491 case GL_REQUESTABLE_EXTENSIONS_ANGLE:
2492 return reinterpret_cast<const GLubyte *>(mRequestableExtensionString);
2493
2494 default:
2495 UNREACHABLE();
2496 return nullptr;
2497 }
Geoff Langcec35902014-04-16 10:52:36 -04002498}
2499
Geoff Langc339c4e2016-11-29 10:37:36 -05002500const GLubyte *Context::getStringi(GLenum name, GLuint index) const
Geoff Langcec35902014-04-16 10:52:36 -04002501{
Geoff Langc339c4e2016-11-29 10:37:36 -05002502 switch (name)
2503 {
2504 case GL_EXTENSIONS:
2505 return reinterpret_cast<const GLubyte *>(mExtensionStrings[index]);
2506
2507 case GL_REQUESTABLE_EXTENSIONS_ANGLE:
2508 return reinterpret_cast<const GLubyte *>(mRequestableExtensionStrings[index]);
2509
2510 default:
2511 UNREACHABLE();
2512 return nullptr;
2513 }
Geoff Langcec35902014-04-16 10:52:36 -04002514}
2515
2516size_t Context::getExtensionStringCount() const
2517{
2518 return mExtensionStrings.size();
2519}
2520
Geoff Langc339c4e2016-11-29 10:37:36 -05002521void Context::requestExtension(const char *name)
2522{
2523 const ExtensionInfoMap &extensionInfos = GetExtensionInfoMap();
2524 ASSERT(extensionInfos.find(name) != extensionInfos.end());
2525 const auto &extension = extensionInfos.at(name);
2526 ASSERT(extension.Requestable);
2527
2528 if (mExtensions.*(extension.ExtensionsMember))
2529 {
2530 // Extension already enabled
2531 return;
2532 }
2533
2534 mExtensions.*(extension.ExtensionsMember) = true;
2535 updateCaps();
2536 initExtensionStrings();
Bryan Bernhart58806562017-01-05 13:09:31 -08002537
Jamie Madill2f348d22017-06-05 10:50:59 -04002538 // Release the shader compiler so it will be re-created with the requested extensions enabled.
2539 releaseShaderCompiler();
Geoff Lang9aded172017-04-05 11:07:56 -04002540
2541 // Invalidate all cached completenesses for textures and framebuffer. Some extensions make new
2542 // formats renderable or sampleable.
2543 mState.mTextures->invalidateTextureComplenessCache();
2544 for (auto &zeroTexture : mZeroTextures)
2545 {
2546 zeroTexture.second->invalidateCompletenessCache();
2547 }
2548
2549 mState.mFramebuffers->invalidateFramebufferComplenessCache();
Geoff Langc339c4e2016-11-29 10:37:36 -05002550}
2551
2552size_t Context::getRequestableExtensionStringCount() const
2553{
2554 return mRequestableExtensionStrings.size();
2555}
2556
Olli Etuahoc3e55a42016-03-09 16:29:18 +02002557void Context::beginTransformFeedback(GLenum primitiveMode)
2558{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002559 TransformFeedback *transformFeedback = mGLState.getCurrentTransformFeedback();
Olli Etuahoc3e55a42016-03-09 16:29:18 +02002560 ASSERT(transformFeedback != nullptr);
2561 ASSERT(!transformFeedback->isPaused());
2562
Jamie Madill6c1f6712017-02-14 19:08:04 -05002563 transformFeedback->begin(this, primitiveMode, mGLState.getProgram());
Olli Etuahoc3e55a42016-03-09 16:29:18 +02002564}
2565
2566bool Context::hasActiveTransformFeedback(GLuint program) const
2567{
2568 for (auto pair : mTransformFeedbackMap)
2569 {
2570 if (pair.second != nullptr && pair.second->hasBoundProgram(program))
2571 {
2572 return true;
2573 }
2574 }
2575 return false;
2576}
2577
Jamie Madill4e0e6f82017-02-17 11:06:03 -05002578void Context::initCaps(const egl::DisplayExtensions &displayExtensions)
Geoff Lang493daf52014-07-03 13:38:44 -04002579{
Jamie Madill53ea9cc2016-05-17 10:12:52 -04002580 mCaps = mImplementation->getNativeCaps();
Geoff Lang493daf52014-07-03 13:38:44 -04002581
Jamie Madill53ea9cc2016-05-17 10:12:52 -04002582 mExtensions = mImplementation->getNativeExtensions();
Geoff Lang493daf52014-07-03 13:38:44 -04002583
Jamie Madill53ea9cc2016-05-17 10:12:52 -04002584 mLimitations = mImplementation->getNativeLimitations();
Austin Kinross02df7962015-07-01 10:03:42 -07002585
Geoff Langeb66a6e2016-10-31 13:06:12 -04002586 if (getClientVersion() < Version(3, 0))
Geoff Lang493daf52014-07-03 13:38:44 -04002587 {
2588 // Disable ES3+ extensions
Jamie Madill231c7f52017-04-26 13:45:37 -04002589 mExtensions.colorBufferFloat = false;
Geoff Langb66a9092016-05-16 15:59:14 -04002590 mExtensions.eglImageExternalEssl3 = false;
Vincent Lang25ab4512016-05-13 18:13:59 +02002591 mExtensions.textureNorm16 = false;
Martin Radev137032d2017-07-13 10:11:12 +03002592 mExtensions.multiview = false;
2593 mExtensions.maxViews = 1u;
Geoff Lang493daf52014-07-03 13:38:44 -04002594 }
2595
Geoff Langeb66a6e2016-10-31 13:06:12 -04002596 if (getClientVersion() > Version(2, 0))
Geoff Lang493daf52014-07-03 13:38:44 -04002597 {
2598 // FIXME(geofflang): Don't support EXT_sRGB in non-ES2 contexts
Jamie Madill231c7f52017-04-26 13:45:37 -04002599 // mExtensions.sRGB = false;
Geoff Lang493daf52014-07-03 13:38:44 -04002600 }
2601
Jamie Madill00ed7a12016-05-19 13:13:38 -04002602 // Some extensions are always available because they are implemented in the GL layer.
Jamie Madill231c7f52017-04-26 13:45:37 -04002603 mExtensions.bindUniformLocation = true;
2604 mExtensions.vertexArrayObject = true;
Geoff Langf41a7152016-09-19 15:11:17 -04002605 mExtensions.bindGeneratesResource = true;
Geoff Langfeb8c682017-02-13 16:07:35 -05002606 mExtensions.clientArrays = true;
Geoff Langc339c4e2016-11-29 10:37:36 -05002607 mExtensions.requestExtension = true;
Jamie Madill00ed7a12016-05-19 13:13:38 -04002608
2609 // Enable the no error extension if the context was created with the flag.
2610 mExtensions.noError = mSkipValidation;
2611
Corentin Wallezccab69d2017-01-27 16:57:15 -05002612 // Enable surfaceless to advertise we'll have the correct behavior when there is no default FBO
Corentin Wallezc295e512017-01-27 17:47:50 -05002613 mExtensions.surfacelessContext = displayExtensions.surfacelessContext;
Corentin Wallezccab69d2017-01-27 16:57:15 -05002614
Geoff Lang70d0f492015-12-10 17:45:46 -05002615 // Explicitly enable GL_KHR_debug
2616 mExtensions.debug = true;
2617 mExtensions.maxDebugMessageLength = 1024;
2618 mExtensions.maxDebugLoggedMessages = 1024;
2619 mExtensions.maxDebugGroupStackDepth = 1024;
2620 mExtensions.maxLabelLength = 1024;
2621
Geoff Langff5b2d52016-09-07 11:32:23 -04002622 // Explicitly enable GL_ANGLE_robust_client_memory
2623 mExtensions.robustClientMemory = true;
2624
Jamie Madille08a1d32017-03-07 17:24:06 -05002625 // Determine robust resource init availability from EGL.
2626 mExtensions.robustResourceInitialization =
Jamie Madill948bbe52017-06-01 13:10:42 -04002627 egl::Display::GetClientExtensions().displayRobustResourceInitialization;
Jamie Madille08a1d32017-03-07 17:24:06 -05002628
Jamie Madillc43be722017-07-13 16:22:14 -04002629 // Enable the cache control query unconditionally.
2630 mExtensions.programCacheControl = true;
2631
Geoff Lang301d1612014-07-09 10:34:37 -04002632 // Apply implementation limits
2633 mCaps.maxVertexAttributes = std::min<GLuint>(mCaps.maxVertexAttributes, MAX_VERTEX_ATTRIBS);
Jiawei-Shao2597fb62016-12-09 16:38:02 +08002634 mCaps.maxVertexAttribBindings =
2635 getClientVersion() < ES_3_1
2636 ? mCaps.maxVertexAttributes
2637 : std::min<GLuint>(mCaps.maxVertexAttribBindings, MAX_VERTEX_ATTRIB_BINDINGS);
2638
Jamie Madill231c7f52017-04-26 13:45:37 -04002639 mCaps.maxVertexUniformBlocks = std::min<GLuint>(
2640 mCaps.maxVertexUniformBlocks, IMPLEMENTATION_MAX_VERTEX_SHADER_UNIFORM_BUFFERS);
2641 mCaps.maxVertexOutputComponents =
2642 std::min<GLuint>(mCaps.maxVertexOutputComponents, IMPLEMENTATION_MAX_VARYING_VECTORS * 4);
Geoff Lang301d1612014-07-09 10:34:37 -04002643
Jamie Madill231c7f52017-04-26 13:45:37 -04002644 mCaps.maxFragmentInputComponents =
2645 std::min<GLuint>(mCaps.maxFragmentInputComponents, IMPLEMENTATION_MAX_VARYING_VECTORS * 4);
Geoff Lang3a61c322014-07-10 13:01:54 -04002646
Geoff Langc287ea62016-09-16 14:46:51 -04002647 // WebGL compatibility
Jamie Madill4e0e6f82017-02-17 11:06:03 -05002648 mExtensions.webglCompatibility = mWebGLContext;
Geoff Langc287ea62016-09-16 14:46:51 -04002649 for (const auto &extensionInfo : GetExtensionInfoMap())
2650 {
2651 // If this context is for WebGL, disable all enableable extensions
Jamie Madill4e0e6f82017-02-17 11:06:03 -05002652 if (mWebGLContext && extensionInfo.second.Requestable)
Geoff Langc287ea62016-09-16 14:46:51 -04002653 {
2654 mExtensions.*(extensionInfo.second.ExtensionsMember) = false;
2655 }
2656 }
2657
2658 // Generate texture caps
2659 updateCaps();
2660}
2661
2662void Context::updateCaps()
2663{
Geoff Lang900013c2014-07-07 11:32:19 -04002664 mCaps.compressedTextureFormats.clear();
Geoff Langc287ea62016-09-16 14:46:51 -04002665 mTextureCaps.clear();
Geoff Lang900013c2014-07-07 11:32:19 -04002666
Jamie Madill4e0e6f82017-02-17 11:06:03 -05002667 for (auto capsIt : mImplementation->getNativeTextureCaps())
Geoff Lang493daf52014-07-03 13:38:44 -04002668 {
Geoff Langca271392017-04-05 12:30:00 -04002669 GLenum sizedInternalFormat = capsIt.first;
Jamie Madill231c7f52017-04-26 13:45:37 -04002670 TextureCaps formatCaps = capsIt.second;
Geoff Lang493daf52014-07-03 13:38:44 -04002671
Geoff Langca271392017-04-05 12:30:00 -04002672 const InternalFormat &formatInfo = GetSizedInternalFormatInfo(sizedInternalFormat);
Geoff Langd87878e2014-09-19 15:42:59 -04002673
Geoff Lang0d8b7242015-09-09 14:56:53 -04002674 // Update the format caps based on the client version and extensions.
2675 // Caps are AND'd with the renderer caps because some core formats are still unsupported in
2676 // ES3.
2677 formatCaps.texturable =
Geoff Langeb66a6e2016-10-31 13:06:12 -04002678 formatCaps.texturable && formatInfo.textureSupport(getClientVersion(), mExtensions);
Geoff Lang0d8b7242015-09-09 14:56:53 -04002679 formatCaps.renderable =
Geoff Langeb66a6e2016-10-31 13:06:12 -04002680 formatCaps.renderable && formatInfo.renderSupport(getClientVersion(), mExtensions);
Geoff Lang0d8b7242015-09-09 14:56:53 -04002681 formatCaps.filterable =
Geoff Langeb66a6e2016-10-31 13:06:12 -04002682 formatCaps.filterable && formatInfo.filterSupport(getClientVersion(), mExtensions);
Geoff Langd87878e2014-09-19 15:42:59 -04002683
He Yunchaoccd8c9b2017-01-18 17:36:14 +08002684 // OpenGL ES does not support multisampling with non-rendererable formats
2685 // OpenGL ES 3.0 or prior does not support multisampling with integer formats
Olli Etuaho50c562d2017-06-06 14:43:30 +03002686 if (!formatCaps.renderable ||
He Yunchaoccd8c9b2017-01-18 17:36:14 +08002687 (getClientVersion() < ES_3_1 &&
2688 (formatInfo.componentType == GL_INT || formatInfo.componentType == GL_UNSIGNED_INT)))
Geoff Lang493daf52014-07-03 13:38:44 -04002689 {
Geoff Langd87878e2014-09-19 15:42:59 -04002690 formatCaps.sampleCounts.clear();
Geoff Lang493daf52014-07-03 13:38:44 -04002691 }
Olli Etuaho50c562d2017-06-06 14:43:30 +03002692 else
2693 {
2694 // We may have limited the max samples for some required renderbuffer formats due to
2695 // non-conformant formats. In this case MAX_SAMPLES needs to be lowered accordingly.
2696 GLuint formatMaxSamples = formatCaps.getMaxSamples();
2697
2698 // GLES 3.0.5 section 4.4.2.2: "Implementations must support creation of renderbuffers
2699 // in these required formats with up to the value of MAX_SAMPLES multisamples, with the
2700 // exception of signed and unsigned integer formats."
2701 if (formatInfo.componentType != GL_INT && formatInfo.componentType != GL_UNSIGNED_INT &&
2702 formatInfo.isRequiredRenderbufferFormat(getClientVersion()))
2703 {
2704 ASSERT(getClientVersion() < ES_3_0 || formatMaxSamples >= 4);
2705 mCaps.maxSamples = std::min(mCaps.maxSamples, formatMaxSamples);
2706 }
2707
2708 // Handle GLES 3.1 MAX_*_SAMPLES values similarly to MAX_SAMPLES.
2709 if (getClientVersion() >= ES_3_1)
2710 {
2711 // GLES 3.1 section 9.2.5: "Implementations must support creation of renderbuffers
2712 // in these required formats with up to the value of MAX_SAMPLES multisamples, with
2713 // the exception that the signed and unsigned integer formats are required only to
2714 // support creation of renderbuffers with up to the value of MAX_INTEGER_SAMPLES
2715 // multisamples, which must be at least one."
2716 if (formatInfo.componentType == GL_INT ||
2717 formatInfo.componentType == GL_UNSIGNED_INT)
2718 {
2719 mCaps.maxIntegerSamples = std::min(mCaps.maxIntegerSamples, formatMaxSamples);
2720 }
2721
2722 // GLES 3.1 section 19.3.1.
2723 if (formatCaps.texturable)
2724 {
2725 if (formatInfo.depthBits > 0)
2726 {
2727 mCaps.maxDepthTextureSamples =
2728 std::min(mCaps.maxDepthTextureSamples, formatMaxSamples);
2729 }
2730 else if (formatInfo.redBits > 0)
2731 {
2732 mCaps.maxColorTextureSamples =
2733 std::min(mCaps.maxColorTextureSamples, formatMaxSamples);
2734 }
2735 }
2736 }
2737 }
Geoff Langd87878e2014-09-19 15:42:59 -04002738
2739 if (formatCaps.texturable && formatInfo.compressed)
2740 {
Geoff Langca271392017-04-05 12:30:00 -04002741 mCaps.compressedTextureFormats.push_back(sizedInternalFormat);
Geoff Langd87878e2014-09-19 15:42:59 -04002742 }
2743
Geoff Langca271392017-04-05 12:30:00 -04002744 mTextureCaps.insert(sizedInternalFormat, formatCaps);
Geoff Lang493daf52014-07-03 13:38:44 -04002745 }
Jamie Madill32447362017-06-28 14:53:52 -04002746
2747 // If program binary is disabled, blank out the memory cache pointer.
2748 if (!mImplementation->getNativeExtensions().getProgramBinary)
2749 {
2750 mMemoryProgramCache = nullptr;
2751 }
Geoff Lang493daf52014-07-03 13:38:44 -04002752}
2753
Kenneth Russellf2f6f652016-10-05 19:53:23 -07002754void Context::initWorkarounds()
2755{
Jamie Madill761b02c2017-06-23 16:27:06 -04002756 // Apply back-end workarounds.
2757 mImplementation->applyNativeWorkarounds(&mWorkarounds);
2758
Kenneth Russellf2f6f652016-10-05 19:53:23 -07002759 // Lose the context upon out of memory error if the application is
2760 // expecting to watch for those events.
2761 mWorkarounds.loseContextOnOutOfMemory = (mResetStrategy == GL_LOSE_CONTEXT_ON_RESET_EXT);
2762}
2763
Jamie Madill4c19a8a2017-07-24 11:46:06 -04002764Error Context::prepareForDraw(GLenum drawMode)
Jamie Madillb6664922017-07-25 12:55:04 -04002765{
2766 syncRendererState();
Jamie Madill4c19a8a2017-07-24 11:46:06 -04002767
2768 InfoLog infoLog;
2769 Error err = mImplementation->triggerDrawCallProgramRecompilation(this, &infoLog,
2770 mMemoryProgramCache, drawMode);
Jamie Madilla836b462017-08-16 14:58:35 -04002771 if (err.isError() || infoLog.getLength() > 0)
Jamie Madill4c19a8a2017-07-24 11:46:06 -04002772 {
2773 WARN() << "Dynamic recompilation error log: " << infoLog.str();
2774 }
2775 return err;
Jamie Madillb6664922017-07-25 12:55:04 -04002776}
2777
Jamie Madill1b94d432015-08-07 13:23:23 -04002778void Context::syncRendererState()
2779{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002780 const State::DirtyBits &dirtyBits = mGLState.getDirtyBits();
Jamie Madillfe548342017-06-19 11:13:24 -04002781 mImplementation->syncState(this, dirtyBits);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002782 mGLState.clearDirtyBits();
Jamie Madilldd43e6c2017-03-24 14:18:49 -04002783 mGLState.syncDirtyObjects(this);
Jamie Madill1b94d432015-08-07 13:23:23 -04002784}
2785
Jamie Madillad9f24e2016-02-12 09:27:24 -05002786void Context::syncRendererState(const State::DirtyBits &bitMask,
2787 const State::DirtyObjects &objectMask)
Jamie Madill1b94d432015-08-07 13:23:23 -04002788{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002789 const State::DirtyBits &dirtyBits = (mGLState.getDirtyBits() & bitMask);
Jamie Madillfe548342017-06-19 11:13:24 -04002790 mImplementation->syncState(this, dirtyBits);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002791 mGLState.clearDirtyBits(dirtyBits);
Jamie Madilldd43e6c2017-03-24 14:18:49 -04002792 mGLState.syncDirtyObjects(this, objectMask);
Jamie Madill1b94d432015-08-07 13:23:23 -04002793}
Jamie Madillc29968b2016-01-20 11:17:23 -05002794
2795void Context::blitFramebuffer(GLint srcX0,
2796 GLint srcY0,
2797 GLint srcX1,
2798 GLint srcY1,
2799 GLint dstX0,
2800 GLint dstY0,
2801 GLint dstX1,
2802 GLint dstY1,
2803 GLbitfield mask,
2804 GLenum filter)
2805{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002806 Framebuffer *drawFramebuffer = mGLState.getDrawFramebuffer();
Jamie Madillc29968b2016-01-20 11:17:23 -05002807 ASSERT(drawFramebuffer);
2808
2809 Rectangle srcArea(srcX0, srcY0, srcX1 - srcX0, srcY1 - srcY0);
2810 Rectangle dstArea(dstX0, dstY0, dstX1 - dstX0, dstY1 - dstY0);
2811
Jamie Madillad9f24e2016-02-12 09:27:24 -05002812 syncStateForBlit();
Jamie Madillc29968b2016-01-20 11:17:23 -05002813
Jamie Madillc564c072017-06-01 12:45:42 -04002814 handleError(drawFramebuffer->blit(this, srcArea, dstArea, mask, filter));
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002815}
Jamie Madillc29968b2016-01-20 11:17:23 -05002816
2817void Context::clear(GLbitfield mask)
2818{
Jamie Madillad9f24e2016-02-12 09:27:24 -05002819 syncStateForClear();
Jamie Madillc564c072017-06-01 12:45:42 -04002820 handleError(mGLState.getDrawFramebuffer()->clear(this, mask));
Jamie Madillc29968b2016-01-20 11:17:23 -05002821}
2822
2823void Context::clearBufferfv(GLenum buffer, GLint drawbuffer, const GLfloat *values)
2824{
Jamie Madillad9f24e2016-02-12 09:27:24 -05002825 syncStateForClear();
Jamie Madillc564c072017-06-01 12:45:42 -04002826 handleError(mGLState.getDrawFramebuffer()->clearBufferfv(this, buffer, drawbuffer, values));
Jamie Madillc29968b2016-01-20 11:17:23 -05002827}
2828
2829void Context::clearBufferuiv(GLenum buffer, GLint drawbuffer, const GLuint *values)
2830{
Jamie Madillad9f24e2016-02-12 09:27:24 -05002831 syncStateForClear();
Jamie Madillc564c072017-06-01 12:45:42 -04002832 handleError(mGLState.getDrawFramebuffer()->clearBufferuiv(this, buffer, drawbuffer, values));
Jamie Madillc29968b2016-01-20 11:17:23 -05002833}
2834
2835void Context::clearBufferiv(GLenum buffer, GLint drawbuffer, const GLint *values)
2836{
Jamie Madillad9f24e2016-02-12 09:27:24 -05002837 syncStateForClear();
Jamie Madillc564c072017-06-01 12:45:42 -04002838 handleError(mGLState.getDrawFramebuffer()->clearBufferiv(this, buffer, drawbuffer, values));
Jamie Madillc29968b2016-01-20 11:17:23 -05002839}
2840
2841void Context::clearBufferfi(GLenum buffer, GLint drawbuffer, GLfloat depth, GLint stencil)
2842{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002843 Framebuffer *framebufferObject = mGLState.getDrawFramebuffer();
Jamie Madillc29968b2016-01-20 11:17:23 -05002844 ASSERT(framebufferObject);
2845
2846 // If a buffer is not present, the clear has no effect
2847 if (framebufferObject->getDepthbuffer() == nullptr &&
2848 framebufferObject->getStencilbuffer() == nullptr)
2849 {
2850 return;
2851 }
2852
Jamie Madillad9f24e2016-02-12 09:27:24 -05002853 syncStateForClear();
Jamie Madillc564c072017-06-01 12:45:42 -04002854 handleError(framebufferObject->clearBufferfi(this, buffer, drawbuffer, depth, stencil));
Jamie Madillc29968b2016-01-20 11:17:23 -05002855}
2856
2857void Context::readPixels(GLint x,
2858 GLint y,
2859 GLsizei width,
2860 GLsizei height,
2861 GLenum format,
2862 GLenum type,
Jamie Madill876429b2017-04-20 15:46:24 -04002863 void *pixels)
Jamie Madillc29968b2016-01-20 11:17:23 -05002864{
Corentin Wallez9a8d3662016-09-22 12:18:29 -04002865 if (width == 0 || height == 0)
2866 {
2867 return;
2868 }
2869
Jamie Madillad9f24e2016-02-12 09:27:24 -05002870 syncStateForReadPixels();
Jamie Madillc29968b2016-01-20 11:17:23 -05002871
Jamie Madillb6664922017-07-25 12:55:04 -04002872 Framebuffer *readFBO = mGLState.getReadFramebuffer();
2873 ASSERT(readFBO);
Jamie Madillc29968b2016-01-20 11:17:23 -05002874
2875 Rectangle area(x, y, width, height);
Jamie Madillb6664922017-07-25 12:55:04 -04002876 handleError(readFBO->readPixels(this, area, format, type, pixels));
Jamie Madillc29968b2016-01-20 11:17:23 -05002877}
2878
2879void Context::copyTexImage2D(GLenum target,
2880 GLint level,
2881 GLenum internalformat,
2882 GLint x,
2883 GLint y,
2884 GLsizei width,
2885 GLsizei height,
2886 GLint border)
2887{
Jamie Madill60ec6ea2016-01-22 15:27:19 -05002888 // Only sync the read FBO
Jamie Madilldd43e6c2017-03-24 14:18:49 -04002889 mGLState.syncDirtyObject(this, GL_READ_FRAMEBUFFER);
Jamie Madill60ec6ea2016-01-22 15:27:19 -05002890
Jamie Madillc29968b2016-01-20 11:17:23 -05002891 Rectangle sourceArea(x, y, width, height);
2892
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002893 const Framebuffer *framebuffer = mGLState.getReadFramebuffer();
Jamie Madillc29968b2016-01-20 11:17:23 -05002894 Texture *texture =
2895 getTargetTexture(IsCubeMapTextureTarget(target) ? GL_TEXTURE_CUBE_MAP : target);
Jamie Madill8897afa2017-02-06 17:17:23 -05002896 handleError(texture->copyImage(this, target, level, sourceArea, internalformat, framebuffer));
Jamie Madillc29968b2016-01-20 11:17:23 -05002897}
2898
2899void Context::copyTexSubImage2D(GLenum target,
2900 GLint level,
2901 GLint xoffset,
2902 GLint yoffset,
2903 GLint x,
2904 GLint y,
2905 GLsizei width,
2906 GLsizei height)
2907{
Corentin Wallez9a8d3662016-09-22 12:18:29 -04002908 if (width == 0 || height == 0)
2909 {
2910 return;
2911 }
2912
Jamie Madill60ec6ea2016-01-22 15:27:19 -05002913 // Only sync the read FBO
Jamie Madilldd43e6c2017-03-24 14:18:49 -04002914 mGLState.syncDirtyObject(this, GL_READ_FRAMEBUFFER);
Jamie Madill60ec6ea2016-01-22 15:27:19 -05002915
Jamie Madillc29968b2016-01-20 11:17:23 -05002916 Offset destOffset(xoffset, yoffset, 0);
2917 Rectangle sourceArea(x, y, width, height);
2918
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002919 const Framebuffer *framebuffer = mGLState.getReadFramebuffer();
Jamie Madillc29968b2016-01-20 11:17:23 -05002920 Texture *texture =
2921 getTargetTexture(IsCubeMapTextureTarget(target) ? GL_TEXTURE_CUBE_MAP : target);
Jamie Madill8897afa2017-02-06 17:17:23 -05002922 handleError(texture->copySubImage(this, target, level, destOffset, sourceArea, framebuffer));
Jamie Madillc29968b2016-01-20 11:17:23 -05002923}
2924
2925void Context::copyTexSubImage3D(GLenum target,
2926 GLint level,
2927 GLint xoffset,
2928 GLint yoffset,
2929 GLint zoffset,
2930 GLint x,
2931 GLint y,
2932 GLsizei width,
2933 GLsizei height)
2934{
Corentin Wallez9a8d3662016-09-22 12:18:29 -04002935 if (width == 0 || height == 0)
2936 {
2937 return;
2938 }
2939
Jamie Madill60ec6ea2016-01-22 15:27:19 -05002940 // Only sync the read FBO
Jamie Madilldd43e6c2017-03-24 14:18:49 -04002941 mGLState.syncDirtyObject(this, GL_READ_FRAMEBUFFER);
Jamie Madill60ec6ea2016-01-22 15:27:19 -05002942
Jamie Madillc29968b2016-01-20 11:17:23 -05002943 Offset destOffset(xoffset, yoffset, zoffset);
2944 Rectangle sourceArea(x, y, width, height);
2945
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002946 const Framebuffer *framebuffer = mGLState.getReadFramebuffer();
Jamie Madillc29968b2016-01-20 11:17:23 -05002947 Texture *texture = getTargetTexture(target);
Jamie Madill8897afa2017-02-06 17:17:23 -05002948 handleError(texture->copySubImage(this, target, level, destOffset, sourceArea, framebuffer));
Jamie Madillc29968b2016-01-20 11:17:23 -05002949}
2950
2951void Context::framebufferTexture2D(GLenum target,
2952 GLenum attachment,
2953 GLenum textarget,
2954 GLuint texture,
2955 GLint level)
2956{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002957 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05002958 ASSERT(framebuffer);
2959
2960 if (texture != 0)
2961 {
2962 Texture *textureObj = getTexture(texture);
2963
2964 ImageIndex index = ImageIndex::MakeInvalid();
2965
2966 if (textarget == GL_TEXTURE_2D)
2967 {
2968 index = ImageIndex::Make2D(level);
2969 }
Corentin Wallez13c0dd42017-07-04 18:27:01 -04002970 else if (textarget == GL_TEXTURE_RECTANGLE_ANGLE)
2971 {
2972 index = ImageIndex::MakeRectangle(level);
2973 }
JiangYizhoubddc46b2016-12-09 09:50:51 +08002974 else if (textarget == GL_TEXTURE_2D_MULTISAMPLE)
2975 {
2976 ASSERT(level == 0);
2977 index = ImageIndex::Make2DMultisample();
2978 }
Jamie Madillc29968b2016-01-20 11:17:23 -05002979 else
2980 {
2981 ASSERT(IsCubeMapTextureTarget(textarget));
2982 index = ImageIndex::MakeCube(textarget, level);
2983 }
2984
Jamie Madilla02315b2017-02-23 14:14:47 -05002985 framebuffer->setAttachment(this, GL_TEXTURE, attachment, index, textureObj);
Jamie Madillc29968b2016-01-20 11:17:23 -05002986 }
2987 else
2988 {
Jamie Madilla02315b2017-02-23 14:14:47 -05002989 framebuffer->resetAttachment(this, attachment);
Jamie Madillc29968b2016-01-20 11:17:23 -05002990 }
Jamie Madill60ec6ea2016-01-22 15:27:19 -05002991
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002992 mGLState.setObjectDirty(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05002993}
2994
2995void Context::framebufferRenderbuffer(GLenum target,
2996 GLenum attachment,
2997 GLenum renderbuffertarget,
2998 GLuint renderbuffer)
2999{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003000 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05003001 ASSERT(framebuffer);
3002
3003 if (renderbuffer != 0)
3004 {
3005 Renderbuffer *renderbufferObject = getRenderbuffer(renderbuffer);
Jamie Madilla02315b2017-02-23 14:14:47 -05003006
3007 framebuffer->setAttachment(this, GL_RENDERBUFFER, attachment, gl::ImageIndex::MakeInvalid(),
Jamie Madillc29968b2016-01-20 11:17:23 -05003008 renderbufferObject);
3009 }
3010 else
3011 {
Jamie Madilla02315b2017-02-23 14:14:47 -05003012 framebuffer->resetAttachment(this, attachment);
Jamie Madillc29968b2016-01-20 11:17:23 -05003013 }
Jamie Madill60ec6ea2016-01-22 15:27:19 -05003014
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003015 mGLState.setObjectDirty(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05003016}
3017
3018void Context::framebufferTextureLayer(GLenum target,
3019 GLenum attachment,
3020 GLuint texture,
3021 GLint level,
3022 GLint layer)
3023{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003024 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05003025 ASSERT(framebuffer);
3026
3027 if (texture != 0)
3028 {
3029 Texture *textureObject = getTexture(texture);
3030
3031 ImageIndex index = ImageIndex::MakeInvalid();
3032
3033 if (textureObject->getTarget() == GL_TEXTURE_3D)
3034 {
3035 index = ImageIndex::Make3D(level, layer);
3036 }
3037 else
3038 {
3039 ASSERT(textureObject->getTarget() == GL_TEXTURE_2D_ARRAY);
3040 index = ImageIndex::Make2DArray(level, layer);
3041 }
3042
Jamie Madilla02315b2017-02-23 14:14:47 -05003043 framebuffer->setAttachment(this, GL_TEXTURE, attachment, index, textureObject);
Jamie Madillc29968b2016-01-20 11:17:23 -05003044 }
3045 else
3046 {
Jamie Madilla02315b2017-02-23 14:14:47 -05003047 framebuffer->resetAttachment(this, attachment);
Jamie Madillc29968b2016-01-20 11:17:23 -05003048 }
Jamie Madill60ec6ea2016-01-22 15:27:19 -05003049
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003050 mGLState.setObjectDirty(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05003051}
3052
Martin Radev137032d2017-07-13 10:11:12 +03003053void Context::framebufferTextureMultiviewLayeredANGLE(GLenum target,
3054 GLenum attachment,
3055 GLuint texture,
3056 GLint level,
3057 GLint baseViewIndex,
3058 GLsizei numViews)
3059{
Martin Radev82ef7742017-08-08 17:44:58 +03003060 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
3061 ASSERT(framebuffer);
3062
3063 if (texture != 0)
3064 {
3065 Texture *textureObj = getTexture(texture);
3066
Martin Radev18b75ba2017-08-15 15:50:40 +03003067 ImageIndex index = ImageIndex::Make2DArrayRange(level, baseViewIndex, numViews);
Martin Radev82ef7742017-08-08 17:44:58 +03003068 framebuffer->setAttachmentMultiviewLayered(this, GL_TEXTURE, attachment, index, textureObj,
3069 numViews, baseViewIndex);
3070 }
3071 else
3072 {
3073 framebuffer->resetAttachment(this, attachment);
3074 }
3075
3076 mGLState.setObjectDirty(target);
Martin Radev137032d2017-07-13 10:11:12 +03003077}
3078
3079void Context::framebufferTextureMultiviewSideBySideANGLE(GLenum target,
3080 GLenum attachment,
3081 GLuint texture,
3082 GLint level,
3083 GLsizei numViews,
3084 const GLint *viewportOffsets)
3085{
Martin Radev5dae57b2017-07-14 16:15:55 +03003086 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
3087 ASSERT(framebuffer);
3088
3089 if (texture != 0)
3090 {
3091 Texture *textureObj = getTexture(texture);
3092
3093 ImageIndex index = ImageIndex::Make2D(level);
3094 framebuffer->setAttachmentMultiviewSideBySide(this, GL_TEXTURE, attachment, index,
3095 textureObj, numViews, viewportOffsets);
3096 }
3097 else
3098 {
3099 framebuffer->resetAttachment(this, attachment);
3100 }
3101
3102 mGLState.setObjectDirty(target);
Martin Radev137032d2017-07-13 10:11:12 +03003103}
3104
Jamie Madillc29968b2016-01-20 11:17:23 -05003105void Context::drawBuffers(GLsizei n, const GLenum *bufs)
3106{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003107 Framebuffer *framebuffer = mGLState.getDrawFramebuffer();
Jamie Madillc29968b2016-01-20 11:17:23 -05003108 ASSERT(framebuffer);
3109 framebuffer->setDrawBuffers(n, bufs);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003110 mGLState.setObjectDirty(GL_DRAW_FRAMEBUFFER);
Jamie Madillc29968b2016-01-20 11:17:23 -05003111}
3112
3113void Context::readBuffer(GLenum mode)
3114{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003115 Framebuffer *readFBO = mGLState.getReadFramebuffer();
Jamie Madillc29968b2016-01-20 11:17:23 -05003116 readFBO->setReadBuffer(mode);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003117 mGLState.setObjectDirty(GL_READ_FRAMEBUFFER);
Jamie Madillc29968b2016-01-20 11:17:23 -05003118}
3119
3120void Context::discardFramebuffer(GLenum target, GLsizei numAttachments, const GLenum *attachments)
3121{
Jamie Madill60ec6ea2016-01-22 15:27:19 -05003122 // Only sync the FBO
Jamie Madilldd43e6c2017-03-24 14:18:49 -04003123 mGLState.syncDirtyObject(this, target);
Jamie Madill60ec6ea2016-01-22 15:27:19 -05003124
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003125 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05003126 ASSERT(framebuffer);
3127
3128 // The specification isn't clear what should be done when the framebuffer isn't complete.
3129 // We leave it up to the framebuffer implementation to decide what to do.
Jamie Madill4928b7c2017-06-20 12:57:39 -04003130 handleError(framebuffer->discard(this, numAttachments, attachments));
Jamie Madillc29968b2016-01-20 11:17:23 -05003131}
3132
3133void Context::invalidateFramebuffer(GLenum target,
3134 GLsizei numAttachments,
3135 const GLenum *attachments)
3136{
Jamie Madill60ec6ea2016-01-22 15:27:19 -05003137 // Only sync the FBO
Jamie Madilldd43e6c2017-03-24 14:18:49 -04003138 mGLState.syncDirtyObject(this, target);
Jamie Madill60ec6ea2016-01-22 15:27:19 -05003139
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003140 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05003141 ASSERT(framebuffer);
3142
Jamie Madilldd43e6c2017-03-24 14:18:49 -04003143 if (framebuffer->checkStatus(this) != GL_FRAMEBUFFER_COMPLETE)
Jamie Madillc29968b2016-01-20 11:17:23 -05003144 {
Jamie Madill437fa652016-05-03 15:13:24 -04003145 return;
Jamie Madillc29968b2016-01-20 11:17:23 -05003146 }
Jamie Madill437fa652016-05-03 15:13:24 -04003147
Jamie Madill4928b7c2017-06-20 12:57:39 -04003148 handleError(framebuffer->invalidate(this, numAttachments, attachments));
Jamie Madillc29968b2016-01-20 11:17:23 -05003149}
3150
3151void Context::invalidateSubFramebuffer(GLenum target,
3152 GLsizei numAttachments,
3153 const GLenum *attachments,
3154 GLint x,
3155 GLint y,
3156 GLsizei width,
3157 GLsizei height)
3158{
Jamie Madill60ec6ea2016-01-22 15:27:19 -05003159 // Only sync the FBO
Jamie Madilldd43e6c2017-03-24 14:18:49 -04003160 mGLState.syncDirtyObject(this, target);
Jamie Madill60ec6ea2016-01-22 15:27:19 -05003161
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003162 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05003163 ASSERT(framebuffer);
3164
Jamie Madilldd43e6c2017-03-24 14:18:49 -04003165 if (framebuffer->checkStatus(this) != GL_FRAMEBUFFER_COMPLETE)
Jamie Madillc29968b2016-01-20 11:17:23 -05003166 {
Jamie Madill437fa652016-05-03 15:13:24 -04003167 return;
Jamie Madillc29968b2016-01-20 11:17:23 -05003168 }
Jamie Madill437fa652016-05-03 15:13:24 -04003169
3170 Rectangle area(x, y, width, height);
Jamie Madill4928b7c2017-06-20 12:57:39 -04003171 handleError(framebuffer->invalidateSub(this, numAttachments, attachments, area));
Jamie Madillc29968b2016-01-20 11:17:23 -05003172}
3173
Jamie Madill73a84962016-02-12 09:27:23 -05003174void Context::texImage2D(GLenum target,
3175 GLint level,
3176 GLint internalformat,
3177 GLsizei width,
3178 GLsizei height,
3179 GLint border,
3180 GLenum format,
3181 GLenum type,
Jamie Madill876429b2017-04-20 15:46:24 -04003182 const void *pixels)
Jamie Madill73a84962016-02-12 09:27:23 -05003183{
Jamie Madillad9f24e2016-02-12 09:27:24 -05003184 syncStateForTexImage();
Jamie Madill73a84962016-02-12 09:27:23 -05003185
3186 Extents size(width, height, 1);
3187 Texture *texture =
3188 getTargetTexture(IsCubeMapTextureTarget(target) ? GL_TEXTURE_CUBE_MAP : target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003189 handleError(texture->setImage(this, mGLState.getUnpackState(), target, level, internalformat,
3190 size, format, type, reinterpret_cast<const uint8_t *>(pixels)));
Jamie Madill73a84962016-02-12 09:27:23 -05003191}
3192
3193void Context::texImage3D(GLenum target,
3194 GLint level,
3195 GLint internalformat,
3196 GLsizei width,
3197 GLsizei height,
3198 GLsizei depth,
3199 GLint border,
3200 GLenum format,
3201 GLenum type,
Jamie Madill876429b2017-04-20 15:46:24 -04003202 const void *pixels)
Jamie Madill73a84962016-02-12 09:27:23 -05003203{
Jamie Madillad9f24e2016-02-12 09:27:24 -05003204 syncStateForTexImage();
Jamie Madill73a84962016-02-12 09:27:23 -05003205
3206 Extents size(width, height, depth);
3207 Texture *texture = getTargetTexture(target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003208 handleError(texture->setImage(this, mGLState.getUnpackState(), target, level, internalformat,
3209 size, format, type, reinterpret_cast<const uint8_t *>(pixels)));
Jamie Madill73a84962016-02-12 09:27:23 -05003210}
3211
3212void Context::texSubImage2D(GLenum target,
3213 GLint level,
3214 GLint xoffset,
3215 GLint yoffset,
3216 GLsizei width,
3217 GLsizei height,
3218 GLenum format,
3219 GLenum type,
Jamie Madill876429b2017-04-20 15:46:24 -04003220 const void *pixels)
Jamie Madill73a84962016-02-12 09:27:23 -05003221{
3222 // Zero sized uploads are valid but no-ops
3223 if (width == 0 || height == 0)
3224 {
3225 return;
3226 }
3227
Jamie Madillad9f24e2016-02-12 09:27:24 -05003228 syncStateForTexImage();
Jamie Madill73a84962016-02-12 09:27:23 -05003229
3230 Box area(xoffset, yoffset, 0, width, height, 1);
3231 Texture *texture =
3232 getTargetTexture(IsCubeMapTextureTarget(target) ? GL_TEXTURE_CUBE_MAP : target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003233 handleError(texture->setSubImage(this, mGLState.getUnpackState(), target, level, area, format,
3234 type, reinterpret_cast<const uint8_t *>(pixels)));
Jamie Madill73a84962016-02-12 09:27:23 -05003235}
3236
3237void Context::texSubImage3D(GLenum target,
3238 GLint level,
3239 GLint xoffset,
3240 GLint yoffset,
3241 GLint zoffset,
3242 GLsizei width,
3243 GLsizei height,
3244 GLsizei depth,
3245 GLenum format,
3246 GLenum type,
Jamie Madill876429b2017-04-20 15:46:24 -04003247 const void *pixels)
Jamie Madill73a84962016-02-12 09:27:23 -05003248{
3249 // Zero sized uploads are valid but no-ops
3250 if (width == 0 || height == 0 || depth == 0)
3251 {
3252 return;
3253 }
3254
Jamie Madillad9f24e2016-02-12 09:27:24 -05003255 syncStateForTexImage();
Jamie Madill73a84962016-02-12 09:27:23 -05003256
3257 Box area(xoffset, yoffset, zoffset, width, height, depth);
3258 Texture *texture = getTargetTexture(target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003259 handleError(texture->setSubImage(this, mGLState.getUnpackState(), target, level, area, format,
3260 type, reinterpret_cast<const uint8_t *>(pixels)));
Jamie Madill73a84962016-02-12 09:27:23 -05003261}
3262
3263void Context::compressedTexImage2D(GLenum target,
3264 GLint level,
3265 GLenum internalformat,
3266 GLsizei width,
3267 GLsizei height,
3268 GLint border,
3269 GLsizei imageSize,
Jamie Madill876429b2017-04-20 15:46:24 -04003270 const void *data)
Jamie Madill73a84962016-02-12 09:27:23 -05003271{
Jamie Madillad9f24e2016-02-12 09:27:24 -05003272 syncStateForTexImage();
Jamie Madill73a84962016-02-12 09:27:23 -05003273
3274 Extents size(width, height, 1);
3275 Texture *texture =
3276 getTargetTexture(IsCubeMapTextureTarget(target) ? GL_TEXTURE_CUBE_MAP : target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003277 handleError(texture->setCompressedImage(this, mGLState.getUnpackState(), target, level,
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003278 internalformat, size, imageSize,
Jamie Madill437fa652016-05-03 15:13:24 -04003279 reinterpret_cast<const uint8_t *>(data)));
Jamie Madill73a84962016-02-12 09:27:23 -05003280}
3281
3282void Context::compressedTexImage3D(GLenum target,
3283 GLint level,
3284 GLenum internalformat,
3285 GLsizei width,
3286 GLsizei height,
3287 GLsizei depth,
3288 GLint border,
3289 GLsizei imageSize,
Jamie Madill876429b2017-04-20 15:46:24 -04003290 const void *data)
Jamie Madill73a84962016-02-12 09:27:23 -05003291{
Jamie Madillad9f24e2016-02-12 09:27:24 -05003292 syncStateForTexImage();
Jamie Madill73a84962016-02-12 09:27:23 -05003293
3294 Extents size(width, height, depth);
3295 Texture *texture = getTargetTexture(target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003296 handleError(texture->setCompressedImage(this, mGLState.getUnpackState(), target, level,
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003297 internalformat, size, imageSize,
Jamie Madill437fa652016-05-03 15:13:24 -04003298 reinterpret_cast<const uint8_t *>(data)));
Jamie Madill73a84962016-02-12 09:27:23 -05003299}
3300
3301void Context::compressedTexSubImage2D(GLenum target,
3302 GLint level,
3303 GLint xoffset,
3304 GLint yoffset,
3305 GLsizei width,
3306 GLsizei height,
3307 GLenum format,
3308 GLsizei imageSize,
Jamie Madill876429b2017-04-20 15:46:24 -04003309 const void *data)
Jamie Madill73a84962016-02-12 09:27:23 -05003310{
Jamie Madillad9f24e2016-02-12 09:27:24 -05003311 syncStateForTexImage();
Jamie Madill73a84962016-02-12 09:27:23 -05003312
3313 Box area(xoffset, yoffset, 0, width, height, 1);
3314 Texture *texture =
3315 getTargetTexture(IsCubeMapTextureTarget(target) ? GL_TEXTURE_CUBE_MAP : target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003316 handleError(texture->setCompressedSubImage(this, mGLState.getUnpackState(), target, level, area,
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003317 format, imageSize,
3318 reinterpret_cast<const uint8_t *>(data)));
Jamie Madill73a84962016-02-12 09:27:23 -05003319}
3320
3321void Context::compressedTexSubImage3D(GLenum target,
3322 GLint level,
3323 GLint xoffset,
3324 GLint yoffset,
3325 GLint zoffset,
3326 GLsizei width,
3327 GLsizei height,
3328 GLsizei depth,
3329 GLenum format,
3330 GLsizei imageSize,
Jamie Madill876429b2017-04-20 15:46:24 -04003331 const void *data)
Jamie Madill73a84962016-02-12 09:27:23 -05003332{
3333 // Zero sized uploads are valid but no-ops
3334 if (width == 0 || height == 0)
3335 {
3336 return;
3337 }
3338
Jamie Madillad9f24e2016-02-12 09:27:24 -05003339 syncStateForTexImage();
Jamie Madill73a84962016-02-12 09:27:23 -05003340
3341 Box area(xoffset, yoffset, zoffset, width, height, depth);
3342 Texture *texture = getTargetTexture(target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003343 handleError(texture->setCompressedSubImage(this, mGLState.getUnpackState(), target, level, area,
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003344 format, imageSize,
3345 reinterpret_cast<const uint8_t *>(data)));
Jamie Madill73a84962016-02-12 09:27:23 -05003346}
3347
Olli Etuaho0f2b1562016-05-13 16:15:35 +03003348void Context::generateMipmap(GLenum target)
3349{
3350 Texture *texture = getTargetTexture(target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003351 handleError(texture->generateMipmap(this));
Olli Etuaho0f2b1562016-05-13 16:15:35 +03003352}
3353
Geoff Lang97073d12016-04-20 10:42:34 -07003354void Context::copyTextureCHROMIUM(GLuint sourceId,
Geoff Langfc72a072017-03-24 14:52:39 -04003355 GLint sourceLevel,
3356 GLenum destTarget,
Geoff Lang97073d12016-04-20 10:42:34 -07003357 GLuint destId,
Geoff Langfc72a072017-03-24 14:52:39 -04003358 GLint destLevel,
Geoff Lang97073d12016-04-20 10:42:34 -07003359 GLint internalFormat,
3360 GLenum destType,
3361 GLboolean unpackFlipY,
3362 GLboolean unpackPremultiplyAlpha,
3363 GLboolean unpackUnmultiplyAlpha)
3364{
3365 syncStateForTexImage();
3366
3367 gl::Texture *sourceTexture = getTexture(sourceId);
3368 gl::Texture *destTexture = getTexture(destId);
Geoff Langfc72a072017-03-24 14:52:39 -04003369 handleError(destTexture->copyTexture(
3370 this, destTarget, destLevel, internalFormat, destType, sourceLevel, unpackFlipY == GL_TRUE,
3371 unpackPremultiplyAlpha == GL_TRUE, unpackUnmultiplyAlpha == GL_TRUE, sourceTexture));
Geoff Lang97073d12016-04-20 10:42:34 -07003372}
3373
3374void Context::copySubTextureCHROMIUM(GLuint sourceId,
Geoff Langfc72a072017-03-24 14:52:39 -04003375 GLint sourceLevel,
3376 GLenum destTarget,
Geoff Lang97073d12016-04-20 10:42:34 -07003377 GLuint destId,
Geoff Langfc72a072017-03-24 14:52:39 -04003378 GLint destLevel,
Geoff Lang97073d12016-04-20 10:42:34 -07003379 GLint xoffset,
3380 GLint yoffset,
3381 GLint x,
3382 GLint y,
3383 GLsizei width,
3384 GLsizei height,
3385 GLboolean unpackFlipY,
3386 GLboolean unpackPremultiplyAlpha,
3387 GLboolean unpackUnmultiplyAlpha)
3388{
3389 // Zero sized copies are valid but no-ops
3390 if (width == 0 || height == 0)
3391 {
3392 return;
3393 }
3394
3395 syncStateForTexImage();
3396
3397 gl::Texture *sourceTexture = getTexture(sourceId);
3398 gl::Texture *destTexture = getTexture(destId);
3399 Offset offset(xoffset, yoffset, 0);
3400 Rectangle area(x, y, width, height);
Geoff Langfc72a072017-03-24 14:52:39 -04003401 handleError(destTexture->copySubTexture(
3402 this, destTarget, destLevel, offset, sourceLevel, area, unpackFlipY == GL_TRUE,
3403 unpackPremultiplyAlpha == GL_TRUE, unpackUnmultiplyAlpha == GL_TRUE, sourceTexture));
Geoff Lang97073d12016-04-20 10:42:34 -07003404}
3405
Geoff Lang47110bf2016-04-20 11:13:22 -07003406void Context::compressedCopyTextureCHROMIUM(GLuint sourceId, GLuint destId)
3407{
3408 syncStateForTexImage();
3409
3410 gl::Texture *sourceTexture = getTexture(sourceId);
3411 gl::Texture *destTexture = getTexture(destId);
Jamie Madill8897afa2017-02-06 17:17:23 -05003412 handleError(destTexture->copyCompressedTexture(this, sourceTexture));
Geoff Lang47110bf2016-04-20 11:13:22 -07003413}
3414
Geoff Lang496c02d2016-10-20 11:38:11 -07003415void Context::getBufferPointerv(GLenum target, GLenum pname, void **params)
Olli Etuaho4f667482016-03-30 15:56:35 +03003416{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003417 Buffer *buffer = mGLState.getTargetBuffer(target);
Olli Etuaho4f667482016-03-30 15:56:35 +03003418 ASSERT(buffer);
3419
Geoff Lang496c02d2016-10-20 11:38:11 -07003420 QueryBufferPointerv(buffer, pname, params);
Olli Etuaho4f667482016-03-30 15:56:35 +03003421}
3422
Jamie Madill876429b2017-04-20 15:46:24 -04003423void *Context::mapBuffer(GLenum target, GLenum access)
Olli Etuaho4f667482016-03-30 15:56:35 +03003424{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003425 Buffer *buffer = mGLState.getTargetBuffer(target);
Olli Etuaho4f667482016-03-30 15:56:35 +03003426 ASSERT(buffer);
3427
Jamie Madill5f56ddb2017-01-13 17:29:55 -05003428 Error error = buffer->map(this, access);
Olli Etuaho4f667482016-03-30 15:56:35 +03003429 if (error.isError())
3430 {
Jamie Madill437fa652016-05-03 15:13:24 -04003431 handleError(error);
Olli Etuaho4f667482016-03-30 15:56:35 +03003432 return nullptr;
3433 }
3434
3435 return buffer->getMapPointer();
3436}
3437
3438GLboolean Context::unmapBuffer(GLenum target)
3439{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003440 Buffer *buffer = mGLState.getTargetBuffer(target);
Olli Etuaho4f667482016-03-30 15:56:35 +03003441 ASSERT(buffer);
3442
3443 GLboolean result;
Jamie Madill5f56ddb2017-01-13 17:29:55 -05003444 Error error = buffer->unmap(this, &result);
Olli Etuaho4f667482016-03-30 15:56:35 +03003445 if (error.isError())
3446 {
Jamie Madill437fa652016-05-03 15:13:24 -04003447 handleError(error);
Olli Etuaho4f667482016-03-30 15:56:35 +03003448 return GL_FALSE;
3449 }
3450
3451 return result;
3452}
3453
Jamie Madill876429b2017-04-20 15:46:24 -04003454void *Context::mapBufferRange(GLenum target, GLintptr offset, GLsizeiptr length, GLbitfield access)
Olli Etuaho4f667482016-03-30 15:56:35 +03003455{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003456 Buffer *buffer = mGLState.getTargetBuffer(target);
Olli Etuaho4f667482016-03-30 15:56:35 +03003457 ASSERT(buffer);
3458
Jamie Madill5f56ddb2017-01-13 17:29:55 -05003459 Error error = buffer->mapRange(this, offset, length, access);
Olli Etuaho4f667482016-03-30 15:56:35 +03003460 if (error.isError())
3461 {
Jamie Madill437fa652016-05-03 15:13:24 -04003462 handleError(error);
Olli Etuaho4f667482016-03-30 15:56:35 +03003463 return nullptr;
3464 }
3465
3466 return buffer->getMapPointer();
3467}
3468
3469void Context::flushMappedBufferRange(GLenum /*target*/, GLintptr /*offset*/, GLsizeiptr /*length*/)
3470{
3471 // We do not currently support a non-trivial implementation of FlushMappedBufferRange
3472}
3473
Jamie Madillad9f24e2016-02-12 09:27:24 -05003474void Context::syncStateForReadPixels()
3475{
3476 syncRendererState(mReadPixelsDirtyBits, mReadPixelsDirtyObjects);
3477}
3478
3479void Context::syncStateForTexImage()
3480{
3481 syncRendererState(mTexImageDirtyBits, mTexImageDirtyObjects);
3482}
3483
3484void Context::syncStateForClear()
3485{
3486 syncRendererState(mClearDirtyBits, mClearDirtyObjects);
3487}
3488
3489void Context::syncStateForBlit()
3490{
3491 syncRendererState(mBlitDirtyBits, mBlitDirtyObjects);
3492}
3493
Jamie Madillc20ab272016-06-09 07:20:46 -07003494void Context::activeTexture(GLenum texture)
3495{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003496 mGLState.setActiveSampler(texture - GL_TEXTURE0);
Jamie Madillc20ab272016-06-09 07:20:46 -07003497}
3498
Jamie Madill876429b2017-04-20 15:46:24 -04003499void Context::blendColor(GLfloat red, GLfloat green, GLfloat blue, GLfloat alpha)
Jamie Madillc20ab272016-06-09 07:20:46 -07003500{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003501 mGLState.setBlendColor(clamp01(red), clamp01(green), clamp01(blue), clamp01(alpha));
Jamie Madillc20ab272016-06-09 07:20:46 -07003502}
3503
Jamie Madill8a9e4bc2016-11-13 20:02:12 -05003504void Context::blendEquation(GLenum mode)
3505{
3506 mGLState.setBlendEquation(mode, mode);
3507}
3508
Jamie Madillc20ab272016-06-09 07:20:46 -07003509void Context::blendEquationSeparate(GLenum modeRGB, GLenum modeAlpha)
3510{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003511 mGLState.setBlendEquation(modeRGB, modeAlpha);
Jamie Madillc20ab272016-06-09 07:20:46 -07003512}
3513
Jamie Madill8a9e4bc2016-11-13 20:02:12 -05003514void Context::blendFunc(GLenum sfactor, GLenum dfactor)
3515{
3516 mGLState.setBlendFactors(sfactor, dfactor, sfactor, dfactor);
3517}
3518
Jamie Madillc20ab272016-06-09 07:20:46 -07003519void Context::blendFuncSeparate(GLenum srcRGB, GLenum dstRGB, GLenum srcAlpha, GLenum dstAlpha)
3520{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003521 mGLState.setBlendFactors(srcRGB, dstRGB, srcAlpha, dstAlpha);
Jamie Madillc20ab272016-06-09 07:20:46 -07003522}
3523
Jamie Madill876429b2017-04-20 15:46:24 -04003524void Context::clearColor(GLfloat red, GLfloat green, GLfloat blue, GLfloat alpha)
Jamie Madillc20ab272016-06-09 07:20:46 -07003525{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003526 mGLState.setColorClearValue(red, green, blue, alpha);
Jamie Madillc20ab272016-06-09 07:20:46 -07003527}
3528
Jamie Madill876429b2017-04-20 15:46:24 -04003529void Context::clearDepthf(GLfloat depth)
Jamie Madillc20ab272016-06-09 07:20:46 -07003530{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003531 mGLState.setDepthClearValue(depth);
Jamie Madillc20ab272016-06-09 07:20:46 -07003532}
3533
3534void Context::clearStencil(GLint s)
3535{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003536 mGLState.setStencilClearValue(s);
Jamie Madillc20ab272016-06-09 07:20:46 -07003537}
3538
3539void Context::colorMask(GLboolean red, GLboolean green, GLboolean blue, GLboolean alpha)
3540{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003541 mGLState.setColorMask(red == GL_TRUE, green == GL_TRUE, blue == GL_TRUE, alpha == GL_TRUE);
Jamie Madillc20ab272016-06-09 07:20:46 -07003542}
3543
3544void Context::cullFace(GLenum mode)
3545{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003546 mGLState.setCullMode(mode);
Jamie Madillc20ab272016-06-09 07:20:46 -07003547}
3548
3549void Context::depthFunc(GLenum func)
3550{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003551 mGLState.setDepthFunc(func);
Jamie Madillc20ab272016-06-09 07:20:46 -07003552}
3553
3554void Context::depthMask(GLboolean flag)
3555{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003556 mGLState.setDepthMask(flag != GL_FALSE);
Jamie Madillc20ab272016-06-09 07:20:46 -07003557}
3558
Jamie Madill876429b2017-04-20 15:46:24 -04003559void Context::depthRangef(GLfloat zNear, GLfloat zFar)
Jamie Madillc20ab272016-06-09 07:20:46 -07003560{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003561 mGLState.setDepthRange(zNear, zFar);
Jamie Madillc20ab272016-06-09 07:20:46 -07003562}
3563
3564void Context::disable(GLenum cap)
3565{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003566 mGLState.setEnableFeature(cap, false);
Jamie Madillc20ab272016-06-09 07:20:46 -07003567}
3568
3569void Context::disableVertexAttribArray(GLuint index)
3570{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003571 mGLState.setEnableVertexAttribArray(index, false);
Jamie Madillc20ab272016-06-09 07:20:46 -07003572}
3573
3574void Context::enable(GLenum cap)
3575{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003576 mGLState.setEnableFeature(cap, true);
Jamie Madillc20ab272016-06-09 07:20:46 -07003577}
3578
3579void Context::enableVertexAttribArray(GLuint index)
3580{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003581 mGLState.setEnableVertexAttribArray(index, true);
Jamie Madillc20ab272016-06-09 07:20:46 -07003582}
3583
3584void Context::frontFace(GLenum mode)
3585{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003586 mGLState.setFrontFace(mode);
Jamie Madillc20ab272016-06-09 07:20:46 -07003587}
3588
3589void Context::hint(GLenum target, GLenum mode)
3590{
3591 switch (target)
3592 {
3593 case GL_GENERATE_MIPMAP_HINT:
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003594 mGLState.setGenerateMipmapHint(mode);
Jamie Madillc20ab272016-06-09 07:20:46 -07003595 break;
3596
3597 case GL_FRAGMENT_SHADER_DERIVATIVE_HINT_OES:
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003598 mGLState.setFragmentShaderDerivativeHint(mode);
Jamie Madillc20ab272016-06-09 07:20:46 -07003599 break;
3600
3601 default:
3602 UNREACHABLE();
3603 return;
3604 }
3605}
3606
3607void Context::lineWidth(GLfloat width)
3608{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003609 mGLState.setLineWidth(width);
Jamie Madillc20ab272016-06-09 07:20:46 -07003610}
3611
3612void Context::pixelStorei(GLenum pname, GLint param)
3613{
3614 switch (pname)
3615 {
3616 case GL_UNPACK_ALIGNMENT:
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003617 mGLState.setUnpackAlignment(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003618 break;
3619
3620 case GL_PACK_ALIGNMENT:
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003621 mGLState.setPackAlignment(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003622 break;
3623
3624 case GL_PACK_REVERSE_ROW_ORDER_ANGLE:
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003625 mGLState.setPackReverseRowOrder(param != 0);
Jamie Madillc20ab272016-06-09 07:20:46 -07003626 break;
3627
3628 case GL_UNPACK_ROW_LENGTH:
Martin Radev1be913c2016-07-11 17:59:16 +03003629 ASSERT((getClientMajorVersion() >= 3) || getExtensions().unpackSubimage);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003630 mGLState.setUnpackRowLength(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003631 break;
3632
3633 case GL_UNPACK_IMAGE_HEIGHT:
Martin Radev1be913c2016-07-11 17:59:16 +03003634 ASSERT(getClientMajorVersion() >= 3);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003635 mGLState.setUnpackImageHeight(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003636 break;
3637
3638 case GL_UNPACK_SKIP_IMAGES:
Martin Radev1be913c2016-07-11 17:59:16 +03003639 ASSERT(getClientMajorVersion() >= 3);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003640 mGLState.setUnpackSkipImages(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003641 break;
3642
3643 case GL_UNPACK_SKIP_ROWS:
Martin Radev1be913c2016-07-11 17:59:16 +03003644 ASSERT((getClientMajorVersion() >= 3) || getExtensions().unpackSubimage);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003645 mGLState.setUnpackSkipRows(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003646 break;
3647
3648 case GL_UNPACK_SKIP_PIXELS:
Martin Radev1be913c2016-07-11 17:59:16 +03003649 ASSERT((getClientMajorVersion() >= 3) || getExtensions().unpackSubimage);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003650 mGLState.setUnpackSkipPixels(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003651 break;
3652
3653 case GL_PACK_ROW_LENGTH:
Martin Radev1be913c2016-07-11 17:59:16 +03003654 ASSERT((getClientMajorVersion() >= 3) || getExtensions().packSubimage);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003655 mGLState.setPackRowLength(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003656 break;
3657
3658 case GL_PACK_SKIP_ROWS:
Martin Radev1be913c2016-07-11 17:59:16 +03003659 ASSERT((getClientMajorVersion() >= 3) || getExtensions().packSubimage);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003660 mGLState.setPackSkipRows(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003661 break;
3662
3663 case GL_PACK_SKIP_PIXELS:
Martin Radev1be913c2016-07-11 17:59:16 +03003664 ASSERT((getClientMajorVersion() >= 3) || getExtensions().packSubimage);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003665 mGLState.setPackSkipPixels(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003666 break;
3667
3668 default:
3669 UNREACHABLE();
3670 return;
3671 }
3672}
3673
3674void Context::polygonOffset(GLfloat factor, GLfloat units)
3675{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003676 mGLState.setPolygonOffsetParams(factor, units);
Jamie Madillc20ab272016-06-09 07:20:46 -07003677}
3678
Jamie Madill876429b2017-04-20 15:46:24 -04003679void Context::sampleCoverage(GLfloat value, GLboolean invert)
Jamie Madillc20ab272016-06-09 07:20:46 -07003680{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003681 mGLState.setSampleCoverageParams(clamp01(value), invert == GL_TRUE);
Jamie Madillc20ab272016-06-09 07:20:46 -07003682}
3683
3684void Context::scissor(GLint x, GLint y, GLsizei width, GLsizei height)
3685{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003686 mGLState.setScissorParams(x, y, width, height);
Jamie Madillc20ab272016-06-09 07:20:46 -07003687}
3688
3689void Context::stencilFuncSeparate(GLenum face, GLenum func, GLint ref, GLuint mask)
3690{
3691 if (face == GL_FRONT || face == GL_FRONT_AND_BACK)
3692 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003693 mGLState.setStencilParams(func, ref, mask);
Jamie Madillc20ab272016-06-09 07:20:46 -07003694 }
3695
3696 if (face == GL_BACK || face == GL_FRONT_AND_BACK)
3697 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003698 mGLState.setStencilBackParams(func, ref, mask);
Jamie Madillc20ab272016-06-09 07:20:46 -07003699 }
3700}
3701
3702void Context::stencilMaskSeparate(GLenum face, GLuint mask)
3703{
3704 if (face == GL_FRONT || face == GL_FRONT_AND_BACK)
3705 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003706 mGLState.setStencilWritemask(mask);
Jamie Madillc20ab272016-06-09 07:20:46 -07003707 }
3708
3709 if (face == GL_BACK || face == GL_FRONT_AND_BACK)
3710 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003711 mGLState.setStencilBackWritemask(mask);
Jamie Madillc20ab272016-06-09 07:20:46 -07003712 }
3713}
3714
3715void Context::stencilOpSeparate(GLenum face, GLenum fail, GLenum zfail, GLenum zpass)
3716{
3717 if (face == GL_FRONT || face == GL_FRONT_AND_BACK)
3718 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003719 mGLState.setStencilOperations(fail, zfail, zpass);
Jamie Madillc20ab272016-06-09 07:20:46 -07003720 }
3721
3722 if (face == GL_BACK || face == GL_FRONT_AND_BACK)
3723 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003724 mGLState.setStencilBackOperations(fail, zfail, zpass);
Jamie Madillc20ab272016-06-09 07:20:46 -07003725 }
3726}
3727
3728void Context::vertexAttrib1f(GLuint index, GLfloat x)
3729{
3730 GLfloat vals[4] = {x, 0, 0, 1};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003731 mGLState.setVertexAttribf(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003732}
3733
3734void Context::vertexAttrib1fv(GLuint index, const GLfloat *values)
3735{
3736 GLfloat vals[4] = {values[0], 0, 0, 1};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003737 mGLState.setVertexAttribf(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003738}
3739
3740void Context::vertexAttrib2f(GLuint index, GLfloat x, GLfloat y)
3741{
3742 GLfloat vals[4] = {x, y, 0, 1};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003743 mGLState.setVertexAttribf(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003744}
3745
3746void Context::vertexAttrib2fv(GLuint index, const GLfloat *values)
3747{
3748 GLfloat vals[4] = {values[0], values[1], 0, 1};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003749 mGLState.setVertexAttribf(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003750}
3751
3752void Context::vertexAttrib3f(GLuint index, GLfloat x, GLfloat y, GLfloat z)
3753{
3754 GLfloat vals[4] = {x, y, z, 1};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003755 mGLState.setVertexAttribf(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003756}
3757
3758void Context::vertexAttrib3fv(GLuint index, const GLfloat *values)
3759{
3760 GLfloat vals[4] = {values[0], values[1], values[2], 1};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003761 mGLState.setVertexAttribf(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003762}
3763
3764void Context::vertexAttrib4f(GLuint index, GLfloat x, GLfloat y, GLfloat z, GLfloat w)
3765{
3766 GLfloat vals[4] = {x, y, z, w};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003767 mGLState.setVertexAttribf(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003768}
3769
3770void Context::vertexAttrib4fv(GLuint index, const GLfloat *values)
3771{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003772 mGLState.setVertexAttribf(index, values);
Jamie Madillc20ab272016-06-09 07:20:46 -07003773}
3774
3775void Context::vertexAttribPointer(GLuint index,
3776 GLint size,
3777 GLenum type,
3778 GLboolean normalized,
3779 GLsizei stride,
Jamie Madill876429b2017-04-20 15:46:24 -04003780 const void *ptr)
Jamie Madillc20ab272016-06-09 07:20:46 -07003781{
Shaodde78e82017-05-22 14:13:27 +08003782 mGLState.setVertexAttribPointer(this, index, mGLState.getTargetBuffer(GL_ARRAY_BUFFER), size,
3783 type, normalized == GL_TRUE, false, stride, ptr);
Jamie Madillc20ab272016-06-09 07:20:46 -07003784}
3785
Shao80957d92017-02-20 21:25:59 +08003786void Context::vertexAttribFormat(GLuint attribIndex,
3787 GLint size,
3788 GLenum type,
3789 GLboolean normalized,
3790 GLuint relativeOffset)
3791{
3792 mGLState.setVertexAttribFormat(attribIndex, size, type, normalized == GL_TRUE, false,
3793 relativeOffset);
3794}
3795
3796void Context::vertexAttribIFormat(GLuint attribIndex,
3797 GLint size,
3798 GLenum type,
3799 GLuint relativeOffset)
3800{
3801 mGLState.setVertexAttribFormat(attribIndex, size, type, false, true, relativeOffset);
3802}
3803
3804void Context::vertexAttribBinding(GLuint attribIndex, GLuint bindingIndex)
3805{
Shaodde78e82017-05-22 14:13:27 +08003806 mGLState.setVertexAttribBinding(this, attribIndex, bindingIndex);
Shao80957d92017-02-20 21:25:59 +08003807}
3808
3809void Context::setVertexBindingDivisor(GLuint bindingIndex, GLuint divisor)
3810{
3811 mGLState.setVertexBindingDivisor(bindingIndex, divisor);
3812}
3813
Jamie Madillc20ab272016-06-09 07:20:46 -07003814void Context::viewport(GLint x, GLint y, GLsizei width, GLsizei height)
3815{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003816 mGLState.setViewportParams(x, y, width, height);
Jamie Madillc20ab272016-06-09 07:20:46 -07003817}
3818
3819void Context::vertexAttribIPointer(GLuint index,
3820 GLint size,
3821 GLenum type,
3822 GLsizei stride,
Jamie Madill876429b2017-04-20 15:46:24 -04003823 const void *pointer)
Jamie Madillc20ab272016-06-09 07:20:46 -07003824{
Shaodde78e82017-05-22 14:13:27 +08003825 mGLState.setVertexAttribPointer(this, index, mGLState.getTargetBuffer(GL_ARRAY_BUFFER), size,
3826 type, false, true, stride, pointer);
Jamie Madillc20ab272016-06-09 07:20:46 -07003827}
3828
3829void Context::vertexAttribI4i(GLuint index, GLint x, GLint y, GLint z, GLint w)
3830{
3831 GLint vals[4] = {x, y, z, w};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003832 mGLState.setVertexAttribi(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003833}
3834
3835void Context::vertexAttribI4ui(GLuint index, GLuint x, GLuint y, GLuint z, GLuint w)
3836{
3837 GLuint vals[4] = {x, y, z, w};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003838 mGLState.setVertexAttribu(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003839}
3840
3841void Context::vertexAttribI4iv(GLuint index, const GLint *v)
3842{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003843 mGLState.setVertexAttribi(index, v);
Jamie Madillc20ab272016-06-09 07:20:46 -07003844}
3845
3846void Context::vertexAttribI4uiv(GLuint index, const GLuint *v)
3847{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003848 mGLState.setVertexAttribu(index, v);
Jamie Madillc20ab272016-06-09 07:20:46 -07003849}
3850
Jiawei-Shao2597fb62016-12-09 16:38:02 +08003851void Context::getVertexAttribiv(GLuint index, GLenum pname, GLint *params)
3852{
3853 const VertexAttribCurrentValueData &currentValues =
3854 getGLState().getVertexAttribCurrentValue(index);
3855 const VertexArray *vao = getGLState().getVertexArray();
3856 QueryVertexAttribiv(vao->getVertexAttribute(index), vao->getBindingFromAttribIndex(index),
3857 currentValues, pname, params);
3858}
3859
3860void Context::getVertexAttribfv(GLuint index, GLenum pname, GLfloat *params)
3861{
3862 const VertexAttribCurrentValueData &currentValues =
3863 getGLState().getVertexAttribCurrentValue(index);
3864 const VertexArray *vao = getGLState().getVertexArray();
3865 QueryVertexAttribfv(vao->getVertexAttribute(index), vao->getBindingFromAttribIndex(index),
3866 currentValues, pname, params);
3867}
3868
3869void Context::getVertexAttribIiv(GLuint index, GLenum pname, GLint *params)
3870{
3871 const VertexAttribCurrentValueData &currentValues =
3872 getGLState().getVertexAttribCurrentValue(index);
3873 const VertexArray *vao = getGLState().getVertexArray();
3874 QueryVertexAttribIiv(vao->getVertexAttribute(index), vao->getBindingFromAttribIndex(index),
3875 currentValues, pname, params);
3876}
3877
3878void Context::getVertexAttribIuiv(GLuint index, GLenum pname, GLuint *params)
3879{
3880 const VertexAttribCurrentValueData &currentValues =
3881 getGLState().getVertexAttribCurrentValue(index);
3882 const VertexArray *vao = getGLState().getVertexArray();
3883 QueryVertexAttribIuiv(vao->getVertexAttribute(index), vao->getBindingFromAttribIndex(index),
3884 currentValues, pname, params);
3885}
3886
Jamie Madill876429b2017-04-20 15:46:24 -04003887void Context::getVertexAttribPointerv(GLuint index, GLenum pname, void **pointer)
Jiawei-Shao2597fb62016-12-09 16:38:02 +08003888{
3889 const VertexAttribute &attrib = getGLState().getVertexArray()->getVertexAttribute(index);
3890 QueryVertexAttribPointerv(attrib, pname, pointer);
3891}
3892
Jamie Madillc20ab272016-06-09 07:20:46 -07003893void Context::debugMessageControl(GLenum source,
3894 GLenum type,
3895 GLenum severity,
3896 GLsizei count,
3897 const GLuint *ids,
3898 GLboolean enabled)
3899{
3900 std::vector<GLuint> idVector(ids, ids + count);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003901 mGLState.getDebug().setMessageControl(source, type, severity, std::move(idVector),
3902 (enabled != GL_FALSE));
Jamie Madillc20ab272016-06-09 07:20:46 -07003903}
3904
3905void Context::debugMessageInsert(GLenum source,
3906 GLenum type,
3907 GLuint id,
3908 GLenum severity,
3909 GLsizei length,
3910 const GLchar *buf)
3911{
3912 std::string msg(buf, (length > 0) ? static_cast<size_t>(length) : strlen(buf));
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003913 mGLState.getDebug().insertMessage(source, type, id, severity, std::move(msg));
Jamie Madillc20ab272016-06-09 07:20:46 -07003914}
3915
3916void Context::debugMessageCallback(GLDEBUGPROCKHR callback, const void *userParam)
3917{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003918 mGLState.getDebug().setCallback(callback, userParam);
Jamie Madillc20ab272016-06-09 07:20:46 -07003919}
3920
3921GLuint Context::getDebugMessageLog(GLuint count,
3922 GLsizei bufSize,
3923 GLenum *sources,
3924 GLenum *types,
3925 GLuint *ids,
3926 GLenum *severities,
3927 GLsizei *lengths,
3928 GLchar *messageLog)
3929{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003930 return static_cast<GLuint>(mGLState.getDebug().getMessages(count, bufSize, sources, types, ids,
3931 severities, lengths, messageLog));
Jamie Madillc20ab272016-06-09 07:20:46 -07003932}
3933
3934void Context::pushDebugGroup(GLenum source, GLuint id, GLsizei length, const GLchar *message)
3935{
3936 std::string msg(message, (length > 0) ? static_cast<size_t>(length) : strlen(message));
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003937 mGLState.getDebug().pushGroup(source, id, std::move(msg));
Jamie Madillc20ab272016-06-09 07:20:46 -07003938}
3939
3940void Context::popDebugGroup()
3941{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003942 mGLState.getDebug().popGroup();
Jamie Madillc20ab272016-06-09 07:20:46 -07003943}
3944
Jamie Madill876429b2017-04-20 15:46:24 -04003945void Context::bufferData(GLenum target, GLsizeiptr size, const void *data, GLenum usage)
Jamie Madill29639852016-09-02 15:00:09 -04003946{
3947 Buffer *buffer = mGLState.getTargetBuffer(target);
3948 ASSERT(buffer);
Jamie Madillb8353b02017-01-25 12:57:21 -08003949 handleError(buffer->bufferData(this, target, data, size, usage));
Jamie Madill29639852016-09-02 15:00:09 -04003950}
3951
Jamie Madill876429b2017-04-20 15:46:24 -04003952void Context::bufferSubData(GLenum target, GLintptr offset, GLsizeiptr size, const void *data)
Jamie Madill29639852016-09-02 15:00:09 -04003953{
3954 if (data == nullptr)
3955 {
3956 return;
3957 }
3958
3959 Buffer *buffer = mGLState.getTargetBuffer(target);
3960 ASSERT(buffer);
Jamie Madillb8353b02017-01-25 12:57:21 -08003961 handleError(buffer->bufferSubData(this, target, data, size, offset));
Jamie Madill29639852016-09-02 15:00:09 -04003962}
3963
Jamie Madillef300b12016-10-07 15:12:09 -04003964void Context::attachShader(GLuint program, GLuint shader)
3965{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05003966 auto programObject = mState.mShaderPrograms->getProgram(program);
3967 auto shaderObject = mState.mShaderPrograms->getShader(shader);
Jamie Madillef300b12016-10-07 15:12:09 -04003968 ASSERT(programObject && shaderObject);
3969 programObject->attachShader(shaderObject);
3970}
3971
Kenneth Russellf2f6f652016-10-05 19:53:23 -07003972const Workarounds &Context::getWorkarounds() const
3973{
3974 return mWorkarounds;
3975}
3976
Jamie Madillb0817d12016-11-01 15:48:31 -04003977void Context::copyBufferSubData(GLenum readTarget,
3978 GLenum writeTarget,
3979 GLintptr readOffset,
3980 GLintptr writeOffset,
3981 GLsizeiptr size)
3982{
3983 // if size is zero, the copy is a successful no-op
3984 if (size == 0)
3985 {
3986 return;
3987 }
3988
3989 // TODO(jmadill): cache these.
3990 Buffer *readBuffer = mGLState.getTargetBuffer(readTarget);
3991 Buffer *writeBuffer = mGLState.getTargetBuffer(writeTarget);
3992
Jamie Madill5f56ddb2017-01-13 17:29:55 -05003993 handleError(writeBuffer->copyBufferSubData(this, readBuffer, readOffset, writeOffset, size));
Jamie Madillb0817d12016-11-01 15:48:31 -04003994}
3995
Jamie Madill01a80ee2016-11-07 12:06:18 -05003996void Context::bindAttribLocation(GLuint program, GLuint index, const GLchar *name)
3997{
3998 Program *programObject = getProgram(program);
3999 // TODO(jmadill): Re-use this from the validation if possible.
4000 ASSERT(programObject);
4001 programObject->bindAttributeLocation(index, name);
4002}
4003
4004void Context::bindBuffer(GLenum target, GLuint buffer)
4005{
4006 switch (target)
4007 {
4008 case GL_ARRAY_BUFFER:
4009 bindArrayBuffer(buffer);
4010 break;
4011 case GL_ELEMENT_ARRAY_BUFFER:
4012 bindElementArrayBuffer(buffer);
4013 break;
4014 case GL_COPY_READ_BUFFER:
4015 bindCopyReadBuffer(buffer);
4016 break;
4017 case GL_COPY_WRITE_BUFFER:
4018 bindCopyWriteBuffer(buffer);
4019 break;
4020 case GL_PIXEL_PACK_BUFFER:
4021 bindPixelPackBuffer(buffer);
4022 break;
4023 case GL_PIXEL_UNPACK_BUFFER:
4024 bindPixelUnpackBuffer(buffer);
4025 break;
4026 case GL_UNIFORM_BUFFER:
4027 bindGenericUniformBuffer(buffer);
4028 break;
4029 case GL_TRANSFORM_FEEDBACK_BUFFER:
4030 bindGenericTransformFeedbackBuffer(buffer);
4031 break;
Geoff Lang3b573612016-10-31 14:08:10 -04004032 case GL_ATOMIC_COUNTER_BUFFER:
Jiajia Qin6eafb042016-12-27 17:04:07 +08004033 bindGenericAtomicCounterBuffer(buffer);
Geoff Lang3b573612016-10-31 14:08:10 -04004034 break;
4035 case GL_SHADER_STORAGE_BUFFER:
Jiajia Qinf546e7d2017-03-27 14:12:59 +08004036 bindGenericShaderStorageBuffer(buffer);
Geoff Lang3b573612016-10-31 14:08:10 -04004037 break;
4038 case GL_DRAW_INDIRECT_BUFFER:
Jiajia Qin9d7d0b12016-11-29 16:30:31 +08004039 bindDrawIndirectBuffer(buffer);
Geoff Lang3b573612016-10-31 14:08:10 -04004040 break;
4041 case GL_DISPATCH_INDIRECT_BUFFER:
Geoff Lang9f090372016-12-02 10:20:43 -05004042 if (buffer != 0)
4043 {
4044 // Binding buffers to this binding point is not implemented yet.
4045 UNIMPLEMENTED();
4046 }
Geoff Lang3b573612016-10-31 14:08:10 -04004047 break;
Jamie Madill01a80ee2016-11-07 12:06:18 -05004048
4049 default:
4050 UNREACHABLE();
4051 break;
4052 }
4053}
4054
Jiajia Qin6eafb042016-12-27 17:04:07 +08004055void Context::bindBufferBase(GLenum target, GLuint index, GLuint buffer)
4056{
4057 bindBufferRange(target, index, buffer, 0, 0);
4058}
4059
4060void Context::bindBufferRange(GLenum target,
4061 GLuint index,
4062 GLuint buffer,
4063 GLintptr offset,
4064 GLsizeiptr size)
4065{
4066 switch (target)
4067 {
4068 case GL_TRANSFORM_FEEDBACK_BUFFER:
4069 bindIndexedTransformFeedbackBuffer(buffer, index, offset, size);
4070 bindGenericTransformFeedbackBuffer(buffer);
4071 break;
4072 case GL_UNIFORM_BUFFER:
4073 bindIndexedUniformBuffer(buffer, index, offset, size);
4074 bindGenericUniformBuffer(buffer);
4075 break;
4076 case GL_ATOMIC_COUNTER_BUFFER:
4077 bindIndexedAtomicCounterBuffer(buffer, index, offset, size);
4078 bindGenericAtomicCounterBuffer(buffer);
4079 break;
4080 case GL_SHADER_STORAGE_BUFFER:
Jiajia Qinf546e7d2017-03-27 14:12:59 +08004081 bindIndexedShaderStorageBuffer(buffer, index, offset, size);
4082 bindGenericShaderStorageBuffer(buffer);
Jiajia Qin6eafb042016-12-27 17:04:07 +08004083 break;
4084 default:
4085 UNREACHABLE();
4086 break;
4087 }
4088}
4089
Jamie Madill01a80ee2016-11-07 12:06:18 -05004090void Context::bindFramebuffer(GLenum target, GLuint framebuffer)
4091{
4092 if (target == GL_READ_FRAMEBUFFER || target == GL_FRAMEBUFFER)
4093 {
4094 bindReadFramebuffer(framebuffer);
4095 }
4096
4097 if (target == GL_DRAW_FRAMEBUFFER || target == GL_FRAMEBUFFER)
4098 {
4099 bindDrawFramebuffer(framebuffer);
4100 }
4101}
4102
4103void Context::bindRenderbuffer(GLenum target, GLuint renderbuffer)
4104{
4105 ASSERT(target == GL_RENDERBUFFER);
4106 Renderbuffer *object =
Geoff Lang4ddf5af2016-12-01 14:30:44 -05004107 mState.mRenderbuffers->checkRenderbufferAllocation(mImplementation.get(), renderbuffer);
Jamie Madill4928b7c2017-06-20 12:57:39 -04004108 mGLState.setRenderbufferBinding(this, object);
Jamie Madill01a80ee2016-11-07 12:06:18 -05004109}
4110
JiangYizhoubddc46b2016-12-09 09:50:51 +08004111void Context::texStorage2DMultisample(GLenum target,
4112 GLsizei samples,
4113 GLenum internalformat,
4114 GLsizei width,
4115 GLsizei height,
4116 GLboolean fixedsamplelocations)
4117{
4118 Extents size(width, height, 1);
4119 Texture *texture = getTargetTexture(target);
Jamie Madill8897afa2017-02-06 17:17:23 -05004120 handleError(texture->setStorageMultisample(this, target, samples, internalformat, size,
JiangYizhoubddc46b2016-12-09 09:50:51 +08004121 fixedsamplelocations));
4122}
4123
4124void Context::getMultisamplefv(GLenum pname, GLuint index, GLfloat *val)
4125{
Jamie Madilldd43e6c2017-03-24 14:18:49 -04004126 mGLState.syncDirtyObject(this, GL_READ_FRAMEBUFFER);
JiangYizhoubddc46b2016-12-09 09:50:51 +08004127 const Framebuffer *framebuffer = mGLState.getReadFramebuffer();
4128
4129 switch (pname)
4130 {
4131 case GL_SAMPLE_POSITION:
4132 handleError(framebuffer->getSamplePosition(index, val));
4133 break;
4134 default:
4135 UNREACHABLE();
4136 }
4137}
4138
Jamie Madille8fb6402017-02-14 17:56:40 -05004139void Context::renderbufferStorage(GLenum target,
4140 GLenum internalformat,
4141 GLsizei width,
4142 GLsizei height)
4143{
Jamie Madill4e0e6f82017-02-17 11:06:03 -05004144 // Hack for the special WebGL 1 "DEPTH_STENCIL" internal format.
4145 GLenum convertedInternalFormat = getConvertedRenderbufferFormat(internalformat);
4146
Jamie Madille8fb6402017-02-14 17:56:40 -05004147 Renderbuffer *renderbuffer = mGLState.getCurrentRenderbuffer();
Jamie Madill4928b7c2017-06-20 12:57:39 -04004148 handleError(renderbuffer->setStorage(this, convertedInternalFormat, width, height));
Jamie Madille8fb6402017-02-14 17:56:40 -05004149}
4150
4151void Context::renderbufferStorageMultisample(GLenum target,
4152 GLsizei samples,
4153 GLenum internalformat,
4154 GLsizei width,
4155 GLsizei height)
4156{
Jamie Madill4e0e6f82017-02-17 11:06:03 -05004157 // Hack for the special WebGL 1 "DEPTH_STENCIL" internal format.
4158 GLenum convertedInternalFormat = getConvertedRenderbufferFormat(internalformat);
Jamie Madille8fb6402017-02-14 17:56:40 -05004159
4160 Renderbuffer *renderbuffer = mGLState.getCurrentRenderbuffer();
Jamie Madill4e0e6f82017-02-17 11:06:03 -05004161 handleError(
Jamie Madill4928b7c2017-06-20 12:57:39 -04004162 renderbuffer->setStorageMultisample(this, samples, convertedInternalFormat, width, height));
Jamie Madille8fb6402017-02-14 17:56:40 -05004163}
4164
Geoff Lang38f2cfb2017-04-11 15:23:08 -04004165void Context::getSynciv(GLsync sync, GLenum pname, GLsizei bufSize, GLsizei *length, GLint *values)
4166{
4167 const FenceSync *syncObject = getFenceSync(sync);
Geoff Lang82483b92017-04-11 15:33:00 -04004168 handleError(QuerySynciv(syncObject, pname, bufSize, length, values));
Geoff Lang38f2cfb2017-04-11 15:23:08 -04004169}
4170
JiangYizhoue18e6392017-02-20 10:32:23 +08004171void Context::getFramebufferParameteriv(GLenum target, GLenum pname, GLint *params)
4172{
4173 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
4174 QueryFramebufferParameteriv(framebuffer, pname, params);
4175}
4176
4177void Context::setFramebufferParameteri(GLenum target, GLenum pname, GLint param)
4178{
4179 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
4180 SetFramebufferParameteri(framebuffer, pname, param);
4181}
4182
Jamie Madillb3f26b92017-07-19 15:07:41 -04004183Error Context::getScratchBuffer(size_t requstedSizeBytes,
4184 angle::MemoryBuffer **scratchBufferOut) const
Jamie Madille14951e2017-03-09 18:55:16 -05004185{
Jamie Madillb3f26b92017-07-19 15:07:41 -04004186 if (!mScratchBuffer.get(requstedSizeBytes, scratchBufferOut))
4187 {
4188 return OutOfMemory() << "Failed to allocate internal buffer.";
4189 }
4190 return NoError();
4191}
4192
4193Error Context::getZeroFilledBuffer(size_t requstedSizeBytes,
4194 angle::MemoryBuffer **zeroBufferOut) const
4195{
4196 if (!mZeroFilledBuffer.getInitialized(requstedSizeBytes, zeroBufferOut, 0))
Jamie Madille14951e2017-03-09 18:55:16 -05004197 {
Yuly Novikovc4d18aa2017-03-09 18:45:02 -05004198 return OutOfMemory() << "Failed to allocate internal buffer.";
Jamie Madille14951e2017-03-09 18:55:16 -05004199 }
Yuly Novikovc4d18aa2017-03-09 18:45:02 -05004200 return NoError();
Jamie Madille14951e2017-03-09 18:55:16 -05004201}
4202
Xinghua Cao2b396592017-03-29 15:36:04 +08004203void Context::dispatchCompute(GLuint numGroupsX, GLuint numGroupsY, GLuint numGroupsZ)
4204{
4205 if (numGroupsX == 0u || numGroupsY == 0u || numGroupsZ == 0u)
4206 {
4207 return;
4208 }
4209
Jamie Madillfe548342017-06-19 11:13:24 -04004210 mImplementation->dispatchCompute(this, numGroupsX, numGroupsY, numGroupsZ);
Xinghua Cao2b396592017-03-29 15:36:04 +08004211}
4212
JiangYizhou165361c2017-06-07 14:56:57 +08004213void Context::texStorage2D(GLenum target,
4214 GLsizei levels,
4215 GLenum internalFormat,
4216 GLsizei width,
4217 GLsizei height)
4218{
4219 Extents size(width, height, 1);
4220 Texture *texture = getTargetTexture(target);
4221 handleError(texture->setStorage(this, target, levels, internalFormat, size));
4222}
4223
4224void Context::texStorage3D(GLenum target,
4225 GLsizei levels,
4226 GLenum internalFormat,
4227 GLsizei width,
4228 GLsizei height,
4229 GLsizei depth)
4230{
4231 Extents size(width, height, depth);
4232 Texture *texture = getTargetTexture(target);
4233 handleError(texture->setStorage(this, target, levels, internalFormat, size));
4234}
4235
Jamie Madillc1d770e2017-04-13 17:31:24 -04004236GLenum Context::checkFramebufferStatus(GLenum target)
4237{
4238 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
4239 ASSERT(framebuffer);
4240
4241 return framebuffer->checkStatus(this);
4242}
4243
4244void Context::compileShader(GLuint shader)
4245{
4246 Shader *shaderObject = GetValidShader(this, shader);
4247 if (!shaderObject)
4248 {
4249 return;
4250 }
4251 shaderObject->compile(this);
4252}
4253
4254void Context::deleteBuffers(GLsizei n, const GLuint *buffers)
4255{
4256 for (int i = 0; i < n; i++)
4257 {
4258 deleteBuffer(buffers[i]);
4259 }
4260}
4261
4262void Context::deleteFramebuffers(GLsizei n, const GLuint *framebuffers)
4263{
4264 for (int i = 0; i < n; i++)
4265 {
4266 if (framebuffers[i] != 0)
4267 {
4268 deleteFramebuffer(framebuffers[i]);
4269 }
4270 }
4271}
4272
4273void Context::deleteRenderbuffers(GLsizei n, const GLuint *renderbuffers)
4274{
4275 for (int i = 0; i < n; i++)
4276 {
4277 deleteRenderbuffer(renderbuffers[i]);
4278 }
4279}
4280
4281void Context::deleteTextures(GLsizei n, const GLuint *textures)
4282{
4283 for (int i = 0; i < n; i++)
4284 {
4285 if (textures[i] != 0)
4286 {
4287 deleteTexture(textures[i]);
4288 }
4289 }
4290}
4291
4292void Context::detachShader(GLuint program, GLuint shader)
4293{
4294 Program *programObject = getProgram(program);
4295 ASSERT(programObject);
4296
4297 Shader *shaderObject = getShader(shader);
4298 ASSERT(shaderObject);
4299
4300 programObject->detachShader(this, shaderObject);
4301}
4302
4303void Context::genBuffers(GLsizei n, GLuint *buffers)
4304{
4305 for (int i = 0; i < n; i++)
4306 {
4307 buffers[i] = createBuffer();
4308 }
4309}
4310
4311void Context::genFramebuffers(GLsizei n, GLuint *framebuffers)
4312{
4313 for (int i = 0; i < n; i++)
4314 {
4315 framebuffers[i] = createFramebuffer();
4316 }
4317}
4318
4319void Context::genRenderbuffers(GLsizei n, GLuint *renderbuffers)
4320{
4321 for (int i = 0; i < n; i++)
4322 {
4323 renderbuffers[i] = createRenderbuffer();
4324 }
4325}
4326
4327void Context::genTextures(GLsizei n, GLuint *textures)
4328{
4329 for (int i = 0; i < n; i++)
4330 {
4331 textures[i] = createTexture();
4332 }
4333}
4334
4335void Context::getActiveAttrib(GLuint program,
4336 GLuint index,
4337 GLsizei bufsize,
4338 GLsizei *length,
4339 GLint *size,
4340 GLenum *type,
4341 GLchar *name)
4342{
4343 Program *programObject = getProgram(program);
4344 ASSERT(programObject);
4345 programObject->getActiveAttribute(index, bufsize, length, size, type, name);
4346}
4347
4348void Context::getActiveUniform(GLuint program,
4349 GLuint index,
4350 GLsizei bufsize,
4351 GLsizei *length,
4352 GLint *size,
4353 GLenum *type,
4354 GLchar *name)
4355{
4356 Program *programObject = getProgram(program);
4357 ASSERT(programObject);
4358 programObject->getActiveUniform(index, bufsize, length, size, type, name);
4359}
4360
4361void Context::getAttachedShaders(GLuint program, GLsizei maxcount, GLsizei *count, GLuint *shaders)
4362{
4363 Program *programObject = getProgram(program);
4364 ASSERT(programObject);
4365 programObject->getAttachedShaders(maxcount, count, shaders);
4366}
4367
4368GLint Context::getAttribLocation(GLuint program, const GLchar *name)
4369{
4370 Program *programObject = getProgram(program);
4371 ASSERT(programObject);
4372 return programObject->getAttributeLocation(name);
4373}
4374
4375void Context::getBooleanv(GLenum pname, GLboolean *params)
4376{
4377 GLenum nativeType;
4378 unsigned int numParams = 0;
4379 getQueryParameterInfo(pname, &nativeType, &numParams);
4380
4381 if (nativeType == GL_BOOL)
4382 {
4383 getBooleanvImpl(pname, params);
4384 }
4385 else
4386 {
4387 CastStateValues(this, nativeType, pname, numParams, params);
4388 }
4389}
4390
4391void Context::getFloatv(GLenum pname, GLfloat *params)
4392{
4393 GLenum nativeType;
4394 unsigned int numParams = 0;
4395 getQueryParameterInfo(pname, &nativeType, &numParams);
4396
4397 if (nativeType == GL_FLOAT)
4398 {
4399 getFloatvImpl(pname, params);
4400 }
4401 else
4402 {
4403 CastStateValues(this, nativeType, pname, numParams, params);
4404 }
4405}
4406
4407void Context::getIntegerv(GLenum pname, GLint *params)
4408{
4409 GLenum nativeType;
4410 unsigned int numParams = 0;
4411 getQueryParameterInfo(pname, &nativeType, &numParams);
4412
4413 if (nativeType == GL_INT)
4414 {
4415 getIntegervImpl(pname, params);
4416 }
4417 else
4418 {
4419 CastStateValues(this, nativeType, pname, numParams, params);
4420 }
4421}
4422
4423void Context::getProgramiv(GLuint program, GLenum pname, GLint *params)
4424{
4425 Program *programObject = getProgram(program);
4426 ASSERT(programObject);
Jamie Madillffe00c02017-06-27 16:26:55 -04004427 QueryProgramiv(this, programObject, pname, params);
Jamie Madillc1d770e2017-04-13 17:31:24 -04004428}
4429
Jamie Madillbe849e42017-05-02 15:49:00 -04004430void Context::getProgramInfoLog(GLuint program, GLsizei bufsize, GLsizei *length, GLchar *infolog)
Jamie Madillc1d770e2017-04-13 17:31:24 -04004431{
4432 Program *programObject = getProgram(program);
4433 ASSERT(programObject);
4434 programObject->getInfoLog(bufsize, length, infolog);
4435}
4436
4437void Context::getShaderiv(GLuint shader, GLenum pname, GLint *params)
4438{
4439 Shader *shaderObject = getShader(shader);
4440 ASSERT(shaderObject);
Jamie Madillbd044ed2017-06-05 12:59:21 -04004441 QueryShaderiv(this, shaderObject, pname, params);
Jamie Madillc1d770e2017-04-13 17:31:24 -04004442}
4443
4444void Context::getShaderInfoLog(GLuint shader, GLsizei bufsize, GLsizei *length, GLchar *infolog)
4445{
4446 Shader *shaderObject = getShader(shader);
4447 ASSERT(shaderObject);
Jamie Madillbd044ed2017-06-05 12:59:21 -04004448 shaderObject->getInfoLog(this, bufsize, length, infolog);
Jamie Madillc1d770e2017-04-13 17:31:24 -04004449}
4450
4451void Context::getShaderPrecisionFormat(GLenum shadertype,
4452 GLenum precisiontype,
4453 GLint *range,
4454 GLint *precision)
4455{
4456 // TODO(jmadill): Compute shaders.
4457
4458 switch (shadertype)
4459 {
4460 case GL_VERTEX_SHADER:
4461 switch (precisiontype)
4462 {
4463 case GL_LOW_FLOAT:
4464 mCaps.vertexLowpFloat.get(range, precision);
4465 break;
4466 case GL_MEDIUM_FLOAT:
4467 mCaps.vertexMediumpFloat.get(range, precision);
4468 break;
4469 case GL_HIGH_FLOAT:
4470 mCaps.vertexHighpFloat.get(range, precision);
4471 break;
4472
4473 case GL_LOW_INT:
4474 mCaps.vertexLowpInt.get(range, precision);
4475 break;
4476 case GL_MEDIUM_INT:
4477 mCaps.vertexMediumpInt.get(range, precision);
4478 break;
4479 case GL_HIGH_INT:
4480 mCaps.vertexHighpInt.get(range, precision);
4481 break;
4482
4483 default:
4484 UNREACHABLE();
4485 return;
4486 }
4487 break;
4488
4489 case GL_FRAGMENT_SHADER:
4490 switch (precisiontype)
4491 {
4492 case GL_LOW_FLOAT:
4493 mCaps.fragmentLowpFloat.get(range, precision);
4494 break;
4495 case GL_MEDIUM_FLOAT:
4496 mCaps.fragmentMediumpFloat.get(range, precision);
4497 break;
4498 case GL_HIGH_FLOAT:
4499 mCaps.fragmentHighpFloat.get(range, precision);
4500 break;
4501
4502 case GL_LOW_INT:
4503 mCaps.fragmentLowpInt.get(range, precision);
4504 break;
4505 case GL_MEDIUM_INT:
4506 mCaps.fragmentMediumpInt.get(range, precision);
4507 break;
4508 case GL_HIGH_INT:
4509 mCaps.fragmentHighpInt.get(range, precision);
4510 break;
4511
4512 default:
4513 UNREACHABLE();
4514 return;
4515 }
4516 break;
4517
4518 default:
4519 UNREACHABLE();
4520 return;
4521 }
4522}
4523
4524void Context::getShaderSource(GLuint shader, GLsizei bufsize, GLsizei *length, GLchar *source)
4525{
4526 Shader *shaderObject = getShader(shader);
4527 ASSERT(shaderObject);
4528 shaderObject->getSource(bufsize, length, source);
4529}
4530
4531void Context::getUniformfv(GLuint program, GLint location, GLfloat *params)
4532{
4533 Program *programObject = getProgram(program);
4534 ASSERT(programObject);
4535 programObject->getUniformfv(location, params);
4536}
4537
4538void Context::getUniformiv(GLuint program, GLint location, GLint *params)
4539{
4540 Program *programObject = getProgram(program);
4541 ASSERT(programObject);
4542 programObject->getUniformiv(location, params);
4543}
4544
4545GLint Context::getUniformLocation(GLuint program, const GLchar *name)
4546{
4547 Program *programObject = getProgram(program);
4548 ASSERT(programObject);
4549 return programObject->getUniformLocation(name);
4550}
4551
4552GLboolean Context::isBuffer(GLuint buffer)
4553{
4554 if (buffer == 0)
4555 {
4556 return GL_FALSE;
4557 }
4558
4559 return (getBuffer(buffer) ? GL_TRUE : GL_FALSE);
4560}
4561
4562GLboolean Context::isEnabled(GLenum cap)
4563{
4564 return mGLState.getEnableFeature(cap);
4565}
4566
4567GLboolean Context::isFramebuffer(GLuint framebuffer)
4568{
4569 if (framebuffer == 0)
4570 {
4571 return GL_FALSE;
4572 }
4573
4574 return (getFramebuffer(framebuffer) ? GL_TRUE : GL_FALSE);
4575}
4576
4577GLboolean Context::isProgram(GLuint program)
4578{
4579 if (program == 0)
4580 {
4581 return GL_FALSE;
4582 }
4583
4584 return (getProgram(program) ? GL_TRUE : GL_FALSE);
4585}
4586
4587GLboolean Context::isRenderbuffer(GLuint renderbuffer)
4588{
4589 if (renderbuffer == 0)
4590 {
4591 return GL_FALSE;
4592 }
4593
4594 return (getRenderbuffer(renderbuffer) ? GL_TRUE : GL_FALSE);
4595}
4596
4597GLboolean Context::isShader(GLuint shader)
4598{
4599 if (shader == 0)
4600 {
4601 return GL_FALSE;
4602 }
4603
4604 return (getShader(shader) ? GL_TRUE : GL_FALSE);
4605}
4606
4607GLboolean Context::isTexture(GLuint texture)
4608{
4609 if (texture == 0)
4610 {
4611 return GL_FALSE;
4612 }
4613
4614 return (getTexture(texture) ? GL_TRUE : GL_FALSE);
4615}
4616
4617void Context::linkProgram(GLuint program)
4618{
4619 Program *programObject = getProgram(program);
4620 ASSERT(programObject);
4621 handleError(programObject->link(this));
4622}
4623
4624void Context::releaseShaderCompiler()
4625{
Jamie Madill4928b7c2017-06-20 12:57:39 -04004626 mCompiler.set(this, nullptr);
Jamie Madillc1d770e2017-04-13 17:31:24 -04004627}
4628
4629void Context::shaderBinary(GLsizei n,
4630 const GLuint *shaders,
4631 GLenum binaryformat,
Jamie Madill876429b2017-04-20 15:46:24 -04004632 const void *binary,
Jamie Madillc1d770e2017-04-13 17:31:24 -04004633 GLsizei length)
4634{
4635 // No binary shader formats are supported.
4636 UNIMPLEMENTED();
4637}
4638
4639void Context::shaderSource(GLuint shader,
4640 GLsizei count,
4641 const GLchar *const *string,
4642 const GLint *length)
4643{
4644 Shader *shaderObject = getShader(shader);
4645 ASSERT(shaderObject);
4646 shaderObject->setSource(count, string, length);
4647}
4648
4649void Context::stencilFunc(GLenum func, GLint ref, GLuint mask)
4650{
4651 stencilFuncSeparate(GL_FRONT_AND_BACK, func, ref, mask);
4652}
4653
4654void Context::stencilMask(GLuint mask)
4655{
4656 stencilMaskSeparate(GL_FRONT_AND_BACK, mask);
4657}
4658
4659void Context::stencilOp(GLenum fail, GLenum zfail, GLenum zpass)
4660{
4661 stencilOpSeparate(GL_FRONT_AND_BACK, fail, zfail, zpass);
4662}
4663
4664void Context::uniform1f(GLint location, GLfloat x)
4665{
4666 Program *program = mGLState.getProgram();
4667 program->setUniform1fv(location, 1, &x);
4668}
4669
4670void Context::uniform1fv(GLint location, GLsizei count, const GLfloat *v)
4671{
4672 Program *program = mGLState.getProgram();
4673 program->setUniform1fv(location, count, v);
4674}
4675
4676void Context::uniform1i(GLint location, GLint x)
4677{
4678 Program *program = mGLState.getProgram();
4679 program->setUniform1iv(location, 1, &x);
4680}
4681
4682void Context::uniform1iv(GLint location, GLsizei count, const GLint *v)
4683{
4684 Program *program = mGLState.getProgram();
4685 program->setUniform1iv(location, count, v);
4686}
4687
4688void Context::uniform2f(GLint location, GLfloat x, GLfloat y)
4689{
4690 GLfloat xy[2] = {x, y};
4691 Program *program = mGLState.getProgram();
4692 program->setUniform2fv(location, 1, xy);
4693}
4694
4695void Context::uniform2fv(GLint location, GLsizei count, const GLfloat *v)
4696{
4697 Program *program = mGLState.getProgram();
4698 program->setUniform2fv(location, count, v);
4699}
4700
4701void Context::uniform2i(GLint location, GLint x, GLint y)
4702{
4703 GLint xy[2] = {x, y};
4704 Program *program = mGLState.getProgram();
4705 program->setUniform2iv(location, 1, xy);
4706}
4707
4708void Context::uniform2iv(GLint location, GLsizei count, const GLint *v)
4709{
4710 Program *program = mGLState.getProgram();
4711 program->setUniform2iv(location, count, v);
4712}
4713
4714void Context::uniform3f(GLint location, GLfloat x, GLfloat y, GLfloat z)
4715{
4716 GLfloat xyz[3] = {x, y, z};
4717 Program *program = mGLState.getProgram();
4718 program->setUniform3fv(location, 1, xyz);
4719}
4720
4721void Context::uniform3fv(GLint location, GLsizei count, const GLfloat *v)
4722{
4723 Program *program = mGLState.getProgram();
4724 program->setUniform3fv(location, count, v);
4725}
4726
4727void Context::uniform3i(GLint location, GLint x, GLint y, GLint z)
4728{
4729 GLint xyz[3] = {x, y, z};
4730 Program *program = mGLState.getProgram();
4731 program->setUniform3iv(location, 1, xyz);
4732}
4733
4734void Context::uniform3iv(GLint location, GLsizei count, const GLint *v)
4735{
4736 Program *program = mGLState.getProgram();
4737 program->setUniform3iv(location, count, v);
4738}
4739
4740void Context::uniform4f(GLint location, GLfloat x, GLfloat y, GLfloat z, GLfloat w)
4741{
4742 GLfloat xyzw[4] = {x, y, z, w};
4743 Program *program = mGLState.getProgram();
4744 program->setUniform4fv(location, 1, xyzw);
4745}
4746
4747void Context::uniform4fv(GLint location, GLsizei count, const GLfloat *v)
4748{
4749 Program *program = mGLState.getProgram();
4750 program->setUniform4fv(location, count, v);
4751}
4752
4753void Context::uniform4i(GLint location, GLint x, GLint y, GLint z, GLint w)
4754{
4755 GLint xyzw[4] = {x, y, z, w};
4756 Program *program = mGLState.getProgram();
4757 program->setUniform4iv(location, 1, xyzw);
4758}
4759
4760void Context::uniform4iv(GLint location, GLsizei count, const GLint *v)
4761{
4762 Program *program = mGLState.getProgram();
4763 program->setUniform4iv(location, count, v);
4764}
4765
4766void Context::uniformMatrix2fv(GLint location,
4767 GLsizei count,
4768 GLboolean transpose,
4769 const GLfloat *value)
4770{
4771 Program *program = mGLState.getProgram();
4772 program->setUniformMatrix2fv(location, count, transpose, value);
4773}
4774
4775void Context::uniformMatrix3fv(GLint location,
4776 GLsizei count,
4777 GLboolean transpose,
4778 const GLfloat *value)
4779{
4780 Program *program = mGLState.getProgram();
4781 program->setUniformMatrix3fv(location, count, transpose, value);
4782}
4783
4784void Context::uniformMatrix4fv(GLint location,
4785 GLsizei count,
4786 GLboolean transpose,
4787 const GLfloat *value)
4788{
4789 Program *program = mGLState.getProgram();
4790 program->setUniformMatrix4fv(location, count, transpose, value);
4791}
4792
4793void Context::validateProgram(GLuint program)
4794{
4795 Program *programObject = getProgram(program);
4796 ASSERT(programObject);
4797 programObject->validate(mCaps);
4798}
4799
Jamie Madilld04908b2017-06-09 14:15:35 -04004800void Context::getProgramBinary(GLuint program,
4801 GLsizei bufSize,
4802 GLsizei *length,
4803 GLenum *binaryFormat,
4804 void *binary)
4805{
4806 Program *programObject = getProgram(program);
4807 ASSERT(programObject != nullptr);
4808
4809 handleError(programObject->saveBinary(this, binaryFormat, binary, bufSize, length));
4810}
4811
4812void Context::programBinary(GLuint program, GLenum binaryFormat, const void *binary, GLsizei length)
4813{
4814 Program *programObject = getProgram(program);
4815 ASSERT(programObject != nullptr);
Jamie Madillb6664922017-07-25 12:55:04 -04004816
Jamie Madilld04908b2017-06-09 14:15:35 -04004817 handleError(programObject->loadBinary(this, binaryFormat, binary, length));
4818}
4819
Jamie Madillff325f12017-08-26 15:06:05 -04004820void Context::uniform1ui(GLint location, GLuint v0)
4821{
4822 Program *program = mGLState.getProgram();
4823 program->setUniform1uiv(location, 1, &v0);
4824}
4825
4826void Context::uniform2ui(GLint location, GLuint v0, GLuint v1)
4827{
4828 Program *program = mGLState.getProgram();
4829 const GLuint xy[] = {v0, v1};
4830 program->setUniform2uiv(location, 1, xy);
4831}
4832
4833void Context::uniform3ui(GLint location, GLuint v0, GLuint v1, GLuint v2)
4834{
4835 Program *program = mGLState.getProgram();
4836 const GLuint xyz[] = {v0, v1, v2};
4837 program->setUniform3uiv(location, 1, xyz);
4838}
4839
4840void Context::uniform4ui(GLint location, GLuint v0, GLuint v1, GLuint v2, GLuint v3)
4841{
4842 Program *program = mGLState.getProgram();
4843 const GLuint xyzw[] = {v0, v1, v2, v3};
4844 program->setUniform4uiv(location, 1, xyzw);
4845}
4846
4847void Context::uniform1uiv(GLint location, GLsizei count, const GLuint *value)
4848{
4849 Program *program = mGLState.getProgram();
4850 program->setUniform1uiv(location, count, value);
4851}
4852void Context::uniform2uiv(GLint location, GLsizei count, const GLuint *value)
4853{
4854 Program *program = mGLState.getProgram();
4855 program->setUniform2uiv(location, count, value);
4856}
4857
4858void Context::uniform3uiv(GLint location, GLsizei count, const GLuint *value)
4859{
4860 Program *program = mGLState.getProgram();
4861 program->setUniform3uiv(location, count, value);
4862}
4863
4864void Context::uniform4uiv(GLint location, GLsizei count, const GLuint *value)
4865{
4866 Program *program = mGLState.getProgram();
4867 program->setUniform4uiv(location, count, value);
4868}
4869
Jamie Madillf0e04492017-08-26 15:28:42 -04004870void Context::genQueries(GLsizei n, GLuint *ids)
4871{
4872 for (GLsizei i = 0; i < n; i++)
4873 {
4874 GLuint handle = mQueryHandleAllocator.allocate();
4875 mQueryMap.assign(handle, nullptr);
4876 ids[i] = handle;
4877 }
4878}
4879
4880void Context::deleteQueries(GLsizei n, const GLuint *ids)
4881{
4882 for (int i = 0; i < n; i++)
4883 {
4884 GLuint query = ids[i];
4885
4886 Query *queryObject = nullptr;
4887 if (mQueryMap.erase(query, &queryObject))
4888 {
4889 mQueryHandleAllocator.release(query);
4890 if (queryObject)
4891 {
4892 queryObject->release(this);
4893 }
4894 }
4895 }
4896}
4897
4898GLboolean Context::isQuery(GLuint id)
4899{
4900 return (getQuery(id, false, GL_NONE) != nullptr) ? GL_TRUE : GL_FALSE;
4901}
4902
Jamie Madillc8c95812017-08-26 18:40:09 -04004903void Context::uniformMatrix2x3fv(GLint location,
4904 GLsizei count,
4905 GLboolean transpose,
4906 const GLfloat *value)
4907{
4908 Program *program = mGLState.getProgram();
4909 program->setUniformMatrix2x3fv(location, count, transpose, value);
4910}
4911
4912void Context::uniformMatrix3x2fv(GLint location,
4913 GLsizei count,
4914 GLboolean transpose,
4915 const GLfloat *value)
4916{
4917 Program *program = mGLState.getProgram();
4918 program->setUniformMatrix3x2fv(location, count, transpose, value);
4919}
4920
4921void Context::uniformMatrix2x4fv(GLint location,
4922 GLsizei count,
4923 GLboolean transpose,
4924 const GLfloat *value)
4925{
4926 Program *program = mGLState.getProgram();
4927 program->setUniformMatrix2x4fv(location, count, transpose, value);
4928}
4929
4930void Context::uniformMatrix4x2fv(GLint location,
4931 GLsizei count,
4932 GLboolean transpose,
4933 const GLfloat *value)
4934{
4935 Program *program = mGLState.getProgram();
4936 program->setUniformMatrix4x2fv(location, count, transpose, value);
4937}
4938
4939void Context::uniformMatrix3x4fv(GLint location,
4940 GLsizei count,
4941 GLboolean transpose,
4942 const GLfloat *value)
4943{
4944 Program *program = mGLState.getProgram();
4945 program->setUniformMatrix3x4fv(location, count, transpose, value);
4946}
4947
4948void Context::uniformMatrix4x3fv(GLint location,
4949 GLsizei count,
4950 GLboolean transpose,
4951 const GLfloat *value)
4952{
4953 Program *program = mGLState.getProgram();
4954 program->setUniformMatrix4x3fv(location, count, transpose, value);
4955}
4956
Jamie Madilld7576732017-08-26 18:49:50 -04004957void Context::deleteVertexArrays(GLsizei n, const GLuint *arrays)
4958{
4959 for (int arrayIndex = 0; arrayIndex < n; arrayIndex++)
4960 {
4961 GLuint vertexArray = arrays[arrayIndex];
4962
4963 if (arrays[arrayIndex] != 0)
4964 {
4965 VertexArray *vertexArrayObject = nullptr;
4966 if (mVertexArrayMap.erase(vertexArray, &vertexArrayObject))
4967 {
4968 if (vertexArrayObject != nullptr)
4969 {
4970 detachVertexArray(vertexArray);
4971 vertexArrayObject->onDestroy(this);
4972 }
4973
4974 mVertexArrayHandleAllocator.release(vertexArray);
4975 }
4976 }
4977 }
4978}
4979
4980void Context::genVertexArrays(GLsizei n, GLuint *arrays)
4981{
4982 for (int arrayIndex = 0; arrayIndex < n; arrayIndex++)
4983 {
4984 GLuint vertexArray = mVertexArrayHandleAllocator.allocate();
4985 mVertexArrayMap.assign(vertexArray, nullptr);
4986 arrays[arrayIndex] = vertexArray;
4987 }
4988}
4989
4990bool Context::isVertexArray(GLuint array)
4991{
4992 if (array == 0)
4993 {
4994 return GL_FALSE;
4995 }
4996
4997 VertexArray *vao = getVertexArray(array);
4998 return (vao != nullptr ? GL_TRUE : GL_FALSE);
4999}
5000
Jamie Madillf0dcb8b2017-08-26 19:05:13 -04005001void Context::endTransformFeedback()
5002{
5003 TransformFeedback *transformFeedback = mGLState.getCurrentTransformFeedback();
5004 transformFeedback->end(this);
5005}
5006
5007void Context::transformFeedbackVaryings(GLuint program,
5008 GLsizei count,
5009 const GLchar *const *varyings,
5010 GLenum bufferMode)
5011{
5012 Program *programObject = getProgram(program);
5013 ASSERT(programObject);
5014 programObject->setTransformFeedbackVaryings(count, varyings, bufferMode);
5015}
5016
5017void Context::getTransformFeedbackVarying(GLuint program,
5018 GLuint index,
5019 GLsizei bufSize,
5020 GLsizei *length,
5021 GLsizei *size,
5022 GLenum *type,
5023 GLchar *name)
5024{
5025 Program *programObject = getProgram(program);
5026 ASSERT(programObject);
5027 programObject->getTransformFeedbackVarying(index, bufSize, length, size, type, name);
5028}
5029
5030void Context::deleteTransformFeedbacks(GLsizei n, const GLuint *ids)
5031{
5032 for (int i = 0; i < n; i++)
5033 {
5034 GLuint transformFeedback = ids[i];
5035 if (transformFeedback == 0)
5036 {
5037 continue;
5038 }
5039
5040 TransformFeedback *transformFeedbackObject = nullptr;
5041 if (mTransformFeedbackMap.erase(transformFeedback, &transformFeedbackObject))
5042 {
5043 if (transformFeedbackObject != nullptr)
5044 {
5045 detachTransformFeedback(transformFeedback);
5046 transformFeedbackObject->release(this);
5047 }
5048
5049 mTransformFeedbackHandleAllocator.release(transformFeedback);
5050 }
5051 }
5052}
5053
5054void Context::genTransformFeedbacks(GLsizei n, GLuint *ids)
5055{
5056 for (int i = 0; i < n; i++)
5057 {
5058 GLuint transformFeedback = mTransformFeedbackHandleAllocator.allocate();
5059 mTransformFeedbackMap.assign(transformFeedback, nullptr);
5060 ids[i] = transformFeedback;
5061 }
5062}
5063
5064bool Context::isTransformFeedback(GLuint id)
5065{
5066 if (id == 0)
5067 {
5068 // The 3.0.4 spec [section 6.1.11] states that if ID is zero, IsTransformFeedback
5069 // returns FALSE
5070 return GL_FALSE;
5071 }
5072
5073 const TransformFeedback *transformFeedback = getTransformFeedback(id);
5074 return ((transformFeedback != nullptr) ? GL_TRUE : GL_FALSE);
5075}
5076
5077void Context::pauseTransformFeedback()
5078{
5079 TransformFeedback *transformFeedback = mGLState.getCurrentTransformFeedback();
5080 transformFeedback->pause();
5081}
5082
5083void Context::resumeTransformFeedback()
5084{
5085 TransformFeedback *transformFeedback = mGLState.getCurrentTransformFeedback();
5086 transformFeedback->resume();
5087}
5088
Jamie Madill12e957f2017-08-26 21:42:26 -04005089void Context::getUniformuiv(GLuint program, GLint location, GLuint *params)
5090{
5091 const Program *programObject = getProgram(program);
5092 programObject->getUniformuiv(location, params);
5093}
5094
5095GLint Context::getFragDataLocation(GLuint program, const GLchar *name)
5096{
5097 const Program *programObject = getProgram(program);
5098 return programObject->getFragDataLocation(name);
5099}
5100
5101void Context::getUniformIndices(GLuint program,
5102 GLsizei uniformCount,
5103 const GLchar *const *uniformNames,
5104 GLuint *uniformIndices)
5105{
5106 const Program *programObject = getProgram(program);
5107 if (!programObject->isLinked())
5108 {
5109 for (int uniformId = 0; uniformId < uniformCount; uniformId++)
5110 {
5111 uniformIndices[uniformId] = GL_INVALID_INDEX;
5112 }
5113 }
5114 else
5115 {
5116 for (int uniformId = 0; uniformId < uniformCount; uniformId++)
5117 {
5118 uniformIndices[uniformId] = programObject->getUniformIndex(uniformNames[uniformId]);
5119 }
5120 }
5121}
5122
5123void Context::getActiveUniformsiv(GLuint program,
5124 GLsizei uniformCount,
5125 const GLuint *uniformIndices,
5126 GLenum pname,
5127 GLint *params)
5128{
5129 const Program *programObject = getProgram(program);
5130 for (int uniformId = 0; uniformId < uniformCount; uniformId++)
5131 {
5132 const GLuint index = uniformIndices[uniformId];
5133 params[uniformId] = programObject->getActiveUniformi(index, pname);
5134 }
5135}
5136
5137GLuint Context::getUniformBlockIndex(GLuint program, const GLchar *uniformBlockName)
5138{
5139 const Program *programObject = getProgram(program);
5140 return programObject->getUniformBlockIndex(uniformBlockName);
5141}
5142
5143void Context::getActiveUniformBlockiv(GLuint program,
5144 GLuint uniformBlockIndex,
5145 GLenum pname,
5146 GLint *params)
5147{
5148 const Program *programObject = getProgram(program);
5149 QueryActiveUniformBlockiv(programObject, uniformBlockIndex, pname, params);
5150}
5151
5152void Context::getActiveUniformBlockName(GLuint program,
5153 GLuint uniformBlockIndex,
5154 GLsizei bufSize,
5155 GLsizei *length,
5156 GLchar *uniformBlockName)
5157{
5158 const Program *programObject = getProgram(program);
5159 programObject->getActiveUniformBlockName(uniformBlockIndex, bufSize, length, uniformBlockName);
5160}
5161
5162void Context::uniformBlockBinding(GLuint program,
5163 GLuint uniformBlockIndex,
5164 GLuint uniformBlockBinding)
5165{
5166 Program *programObject = getProgram(program);
5167 programObject->bindUniformBlock(uniformBlockIndex, uniformBlockBinding);
5168}
5169
Jamie Madill7f0c5a42017-08-26 22:43:26 -04005170GLsync Context::fenceSync(GLenum condition, GLbitfield flags)
5171{
5172 GLuint handle = mState.mFenceSyncs->createFenceSync(mImplementation.get());
5173 GLsync fenceSync = reinterpret_cast<GLsync>(static_cast<uintptr_t>(handle));
5174
5175 FenceSync *fenceSyncObject = getFenceSync(fenceSync);
5176 Error error = fenceSyncObject->set(condition, flags);
5177 if (error.isError())
5178 {
5179 deleteSync(fenceSync);
5180 handleError(error);
5181 return nullptr;
5182 }
5183
5184 return fenceSync;
5185}
5186
5187GLboolean Context::isSync(GLsync sync)
5188{
5189 return (getFenceSync(sync) != nullptr);
5190}
5191
5192GLenum Context::clientWaitSync(GLsync sync, GLbitfield flags, GLuint64 timeout)
5193{
5194 FenceSync *syncObject = getFenceSync(sync);
5195
5196 GLenum result = GL_WAIT_FAILED;
5197 handleError(syncObject->clientWait(flags, timeout, &result));
5198 return result;
5199}
5200
5201void Context::waitSync(GLsync sync, GLbitfield flags, GLuint64 timeout)
5202{
5203 FenceSync *syncObject = getFenceSync(sync);
5204 handleError(syncObject->serverWait(flags, timeout));
5205}
5206
5207void Context::getInteger64v(GLenum pname, GLint64 *params)
5208{
5209 GLenum nativeType = GL_NONE;
5210 unsigned int numParams = 0;
5211 getQueryParameterInfo(pname, &nativeType, &numParams);
5212
5213 if (nativeType == GL_INT_64_ANGLEX)
5214 {
5215 getInteger64vImpl(pname, params);
5216 }
5217 else
5218 {
5219 CastStateValues(this, nativeType, pname, numParams, params);
5220 }
5221}
5222
Jamie Madillc29968b2016-01-20 11:17:23 -05005223} // namespace gl