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